1 /**
2 * Copyright (c) 2021-2024 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 /*
17 Compiler -> Pass(Codegen)
18 Encoder = Fabric->getAsm
19
20 Define arch-specific interfaces
21 */
22
23 #include "operands.h"
24 #include "encode.h"
25 #include "compiler/optimizer/code_generator/callconv.h"
26 #include "registers_description.h"
27
28 #ifdef PANDA_COMPILER_TARGET_X86_64
29 #include "amd64/target.h"
30 #endif
31
32 #ifdef PANDA_COMPILER_TARGET_AARCH32
33 #include "aarch32/target.h"
34 #endif
35
36 #ifdef PANDA_COMPILER_TARGET_AARCH64
37 #include "aarch64/target.h"
38 #endif
39
40 #include "asm_printer.h"
41
42 #include "frame_info.h"
43
44 namespace ark::compiler {
BackendSupport(Arch arch)45 bool BackendSupport(Arch arch)
46 {
47 switch (arch) {
48 #ifdef PANDA_COMPILER_TARGET_AARCH32
49 // NOLINTNEXTLINE(bugprone-branch-clone)
50 case Arch::AARCH32: {
51 return true;
52 }
53 #endif
54 #ifdef PANDA_COMPILER_TARGET_AARCH64
55 case Arch::AARCH64: {
56 return true;
57 }
58 #endif
59 #ifdef PANDA_COMPILER_TARGET_X86_64
60 case Arch::X86_64: {
61 return true;
62 }
63 #endif
64 default:
65 return false;
66 }
67 }
68
Create(ArenaAllocator * arenaAllocator,Arch arch,bool printAsm,bool jsNumberCast)69 Encoder *Encoder::Create([[maybe_unused]] ArenaAllocator *arenaAllocator, [[maybe_unused]] Arch arch,
70 [[maybe_unused]] bool printAsm, [[maybe_unused]] bool jsNumberCast)
71 {
72 switch (arch) {
73 #ifdef PANDA_COMPILER_TARGET_AARCH32
74 case Arch::AARCH32: {
75 aarch32::Aarch32Encoder *enc = arenaAllocator->New<aarch32::Aarch32Encoder>(arenaAllocator);
76 enc->SetIsJsNumberCast(jsNumberCast);
77 if (printAsm) {
78 return arenaAllocator->New<aarch32::Aarch32Assembly>(arenaAllocator, enc);
79 }
80 return enc;
81 }
82 #endif
83 #ifdef PANDA_COMPILER_TARGET_AARCH64
84 case Arch::AARCH64: {
85 aarch64::Aarch64Encoder *enc = arenaAllocator->New<aarch64::Aarch64Encoder>(arenaAllocator);
86 enc->SetIsJsNumberCast(jsNumberCast);
87 if (printAsm) {
88 return arenaAllocator->New<aarch64::Aarch64Assembly>(arenaAllocator, enc);
89 }
90 return enc;
91 }
92 #endif
93 #ifdef PANDA_COMPILER_TARGET_X86_64
94 case Arch::X86_64: {
95 amd64::Amd64Encoder *enc =
96 arenaAllocator->New<amd64::Amd64Encoder>(arenaAllocator, Arch::X86_64, jsNumberCast);
97 enc->SetIsJsNumberCast(jsNumberCast);
98 if (printAsm) {
99 return arenaAllocator->New<amd64::Amd64Assembly>(arenaAllocator, enc);
100 }
101 return enc;
102 }
103 #endif
104 default:
105 return nullptr;
106 }
107 }
108
Create(ArenaAllocator * arenaAllocator,Arch arch)109 RegistersDescription *RegistersDescription::Create([[maybe_unused]] ArenaAllocator *arenaAllocator,
110 [[maybe_unused]] Arch arch)
111 {
112 switch (arch) {
113 #ifdef PANDA_COMPILER_TARGET_AARCH32
114 case Arch::AARCH32: {
115 return arenaAllocator->New<aarch32::Aarch32RegisterDescription>(arenaAllocator);
116 }
117 #endif
118
119 #ifdef PANDA_COMPILER_TARGET_AARCH64
120 case Arch::AARCH64: {
121 return arenaAllocator->New<aarch64::Aarch64RegisterDescription>(arenaAllocator);
122 }
123 #endif
124 #ifdef PANDA_COMPILER_TARGET_X86_64
125 case Arch::X86_64: {
126 return arenaAllocator->New<amd64::Amd64RegisterDescription>(arenaAllocator);
127 }
128 #endif
129 default:
130 return nullptr;
131 }
132 }
133
Create(ArenaAllocator * arenaAllocator,Encoder * enc,RegistersDescription * descr,Arch arch,bool isPandaAbi,bool isOsr,bool isDyn,bool printAsm,bool isOptIrtoc)134 CallingConvention *CallingConvention::Create([[maybe_unused]] ArenaAllocator *arenaAllocator,
135 [[maybe_unused]] Encoder *enc,
136 [[maybe_unused]] RegistersDescription *descr, [[maybe_unused]] Arch arch,
137 bool isPandaAbi, bool isOsr, bool isDyn, [[maybe_unused]] bool printAsm,
138 bool isOptIrtoc)
139 {
140 [[maybe_unused]] auto mode = CallConvMode::Panda(isPandaAbi) | CallConvMode::Osr(isOsr) |
141 CallConvMode::DynCall(isDyn) | CallConvMode::OptIrtoc(isOptIrtoc);
142 switch (arch) {
143 #ifdef PANDA_COMPILER_TARGET_AARCH32
144 case Arch::AARCH32: {
145 if (printAsm) {
146 using PrinterType =
147 PrinterCallingConvention<aarch32::Aarch32CallingConvention, aarch32::Aarch32Assembly>;
148 return arenaAllocator->New<PrinterType>(arenaAllocator,
149 reinterpret_cast<aarch32::Aarch32Assembly *>(enc), descr, mode);
150 }
151 return arenaAllocator->New<aarch32::Aarch32CallingConvention>(arenaAllocator, enc, descr, mode);
152 }
153 #endif
154 #ifdef PANDA_COMPILER_TARGET_AARCH64
155 case Arch::AARCH64: {
156 if (printAsm) {
157 using PrinterType =
158 PrinterCallingConvention<aarch64::Aarch64CallingConvention, aarch64::Aarch64Assembly>;
159 return arenaAllocator->New<PrinterType>(arenaAllocator,
160 reinterpret_cast<aarch64::Aarch64Assembly *>(enc), descr, mode);
161 }
162 return arenaAllocator->New<aarch64::Aarch64CallingConvention>(arenaAllocator, enc, descr, mode);
163 }
164 #endif
165 #ifdef PANDA_COMPILER_TARGET_X86_64
166 case Arch::X86_64: {
167 if (printAsm) {
168 using PrinterType = PrinterCallingConvention<amd64::Amd64CallingConvention, amd64::Amd64Assembly>;
169 return arenaAllocator->New<PrinterType>(arenaAllocator, reinterpret_cast<amd64::Amd64Assembly *>(enc),
170 descr, mode);
171 }
172 return arenaAllocator->New<amd64::Amd64CallingConvention>(arenaAllocator, enc, descr, mode);
173 }
174 #endif
175 default:
176 return nullptr;
177 }
178 }
179 } // namespace ark::compiler
180