diff options
Diffstat (limited to 'frontends')
-rw-r--r-- | frontends/ast/ast.cc | 22 | ||||
-rw-r--r-- | frontends/ast/ast.h | 4 | ||||
-rw-r--r-- | frontends/verilog/verilog_frontend.cc | 14 | ||||
-rw-r--r-- | frontends/verilog/verilog_frontend.h | 3 | ||||
-rw-r--r-- | frontends/verilog/verilog_parser.y | 10 |
5 files changed, 42 insertions, 11 deletions
diff --git a/frontends/ast/ast.cc b/frontends/ast/ast.cc index d48996167..720b3f3d1 100644 --- a/frontends/ast/ast.cc +++ b/frontends/ast/ast.cc @@ -46,7 +46,7 @@ namespace AST { // instantiate global variables (private API) namespace AST_INTERNAL { bool flag_dump_ast1, flag_dump_ast2, flag_no_dump_ptr, flag_dump_vlog1, flag_dump_vlog2, flag_dump_rtlil, flag_nolatches, flag_nomeminit; - bool flag_nomem2reg, flag_mem2reg, flag_lib, flag_noopt, flag_icells, flag_autowire; + bool flag_nomem2reg, flag_mem2reg, flag_lib, flag_wb, flag_noopt, flag_icells, flag_autowire; AstNode *current_ast, *current_ast_mod; std::map<std::string, AstNode*> current_scope; const dict<RTLIL::SigBit, RTLIL::SigBit> *genRTLIL_subst_ptr = NULL; @@ -956,7 +956,18 @@ static AstModule* process_module(AstNode *ast, bool defer, AstNode *original_ast log("--- END OF AST DUMP ---\n"); } + if (flag_wb) { + if (!ast->attributes.count("\\whitebox")) + goto blackbox_module; + AstNode *n = ast->attributes.at("\\whitebox"); + if (n->type != AST_CONSTANT) + log_file_error(ast->filename, ast->linenum, "Whitebox attribute with non-constant value!\n"); + if (!n->asBool()) + goto blackbox_module; + } + if (flag_lib) { + blackbox_module: std::vector<AstNode*> new_children; for (auto child : ast->children) { if (child->type == AST_WIRE && (child->is_input || child->is_output)) { @@ -970,6 +981,10 @@ static AstModule* process_module(AstNode *ast, bool defer, AstNode *original_ast } } ast->children.swap(new_children); + if (ast->attributes.count("\\whitebox")) { + delete ast->attributes.at("\\whitebox"); + ast->attributes.erase("\\whitebox"); + } ast->attributes["\\blackbox"] = AstNode::mkconst_int(1, false); } @@ -1010,6 +1025,7 @@ static AstModule* process_module(AstNode *ast, bool defer, AstNode *original_ast current_module->nomem2reg = flag_nomem2reg; current_module->mem2reg = flag_mem2reg; current_module->lib = flag_lib; + current_module->wb = flag_wb; current_module->noopt = flag_noopt; current_module->icells = flag_icells; current_module->autowire = flag_autowire; @@ -1026,7 +1042,7 @@ static AstModule* process_module(AstNode *ast, bool defer, AstNode *original_ast // create AstModule instances for all modules in the AST tree and add them to 'design' void AST::process(RTLIL::Design *design, AstNode *ast, bool dump_ast1, bool dump_ast2, bool no_dump_ptr, bool dump_vlog1, bool dump_vlog2, bool dump_rtlil, - bool nolatches, bool nomeminit, bool nomem2reg, bool mem2reg, bool lib, bool noopt, bool icells, bool nooverwrite, bool overwrite, bool defer, bool autowire) + bool nolatches, bool nomeminit, bool nomem2reg, bool mem2reg, bool lib, bool wb, bool noopt, bool icells, bool nooverwrite, bool overwrite, bool defer, bool autowire) { current_ast = ast; flag_dump_ast1 = dump_ast1; @@ -1040,6 +1056,7 @@ void AST::process(RTLIL::Design *design, AstNode *ast, bool dump_ast1, bool dump flag_nomem2reg = nomem2reg; flag_mem2reg = mem2reg; flag_lib = lib; + flag_wb = wb; flag_noopt = noopt; flag_icells = icells; flag_autowire = autowire; @@ -1374,6 +1391,7 @@ std::string AstModule::derive_common(RTLIL::Design *design, dict<RTLIL::IdString flag_nomem2reg = nomem2reg; flag_mem2reg = mem2reg; flag_lib = lib; + flag_wb = wb; flag_noopt = noopt; flag_icells = icells; flag_autowire = autowire; diff --git a/frontends/ast/ast.h b/frontends/ast/ast.h index ddd59d4be..610e00fbf 100644 --- a/frontends/ast/ast.h +++ b/frontends/ast/ast.h @@ -283,13 +283,13 @@ namespace AST // process an AST tree (ast must point to an AST_DESIGN node) and generate RTLIL code void process(RTLIL::Design *design, AstNode *ast, bool dump_ast1, bool dump_ast2, bool no_dump_ptr, bool dump_vlog1, bool dump_vlog2, bool dump_rtlil, bool nolatches, bool nomeminit, - bool nomem2reg, bool mem2reg, bool lib, bool noopt, bool icells, bool nooverwrite, bool overwrite, bool defer, bool autowire); + bool nomem2reg, bool mem2reg, bool lib, bool wb, bool noopt, bool icells, bool nooverwrite, bool overwrite, bool defer, bool autowire); // parametric modules are supported directly by the AST library // therefore we need our own derivate of RTLIL::Module with overloaded virtual functions struct AstModule : RTLIL::Module { AstNode *ast; - bool nolatches, nomeminit, nomem2reg, mem2reg, lib, noopt, icells, autowire; + bool nolatches, nomeminit, nomem2reg, mem2reg, lib, wb, noopt, icells, autowire; ~AstModule() YS_OVERRIDE; RTLIL::IdString derive(RTLIL::Design *design, dict<RTLIL::IdString, RTLIL::Const> parameters, bool mayfail) YS_OVERRIDE; RTLIL::IdString derive(RTLIL::Design *design, dict<RTLIL::IdString, RTLIL::Const> parameters, dict<RTLIL::IdString, RTLIL::Module*> interfaces, dict<RTLIL::IdString, RTLIL::IdString> modports, bool mayfail) YS_OVERRIDE; diff --git a/frontends/verilog/verilog_frontend.cc b/frontends/verilog/verilog_frontend.cc index 504f8b3f3..4e2c5abb5 100644 --- a/frontends/verilog/verilog_frontend.cc +++ b/frontends/verilog/verilog_frontend.cc @@ -148,6 +148,10 @@ struct VerilogFrontend : public Frontend { log(" -lib\n"); log(" only create empty blackbox modules. This implies -DBLACKBOX.\n"); log("\n"); + log(" -wb\n"); + log(" like -lib, except do not touch modules with the whitebox\n"); + log(" attribute set. This also implies -DBLACKBOX.\n"); + log("\n"); log(" -noopt\n"); log(" don't perform basic optimizations (such as const folding) in the\n"); log(" high-level front-end.\n"); @@ -228,6 +232,7 @@ struct VerilogFrontend : public Frontend { norestrict_mode = false; assume_asserts_mode = false; lib_mode = false; + wb_mode = false; default_nettype_wire = true; log_header(design, "Executing Verilog-2005 frontend.\n"); @@ -329,11 +334,16 @@ struct VerilogFrontend : public Frontend { flag_nodpi = true; continue; } - if (arg == "-lib") { + if (arg == "-lib" && !wb_mode) { lib_mode = true; defines_map["BLACKBOX"] = string(); continue; } + if (arg == "-wb" && !lib_mode) { + wb_mode = true; + defines_map["BLACKBOX"] = string(); + continue; + } if (arg == "-noopt") { flag_noopt = true; continue; @@ -429,7 +439,7 @@ struct VerilogFrontend : public Frontend { if (flag_nodpi) error_on_dpi_function(current_ast); - AST::process(design, current_ast, flag_dump_ast1, flag_dump_ast2, flag_no_dump_ptr, flag_dump_vlog1, flag_dump_vlog2, flag_dump_rtlil, flag_nolatches, flag_nomeminit, flag_nomem2reg, flag_mem2reg, lib_mode, flag_noopt, flag_icells, flag_nooverwrite, flag_overwrite, flag_defer, default_nettype_wire); + AST::process(design, current_ast, flag_dump_ast1, flag_dump_ast2, flag_no_dump_ptr, flag_dump_vlog1, flag_dump_vlog2, flag_dump_rtlil, flag_nolatches, flag_nomeminit, flag_nomem2reg, flag_mem2reg, lib_mode, wb_mode, flag_noopt, flag_icells, flag_nooverwrite, flag_overwrite, flag_defer, default_nettype_wire); if (!flag_nopp) delete lexin; diff --git a/frontends/verilog/verilog_frontend.h b/frontends/verilog/verilog_frontend.h index 523bbc897..b5cf70c57 100644 --- a/frontends/verilog/verilog_frontend.h +++ b/frontends/verilog/verilog_frontend.h @@ -72,6 +72,9 @@ namespace VERILOG_FRONTEND // running in -lib mode extern bool lib_mode; + // running in -wb mode + extern bool wb_mode; + // lexer input stream extern std::istream *lexin; } diff --git a/frontends/verilog/verilog_parser.y b/frontends/verilog/verilog_parser.y index 52685f637..122eb1230 100644 --- a/frontends/verilog/verilog_parser.y +++ b/frontends/verilog/verilog_parser.y @@ -59,7 +59,7 @@ namespace VERILOG_FRONTEND { std::vector<char> case_type_stack; bool do_not_require_port_stubs; bool default_nettype_wire; - bool sv_mode, formal_mode, lib_mode; + bool sv_mode, formal_mode, lib_mode, wb_mode; bool noassert_mode, noassume_mode, norestrict_mode; bool assume_asserts_mode, assert_assumes_mode; bool current_wire_rand, current_wire_const; @@ -1906,7 +1906,7 @@ basic_expr: if ($4->substr(0, 1) != "'") frontend_verilog_yyerror("Cast operation must be applied on sized constants e.g. (<expr>)<constval> , while %s is not a sized constant.", $4->c_str()); AstNode *bits = $2; - AstNode *val = const2ast(*$4, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode); + AstNode *val = const2ast(*$4, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode && !wb_mode); if (val == NULL) log_error("Value conversion failed: `%s'\n", $4->c_str()); $$ = new AstNode(AST_TO_BITS, bits, val); @@ -1917,7 +1917,7 @@ basic_expr: frontend_verilog_yyerror("Cast operation must be applied on sized constants, e.g. <ID>\'d0, while %s is not a sized constant.", $2->c_str()); AstNode *bits = new AstNode(AST_IDENTIFIER); bits->str = *$1; - AstNode *val = const2ast(*$2, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode); + AstNode *val = const2ast(*$2, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode && !wb_mode); if (val == NULL) log_error("Value conversion failed: `%s'\n", $2->c_str()); $$ = new AstNode(AST_TO_BITS, bits, val); @@ -1925,14 +1925,14 @@ basic_expr: delete $2; } | TOK_CONSTVAL TOK_CONSTVAL { - $$ = const2ast(*$1 + *$2, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode); + $$ = const2ast(*$1 + *$2, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode && !wb_mode); if ($$ == NULL || (*$2)[0] != '\'') log_error("Value conversion failed: `%s%s'\n", $1->c_str(), $2->c_str()); delete $1; delete $2; } | TOK_CONSTVAL { - $$ = const2ast(*$1, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode); + $$ = const2ast(*$1, case_type_stack.size() == 0 ? 0 : case_type_stack.back(), !lib_mode && !wb_mode); if ($$ == NULL) log_error("Value conversion failed: `%s'\n", $1->c_str()); delete $1; |