Skip to content

Commit 76883ff

Browse files
committed
done
1 parent 860c4b3 commit 76883ff

File tree

5 files changed

+64
-8
lines changed

5 files changed

+64
-8
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -216,3 +216,4 @@ integration_tests/array_02_decl
216216
integration_tests/array_02_decl.c
217217
integration_tests/expr_12
218218
integration_tests/expr_12.c
219+
integration_tests/expr_07_generated.c

integration_tests/CMakeLists.txt

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -46,12 +46,13 @@ message("LPYTHON_RTLIB_LIBRARY: ${LPYTHON_RTLIB_LIBRARY}")
4646

4747
macro(RUN)
4848
set(options FAIL)
49-
set(oneValueArgs NAME IMPORT_PATH)
49+
set(oneValueArgs NAME IMPORT_PATH CUSTOM_C_POSTPROCESSOR)
5050
set(multiValueArgs LABELS EXTRAFILES)
5151
cmake_parse_arguments(RUN "${options}" "${oneValueArgs}"
5252
"${multiValueArgs}" ${ARGN} )
5353
set(name ${RUN_NAME})
5454
set(import_path ${RUN_IMPORT_PATH})
55+
set(custom_c_postprocessor ${RUN_CUSTOM_C_POSTPROCESSOR})
5556
if (NOT name)
5657
message(FATAL_ERROR "Must specify the NAME argument")
5758
endif()
@@ -82,11 +83,20 @@ macro(RUN)
8283
set_tests_properties(${name} PROPERTIES WILL_FAIL TRUE)
8384
endif()
8485
elseif(KIND STREQUAL "c")
85-
add_custom_command(
86-
OUTPUT ${name}.c
87-
COMMAND lpython --show-c ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py > ${name}.c
88-
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py
89-
VERBATIM)
86+
if (custom_c_postprocessor)
87+
add_custom_command(
88+
OUTPUT ${name}.c
89+
COMMAND lpython --show-c ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py
90+
--custom-c-postprocessor ${CMAKE_CURRENT_SOURCE_DIR}/${custom_c_postprocessor} > ${name}.c
91+
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py
92+
VERBATIM)
93+
else ()
94+
add_custom_command(
95+
OUTPUT ${name}.c
96+
COMMAND lpython --show-c ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py > ${name}.c
97+
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/${name}.py
98+
VERBATIM)
99+
endif()
90100
add_executable(${name} ${name}.c ${RUN_EXTRAFILES})
91101
set_target_properties(${name} PROPERTIES LINKER_LANGUAGE C)
92102
target_link_libraries(${name} lpython_rtlib)
@@ -209,7 +219,8 @@ RUN(NAME expr_03 LABELS cpython llvm c wasm)
209219
RUN(NAME expr_04 LABELS cpython llvm c)
210220
RUN(NAME expr_05 LABELS cpython llvm c)
211221
RUN(NAME expr_06 LABELS cpython llvm c)
212-
RUN(NAME expr_07 LABELS cpython llvm c)
222+
RUN(NAME expr_07 CUSTOM_C_POSTPROCESSOR test_c_custom_postprocessor.py
223+
LABELS cpython llvm c)
213224
RUN(NAME expr_08 LABELS llvm c)
214225
RUN(NAME expr_09 LABELS cpython llvm c)
215226
RUN(NAME expr_10 LABELS cpython llvm c)
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
#!/usr/bin/env python
2+
3+
import sys
4+
5+
filename = sys.argv[1]
6+
7+
f = open(filename).read()
8+
9+
open(filename, "w").write(f)

src/bin/lpython.cpp

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,12 @@ std::string remove_extension(const std::string& filename) {
5959
return filename.substr(0, lastdot);
6060
}
6161

62+
std::string extract_extension(const std::string& filename) {
63+
size_t lastdot = filename.find_last_of(".");
64+
if (lastdot == std::string::npos) return "";
65+
return filename.substr(lastdot);
66+
}
67+
6268
std::string remove_path(const std::string& filename) {
6369
size_t lastslash = filename.find_last_of("/");
6470
if (lastslash == std::string::npos) return filename;
@@ -288,7 +294,22 @@ int emit_c(const std::string &infile,
288294
LFORTRAN_ASSERT(diagnostics.has_error())
289295
return 3;
290296
}
291-
std::cout << res.result;
297+
if( !compiler_options.c_postprocessor_script.empty() ) {
298+
std::string ccode_file = remove_extension(infile) + "_generated.c";
299+
std::ofstream ccode_out(ccode_file);
300+
ccode_out << res.result;
301+
std::string command = "python " + compiler_options.c_postprocessor_script + " " + ccode_file;
302+
system(command.c_str());
303+
ccode_out.close();
304+
std::ifstream ccode_in(ccode_file);
305+
std::string modified_result = "";
306+
while( std::getline(ccode_in, modified_result) ) {
307+
std::cout << modified_result << "\n";
308+
}
309+
ccode_in.close();
310+
} else {
311+
std::cout << res.result;
312+
}
292313
return 0;
293314
}
294315

@@ -1283,6 +1304,7 @@ int main(int argc, char *argv[])
12831304
bool show_errors = false;
12841305
bool with_intrinsic_modules = false;
12851306
std::string arg_pass;
1307+
std::string script_path;
12861308
bool arg_no_color = false;
12871309
bool show_llvm = false;
12881310
bool show_asm = false;
@@ -1349,6 +1371,7 @@ int main(int argc, char *argv[])
13491371
app.add_flag("--indent", compiler_options.indent, "Indented print ASR/AST");
13501372
app.add_flag("--tree", compiler_options.tree, "Tree structure print ASR/AST");
13511373
app.add_option("--pass", arg_pass, "Apply the ASR pass and show ASR (implies --show-asr)");
1374+
app.add_option("--custom-c-postprocessor", script_path, "The script for processing the C code generated by --show-c command.");
13521375
app.add_flag("--disable-main", compiler_options.disable_main, "Do not generate any code for the `main` function");
13531376
app.add_flag("--symtab-only", compiler_options.symtab_only, "Only create symbol tables in ASR (skip executable stmt)");
13541377
app.add_flag("--time-report", time_report, "Show compilation time report");
@@ -1471,6 +1494,17 @@ int main(int argc, char *argv[])
14711494
return 1;
14721495
}
14731496

1497+
if( !script_path.empty() && extract_extension(script_path) != ".py" ) {
1498+
std::cerr << "Only a Python script is supported as a postprocessor for generated C code." << std::endl;
1499+
return 1;
1500+
}
1501+
1502+
if( !script_path.empty() && !LFortran::path_exists(script_path) ) {
1503+
std::cerr << script_path << " is inaccessible or doesn't exist on your system." << std::endl;
1504+
return 1;
1505+
}
1506+
1507+
compiler_options.c_postprocessor_script = script_path;
14741508
if (arg_backend == "llvm") {
14751509
backend = Backend::llvm;
14761510
} else if (arg_backend == "cpp") {

src/libasr/utils.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ struct CompilerOptions {
5252
bool emit_debug_info = false;
5353
bool emit_debug_line_column = false;
5454
std::string import_path = "";
55+
std::string c_postprocessor_script = "";
5556
Platform platform;
5657

5758
CompilerOptions () : platform{get_platform()} {};

0 commit comments

Comments
 (0)