Franck Pommereau

started to replace parser

This diff is collapsed. Click to expand it.
This diff is collapsed. Click to expand it.
...@@ -177,7 +177,14 @@ class CodeGenVisitor (Visitor) : ...@@ -177,7 +177,14 @@ class CodeGenVisitor (Visitor) :
177 def concat (cls, outfile, chunks) : 177 def concat (cls, outfile, chunks) :
178 outfile.write("# Generated by cct\n" 178 outfile.write("# Generated by cct\n"
179 "# Franck Pommereau (2018)\n" 179 "# Franck Pommereau (2018)\n"
180 - "# Adapted from Atul Varma's c.py (Spring 2004)\n") 180 + "# Adapted from Atul Varma's c.py (Spring 2004)\n\n")
181 + outfile.write("#\n"
182 + "# on computer start: call main and halt\n"
183 + "#\n\n"
184 + "IRQ0:\n"
185 + " set R9 @main\n"
186 + " call R9\n"
187 + " halt\n")
181 for c in chunks : 188 for c in chunks :
182 s = c.curr_str.getvalue() 189 s = c.curr_str.getvalue()
183 if s.strip() : 190 if s.strip() :
...@@ -194,13 +201,6 @@ class CodeGenVisitor (Visitor) : ...@@ -194,13 +201,6 @@ class CodeGenVisitor (Visitor) :
194 outfile.write("\n#\n# string literals from file %r\n#\n\n" 201 outfile.write("\n#\n# string literals from file %r\n#\n\n"
195 % c.path) 202 % c.path)
196 outfile.write(s) 203 outfile.write(s)
197 - outfile.write("\n#\n"
198 - "# call main\n"
199 - "#\n\n"
200 - "IRQ0:\n"
201 - " set R9 @main\n"
202 - " call R9\n"
203 - " halt\n")
204 204
205 def _calc_function_var_addrs(self, symtab, last_fp_loc): 205 def _calc_function_var_addrs(self, symtab, last_fp_loc):
206 self._calc_function_arg_addrs(symtab) 206 self._calc_function_arg_addrs(symtab)
...@@ -353,7 +353,7 @@ class CodeGenVisitor (Visitor) : ...@@ -353,7 +353,7 @@ class CodeGenVisitor (Visitor) :
353 353
354 label_str = "_LC%d" % self.__str_literal_label 354 label_str = "_LC%d" % self.__str_literal_label
355 self.str_literal_dict[str] = label_str 355 self.str_literal_dict[str] = label_str
356 - str = str.replace('\n', '\\12') 356 + str = str.replace('\n', '\\n')
357 self.str_literal_str.write("""%s:\n str "%s\\0"\n""" % (label_str, str)) 357 self.str_literal_str.write("""%s:\n str "%s\\0"\n""" % (label_str, str))
358 self.__class__.__str_literal_label += 1 358 self.__class__.__str_literal_label += 1
359 return label_str 359 return label_str
......
...@@ -340,11 +340,9 @@ class SymtabVisitor(Visitor): ...@@ -340,11 +340,9 @@ class SymtabVisitor(Visitor):
340 # TODO: might be best to just move this to the code 340 # TODO: might be best to just move this to the code
341 # generation phase, since this doesn't have anything to 341 # generation phase, since this doesn't have anything to
342 # do with symbol table generation. 342 # do with symbol table generation.
343 - param_num = 0 343 + for param_num, param in enumerate(node.nodes):
344 - for param in node.nodes:
345 param.accept(self) 344 param.accept(self)
346 param.param_num = param_num 345 param.param_num = param_num
347 - param_num += 1
348 346
349 def vTranslationUnit(self, node): 347 def vTranslationUnit(self, node):
350 self.root_symtab = Symtab() 348 self.root_symtab = Symtab()
......
1 +import pycparser
2 +
3 +from . import cast
4 +
5 +def _coord (node) :
6 + if node.coord is not None :
7 + return {"lineno" : node.coord.line,
8 + "colno" : node.coord.column - 1,
9 + "filename" : node.coord.file}
10 + else :
11 + return {}
12 +
13 +class ast2ast (object) :
14 + def __call__ (self, node) :
15 + return getattr(self, "v" + node.__class__.__name__)(node)
16 +
17 + # # This is the top of the AST, representing a single C file (a
18 + # # translation unit in K&R jargon). It contains a list of
19 + # # "external-declaration"s, which is either declarations (Decl),
20 + # # Typedef or function definitions (FuncDef).
21 + # #
22 + # FileAST: [ext**]
23 + def vFileAST (self, node) :
24 + ret = cast.TranslationUnit(None, **_coord(node))
25 + for _, child in node.children() :
26 + ret.add(self(child))
27 + return ret
28 +
29 + # # name: the variable being declared
30 + # # quals: list of qualifiers (const, volatile)
31 + # # funcspec: list function specifiers (i.e. inline in C99)
32 + # # storage: list of storage specifiers (extern, register, etc.)
33 + # # type: declaration type (probably nested with all the modifiers)
34 + # # init: initialization value, or None
35 + # # bitsize: bit field size, or None
36 + # #
37 + # Decl: [name, quals, storage, funcspec, type*, init*, bitsize*]
38 + def vDecl (self, node) :
39 + typ = self(node.type)
40 + ret = cast.Declaration(node.name, typ, **_coord(node))
41 + ret.extern = "extern" in node.storage
42 + ret.static = "static" in node.quals
43 + return ret
44 +
45 + # # A typedef declaration.
46 + # # Very similar to Decl, but without some attributes
47 + # #
48 + # Typedef: [name, quals, storage, type*]
49 + def vTypedef (self, node) :
50 + raise NotImplementedError("typdef")
51 +
52 + # # type <decl>(args)
53 + # #
54 + # FuncDecl: [args*, type*]
55 + def vFuncDecl (self, node) :
56 + return cast.FunctionType(self(node.args), self(node.type))
57 +
58 + # # a list of comma separated function parameter declarations
59 + # #
60 + # ParamList: [params**]
61 + def vParamList (self, node) :
62 + pass
63 +
64 + # # A base type declaration
65 + # #
66 + # TypeDecl: [declname, quals, type*]
67 + def vTypeDecl (self, node) :
68 + pass
69 +
70 + # # Function definition: a declarator for the function name and
71 + # # a body, which is a compound statement.
72 + # # There's an optional list of parameter declarations for old
73 + # # K&R-style definitions
74 + # #
75 + # FuncDef: [decl*, param_decls**, body*]
76 + def vFuncDef (self, node) :
77 + pass
78 +
79 + # # ArrayDecl is a nested declaration of an array with the given type.
80 + # # dim: the dimension (for example, constant 42)
81 + # # dim_quals: list of dimension qualifiers, to support C99's allowing 'const'
82 + # # and 'static' within the array dimension in function declarations.
83 + # ArrayDecl: [type*, dim*, dim_quals]
84 +
85 + # ArrayRef: [name*, subscript*]
86 +
87 + # # op: =, +=, /= etc.
88 + # #
89 + # Assignment: [op, lvalue*, rvalue*]
90 +
91 + # BinaryOp: [op, left*, right*]
92 +
93 + # Break: []
94 +
95 + # Case: [expr*, stmts**]
96 +
97 + # Cast: [to_type*, expr*]
98 +
99 + # # Compound statement in C99 is a list of block items (declarations or
100 + # # statements).
101 + # #
102 + # Compound: [block_items**]
103 +
104 + # # Compound literal (anonymous aggregate) for C99.
105 + # # (type-name) {initializer_list}
106 + # # type: the typename
107 + # # init: InitList for the initializer list
108 + # #
109 + # CompoundLiteral: [type*, init*]
110 +
111 + # # type: int, char, float, etc. see CLexer for constant token types
112 + # #
113 + # Constant: [type, value]
114 +
115 + # Continue: []
116 +
117 + # DeclList: [decls**]
118 +
119 + # Default: [stmts**]
120 +
121 + # DoWhile: [cond*, stmt*]
122 +
123 + # # Represents the ellipsis (...) parameter in a function
124 + # # declaration
125 + # #
126 + # EllipsisParam: []
127 +
128 + # # An empty statement (a semicolon ';' on its own)
129 + # #
130 + # EmptyStatement: []
131 +
132 + # # Enumeration type specifier
133 + # # name: an optional ID
134 + # # values: an EnumeratorList
135 + # #
136 + # Enum: [name, values*]
137 +
138 + # # A name/value pair for enumeration values
139 + # #
140 + # Enumerator: [name, value*]
141 +
142 + # # A list of enumerators
143 + # #
144 + # EnumeratorList: [enumerators**]
145 +
146 + # # A list of expressions separated by the comma operator.
147 + # #
148 + # ExprList: [exprs**]
149 +
150 + # # for (init; cond; next) stmt
151 + # #
152 + # For: [init*, cond*, next*, stmt*]
153 +
154 + # # name: Id
155 + # # args: ExprList
156 + # #
157 + # FuncCall: [name*, args*]
158 +
159 + # Goto: [name]
160 +
161 + # ID: [name]
162 +
163 + # # Holder for types that are a simple identifier (e.g. the built
164 + # # ins void, char etc. and typedef-defined types)
165 + # #
166 + # IdentifierType: [names]
167 +
168 + # If: [cond*, iftrue*, iffalse*]
169 +
170 + # # An initialization list used for compound literals.
171 + # #
172 + # InitList: [exprs**]
173 +
174 + # Label: [name, stmt*]
175 +
176 + # # A named initializer for C99.
177 + # # The name of a NamedInitializer is a sequence of Nodes, because
178 + # # names can be hierarchical and contain constant expressions.
179 + # #
180 + # NamedInitializer: [name**, expr*]
181 +
182 + # PtrDecl: [quals, type*]
183 +
184 + # Return: [expr*]
185 +
186 + # # name: struct tag name
187 + # # decls: declaration of members
188 + # #
189 + # Struct: [name, decls**]
190 +
191 + # # type: . or ->
192 + # # name.field or name->field
193 + # #
194 + # StructRef: [name*, type, field*]
195 +
196 + # Switch: [cond*, stmt*]
197 +
198 + # # cond ? iftrue : iffalse
199 + # #
200 + # TernaryOp: [cond*, iftrue*, iffalse*]
201 +
202 + # Typename: [name, quals, type*]
203 +
204 + # UnaryOp: [op, expr*]
205 +
206 + # # name: union tag name
207 + # # decls: declaration of members
208 + # #
209 + # Union: [name, decls**]
210 +
211 + # While: [cond*, stmt*]
212 +
213 + # Pragma: [string]
214 +
215 +def parse (path, *cpp_args) :
216 + ast = pycparser.parse_file(path, use_cpp=True, cpp_args=list(cpp_args))
217 + return ast2ast()(ast)
218 +
219 +if __name__ == "__main__" :
220 + tree = parse(",test.c", "-DTTC")