• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 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 #include "ast/ast.h"
17 
18 #include <cstdlib>
19 
20 #include "util/string_builder.h"
21 
22 namespace OHOS {
23 namespace Idl {
24 AST::TypeStringMap AST::basicTypes_ = {
25     {"void",           new ASTVoidType()     },
26     {"boolean",        new ASTBooleanType()     },
27     {"byte",           new ASTByteType()        },
28     {"short",          new ASTShortType()       },
29     {"int",            new ASTIntegerType()     },
30     {"long",           new ASTLongType()        },
31     {"float",          new ASTFloatType()       },
32     {"double",         new ASTDoubleType()      },
33     {"String",         new ASTStringType()      },
34     {"String16",       new ASTString16Type()    },
35     {"char",           new ASTCharType()        },
36     {"unsigned char",  new ASTUcharType()       },
37     {"unsigned short", new ASTUshortType()      },
38     {"unsigned int",   new ASTUintType()        },
39     {"unsigned long",  new ASTUlongType()       },
40     {"FileDescriptor", new ASTFdType()          },
41     {"Ashmem",         new ASTAshmemType()      },
42     {"NativeBuffer",   new ASTNativeBufferType()},
43     {"Pointer",        new ASTPointerType()     },
44 };
45 
SetIdlFile(const std::string & idlFile)46 void AST::SetIdlFile(const std::string &idlFile)
47 {
48     idlFilePath_ = idlFile;
49 #ifdef __MINGW32__
50     size_t index = idlFilePath_.rfind('\\');
51 #else
52     size_t index = idlFilePath_.rfind('/');
53 #endif
54 
55     size_t end = idlFilePath_.rfind(".idl");
56     if (end == std::string::npos) {
57         end = idlFile.size();
58     }
59 
60     name_ = StringHelper::SubStr(idlFilePath_, (index == std::string::npos) ? 0 : (index + 1), end);
61 }
62 
SetFullName(const std::string & fullName)63 void AST::SetFullName(const std::string &fullName)
64 {
65     std::string name = fullName;
66     size_t start = fullName.rfind("..");
67     if (start != std::string::npos) {
68         name = StringHelper::SubStr(fullName, start + strlen(".."));
69     }
70     size_t index = name.rfind('.');
71     if (index != std::string::npos) {
72         packageName_ = StringHelper::SubStr(name, 0, index);
73         name_ = StringHelper::SubStr(name, index + 1);
74     } else {
75         packageName_ = "";
76         name_ = name;
77     }
78 }
79 
SetPackageName(const std::string & packageName)80 void AST::SetPackageName(const std::string &packageName)
81 {
82     packageName_ = packageName;
83     ParseNamespace(packageName_);
84 }
85 
ParseNamespace(const std::string & nspaceStr)86 AutoPtr<ASTNamespace> AST::ParseNamespace(const std::string &nspaceStr)
87 {
88     AutoPtr<ASTNamespace> currNspace;
89     size_t begin = 0;
90     size_t index = 0;
91     while ((index = nspaceStr.find('.', begin)) != std::string::npos) {
92         std::string ns = StringHelper::SubStr(nspaceStr, begin, index);
93         AutoPtr<ASTNamespace> nspace;
94         if (currNspace == nullptr) {
95             nspace = NewNameSpace(ns);
96         } else {
97             nspace = currNspace->FindNamespace(ns);
98             if (nspace == nullptr) {
99                 nspace = new ASTNamespace(ns);
100                 currNspace->AddNamespace(nspace);
101             }
102         }
103         currNspace = nspace;
104         begin = index + 1;
105     }
106     if (currNspace == nullptr) {
107         currNspace = NewNameSpace("");
108     }
109     return currNspace;
110 }
111 
NewNameSpace(std::string nameSpace)112 AutoPtr<ASTNamespace> AST::NewNameSpace(std::string nameSpace)
113 {
114     AutoPtr<ASTNamespace> currNspace = FindNamespace(nameSpace);
115     if (currNspace == nullptr) {
116         currNspace = new ASTNamespace(nameSpace);
117         AddNamespace(currNspace);
118     }
119     return currNspace;
120 }
121 
AddNamespace(const AutoPtr<ASTNamespace> & nspace)122 void AST::AddNamespace(const AutoPtr<ASTNamespace> &nspace)
123 {
124     if (nspace == nullptr) {
125         return;
126     }
127     namespaces_.push_back(nspace);
128 }
129 
FindNamespace(const std::string & nspaceStr)130 AutoPtr<ASTNamespace> AST::FindNamespace(const std::string &nspaceStr)
131 {
132     for (auto nspace : namespaces_) {
133         if (nspace->ToShortString() == nspaceStr) {
134             return nspace;
135         }
136     }
137     return nullptr;
138 }
139 
GetNamespace(size_t index)140 AutoPtr<ASTNamespace> AST::GetNamespace(size_t index)
141 {
142     if (index >= namespaces_.size()) {
143         return nullptr;
144     }
145 
146     return namespaces_[index];
147 }
148 
AddInterfaceDef(const AutoPtr<ASTInterfaceType> & interface)149 void AST::AddInterfaceDef(const AutoPtr<ASTInterfaceType> &interface)
150 {
151     if (interface == nullptr) {
152         return;
153     }
154 
155     interfaceDefs_.push_back(interface);
156     AddType(interface.Get());
157 }
158 
GetInterfaceDef(size_t index)159 AutoPtr<ASTInterfaceType> AST::GetInterfaceDef(size_t index)
160 {
161     if (index >= interfaceDefs_.size()) {
162         return nullptr;
163     }
164 
165     return interfaceDefs_[index];
166 }
167 
GetSequenceableDef(size_t index)168 AutoPtr<ASTSequenceableType> AST::GetSequenceableDef(size_t index)
169 {
170     if (index >= sequenceableDefs_.size()) {
171         return nullptr;
172     }
173 
174     return sequenceableDefs_[index];
175 }
176 
AddSequenceableDef(const AutoPtr<ASTSequenceableType> & sequenceable)177 void AST::AddSequenceableDef(const AutoPtr<ASTSequenceableType> &sequenceable)
178 {
179     if (sequenceable == nullptr) {
180         return;
181     }
182 
183     sequenceableDefs_.push_back(sequenceable);
184     AddType(sequenceable.Get());
185 }
186 
GetRawDataDef(size_t index)187 AutoPtr<ASTRawDataType> AST::GetRawDataDef(size_t index)
188 {
189     if (index >= rawdataDefs_.size()) {
190         return nullptr;
191     }
192 
193     return rawdataDefs_[index];
194 }
195 
AddRawDataDef(const AutoPtr<ASTRawDataType> & rawdata)196 void AST::AddRawDataDef(const AutoPtr<ASTRawDataType> &rawdata)
197 {
198     if (rawdata == nullptr) {
199         return;
200     }
201 
202     rawdataDefs_.push_back(rawdata);
203     AddType(rawdata.Get());
204 }
205 
IndexOf(ASTInterfaceType * interface)206 int AST::IndexOf(ASTInterfaceType* interface)
207 {
208     for (size_t i = 0; i < interfaceDefs_.size(); i++) {
209         if (interfaceDefs_[i] == interface) {
210             return i;
211         }
212     }
213     return -1;
214 }
215 
IndexOf(ASTSequenceableType * sequenceable)216 int AST::IndexOf(ASTSequenceableType* sequenceable)
217 {
218     for (size_t i = 0; i < sequenceableDefs_.size(); i++) {
219         if (sequenceableDefs_[i] == sequenceable) {
220             return i;
221         }
222     }
223     return -1;
224 }
225 
IndexOf(ASTRawDataType * rawdata)226 int AST::IndexOf(ASTRawDataType* rawdata)
227 {
228     for (size_t i = 0; i < rawdataDefs_.size(); i++) {
229         if (rawdataDefs_[i] == rawdata) {
230             return i;
231         }
232     }
233     return -1;
234 }
235 
IndexOf(ASTType * type)236 int AST::IndexOf(ASTType* type)
237 {
238     int i = 0;
239     for (auto it = types_.begin(); it != types_.end(); ++it, ++i) {
240         if (it->second == type) {
241             return i;
242         }
243     }
244     return -1;
245 }
246 
AddType(const AutoPtr<ASTType> & type)247 void AST::AddType(const AutoPtr<ASTType> &type)
248 {
249     if (type == nullptr) {
250         return;
251     }
252 
253     types_[type->ToString()] = type;
254 }
255 
FindType(const std::string & typeName,bool lookImports)256 AutoPtr<ASTType> AST::FindType(const std::string &typeName, bool lookImports)
257 {
258     if (typeName.empty()) {
259         return nullptr;
260     }
261 
262     for (const auto &type : types_) {
263         if ((typeName.find('.') == std::string::npos && type.second->GetName() == typeName) ||
264             type.first == typeName) {
265             return type.second;
266         }
267     }
268 
269     auto basicTypePair = basicTypes_.find(typeName);
270     if (basicTypePair != basicTypes_.end()) {
271         return basicTypePair->second;
272     }
273 
274     if (!lookImports) {
275         return nullptr;
276     }
277 
278     AutoPtr<ASTType> type = nullptr;
279     for (const auto &importPair : imports_) {
280         type = importPair.second->FindType(typeName, false);
281         if (type != nullptr) {
282             break;
283         }
284     }
285     return type;
286 }
287 
AddTypeDefinition(const AutoPtr<ASTType> & type)288 void AST::AddTypeDefinition(const AutoPtr<ASTType> &type)
289 {
290     if (type == nullptr) {
291         return;
292     }
293 
294     AddType(type);
295     typeDefinitions_.push_back(type);
296 }
297 
GetTypeDefintion(size_t index)298 AutoPtr<ASTType> AST::GetTypeDefintion(size_t index)
299 {
300     if (index >= typeDefinitions_.size()) {
301         return nullptr;
302     }
303     return typeDefinitions_[index];
304 }
305 
Dump(const std::string & prefix)306 std::string AST::Dump(const std::string &prefix)
307 {
308     StringBuilder sb;
309 
310     sb.Append(prefix);
311     if (Options::GetInstance().GetInterfaceType() == InterfaceType::SA) {
312         sb.Append("Module[");
313     } else {
314         sb.Append("AST[");
315     }
316     sb.Append("name: ").Append(name_).Append(" ");
317     sb.Append("file: ").Append(idlFilePath_);
318     sb.Append("]\n");
319 
320     if (!packageName_.empty()) {
321         sb.Append("package ").Append(packageName_).Append(";");
322         sb.Append('\n');
323         sb.Append('\n');
324     }
325 
326     if (imports_.size() > 0) {
327         std::string Keyword = "import";
328         if (Options::GetInstance().GetInterfaceType() == InterfaceType::SA) {
329             Keyword = "sequenceable";
330         }
331         for (const auto &import : imports_) {
332             sb.AppendFormat("%s %s;\n", Keyword.c_str(), import.first.c_str());
333         }
334         sb.Append("\n");
335     }
336 
337     if (typeDefinitions_.size() > 0) {
338         for (auto type : typeDefinitions_) {
339             std::string info = type->Dump("");
340             sb.Append(info).Append("\n");
341         }
342     }
343 
344     if (interfaceDefs_.size() > 0) {
345         for (auto type : interfaceDefs_) {
346             if (type->IsExternal()) {
347                 std::string info = type->Dump("");
348                 sb.Append(info).Append("\n");
349             }
350         }
351 
352         for (auto type : interfaceDefs_) {
353             if (!type->IsExternal()) {
354                 std::string info = type->Dump("");
355                 sb.Append(info).Append("\n");
356             }
357         }
358     }
359 
360     return sb.ToString();
361 }
362 
AddImport(const AutoPtr<AST> & importAst)363 bool AST::AddImport(const AutoPtr<AST> &importAst)
364 {
365     if (imports_.find(importAst->GetFullName()) != imports_.end()) {
366         return false;
367     }
368 
369     imports_[importAst->GetFullName()] = importAst;
370 
371     return true;
372 }
373 
AddImportName(const std::string & importName)374 void AST::AddImportName(const std::string &importName)
375 {
376     importNames_.emplace_back(importName);
377 }
378 
SetVersion(size_t & majorVer,size_t & minorVer)379 void AST::SetVersion(size_t &majorVer, size_t &minorVer)
380 {
381     majorVersion_ = majorVer;
382     minorVersion_ = minorVer;
383 }
384 
IsValid()385 bool AST::IsValid()
386 {
387     if (name_.empty()) {
388         return false;
389     }
390 
391     return interfaceDefs_.size() > 0;
392 }
393 
394 } // namespace Idl
395 } // namespace OHOS