1
1
#include " TypeTranslator.h"
2
2
#include " Utils.h"
3
+ #include " ir/types/FunctionPointerType.h"
4
+ #include " ir/types/PointerType.h"
3
5
4
- TypeTranslator::TypeTranslator (clang::ASTContext *ctx_) : ctx(ctx_), typeMap() {
6
+ TypeTranslator::TypeTranslator (clang::ASTContext *ctx_, IR &ir)
7
+ : ctx(ctx_), ir(ir), typeMap() {
5
8
6
9
// Native Types
7
10
typeMap[" void" ] = " Unit" ;
@@ -27,38 +30,24 @@ TypeTranslator::TypeTranslator(clang::ASTContext *ctx_) : ctx(ctx_), typeMap() {
27
30
typeMap[" char32_t" ] = " native.CChar32" ;
28
31
typeMap[" float" ] = " native.CFloat" ;
29
32
typeMap[" double" ] = " native.CDouble" ;
30
- typeMap[" void*" ] = " native.Ptr[Byte]" ;
31
33
}
32
34
33
- std::string
34
- TypeTranslator::TranslateFunctionPointer (const clang::QualType &qtpe,
35
- const std::string *avoid) {
36
- const clang::PointerType *ptr =
37
- qtpe.getTypePtr ()->getAs <clang::PointerType>();
35
+ Type *TypeTranslator::translateFunctionPointer (const clang::QualType &qtpe,
36
+ const std::string *avoid) {
37
+ const auto *ptr = qtpe.getTypePtr ()->getAs <clang::PointerType>();
38
38
const clang::QualType &inner = ptr->getPointeeType ();
39
39
40
40
if (inner->isFunctionProtoType ()) {
41
- const clang::FunctionProtoType *fc =
42
- inner->getAs <clang::FunctionProtoType>();
43
- std::string ret = Translate (fc->getReturnType (), avoid);
44
- std::string params = " " ;
45
- int counter = 0 ;
41
+ const auto *fc = inner->getAs <clang::FunctionProtoType>();
42
+ Type *returnType = translate (fc->getReturnType (), avoid);
43
+ std::vector<Type *> parametersTypes;
46
44
47
45
for (const clang::QualType ¶m : fc->param_types ()) {
48
- params += Translate (param, avoid);
49
- params += " , " ;
50
- counter++;
46
+ parametersTypes.push_back (translate (param, avoid));
51
47
}
52
48
53
- std::string variad = " " ;
54
-
55
- if (fc->isVariadic ()) {
56
- counter++;
57
- variad = " native.CVararg, " ;
58
- }
59
-
60
- return std::string (" native.CFunctionPtr" ) + std::to_string (counter) +
61
- " [" + params + variad + ret + " ]" ;
49
+ return new FunctionPointerType (returnType, parametersTypes,
50
+ fc->isVariadic ());
62
51
63
52
} else {
64
53
llvm::errs () << " Unsupported function pointer type: "
@@ -68,111 +57,111 @@ TypeTranslator::TranslateFunctionPointer(const clang::QualType &qtpe,
68
57
}
69
58
}
70
59
71
- std::string TypeTranslator::TranslatePointer (const clang::QualType &pte,
72
- const std::string *avoid) {
60
+ Type * TypeTranslator::translatePointer (const clang::QualType &pte,
61
+ const std::string *avoid) {
73
62
74
63
if (pte->isBuiltinType ()) {
75
64
const clang::BuiltinType *as = pte->getAs <clang::BuiltinType>();
76
65
77
66
// Take care of void*
78
67
if (as->getKind () == clang::BuiltinType::Void) {
79
- return " native.Ptr[ Byte] " ;
68
+ return new PointerType ( new PrimitiveType ( " Byte" )) ;
80
69
}
81
70
82
71
// Take care of char*
83
72
if (as->getKind () == clang::BuiltinType::Char_S ||
84
73
as->getKind () == clang::BuiltinType::SChar) {
85
- return " native.CString" ;
74
+ // TODO: new PointerType(new PrimitiveType("native.CChar"))
75
+ return new PrimitiveType (" native.CString" );
86
76
}
87
77
}
88
78
89
- return std::string (" native.Ptr[" ) + Translate (pte, avoid) +
90
- std::string (" ]" );
79
+ return new PointerType (translate (pte, avoid));
91
80
}
92
81
93
- std::string
94
- TypeTranslator::TranslateStructOrUnion (const clang::QualType &qtpe) {
95
- if (qtpe->hasUnnamedOrLocalType ()) {
96
- // TODO: Verify that the local part is not a problem
97
- uint64_t size = ctx->getTypeSize (qtpe);
98
- return " native.CArray[Byte, " + uint64ToScalaNat (size) + " ]" ;
99
- }
100
-
82
+ Type *
83
+ TypeTranslator::translateStructOrUnionOrEnum (const clang::QualType &qtpe) {
101
84
std::string name = qtpe.getUnqualifiedType ().getAsString ();
102
85
103
- // TODO: do it properly
104
- size_t f = name.find (std::string (" struct __dirstream" ));
105
- if (f != std::string::npos) {
106
- return std::string (" native.CArray[Byte, Digit[_3, Digit[_2, _0]]]" );
107
- }
108
-
109
- f = name.find (" " );
110
- if (f != std::string::npos) {
111
- return name.replace (f, std::string (" " ).length (), " _" );
86
+ auto it = aliasesMap.find (name);
87
+ if (it != aliasesMap.end ()) {
88
+ /* name contains space: struct <name>.
89
+ * Use type alias instead struct type */
90
+ return (*it).second ;
112
91
}
113
- return name;
92
+ /* type has typedef alias */
93
+ return ir.getTypeDefWithName (name);
114
94
}
115
95
116
- std::string TypeTranslator::TranslateEnum (const clang::QualType &qtpe) {
117
- std::string name = qtpe. getUnqualifiedType (). getAsString ();
118
- size_t f = name. find ( " " );
119
- if (f != std::string::npos) {
120
- return name. replace (f, std::string ( " " ). length (), " _ " );
96
+ Type * TypeTranslator::translateStructOrUnion (const clang::QualType &qtpe) {
97
+ if ( qtpe-> hasUnnamedOrLocalType ()) {
98
+ // TODO: Verify that the local part is not a problem
99
+ uint64_t size = ctx-> getTypeSize (qtpe);
100
+ return new ArrayType ( new PrimitiveType ( " Byte " ), size );
121
101
}
122
- return name;
102
+
103
+ return translateStructOrUnionOrEnum (qtpe);
123
104
}
124
105
125
- std::string
126
- TypeTranslator::TranslateConstantArray (const clang::ConstantArrayType *ar,
127
- const std::string *avoid) {
106
+ Type *TypeTranslator::translateConstantArray (const clang::ConstantArrayType *ar,
107
+ const std::string *avoid) {
128
108
const uint64_t size = ar->getSize ().getZExtValue ();
129
- const std::string nat = uint64ToScalaNat (size);
130
- return " native.CArray[" + Translate (ar->getElementType (), avoid) + " , " +
131
- nat + " ]" ;
109
+ return new ArrayType (translate (ar->getElementType (), avoid), size);
132
110
}
133
111
134
- std::string TypeTranslator::Translate (const clang::QualType &qtpe,
135
- const std::string *avoid) {
112
+ Type * TypeTranslator::translate (const clang::QualType &qtpe,
113
+ const std::string *avoid) {
136
114
137
115
const clang::Type *tpe = qtpe.getTypePtr ();
138
116
139
117
if (typeEquals (tpe, avoid)) {
140
118
// This is a type that we want to avoid the usage.
141
- // Êxample: A struct that has a pointer to itself
119
+ // Êxample: A struct that has a pointer to itself
142
120
uint64_t size = ctx->getTypeSize (tpe);
143
- return " native.CArray[ Byte, " + uint64ToScalaNat ( size) + " ] " ;
121
+ return new ArrayType ( new PrimitiveType ( " Byte" ), size);
144
122
}
145
123
146
124
if (tpe->isFunctionPointerType ()) {
147
- return TranslateFunctionPointer (qtpe, avoid);
125
+ return translateFunctionPointer (qtpe, avoid);
148
126
149
127
} else if (tpe->isPointerType ()) {
150
- return TranslatePointer (
128
+ return translatePointer (
151
129
tpe->getAs <clang::PointerType>()->getPointeeType (), avoid);
152
130
153
- } else if (qtpe->isStructureType () || qtpe->isUnionType ()) {
154
- return handleReservedWords (TranslateStructOrUnion (qtpe));
131
+ } else if (qtpe->isStructureType ()) {
132
+ return translateStructOrUnion (qtpe);
133
+
134
+ } else if (qtpe->isUnionType ()) {
135
+ return translateStructOrUnion (qtpe);
155
136
156
137
} else if (qtpe->isEnumeralType ()) {
157
- return TranslateEnum (qtpe);
138
+ return translateStructOrUnionOrEnum (qtpe);
158
139
159
140
} else if (qtpe->isConstantArrayType ()) {
160
- return TranslateConstantArray (ctx->getAsConstantArrayType (qtpe), avoid);
141
+ return translateConstantArray (ctx->getAsConstantArrayType (qtpe), avoid);
161
142
} else if (qtpe->isArrayType ()) {
162
- return TranslatePointer (ctx->getAsArrayType (qtpe)->getElementType (),
143
+ return translatePointer (ctx->getAsArrayType (qtpe)->getElementType (),
163
144
avoid);
164
145
} else {
165
146
166
147
auto found = typeMap.find (qtpe.getUnqualifiedType ().getAsString ());
167
148
if (found != typeMap.end ()) {
168
- return handleReservedWords (found->second );
149
+ return new PrimitiveType (found->second );
169
150
} else {
170
- // TODO: Properly handle non-default types
171
- return handleReservedWords ( qtpe.getUnqualifiedType ().getAsString ());
151
+ return ir. getTypeDefWithName (
152
+ qtpe.getUnqualifiedType ().getAsString ());
172
153
}
173
154
}
174
155
}
175
156
176
- void TypeTranslator::AddTranslation (std::string from, std::string to) {
177
- typeMap[from] = to;
157
+ void TypeTranslator::addAlias (std::string cName, Type *type) {
158
+ aliasesMap[cName] = type;
159
+ }
160
+
161
+ std::string TypeTranslator::getTypeFromTypeMap (std::string cType) {
162
+ auto it = typeMap.find (cType);
163
+ if (it != typeMap.end ()) {
164
+ return (*it).second ;
165
+ }
166
+ return " " ;
178
167
}
0 commit comments