diff options
Diffstat (limited to 'frontends')
-rw-r--r-- | frontends/ast/genrtlil.cc | 15 | ||||
-rw-r--r-- | frontends/ilang/ilang_lexer.l | 1 | ||||
-rw-r--r-- | frontends/ilang/ilang_parser.y | 8 |
3 files changed, 19 insertions, 5 deletions
diff --git a/frontends/ast/genrtlil.cc b/frontends/ast/genrtlil.cc index 3c57162aa..229a3b596 100644 --- a/frontends/ast/genrtlil.cc +++ b/frontends/ast/genrtlil.cc @@ -220,12 +220,19 @@ struct AST_INTERNAL::ProcessGenerator subst_lvalue_to = new_temp_signal(subst_lvalue_from); subst_lvalue_map = subst_lvalue_from.to_sigbit_map(subst_lvalue_to); + bool found_global_syncs = false; bool found_anyedge_syncs = false; for (auto child : always->children) - if (child->type == AST_EDGE) - found_anyedge_syncs = true; + if (child->type == AST_EDGE) { + if (GetSize(child->children) == 1 && child->children.at(0)->type == AST_IDENTIFIER && child->children.at(0)->str == "\\$global_clock") + found_global_syncs = true; + else + found_anyedge_syncs = true; + } if (found_anyedge_syncs) { + if (found_global_syncs) + log_error("Found non-synthesizable event list at %s:%d!\n", always->filename.c_str(), always->linenum); log("Note: Assuming pure combinatorial block at %s:%d in\n", always->filename.c_str(), always->linenum); log("compliance with IEC 62142(E):2005 / IEEE Std. 1364.1(E):2002. Recommending\n"); log("use of @* instead of @(...) for better match of synthesis and simulation.\n"); @@ -236,7 +243,7 @@ struct AST_INTERNAL::ProcessGenerator for (auto child : always->children) if (child->type == AST_POSEDGE || child->type == AST_NEGEDGE) { found_clocked_sync = true; - if (found_anyedge_syncs) + if (found_global_syncs || found_anyedge_syncs) log_error("Found non-synthesizable event list at %s:%d!\n", always->filename.c_str(), always->linenum); RTLIL::SyncRule *syncrule = new RTLIL::SyncRule; syncrule->type = child->type == AST_POSEDGE ? RTLIL::STp : RTLIL::STn; @@ -248,7 +255,7 @@ struct AST_INTERNAL::ProcessGenerator } if (proc->syncs.empty()) { RTLIL::SyncRule *syncrule = new RTLIL::SyncRule; - syncrule->type = RTLIL::STa; + syncrule->type = found_global_syncs ? RTLIL::STg : RTLIL::STa; syncrule->signal = RTLIL::SigSpec(); addChunkActions(syncrule->actions, subst_lvalue_from, subst_lvalue_to, true); proc->syncs.push_back(syncrule); diff --git a/frontends/ilang/ilang_lexer.l b/frontends/ilang/ilang_lexer.l index 415de74eb..842388548 100644 --- a/frontends/ilang/ilang_lexer.l +++ b/frontends/ilang/ilang_lexer.l @@ -74,6 +74,7 @@ USING_YOSYS_NAMESPACE "negedge" { return TOK_NEGEDGE; } "edge" { return TOK_EDGE; } "always" { return TOK_ALWAYS; } +"global" { return TOK_GLOBAL; } "init" { return TOK_INIT; } "update" { return TOK_UPDATE; } "process" { return TOK_PROCESS; } diff --git a/frontends/ilang/ilang_parser.y b/frontends/ilang/ilang_parser.y index cc31c8642..fe5f23d66 100644 --- a/frontends/ilang/ilang_parser.y +++ b/frontends/ilang/ilang_parser.y @@ -57,7 +57,7 @@ USING_YOSYS_NAMESPACE %token <integer> TOK_INT %token TOK_AUTOIDX TOK_MODULE TOK_WIRE TOK_WIDTH TOK_INPUT TOK_OUTPUT TOK_INOUT %token TOK_CELL TOK_CONNECT TOK_SWITCH TOK_CASE TOK_ASSIGN TOK_SYNC -%token TOK_LOW TOK_HIGH TOK_POSEDGE TOK_NEGEDGE TOK_EDGE TOK_ALWAYS TOK_INIT +%token TOK_LOW TOK_HIGH TOK_POSEDGE TOK_NEGEDGE TOK_EDGE TOK_ALWAYS TOK_GLOBAL TOK_INIT %token TOK_UPDATE TOK_PROCESS TOK_END TOK_INVALID TOK_EOL TOK_OFFSET %token TOK_PARAMETER TOK_ATTRIBUTE TOK_MEMORY TOK_SIZE TOK_SIGNED TOK_UPTO @@ -301,6 +301,12 @@ sync_list: rule->signal = RTLIL::SigSpec(); current_process->syncs.push_back(rule); } update_list | + sync_list TOK_SYNC TOK_GLOBAL EOL { + RTLIL::SyncRule *rule = new RTLIL::SyncRule; + rule->type = RTLIL::SyncType::STg; + rule->signal = RTLIL::SigSpec(); + current_process->syncs.push_back(rule); + } update_list | sync_list TOK_SYNC TOK_INIT EOL { RTLIL::SyncRule *rule = new RTLIL::SyncRule; rule->type = RTLIL::SyncType::STi; |