| /* |
| * yosys -- Yosys Open SYnthesis Suite |
| * |
| * Copyright (C) 2020 Antmicro |
| |
| * Based on frontends/json/jsonparse.cc |
| * |
| * Permission to use, copy, modify, and/or distribute this software for any |
| * purpose with or without fee is hereby granted, provided that the above |
| * copyright notice and this permission notice appear in all copies. |
| * |
| * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |
| * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |
| * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |
| * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |
| * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN |
| * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF |
| * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |
| * |
| */ |
| |
| #include "UhdmAst.h" |
| #include "frontends/ast/ast.h" |
| #include "kernel/yosys.h" |
| |
| #if defined(_MSC_VER) |
| #include <direct.h> |
| #include <process.h> |
| #else |
| #include <sys/param.h> |
| #include <unistd.h> |
| #endif |
| |
| #include "surelog/ErrorReporting/Report.h" |
| #include "surelog/surelog.h" |
| |
| namespace UHDM |
| { |
| extern void visit_object(vpiHandle obj_h, int indent, const char *relation, std::set<const BaseClass *> *visited, std::ostream &out, |
| bool shallowVisit = false); |
| } |
| |
| YOSYS_NAMESPACE_BEGIN |
| |
| std::vector<vpiHandle> executeCompilation(SURELOG::SymbolTable *symbolTable, SURELOG::ErrorContainer *errors, SURELOG::CommandLineParser *clp, |
| SURELOG::scompiler *compiler) |
| { |
| bool success = true; |
| bool noFatalErrors = true; |
| unsigned int codedReturn = 0; |
| clp->setWriteUhdm(false); |
| errors->printMessages(clp->muteStdout()); |
| std::vector<vpiHandle> the_design; |
| if (success && (!clp->help())) { |
| compiler = SURELOG::start_compiler(clp); |
| if (!compiler) |
| codedReturn |= 1; |
| the_design.push_back(SURELOG::get_uhdm_design(compiler)); |
| } |
| SURELOG::ErrorContainer::Stats stats; |
| if (!clp->help()) { |
| stats = errors->getErrorStats(); |
| if (stats.nbFatal) |
| codedReturn |= 1; |
| if (stats.nbSyntax) |
| codedReturn |= 2; |
| } |
| bool noFErrors = true; |
| if (!clp->help()) |
| noFErrors = errors->printStats(stats, clp->muteStdout()); |
| if (noFErrors == false) { |
| noFatalErrors = false; |
| } |
| if ((!noFatalErrors) || (!success)) |
| codedReturn |= 1; |
| return the_design; |
| } |
| |
| struct UhdmSurelogAstFrontend : public Frontend { |
| UhdmSurelogAstFrontend() : Frontend("verilog_with_uhdm", "generate/read UHDM file") {} |
| void help() |
| { |
| // |---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---|---v---| |
| log("\n"); |
| log(" read_verilog_with_uhdm [options] [filenames]\n"); |
| log("\n"); |
| log("Generate or load design from a UHDM file into the current design\n"); |
| log("\n"); |
| log(" -process\n"); |
| log(" loads design from given UHDM file\n"); |
| log("\n"); |
| log(" -noassert\n"); |
| log(" ignore assert() statements"); |
| log("\n"); |
| log(" -debug\n"); |
| log(" print debug info to stdout"); |
| log("\n"); |
| log(" -report [directory]\n"); |
| log(" write a coverage report for the UHDM file\n"); |
| log("\n"); |
| log(" -defer\n"); |
| log(" only read the abstract syntax tree and defer actual compilation\n"); |
| log(" to a later 'hierarchy' command. Useful in cases where the default\n"); |
| log(" parameters of modules yield invalid or not synthesizable code.\n"); |
| log("\n"); |
| } |
| void execute(std::istream *&f, std::string filename, std::vector<std::string> args, RTLIL::Design *design) |
| { |
| log_header(design, "Executing Verilog with UHDM frontend.\n"); |
| |
| UhdmAstShared shared; |
| UhdmAst uhdm_ast(shared); |
| bool defer = false; |
| |
| std::string report_directory; |
| auto it = args.begin(); |
| while (it != args.end()) { |
| if (*it == "-debug") { |
| shared.debug_flag = true; |
| it = args.erase(it); |
| } else if (*it == "-report" && (it = args.erase(it)) < args.end()) { |
| report_directory = *it; |
| shared.stop_on_error = false; |
| it = args.erase(it); |
| } else if (*it == "-noassert") { |
| shared.no_assert = true; |
| it = args.erase(it); |
| } else if (*it == "-defer") { |
| defer = true; |
| it = args.erase(it); |
| } else { |
| ++it; |
| } |
| } |
| std::vector<const char *> cstrings; |
| cstrings.reserve(args.size()); |
| for (size_t i = 0; i < args.size(); ++i) |
| cstrings.push_back(const_cast<char *>(args[i].c_str())); |
| |
| SURELOG::SymbolTable *symbolTable = new SURELOG::SymbolTable(); |
| SURELOG::ErrorContainer *errors = new SURELOG::ErrorContainer(symbolTable); |
| SURELOG::CommandLineParser *clp = new SURELOG::CommandLineParser(errors, symbolTable, false, false); |
| bool success = clp->parseCommandLine(cstrings.size(), &cstrings[0]); |
| if (!success) { |
| log_error("Error parsing Surelog arguments!\n"); |
| } |
| SURELOG::scompiler *compiler = nullptr; |
| const std::vector<vpiHandle> uhdm_design = executeCompilation(symbolTable, errors, clp, compiler); |
| struct AST::AstNode *current_ast = uhdm_ast.visit_designs(uhdm_design); |
| if (report_directory != "") { |
| shared.report.write(report_directory); |
| } |
| bool dump_ast1 = shared.debug_flag; |
| bool dump_ast2 = shared.debug_flag; |
| bool dont_redefine = false; |
| bool default_nettype_wire = true; |
| AST::process(design, current_ast, dump_ast1, dump_ast2, false, false, false, false, false, false, false, false, false, false, false, false, |
| false, false, dont_redefine, false, defer, default_nettype_wire); |
| delete current_ast; |
| SURELOG::shutdown_compiler(compiler); |
| delete clp; |
| delete symbolTable; |
| delete errors; |
| } |
| } UhdmSurelogAstFrontend; |
| |
| YOSYS_NAMESPACE_END |