1
1
package CBuilder ;
2
2
3
+ import static java .nio .file .StandardCopyOption .REPLACE_EXISTING ;
4
+
3
5
import CBuilder .objects .MPyClass ;
4
6
import CBuilder .objects .functions .Function ;
5
7
import CBuilder .objects .functions .ReturnStatement ;
6
8
import CBuilder .variables .VariableDeclaration ;
7
-
8
9
import java .io .IOException ;
9
10
import java .net .URI ;
10
11
import java .net .URISyntaxException ;
16
17
import java .util .stream .Collectors ;
17
18
import java .util .stream .Stream ;
18
19
19
- import static java .nio .file .StandardCopyOption .REPLACE_EXISTING ;
20
-
21
- /**
22
- * Entrypoint to creating C code from a MiniPython AST.
23
- */
20
+ /** Entrypoint to creating C code from a MiniPython AST. */
24
21
public class ProgramBuilder {
25
22
26
- /**
27
- * Definition of the c-runtime header files.
28
- */
23
+ /** Definition of the c-runtime header files. */
29
24
private static final String [] headers = {
30
- // allow usage of assertions
31
- "assert" ,
32
- // aliases mapping python names to the internal c names
33
- "mpy_aliases" ,
34
- // ref-counting
35
- "mpy_obj" ,
36
- // initialisation
37
- "builtins-setup" ,
38
- // building function args
39
- "function-args" ,
40
- "literals/tuple" ,
41
- "literals/int" ,
42
- "literals/boolean" ,
43
- "literals/str" ,
44
- "type-hierarchy/object" ,
45
- // custom objects
46
- "type-hierarchy/type" ,
25
+ // allow usage of assertions
26
+ "assert" ,
27
+ // aliases mapping python names to the internal c names
28
+ "mpy_aliases" ,
29
+ // ref-counting
30
+ "mpy_obj" ,
31
+ // initialisation
32
+ "builtins-setup" ,
33
+ // building function args
34
+ "function-args" ,
35
+ "literals/tuple" ,
36
+ "literals/int" ,
37
+ "literals/boolean" ,
38
+ "literals/str" ,
39
+ "type-hierarchy/object" ,
40
+ // custom objects
41
+ "type-hierarchy/type" ,
47
42
};
48
43
49
- /**
50
- * A list of all statements in the global scope.
51
- */
44
+ /** A list of all statements in the global scope. */
52
45
private final List <Statement > statements ;
53
46
54
- /**
55
- * A list of all defined variables in the global scope.
56
- */
47
+ /** A list of all defined variables in the global scope. */
57
48
private final List <VariableDeclaration > globalVariables ;
58
49
59
- /**
60
- * A list of all defined functions in the global scope.
61
- */
50
+ /** A list of all defined functions in the global scope. */
62
51
private final List <Function > globalFunctions ;
63
52
64
- /**
65
- * A list of all defined classes in th global scope.
66
- */
53
+ /** A list of all defined classes in th global scope. */
67
54
private final List <MPyClass > classes ;
68
55
69
56
/**
70
- * Create a new program with empty global scope.
71
- * Allows to manually specify options regarding c-code generation.
57
+ * Create a new program with empty global scope. Allows to manually specify options regarding
58
+ * c-code generation.
72
59
*/
73
60
public ProgramBuilder () {
74
61
statements = new LinkedList <>();
@@ -78,14 +65,15 @@ public ProgramBuilder() {
78
65
}
79
66
80
67
/**
81
- * Add a new statement to the global scope.
82
- * The resulting statement list more or less represents the program's main method.
68
+ * Add a new statement to the global scope. The resulting statement list more or less represents
69
+ * the program's main method.
83
70
*
84
71
* @param statement The statement to add.
85
72
*/
86
73
public void addStatement (Statement statement ) {
87
74
if (statement instanceof ReturnStatement ) {
88
- // I'd prefer to have this type safe (i. e. different statement interfaces for global/non-global scope,
75
+ // I'd prefer to have this type safe (i. e. different statement interfaces for
76
+ // global/non-global scope,
89
77
// but this is just a prototype after all and shouldn't happen too often anyway)
90
78
throw new IllegalArgumentException ("Cannot return from global scope" );
91
79
}
@@ -204,8 +192,11 @@ public String buildProgram() {
204
192
205
193
body .append ("return 0;\n " );
206
194
207
- program .append (body .toString ().lines ().map (string -> "\t " + string + "\n " ).collect (
208
- Collectors .joining ()));
195
+ program .append (
196
+ body .toString ()
197
+ .lines ()
198
+ .map (string -> "\t " + string + "\n " )
199
+ .collect (Collectors .joining ()));
209
200
program .append ("}\n " );
210
201
211
202
return program .toString ();
@@ -235,7 +226,12 @@ public void writeProgram(Path destDir) {
235
226
236
227
try {
237
228
Path output = Path .of (destDir .toString (), "src/program.c" );
238
- java .nio .file .Files .writeString (output , this .buildProgram (), java .nio .file .StandardOpenOption .CREATE , java .nio .file .StandardOpenOption .WRITE , java .nio .file .StandardOpenOption .TRUNCATE_EXISTING );
229
+ java .nio .file .Files .writeString (
230
+ output ,
231
+ this .buildProgram (),
232
+ java .nio .file .StandardOpenOption .CREATE ,
233
+ java .nio .file .StandardOpenOption .WRITE ,
234
+ java .nio .file .StandardOpenOption .TRUNCATE_EXISTING );
239
235
} catch (java .io .IOException e ) {
240
236
throw new RuntimeException ("Failed to write 'program.c'!" , e );
241
237
}
@@ -250,13 +246,18 @@ public void writeProgram(Path destDir) {
250
246
*/
251
247
public void copyFolder (Path srcDir , Path destDir ) throws IOException {
252
248
try (Stream <Path > stream = Files .walk (srcDir )) {
253
- stream .forEach (source -> {
254
- try {
255
- Files .copy (source , destDir .resolve (srcDir .relativize (source )), REPLACE_EXISTING );
256
- } catch (IOException e ) {
257
- throw new RuntimeException ("Failed to copy template folder to output directory" , e );
258
- }
259
- });
249
+ stream .forEach (
250
+ source -> {
251
+ try {
252
+ Files .copy (
253
+ source ,
254
+ destDir .resolve (srcDir .relativize (source )),
255
+ REPLACE_EXISTING );
256
+ } catch (IOException e ) {
257
+ throw new RuntimeException (
258
+ "Failed to copy template folder to output directory" , e );
259
+ }
260
+ });
260
261
}
261
262
}
262
263
@@ -265,29 +266,37 @@ public void copyFolder(Path srcDir, Path destDir) throws IOException {
265
266
*
266
267
* @param resourcePath The Path to the jar archive.
267
268
* @param targetLocation The output directory.
268
- * @throws URISyntaxException Will be thrown if the c-runtime can not be found in the application resources.
269
+ * @throws URISyntaxException Will be thrown if the c-runtime can not be found in the
270
+ * application resources.
269
271
* @throws IOException Will be thrown if a needed file or folder is not accessible.
270
272
*/
271
- public void copyFolderFromJar (String resourcePath , final Path targetLocation ) throws URISyntaxException , IOException {
273
+ public void copyFolderFromJar (String resourcePath , final Path targetLocation )
274
+ throws URISyntaxException , IOException {
272
275
URI resource = getClass ().getResource ("/c-runtime" ).toURI ();
273
276
274
277
try (FileSystem fileSystem = FileSystems .newFileSystem (resource , Map .of ())) {
275
278
final Path jarArchive = fileSystem .getPath (resourcePath );
276
- Files .walkFileTree (jarArchive , new SimpleFileVisitor <>() {
277
- @ Override
278
- public FileVisitResult preVisitDirectory (Path dir , BasicFileAttributes attrs ) throws IOException {
279
- Files .createDirectories (targetLocation .resolve (jarArchive .relativize (dir ).toString ()));
280
- return FileVisitResult .CONTINUE ;
281
- }
282
-
283
- @ Override
284
- public FileVisitResult visitFile (Path file , BasicFileAttributes attrs ) throws IOException {
285
- Files .copy (file , targetLocation .resolve (jarArchive .relativize (file ).toString ()), REPLACE_EXISTING );
286
- return FileVisitResult .CONTINUE ;
287
- }
288
-
289
- });
279
+ Files .walkFileTree (
280
+ jarArchive ,
281
+ new SimpleFileVisitor <>() {
282
+ @ Override
283
+ public FileVisitResult preVisitDirectory (
284
+ Path dir , BasicFileAttributes attrs ) throws IOException {
285
+ Files .createDirectories (
286
+ targetLocation .resolve (jarArchive .relativize (dir ).toString ()));
287
+ return FileVisitResult .CONTINUE ;
288
+ }
289
+
290
+ @ Override
291
+ public FileVisitResult visitFile (Path file , BasicFileAttributes attrs )
292
+ throws IOException {
293
+ Files .copy (
294
+ file ,
295
+ targetLocation .resolve (jarArchive .relativize (file ).toString ()),
296
+ REPLACE_EXISTING );
297
+ return FileVisitResult .CONTINUE ;
298
+ }
299
+ });
290
300
}
291
301
}
292
-
293
302
}
0 commit comments