From c297cdc14ed52d9801de85952690c8418af1b7ad Mon Sep 17 00:00:00 2001 From: Shaikh Ubaid Date: Fri, 10 Nov 2023 05:46:06 +0530 Subject: [PATCH 1/2] Support --dump-all-passes, --dump-all-passes-fortran --- src/bin/lpython.cpp | 45 +++++++++++++++++++++ src/lpython/semantics/python_ast_to_asr.cpp | 32 +++++++++++++++ 2 files changed, 77 insertions(+) diff --git a/src/bin/lpython.cpp b/src/bin/lpython.cpp index ae53ac03a8..43263fa0c4 100644 --- a/src/bin/lpython.cpp +++ b/src/bin/lpython.cpp @@ -443,6 +443,45 @@ int emit_wat(const std::string &infile, return 0; } +int dump_all_passes(const std::string &infile, + const std::string &runtime_library_dir, + CompilerOptions &compiler_options) { + std::string input = LCompilers::read_file(infile); + + Allocator al(4*1024); + LCompilers::LocationManager lm; + LCompilers::diag::Diagnostics diagnostics; + { + LCompilers::LocationManager::FileLocations fl; + fl.in_filename = infile; + lm.files.push_back(fl); + lm.file_ends.push_back(input.size()); + } + + LCompilers::Result r = parse_python_file( + al, runtime_library_dir, infile, diagnostics, 0, compiler_options.new_parser); + std::cerr << diagnostics.render(lm, compiler_options); + if (!r.ok) { + return 1; + } + LCompilers::LPython::AST::ast_t* ast = r.result; + diagnostics.diagnostics.clear(); + LCompilers::Result + r1 = LCompilers::LPython::python_ast_to_asr(al, lm, nullptr, *ast, diagnostics, compiler_options, true, "__main__", infile); + std::cerr << diagnostics.render(lm, compiler_options); + if (r1.ok) { + LCompilers::PassManager pass_manager; + compiler_options.po.always_run = true; + compiler_options.po.run_fun = "f"; + pass_manager.dump_all_passes(al, r1.result, compiler_options.po, diagnostics, lm); + std::cerr << diagnostics.render(lm, compiler_options); + } else { + LCOMPILERS_ASSERT(diagnostics.has_error()) + return 1; + } + return 0; +} + #ifdef HAVE_LFORTRAN_RAPIDJSON int get_symbols (const std::string &infile, @@ -1549,6 +1588,8 @@ int main(int argc, char *argv[]) app.add_flag("--get-rtl-header-dir", print_rtl_header_dir, "Print the path to the runtime library header file"); app.add_flag("--get-rtl-dir", print_rtl_dir, "Print the path to the runtime library file"); app.add_flag("--verbose", compiler_options.po.verbose, "Print debugging statements"); + app.add_flag("--dump-all-passes", compiler_options.po.dump_all_passes, "Apply all the passes and dump the ASR into a file"); + app.add_flag("--dump-all-passes-fortran", compiler_options.po.dump_fortran, "Apply all passes and dump the ASR after each pass into fortran file"); app.add_flag("--cumulative", compiler_options.po.pass_cumulative, "Apply all the passes cumulatively till the given pass"); app.add_flag("--enable-cpython", compiler_options.enable_cpython, "Enable CPython runtime"); app.add_flag("--enable-symengine", compiler_options.enable_symengine, "Enable Symengine runtime"); @@ -1726,6 +1767,10 @@ int main(int argc, char *argv[]) outfile = basename + ".out"; } + if (compiler_options.po.dump_fortran || compiler_options.po.dump_all_passes) { + dump_all_passes(arg_file, compiler_options); + } + // if (arg_E) { // return emit_c_preprocessor(arg_file, compiler_options); // } diff --git a/src/lpython/semantics/python_ast_to_asr.cpp b/src/lpython/semantics/python_ast_to_asr.cpp index e6e17da543..86b72e5bec 100644 --- a/src/lpython/semantics/python_ast_to_asr.cpp +++ b/src/lpython/semantics/python_ast_to_asr.cpp @@ -23,6 +23,8 @@ #include #include #include +#include +#include #include #include @@ -7940,6 +7942,21 @@ Result python_ast_to_asr(Allocator &al, LocationManager return res.error; } ASR::TranslationUnit_t *tu = ASR::down_cast2(unit); + if (compiler_options.po.dump_all_passes) { + std::ofstream outfile ("pass_00_initial_asr_01.clj"); + outfile << ";; ASR after SymbolTable Visitor\n" << pickle(*tu, false, true, compiler_options.po.with_intrinsic_mods) << "\n"; + outfile.close(); + } + if (compiler_options.po.dump_fortran) { + LCompilers::Result fortran_code = LCompilers::asr_to_fortran(*tu, diagnostics, false, 4); + if (!fortran_code.ok) { + LCOMPILERS_ASSERT(diagnostics.has_error()); + throw LCompilersException("Fortran code could not be generated after symbol_table_visitor"); + } + std::ofstream outfile ("pass_fortran_00_initial_code_01.f90"); + outfile << "! Fortran code after SymbolTable Visitor\n" << fortran_code.result << "\n"; + outfile.close(); + } #if defined(WITH_LFORTRAN_ASSERT) if (!asr_verify(*tu, true, diagnostics)) { std::cerr << diagnostics.render2(); @@ -7955,6 +7972,21 @@ Result python_ast_to_asr(Allocator &al, LocationManager } else { return res2.error; } + if (compiler_options.po.dump_all_passes) { + std::ofstream outfile ("pass_00_initial_asr_02.clj"); + outfile << ";; Initial ASR after Body Visitor\n" << pickle(*tu, false, true, compiler_options.po.with_intrinsic_mods) << "\n"; + outfile.close(); + } + if (compiler_options.po.dump_fortran) { + LCompilers::Result fortran_code = LCompilers::asr_to_fortran(*tu, diagnostics, false, 4); + if (!fortran_code.ok) { + LCOMPILERS_ASSERT(diagnostics.has_error()); + throw LCompilersException("Fortran code could not be generated after body_visitor"); + } + std::ofstream outfile ("pass_fortran_00_initial_code_02.f90"); + outfile << "! Fortran code after Body Visitor\n" << fortran_code.result << "\n"; + outfile.close(); + } #if defined(WITH_LFORTRAN_ASSERT) diag::Diagnostics diagnostics; if (!asr_verify(*tu, true, diagnostics)) { From 79bf06ca3ecefe6b66c72cf38cfd737325b92d5a Mon Sep 17 00:00:00 2001 From: Shaikh Ubaid Date: Sun, 12 Nov 2023 10:51:06 +0530 Subject: [PATCH 2/2] Remove duplicate flags from CompilerOptions --- src/bin/lpython.cpp | 32 ++++++++++----------- src/libasr/utils.h | 5 ---- src/lpython/semantics/python_ast_to_asr.cpp | 4 +-- 3 files changed, 18 insertions(+), 23 deletions(-) diff --git a/src/bin/lpython.cpp b/src/bin/lpython.cpp index 43263fa0c4..3d75cf7190 100644 --- a/src/bin/lpython.cpp +++ b/src/bin/lpython.cpp @@ -220,12 +220,12 @@ int emit_asr(const std::string &infile, pass_manager.apply_passes(al, asr, compiler_options.po, diagnostics); - if (compiler_options.tree) { + if (compiler_options.po.tree) { std::cout << LCompilers::LPython::pickle_tree(*asr, compiler_options.use_colors, with_intrinsic_modules) << std::endl; - } else if (compiler_options.json) { + } else if (compiler_options.po.json) { std::cout << LCompilers::LPython::pickle_json(*asr, lm, with_intrinsic_modules) << std::endl; - } else if (compiler_options.visualize) { + } else if (compiler_options.po.visualize) { std::string astr_data_json = LCompilers::LPython::pickle_json(*asr, lm, with_intrinsic_modules); return visualize_json(astr_data_json, compiler_options.platform); } else { @@ -790,7 +790,7 @@ int compile_python_to_object_file( auto ast_to_asr_start = std::chrono::high_resolution_clock::now(); LCompilers::Result r1 = LCompilers::LPython::python_ast_to_asr(al, lm, nullptr, *ast, diagnostics, compiler_options, - !(arg_c && compiler_options.disable_main), "__main__", infile); + !(arg_c && compiler_options.po.disable_main), "__main__", infile); auto ast_to_asr_end = std::chrono::high_resolution_clock::now(); times.push_back(std::make_pair("AST to ASR", std::chrono::duration(ast_to_asr_end - ast_to_asr_start).count())); @@ -801,7 +801,7 @@ int compile_python_to_object_file( return 2; } LCompilers::ASR::TranslationUnit_t* asr = r1.result; - if( compiler_options.disable_main ) { + if( compiler_options.po.disable_main ) { int err = LCompilers::LPython::save_pyc_files(*asr, infile); if( err ) { return err; @@ -909,7 +909,7 @@ int compile_to_binary_wasm( return 2; } LCompilers::ASR::TranslationUnit_t* asr = r1.result; - if( compiler_options.disable_main ) { + if( compiler_options.po.disable_main ) { int err = LCompilers::LPython::save_pyc_files(*asr, infile); if( err ) { return err; @@ -982,7 +982,7 @@ int compile_to_binary_x86( return 2; } LCompilers::ASR::TranslationUnit_t* asr = r1.result; - if( compiler_options.disable_main ) { + if( compiler_options.po.disable_main ) { int err = LCompilers::LPython::save_pyc_files(*asr, infile); if( err ) { return err; @@ -1056,7 +1056,7 @@ int compile_to_binary_wasm_to_x86( return 2; } LCompilers::ASR::TranslationUnit_t* asr = r1.result; - if( compiler_options.disable_main ) { + if( compiler_options.po.disable_main ) { int err = LCompilers::LPython::save_pyc_files(*asr, infile); if( err ) { return err; @@ -1568,12 +1568,12 @@ int main(int argc, char *argv[]) app.add_flag("--with-intrinsic-mods", with_intrinsic_modules, "Show intrinsic modules in ASR"); app.add_flag("--no-color", arg_no_color, "Turn off colored AST/ASR"); app.add_flag("--no-indent", arg_no_indent, "Turn off Indented print ASR/AST"); - app.add_flag("--tree", compiler_options.tree, "Tree structure print ASR/AST"); - app.add_flag("--json", compiler_options.json, "Print ASR/AST Json format"); - app.add_flag("--visualize", compiler_options.visualize, "Print ASR/AST Visualization"); + app.add_flag("--tree", compiler_options.po.tree, "Tree structure print ASR/AST"); + app.add_flag("--json", compiler_options.po.json, "Print ASR/AST Json format"); + app.add_flag("--visualize", compiler_options.po.visualize, "Print ASR/AST Visualization"); app.add_option("--pass", arg_pass, "Apply the ASR pass and show ASR (implies --show-asr)"); app.add_option("--skip-pass", skip_pass, "Skip an ASR pass in default pipeline"); - app.add_flag("--disable-main", compiler_options.disable_main, "Do not generate any code for the `main` function"); + app.add_flag("--disable-main", compiler_options.po.disable_main, "Do not generate any code for the `main` function"); app.add_flag("--symtab-only", compiler_options.symtab_only, "Only create symbol tables in ASR (skip executable stmt)"); app.add_flag("--time-report", time_report, "Show compilation time report"); app.add_flag("--static", static_link, "Create a static executable"); @@ -1582,7 +1582,7 @@ int main(int argc, char *argv[]) app.add_option("--backend", arg_backend, "Select a backend (llvm, cpp, x86, wasm, wasm_x86, wasm_x64)")->capture_default_str(); app.add_flag("--enable-bounds-checking", compiler_options.enable_bounds_checking, "Turn on index bounds checking"); app.add_flag("--openmp", compiler_options.openmp, "Enable openmp"); - app.add_flag("--fast", compiler_options.fast, "Best performance (disable strict standard compliance)"); + app.add_flag("--fast", compiler_options.po.fast, "Best performance (disable strict standard compliance)"); app.add_option("--target", compiler_options.target, "Generate code for the given target")->capture_default_str(); app.add_flag("--print-targets", print_targets, "Print the registered targets"); app.add_flag("--get-rtl-header-dir", print_rtl_header_dir, "Print the path to the runtime library header file"); @@ -1639,9 +1639,9 @@ int main(int argc, char *argv[]) lcompilers_unique_ID = separate_compilation ? LCompilers::get_unique_ID(): ""; - if( compiler_options.fast && compiler_options.enable_bounds_checking ) { + if( compiler_options.po.fast && compiler_options.enable_bounds_checking ) { // ReleaseSafe Mode - } else if ( compiler_options.fast ) { + } else if ( compiler_options.po.fast ) { // Release Mode lpython_pass_manager.use_optimization_passes(); } else { @@ -1768,7 +1768,7 @@ int main(int argc, char *argv[]) } if (compiler_options.po.dump_fortran || compiler_options.po.dump_all_passes) { - dump_all_passes(arg_file, compiler_options); + dump_all_passes(arg_file, runtime_library_dir, compiler_options); } // if (arg_E) { diff --git a/src/libasr/utils.h b/src/libasr/utils.h index 50b5929b91..073a7bebe1 100644 --- a/src/libasr/utils.h +++ b/src/libasr/utils.h @@ -68,15 +68,10 @@ struct CompilerOptions { bool c_preprocessor = false; std::vector c_preprocessor_defines; bool prescan = true; - bool disable_main = false; bool symtab_only = false; bool show_stacktrace = false; bool use_colors = true; bool indent = true; - bool json = false; - bool tree = false; - bool visualize = false; - bool fast = false; bool openmp = false; bool generate_object_code = false; bool no_warnings = false; diff --git a/src/lpython/semantics/python_ast_to_asr.cpp b/src/lpython/semantics/python_ast_to_asr.cpp index 86b72e5bec..03d0420355 100644 --- a/src/lpython/semantics/python_ast_to_asr.cpp +++ b/src/lpython/semantics/python_ast_to_asr.cpp @@ -139,7 +139,7 @@ ASR::TranslationUnit_t* compile_module_till_asr( // Convert the module from AST to ASR CompilerOptions compiler_options; - compiler_options.disable_main = true; + compiler_options.po.disable_main = true; compiler_options.symtab_only = false; Result r2 = python_ast_to_asr(al, lm, symtab, *ast, diagnostics, compiler_options, false, module_name, infile, allow_implicit_casting); @@ -7996,7 +7996,7 @@ Result python_ast_to_asr(Allocator &al, LocationManager #endif } - if (main_module && !compiler_options.disable_main) { + if (main_module && !compiler_options.po.disable_main) { // If it is a main module, turn it into a program // Note: we can modify this behavior for interactive mode later