1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "memlayout.h"
17 #include "cgfunc.h"
18
19 namespace maplebe {
20 using namespace maple;
21
22 /*
23 * Go over all outgoing calls in the function body and get the maximum space
24 * needed for storing the actuals based on the actual parameters and the ABI.
25 * These are usually those arguments that cannot be passed
26 * through registers because a call passes more than 8 arguments, or
27 * they cannot be fit in a pair of registers.
28
29 * This assumes that all nesting of statements has been removed,
30 * so that all the statements are at only one block level.
31 */
FindLargestActualArea(int32 & aggCopySize)32 uint32 MemLayout::FindLargestActualArea(int32 &aggCopySize)
33 {
34 CHECK_FATAL(mirFunction != nullptr, "nullptr check");
35 StmtNode *stmt = mirFunction->GetBody()->GetFirst();
36 if (stmt == nullptr) {
37 return 0;
38 }
39 uint32 maxActualSize = 0;
40 uint32 maxParamStackSize = 0; // Size of parameter stack requirement
41 uint32 maxCopyStackSize = 0; // Size of aggregate param stack copy requirement
42 for (; stmt != nullptr; stmt = stmt->GetNext()) {
43 Opcode opCode = stmt->GetOpCode();
44 if ((opCode < OP_call || opCode > OP_intrinsiccallassigned) && opCode != OP_icallproto) {
45 continue;
46 }
47 if (opCode == OP_intrinsiccallwithtype ||
48 opCode == OP_intrinsiccallassigned || opCode == OP_intrinsiccall) {
49 /*
50 * Some intrinsics, such as MPL_ATOMIC_EXCHANGE_PTR, are handled by CG,
51 * and map to machine code sequences. We ignore them because they are not
52 * function calls.
53 */
54 continue;
55 }
56 /*
57 * if the following check fails, most likely it has invoke-custom etc
58 * that is not supported yet
59 */
60 DCHECK((opCode == OP_call || opCode == OP_icall || opCode == OP_icallproto), "Not lowered to call or icall?");
61 int32 copySize;
62 uint32 size =
63 ComputeStackSpaceRequirementForCall(*stmt, copySize, opCode == OP_icall || opCode == OP_icallproto);
64 if (size > maxParamStackSize) {
65 maxParamStackSize = size;
66 }
67 if (static_cast<uint32>(copySize) > maxCopyStackSize) {
68 maxCopyStackSize = static_cast<uint32>(copySize);
69 }
70 if ((maxParamStackSize + maxCopyStackSize) > maxActualSize) {
71 maxActualSize = maxParamStackSize + maxCopyStackSize;
72 }
73 }
74 aggCopySize = static_cast<int32>(maxCopyStackSize);
75 /* GetPointerSize() * 2's pow 2 is 4, set the low 4 bit of maxActualSize to 0 */
76 if (CGOptions::IsArm64ilp32()) {
77 maxActualSize = RoundUp(maxActualSize, k8ByteSize << 1);
78 } else {
79 maxActualSize = RoundUp(maxActualSize, GetPointerSize() << 1);
80 }
81 return maxActualSize;
82 }
83
PhaseRun(maplebe::CGFunc & f)84 bool CgLayoutFrame::PhaseRun(maplebe::CGFunc &f)
85 {
86 f.LayoutStackFrame();
87 return false;
88 }
89 } /* namespace maplebe */
90