1 /**
2    Deals with D-specific translation, such as avoiding keywords
3  */
4 module dpp.translation.dlang;
5 
6 import dpp.from;
7 
8 
9 string maybeRename(in from!"clang".Cursor cursor,
10                    in from!"dpp.runtime.context".Context context)
11     @safe pure nothrow
12 {
13     return nameClashes(cursor, context)
14         ? rename(cursor.spelling, context)
15         : cursor.spelling.idup;
16 }
17 
18 string maybePragma(in from!"clang".Cursor cursor,
19                    in from!"dpp.runtime.context".Context context)
20     @safe pure nothrow
21 {
22     import dpp.runtime.context: Language;
23     import std.algorithm: startsWith;
24     const isCpp = context.language == Language.Cpp;
25     if(isCpp) return pragmaMangle(cursor.mangling);
26     return nameClashes(cursor, context) ? pragmaMangle(cursor.mangling) : "";
27 }
28 
29 string rename(string spelling,
30               in from!"dpp.runtime.context".Context context)
31     @safe pure nothrow
32 {
33     do
34         spelling ~= "_";
35     while(spelling in context.aggregateDeclarations || isKeyword(spelling));
36 
37     return spelling;
38 }
39 
40 string pragmaMangle(in string mangling) @safe pure nothrow {
41     return mangling == "" ? "" : `pragma(mangle, "` ~ mangling ~ `") `;
42 }
43 
44 private bool nameClashes(in from!"clang".Cursor cursor,
45                          in from!"dpp.runtime.context".Context context)
46     @safe pure nothrow
47 {
48     return
49         cursor.spelling.isKeyword ||
50         cursor.spelling in context.aggregateDeclarations;
51 }
52 
53 bool isKeyword(string str) @safe @nogc pure nothrow {
54     switch (str) {
55         default: return false;
56         case "abstract":
57         case "alias":
58         case "align":
59         case "asm":
60         case "assert":
61         case "auto":
62 
63         case "body":
64         case "bool":
65         case "break":
66         case "byte":
67 
68         case "case":
69         case "cast":
70         case "catch":
71         case "cdouble":
72         case "cent":
73         case "cfloat":
74         case "char":
75         case "class":
76         case "const":
77         case "continue":
78         case "creal":
79 
80         case "dchar":
81         case "debug":
82         case "default":
83         case "delegate":
84         case "delete":
85         case "deprecated":
86         case "do":
87         case "double":
88 
89         case "else":
90         case "enum":
91         case "export":
92         case "extern":
93 
94         case "false":
95         case "final":
96         case "finally":
97         case "float":
98         case "for":
99         case "foreach":
100         case "foreach_reverse":
101         case "function":
102 
103         case "goto":
104 
105         case "idouble":
106         case "if":
107         case "ifloat":
108         case "import":
109         case "in":
110         case "inout":
111         case "int":
112         case "interface":
113         case "invariant":
114         case "ireal":
115         case "is":
116 
117         case "lazy":
118         case "long":
119 
120         case "macro":
121         case "mixin":
122         case "module":
123 
124         case "new":
125         case "nothrow":
126         case "null":
127 
128         case "out":
129         case "override":
130 
131         case "package":
132         case "pragma":
133         case "private":
134         case "protected":
135         case "public":
136         case "pure":
137 
138         case "real":
139         case "ref":
140         case "return":
141 
142         case "scope":
143         case "shared":
144         case "short":
145         case "static":
146         case "struct":
147         case "super":
148         case "switch":
149         case "synchronized":
150 
151         case "template":
152         case "this":
153         case "throw":
154         case "true":
155         case "try":
156         case "typedef":
157         case "typeid":
158         case "typeof":
159 
160         case "ubyte":
161         case "ucent":
162         case "uint":
163         case "ulong":
164         case "union":
165         case "unittest":
166         case "ushort":
167 
168         case "version":
169         case "void":
170         case "volatile":
171 
172         case "wchar":
173         case "while":
174         case "with":
175         case "immutable":
176         case "__gshared":
177         case "__thread":
178         case "__traits":
179 
180         case "__EOF__":
181         case "__FILE__":
182         case "__LINE__":
183         case "__DATE__":
184         case "__TIME__":
185         case "__TIMESTAMP__":
186         case "__VENDOR__":
187         case "__VERSION__":
188 
189         case "string":
190             return true;
191     }
192 
193     assert(0);
194 }