diff --git a/.gitignore b/.gitignore index 725173409..e9235a3a7 100644 --- a/.gitignore +++ b/.gitignore @@ -17,6 +17,7 @@ README TAGS autom4te.cache +compile_commands.json config.cache config.status configure diff --git a/.travis.yml b/.travis.yml index 0307d98ac..71442d049 100644 --- a/.travis.yml +++ b/.travis.yml @@ -27,6 +27,7 @@ before_install: # Perl modules needed for testing - yes yes | sudo cpan -fi Unix::Processors Parallel::Forker Bit::Vector - sudo apt-get install gdb gtkwave + - sudo apt-get install libgoogle-perftools-dev before_script: - bash -x ci/build_vcddiff.sh - bash -x ci/build_verilator.sh diff --git a/Changes b/Changes index 6d0b6c432..b62f845a3 100644 --- a/Changes +++ b/Changes @@ -9,14 +9,36 @@ The contributors that suggested a given feature are shown in []. Thanks! ** Add -match to lint_off to waive warnings. [Philipp Wagner] -*** Support $readmem/$writemem with assoc arrarys. Closes #2100. [agrobman] +*** Verilation speed improvements, #2133, #2138. [Geza Lore] -**** Support left justified $display. Closes #2101. [Pieter Kapsenberg] +*** Support libgoogle-perftools-dev's libtcmalloc if available, #2137. [Geza Lore] + +*** Support $readmem/$writemem with assoc arrarys, #2100. [agrobman] + +**** Support type(expression) operator and $typename, #1650. + +**** Support left justified $display, #2101. [Pieter Kapsenberg] + +**** Support string character access via indexing. + +**** Support enum.next(k) with constant k > 1, #2125. [Tobias Rosenkranz] **** Add parameter values in XML. #2110. [Pieter Kapsenberg] +**** Add loc column location in XML (replaces fl), #2122. [Pieter Kapsenberg] + **** Add error on misused define. [Topa Tota] +**** Add parameter to set maximum signal width, #2082. [Øyvind Harboe] + +**** Add warning on genvar in normal for loop, #2143. [yurivict] + +**** Fix VPI scope naming for public modules. [Nandu Raj] + +**** Fix FST tracing of enums inside structs. [fsiegle] + +**** Fix WIDTH warning on for more information. --language Default language standard to parse +libext++[ext]... Extensions for finding modules --lint-only Lint, but do not make output + --max-num-width Maximum number width (default: 64K) --MMD Create .d dependency files --MP Create phony dependency targets --Mdir Name of output object directory @@ -968,6 +969,11 @@ stylistic and not enabled by default. If the design is not to be completely Verilated see also the --bbox-sys and --bbox-unsup options. +=item --max-num-width I + +Set the maximum number literal width (e.g. in 1024'd22 this it the 1024). +Defaults to 64K. + =item --MMD =item --no-MMD @@ -3144,7 +3150,7 @@ analysis.) For example: The clock_enable attribute will cause the clock gate to be ignored in the scheduling algorithm, sometimes required for correct clock behavior, and always improving performance. It's also a good idea to enable the -IMPERFECTSCH warning, to insure all clock enables are properly recognized. +IMPERFECTSCH warning, to ensure all clock enables are properly recognized. Same as C in configuration files, see L for more information. @@ -4694,6 +4700,37 @@ that is not yet supported in Verilator. See the Limitations chapter. =back +=head1 DEPRECATIONS + +The following deprecated items are scheduled for future removal: + +=over 4 + +=item Pre-C++11 compiler support + +Verilator supports pre-C++11 compilers for non-threaded models when +configured with --enable-prec11. This flag will be removed and C++11 +compilers will be required for both compiling Verilator and compiling +Verilated models no sooner than September 2020. + +=item SystemC 2.1 and earlier support + +Support for SystemC versions 2.1 and earlier and the related sc_clock +variable attribute will be removed no sooner than July 2020. + +=item Configuration File -msg + +The -msg argument to lint_off has been replaced with -rule. -msg is +planned for removal no sooner than January 2021. + +=item XML locations + +The XML C attribute has been replaced with C. C is planned +for removal no sooner than January 2021. + +=back + + =head1 FAQ/FREQUENTLY ASKED QUESTIONS =over 4 @@ -4925,7 +4962,7 @@ Most synthesis tools similarly define SYNTHESIS for you. =item Why do I get "unexpected `do'" or "unexpected `bit'" errors? Do, bit, ref, return, and other words are now SystemVerilog keywords. You -should change your code to not use them to insure it works with newer +should change your code to not use them to ensure it works with newer tools. Alternatively, surround them by the Verilog 2005/SystemVerilog begin_keywords pragma to indicate Verilog 2001 code. diff --git a/ci/docker/run/hooks/post_push b/ci/docker/run/hooks/post_push new file mode 100755 index 000000000..8a12ed478 --- /dev/null +++ b/ci/docker/run/hooks/post_push @@ -0,0 +1,12 @@ +#!/bin/bash +# DESCRIPTION: Docker hub hook to tag the latest release (stable) +# +# Copyright 2020 by Stefan Wallentowitz. This program is free +# software; you can redistribute it and/or modify it under the terms +# of either the GNU Lesser General Public License Version 3 or the +# Perl Artistic License Version 2.0.FROM ubuntu:18.04 + +if [ "$SOURCE_BRANCH"="stable" ]; then + docker tag $IMAGE_NAME $DOCKER_REPO:latest + docker push $DOCKER_REPO:latest +fi diff --git a/configure.ac b/configure.ac index 8004af5c4..c98341558 100644 --- a/configure.ac +++ b/configure.ac @@ -25,6 +25,18 @@ AC_ARG_ENABLE([maintainer-mode], AC_ARG_ENABLE([silent-rules], [AS_HELP_STRING([--disable-silent-rules], [ignored])]) +# Flag to enable linking Verilator with tcmalloc if available +AC_ARG_ENABLE([tcmalloc], + [AS_HELP_STRING([--enable-tcmalloc], + [Use libtcmalloc for faster dynamic memory + management @<:@default=check@:>@])], + [case "${enableval}" in + yes) CFG_WITH_TCMALLOC=yes ;; + no) CFG_WITH_TCMALLOC=no ;; + *) AC_MSG_ERROR([bad value '${enableval}' for --enable-tcmalloc]) ;; + esac], + [CFG_WITH_TCMALLOC=check;]) + # Special Substitutions - CFG_WITH_DEFENV AC_MSG_CHECKING(whether to use hardcoded paths) AC_ARG_ENABLE([defenv], @@ -209,15 +221,26 @@ AC_DEFUN([_MY_LDLIBS_CHECK_FLAG], LIBS="$ACO_SAVE_LIBS" ]) -AC_DEFUN([_MY_LDLIBS_CHECK_OPT], - [# _MY_LDLIBS_CHECK_OPT(flag) -- Check if linker supports specific options - # If it does, append flag to variable - _MY_LDLIBS_CHECK_FLAG($2) +AC_DEFUN([_MY_LDLIBS_CHECK_IFELSE], + [# _MY_LDLIBS_CHECK_IFELSE(flag,action-if-supported,action-if-not-supported) + # Check if linker supports specific flag, if it does do action-if-supported + # otherwise do action-if-not-supported + _MY_LDLIBS_CHECK_FLAG($1) if test "$_my_result" = "yes" ; then - $1="$$1 $2" + true + $2 + else + true + $3 fi ]) +AC_DEFUN([_MY_LDLIBS_CHECK_OPT], + [# _MY_LDLIBS_CHECK_OPT(variable, flag) -- Check if linker supports specific + # options. If it does, append flag to variable. + _MY_LDLIBS_CHECK_IFELSE($2, $1="$$1 $2") + ]) + # Flag to select newest language standard supported # Macros work such that first option that passes is the one we take # gnu++17 code is clean, but SystemC in 2018 doesn't link with it (bug1339) @@ -258,7 +281,6 @@ _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-faligned-new) _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-Wno-unused-parameter) _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-Wno-undefined-bool-conversion) _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-Wno-shadow) -AC_SUBST(CFG_CXXFLAGS_SRC) # Flags for compiling Verilator parser always (in addition to above CFG_CXXFLAGS_SRC) _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_PARSER,-Wno-char-subscripts) @@ -310,6 +332,24 @@ m4_foreach([ldflag], [ AC_SUBST(CFG_LDLIBS_THREADS) AC_SUBST(CFG_LDFLAGS_THREADS_CMAKE) +# Check if tcmalloc is available based on --enable-tcmalloc +_MY_LDLIBS_CHECK_IFELSE( + -ltcmalloc, + [if test "$CFG_WITH_TCMALLOC" != "no"; then + CFG_LIBS="$CFG_LIBS -ltcmalloc"; + # If using tcmalloc, add some extra options to make the compiler not assume + # it is using it's own versions of the standard library functions + _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-fno-builtin-malloc) + _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-fno-builtin-calloc) + _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-fno-builtin-realloc) + _MY_CXX_CHECK_OPT(CFG_CXXFLAGS_SRC,-fno-builtin-free) + AC_SUBST(CFG_CXXFLAGS_SRC) + fi], + [if test "$CFG_WITH_TCMALLOC" = "yes"; then + AC_MSG_ERROR([--enable-tcmalloc was given but test for -ltcmalloc failed]) + fi]) +AC_SUBST(CFG_LIBS) + # Set CFG_WITH_THREADED if can support threading AC_MSG_CHECKING(whether $CXX supports Verilated threads) ACO_SAVE_CXXFLAGS="$CXXFLAGS" diff --git a/docs/CONTRIBUTORS b/docs/CONTRIBUTORS index 0f7156136..34ac03ccf 100644 --- a/docs/CONTRIBUTORS +++ b/docs/CONTRIBUTORS @@ -11,6 +11,7 @@ Chris Randall Driss Hafdi Eric Rippey Garrett Smith +Geza Lore Gianfranco Costamagna Howard Su Iztok Jeras diff --git a/docs/install.adoc b/docs/install.adoc index fb785878b..d71f8d6e8 100644 --- a/docs/install.adoc +++ b/docs/install.adoc @@ -84,6 +84,10 @@ To build Verilator you will need to install some standard packages: sudo apt-get install autoconf sudo apt-get install flex bison +The following are optional, but improve compilation speed: + + sudo apt-get install libgoogle-perftools-dev + Additionally, to build or run Verilator you need these standard packages: sudo apt-get install perl python3 diff --git a/docs/internals.adoc b/docs/internals.adoc index 3a8550200..a7e155200 100644 --- a/docs/internals.adoc +++ b/docs/internals.adoc @@ -70,7 +70,10 @@ The AST is represented at the top level by the class `AstNode`. This abstract class has derived classes for the individual components (e.g. `AstGenerate` for a generate block) or groups of components (e.g. `AstNodeFTask` for functions and tasks, which in turn has `AstFunc` -and `AstTask` as derived classes). +and `AstTask` as derived classes). An important property of the `AstNode` +type hierarchy is that all non-final subclasses of `AstNode` (i.e.: those +which themselves have subclasses) must be abstract as well, and be named +with the prefix `AstNode*`. The `astgen` (see below) script relies on this. Each `AstNode` has pointers to up to four children, accessed by the `op1p` through `op4p` methods. These methods are then abstracted in a specific @@ -394,7 +397,7 @@ e.g. threads. We will work with contributors to fix up indentation style issues, but it is appreciated if you could match our style: -* All files should contain the magic header to insure standard indentation: +* All files should contain the magic header to ensure standard indentation: + // -*- mode: C++; c-file-style: "cc-mode" -*- + @@ -959,7 +962,8 @@ src/VParseGrammar.y, as this grammar supports the full SystemVerilog language and has a lot of back-and-forth with Verilator's grammar. Copy the appropriate rules to src/verilog.y and modify the productions. -. If a new Ast type is needed, add it to V3AstNodes.h. +. If a new Ast type is needed, add it to V3AstNodes.h. Follow the convention +described above about the AstNode type hierarchy. . Now you can run "test_regress/t/t_{new testcase}.pl --debug" and it'll probably fail but you'll see a test_regress/obj_dir/t_{newtestcase}/*.tree diff --git a/docs/xml.adoc b/docs/xml.adoc new file mode 100644 index 000000000..a501095d8 --- /dev/null +++ b/docs/xml.adoc @@ -0,0 +1,65 @@ += Verilator XML Output +:toc: right + +// Github doesn't render unless absolute URL +image::https://www.veripool.org/img/verilator_256_200_min.png[Logo,256,200,role="right"] + +== Introduction + +This document describes Verilator's XML output. For more general information +please see https://verilator.org[verilator.org]. + +== General + +Verilator's XML output is enabled with the `--xml-only` flag. It contains +limited information about the elaborated design including files, modules, +instance hierarchy, logic and data types. There is no formal schema since part +of the structure of the XML document matches the compiled code which would +require the schema to describe legal SystemVerilog structure. The intended +usage is to enable other downstream tools to take advantage of Verilator's +parser. + +== Structure + +The XML document is consists of 4 sections within the top level `verilator_xml` +element: + +``...``:: + +This section contains a list of all design files read, including the +built-in constructs and the command line as their own entries. Each +`` has an attribute `id` which is a short ASCII string unique to that +file. Other elements' `loc` attributes use this id to refer to a particular +file. + +``...``:: + +All files containing Verilog module definitions are listed in this section. +This element's contents is a subset of the `` element's contents. + +``...``:: + +The cells section of the XML document contains the design instance +hierarchy. Each instance is represented with the `` element with the +following attributes: + +* `fl` (deprecated): The file id and line number where the module was + instanced. Use `loc` instead. + +* `loc`: The file id, first line number, last line number, first column + number and last column number of the identifier where the module was + instanced, separated by commas. + +* `name`: The instance name. + +* `submodname`: The module name uniquified with particular parameter values (if any). + +* `hier`: The full hierarchy path. + +``...``:: + +The netlist section contains a number of ``...`` elements, +each describing the contents of that module, and a single ``... +`` element which lists all used types used within the +modules. Each type has a numeric `id` attribute that is referred to by +elements in the `` elements using the `dtype_id` attribute. diff --git a/include/gtkwave/fastlz.c b/include/gtkwave/fastlz.c index 3d2c3dc1e..50bf56a46 100644 --- a/include/gtkwave/fastlz.c +++ b/include/gtkwave/fastlz.c @@ -418,9 +418,7 @@ static FASTLZ_INLINE int FASTLZ_DECOMPRESSOR(const void* input, int length, void const flzuint8* ip = (const flzuint8*) input; const flzuint8* ip_limit = ip + length; flzuint8* op = (flzuint8*) output; -#ifdef FASTLZ_SAFE flzuint8* op_limit = op + maxout; -#endif flzuint32 ctrl = (*ip++) & 31; int loop = 1; diff --git a/include/gtkwave/wavealloca.h b/include/gtkwave/wavealloca.h index 86276648f..8c064fe03 100644 --- a/include/gtkwave/wavealloca.h +++ b/include/gtkwave/wavealloca.h @@ -33,9 +33,6 @@ #else #include #endif -#elif defined(_MSC_VER) -#include -#define alloca _alloca #endif #define wave_alloca alloca #endif diff --git a/include/verilated_cov.cpp b/include/verilated_cov.cpp index 35d2ea2cc..cfa129a0c 100644 --- a/include/verilated_cov.cpp +++ b/include/verilated_cov.cpp @@ -73,12 +73,12 @@ private: public: // METHODS // cppcheck-suppress truncLongCastReturn - virtual vluint64_t count() const { return *m_countp; } - virtual void zero() const { *m_countp = 0; } + virtual vluint64_t count() const VL_OVERRIDE { return *m_countp; } + virtual void zero() const VL_OVERRIDE { *m_countp = 0; } // CONSTRUCTORS // cppcheck-suppress noExplicitConstructor VerilatedCoverItemSpec(T* countp) : m_countp(countp) { *m_countp = 0; } - virtual ~VerilatedCoverItemSpec() {} + virtual ~VerilatedCoverItemSpec() VL_OVERRIDE {} }; //============================================================================= diff --git a/include/verilated_save.h b/include/verilated_save.h index 0d23f4ebc..e755b77b0 100644 --- a/include/verilated_save.h +++ b/include/verilated_save.h @@ -164,12 +164,12 @@ private: public: // CONSTRUCTORS VerilatedSave() { m_fd = -1; } - virtual ~VerilatedSave() { close(); } + virtual ~VerilatedSave() VL_OVERRIDE { close(); } // METHODS void open(const char* filenamep) VL_MT_UNSAFE_ONE; ///< Open the file; call isOpen() to see if errors void open(const std::string& filename) VL_MT_UNSAFE_ONE { open(filename.c_str()); } - virtual void close() VL_MT_UNSAFE_ONE; - virtual void flush() VL_MT_UNSAFE_ONE; + virtual void close() VL_OVERRIDE VL_MT_UNSAFE_ONE; + virtual void flush() VL_OVERRIDE VL_MT_UNSAFE_ONE; }; //============================================================================= @@ -183,14 +183,14 @@ private: public: // CONSTRUCTORS VerilatedRestore() { m_fd = -1; } - virtual ~VerilatedRestore() { close(); } + virtual ~VerilatedRestore() VL_OVERRIDE { close(); } // METHODS void open(const char* filenamep) VL_MT_UNSAFE_ONE; ///< Open the file; call isOpen() to see if errors void open(const std::string& filename) VL_MT_UNSAFE_ONE { open(filename.c_str()); } - virtual void close() VL_MT_UNSAFE_ONE; - virtual void flush() VL_MT_UNSAFE_ONE {} - virtual void fill() VL_MT_UNSAFE_ONE; + virtual void close() VL_OVERRIDE VL_MT_UNSAFE_ONE; + virtual void flush() VL_OVERRIDE VL_MT_UNSAFE_ONE {} + virtual void fill() VL_OVERRIDE VL_MT_UNSAFE_ONE; }; //============================================================================= diff --git a/include/verilatedos.h b/include/verilatedos.h index 001e0db3e..6628c5584 100644 --- a/include/verilatedos.h +++ b/include/verilatedos.h @@ -184,12 +184,14 @@ # define VL_INCLUDE_UNORDERED_MAP # define VL_INCLUDE_UNORDERED_SET # endif +# define VL_FINAL final # define VL_OVERRIDE override #else # define VL_EQ_DELETE # define vl_unique_ptr std::auto_ptr # define VL_INCLUDE_UNORDERED_MAP "verilated_unordered_set_map.h" # define VL_INCLUDE_UNORDERED_SET "verilated_unordered_set_map.h" +# define VL_FINAL # define VL_OVERRIDE #endif @@ -271,6 +273,10 @@ typedef signed __int32 ssize_t; ///< signed size_t; returned fro #else // Linux or compliant Unix flavors, -m64 +// The inttypes supplied with some GCC versions requires STDC_FORMAT_MACROS +// to be declared in order to get the PRIxx macros used by fstapi.c +#define __STDC_FORMAT_MACROS + # include // Solaris # include // Linux and most flavors # include // __WORDSIZE diff --git a/src/Makefile_obj.in b/src/Makefile_obj.in index 82476dcdf..140938a9a 100644 --- a/src/Makefile_obj.in +++ b/src/Makefile_obj.in @@ -68,6 +68,7 @@ CFG_CXXFLAGS_SRC = @CFG_CXXFLAGS_SRC@ CFG_CXXFLAGS_PARSER = @CFG_CXXFLAGS_PARSER@ # Compiler flags that turn on extra warnings CFG_CXXFLAGS_WEXTRA = @CFG_CXXFLAGS_WEXTRA@ +CFG_LIBS = @CFG_LIBS@ #### End of system configuration section. #### @@ -92,7 +93,7 @@ endif # -lfl not needed as Flex invoked with %nowrap option # -lstdc++ needed for clang, believed harmless with gcc -LIBS = -lm -lstdc++ +LIBS = $(CFG_LIBS) -lm -lstdc++ CPPFLAGS += -MMD CPPFLAGS += -I. -I$(bldsrc) -I$(srcdir) -I$(incdir) -I../../include @@ -193,6 +194,7 @@ RAW_OBJS = \ V3FileLine.o \ V3Gate.o \ V3GenClk.o \ + V3Global.o \ V3Graph.o \ V3GraphAlg.o \ V3GraphAcyc.o \ diff --git a/src/V3Active.cpp b/src/V3Active.cpp index 7510050cb..a41f48650 100644 --- a/src/V3Active.cpp +++ b/src/V3Active.cpp @@ -70,7 +70,7 @@ private: m_scopep->addActivep(nodep); } // VISITORS - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { m_scopep = nodep; m_iActivep = NULL; m_cActivep = NULL; @@ -79,15 +79,15 @@ private: iterateChildren(nodep); // Don't clear scopep, the namer persists beyond this visit } - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { // Simplify sensitivity list VL_DO_DANGLING(V3Const::constifyExpensiveEdit(nodep), nodep); } // Empty visitors, speed things up - virtual void visit(AstNodeStmt* nodep) { } + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { } //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -163,7 +163,7 @@ private: AstNode* m_alwaysp; // Always we're under AstNode* m_assignp; // In assign // VISITORS - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { if (m_check != CT_SEQ) { // Convert to a non-delayed assignment UINFO(5," ASSIGNDLY "<deleteTree(), nodep); } } - virtual void visit(AstAssign* nodep) { + virtual void visit(AstAssign* nodep) VL_OVERRIDE { if (m_check == CT_SEQ) { AstNode* las = m_assignp; m_assignp = nodep; @@ -192,7 +192,7 @@ private: m_assignp = las; } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { AstVar* varp = nodep->varp(); if (m_check == CT_SEQ && m_assignp @@ -210,7 +210,7 @@ private: } } //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -240,7 +240,7 @@ private: bool m_itemSequent; // Found a SenItem sequential // VISITORS - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { // Create required actives and add to scope UINFO(4," SCOPE "<unlinkFrBack(); wantactivep->addStmtsp(nodep); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // Relink to CACTIVE, unless already under it UINFO(4," ASSIGNW "<fileline()); nodep->unlinkFrBack(); wantactivep->addStmtsp(nodep); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { // Relink to CACTIVE, unless already under it UINFO(4," ASSIGNW "<fileline()); nodep->unlinkFrBack(); wantactivep->addStmtsp(nodep); } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { // Relink to CACTIVE, unless already under it UINFO(4," COVERTOGGLE "<fileline()); nodep->unlinkFrBack(); wantactivep->addStmtsp(nodep); } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { // Relink to CFUNC for the final UINFO(4," FINAL "<bodysp()) { // Empty, Kill it. @@ -372,7 +372,7 @@ private: ActiveDlyVisitor dlyvisitor (nodep, ActiveDlyVisitor::CT_SEQ); } } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { // Move always to appropriate ACTIVE based on its sense list UINFO(4," ALW "<=9) nodep->dumpTree(cout, " Alw: "); @@ -384,13 +384,13 @@ private: } visitAlways(nodep, nodep->sensesp(), nodep->keyword()); } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { // Move always to appropriate ACTIVE based on its sense list UINFO(4," ALWPub "<=9) nodep->dumpTree(cout, " Alw: "); visitAlways(nodep, nodep->sensesp(), VAlwaysKwd::ALWAYS); } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { AstSenItem* subitemp = nodep->sensesp(); UASSERT_OBJ(subitemp->edgeType() == VEdgeType::ET_ANYEDGE || subitemp->edgeType() == VEdgeType::ET_POSEDGE @@ -398,7 +398,7 @@ private: nodep, "Strange activity type under SenGate"); iterateChildren(nodep); } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { if (nodep->edgeType() == VEdgeType::ET_ANYEDGE) { m_itemCombo = true; // Delete the sensitivity @@ -416,10 +416,10 @@ private: } // Empty visitors, speed things up - virtual void visit(AstNodeMath* nodep) {} - virtual void visit(AstVarScope* nodep) {} + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} + virtual void visit(AstVarScope* nodep) VL_OVERRIDE {} //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3ActiveTop.cpp b/src/V3ActiveTop.cpp index 8be5c9b4f..924680335 100644 --- a/src/V3ActiveTop.cpp +++ b/src/V3ActiveTop.cpp @@ -56,19 +56,19 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { m_topscopep = nodep; m_finder.main(m_topscopep); iterateChildren(nodep); m_topscopep = NULL; } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Create required actives and add to module // We can start ordering at a module, or a scope UINFO(4," MOD "<sensesp(); @@ -113,29 +113,29 @@ private: // No need to do statements under it, they're already moved. //iterateChildren(nodep); } - virtual void visit(AstInitial* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstInitial* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been under ACTIVE"); } - virtual void visit(AstAssignAlias* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been under ACTIVE"); } - virtual void visit(AstAssignW* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been under ACTIVE"); } - virtual void visit(AstAlways* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstAlways* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been under ACTIVE"); } - virtual void visit(AstAlwaysPublic* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been under ACTIVE"); } - virtual void visit(AstFinal* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstFinal* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE nodep->v3fatalSrc("Node should have been deleted"); } // Empty visitors, speed things up - virtual void visit(AstNodeMath* nodep) {} - virtual void visit(AstVarScope* nodep) {} + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} + virtual void visit(AstVarScope* nodep) VL_OVERRIDE {} //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3Assert.cpp b/src/V3Assert.cpp index 953367966..6e593c339 100644 --- a/src/V3Assert.cpp +++ b/src/V3Assert.cpp @@ -115,9 +115,9 @@ private: if (failsp) failsp->unlinkFrBackWithNext(); if (nodep->immediate()) { - UASSERT_OBJ(!sentreep, nodep, "Immediate assertions don't have sensivity"); + UASSERT_OBJ(!sentreep, nodep, "Immediate assertions don't have sensitivity"); } else { - UASSERT_OBJ(sentreep, nodep, "Concurrent assertions must have sensivity"); + UASSERT_OBJ(sentreep, nodep, "Concurrent assertions must have sensitivity"); sentreep->unlinkFrBack(); } // @@ -174,7 +174,7 @@ private: } // VISITORS - virtual void visit(AstIf* nodep) { + virtual void visit(AstIf* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; if (nodep->uniquePragma() || nodep->unique0Pragma()) { AstNodeIf* ifp = nodep; @@ -234,7 +234,7 @@ private: } //========== Case assertions - virtual void visit(AstCase* nodep) { + virtual void visit(AstCase* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!nodep->user1SetOnce()) { bool has_default = false; @@ -296,7 +296,7 @@ private: } //========== Past - virtual void visit(AstPast* nodep) { + virtual void visit(AstPast* nodep) VL_OVERRIDE { iterateChildren(nodep); uint32_t ticks = 1; if (nodep->ticksp()) { @@ -326,9 +326,13 @@ private: } nodep->replaceWith(inp); } + virtual void visit(AstSampled* nodep) VL_OVERRIDE { + nodep->replaceWith(nodep->exprp()->unlinkFrBack()); + VL_DO_DANGLING(pushDeletep(nodep), nodep); + } //========== Statements - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { iterateChildren(nodep); // Replace the special types with standard text if (nodep->displayType()==AstDisplayType::DT_INFO) { @@ -341,29 +345,32 @@ private: } } - virtual void visit(AstAssert* nodep) { + virtual void visit(AstAssert* nodep) VL_OVERRIDE { iterateChildren(nodep); newPslAssertion(nodep, nodep->failsp()); } - virtual void visit(AstCover* nodep) { + virtual void visit(AstCover* nodep) VL_OVERRIDE { iterateChildren(nodep); newPslAssertion(nodep, NULL); } - virtual void visit(AstRestrict* nodep) { + virtual void visit(AstRestrict* nodep) VL_OVERRIDE { iterateChildren(nodep); // IEEE says simulator ignores these VL_DO_DANGLING(pushDeletep(nodep->unlinkFrBack()), nodep); } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - m_modPastNum = 0; - // - iterateChildren(nodep); - // Reset defaults - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + unsigned origPastNum = m_modPastNum; + { + m_modp = nodep; + m_modPastNum = 0; + iterateChildren(nodep); + } + m_modp = origModp; + m_modPastNum = origPastNum; } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { // This code is needed rather than a visitor in V3Begin, // because V3Assert is called before V3Begin AstBegin* lastp = m_beginp; @@ -374,7 +381,7 @@ private: m_beginp = lastp; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3AssertPre.cpp b/src/V3AssertPre.cpp index 37372511c..2dc09f85f 100644 --- a/src/V3AssertPre.cpp +++ b/src/V3AssertPre.cpp @@ -71,7 +71,7 @@ private: // VISITORS //========== Statements - virtual void visit(AstClocking* nodep) { + virtual void visit(AstClocking* nodep) VL_OVERRIDE { UINFO(8," CLOCKING"<sensesp(); @@ -83,7 +83,7 @@ private: } VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->sensesp()); if (nodep->sensesp()) { m_seniAlwaysp = nodep->sensesp()->sensesp(); @@ -92,7 +92,7 @@ private: m_seniAlwaysp = NULL; } - virtual void visit(AstNodeCoverOrAssert* nodep) { + virtual void visit(AstNodeCoverOrAssert* nodep) VL_OVERRIDE { if (nodep->sentreep()) return; // Already processed clearAssertInfo(); // Find Clocking's buried under nodep->exprsp @@ -102,12 +102,12 @@ private: } clearAssertInfo(); } - virtual void visit(AstPast* nodep) { + virtual void visit(AstPast* nodep) VL_OVERRIDE { if (nodep->sentreep()) return; // Already processed iterateChildren(nodep); nodep->sentreep(newSenTree(nodep)); } - virtual void visit(AstPropClocked* nodep) { + virtual void visit(AstPropClocked* nodep) VL_OVERRIDE { // No need to iterate the body, once replace will get iterated iterateAndNextNull(nodep->sensesp()); if (m_senip) { @@ -132,12 +132,12 @@ private: nodep->replaceWith(blockp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { iterateChildren(nodep); // Reset defaults m_seniDefaultp = NULL; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Ast.h b/src/V3Ast.h index b8e34424b..8f6968b66 100644 --- a/src/V3Ast.h +++ b/src/V3Ast.h @@ -51,15 +51,18 @@ typedef std::set MTaskIdSet; // Set of mtaskIds for Var sorting //###################################################################### // For broken() function, return error string if have a match -#define BROKEN_RTN(test) do { if (VL_UNCOVERABLE(test)) return # test; } while(0) +#define BROKEN_RTN(test) \ + do { \ + if (VL_UNCOVERABLE(test)) return #test; \ + } while (0) // (V)erilator (N)ode is: True if AstNode is of a a given AstType -#define VN_IS(nodep,nodetypename) (AstNode::privateIs ## nodetypename(nodep)) +#define VN_IS(nodep,nodetypename) (AstNode::privateIs(nodep)) // (V)erilator (N)ode cast: Cast to given type if can; effectively // dynamic_cast(nodep) -#define VN_CAST(nodep,nodetypename) (AstNode::privateCast ## nodetypename(nodep)) -#define VN_CAST_CONST(nodep,nodetypename) (AstNode::privateConstCast ## nodetypename(nodep) ) +#define VN_CAST(nodep,nodetypename) (AstNode::privateCast(nodep)) +#define VN_CAST_CONST(nodep,nodetypename) (AstNode::privateConstCast(nodep)) // (V)erilator (N)ode deleted: Reference to deleted child (for assertions only) #define VN_DELETED(nodep) VL_UNLIKELY((vluint64_t)(nodep) == 0x1) @@ -305,6 +308,8 @@ public: // MEMBER_BASE, // V3LinkResolve creates for AstPreSel, V3LinkParam removes // + TYPENAME, // V3Width processes + // VAR_BASE, // V3LinkResolve creates for AstPreSel, V3LinkParam removes VAR_CLOCK, // V3LinkParse moves to AstVar::attrScClocked VAR_CLOCK_ENABLE, // V3LinkParse moves to AstVar::attrClockEn @@ -328,6 +333,7 @@ public: "ENUM_BASE", "ENUM_FIRST", "ENUM_LAST", "ENUM_NUM", "ENUM_NEXT", "ENUM_PREV", "ENUM_NAME", "MEMBER_BASE", + "TYPENAME", "VAR_BASE", "VAR_CLOCK", "VAR_CLOCK_ENABLE", "VAR_PUBLIC", "VAR_PUBLIC_FLAT", "VAR_PUBLIC_FLAT_RD", "VAR_PUBLIC_FLAT_RW", "VAR_ISOLATE_ASSIGNMENTS", "VAR_SC_BV", "VAR_SFORMAT", "VAR_CLOCKER", @@ -1157,6 +1163,8 @@ class AstNode { AstNode* m_headtailp; // When at begin/end of list, the opposite end of the list + const AstType m_type; // Node sub-type identifier + FileLine* m_fileline; // Where it was declared vluint64_t m_editCount; // When it was last edited static vluint64_t s_editCntGbl; // Global edit counter @@ -1211,8 +1219,10 @@ public: protected: // CONSTRUCTORS - AstNode() { init(); } - explicit AstNode(FileLine* fileline) {init(); m_fileline = fileline; } + AstNode(AstType t) + : m_type(t) { init(); } + AstNode(AstType t, FileLine* fl) + : m_type(t) { init(); m_fileline = fl; } virtual AstNode* clone() = 0; // Generally, cloneTree is what you want instead virtual void cloneRelink() {} void cloneRelinkTree(); @@ -1243,7 +1253,7 @@ protected: public: // ACCESSORS - virtual AstType type() const = 0; + inline AstType type() const { return m_type; } const char* typeName() const { return type().ascii(); } // See also prettyTypeName AstNode* nextp() const { return m_nextp; } AstNode* backp() const { return m_backp; } @@ -1299,7 +1309,7 @@ public: static string vcdName(const string& namein); // Name for printing out to vcd files string prettyName() const { return prettyName(name()); } string prettyNameQ() const { return prettyNameQ(name()); } - string prettyTypeName() const; // "VARREF" for error messages + string prettyTypeName() const; // "VARREF" for error messages (NOT dtype's pretty name) virtual string prettyOperatorName() const { return "operator "+prettyTypeName(); } FileLine* fileline() const { return m_fileline; } void fileline(FileLine* fl) { m_fileline = fl; } @@ -1533,11 +1543,22 @@ private: // CONVERSION public: -#include "V3Ast__gen_interface.h" // From ./astgen - // Things like: - // AstAlways* castAlways(); + // These for use by VN_IS macro only + template + static bool privateIs(const AstNode* nodep); + + // These for use by VN_CAST macro only + template + static T* privateCast(AstNode* nodep); + + // These for use by VN_CAST_CONST macro only + template + static const T* privateConstCast(const AstNode* nodep); }; +// Specialisations of privateIs/privateCast +#include "V3Ast__gen_impl.h" // From ./astgen + inline std::ostream& operator<<(std::ostream& os, const AstNode* rhs) { if (!rhs) os<<"NULL"; else rhs->dump(os); return os; } @@ -1557,8 +1578,8 @@ inline void AstNRelinker::relink(AstNode* newp) { newp->AstNode::relink(this); } class AstNodeMath : public AstNode { // Math -- anything that's part of an expression tree public: - explicit AstNodeMath(FileLine* fl) - : AstNode(fl) {} + AstNodeMath(AstType t, FileLine* fl) + : AstNode(t, fl) {} ASTNODE_BASE_FUNCS(NodeMath) // METHODS virtual bool hasDType() const { return true; } @@ -1574,8 +1595,8 @@ public: class AstNodeTermop : public AstNodeMath { // Terminal operator -- a operator with no "inputs" public: - explicit AstNodeTermop(FileLine* fl) - : AstNodeMath(fl) {} + AstNodeTermop(AstType t, FileLine* fl) + : AstNodeMath(t, fl) {} ASTNODE_BASE_FUNCS(NodeTermop) // Know no children, and hot function, so skip iterator for speed // See checkTreeIter also that asserts no children @@ -1586,8 +1607,8 @@ public: class AstNodeUniop : public AstNodeMath { // Unary math public: - AstNodeUniop(FileLine* fl, AstNode* lhsp) - : AstNodeMath(fl) { + AstNodeUniop(AstType t, FileLine* fl, AstNode* lhsp) + : AstNodeMath(t, fl) { dtypeFrom(lhsp); setOp1p(lhsp); } ASTNODE_BASE_FUNCS(NodeUniop) @@ -1608,8 +1629,8 @@ public: class AstNodeBiop : public AstNodeMath { // Binary math public: - AstNodeBiop(FileLine* fl, AstNode* lhs, AstNode* rhs) - : AstNodeMath(fl) { + AstNodeBiop(AstType t, FileLine* fl, AstNode* lhs, AstNode* rhs) + : AstNodeMath(t, fl) { setOp1p(lhs); setOp2p(rhs); } ASTNODE_BASE_FUNCS(NodeBiop) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) = 0; // Clone single node, just get same type back. @@ -1635,8 +1656,8 @@ public: class AstNodeTriop : public AstNodeMath { // Trinary math public: - AstNodeTriop(FileLine* fl, AstNode* lhs, AstNode* rhs, AstNode* ths) - : AstNodeMath(fl) { + AstNodeTriop(AstType t, FileLine* fl, AstNode* lhs, AstNode* rhs, AstNode* ths) + : AstNodeMath(t, fl) { setOp1p(lhs); setOp2p(rhs); setOp3p(ths); } ASTNODE_BASE_FUNCS(NodeTriop) AstNode* lhsp() const { return op1p(); } @@ -1663,22 +1684,22 @@ public: class AstNodeBiCom : public AstNodeBiop { // Binary math with commutative properties public: - AstNodeBiCom(FileLine* fl, AstNode* lhs, AstNode* rhs) - : AstNodeBiop(fl, lhs, rhs) {} + AstNodeBiCom(AstType t, FileLine* fl, AstNode* lhs, AstNode* rhs) + : AstNodeBiop(t, fl, lhs, rhs) {} ASTNODE_BASE_FUNCS(NodeBiCom) }; class AstNodeBiComAsv : public AstNodeBiCom { // Binary math with commutative & associative properties public: - AstNodeBiComAsv(FileLine* fl, AstNode* lhs, AstNode* rhs) - : AstNodeBiCom(fl, lhs, rhs) {} + AstNodeBiComAsv(AstType t, FileLine* fl, AstNode* lhs, AstNode* rhs) + : AstNodeBiCom(t, fl, lhs, rhs) {} ASTNODE_BASE_FUNCS(NodeBiComAsv) }; class AstNodeCond : public AstNodeTriop { public: - AstNodeCond(FileLine* fl, AstNode* condp, AstNode* expr1p, AstNode* expr2p) - : AstNodeTriop(fl, condp, expr1p, expr2p) { + AstNodeCond(AstType t, FileLine* fl, AstNode* condp, AstNode* expr1p, AstNode* expr2p) + : AstNodeTriop(t, fl, condp, expr1p, expr2p) { if (expr1p) dtypeFrom(expr1p); else if (expr2p) dtypeFrom(expr2p); } @@ -1704,8 +1725,8 @@ public: class AstNodePreSel : public AstNode { // Something that becomes an AstSel public: - AstNodePreSel(FileLine* fl, AstNode* lhs, AstNode* rhs, AstNode* ths) - : AstNode(fl) { + AstNodePreSel(AstType t, FileLine* fl, AstNode* lhs, AstNode* rhs, AstNode* ths) + : AstNode(t, fl) { setOp1p(lhs); setOp2p(rhs); setNOp3p(ths); } ASTNODE_BASE_FUNCS(NodePreSel) AstNode* lhsp() const { return op1p(); } @@ -1726,8 +1747,8 @@ class AstNodeStmt : public AstNode { // Statement -- anything that's directly under a function bool m_statement; // Really a statement (e.g. not a function with return) public: - explicit AstNodeStmt(FileLine* fl, bool statement = true) - : AstNode(fl) + AstNodeStmt(AstType t, FileLine* fl, bool statement = true) + : AstNode(t, fl) , m_statement(statement) {} ASTNODE_BASE_FUNCS(NodeStmt) // METHODS @@ -1739,8 +1760,8 @@ public: class AstNodeAssign : public AstNodeStmt { public: - AstNodeAssign(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeStmt(fl) { + AstNodeAssign(AstType t, FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : AstNodeStmt(t, fl) { setOp1p(rhsp); setOp2p(lhsp); dtypeFrom(lhsp); } @@ -1762,9 +1783,9 @@ public: class AstNodeFor : public AstNodeStmt { public: - AstNodeFor(FileLine* fileline, AstNode* initsp, AstNode* condp, + AstNodeFor(AstType t, FileLine* fl, AstNode* initsp, AstNode* condp, AstNode* incsp, AstNode* bodysp) - : AstNodeStmt(fileline) { + : AstNodeStmt(t, fl) { addNOp1p(initsp); setOp2p(condp); addNOp3p(incsp); addNOp4p(bodysp); } ASTNODE_BASE_FUNCS(NodeFor) @@ -1782,8 +1803,8 @@ class AstNodeIf : public AstNodeStmt { private: VBranchPred m_branchPred; // Branch prediction as taken/untaken? public: - AstNodeIf(FileLine* fl, AstNode* condp, AstNode* ifsp, AstNode* elsesp) - : AstNodeStmt(fl) { + AstNodeIf(AstType t, FileLine* fl, AstNode* condp, AstNode* ifsp, AstNode* elsesp) + : AstNodeStmt(t, fl) { setOp1p(condp); addNOp2p(ifsp); addNOp3p(elsesp); } ASTNODE_BASE_FUNCS(NodeIf) @@ -1804,8 +1825,8 @@ public: class AstNodeCase : public AstNodeStmt { public: - AstNodeCase(FileLine* fl, AstNode* exprp, AstNode* casesp) - : AstNodeStmt(fl) { + AstNodeCase(AstType t, FileLine* fl, AstNode* exprp, AstNode* casesp) + : AstNodeStmt(t, fl) { setOp1p(exprp); addNOp2p(casesp); } ASTNODE_BASE_FUNCS(NodeCase) @@ -1820,7 +1841,8 @@ public: class AstNodeSenItem : public AstNode { // An AstSenItem or AstSenGate public: - explicit AstNodeSenItem(FileLine* fl) : AstNode(fl) {} + AstNodeSenItem(AstType t, FileLine* fl) + : AstNode(t, fl) {} ASTNODE_BASE_FUNCS(NodeSenItem) virtual bool isClocked() const = 0; virtual bool isCombo() const = 0; @@ -1841,14 +1863,14 @@ private: bool m_hierThis; // Hiername points to "this" function void init(); public: - AstNodeVarRef(FileLine* fl, const string& name, bool lvalue) - : AstNodeMath(fl), m_lvalue(lvalue), m_varp(NULL), m_varScopep(NULL), - m_packagep(NULL), m_name(name), m_hierThis(false) { + AstNodeVarRef(AstType t, FileLine* fl, const string& name, bool lvalue) + : AstNodeMath(t, fl), m_lvalue(lvalue), m_varp(NULL), m_varScopep(NULL) + , m_packagep(NULL), m_name(name), m_hierThis(false) { init(); } - AstNodeVarRef(FileLine* fl, const string& name, AstVar* varp, bool lvalue) - : AstNodeMath(fl), m_lvalue(lvalue), m_varp(varp), m_varScopep(NULL), - m_packagep(NULL), m_name(name), m_hierThis(false) { + AstNodeVarRef(AstType t, FileLine* fl, const string& name, AstVar* varp, bool lvalue) + : AstNodeMath(t, fl), m_lvalue(lvalue), m_varp(varp), m_varScopep(NULL) + , m_packagep(NULL), m_name(name), m_hierThis(false) { // May have varp==NULL init(); } @@ -1883,8 +1905,8 @@ private: string m_text; public: // Node that simply puts text into the output stream - AstNodeText(FileLine* fileline, const string& textp) - : AstNode(fileline) { + AstNodeText(AstType t, FileLine* fl, const string& textp) + : AstNode(t, fl) { m_text = textp; // Copy it } ASTNODE_BASE_FUNCS(NodeText) @@ -1909,7 +1931,8 @@ private: static int s_uniqueNum; // Unique number assigned to each dtype during creation for IEEE matching public: // CONSTRUCTORS - explicit AstNodeDType(FileLine* fl) : AstNode(fl) { + AstNodeDType(AstType t, FileLine* fl) + : AstNode(t, fl) { m_width = 0; m_widthMin = 0; m_generic = false; } ASTNODE_BASE_FUNCS(NodeDType) @@ -1931,6 +1954,8 @@ public: virtual bool similarDType(AstNodeDType* samep) const = 0; // Assignable equivalence. Call skipRefp() on this and samep before calling virtual AstNodeDType* subDTypep() const { return NULL; } // Iff has a non-null subDTypep(), as generic node function virtual bool isFourstate() const; + virtual string prettyDTypeName() const { return prettyTypeName(); } // Ideally an IEEE $typename + string prettyDTypeNameQ() const { return "'" + prettyDTypeName() + "'"; } // // Changing the width may confuse the data type resolution, so must clear // TypeTable cache after use. @@ -1969,8 +1994,8 @@ private: bool m_isFourstate; MemberNameMap m_members; public: - AstNodeUOrStructDType(FileLine* fl, AstNumeric numericUnpack) - : AstNodeDType(fl) { + AstNodeUOrStructDType(AstType t, FileLine* fl, AstNumeric numericUnpack) + : AstNodeDType(t, fl) { // AstNumeric::NOSIGN overloaded to indicate not packed m_packed = (numericUnpack != AstNumeric::NOSIGN); m_isFourstate = false; // V3Width computes @@ -2020,7 +2045,8 @@ private: AstNodeDType* m_refDTypep; // Elements of this type (after widthing) AstNode* rangenp() const { return op2p(); } // op2 = Array(s) of variable public: - explicit AstNodeArrayDType(FileLine* fl) : AstNodeDType(fl) { + AstNodeArrayDType(AstType t, FileLine* fl) + : AstNodeDType(t, fl) { m_refDTypep = NULL; } ASTNODE_BASE_FUNCS(NodeArrayDType) @@ -2071,8 +2097,8 @@ public: class AstNodeSel : public AstNodeBiop { // Single bit range extraction, perhaps with non-constant selection or array selection public: - AstNodeSel(FileLine* fl, AstNode* fromp, AstNode* bitp) - : AstNodeBiop(fl, fromp, bitp) {} + AstNodeSel(AstType t, FileLine* fl, AstNode* fromp, AstNode* bitp) + : AstNodeBiop(t, fl, fromp, bitp) {} ASTNODE_BASE_FUNCS(NodeSel) AstNode* fromp() const { return op1p(); } // op1 = Extracting what (NULL=TBD during parsing) void fromp(AstNode* nodep) { setOp1p(nodep); } @@ -2085,7 +2111,8 @@ public: class AstNodeStream : public AstNodeBiop { // Verilog {rhs{lhs}} - Note rhsp() is the slice size, not the lhsp() public: - AstNodeStream(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { + AstNodeStream(AstType t, FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : AstNodeBiop(t, fl, lhsp, rhsp) { if (lhsp->dtypep()) { dtypeSetLogicSized(lhsp->dtypep()->width(), AstNumeric::UNSIGNED); } @@ -2111,8 +2138,8 @@ private: bool m_dpiTask:1; // DPI import task (vs. void function) bool m_pure:1; // DPI import pure public: - AstNodeFTask(FileLine* fileline, const string& name, AstNode* stmtsp) - : AstNode(fileline) + AstNodeFTask(AstType t, FileLine* fl, const string& name, AstNode* stmtsp) + : AstNode(t, fl) , m_name(name) , m_dpiOpenParent(0), m_taskPublic(false) , m_attrIsolateAssign(false), m_prototype(false) @@ -2174,13 +2201,13 @@ private: string m_inlinedDots; // Dotted hierarchy flattened out AstPackage* m_packagep; // Package hierarchy public: - AstNodeFTaskRef(FileLine* fl, bool statement, AstNode* namep, AstNode* pinsp) - : AstNodeStmt(fl, statement) + AstNodeFTaskRef(AstType t, FileLine* fl, bool statement, AstNode* namep, AstNode* pinsp) + : AstNodeStmt(t, fl, statement) , m_taskp(NULL), m_packagep(NULL) { setOp1p(namep); addNOp2p(pinsp); } - AstNodeFTaskRef(FileLine* fl, bool statement, const string& name, AstNode* pinsp) - : AstNodeStmt(fl, statement) + AstNodeFTaskRef(AstType t, FileLine* fl, bool statement, const string& name, AstNode* pinsp) + : AstNodeStmt(t, fl, statement) , m_taskp(NULL), m_name(name), m_packagep(NULL) { addNOp2p(pinsp); } @@ -2231,8 +2258,8 @@ private: int m_varNum; // Incrementing variable number int m_typeNum; // Incrementing implicit type number public: - AstNodeModule(FileLine* fl, const string& name) - : AstNode(fl) + AstNodeModule(AstType t, FileLine* fl, const string& name) + : AstNode(t, fl) , m_name(name), m_origName(name) , m_modPublic(false), m_modTrace(false), m_inLibrary(false), m_dead(false) , m_internal(false), m_recursive(false), m_recursiveClone(false) @@ -2245,7 +2272,7 @@ public: AstActive* activesp() const { return VN_CAST(op3p(), Active); } // op3 = List of i/sblocks // METHODS void addInlinesp(AstNode* nodep) { addOp1p(nodep); } - void addStmtp(AstNode* nodep) { addOp2p(nodep); } + void addStmtp(AstNode* nodep) { addNOp2p(nodep); } void addActivep(AstNode* nodep) { addOp3p(nodep); } // ACCESSORS virtual void name(const string& name) { m_name = name; } @@ -2276,18 +2303,14 @@ public: class AstNodeRange : public AstNode { // A range, sized or unsized public: - explicit AstNodeRange(FileLine* fl) : AstNode(fl) { } + AstNodeRange(AstType t, FileLine* fl) + : AstNode(t, fl) {} ASTNODE_BASE_FUNCS(NodeRange) }; //###################################################################### -#include "V3AstNodes.h" - -#include "V3Ast__gen_impl.h" // From ./astgen -// Things like: -// inline AstAlways* AstNode::castAlways() { return dynamic_cast(this); } -// inline bool AstNode::privateIsaAlways(const AstNode* nodep) { return nodep && nodep->type() == AstType::atAlways; } +#include "V3AstNodes__gen.h" //###################################################################### // Inline AstNVisitor METHODS diff --git a/src/V3AstNodes.cpp b/src/V3AstNodes.cpp index 5da84c5c8..8b2f93b3b 100644 --- a/src/V3AstNodes.cpp +++ b/src/V3AstNodes.cpp @@ -168,7 +168,7 @@ AstNodeBiop* AstEqWild::newTyped(FileLine* fl, AstNode* lhsp, AstNode* rhsp) { } AstExecGraph::AstExecGraph(FileLine* fileline) - : AstNode(fileline) { + : AstNode(AstType::atExecGraph, fileline) { m_depGraphp = new V3Graph; } AstExecGraph::~AstExecGraph() { @@ -943,6 +943,14 @@ void AstBasicDType::dump(std::ostream& str) const { str<<" kwd="<AstNode::dump(str); str<<" sz"<AstNodeDType::dump(str); str<<" "<prettyDTypeName() << declRange(); + return os.str(); +} +string AstUnpackArrayDType::prettyDTypeName() const { + std::ostringstream os; + string ranges = cvtToStr(declRange()); + // Unfortunately we need a single $ for the first unpacked, and all + // dimensions shown in "reverse" order + AstNodeDType* subp = subDTypep()->skipRefp(); + while (AstUnpackArrayDType* adtypep = VN_CAST(subp, UnpackArrayDType)) { + ranges += cvtToStr(adtypep->declRange()); + subp = adtypep->subDTypep()->skipRefp(); + } + os << subp->prettyDTypeName() << "$" << ranges; + return os.str(); +} void AstNodeModule::dump(std::ostream& str) const { this->AstNode::dump(str); str<<" L"<AstNodeDType::dumpSmall(str); str<<"[assoc-"<<(void*)keyDTypep()<<"]"; } +string AstAssocArrayDType::prettyDTypeName() const { + return subDTypep()->prettyDTypeName() + "[" + keyDTypep()->prettyDTypeName() + "]"; +} void AstQueueDType::dumpSmall(std::ostream& str) const { this->AstNodeDType::dumpSmall(str); str<<"[queue]"; } +string AstQueueDType::prettyDTypeName() const { + string str = subDTypep()->prettyDTypeName() + "[$"; + if (boundConst()) str += ":" + cvtToStr(boundConst()); + return str + "]"; +} void AstUnsizedArrayDType::dumpSmall(std::ostream& str) const { this->AstNodeDType::dumpSmall(str); str<<"[]"; diff --git a/src/V3AstNodes.h b/src/V3AstNodes.h index 865014825..37947da07 100644 --- a/src/V3AstNodes.h +++ b/src/V3AstNodes.h @@ -30,7 +30,6 @@ #define ASTNODE_NODE_FUNCS_NO_DTOR(name) \ virtual void accept(AstNVisitor& v) { v.visit(this); } \ - virtual AstType type() const { return AstType::at ## name; } \ virtual AstNode* clone() { return new Ast ##name (*this); } \ static Ast ##name * cloneTreeNull(Ast ##name * nodep, bool cloneNextLink) { \ return nodep ? nodep->cloneTree(cloneNextLink) : NULL; } \ @@ -41,6 +40,11 @@ virtual ~Ast ##name() {} \ ASTNODE_NODE_FUNCS_NO_DTOR(name) +//###################################################################### +// Macros replaced by 'astgen' + +#define ASTGEN_SUPER(...) // Roughly: (AstType::at, ...) + //###################################################################### //=== Ast* : Specific types // Netlist interconnect @@ -62,75 +66,75 @@ private: } public: AstConst(FileLine* fl, const V3Number& num) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(num) { initWithNumber(); } class WidthedValue {}; // for creator type-overload selection AstConst(FileLine* fl, WidthedValue, int width, uint32_t value) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, width, value) { initWithNumber(); } class DtypedValue{}; // for creator type-overload selection AstConst(FileLine* fl, DtypedValue, AstNodeDType* nodedtypep, uint32_t value) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, nodedtypep->width(), value, nodedtypep->widthSized()) { initWithNumber(); } class StringToParse {}; // for creator type-overload selection AstConst(FileLine* fl, StringToParse, const char* sourcep) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, sourcep) { initWithNumber(); } class VerilogStringLiteral {}; // for creator type-overload selection AstConst(FileLine* fl, VerilogStringLiteral, const string& str) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(V3Number::VerilogStringLiteral(), this, str) { initWithNumber(); } AstConst(FileLine* fl, uint32_t num) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 32, num) { dtypeSetLogicUnsized(m_num.width(), 0, AstNumeric::UNSIGNED); } class Unsized32 {}; // for creator type-overload selection AstConst(FileLine* fl, Unsized32, uint32_t num) // Unsized 32-bit integer of specified value - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 32, num) { m_num.width(32, false); dtypeSetLogicUnsized(32, m_num.widthMin(), AstNumeric::UNSIGNED); } class Signed32 {}; // for creator type-overload selection AstConst(FileLine* fl, Signed32, int32_t num) // Signed 32-bit integer of specified value - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 32, num) { m_num.width(32, true); dtypeSetLogicUnsized(32, m_num.widthMin(), AstNumeric::SIGNED); } class SizedEData {}; // for creator type-overload selection AstConst(FileLine* fl, SizedEData, vluint64_t num) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, VL_EDATASIZE, 0) { m_num.setQuad(num); dtypeSetLogicSized(VL_EDATASIZE, AstNumeric::UNSIGNED); } class RealDouble {}; // for creator type-overload selection AstConst(FileLine* fl, RealDouble, double num) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 64) { m_num.setDouble(num); dtypeSetDouble(); } class String {}; // for creator type-overload selection AstConst(FileLine* fl, String, const string& num) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(V3Number::String(), this, num) { dtypeSetString(); } class LogicFalse {}; AstConst(FileLine* fl, LogicFalse) // Shorthand const 0, dtype should be a logic of size 1 - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 1, 0) { dtypeSetLogicBool(); } class LogicTrue {}; AstConst(FileLine* fl, LogicTrue) // Shorthand const 1, dtype should be a logic of size 1 - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_num(this, 1, 1) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Const) virtual string name() const { return num().ascii(); } // * = Value @@ -157,17 +161,17 @@ private: bool m_littleEndian:1; // Bit vector is little endian public: AstRange(FileLine* fl, AstNode* msbp, AstNode* lsbp) - : AstNodeRange(fl) { + : ASTGEN_SUPER(fl) { m_littleEndian = false; setOp2p(msbp); setOp3p(lsbp); } AstRange(FileLine* fl, int msb, int lsb) - : AstNodeRange(fl) { + : ASTGEN_SUPER(fl) { m_littleEndian = false; setOp2p(new AstConst(fl, msb)); setOp3p(new AstConst(fl, lsb)); } AstRange(FileLine* fl, const VNumRange& range) - : AstNodeRange(fl) { + : ASTGEN_SUPER(fl) { m_littleEndian = range.littleEndian(); setOp2p(new AstConst(fl, range.hi())); setOp3p(new AstConst(fl, range.lo())); @@ -195,8 +199,8 @@ class AstAssocRange : public AstNodeRange { // Associative array range specification // Only for early parsing - becomes AstAssocDType public: - explicit AstAssocRange(FileLine* fl, AstNodeDType* dtp) - : AstNodeRange(fl) { + AstAssocRange(FileLine* fl, AstNodeDType* dtp) + : ASTGEN_SUPER(fl) { setOp1p(dtp); } ASTNODE_NODE_FUNCS(AssocRange) @@ -212,7 +216,7 @@ class AstQueueRange : public AstNodeRange { // Only for early parsing - becomes AstQueueDType public: explicit AstQueueRange(FileLine* fl) - : AstNodeRange(fl) {} + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(QueueRange) virtual string emitC() { V3ERROR_NA; return ""; } virtual string emitVerilog() { V3ERROR_NA; return ""; } @@ -223,7 +227,8 @@ public: class AstUnsizedRange : public AstNodeRange { // Unsized range specification, for open arrays public: - explicit AstUnsizedRange(FileLine* fl) : AstNodeRange(fl) { } + explicit AstUnsizedRange(FileLine* fl) + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(UnsizedRange) virtual string emitC() { V3ERROR_NA; return ""; } virtual string emitVerilog() { return "[]"; } @@ -234,7 +239,8 @@ public: class AstGatePin : public AstNodeMath { // Possibly expand a gate primitive input pin value to match the range of the gate primitive public: - AstGatePin(FileLine* fl, AstNode* lhsp, AstRange* rangep) : AstNodeMath(fl) { + AstGatePin(FileLine* fl, AstNode* lhsp, AstRange* rangep) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); setOp2p(rangep); } ASTNODE_NODE_FUNCS(GatePin) @@ -250,7 +256,7 @@ class AstClass : public AstNode { string m_name; // Name public: AstClass(FileLine* fl, const string& name) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) {} ASTNODE_NODE_FUNCS(Class) virtual string name() const { return m_name; } // * = Var name @@ -272,7 +278,7 @@ private: string m_name; // Name of variable public: AstParamTypeDType(FileLine* fl, AstVarType type, const string& name, VFlagChildDType, AstNodeDType* dtp) - : AstNodeDType(fl), m_varType(type), m_name(name) { + : ASTGEN_SUPER(fl), m_varType(type), m_name(name) { childDTypep(dtp); // Only for parser dtypep(NULL); // V3Width will resolve } @@ -308,7 +314,7 @@ private: string m_tag; // Holds the string of the verilator tag -- used in XML output. public: AstTypedef(FileLine* fl, const string& name, AstNode* attrsp, VFlagChildDType, AstNodeDType* dtp) - : AstNode(fl), m_name(name) { + : ASTGEN_SUPER(fl), m_name(name) { childDTypep(dtp); // Only for parser addAttrsp(attrsp); dtypep(NULL); // V3Width will resolve @@ -339,7 +345,7 @@ private: string m_name; public: AstTypedefFwd(FileLine* fl, const string& name) - : AstNode(fl), m_name(name) {} + : ASTGEN_SUPER(fl), m_name(name) {} ASTNODE_NODE_FUNCS(TypedefFwd) // METHODS virtual string name() const { return m_name; } @@ -356,7 +362,7 @@ private: public: AstDefImplicitDType(FileLine* fl, const string& name, void* containerp, VFlagChildDType, AstNodeDType* dtp) - : AstNodeDType(fl), m_name(name), m_containerp(containerp) { + : ASTGEN_SUPER(fl), m_name(name), m_containerp(containerp) { childDTypep(dtp); // Only for parser dtypep(NULL); // V3Width will resolve m_uniqueNum = uniqueNumInc(); @@ -394,7 +400,7 @@ private: AstNodeDType* m_keyDTypep; // Keys of this type (after widthing) public: AstAssocArrayDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp, AstNodeDType* keyDtp) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser keyChildDTypep(keyDtp); // Only for parser refDTypep(NULL); @@ -419,6 +425,7 @@ public: const AstAssocArrayDType* asamep = static_cast(samep); return (subDTypep()->skipRefp()->similarDType(asamep->subDTypep()->skipRefp())); } + virtual string prettyDTypeName() const; virtual void dumpSmall(std::ostream& str) const; virtual V3Hash sameHash() const { return V3Hash(m_refDTypep); } AstNodeDType* getChildDTypep() const { return childDTypep(); } @@ -450,7 +457,7 @@ class AstPackArrayDType : public AstNodeArrayDType { // Children: RANGE (array bounds) public: AstPackArrayDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp, AstRange* rangep) - : AstNodeArrayDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser refDTypep(NULL); setOp2p(rangep); @@ -459,7 +466,7 @@ public: widthForce(width, width); } AstPackArrayDType(FileLine* fl, AstNodeDType* dtp, AstRange* rangep) - : AstNodeArrayDType(fl) { + : ASTGEN_SUPER(fl) { refDTypep(dtp); setOp2p(rangep); dtypep(this); @@ -467,6 +474,7 @@ public: widthForce(width, width); } ASTNODE_NODE_FUNCS(PackArrayDType) + virtual string prettyDTypeName() const; }; class AstUnpackArrayDType : public AstNodeArrayDType { @@ -475,7 +483,7 @@ class AstUnpackArrayDType : public AstNodeArrayDType { // Children: RANGE (array bounds) public: AstUnpackArrayDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp, AstRange* rangep) - : AstNodeArrayDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser refDTypep(NULL); setOp2p(rangep); @@ -485,7 +493,7 @@ public: widthFromSub(subDTypep()); } AstUnpackArrayDType(FileLine* fl, AstNodeDType* dtp, AstRange* rangep) - : AstNodeArrayDType(fl) { + : ASTGEN_SUPER(fl) { refDTypep(dtp); setOp2p(rangep); dtypep(this); @@ -494,6 +502,7 @@ public: widthFromSub(subDTypep()); } ASTNODE_NODE_FUNCS(UnpackArrayDType) + virtual string prettyDTypeName() const; }; class AstUnsizedArrayDType : public AstNodeDType { @@ -503,7 +512,7 @@ private: AstNodeDType* m_refDTypep; // Elements of this type (after widthing) public: AstUnsizedArrayDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser refDTypep(NULL); dtypep(NULL); // V3Width will resolve @@ -553,23 +562,23 @@ private: // See also in AstNodeDType: m_width, m_widthMin, m_numeric(issigned) public: AstBasicDType(FileLine* fl, AstBasicDTypeKwd kwd, VSignedState signst=signedst_NOSIGN) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { init(kwd, AstNumeric(signst), 0, -1, NULL); } AstBasicDType(FileLine* fl, VFlagLogicPacked, int wantwidth) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { init(AstBasicDTypeKwd::LOGIC, AstNumeric::NOSIGN, wantwidth, -1, NULL); } AstBasicDType(FileLine* fl, VFlagBitPacked, int wantwidth) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { init(AstBasicDTypeKwd::BIT, AstNumeric::NOSIGN, wantwidth, -1, NULL); } AstBasicDType(FileLine* fl, AstBasicDTypeKwd kwd, AstNumeric numer, int wantwidth, int widthmin) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { init(kwd, numer, wantwidth, widthmin, NULL); } AstBasicDType(FileLine* fl, AstBasicDTypeKwd kwd, AstNumeric numer, VNumRange range, int widthmin) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { init(kwd, numer, range.elements(), widthmin, NULL); m.m_nrange = range; // as init() presumes lsb==0, but range.lsb() might not be } @@ -617,6 +626,7 @@ public: virtual bool similarDType(AstNodeDType* samep) const { return type()==samep->type() && same(samep); } virtual string name() const { return m.m_keyword.ascii(); } + virtual string prettyDTypeName() const; virtual const char* broken() const { BROKEN_RTN(dtypep()!=this); return NULL; } AstRange* rangep() const { return VN_CAST(op1p(), Range); } // op1 = Range of variable void rangep(AstRange* nodep) { setNOp1p(nodep); } @@ -667,7 +677,7 @@ private: AstNodeDType* m_refDTypep; // Inherit from this base data type public: AstConstDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser refDTypep(NULL); // V3Width will resolve dtypep(NULL); // V3Width will resolve @@ -708,7 +718,7 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstClassRefDType(FileLine* fl, AstClass* classp) - : AstNodeDType(fl), m_classp(classp), m_packagep(NULL) { + : ASTGEN_SUPER(fl), m_classp(classp), m_packagep(NULL) { dtypep(this); } ASTNODE_NODE_FUNCS(ClassRefDType) @@ -753,14 +763,14 @@ private: public: AstIfaceRefDType(FileLine* fl, const string& cellName, const string& ifaceName) - : AstNodeDType(fl), m_modportFileline(NULL), - m_cellName(cellName), m_ifaceName(ifaceName), m_modportName(""), - m_ifacep(NULL), m_cellp(NULL), m_modportp(NULL) { } + : ASTGEN_SUPER(fl), m_modportFileline(NULL) + , m_cellName(cellName), m_ifaceName(ifaceName), m_modportName("") + , m_ifacep(NULL), m_cellp(NULL), m_modportp(NULL) { } AstIfaceRefDType(FileLine* fl, FileLine* modportFl, const string& cellName, const string& ifaceName, const string& modport) - : AstNodeDType(fl), m_modportFileline(modportFl), - m_cellName(cellName), m_ifaceName(ifaceName), m_modportName(modport), - m_ifacep(NULL), m_cellp(NULL), m_modportp(NULL) { } + : ASTGEN_SUPER(fl), m_modportFileline(modportFl) + , m_cellName(cellName), m_ifaceName(ifaceName), m_modportName(modport) + , m_ifacep(NULL), m_cellp(NULL), m_modportp(NULL) { } ASTNODE_NODE_FUNCS(IfaceRefDType) // METHODS virtual const char* broken() const; @@ -799,7 +809,7 @@ private: AstNodeDType* m_refDTypep; // Elements of this type (after widthing) public: AstQueueDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp, AstNode* boundp) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { setNOp2p(boundp); childDTypep(dtp); // Only for parser refDTypep(NULL); @@ -821,6 +831,7 @@ public: } virtual void dumpSmall(std::ostream& str) const; virtual V3Hash sameHash() const { return V3Hash(m_refDTypep); } + virtual string prettyDTypeName() const; AstNodeDType* getChildDTypep() const { return childDTypep(); } AstNodeDType* childDTypep() const { return VN_CAST(op1p(), NodeDType); } // op1 = Range of variable void childDTypep(AstNodeDType* nodep) { setOp1p(nodep); } @@ -847,12 +858,17 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstRefDType(FileLine* fl, const string& name) - : AstNodeDType(fl), m_refDTypep(NULL), m_name(name), m_packagep(NULL) {} + : ASTGEN_SUPER(fl), m_refDTypep(NULL), m_name(name), m_packagep(NULL) {} AstRefDType(FileLine* fl, AstNodeDType* defp) - : AstNodeDType(fl), m_refDTypep(defp), m_packagep(NULL) { + : ASTGEN_SUPER(fl), m_refDTypep(defp), m_packagep(NULL) { dtypeFrom(defp->dtypep()); widthFromSub(subDTypep()); } + class FlagTypeOfExpr {}; // type(expr) for parser only + AstRefDType(FileLine* fl, FlagTypeOfExpr, AstNode* typeofp) + : ASTGEN_SUPER(fl), m_refDTypep(NULL), m_packagep(NULL) { + setOp2p(typeofp); + } ASTNODE_NODE_FUNCS(RefDType) // METHODS virtual const char* broken() const { BROKEN_RTN(m_refDTypep && !m_refDTypep->brokeExists()); return NULL; } @@ -869,6 +885,8 @@ public: virtual V3Hash sameHash() const { return V3Hash(V3Hash(m_refDTypep), V3Hash(m_packagep)); } virtual void dump(std::ostream& str=std::cout) const; virtual string name() const { return m_name; } + virtual string prettyDTypeName() const { + return subDTypep() ? subDTypep()->name() : prettyName(); } virtual AstBasicDType* basicp() const { return subDTypep() ? subDTypep()->basicp() : NULL; } virtual AstNodeDType* skipRefp() const { // Skip past both the Ref and the Typedef @@ -895,13 +913,14 @@ public: virtual AstNodeDType* subDTypep() const { return m_refDTypep; } AstPackage* packagep() const { return m_packagep; } void packagep(AstPackage* nodep) { m_packagep = nodep; } + AstNode* typeofp() const { return op2p(); } }; class AstStructDType : public AstNodeUOrStructDType { public: // AstNumeric below is mispurposed to indicate if packed or not AstStructDType(FileLine* fl, AstNumeric numericUnpack) - : AstNodeUOrStructDType(fl, numericUnpack) {} + : ASTGEN_SUPER(fl, numericUnpack) {} ASTNODE_NODE_FUNCS(StructDType) virtual string verilogKwd() const { return "struct"; } }; @@ -911,7 +930,7 @@ public: //UNSUP: bool isTagged; // AstNumeric below is mispurposed to indicate if packed or not AstUnionDType(FileLine* fl, AstNumeric numericUnpack) - : AstNodeUOrStructDType(fl, numericUnpack) {} + : ASTGEN_SUPER(fl, numericUnpack) {} ASTNODE_NODE_FUNCS(UnionDType) virtual string verilogKwd() const { return "union"; } }; @@ -927,14 +946,14 @@ private: //UNSUP: int m_randType; // Randomization type (IEEE) public: AstMemberDType(FileLine* fl, const string& name, VFlagChildDType, AstNodeDType* dtp) - : AstNodeDType(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_lsb(-1) { childDTypep(dtp); // Only for parser dtypep(NULL); // V3Width will resolve refDTypep(NULL); } AstMemberDType(FileLine* fl, const string& name, AstNodeDType* dtp) - : AstNodeDType(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_lsb(-1) { UASSERT(dtp, "AstMember created with no dtype"); refDTypep(dtp); @@ -978,7 +997,7 @@ class AstVoidDType : public AstNodeDType { // For e.g. a function returning void public: AstVoidDType(FileLine* fl) - : AstNodeDType(fl) { dtypep(this); } + : ASTGEN_SUPER(fl) { dtypep(this); } ASTNODE_NODE_FUNCS(VoidDType) virtual void dumpSmall(std::ostream& str) const; virtual bool hasDType() const { return true; } @@ -1002,7 +1021,7 @@ private: public: // Parents: ENUM AstEnumItem(FileLine* fl, const string& name, AstNode* rangep, AstNode* initp) - : AstNode(fl), m_name(name) + : ASTGEN_SUPER(fl), m_name(name) { addNOp1p(rangep); addNOp2p(initp); } ASTNODE_NODE_FUNCS(EnumItem) virtual string name() const { return m_name; } @@ -1021,7 +1040,7 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstEnumItemRef(FileLine* fl, AstEnumItem* itemp, AstPackage* packagep) - : AstNodeMath(fl), m_itemp(itemp), m_packagep(packagep) { + : ASTGEN_SUPER(fl), m_itemp(itemp), m_packagep(packagep) { dtypeFrom(m_itemp); } ASTNODE_NODE_FUNCS(EnumItemRef) @@ -1050,7 +1069,7 @@ private: int m_uniqueNum; public: AstEnumDType(FileLine* fl, VFlagChildDType, AstNodeDType* dtp, AstNode* itemsp) - : AstNodeDType(fl) { + : ASTGEN_SUPER(fl) { childDTypep(dtp); // Only for parser refDTypep(NULL); addNOp2p(itemsp); @@ -1095,7 +1114,7 @@ class AstParseTypeDType : public AstNodeDType { // e.g. the data type is a container of any data type public: explicit AstParseTypeDType(FileLine* fl) - : AstNodeDType(fl) {} + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(ParseTypeDType) AstNodeDType* dtypep() const { return NULL; } // METHODS @@ -1122,11 +1141,11 @@ private: } public: AstArraySel(FileLine* fl, AstNode* fromp, AstNode* bitp) - :AstNodeSel(fl, fromp, bitp) { + : ASTGEN_SUPER(fl, fromp, bitp) { init(fromp); } AstArraySel(FileLine* fl, AstNode* fromp, int bit) - :AstNodeSel(fl, fromp, new AstConst(fl, bit)) { + : ASTGEN_SUPER(fl, fromp, new AstConst(fl, bit)) { init(fromp); } ASTNODE_NODE_FUNCS(ArraySel) @@ -1161,7 +1180,7 @@ private: } public: AstAssocSel(FileLine* fl, AstNode* fromp, AstNode* bitp) - : AstNodeSel(fl, fromp, bitp) { + : ASTGEN_SUPER(fl, fromp, bitp) { init(fromp); } ASTNODE_NODE_FUNCS(AssocSel) @@ -1187,7 +1206,7 @@ class AstWordSel : public AstNodeSel { // Select a single word from a multi-word wide value public: AstWordSel(FileLine* fl, AstNode* fromp, AstNode* bitp) - : AstNodeSel(fl, fromp, bitp) { + : ASTGEN_SUPER(fl, fromp, bitp) { dtypeSetUInt32(); // Always used on WData arrays so returns edata size } ASTNODE_NODE_FUNCS(WordSel) @@ -1208,7 +1227,7 @@ class AstSelExtract : public AstNodePreSel { // Range extraction, gets replaced with AstSel public: AstSelExtract(FileLine* fl, AstNode* fromp, AstNode* msbp, AstNode* lsbp) - : AstNodePreSel(fl, fromp, msbp, lsbp) {} + : ASTGEN_SUPER(fl, fromp, msbp, lsbp) {} ASTNODE_NODE_FUNCS(SelExtract) AstNode* msbp() const { return rhsp(); } AstNode* lsbp() const { return thsp(); } @@ -1219,7 +1238,7 @@ class AstSelBit : public AstNodePreSel { // Gets replaced during link with AstArraySel or AstSel public: AstSelBit(FileLine* fl, AstNode* fromp, AstNode* bitp) - :AstNodePreSel(fl, fromp, bitp, NULL) { + : ASTGEN_SUPER(fl, fromp, bitp, NULL) { UASSERT_OBJ(!v3Global.assertDTypesResolved(), this, "not coded to create after dtypes resolved"); } ASTNODE_NODE_FUNCS(SelBit) @@ -1231,7 +1250,7 @@ class AstSelPlus : public AstNodePreSel { // Gets replaced during link with AstSel public: AstSelPlus(FileLine* fl, AstNode* fromp, AstNode* bitp, AstNode* widthp) - : AstNodePreSel(fl, fromp, bitp, widthp) {} + : ASTGEN_SUPER(fl, fromp, bitp, widthp) {} ASTNODE_NODE_FUNCS(SelPlus) AstNode* bitp() const { return rhsp(); } AstNode* widthp() const { return thsp(); } @@ -1242,7 +1261,7 @@ class AstSelMinus : public AstNodePreSel { // Gets replaced during link with AstSel public: AstSelMinus(FileLine* fl, AstNode* fromp, AstNode* bitp, AstNode* widthp) - : AstNodePreSel(fl, fromp, bitp, widthp) {} + : ASTGEN_SUPER(fl, fromp, bitp, widthp) {} ASTNODE_NODE_FUNCS(SelMinus) AstNode* bitp() const { return rhsp(); } AstNode* widthp() const { return thsp(); } @@ -1259,7 +1278,7 @@ private: int m_declElWidth; // If a packed array, the number of bits per element public: AstSel(FileLine* fl, AstNode* fromp, AstNode* lsbp, AstNode* widthp) - : AstNodeTriop(fl, fromp, lsbp, widthp) { + : ASTGEN_SUPER(fl, fromp, lsbp, widthp) { m_declElWidth = 1; if (VN_IS(widthp, Const)) { dtypeSetLogicSized(VN_CAST(widthp, Const)->toUInt(), @@ -1267,7 +1286,7 @@ public: } } AstSel(FileLine* fl, AstNode* fromp, int lsb, int bitwidth) - : AstNodeTriop(fl, fromp, + : ASTGEN_SUPER(fl, fromp, new AstConst(fl, lsb), new AstConst(fl, bitwidth)) { m_declElWidth = 1; dtypeSetLogicSized(bitwidth, AstNumeric::UNSIGNED); @@ -1312,7 +1331,7 @@ private: VNumRange m_declRange; // Range of the 'from' array if isRanged() is set, else invalid public: AstSliceSel(FileLine* fl, AstNode* fromp, const VNumRange& declRange) - : AstNodeTriop(fl, fromp, + : ASTGEN_SUPER(fl, fromp, new AstConst(fl, declRange.lo()), new AstConst(fl, declRange.elements())) , m_declRange(declRange) { } @@ -1347,13 +1366,13 @@ private: string m_name; // Name of method public: AstMethodCall(FileLine* fl, AstNode* fromp, VFlagChildDType, const string& name, AstNode* pinsp) - : AstNode(fl), m_name(name) { + : ASTGEN_SUPER(fl), m_name(name) { setOp1p(fromp); dtypep(NULL); // V3Width will resolve addNOp2p(pinsp); } AstMethodCall(FileLine* fl, AstNode* fromp, const string& name, AstNode* pinsp) - : AstNode(fl), m_name(name) { + : ASTGEN_SUPER(fl), m_name(name) { setOp1p(fromp); addNOp2p(pinsp); } @@ -1367,7 +1386,7 @@ public: }; class AstCMethodHard : public AstNodeStmt { - // A reference to a "C" hardocded member task (or function) + // A reference to a "C" hardcoded member task (or function) // PARENTS: stmt/math // Not all calls are statments vs math. AstNodeStmt needs isStatement() to deal. private: @@ -1376,7 +1395,7 @@ private: public: AstCMethodHard(FileLine* fl, AstNode* fromp, VFlagChildDType, const string& name, AstNode* pinsp) - : AstNodeStmt(fl, false) + : ASTGEN_SUPER(fl, false) , m_name(name) , m_pure(false) { setOp1p(fromp); @@ -1384,7 +1403,7 @@ public: addNOp2p(pinsp); } AstCMethodHard(FileLine* fl, AstNode* fromp, const string& name, AstNode* pinsp) - : AstNodeStmt(fl, false) + : ASTGEN_SUPER(fl, false) , m_name(name) { setOp1p(fromp); addNOp2p(pinsp); @@ -1467,7 +1486,7 @@ private: } public: AstVar(FileLine* fl, AstVarType type, const string& name, VFlagChildDType, AstNodeDType* dtp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origName(name) { init(); combineType(type); @@ -1477,7 +1496,7 @@ public: else m_declKwd = AstBasicDTypeKwd::LOGIC; } AstVar(FileLine* fl, AstVarType type, const string& name, AstNodeDType* dtp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origName(name) { init(); combineType(type); @@ -1487,7 +1506,7 @@ public: else m_declKwd = AstBasicDTypeKwd::LOGIC; } AstVar(FileLine* fl, AstVarType type, const string& name, VFlagLogicPacked, int wantwidth) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origName(name) { init(); combineType(type); @@ -1495,7 +1514,7 @@ public: m_declKwd = AstBasicDTypeKwd::LOGIC; } AstVar(FileLine* fl, AstVarType type, const string& name, VFlagBitPacked, int wantwidth) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origName(name) { init(); combineType(type); @@ -1503,7 +1522,7 @@ public: m_declKwd = AstBasicDTypeKwd::BIT; } AstVar(FileLine* fl, AstVarType type, const string& name, AstVar* examplep) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origName(name) { init(); combineType(type); @@ -1690,7 +1709,7 @@ private: string m_path; // Dotted cellname to set parameter of public: AstDefParam(FileLine* fl, const string& path, const string& name, AstNode* rhsp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { setOp1p(rhsp); m_name = name; m_path = path; @@ -1709,7 +1728,7 @@ class AstImplicit : public AstNode { // Parents: MODULE public: AstImplicit(FileLine* fl, AstNode* exprsp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(Implicit) @@ -1729,7 +1748,7 @@ private: public: AstScope(FileLine* fl, AstNodeModule* modp, const string& name, AstScope* aboveScopep, AstCell* aboveCellp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_aboveScopep(aboveScopep), m_aboveCellp(aboveCellp), m_modp(modp) {} ASTNODE_NODE_FUNCS(Scope) virtual void cloneRelink(); @@ -1758,7 +1777,7 @@ class AstTopScope : public AstNode { // Children: SCOPEs public: AstTopScope(FileLine* fl, AstScope* ascopep) - : AstNode(fl) + : ASTGEN_SUPER(fl) {addNOp2p(ascopep);} ASTNODE_NODE_FUNCS(TopScope) AstNode* stmtsp() const { return op1p(); } @@ -1779,7 +1798,7 @@ private: bool m_trace:1; // Tracing is turned on for this scope public: AstVarScope(FileLine* fl, AstScope* scopep, AstVar* varp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_scopep(scopep), m_varp(varp) { m_circular = false; m_trace = true; @@ -1811,14 +1830,14 @@ class AstVarRef : public AstNodeVarRef { // A reference to a variable (lvalue or rvalue) public: AstVarRef(FileLine* fl, const string& name, bool lvalue) - : AstNodeVarRef(fl, name, NULL, lvalue) {} + : ASTGEN_SUPER(fl, name, NULL, lvalue) {} // This form only allowed post-link because output/wire compression may // lead to deletion of AstVar's AstVarRef(FileLine* fl, AstVar* varp, bool lvalue) - : AstNodeVarRef(fl, varp->name(), varp, lvalue) {} + : ASTGEN_SUPER(fl, varp->name(), varp, lvalue) {} // This form only allowed post-link (see above) AstVarRef(FileLine* fl, AstVarScope* varscp, bool lvalue) - : AstNodeVarRef(fl, varscp->varp()->name(), varscp->varp(), lvalue) { + : ASTGEN_SUPER(fl, varscp->varp()->name(), varscp->varp(), lvalue) { varScopep(varscp); } ASTNODE_NODE_FUNCS(VarRef) @@ -1850,10 +1869,10 @@ private: string m_inlinedDots; // Dotted hierarchy flattened out public: AstVarXRef(FileLine* fl, const string& name, const string& dotted, bool lvalue) - : AstNodeVarRef(fl, name, NULL, lvalue) + : ASTGEN_SUPER(fl, name, NULL, lvalue) , m_dotted(dotted) { } AstVarXRef(FileLine* fl, AstVar* varp, const string& dotted, bool lvalue) - : AstNodeVarRef(fl, varp->name(), varp, lvalue) + : ASTGEN_SUPER(fl, varp->name(), varp, lvalue) , m_dotted(dotted) { dtypeFrom(varp); } @@ -1888,7 +1907,7 @@ private: bool m_svImplicit; // Pin is SystemVerilog .name'ed public: AstPin(FileLine* fl, int pinNum, const string& name, AstNode* exprp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_param(false), m_svImplicit(false) { m_pinNum = pinNum; m_modVarp = NULL; @@ -1896,7 +1915,7 @@ public: setNOp1p(exprp); } AstPin(FileLine* fl, int pinNum, AstVarRef* varname, AstNode* exprp) - : AstNode(fl), m_param(false), m_svImplicit(false) { + : ASTGEN_SUPER(fl), m_param(false), m_svImplicit(false) { m_name = varname->name(); m_pinNum = pinNum; m_modVarp = NULL; @@ -1937,7 +1956,7 @@ private: string m_name; // Pin name, or "" for number based interconnect public: AstArg(FileLine* fl, const string& name, AstNode* exprp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) { setNOp1p(exprp); } @@ -1954,7 +1973,7 @@ class AstModule : public AstNodeModule { // A module declaration public: AstModule(FileLine* fl, const string& name) - : AstNodeModule(fl, name) {} + : ASTGEN_SUPER(fl, name) {} ASTNODE_NODE_FUNCS(Module) virtual string verilogKwd() const { return "module"; } }; @@ -1963,7 +1982,7 @@ class AstNotFoundModule : public AstNodeModule { // A missing module declaration public: AstNotFoundModule(FileLine* fl, const string& name) - : AstNodeModule(fl, name) {} + : ASTGEN_SUPER(fl, name) {} ASTNODE_NODE_FUNCS(NotFoundModule) virtual string verilogKwd() const { return "/*not-found-*/ module"; } }; @@ -1972,7 +1991,7 @@ class AstPackage : public AstNodeModule { // A package declaration public: AstPackage(FileLine* fl, const string& name) - : AstNodeModule(fl, name) {} + : ASTGEN_SUPER(fl, name) {} ASTNODE_NODE_FUNCS(Package) virtual string verilogKwd() const { return "package"; } static string dollarUnitName() { return AstNode::encodeName("$unit"); } @@ -1983,7 +2002,7 @@ class AstPrimitive : public AstNodeModule { // A primitive declaration public: AstPrimitive(FileLine* fl, const string& name) - : AstNodeModule(fl, name) {} + : ASTGEN_SUPER(fl, name) {} ASTNODE_NODE_FUNCS(Primitive) virtual string verilogKwd() const { return "primitive"; } }; @@ -1993,7 +2012,7 @@ class AstPackageExportStarStar : public AstNode { public: // cppcheck-suppress noExplicitConstructor AstPackageExportStarStar(FileLine* fl) - : AstNode(fl) {} + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(PackageExportStarStar) }; @@ -2004,7 +2023,7 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstPackageExport(FileLine* fl, AstPackage* packagep, const string& name) - : AstNode(fl), m_name(name), m_packagep(packagep) {} + : ASTGEN_SUPER(fl), m_name(name), m_packagep(packagep) {} ASTNODE_NODE_FUNCS(PackageExport) virtual const char* broken() const { BROKEN_RTN(!m_packagep || !m_packagep->brokeExists()); return NULL; } virtual void cloneRelink() { if (m_packagep && m_packagep->clonep()) m_packagep = m_packagep->clonep(); } @@ -2021,7 +2040,7 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstPackageImport(FileLine* fl, AstPackage* packagep, const string& name) - : AstNode(fl), m_name(name), m_packagep(packagep) {} + : ASTGEN_SUPER(fl), m_name(name), m_packagep(packagep) {} ASTNODE_NODE_FUNCS(PackageImport) virtual const char* broken() const { BROKEN_RTN(!m_packagep || !m_packagep->brokeExists()); return NULL; } virtual void cloneRelink() { if (m_packagep && m_packagep->clonep()) m_packagep = m_packagep->clonep(); } @@ -2035,7 +2054,7 @@ class AstIface : public AstNodeModule { // A module declaration public: AstIface(FileLine* fl, const string& name) - : AstNodeModule(fl, name) { } + : ASTGEN_SUPER(fl, name) { } ASTNODE_NODE_FUNCS(Iface) }; @@ -2048,14 +2067,14 @@ private: AstVar* m_varp; // Post link, variable within class that is target of selection public: AstMemberSel(FileLine* fl, AstNode* fromp, VFlagChildDType, const string& name) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_name(name) , m_varp(NULL) { setOp1p(fromp); dtypep(NULL); // V3Width will resolve } AstMemberSel(FileLine* fl, AstNode* fromp, AstNodeDType* dtp) - : AstNodeMath(fl) + : ASTGEN_SUPER(fl) , m_name(dtp->name()) , m_varp(NULL) { setOp1p(fromp); @@ -2092,7 +2111,7 @@ private: AstNodeFTask* m_ftaskp; // Link to the function public: AstModportFTaskRef(FileLine* fl, const string& name, bool isExport) - : AstNode(fl), m_name(name), m_export(isExport), m_ftaskp(NULL) { } + : ASTGEN_SUPER(fl), m_name(name), m_export(isExport), m_ftaskp(NULL) { } ASTNODE_NODE_FUNCS(ModportFTaskRef) virtual const char* broken() const { BROKEN_RTN(m_ftaskp && !m_ftaskp->brokeExists()); return NULL; } virtual void dump(std::ostream& str) const; @@ -2114,7 +2133,7 @@ private: AstVar* m_varp; // Link to the actual Var public: AstModportVarRef(FileLine* fl, const string& name, VDirection::en direction) - : AstNode(fl), m_name(name), m_direction(direction), m_varp(NULL) { } + : ASTGEN_SUPER(fl), m_name(name), m_direction(direction), m_varp(NULL) { } ASTNODE_NODE_FUNCS(ModportVarRef) virtual const char* broken() const { BROKEN_RTN(m_varp && !m_varp->brokeExists()); return NULL; } virtual void dump(std::ostream& str) const; @@ -2132,7 +2151,7 @@ private: string m_name; // Name of the modport public: AstModport(FileLine* fl, const string& name, AstNode* varsp) - : AstNode(fl), m_name(name) { + : ASTGEN_SUPER(fl), m_name(name) { addNOp1p(varsp); } virtual string name() const { return m_name; } virtual bool maybePointedTo() const { return true; } @@ -2146,7 +2165,7 @@ private: string m_name; // Name of the reference public: AstIntfRef(FileLine* fl, const string& name) - : AstNode(fl), m_name(name) { } + : ASTGEN_SUPER(fl), m_name(name) { } virtual string name() const { return m_name; } ASTNODE_NODE_FUNCS(IntfRef) }; @@ -2166,7 +2185,7 @@ public: AstCell(FileLine* fl, FileLine* mfl, const string& instName, const string& modName, AstPin* pinsp, AstPin* paramsp, AstRange* rangep) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_modNameFileline(mfl) , m_name(instName), m_origName(instName), m_modName(modName) , m_modp(NULL), m_hasIfaceVar(false), m_recursive(false), m_trace(true) { @@ -2213,7 +2232,7 @@ private: AstScope* m_scopep; // The scope that the cell is inlined into public: AstCellInline(FileLine* fl, const string& name, const string& origModName) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name), m_origModName(origModName), m_scopep(NULL) {} ASTNODE_NODE_FUNCS(CellInline) virtual void dump(std::ostream& str) const; @@ -2233,7 +2252,7 @@ private: public: AstCellRef(FileLine* fl, const string& name, AstNode* cellp, AstNode* exprp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) { addNOp1p(cellp); addNOp2p(exprp); } ASTNODE_NODE_FUNCS(CellRef) @@ -2250,7 +2269,7 @@ private: public: AstCellArrayRef(FileLine* fl, const string& name, AstNode* selectExprp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) { addNOp1p(selectExprp); } ASTNODE_NODE_FUNCS(CellArrayRef) @@ -2266,7 +2285,7 @@ private: public: AstUnlinkedRef(FileLine* fl, AstNode* refp, const string& name, AstNode* crp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) { addNOp1p(refp); addNOp2p(crp); } ASTNODE_NODE_FUNCS(UnlinkedRef) @@ -2283,7 +2302,7 @@ private: string m_name; // Binding to name public: AstBind(FileLine* fl, const string& name, AstNode* cellsp) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_name(name) { UASSERT_OBJ(VN_IS(cellsp, Cell), cellsp, "Only cells allowed to be bound"); addNOp1p(cellsp); @@ -2302,7 +2321,7 @@ private: string m_name; // Name of pin public: AstPort(FileLine* fl, int pinnum, const string& name) - : AstNode(fl) + : ASTGEN_SUPER(fl) , m_pinNum(pinnum), m_name(name) {} ASTNODE_NODE_FUNCS(Port) virtual string name() const { return m_name; } // * = Port name @@ -2317,8 +2336,8 @@ class AstGenerate : public AstNode { // Parents: MODULE // Children: modItems public: - AstGenerate(FileLine* fileline, AstNode* stmtsp) - : AstNode(fileline) { + AstGenerate(FileLine* fl, AstNode* stmtsp) + : ASTGEN_SUPER(fl) { addNOp1p(stmtsp); } ASTNODE_NODE_FUNCS(Generate) @@ -2339,7 +2358,7 @@ private: public: AstParseRef(FileLine* fl, VParseRefExp expect, const string& name, AstNode* lhsp, AstNodeFTaskRef* ftaskrefp) - : AstNode(fl), m_expect(expect), m_name(name) { setNOp1p(lhsp); setNOp2p(ftaskrefp); } + : ASTGEN_SUPER(fl), m_expect(expect), m_name(name) { setNOp1p(lhsp); setNOp2p(ftaskrefp); } ASTNODE_NODE_FUNCS(ParseRef) virtual void dump(std::ostream& str) const; virtual string name() const { return m_name; } // * = Var name @@ -2364,7 +2383,7 @@ private: AstPackage* m_packagep; // Package hierarchy public: AstPackageRef(FileLine* fl, AstPackage* packagep) - : AstNode(fl), m_packagep(packagep) {} + : ASTGEN_SUPER(fl), m_packagep(packagep) {} ASTNODE_NODE_FUNCS(PackageRef) // METHODS virtual const char* broken() const { BROKEN_RTN(!m_packagep || !m_packagep->brokeExists()); return NULL; } @@ -2384,7 +2403,7 @@ class AstDot : public AstNode { // These are eliminated in the link stage public: AstDot(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNode(fl) { setOp1p(lhsp); setOp2p(rhsp); } + : ASTGEN_SUPER(fl) { setOp1p(lhsp); setOp2p(rhsp); } ASTNODE_NODE_FUNCS(Dot) static AstNode* newIfPkg(FileLine*fl, AstPackage* packagep, AstNode* rhsp) { // For parser, make only if non-null package if (!packagep) return rhsp; @@ -2401,7 +2420,7 @@ class AstUnbounded : public AstNode { // A $ in the parser, used for unbounded and queues public: AstUnbounded(FileLine* fl) - : AstNode(fl) {} + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(Unbounded) virtual string emitVerilog() { return "$"; } virtual string emitC() { V3ERROR_NA; return ""; } @@ -2413,7 +2432,7 @@ class AstTask : public AstNodeFTask { // A task inside a module public: AstTask(FileLine* fl, const string& name, AstNode* stmtp) - : AstNodeFTask(fl, name, stmtp) {} + : ASTGEN_SUPER(fl, name, stmtp) {} ASTNODE_NODE_FUNCS(Task) }; @@ -2421,7 +2440,7 @@ class AstFunc : public AstNodeFTask { // A function inside a module public: AstFunc(FileLine* fl, const string& name, AstNode* stmtp, AstNode* fvarsp) - : AstNodeFTask(fl, name, stmtp) { + : ASTGEN_SUPER(fl, name, stmtp) { addNOp1p(fvarsp); } ASTNODE_NODE_FUNCS(Func) @@ -2432,11 +2451,11 @@ class AstTaskRef : public AstNodeFTaskRef { // A reference to a task public: AstTaskRef(FileLine* fl, AstParseRef* namep, AstNode* pinsp) - : AstNodeFTaskRef(fl, true, namep, pinsp) { + : ASTGEN_SUPER(fl, true, namep, pinsp) { statement(true); } AstTaskRef(FileLine* fl, const string& name, AstNode* pinsp) - : AstNodeFTaskRef(fl, true, name, pinsp) {} + : ASTGEN_SUPER(fl, true, name, pinsp) {} ASTNODE_NODE_FUNCS(TaskRef) }; @@ -2444,9 +2463,9 @@ class AstFuncRef : public AstNodeFTaskRef { // A reference to a function public: AstFuncRef(FileLine* fl, AstParseRef* namep, AstNode* pinsp) - : AstNodeFTaskRef(fl, false, namep, pinsp) {} + : ASTGEN_SUPER(fl, false, namep, pinsp) {} AstFuncRef(FileLine* fl, const string& name, AstNode* pinsp) - : AstNodeFTaskRef(fl, false, name, pinsp) {} + : ASTGEN_SUPER(fl, false, name, pinsp) {} ASTNODE_NODE_FUNCS(FuncRef) virtual bool hasDType() const { return true; } }; @@ -2460,7 +2479,7 @@ private: string m_cname; // Name of function on c side public: AstDpiExport(FileLine* fl, const string& vname, const string& cname) - : AstNode(fl), m_name(vname), m_cname(cname) { } + : ASTGEN_SUPER(fl), m_name(vname), m_cname(cname) { } ASTNODE_NODE_FUNCS(DpiExport) virtual string name() const { return m_name; } virtual void name(const string& name) { m_name = name; } @@ -2482,27 +2501,27 @@ public: class Settle {}; // for creator type-overload selection class Never {}; // for creator type-overload selection AstSenItem(FileLine* fl, VEdgeType edgeType, AstNode* varrefp) - : AstNodeSenItem(fl), m_edgeType(edgeType) { + : ASTGEN_SUPER(fl), m_edgeType(edgeType) { setOp1p(varrefp); } AstSenItem(FileLine* fl, Combo) - : AstNodeSenItem(fl) { + : ASTGEN_SUPER(fl) { m_edgeType = VEdgeType::ET_COMBO; } AstSenItem(FileLine* fl, Illegal) - : AstNodeSenItem(fl) { + : ASTGEN_SUPER(fl) { m_edgeType = VEdgeType::ET_ILLEGAL; } AstSenItem(FileLine* fl, Initial) - : AstNodeSenItem(fl) { + : ASTGEN_SUPER(fl) { m_edgeType = VEdgeType::ET_INITIAL; } AstSenItem(FileLine* fl, Settle) - : AstNodeSenItem(fl) { + : ASTGEN_SUPER(fl) { m_edgeType = VEdgeType::ET_SETTLE; } AstSenItem(FileLine* fl, Never) - : AstNodeSenItem(fl) { + : ASTGEN_SUPER(fl) { m_edgeType = VEdgeType::ET_NEVER; } ASTNODE_NODE_FUNCS(SenItem) @@ -2530,7 +2549,8 @@ class AstSenGate : public AstNodeSenItem { // AND as applied to a sensitivity list and a gating expression // Performing this gating is optional; it may be removed by later optimizations public: - AstSenGate(FileLine* fl, AstSenItem* sensesp, AstNode* rhsp) : AstNodeSenItem(fl) { + AstSenGate(FileLine* fl, AstSenItem* sensesp, AstNode* rhsp) + : ASTGEN_SUPER(fl) { dtypeSetLogicBool(); addOp1p(sensesp); setOp2p(rhsp); } ASTNODE_NODE_FUNCS(SenGate) @@ -2555,7 +2575,7 @@ private: bool m_multi; // Created from combo logic by ORing multiple clock domains public: AstSenTree(FileLine* fl, AstNodeSenItem* sensesp) - : AstNode(fl), m_multi(false) { + : ASTGEN_SUPER(fl), m_multi(false) { addNOp1p(sensesp); } ASTNODE_NODE_FUNCS(SenTree) @@ -2577,7 +2597,7 @@ class AstAlways : public AstNode { VAlwaysKwd m_keyword; public: AstAlways(FileLine* fl, VAlwaysKwd keyword, AstSenTree* sensesp, AstNode* bodysp) - : AstNode(fl), m_keyword(keyword) { + : ASTGEN_SUPER(fl), m_keyword(keyword) { addNOp1p(sensesp); addNOp2p(bodysp); } ASTNODE_NODE_FUNCS(Always) @@ -2596,7 +2616,7 @@ class AstAlwaysPublic : public AstNodeStmt { // Body statements are just AstVarRefs to the public signals public: AstAlwaysPublic(FileLine* fl, AstSenTree* sensesp, AstNode* bodysp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(sensesp); addNOp2p(bodysp); } ASTNODE_NODE_FUNCS(AlwaysPublic) @@ -2614,7 +2634,7 @@ class AstAlwaysPost : public AstNode { // Like always but post assignments for memory assignment IFs public: AstAlwaysPost(FileLine* fl, AstSenTree* sensesp, AstNode* bodysp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(sensesp); addNOp2p(bodysp); } ASTNODE_NODE_FUNCS(AlwaysPost) @@ -2625,8 +2645,8 @@ public: class AstAssign : public AstNodeAssign { public: - AstAssign(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) { + AstAssign(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Assign) @@ -2638,8 +2658,8 @@ class AstAssignAlias : public AstNodeAssign { // Like AstAssignW, but a true bidirect interconnection alias // If both sides are wires, there's no LHS vs RHS, public: - AstAssignAlias(FileLine* fileline, AstVarRef* lhsp, AstVarRef* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) {} + AstAssignAlias(FileLine* fl, AstVarRef* lhsp, AstVarRef* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(AssignAlias) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { V3ERROR_NA; return NULL; } virtual bool brokeLhsMustBeLvalue() const { return false; } @@ -2647,8 +2667,8 @@ public: class AstAssignDly : public AstNodeAssign { public: - AstAssignDly(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) {} + AstAssignDly(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(AssignDly) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAssignDly(this->fileline(), lhsp, rhsp); } virtual bool isGateOptimizable() const { return false; } @@ -2659,8 +2679,8 @@ public: class AstAssignW : public AstNodeAssign { // Like assign, but wire/assign's in verilog, the only setting of the specified variable public: - AstAssignW(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) { } + AstAssignW(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { } ASTNODE_NODE_FUNCS(AssignW) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAssignW(this->fileline(), lhsp, rhsp); } virtual bool brokeLhsMustBeLvalue() const { return true; } @@ -2677,8 +2697,8 @@ public: class AstAssignVarScope : public AstNodeAssign { // Assign two VarScopes to each other public: - AstAssignVarScope(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) { + AstAssignVarScope(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(rhsp); } ASTNODE_NODE_FUNCS(AssignVarScope) @@ -2690,8 +2710,8 @@ class AstPull : public AstNode { private: bool m_direction; public: - AstPull(FileLine* fileline, AstNode* lhsp, bool direction) - : AstNode(fileline) { + AstPull(FileLine* fl, AstNode* lhsp, bool direction) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); m_direction = direction; } @@ -2706,8 +2726,8 @@ public: class AstAssignPre : public AstNodeAssign { // Like Assign, but predelayed assignment requiring special order handling public: - AstAssignPre(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) {} + AstAssignPre(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(AssignPre) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAssignPre(this->fileline(), lhsp, rhsp); } virtual bool brokeLhsMustBeLvalue() const { return true; } @@ -2716,8 +2736,8 @@ public: class AstAssignPost : public AstNodeAssign { // Like Assign, but predelayed assignment requiring special order handling public: - AstAssignPost(FileLine* fileline, AstNode* lhsp, AstNode* rhsp) - : AstNodeAssign(fileline, lhsp, rhsp) {} + AstAssignPost(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(AssignPost) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAssignPost(this->fileline(), lhsp, rhsp); } virtual bool brokeLhsMustBeLvalue() const { return true; } @@ -2732,7 +2752,7 @@ private: string m_name; // Text of comment public: AstComment(FileLine* fl, const string& name, bool showAt=false) - : AstNodeStmt(fl) + : ASTGEN_SUPER(fl) , m_showAt(showAt), m_name(name) {} ASTNODE_NODE_FUNCS(Comment) virtual string name() const { return m_name; } // * = Text @@ -2747,7 +2767,7 @@ class AstCond : public AstNodeCond { // Children: MATH public: AstCond(FileLine* fl, AstNode* condp, AstNode* expr1p, AstNode* expr2p) - : AstNodeCond(fl, condp, expr1p, expr2p) {} + : ASTGEN_SUPER(fl, condp, expr1p, expr2p) {} ASTNODE_NODE_FUNCS(Cond) virtual AstNode* cloneType(AstNode* condp, AstNode* expr1p, AstNode* expr2p) { return new AstCond(this->fileline(), condp, expr1p, expr2p); } @@ -2759,7 +2779,7 @@ class AstCondBound : public AstNodeCond { // Children: MATH public: AstCondBound(FileLine* fl, AstNode* condp, AstNode* expr1p, AstNode* expr2p) - : AstNodeCond(fl, condp, expr1p, expr2p) {} + : ASTGEN_SUPER(fl, condp, expr1p, expr2p) {} ASTNODE_NODE_FUNCS(CondBound) virtual AstNode* cloneType(AstNode* condp, AstNode* expr1p, AstNode* expr2p) { return new AstCondBound(this->fileline(), condp, expr1p, expr2p); } @@ -2778,7 +2798,7 @@ private: int m_binNum; // Set by V3EmitCSyms to tell final V3Emit what to increment public: AstCoverDecl(FileLine* fl, int column, const string& page, const string& comment) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { m_text = comment; m_page = page; m_column = column; m_binNum = 0; m_dataDeclp = NULL; @@ -2825,7 +2845,7 @@ private: AstCoverDecl* m_declp; // [After V3Coverage] Pointer to declaration public: AstCoverInc(FileLine* fl, AstCoverDecl* declp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { m_declp = declp; } ASTNODE_NODE_FUNCS(CoverInc) @@ -2849,7 +2869,7 @@ class AstCoverToggle : public AstNodeStmt { // Children: AstCoverInc, orig var, change det var public: AstCoverToggle(FileLine* fl, AstCoverInc* incp, AstNode* origp, AstNode* changep) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { setOp1p(incp); setOp2p(origp); setOp3p(changep); @@ -2874,8 +2894,8 @@ class AstGenCase : public AstNodeCase { // exprp Children: MATHs // casesp Children: CASEITEMs public: - AstGenCase(FileLine* fileline, AstNode* exprp, AstNode* casesp) - : AstNodeCase(fileline, exprp, casesp) { + AstGenCase(FileLine* fl, AstNode* exprp, AstNode* casesp) + : ASTGEN_SUPER(fl, exprp, casesp) { } ASTNODE_NODE_FUNCS(GenCase) }; @@ -2893,8 +2913,8 @@ private: bool m_unique0Pragma; // unique0 case bool m_priorityPragma; // priority case public: - AstCase(FileLine* fileline, VCaseType casex, AstNode* exprp, AstNode* casesp) - : AstNodeCase(fileline, exprp, casesp) { + AstCase(FileLine* fl, VCaseType casex, AstNode* exprp, AstNode* casesp) + : ASTGEN_SUPER(fl, exprp, casesp) { m_casex = casex; m_fullPragma = false; m_parallelPragma = false; m_uniquePragma = false; m_unique0Pragma = false; m_priorityPragma = false; @@ -2928,8 +2948,8 @@ class AstCaseItem : public AstNode { private: bool m_ignoreOverlap; // Default created by assertions; ignore overlaps public: - AstCaseItem(FileLine* fileline, AstNode* condsp, AstNode* bodysp) - : AstNode(fileline) { + AstCaseItem(FileLine* fl, AstNode* condsp, AstNode* bodysp) + : ASTGEN_SUPER(fl) { addNOp1p(condsp); addNOp2p(bodysp); m_ignoreOverlap = false; } @@ -2953,11 +2973,11 @@ class AstSFormatF : public AstNode { public: class NoFormat {}; AstSFormatF(FileLine* fl, const string& text, bool hidden, AstNode* exprsp) - : AstNode(fl), m_text(text), m_hidden(hidden), m_hasFormat(true) { + : ASTGEN_SUPER(fl), m_text(text), m_hidden(hidden), m_hasFormat(true) { dtypeSetString(); addNOp1p(exprsp); addNOp2p(NULL); } AstSFormatF(FileLine* fl, NoFormat, AstNode* exprsp) - : AstNode(fl), m_text(""), m_hidden(true), m_hasFormat(false) { + : ASTGEN_SUPER(fl), m_text(""), m_hidden(true), m_hasFormat(false) { dtypeSetString(); addNOp1p(exprsp); addNOp2p(NULL); } ASTNODE_NODE_FUNCS(SFormatF) @@ -2988,15 +3008,16 @@ class AstDisplay : public AstNodeStmt { private: AstDisplayType m_displayType; public: - AstDisplay(FileLine* fileline, AstDisplayType dispType, const string& text, AstNode* filep, AstNode* exprsp) - : AstNodeStmt(fileline) { - setOp1p(new AstSFormatF(fileline, text, true, exprsp)); + AstDisplay(FileLine* fl, AstDisplayType dispType, const string& text, AstNode* filep, + AstNode* exprsp) + : ASTGEN_SUPER(fl) { + setOp1p(new AstSFormatF(fl, text, true, exprsp)); setNOp3p(filep); m_displayType = dispType; } - AstDisplay(FileLine* fileline, AstDisplayType dispType, AstNode* filep, AstNode* exprsp) - : AstNodeStmt(fileline) { - setOp1p(new AstSFormatF(fileline, AstSFormatF::NoFormat(), exprsp)); + AstDisplay(FileLine* fl, AstDisplayType dispType, AstNode* filep, AstNode* exprsp) + : ASTGEN_SUPER(fl) { + setOp1p(new AstSFormatF(fl, AstSFormatF::NoFormat(), exprsp)); setNOp3p(filep); m_displayType = dispType; } @@ -3029,9 +3050,9 @@ class AstElabDisplay : public AstNode { private: AstDisplayType m_displayType; public: - AstElabDisplay(FileLine* fileline, AstDisplayType dispType, AstNode* exprsp) - : AstNode(fileline) { - setOp1p(new AstSFormatF(fileline, AstSFormatF::NoFormat(), exprsp)); + AstElabDisplay(FileLine* fl, AstDisplayType dispType, AstNode* exprsp) + : ASTGEN_SUPER(fl) { + setOp1p(new AstSFormatF(fl, AstSFormatF::NoFormat(), exprsp)); m_displayType = dispType; } ASTNODE_NODE_FUNCS(ElabDisplay) @@ -3057,9 +3078,9 @@ class AstSFormat : public AstNodeStmt { // Children: string to load // Children: SFORMATF to generate print string public: - AstSFormat(FileLine* fileline, AstNode* lhsp, const string& text, AstNode* exprsp) - : AstNodeStmt(fileline) { - setOp1p(new AstSFormatF(fileline, text, true, exprsp)); + AstSFormat(FileLine* fl, AstNode* lhsp, const string& text, AstNode* exprsp) + : ASTGEN_SUPER(fl) { + setOp1p(new AstSFormatF(fl, text, true, exprsp)); setOp3p(lhsp); } ASTNODE_NODE_FUNCS(SFormat) @@ -3086,8 +3107,8 @@ class AstSysFuncAsTask : public AstNodeStmt { // Parents: stmtlist // Children: a system function public: - AstSysFuncAsTask(FileLine* fileline, AstNode* exprsp) - : AstNodeStmt(fileline) { addNOp1p(exprsp); } + AstSysFuncAsTask(FileLine* fl, AstNode* exprsp) + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(SysFuncAsTask) virtual string verilogKwd() const { return ""; } virtual bool isGateOptimizable() const { return true; } @@ -3105,8 +3126,8 @@ class AstSysIgnore : public AstNodeStmt { // Parents: stmtlist // Children: varrefs or exprs public: - AstSysIgnore(FileLine* fileline, AstNode* exprsp) - : AstNodeStmt(fileline) { addNOp1p(exprsp); } + AstSysIgnore(FileLine* fl, AstNode* exprsp) + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(SysIgnore) virtual string verilogKwd() const { return "$ignored"; } virtual bool isGateOptimizable() const { return false; } // Though deleted before opt @@ -3122,8 +3143,8 @@ class AstFClose : public AstNodeStmt { // Parents: stmtlist // Children: file which must be a varref public: - AstFClose(FileLine* fileline, AstNode* filep) - : AstNodeStmt(fileline) { + AstFClose(FileLine* fl, AstNode* filep) + : ASTGEN_SUPER(fl) { setNOp2p(filep); } ASTNODE_NODE_FUNCS(FClose) @@ -3142,8 +3163,8 @@ public: class AstFOpen : public AstNodeStmt { // Although a system function in IEEE, here a statement which sets the file pointer (MCD) public: - AstFOpen(FileLine* fileline, AstNode* filep, AstNode* filenamep, AstNode* modep) - : AstNodeStmt(fileline) { + AstFOpen(FileLine* fl, AstNode* filep, AstNode* filenamep, AstNode* modep) + : ASTGEN_SUPER(fl) { setOp1p(filep); setOp2p(filenamep); setOp3p(modep); @@ -3166,8 +3187,8 @@ class AstFFlush : public AstNodeStmt { // Parents: stmtlist // Children: file which must be a varref public: - AstFFlush(FileLine* fileline, AstNode* filep) - : AstNodeStmt(fileline) { + AstFFlush(FileLine* fl, AstNode* filep) + : ASTGEN_SUPER(fl) { setNOp2p(filep); } ASTNODE_NODE_FUNCS(FFlush) @@ -3190,9 +3211,9 @@ class AstFRead : public AstNodeMath { // Children: low index // Children: count public: - AstFRead(FileLine* fileline, AstNode* memp, AstNode* filep, + AstFRead(FileLine* fl, AstNode* memp, AstNode* filep, AstNode* startp, AstNode* countp) - : AstNodeMath(fileline) { + : ASTGEN_SUPER(fl) { setOp1p(memp); setOp2p(filep); setNOp3p(startp); @@ -3223,8 +3244,8 @@ class AstFRewind : public AstNodeMath { // Parents: stmtlist // Children: file which must be a varref public: - AstFRewind(FileLine* fileline, AstNode* filep) - : AstNodeMath(fileline) { + AstFRewind(FileLine* fl, AstNode* filep) + : ASTGEN_SUPER(fl) { setNOp2p(filep); } ASTNODE_NODE_FUNCS(FRewind) @@ -3247,8 +3268,8 @@ class AstFTell : public AstNodeMath { // Parents: stmtlist // Children: file which must be a varref public: - AstFTell(FileLine* fileline, AstNode* filep) - : AstNodeMath(fileline) { + AstFTell(FileLine* fl, AstNode* filep) + : ASTGEN_SUPER(fl) { setNOp2p(filep); } ASTNODE_NODE_FUNCS(FTell) @@ -3273,9 +3294,9 @@ class AstFSeek : public AstNodeMath { // Children: offset // Children: operation public: - AstFSeek(FileLine* fileline, AstNode* filep, + AstFSeek(FileLine* fl, AstNode* filep, AstNode* offset, AstNode* operation) - : AstNodeMath(fileline) { + : ASTGEN_SUPER(fl) { setOp2p(filep); setNOp3p(offset); setNOp4p(operation); @@ -3306,8 +3327,8 @@ class AstFScanF : public AstNodeMath { private: string m_text; public: - AstFScanF(FileLine* fileline, const string& text, AstNode* filep, AstNode* exprsp) - : AstNodeMath(fileline), m_text(text) { + AstFScanF(FileLine* fl, const string& text, AstNode* filep, AstNode* exprsp) + : ASTGEN_SUPER(fl), m_text(text) { addNOp1p(exprsp); setNOp2p(filep); } @@ -3339,8 +3360,8 @@ class AstSScanF : public AstNodeMath { private: string m_text; public: - AstSScanF(FileLine* fileline, const string& text, AstNode* fromp, AstNode* exprsp) - : AstNodeMath(fileline), m_text(text) { + AstSScanF(FileLine* fl, const string& text, AstNode* fromp, AstNode* exprsp) + : ASTGEN_SUPER(fl), m_text(text) { addNOp1p(exprsp); setOp2p(fromp); } @@ -3369,10 +3390,10 @@ class AstNodeReadWriteMem : public AstNodeStmt { private: bool m_isHex; // readmemh, not readmemb public: - AstNodeReadWriteMem(FileLine* fileline, bool hex, + AstNodeReadWriteMem(AstType t, FileLine* fl, bool hex, AstNode* filenamep, AstNode* memp, AstNode* lsbp, AstNode* msbp) - : AstNodeStmt(fileline), m_isHex(hex) { + : AstNodeStmt(t, fl), m_isHex(hex) { setOp1p(filenamep); setOp2p(memp); setNOp3p(lsbp); setNOp4p(msbp); } virtual bool isGateOptimizable() const { return false; } @@ -3394,20 +3415,19 @@ public: class AstReadMem : public AstNodeReadWriteMem { public: - AstReadMem(FileLine* fileline, bool hex, - AstNode* filenamep, AstNode* memp, AstNode* lsbp, AstNode* msbp) - : AstNodeReadWriteMem(fileline, hex, filenamep, memp, lsbp, msbp) - { } + AstReadMem(FileLine* fl, bool hex, AstNode* filenamep, AstNode* memp, AstNode* lsbp, + AstNode* msbp) + : ASTGEN_SUPER(fl, hex, filenamep, memp, lsbp, msbp) {} ASTNODE_NODE_FUNCS(ReadMem); - virtual string verilogKwd() const { return (isHex()?"$readmemh":"$readmemb"); } + virtual string verilogKwd() const { return (isHex() ? "$readmemh" : "$readmemb"); } virtual const char* cFuncPrefixp() const { return "VL_READMEM_"; } }; class AstWriteMem : public AstNodeReadWriteMem { public: - AstWriteMem(FileLine* fileline, + AstWriteMem(FileLine* fl, AstNode* filenamep, AstNode* memp, AstNode* lsbp, AstNode* msbp) - : AstNodeReadWriteMem(fileline, true, filenamep, memp, lsbp, msbp) { } + : ASTGEN_SUPER(fl, true, filenamep, memp, lsbp, msbp) { } ASTNODE_NODE_FUNCS(WriteMem) virtual string verilogKwd() const { return (isHex()?"$writememh":"$writememb"); } virtual const char* cFuncPrefixp() const { return "VL_WRITEMEM_"; } @@ -3416,8 +3436,8 @@ public: class AstSystemT : public AstNodeStmt { // $system used as task public: - AstSystemT(FileLine* fileline, AstNode* lhsp) - : AstNodeStmt(fileline) { + AstSystemT(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); } ASTNODE_NODE_FUNCS(SystemT) @@ -3435,8 +3455,8 @@ public: class AstSystemF : public AstNodeMath { // $system used as function public: - AstSystemF(FileLine* fileline, AstNode* lhsp) - : AstNodeMath(fileline) { + AstSystemF(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); } ASTNODE_NODE_FUNCS(SystemF) @@ -3458,8 +3478,8 @@ class AstValuePlusArgs : public AstNodeMath { // Parents: expr // Child: variable to set. If NULL then this is a $test$plusargs instead of $value$plusargs public: - AstValuePlusArgs(FileLine* fileline, AstNode* searchp, AstNode* outp) - : AstNodeMath(fileline) { + AstValuePlusArgs(FileLine* fl, AstNode* searchp, AstNode* outp) + : ASTGEN_SUPER(fl) { setOp1p(searchp); setOp2p(outp); } ASTNODE_NODE_FUNCS(ValuePlusArgs) @@ -3483,8 +3503,9 @@ class AstTestPlusArgs : public AstNodeMath { private: string m_text; public: - AstTestPlusArgs(FileLine* fileline, const string& text) - : AstNodeMath(fileline), m_text(text) { } + AstTestPlusArgs(FileLine* fl, const string& text) + : ASTGEN_SUPER(fl) + , m_text(text) {} ASTNODE_NODE_FUNCS(TestPlusArgs) virtual string name() const { return m_text; } virtual string verilogKwd() const { return "$test$plusargs"; } @@ -3502,18 +3523,15 @@ public: class AstGenFor : public AstNodeFor { public: - AstGenFor(FileLine* fileline, AstNode* initsp, AstNode* condp, - AstNode* incsp, AstNode* bodysp) - : AstNodeFor(fileline, initsp, condp, incsp, bodysp) { - } + AstGenFor(FileLine* fl, AstNode* initsp, AstNode* condp, AstNode* incsp, AstNode* bodysp) + : ASTGEN_SUPER(fl, initsp, condp, incsp, bodysp) {} ASTNODE_NODE_FUNCS(GenFor) }; class AstForeach : public AstNodeStmt { public: - AstForeach(FileLine* fileline, AstNode* arrayp, AstNode* varsp, - AstNode* bodysp) - : AstNodeStmt(fileline) { + AstForeach(FileLine* fl, AstNode* arrayp, AstNode* varsp, AstNode* bodysp) + : ASTGEN_SUPER(fl) { setOp1p(arrayp); addNOp2p(varsp); addNOp4p(bodysp); } ASTNODE_NODE_FUNCS(Foreach) @@ -3528,8 +3546,8 @@ public: class AstRepeat : public AstNodeStmt { public: - AstRepeat(FileLine* fileline, AstNode* countp, AstNode* bodysp) - : AstNodeStmt(fileline) { + AstRepeat(FileLine* fl, AstNode* countp, AstNode* bodysp) + : ASTGEN_SUPER(fl) { setOp2p(countp); addNOp3p(bodysp); } ASTNODE_NODE_FUNCS(Repeat) @@ -3543,8 +3561,8 @@ public: class AstWhile : public AstNodeStmt { public: - AstWhile(FileLine* fileline, AstNode* condp, AstNode* bodysp, AstNode* incsp=NULL) - : AstNodeStmt(fileline) { + AstWhile(FileLine* fl, AstNode* condp, AstNode* bodysp, AstNode* incsp=NULL) + : ASTGEN_SUPER(fl) { setOp2p(condp); addNOp3p(bodysp); addNOp4p(incsp); } ASTNODE_NODE_FUNCS(While) @@ -3565,8 +3583,8 @@ public: class AstBreak : public AstNodeStmt { public: - explicit AstBreak(FileLine* fileline) - : AstNodeStmt(fileline) {} + explicit AstBreak(FileLine* fl) + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(Break) virtual string verilogKwd() const { return "break"; } virtual V3Hash sameHash() const { return V3Hash(); } @@ -3575,8 +3593,8 @@ public: class AstContinue : public AstNodeStmt { public: - explicit AstContinue(FileLine* fileline) - : AstNodeStmt(fileline) {} + explicit AstContinue(FileLine* fl) + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(Continue) virtual string verilogKwd() const { return "continue"; } virtual V3Hash sameHash() const { return V3Hash(); } @@ -3587,8 +3605,8 @@ class AstDisable : public AstNodeStmt { private: string m_name; // Name of block public: - AstDisable(FileLine* fileline, const string& name) - : AstNodeStmt(fileline), m_name(name) {} + AstDisable(FileLine* fl, const string& name) + : ASTGEN_SUPER(fl), m_name(name) {} ASTNODE_NODE_FUNCS(Disable) virtual string name() const { return m_name; } // * = Block name void name(const string& flag) { m_name = flag; } @@ -3597,8 +3615,8 @@ public: class AstReturn : public AstNodeStmt { public: - AstReturn(FileLine* fileline, AstNode* lhsp=NULL) - : AstNodeStmt(fileline) { + AstReturn(FileLine* fl, AstNode* lhsp = NULL) + : ASTGEN_SUPER(fl) { setNOp1p(lhsp); } ASTNODE_NODE_FUNCS(Return) @@ -3610,9 +3628,8 @@ public: class AstGenIf : public AstNodeIf { public: - AstGenIf(FileLine* fileline, AstNode* condp, AstNode* ifsp, AstNode* elsesp) - : AstNodeIf(fileline, condp, ifsp, elsesp) { - } + AstGenIf(FileLine* fl, AstNode* condp, AstNode* ifsp, AstNode* elsesp) + : ASTGEN_SUPER(fl, condp, ifsp, elsesp) {} ASTNODE_NODE_FUNCS(GenIf) }; @@ -3622,8 +3639,8 @@ private: bool m_unique0Pragma; // unique0 case bool m_priorityPragma; // priority case public: - AstIf(FileLine* fileline, AstNode* condp, AstNode* ifsp, AstNode* elsesp=NULL) - : AstNodeIf(fileline, condp, ifsp, elsesp) { + AstIf(FileLine* fl, AstNode* condp, AstNode* ifsp, AstNode* elsesp=NULL) + : ASTGEN_SUPER(fl, condp, ifsp, elsesp) { m_uniquePragma = false; m_unique0Pragma = false; m_priorityPragma = false; } ASTNODE_NODE_FUNCS(If) @@ -3644,7 +3661,7 @@ private: int m_labelNum; // Set by V3EmitCSyms to tell final V3Emit what to increment public: AstJumpLabel(FileLine* fl, AstNode* stmtsp) - : AstNodeStmt(fl), m_labelNum(0) { + : ASTGEN_SUPER(fl), m_labelNum(0) { addNOp1p(stmtsp); } virtual int instrCount() const { return 0; } @@ -3666,7 +3683,7 @@ private: AstJumpLabel* m_labelp; // [After V3Jump] Pointer to declaration public: AstJumpGo(FileLine* fl, AstJumpLabel* labelp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { m_labelp = labelp; } ASTNODE_NODE_FUNCS(JumpGo) @@ -3689,7 +3706,7 @@ class AstChangeXor : public AstNodeBiComAsv { // Children: VARREF public: AstChangeXor(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeBiComAsv(fl, lhsp, rhsp) { + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetUInt32(); // Always used on, and returns word entities } ASTNODE_NODE_FUNCS(ChangeXor) @@ -3713,7 +3730,7 @@ private: public: // Null lhs+rhs used to indicate change needed with no spec vars AstChangeDet(FileLine* fl, AstNode* lhsp, AstNode* rhsp, bool clockReq) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { setNOp1p(lhsp); setNOp2p(rhsp); m_clockReq = clockReq; } ASTNODE_NODE_FUNCS(ChangeDet) @@ -3737,8 +3754,8 @@ private: bool m_generate; // Underneath a generate public: // Node that simply puts name into the output stream - AstBegin(FileLine* fileline, const string& name, AstNode* stmtsp, bool generate=false) - : AstNode(fileline) + AstBegin(FileLine* fl, const string& name, AstNode* stmtsp, bool generate=false) + : ASTGEN_SUPER(fl) , m_name(name) { addNOp1p(stmtsp); m_unnamed = (name==""); @@ -3762,7 +3779,7 @@ public: class AstInitial : public AstNode { public: AstInitial(FileLine* fl, AstNode* bodysp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(bodysp); } ASTNODE_NODE_FUNCS(Initial) @@ -3774,7 +3791,7 @@ public: class AstFinal : public AstNode { public: AstFinal(FileLine* fl, AstNode* bodysp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(bodysp); } ASTNODE_NODE_FUNCS(Final) @@ -3784,7 +3801,7 @@ public: class AstInside : public AstNodeMath { public: AstInside(FileLine* fl, AstNode* exprp, AstNode* itemsp) - : AstNodeMath(fl) { + : ASTGEN_SUPER(fl) { addOp1p(exprp); addOp2p(itemsp); dtypeSetLogicBool(); } @@ -3799,7 +3816,7 @@ public: class AstInsideRange : public AstNodeMath { public: AstInsideRange(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeMath(fl) { + : ASTGEN_SUPER(fl) { addOp1p(lhsp); addOp2p(rhsp); } ASTNODE_NODE_FUNCS(InsideRange) @@ -3817,7 +3834,7 @@ class AstInitItem : public AstNode { public: // Parents: INITARRAY AstInitItem(FileLine* fl, AstNode* valuep) - : AstNode(fl) { addOp1p(valuep); } + : ASTGEN_SUPER(fl) { addOp1p(valuep); } ASTNODE_NODE_FUNCS(InitItem) virtual bool maybePointedTo() const { return true; } virtual bool hasDType() const { return false; } // See valuep()'s dtype instead @@ -3839,7 +3856,7 @@ private: KeyItemMap m_map; // Node value for each array index public: AstInitArray(FileLine* fl, AstNodeArrayDType* newDTypep, AstNode* defaultp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { dtypep(newDTypep); addNOp1p(defaultp); } @@ -3900,7 +3917,7 @@ class AstNew : public AstNodeMath { // Children: varref|arraysel, math public: AstNew(FileLine* fl) - : AstNodeMath(fl) { + : ASTGEN_SUPER(fl) { dtypep(NULL); // V3Width will resolve } ASTNODE_NODE_FUNCS(New) @@ -3921,7 +3938,7 @@ public: // Pragmas don't result in any output code, they're just flags that affect // other processing in verilator. AstPragma(FileLine* fl, AstPragmaType pragType) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { m_pragType = pragType; } ASTNODE_NODE_FUNCS(Pragma) @@ -3934,8 +3951,8 @@ public: class AstStop : public AstNodeStmt { public: - explicit AstStop(FileLine* fl, bool maybe) - : AstNodeStmt(fl) {} + AstStop(FileLine* fl, bool maybe) + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(Stop) virtual bool isGateOptimizable() const { return false; } virtual bool isPredictOptimizable() const { return false; } @@ -3951,7 +3968,7 @@ public: class AstFinish : public AstNodeStmt { public: explicit AstFinish(FileLine* fl) - : AstNodeStmt(fl) {} + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(Finish) virtual bool isGateOptimizable() const { return false; } virtual bool isPredictOptimizable() const { return false; } @@ -3985,7 +4002,7 @@ public: AstNode* valuep, const VNumRange& bitRange, const VNumRange& arrayRange, bool isScoped) - : AstNodeStmt(fl) + : ASTGEN_SUPER(fl) , m_showname(showname), m_bitRange(bitRange), m_arrayRange(arrayRange) , m_isScoped(isScoped) { dtypeFrom(valuep); @@ -4024,7 +4041,7 @@ private: AstTraceDecl* m_declp; // [After V3Trace] Pointer to declaration public: AstTraceInc(FileLine* fl, AstTraceDecl* declp, AstNode* valuep) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { dtypeFrom(declp); m_declp = declp; addNOp2p(valuep); @@ -4058,8 +4075,8 @@ private: string m_name; AstSenTree* m_sensesp; public: - AstActive(FileLine* fileline, const string& name, AstSenTree* sensesp) - : AstNode(fileline) { + AstActive(FileLine* fl, const string& name, AstSenTree* sensesp) + : ASTGEN_SUPER(fl) { m_name = name; // Copy it UASSERT(sensesp, "Sensesp required arg"); m_sensesp = sensesp; @@ -4095,7 +4112,7 @@ private: AstAttrType m_attrType; // What sort of extraction public: AstAttrOf(FileLine* fl, AstAttrType attrtype, AstNode* fromp=NULL, AstNode* dimp=NULL) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { setNOp1p(fromp); setNOp2p(dimp); m_attrType = attrtype; } @@ -4116,8 +4133,11 @@ private: string scopeNameFormatter(AstText* scopeTextp) const; string scopePrettyNameFormatter(AstText* scopeTextp) const; public: - explicit AstScopeName(FileLine* fl) : AstNodeMath(fl), m_dpiExport(false) { - dtypeSetUInt64(); } + explicit AstScopeName(FileLine* fl) + : ASTGEN_SUPER(fl) + , m_dpiExport(false) { + dtypeSetUInt64(); + } ASTNODE_NODE_FUNCS(ScopeName) virtual V3Hash sameHash() const { return V3Hash(); } virtual bool same(const AstNode* samep) const { @@ -4144,7 +4164,7 @@ public: class AstUdpTable : public AstNode { public: AstUdpTable(FileLine* fl, AstNode* bodysp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(bodysp); } ASTNODE_NODE_FUNCS(UdpTable) @@ -4155,7 +4175,8 @@ class AstUdpTableLine : public AstNode { string m_text; public: AstUdpTableLine(FileLine* fl, const string& text) - : AstNode(fl), m_text(text) {} + : ASTGEN_SUPER(fl) + , m_text(text) {} ASTNODE_NODE_FUNCS(UdpTableLine) virtual string name() const { return m_text; } string text() const { return m_text; } @@ -4169,9 +4190,11 @@ class AstRand : public AstNodeTermop { private: bool m_reset; // Random reset, versus always random public: - AstRand(FileLine* fl, AstNodeDType* dtp, bool reset) : AstNodeTermop(fl) { - dtypep(dtp); m_reset = reset; } - explicit AstRand(FileLine* fl) : AstNodeTermop(fl), m_reset(false) { } + AstRand(FileLine* fl, AstNodeDType* dtp, bool reset) + : ASTGEN_SUPER(fl) { dtypep(dtp); m_reset = reset; } + explicit AstRand(FileLine* fl) + : ASTGEN_SUPER(fl) + , m_reset(false) {} ASTNODE_NODE_FUNCS(Rand) virtual string emitVerilog() { return "%f$random"; } virtual string emitC() { @@ -4188,8 +4211,8 @@ public: class AstTime : public AstNodeTermop { public: - explicit AstTime(FileLine* fl) : AstNodeTermop(fl) { - dtypeSetUInt64(); } + explicit AstTime(FileLine* fl) + : ASTGEN_SUPER(fl) { dtypeSetUInt64(); } ASTNODE_NODE_FUNCS(Time) virtual string emitVerilog() { return "%f$time"; } virtual string emitC() { return "VL_TIME_%nq()"; } @@ -4203,8 +4226,8 @@ public: class AstTimeD : public AstNodeTermop { public: - explicit AstTimeD(FileLine* fl) : AstNodeTermop(fl) { - dtypeSetDouble(); } + explicit AstTimeD(FileLine* fl) + : ASTGEN_SUPER(fl) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(TimeD) virtual string emitVerilog() { return "%f$realtime"; } virtual string emitC() { return "VL_TIME_D()"; } @@ -4221,7 +4244,7 @@ class AstUCFunc : public AstNodeMath { // Perhaps this should be an AstNodeListop; but there's only one list math right now public: AstUCFunc(FileLine* fl, AstNode* exprsp) - : AstNodeMath(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(UCFunc) @@ -4244,8 +4267,8 @@ public: class AstNegate : public AstNodeUniop { public: - AstNegate(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeFrom(lhsp); } + AstNegate(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Negate) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opNegate(lhs); } virtual string emitVerilog() { return "%f(- %l)"; } @@ -4256,8 +4279,8 @@ public: }; class AstNegateD : public AstNodeUniop { public: - AstNegateD(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetDouble(); } + AstNegateD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(NegateD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opNegateD(lhs); } virtual string emitVerilog() { return "%f(- %l)"; } @@ -4271,8 +4294,8 @@ public: }; class AstRedAnd : public AstNodeUniop { public: - AstRedAnd(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstRedAnd(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(RedAnd) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRedAnd(lhs); } virtual string emitVerilog() { return "%f(& %l)"; } @@ -4283,8 +4306,8 @@ public: }; class AstRedOr : public AstNodeUniop { public: - AstRedOr(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstRedOr(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(RedOr) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRedOr(lhs); } virtual string emitVerilog() { return "%f(| %l)"; } @@ -4295,8 +4318,8 @@ public: }; class AstRedXor : public AstNodeUniop { public: - AstRedXor(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstRedXor(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(RedXor) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRedXor(lhs); } virtual string emitVerilog() { return "%f(^ %l)"; } @@ -4310,8 +4333,8 @@ public: class AstRedXnor : public AstNodeUniop { // AstRedXnors are replaced with AstRedXors in V3Const. public: - AstRedXnor(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstRedXnor(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(RedXnor) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRedXnor(lhs); } virtual string emitVerilog() { return "%f(~^ %l)"; } @@ -4325,8 +4348,8 @@ public: class AstLenN : public AstNodeUniop { // Length of a string public: - AstLenN(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetSigned32(); } + AstLenN(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetSigned32(); } ASTNODE_NODE_FUNCS(LenN) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opLenN(lhs); } virtual string emitVerilog() { return "%f(%l)"; } @@ -4337,8 +4360,8 @@ public: }; class AstLogNot : public AstNodeUniop { public: - AstLogNot(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstLogNot(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LogNot) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opLogNot(lhs); } virtual string emitVerilog() { return "%f(! %l)"; } @@ -4350,8 +4373,8 @@ public: }; class AstNot : public AstNodeUniop { public: - AstNot(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeFrom(lhsp); } + AstNot(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Not) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opNot(lhs); } virtual string emitVerilog() { return "%f(~ %l)"; } @@ -4364,9 +4387,10 @@ public: class AstExtend : public AstNodeUniop { // Expand a value into a wider entity by 0 extension. Width is implied from nodep->width() public: - AstExtend(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} - AstExtend(FileLine* fl, AstNode* lhsp, int width) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicSized(width, AstNumeric::UNSIGNED); } + AstExtend(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} + AstExtend(FileLine* fl, AstNode* lhsp, int width) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicSized(width, AstNumeric::UNSIGNED); } ASTNODE_NODE_FUNCS(Extend) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opAssign(lhs); } virtual string emitVerilog() { return "%l"; } @@ -4379,10 +4403,11 @@ public: class AstExtendS : public AstNodeUniop { // Expand a value into a wider entity by sign extension. Width is implied from nodep->width() public: - AstExtendS(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} - AstExtendS(FileLine* fl, AstNode* lhsp, int width) : AstNodeUniop(fl, lhsp) { + AstExtendS(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} + AstExtendS(FileLine* fl, AstNode* lhsp, int width) // Important that widthMin be correct, as opExtend requires it after V3Expand - dtypeSetLogicSized(width, AstNumeric::UNSIGNED); } + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicSized(width, AstNumeric::UNSIGNED); } ASTNODE_NODE_FUNCS(ExtendS) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opExtendS(lhs, lhsp()->widthMinV()); @@ -4398,7 +4423,8 @@ public: class AstSigned : public AstNodeUniop { // $signed(lhs) public: - AstSigned(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { + AstSigned(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { UASSERT_OBJ(!v3Global.assertDTypesResolved(), this, "not coded to create after dtypes resolved"); } ASTNODE_NODE_FUNCS(Signed) @@ -4413,7 +4439,8 @@ public: class AstUnsigned : public AstNodeUniop { // $unsigned(lhs) public: - AstUnsigned(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { + AstUnsigned(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { UASSERT_OBJ(!v3Global.assertDTypesResolved(), this, "not coded to create after dtypes resolved"); } ASTNODE_NODE_FUNCS(Unsigned) @@ -4428,8 +4455,8 @@ public: class AstRToIS : public AstNodeUniop { // $rtoi(lhs) public: - AstRToIS(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetSigned32(); } + AstRToIS(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetSigned32(); } ASTNODE_NODE_FUNCS(RToIS) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRToIS(lhs); } virtual string emitVerilog() { return "%f$rtoi(%l)"; } @@ -4441,8 +4468,8 @@ public: }; class AstRToIRoundS : public AstNodeUniop { public: - AstRToIRoundS(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetSigned32(); } + AstRToIRoundS(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetSigned32(); } ASTNODE_NODE_FUNCS(RToIRoundS) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRToIRoundS(lhs); } virtual string emitVerilog() { return "%f$rtoi_rounded(%l)"; } @@ -4454,8 +4481,8 @@ public: }; class AstIToRD : public AstNodeUniop { public: - AstIToRD(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetDouble(); } + AstIToRD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(IToRD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opIToRD(lhs); } virtual string emitVerilog() { return "%f$itor(%l)"; } @@ -4467,8 +4494,8 @@ public: }; class AstRealToBits : public AstNodeUniop { public: - AstRealToBits(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetUInt64(); } + AstRealToBits(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetUInt64(); } ASTNODE_NODE_FUNCS(RealToBits) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opRealToBits(lhs); } virtual string emitVerilog() { return "%f$realtobits(%l)"; } @@ -4480,8 +4507,8 @@ public: }; class AstBitsToRealD : public AstNodeUniop { public: - AstBitsToRealD(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetDouble(); } + AstBitsToRealD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(BitsToRealD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opBitsToRealD(lhs); } virtual string emitVerilog() { return "%f$bitstoreal(%l)"; } @@ -4494,7 +4521,8 @@ public: class AstCLog2 : public AstNodeUniop { public: - AstCLog2(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} + AstCLog2(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(CLog2) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opCLog2(lhs); } virtual string emitVerilog() { return "%f$clog2(%l)"; } @@ -4507,7 +4535,8 @@ public: class AstCountOnes : public AstNodeUniop { // Number of bits set in vector public: - AstCountOnes(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} + AstCountOnes(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(CountOnes) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opCountOnes(lhs); } virtual string emitVerilog() { return "%f$countones(%l)"; } @@ -4520,8 +4549,8 @@ public: class AstIsUnknown : public AstNodeUniop { // True if any unknown bits public: - AstIsUnknown(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstIsUnknown(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(IsUnknown) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opIsUnknown(lhs); } virtual string emitVerilog() { return "%f$isunknown(%l)"; } @@ -4533,8 +4562,8 @@ public: class AstOneHot : public AstNodeUniop { // True if only single bit set in vector public: - AstOneHot(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstOneHot(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(OneHot) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opOneHot(lhs); } virtual string emitVerilog() { return "%f$onehot(%l)"; } @@ -4547,8 +4576,8 @@ public: class AstOneHot0 : public AstNodeUniop { // True if only single bit, or no bits set in vector public: - AstOneHot0(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetLogicBool(); } + AstOneHot0(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(OneHot0) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opOneHot0(lhs); } virtual string emitVerilog() { return "%f$onehot0(%l)"; } @@ -4562,7 +4591,8 @@ public: class AstCast : public AstNode { // Cast to appropriate data type - note lhsp is value, to match AstTypedef, AstCCast, etc public: - AstCast(FileLine* fl, AstNode* lhsp, AstNodeDType* dtp) : AstNode(fl) { + AstCast(FileLine* fl, AstNode* lhsp, AstNodeDType* dtp) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); setOp2p(dtp); dtypeFrom(dtp); } @@ -4581,7 +4611,8 @@ public: class AstCastParse : public AstNode { // Cast to appropriate type, where we haven't determined yet what the data type is public: - AstCastParse(FileLine* fl, AstNode* lhsp, AstNode* dtp) : AstNode(fl) { + AstCastParse(FileLine* fl, AstNode* lhsp, AstNode* dtp) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); setOp2p(dtp); } ASTNODE_NODE_FUNCS(CastParse) @@ -4597,7 +4628,8 @@ public: class AstCastSize : public AstNode { // Cast to specific size; signed/twostate inherited from lower element per IEEE public: - AstCastSize(FileLine* fl, AstNode* lhsp, AstConst* rhsp) : AstNode(fl) { + AstCastSize(FileLine* fl, AstNode* lhsp, AstConst* rhsp) + : ASTGEN_SUPER(fl) { setOp1p(lhsp); setOp2p(rhsp); } ASTNODE_NODE_FUNCS(CastSize) @@ -4616,14 +4648,16 @@ class AstCCast : public AstNodeUniop { private: int m_size; public: - AstCCast(FileLine* fl, AstNode* lhsp, int setwidth, int minwidth=-1) : AstNodeUniop(fl, lhsp) { + AstCCast(FileLine* fl, AstNode* lhsp, int setwidth, int minwidth=-1) + : ASTGEN_SUPER(fl, lhsp) { m_size = setwidth; if (setwidth) { if (minwidth==-1) minwidth = setwidth; dtypeSetLogicUnsized(setwidth, minwidth, AstNumeric::UNSIGNED); } } - AstCCast(FileLine* fl, AstNode* lhsp, AstNode* typeFromp) : AstNodeUniop(fl, lhsp) { + AstCCast(FileLine* fl, AstNode* lhsp, AstNode* typeFromp) + : ASTGEN_SUPER(fl, lhsp) { dtypeFrom(typeFromp); m_size = width(); } @@ -4645,8 +4679,8 @@ public: class AstCvtPackString : public AstNodeUniop { // Convert to Verilator Packed String (aka verilog "string") public: - AstCvtPackString(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetString(); } // Really, width should be dtypep -> STRING + AstCvtPackString(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetString(); } // Really, width should be dtypep -> STRING ASTNODE_NODE_FUNCS(CvtPackString) virtual void numberOperate(V3Number& out, const V3Number& lhs) { V3ERROR_NA; } virtual string emitVerilog() { return "%f$_CAST(%l)"; } @@ -4660,7 +4694,8 @@ public: class AstFEof : public AstNodeUniop { public: - AstFEof(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} + AstFEof(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(FEof) virtual void numberOperate(V3Number& out, const V3Number& lhs) { V3ERROR_NA; } virtual string emitVerilog() { return "%f$feof(%l)"; } @@ -4675,7 +4710,8 @@ public: class AstFGetC : public AstNodeUniop { public: - AstFGetC(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) {} + AstFGetC(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(FGetC) virtual void numberOperate(V3Number& out, const V3Number& lhs) { V3ERROR_NA; } virtual string emitVerilog() { return "%f$fgetc(%l)"; } @@ -4692,7 +4728,7 @@ public: class AstFUngetC : public AstNodeBiop { public: AstFUngetC(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeBiop(fl, lhsp, rhsp) {} + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(FUngetC) virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { V3ERROR_NA; } virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { @@ -4713,8 +4749,8 @@ public: class AstNodeSystemUniop : public AstNodeUniop { public: - AstNodeSystemUniop(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetDouble(); } + AstNodeSystemUniop(AstType t, FileLine* fl, AstNode* lhsp) + : AstNodeUniop(t, fl, lhsp) { dtypeSetDouble(); } ASTNODE_BASE_FUNCS(NodeSystemUniop) virtual bool cleanOut() const { return true; } virtual bool cleanLhs() const { return false; } @@ -4725,7 +4761,8 @@ public: class AstLogD : public AstNodeSystemUniop { public: - AstLogD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstLogD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(LogD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(log(lhs.toDouble())); } virtual string emitVerilog() { return "%f$ln(%l)"; } @@ -4733,7 +4770,8 @@ public: }; class AstLog10D : public AstNodeSystemUniop { public: - AstLog10D(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstLog10D(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(Log10D) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(log10(lhs.toDouble())); } virtual string emitVerilog() { return "%f$log10(%l)"; } @@ -4742,7 +4780,8 @@ public: class AstExpD : public AstNodeSystemUniop { public: - AstExpD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstExpD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(ExpD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(exp(lhs.toDouble())); } virtual string emitVerilog() { return "%f$exp(%l)"; } @@ -4751,7 +4790,8 @@ public: class AstSqrtD : public AstNodeSystemUniop { public: - AstSqrtD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstSqrtD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(SqrtD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(sqrt(lhs.toDouble())); } virtual string emitVerilog() { return "%f$sqrt(%l)"; } @@ -4760,7 +4800,8 @@ public: class AstFloorD : public AstNodeSystemUniop { public: - AstFloorD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstFloorD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(FloorD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(floor(lhs.toDouble())); } virtual string emitVerilog() { return "%f$floor(%l)"; } @@ -4769,7 +4810,8 @@ public: class AstCeilD : public AstNodeSystemUniop { public: - AstCeilD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstCeilD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(CeilD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(ceil(lhs.toDouble())); } virtual string emitVerilog() { return "%f$ceil(%l)"; } @@ -4778,7 +4820,8 @@ public: class AstSinD : public AstNodeSystemUniop { public: - AstSinD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstSinD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(SinD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(sin(lhs.toDouble())); } virtual string emitVerilog() { return "%f$sin(%l)"; } @@ -4787,7 +4830,8 @@ public: class AstCosD : public AstNodeSystemUniop { public: - AstCosD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstCosD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(CosD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(cos(lhs.toDouble())); } virtual string emitVerilog() { return "%f$cos(%l)"; } @@ -4796,7 +4840,8 @@ public: class AstTanD : public AstNodeSystemUniop { public: - AstTanD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstTanD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(TanD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(tan(lhs.toDouble())); } virtual string emitVerilog() { return "%f$tan(%l)"; } @@ -4805,7 +4850,8 @@ public: class AstAsinD : public AstNodeSystemUniop { public: - AstAsinD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAsinD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AsinD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(asin(lhs.toDouble())); } virtual string emitVerilog() { return "%f$asin(%l)"; } @@ -4814,7 +4860,8 @@ public: class AstAcosD : public AstNodeSystemUniop { public: - AstAcosD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAcosD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AcosD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(acos(lhs.toDouble())); } virtual string emitVerilog() { return "%f$acos(%l)"; } @@ -4823,7 +4870,8 @@ public: class AstAtanD : public AstNodeSystemUniop { public: - AstAtanD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAtanD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AtanD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(atan(lhs.toDouble())); } virtual string emitVerilog() { return "%f$atan(%l)"; } @@ -4832,7 +4880,8 @@ public: class AstSinhD : public AstNodeSystemUniop { public: - AstSinhD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstSinhD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(SinhD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(sinh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$sinh(%l)"; } @@ -4841,7 +4890,8 @@ public: class AstCoshD : public AstNodeSystemUniop { public: - AstCoshD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstCoshD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(CoshD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(cosh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$cosh(%l)"; } @@ -4850,7 +4900,8 @@ public: class AstTanhD : public AstNodeSystemUniop { public: - AstTanhD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstTanhD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(TanhD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(tanh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$tanh(%l)"; } @@ -4859,7 +4910,8 @@ public: class AstAsinhD : public AstNodeSystemUniop { public: - AstAsinhD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAsinhD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AsinhD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(asinh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$asinh(%l)"; } @@ -4868,7 +4920,8 @@ public: class AstAcoshD : public AstNodeSystemUniop { public: - AstAcoshD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAcoshD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AcoshD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(acosh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$acosh(%l)"; } @@ -4877,7 +4930,8 @@ public: class AstAtanhD : public AstNodeSystemUniop { public: - AstAtanhD(FileLine* fl, AstNode* lhsp) : AstNodeSystemUniop(fl, lhsp) {} + AstAtanhD(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) {} ASTNODE_NODE_FUNCS(AtanhD) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.setDouble(atanh(lhs.toDouble())); } virtual string emitVerilog() { return "%f$atanh(%l)"; } @@ -4886,8 +4940,8 @@ public: class AstToLowerN : public AstNodeUniop { // string.tolower() public: - AstToLowerN(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetString(); } + AstToLowerN(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetString(); } ASTNODE_NODE_FUNCS(ToLowerN) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opToLowerN(lhs); } virtual string emitVerilog() { return "%l.tolower()"; } @@ -4899,8 +4953,8 @@ public: class AstToUpperN : public AstNodeUniop { // string.toupper() public: - AstToUpperN(FileLine* fl, AstNode* lhsp) : AstNodeUniop(fl, lhsp) { - dtypeSetString(); } + AstToUpperN(FileLine* fl, AstNode* lhsp) + : ASTGEN_SUPER(fl, lhsp) { dtypeSetString(); } ASTNODE_NODE_FUNCS(ToUpperN) virtual void numberOperate(V3Number& out, const V3Number& lhs) { out.opToUpperN(lhs); } virtual string emitVerilog() { return "%l.toupper()"; } @@ -4918,7 +4972,7 @@ private: FmtType m_fmt; // Operation type public: AstAtoN(FileLine* fl, AstNode* lhsp, FmtType fmt) - : AstNodeUniop(fl, lhsp) + : ASTGEN_SUPER(fl, lhsp) , m_fmt(fmt) { fmt == ATOREAL ? dtypeSetDouble() : dtypeSetSigned32(); } @@ -4956,8 +5010,8 @@ public: class AstLogOr : public AstNodeBiop { public: - AstLogOr(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLogOr(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LogOr) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLogOr(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLogOr(lhs, rhs); } @@ -4973,8 +5027,8 @@ public: }; class AstLogAnd : public AstNodeBiop { public: - AstLogAnd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLogAnd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LogAnd) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLogAnd(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLogAnd(lhs, rhs); } @@ -4990,8 +5044,8 @@ public: }; class AstLogEq : public AstNodeBiCom { public: - AstLogEq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLogEq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LogEq) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLogEq(this->fileline(), lhsp, rhsp); } @@ -5009,8 +5063,8 @@ public: }; class AstLogIf : public AstNodeBiop { public: - AstLogIf(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLogIf(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LogIf) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLogIf(this->fileline(), lhsp, rhsp); } @@ -5028,8 +5082,8 @@ public: }; class AstOr : public AstNodeBiComAsv { public: - AstOr(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstOr(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Or) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstOr(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opOr(lhs, rhs); } @@ -5044,8 +5098,8 @@ public: }; class AstAnd : public AstNodeBiComAsv { public: - AstAnd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstAnd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(And) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAnd(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opAnd(lhs, rhs); } @@ -5060,8 +5114,8 @@ public: }; class AstXor : public AstNodeBiComAsv { public: - AstXor(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstXor(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Xor) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstXor(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opXor(lhs, rhs); } @@ -5076,8 +5130,8 @@ public: }; class AstXnor : public AstNodeBiComAsv { public: - AstXnor(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstXnor(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Xnor) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstXnor(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opXnor(lhs, rhs); } @@ -5092,8 +5146,8 @@ public: }; class AstEq : public AstNodeBiCom { public: - AstEq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstEq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Eq) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstEq(this->fileline(), lhsp, rhsp); } static AstNodeBiop* newTyped(FileLine* fl, AstNode* lhsp, AstNode* rhsp); // Return AstEq/AstEqD @@ -5109,8 +5163,8 @@ public: }; class AstEqD : public AstNodeBiCom { public: - AstEqD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstEqD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(EqD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstEqD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opEqD(lhs, rhs); } @@ -5127,8 +5181,8 @@ public: }; class AstEqN : public AstNodeBiCom { public: - AstEqN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstEqN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(EqN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstEqN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opEqN(lhs, rhs); } @@ -5145,8 +5199,8 @@ public: }; class AstNeq : public AstNodeBiCom { public: - AstNeq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstNeq(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Neq) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstNeq(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opNeq(lhs, rhs); } @@ -5161,8 +5215,8 @@ public: }; class AstNeqD : public AstNodeBiCom { public: - AstNeqD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstNeqD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(NeqD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstNeqD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opNeqD(lhs, rhs); } @@ -5179,8 +5233,8 @@ public: }; class AstNeqN : public AstNodeBiCom { public: - AstNeqN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstNeqN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(NeqN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstNeqN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opNeqN(lhs, rhs); } @@ -5197,8 +5251,8 @@ public: }; class AstLt : public AstNodeBiop { public: - AstLt(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLt(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Lt) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLt(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLt(lhs, rhs); } @@ -5213,8 +5267,8 @@ public: }; class AstLtD : public AstNodeBiop { public: - AstLtD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLtD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LtD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLtD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLtD(lhs, rhs); } @@ -5231,8 +5285,8 @@ public: }; class AstLtS : public AstNodeBiop { public: - AstLtS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLtS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LtS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLtS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLtS(lhs, rhs); } @@ -5248,8 +5302,8 @@ public: }; class AstLtN : public AstNodeBiop { public: - AstLtN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLtN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LtN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLtN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLtN(lhs, rhs); } @@ -5266,8 +5320,8 @@ public: }; class AstGt : public AstNodeBiop { public: - AstGt(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGt(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Gt) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGt(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGt(lhs, rhs); } @@ -5282,8 +5336,8 @@ public: }; class AstGtD : public AstNodeBiop { public: - AstGtD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGtD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GtD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGtD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGtD(lhs, rhs); } @@ -5300,8 +5354,8 @@ public: }; class AstGtS : public AstNodeBiop { public: - AstGtS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGtS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GtS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGtS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGtS(lhs, rhs); } @@ -5317,8 +5371,8 @@ public: }; class AstGtN : public AstNodeBiop { public: - AstGtN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGtN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GtN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGtN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGtN(lhs, rhs); } @@ -5335,8 +5389,8 @@ public: }; class AstGte : public AstNodeBiop { public: - AstGte(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGte(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Gte) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGte(this->fileline(), lhsp, rhsp); } static AstNodeBiop* newTyped(FileLine* fl, AstNode* lhsp, AstNode* rhsp); // Return AstGte/AstGteS/AstGteD @@ -5352,8 +5406,8 @@ public: }; class AstGteD : public AstNodeBiop { public: - AstGteD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGteD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GteD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGteD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGteD(lhs, rhs); } @@ -5370,8 +5424,8 @@ public: }; class AstGteS : public AstNodeBiop { public: - AstGteS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGteS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GteS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGteS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGteS(lhs, rhs); } @@ -5387,8 +5441,8 @@ public: }; class AstGteN : public AstNodeBiop { public: - AstGteN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstGteN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(GteN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGteN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opGteN(lhs, rhs); } @@ -5405,8 +5459,8 @@ public: }; class AstLte : public AstNodeBiop { public: - AstLte(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLte(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(Lte) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLte(this->fileline(), lhsp, rhsp); } static AstNodeBiop* newTyped(FileLine* fl, AstNode* lhsp, AstNode* rhsp); // Return AstLte/AstLteS/AstLteD @@ -5422,8 +5476,8 @@ public: }; class AstLteD : public AstNodeBiop { public: - AstLteD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLteD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LteD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLteD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLteD(lhs, rhs); } @@ -5440,8 +5494,8 @@ public: }; class AstLteS : public AstNodeBiop { public: - AstLteS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLteS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LteS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLteS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLteS(lhs, rhs); } @@ -5457,8 +5511,8 @@ public: }; class AstLteN : public AstNodeBiop { public: - AstLteN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstLteN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(LteN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstLteN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opLteN(lhs, rhs); } @@ -5476,7 +5530,7 @@ public: class AstShiftL : public AstNodeBiop { public: AstShiftL(FileLine* fl, AstNode* lhsp, AstNode* rhsp, int setwidth=0) - : AstNodeBiop(fl, lhsp, rhsp) { + : ASTGEN_SUPER(fl, lhsp, rhsp) { if (setwidth) { dtypeSetLogicSized(setwidth, AstNumeric::UNSIGNED); } } ASTNODE_NODE_FUNCS(ShiftL) @@ -5494,7 +5548,7 @@ public: class AstShiftR : public AstNodeBiop { public: AstShiftR(FileLine* fl, AstNode* lhsp, AstNode* rhsp, int setwidth=0) - : AstNodeBiop(fl, lhsp, rhsp) { + : ASTGEN_SUPER(fl, lhsp, rhsp) { if (setwidth) { dtypeSetLogicSized(setwidth, AstNumeric::UNSIGNED); } } ASTNODE_NODE_FUNCS(ShiftR) @@ -5515,7 +5569,7 @@ class AstShiftRS : public AstNodeBiop { // Output data type's width determines which bit is used for sign extension public: AstShiftRS(FileLine* fl, AstNode* lhsp, AstNode* rhsp, int setwidth=0) - : AstNodeBiop(fl, lhsp, rhsp) { + : ASTGEN_SUPER(fl, lhsp, rhsp) { // Important that widthMin be correct, as opExtend requires it after V3Expand if (setwidth) { dtypeSetLogicSized(setwidth, AstNumeric::SIGNED); } } @@ -5535,8 +5589,8 @@ public: }; class AstAdd : public AstNodeBiComAsv { public: - AstAdd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstAdd(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Add) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAdd(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opAdd(lhs, rhs); } @@ -5551,8 +5605,8 @@ public: }; class AstAddD : public AstNodeBiComAsv { public: - AstAddD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstAddD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(AddD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAddD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opAddD(lhs, rhs); } @@ -5569,8 +5623,8 @@ public: }; class AstSub : public AstNodeBiop { public: - AstSub(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstSub(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Sub) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstSub(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opSub(lhs, rhs); } @@ -5585,8 +5639,8 @@ public: }; class AstSubD : public AstNodeBiop { public: - AstSubD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstSubD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(SubD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstSubD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opSubD(lhs, rhs); } @@ -5603,8 +5657,8 @@ public: }; class AstMul : public AstNodeBiComAsv { public: - AstMul(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstMul(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Mul) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstMul(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opMul(lhs, rhs); } @@ -5620,8 +5674,8 @@ public: }; class AstMulD : public AstNodeBiComAsv { public: - AstMulD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstMulD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(MulD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstMulD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opMulD(lhs, rhs); } @@ -5638,8 +5692,8 @@ public: }; class AstMulS : public AstNodeBiComAsv { public: - AstMulS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiComAsv(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstMulS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(MulS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstMulS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opMulS(lhs, rhs); } @@ -5656,8 +5710,8 @@ public: }; class AstDiv : public AstNodeBiop { public: - AstDiv(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstDiv(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Div) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstDiv(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opDiv(lhs, rhs); } @@ -5672,8 +5726,8 @@ public: }; class AstDivD : public AstNodeBiop { public: - AstDivD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstDivD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(DivD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstDivD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opDivD(lhs, rhs); } @@ -5690,8 +5744,8 @@ public: }; class AstDivS : public AstNodeBiop { public: - AstDivS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstDivS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(DivS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstDivS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opDivS(lhs, rhs); } @@ -5707,8 +5761,8 @@ public: }; class AstModDiv : public AstNodeBiop { public: - AstModDiv(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstModDiv(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(ModDiv) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstModDiv(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opModDiv(lhs, rhs); } @@ -5723,8 +5777,8 @@ public: }; class AstModDivS : public AstNodeBiop { public: - AstModDivS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstModDivS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(ModDivS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstModDivS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opModDivS(lhs, rhs); } @@ -5740,8 +5794,8 @@ public: }; class AstPow : public AstNodeBiop { public: - AstPow(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstPow(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(Pow) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstPow(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opPow(lhs, rhs); } @@ -5756,8 +5810,8 @@ public: }; class AstPowD : public AstNodeBiop { public: - AstPowD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstPowD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetDouble(); } ASTNODE_NODE_FUNCS(PowD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstPowD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opPowD(lhs, rhs); } @@ -5773,8 +5827,8 @@ public: }; class AstPowSU : public AstNodeBiop { public: - AstPowSU(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstPowSU(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(PowSU) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstPowSU(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opPowSU(lhs, rhs); } @@ -5790,8 +5844,8 @@ public: }; class AstPowSS : public AstNodeBiop { public: - AstPowSS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstPowSS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(PowSS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstPowSS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opPowSS(lhs, rhs); } @@ -5807,8 +5861,8 @@ public: }; class AstPowUS : public AstNodeBiop { public: - AstPowUS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstPowUS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(PowUS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstPowUS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opPowUS(lhs, rhs); } @@ -5824,8 +5878,8 @@ public: }; class AstEqCase : public AstNodeBiCom { public: - AstEqCase(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstEqCase(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(EqCase) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstEqCase(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opCaseEq(lhs, rhs); } @@ -5840,8 +5894,8 @@ public: }; class AstNeqCase : public AstNodeBiCom { public: - AstNeqCase(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiCom(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstNeqCase(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(NeqCase) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstNeqCase(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opCaseNeq(lhs, rhs); } @@ -5857,8 +5911,8 @@ public: class AstEqWild : public AstNodeBiop { // Note wildcard operator rhs differs from lhs public: - AstEqWild(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstEqWild(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(EqWild) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstEqWild(this->fileline(), lhsp, rhsp); } static AstNodeBiop* newTyped(FileLine* fl, AstNode* lhsp, AstNode* rhsp); // Return AstEqWild/AstEqD @@ -5874,8 +5928,8 @@ public: }; class AstNeqWild : public AstNodeBiop { public: - AstNeqWild(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetLogicBool(); } + AstNeqWild(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetLogicBool(); } ASTNODE_NODE_FUNCS(NeqWild) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstNeqWild(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opWildNeq(lhs, rhs); } @@ -5891,7 +5945,8 @@ public: class AstConcat : public AstNodeBiop { // If you're looking for {#{}}, see AstReplicate public: - AstConcat(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { + AstConcat(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { if (lhsp->dtypep() && rhsp->dtypep()) { dtypeSetLogicSized(lhsp->dtypep()->width()+rhsp->dtypep()->width(), AstNumeric::UNSIGNED); @@ -5912,9 +5967,8 @@ public: class AstConcatN : public AstNodeBiop { // String concatenate public: - AstConcatN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetString(); - } + AstConcatN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetString(); } ASTNODE_NODE_FUNCS(ConcatN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstConcatN(this->fileline(), lhsp, rhsp); } virtual string emitVerilog() { return "%f{%l, %k%r}"; } @@ -5942,9 +5996,9 @@ private: } public: AstReplicate(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeBiop(fl, lhsp, rhsp) { init(); } + : ASTGEN_SUPER(fl, lhsp, rhsp) { init(); } AstReplicate(FileLine* fl, AstNode* lhsp, uint32_t repCount) - : AstNodeBiop(fl, lhsp, new AstConst(fl, repCount)) { init(); } + : ASTGEN_SUPER(fl, lhsp, new AstConst(fl, repCount)) { init(); } ASTNODE_NODE_FUNCS(Replicate) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstReplicate(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opRepl(lhs, rhs); } @@ -5963,9 +6017,9 @@ private: void init() { dtypeSetString(); } public: AstReplicateN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) - : AstNodeBiop(fl, lhsp, rhsp) { init(); } + : ASTGEN_SUPER(fl, lhsp, rhsp) { init(); } AstReplicateN(FileLine* fl, AstNode* lhsp, uint32_t repCount) - : AstNodeBiop(fl, lhsp, new AstConst(fl, repCount)) { init(); } + : ASTGEN_SUPER(fl, lhsp, new AstConst(fl, repCount)) { init(); } ASTNODE_NODE_FUNCS(ReplicateN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstReplicateN(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opReplN(lhs, rhs); } @@ -5982,7 +6036,8 @@ public: class AstStreamL : public AstNodeStream { // Verilog {rhs{lhs}} - Note rhsp() is the slice size, not the lhsp() public: - AstStreamL(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeStream(fl, lhsp, rhsp) {} + AstStreamL(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(StreamL) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstStreamL(this->fileline(), lhsp, rhsp); } virtual string emitVerilog() { return "%f{ << %r %k{%l} }"; } @@ -5998,7 +6053,8 @@ public: class AstStreamR : public AstNodeStream { // Verilog {rhs{lhs}} - Note rhsp() is the slice size, not the lhsp() public: - AstStreamR(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeStream(fl, lhsp, rhsp) {} + AstStreamR(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(StreamR) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstStreamR(this->fileline(), lhsp, rhsp); } virtual string emitVerilog() { return "%f{ >> %r %k{%l} }"; } @@ -6016,8 +6072,8 @@ class AstBufIf1 : public AstNodeBiop { // Note unlike the Verilog bufif1() UDP, this allows any width; each lhsp // bit enables respective rhsp bit public: - AstBufIf1(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeFrom(lhsp); } + AstBufIf1(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeFrom(lhsp); } ASTNODE_NODE_FUNCS(BufIf1) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstBufIf1(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { out.opBufIf1(lhs, rhs); } @@ -6032,7 +6088,8 @@ public: }; class AstFGetS : public AstNodeBiop { public: - AstFGetS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) {} + AstFGetS(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(FGetS) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstFGetS(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { V3ERROR_NA; } @@ -6050,8 +6107,8 @@ public: class AstNodeSystemBiop : public AstNodeBiop { public: - AstNodeSystemBiop(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetDouble(); } + AstNodeSystemBiop(AstType t, FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : AstNodeBiop(t, fl, lhsp, rhsp) { dtypeSetDouble(); } virtual bool cleanOut() const { return false; } virtual bool cleanLhs() const { return false; } virtual bool cleanRhs() const { return false; } @@ -6063,7 +6120,8 @@ public: class AstAtan2D : public AstNodeSystemBiop { public: - AstAtan2D(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeSystemBiop(fl, lhsp, rhsp) {} + AstAtan2D(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(Atan2D) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstAtan2D(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { @@ -6074,7 +6132,8 @@ public: class AstHypotD : public AstNodeSystemBiop { public: - AstHypotD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeSystemBiop(fl, lhsp, rhsp) {} + AstHypotD(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) {} ASTNODE_NODE_FUNCS(HypotD) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstHypotD(this->fileline(), lhsp, rhsp); } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { @@ -6086,9 +6145,8 @@ public: class AstPutcN : public AstNodeTriop { // Verilog string.putc() public: - AstPutcN(FileLine* fl, AstNode* lhsp, AstNode* rhsp, AstNode* ths) : AstNodeTriop(fl, lhsp, rhsp, ths) { - dtypeSetString(); - } + AstPutcN(FileLine* fl, AstNode* lhsp, AstNode* rhsp, AstNode* ths) + : ASTGEN_SUPER(fl, lhsp, rhsp, ths) { dtypeSetString(); } ASTNODE_NODE_FUNCS(PutcN) virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs, const V3Number& ths) { @@ -6110,9 +6168,8 @@ public: class AstGetcN : public AstNodeBiop { // Verilog string.getc() public: - AstGetcN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) : AstNodeBiop(fl, lhsp, rhsp) { - dtypeSetBitSized(8, AstNumeric::UNSIGNED); - } + AstGetcN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetBitSized(8, AstNumeric::UNSIGNED); } ASTNODE_NODE_FUNCS(GetcN) virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { return new AstGetcN(this->fileline(), lhsp, rhsp); @@ -6131,12 +6188,34 @@ public: virtual bool sizeMattersRhs() const { return false; } }; +class AstGetcRefN : public AstNodeBiop { + // Verilog string[#] on the left-hand-side of assignment + // Spec says is of type byte (not string of single character) +public: + AstGetcRefN(FileLine* fl, AstNode* lhsp, AstNode* rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) { dtypeSetBitSized(8, AstNumeric::UNSIGNED); } + ASTNODE_NODE_FUNCS(GetcRefN) + virtual AstNode* cloneType(AstNode* lhsp, AstNode* rhsp) { + return new AstGetcRefN(this->fileline(), lhsp, rhsp); + } + virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { + V3ERROR_NA; + } + virtual string emitVerilog() { return "%k%l[%r]"; } + virtual string emitC() { V3ERROR_NA; } + virtual string emitSimpleOperator() { return ""; } + virtual bool cleanOut() const { return true; } + virtual bool cleanLhs() const { return true; } + virtual bool cleanRhs() const { return true; } + virtual bool sizeMattersLhs() const { return false; } + virtual bool sizeMattersRhs() const { return false; } +}; + class AstSubstrN : public AstNodeTriop { // Verilog string.substr() public: - AstSubstrN(FileLine* fl, AstNode* lhsp, AstNode* rhsp, AstNode* ths) : AstNodeTriop(fl, lhsp, rhsp, ths) { - dtypeSetString(); - } + AstSubstrN(FileLine* fl, AstNode* lhsp, AstNode* rhsp, AstNode* ths) + : ASTGEN_SUPER(fl, lhsp, rhsp, ths) { dtypeSetString(); } ASTNODE_NODE_FUNCS(SubstrN) virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs, const V3Number& ths) { @@ -6161,7 +6240,7 @@ private: bool m_ignoreCase; // True for str.icompare() public: AstCompareNN(FileLine* fl, AstNode* lhsp, AstNode* rhsp, bool ignoreCase) - : AstNodeBiop(fl, lhsp, rhsp) + : ASTGEN_SUPER(fl, lhsp, rhsp) , m_ignoreCase(ignoreCase) { dtypeSetUInt32(); } @@ -6192,10 +6271,8 @@ class AstPast : public AstNodeMath { // Parents: math // Children: expression public: - AstPast(FileLine* fl, AstNode* exprp, AstNode* ticksp) : AstNodeMath(fl) { - addOp1p(exprp); - addNOp2p(ticksp); - } + AstPast(FileLine* fl, AstNode* exprp, AstNode* ticksp) + : ASTGEN_SUPER(fl) { addOp1p(exprp); addNOp2p(ticksp); } ASTNODE_NODE_FUNCS(Past) virtual string emitVerilog() { V3ERROR_NA; return ""; } virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { V3ERROR_NA; } @@ -6211,14 +6288,31 @@ public: virtual bool same(const AstNode* samep) const { return true; } }; +class AstSampled : public AstNodeMath { + // Verilog $sampled + // Parents: math + // Children: expression +public: + AstSampled(FileLine* fl, AstNode* exprp) + : ASTGEN_SUPER(fl) { addOp1p(exprp); } + ASTNODE_NODE_FUNCS(Sampled) + virtual string emitVerilog() { return "$sampled(%l)"; } + virtual string emitC() { V3ERROR_NA; return "";} + virtual string emitSimpleOperator() { V3ERROR_NA; return ""; } + virtual bool cleanOut() const { V3ERROR_NA; return ""; } + virtual int instrCount() const { return 0; } + AstNode* exprp() const { return op1p(); } // op1 = expression + virtual V3Hash sameHash() const { return V3Hash(); } + virtual bool same(const AstNode* samep) const { return true; } +}; + class AstPattern : public AstNodeMath { // Verilog '{a,b,c,d...} // Parents: AstNodeAssign, AstPattern, ... // Children: expression, AstPattern, AstPatReplicate public: - AstPattern(FileLine* fl, AstNode* itemsp) : AstNodeMath(fl) { - addNOp2p(itemsp); - } + AstPattern(FileLine* fl, AstNode* itemsp) + : ASTGEN_SUPER(fl) { addNOp2p(itemsp); } ASTNODE_NODE_FUNCS(Pattern) virtual string emitVerilog() { V3ERROR_NA; return ""; } // Implemented specially virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { V3ERROR_NA; } @@ -6239,8 +6333,8 @@ class AstPatMember : public AstNodeMath { private: bool m_default; public: - AstPatMember(FileLine* fl, AstNode* lhsp, AstNode* keyp, AstNode* repp) : AstNodeMath(fl) { - addOp1p(lhsp), setNOp2p(keyp), setNOp3p(repp); m_default = false; } + AstPatMember(FileLine* fl, AstNode* lhsp, AstNode* keyp, AstNode* repp) + : ASTGEN_SUPER(fl) { addOp1p(lhsp), setNOp2p(keyp), setNOp3p(repp); m_default = false; } ASTNODE_NODE_FUNCS(PatMember) virtual void numberOperate(V3Number& out, const V3Number& lhs, const V3Number& rhs) { V3ERROR_NA; } virtual string emitVerilog() { return lhssp()?"%f{%r{%k%l}}":"%l"; } @@ -6264,7 +6358,7 @@ class AstClocking : public AstNode { // Children: Assertions public: AstClocking(FileLine* fl, AstNodeSenItem* sensesp, AstNode* bodysp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addOp1p(sensesp); addNOp2p(bodysp); } @@ -6282,7 +6376,7 @@ class AstPropClocked : public AstNode { // Children: SENITEM, Properties public: AstPropClocked(FileLine* fl, AstNodeSenItem* sensesp, AstNode* disablep, AstNode* propp) - : AstNode(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(sensesp); addNOp2p(disablep); addOp3p(propp); @@ -6302,9 +6396,9 @@ private: bool m_immediate; // Immediate assertion/cover string m_name; // Name to report public: - AstNodeCoverOrAssert(FileLine* fl, AstNode* propp, AstNode* passsp, + AstNodeCoverOrAssert(AstType t, FileLine* fl, AstNode* propp, AstNode* passsp, bool immediate, const string& name="") - : AstNodeStmt(fl) + : AstNodeStmt(t, fl) , m_immediate(immediate) , m_name(name) { addOp1p(propp); @@ -6328,7 +6422,7 @@ public: ASTNODE_NODE_FUNCS(Assert) AstAssert(FileLine* fl, AstNode* propp, AstNode* passsp, AstNode* failsp, bool immediate, const string& name = "") - : AstNodeCoverOrAssert(fl, propp, passsp, immediate, name) { + : ASTGEN_SUPER(fl, propp, passsp, immediate, name) { addNOp3p(failsp); } AstNode* failsp() const { return op3p(); } // op3 = if assertion fails @@ -6339,7 +6433,7 @@ public: ASTNODE_NODE_FUNCS(Cover) AstCover(FileLine* fl, AstNode* propp, AstNode* stmtsp, bool immediate, const string& name = "") - : AstNodeCoverOrAssert(fl, propp, stmtsp, immediate, name) {} + : ASTGEN_SUPER(fl, propp, stmtsp, immediate, name) {} AstNode* coverincp() const { return op3p(); } // op3 = coverage node void coverincp(AstCoverInc* nodep) { addOp3p(nodep); } // op3 = coverage node virtual bool immediate() const { return false; } @@ -6349,30 +6443,37 @@ class AstRestrict : public AstNodeCoverOrAssert { public: ASTNODE_NODE_FUNCS(Restrict) AstRestrict(FileLine* fl, AstNode* propp) - : AstNodeCoverOrAssert(fl, propp, NULL, false, "") {} + : ASTGEN_SUPER(fl, propp, NULL, false, "") {} }; //====================================================================== // Text based nodes -class AstText : public AstNodeText { +class AstNodeSimpleText : public AstNodeText { private: bool m_tracking; // When emit, it's ok to parse the string to do indentation public: - AstText(FileLine* fl, const string& textp, bool tracking=false) - : AstNodeText(fl, textp), m_tracking(tracking) {} - ASTNODE_NODE_FUNCS(Text) + AstNodeSimpleText(AstType t, FileLine* fl, const string& textp, bool tracking=false) + : AstNodeText(t, fl, textp), m_tracking(tracking) {} + ASTNODE_BASE_FUNCS(NodeSimpleText) void tracking(bool flag) { m_tracking = flag; } bool tracking() const { return m_tracking; } }; -class AstTextBlock : public AstText { +class AstText : public AstNodeSimpleText { +public: + AstText(FileLine* fl, const string& textp, bool tracking=false) + : ASTGEN_SUPER(fl, textp, tracking) {} + ASTNODE_NODE_FUNCS(Text) +}; + +class AstTextBlock : public AstNodeSimpleText { private: bool m_commas; // Comma separate emitted children public: AstTextBlock(FileLine* fl, const string& textp="", bool tracking=false, bool commas=false) - : AstText(fl, textp, tracking), m_commas(commas) {} + : ASTGEN_SUPER(fl, textp, tracking), m_commas(commas) {} ASTNODE_NODE_FUNCS(TextBlock) void commas(bool flag) { m_commas = flag; } bool commas() const { return m_commas; } @@ -6386,7 +6487,7 @@ public: class AstScCtor : public AstNodeText { public: AstScCtor(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScCtor) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6395,7 +6496,7 @@ public: class AstScDtor : public AstNodeText { public: AstScDtor(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScDtor) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6404,7 +6505,7 @@ public: class AstScHdr : public AstNodeText { public: AstScHdr(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScHdr) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6413,7 +6514,7 @@ public: class AstScImp : public AstNodeText { public: AstScImp(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScImp) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6422,7 +6523,7 @@ public: class AstScImpHdr : public AstNodeText { public: AstScImpHdr(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScImpHdr) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6431,7 +6532,7 @@ public: class AstScInt : public AstNodeText { public: AstScInt(FileLine* fl, const string& textp) - : AstNodeText(fl, textp) {} + : ASTGEN_SUPER(fl, textp) {} ASTNODE_NODE_FUNCS(ScInt) virtual bool isPure() const { return false; } // SPECIAL: User may order w/other sigs virtual bool isOutputter() const { return true; } @@ -6441,7 +6542,7 @@ class AstUCStmt : public AstNodeStmt { // User $c statement public: AstUCStmt(FileLine* fl, AstNode* exprsp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(UCStmt) @@ -6457,18 +6558,18 @@ public: //====================================================================== // Emitted file nodes -class AstFile : public AstNode { +class AstNodeFile : public AstNode { // Emitted Otput file // Parents: NETLIST // Children: AstTextBlock private: string m_name; ///< Filename public: - AstFile(FileLine* fl, const string& name) - : AstNode(fl) { + AstNodeFile(AstType t, FileLine* fl, const string& name) + : AstNode(t, fl) { m_name = name; } - ASTNODE_BASE_FUNCS(File) + ASTNODE_BASE_FUNCS(NodeFile) virtual string name() const { return m_name; } virtual V3Hash sameHash() const { return V3Hash(); } virtual bool same(const AstNode* samep) const { return true; } @@ -6479,12 +6580,12 @@ public: //====================================================================== // Emit V nodes -class AstVFile : public AstFile { +class AstVFile : public AstNodeFile { // Verilog output file // Parents: NETLIST public: AstVFile(FileLine* fl, const string& name) - : AstFile(fl, name) { } + : ASTGEN_SUPER(fl, name) {} ASTNODE_NODE_FUNCS(VFile) virtual void dump(std::ostream& str=std::cout) const; }; @@ -6492,7 +6593,7 @@ public: //====================================================================== // Emit C nodes -class AstCFile : public AstFile { +class AstCFile : public AstNodeFile { // C++ output file // Parents: NETLIST private: @@ -6501,7 +6602,7 @@ private: bool m_support:1; ///< Support file (non systemc) public: AstCFile(FileLine* fl, const string& name) - : AstFile(fl, name) { + : ASTGEN_SUPER(fl, name) { m_slow = false; m_source = false; m_support = false; @@ -6545,7 +6646,7 @@ private: bool m_dpiImportWrapper:1; // Wrapper from dpi import public: AstCFunc(FileLine* fl, const string& name, AstScope* scopep, const string& rtnType="") - : AstNode(fl) { + : ASTGEN_SUPER(fl) { m_funcType = AstCFuncType::FT_NORMAL; m_isStatic = VBoolOrUnknown::BU_UNKNOWN; // Unknown until see where thisp needed m_scopep = scopep; @@ -6649,13 +6750,13 @@ private: string m_argTypes; public: AstCCall(FileLine* fl, AstCFunc* funcp, AstNode* argsp=NULL) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { m_funcp = funcp; addNOp1p(argsp); } AstCCall(AstCCall* oldp, AstCFunc* funcp) // Replacement form for V3Combine // Note this removes old attachments from the oldp - : AstNodeStmt(oldp->fileline()) { + : ASTGEN_SUPER(oldp->fileline()) { m_funcp = funcp; m_hiername = oldp->hiername(); m_argTypes = oldp->argTypes(); @@ -6695,7 +6796,7 @@ class AstCReturn : public AstNodeStmt { // Children: Math public: AstCReturn(FileLine* fl, AstNode* lhsp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { setOp1p(lhsp); } ASTNODE_NODE_FUNCS(CReturn) @@ -6713,12 +6814,12 @@ private: public: // Emit C textual math function (like AstUCFunc) AstCMath(FileLine* fl, AstNode* exprsp) - : AstNodeMath(fl), m_cleanOut(true), m_pure(false) { + : ASTGEN_SUPER(fl), m_cleanOut(true), m_pure(false) { addOp1p(exprsp); dtypeFrom(exprsp); } AstCMath(FileLine* fl, const string& textStmt, int setwidth, bool cleanOut=true) - : AstNodeMath(fl), m_cleanOut(cleanOut) { + : ASTGEN_SUPER(fl), m_cleanOut(cleanOut) { addNOp1p(new AstText(fl, textStmt, true)); if (setwidth) { dtypeSetLogicSized(setwidth, AstNumeric::UNSIGNED); } } @@ -6740,7 +6841,7 @@ class AstCReset : public AstNodeStmt { // Reset variable at startup public: AstCReset(FileLine* fl, AstNode* exprsp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } ASTNODE_NODE_FUNCS(CReset) @@ -6755,11 +6856,11 @@ class AstCStmt : public AstNodeStmt { // Emit C statement public: AstCStmt(FileLine* fl, AstNode* exprsp) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(exprsp); } AstCStmt(FileLine* fl, const string& textStmt) - : AstNodeStmt(fl) { + : ASTGEN_SUPER(fl) { addNOp1p(new AstText(fl, textStmt, true)); } ASTNODE_NODE_FUNCS(CStmt) @@ -6776,8 +6877,8 @@ class AstMTaskBody : public AstNode { private: ExecMTask* m_execMTaskp; public: - explicit AstMTaskBody(FileLine* flp) - : AstNode(flp) + explicit AstMTaskBody(FileLine* fl) + : ASTGEN_SUPER(fl) , m_execMTaskp(NULL) {} ASTNODE_NODE_FUNCS(MTaskBody); virtual const char* broken() const { BROKEN_RTN(!m_execMTaskp); return NULL; } @@ -6800,7 +6901,7 @@ class AstExecGraph : public AstNode { private: V3Graph *m_depGraphp; // contains ExecMTask's public: - explicit AstExecGraph(FileLine* fileline); + explicit AstExecGraph(FileLine* fl); ASTNODE_NODE_FUNCS_NO_DTOR(ExecGraph) virtual ~AstExecGraph(); virtual const char* broken() const { BROKEN_RTN(!m_depGraphp); return NULL; } @@ -6812,8 +6913,8 @@ public: class AstSplitPlaceholder : public AstNode { public: // Dummy node used within V3Split; never exists outside of V3Split. - explicit AstSplitPlaceholder(FileLine* filelinep) - : AstNode(filelinep) {} + explicit AstSplitPlaceholder(FileLine* fl) + : ASTGEN_SUPER(fl) {} ASTNODE_NODE_FUNCS(SplitPlaceholder) }; @@ -6829,7 +6930,8 @@ class AstTypeTable : public AstNode { typedef std::map DetailedMap; DetailedMap m_detailedMap; public: - explicit AstTypeTable(FileLine* fl) : AstNode(fl), m_voidp(NULL) { + explicit AstTypeTable(FileLine* fl) + : ASTGEN_SUPER(fl), m_voidp(NULL) { for (int i=0; i1 mode public: AstNetlist() - : AstNode(new FileLine(FileLine::builtInFilename())) + : ASTGEN_SUPER(new FileLine(FileLine::builtInFilename())) , m_typeTablep(NULL) , m_dollarUnitPkgp(NULL) , m_evalp(NULL) - , m_execGraphp(NULL) { } + , m_execGraphp(NULL) {} ASTNODE_NODE_FUNCS(Netlist) virtual const char* broken() const { BROKEN_RTN(m_dollarUnitPkgp && !m_dollarUnitPkgp->brokeExists()); @@ -6877,8 +6979,8 @@ public: AstNodeModule* topModulep() const { // * = Top module in hierarchy (first one added, for now) return VN_CAST(op1p(), NodeModule); } void addModulep(AstNodeModule* modulep) { addOp1p(modulep); } - AstFile* filesp() const { return VN_CAST(op2p(), File);} // op2 = List of files - void addFilesp(AstFile* filep) { addOp2p(filep); } + AstNodeFile* filesp() const { return VN_CAST(op2p(), NodeFile); } // op2 = List of files + void addFilesp(AstNodeFile* filep) { addOp2p(filep); } AstNode* miscsp() const { return op3p(); } // op3 = List of dtypes etc void addMiscsp(AstNode* nodep) { addOp3p(nodep); } AstTypeTable* typeTablep() { return m_typeTablep; } @@ -6901,4 +7003,6 @@ public: //###################################################################### +#undef ASTGEN_SUPER + #endif // Guard diff --git a/src/V3Begin.cpp b/src/V3Begin.cpp index ae4c4ef3f..2cb65de2e 100644 --- a/src/V3Begin.cpp +++ b/src/V3Begin.cpp @@ -72,20 +72,21 @@ private: AstNodeFTask* m_ftaskp; // Current function/task string m_namedScope; // Name of begin blocks above us string m_unnamedScope; // Name of begin blocks, including unnamed blocks - int m_repeatNum; // Repeat counter int m_ifDepth; // Current if depth // METHODS VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - m_repeatNum = 0; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { UINFO(8," "<name(m_unnamedScope+"__DOT__"+nodep->name()); @@ -170,7 +171,7 @@ private: else m_modp->addStmtp(nodep); } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { UINFO(8," CELL "<userMarkChanged(nodep); @@ -183,14 +184,14 @@ private: } iterateChildren(nodep); } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { UINFO(9, " VARXREF "<inlinedDots() == "") { nodep->inlinedDots(m_namedScope); UINFO(9, " rescope to "<user1SetOnce()) return; // Don't double-add text's @@ -203,13 +204,13 @@ private: } iterateChildren(nodep); } - virtual void visit(AstCoverDecl* nodep) { + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE { // Don't need to fix path in coverage statements, they're not under // any BEGINs, but V3Coverage adds them all under the module itself. iterateChildren(nodep); } // VISITORS - LINT CHECK - virtual void visit(AstIf* nodep) { // Note not AstNodeIf; other types don't get covered + virtual void visit(AstIf* nodep) VL_OVERRIDE { // Note not AstNodeIf; other types don't get covered // Check IFDEPTH warning - could be in other transform files if desire int prevIfDepth = m_ifDepth; if (m_ifDepth == -1 || v3Global.opt.ifDepth()<1) { // Turned off @@ -223,7 +224,7 @@ private: iterateChildren(nodep); m_ifDepth = prevIfDepth; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -232,7 +233,6 @@ public: m_statep = statep; m_modp = NULL; m_ftaskp = NULL; - m_repeatNum = 0; m_ifDepth = 0; iterate(nodep); } @@ -249,21 +249,21 @@ private: // AstNodeFTask::user1p // Node replaced, rename it // VISITORS - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { if (nodep->taskp()->user1()) { // It was converted UINFO(9, " relinkFTask "<name(nodep->taskp()->name()); } iterateChildren(nodep); } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp()->user1()) { // It was converted UINFO(9, " relinVarRef "<name(nodep->varp()->name()); } iterateChildren(nodep); } - virtual void visit(AstIfaceRefDType* nodep) { + virtual void visit(AstIfaceRefDType* nodep) VL_OVERRIDE { // May have changed cell names // TypeTable is always after all modules, so names are stable UINFO(8," IFACEREFDTYPE "<funcp()->user1Inc(); iterateChildren(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { checkUnlikely(nodep); m_cfuncsp.push_back(nodep); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { checkUnlikely(nodep); iterateChildren(nodep); } diff --git a/src/V3Broken.cpp b/src/V3Broken.cpp index c8d413117..6cde15b0e 100644 --- a/src/V3Broken.cpp +++ b/src/V3Broken.cpp @@ -209,7 +209,7 @@ private: iterateChildrenConst(nodep); } // VISITORS - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { processAndIterate(nodep); } public: @@ -257,7 +257,7 @@ private: iterateChildrenConst(nodep); BrokenTable::setUnder(nodep, false); } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { processAndIterate(nodep); UASSERT_OBJ(!(v3Global.assertDTypesResolved() && nodep->brokeLhsMustBeLvalue() @@ -265,7 +265,7 @@ private: && !VN_CAST(nodep->lhsp(), NodeVarRef)->lvalue()), nodep, "Assignment LHS is not an lvalue"); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { processAndIterate(nodep); } public: diff --git a/src/V3Case.cpp b/src/V3Case.cpp index abc94ed38..86c3d16c9 100644 --- a/src/V3Case.cpp +++ b/src/V3Case.cpp @@ -62,7 +62,7 @@ private: // METHODS VL_DEBUG_FUNC; // Declare debug() - virtual void visit(AstNodeCase* nodep) { + virtual void visit(AstNodeCase* nodep) VL_OVERRIDE { if (VN_IS(nodep, Case) && VN_CAST(nodep, Case)->casex()) { nodep->v3warn(CASEX, "Suggest casez (with ?'s) in place of casex (with X's)"); } @@ -89,7 +89,7 @@ private: m_caseExprp = NULL; } } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { // See also neverItem if (m_caseExprp && nodep->num().isFourState()) { if (VN_IS(m_caseExprp, GenCase)) { @@ -106,7 +106,7 @@ private: } } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -460,7 +460,7 @@ private: } // VISITORS - virtual void visit(AstCase* nodep) { + virtual void visit(AstCase* nodep) VL_OVERRIDE { V3Case::caseLint(nodep); iterateChildren(nodep); if (debug()>=9) nodep->dumpTree(cout, " case_old: "); @@ -476,7 +476,7 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Cast.cpp b/src/V3Cast.cpp index b7246184b..533faa24d 100644 --- a/src/V3Cast.cpp +++ b/src/V3Cast.cpp @@ -75,7 +75,7 @@ private: relinkHandle.relink(castp); //if (debug()>8) castp->dumpTree(cout, "-castins: "); // - insureLower32Cast(castp); + ensureLower32Cast(castp); nodep->user1(1); // Now must be of known size } int castSize(AstNode* nodep) { @@ -84,13 +84,13 @@ private: else if (nodep->width() <= 16) return 16; else return VL_IDATASIZE; } - void insureCast(AstNode* nodep) { + void ensureCast(AstNode* nodep) { if (castSize(nodep->backp()) != castSize(nodep) || !nodep->user1()) { insertCast(nodep, castSize(nodep->backp())); } } - void insureLower32Cast(AstCCast* nodep) { + void ensureLower32Cast(AstCCast* nodep) { // If we have uint64 = CAST(uint64(x)) then the upcasting // really needs to be CAST(uint64(CAST(uint32(x))). // Otherwise a (uint64)(a>b) would return wrong value, as @@ -102,33 +102,33 @@ private: } // VISITORS - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->user1(nodep->lhsp()->user1()); - if (nodep->sizeMattersLhs()) insureCast(nodep->lhsp()); + if (nodep->sizeMattersLhs()) ensureCast(nodep->lhsp()); } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->user1(nodep->lhsp()->user1() | nodep->rhsp()->user1()); - if (nodep->sizeMattersLhs()) insureCast(nodep->lhsp()); - if (nodep->sizeMattersRhs()) insureCast(nodep->rhsp()); + if (nodep->sizeMattersLhs()) ensureCast(nodep->lhsp()); + if (nodep->sizeMattersRhs()) ensureCast(nodep->rhsp()); } - virtual void visit(AstNodeTriop* nodep) { + virtual void visit(AstNodeTriop* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->user1(nodep->lhsp()->user1() | nodep->rhsp()->user1() | nodep->thsp()->user1()); - if (nodep->sizeMattersLhs()) insureCast(nodep->lhsp()); - if (nodep->sizeMattersRhs()) insureCast(nodep->rhsp()); - if (nodep->sizeMattersThs()) insureCast(nodep->thsp()); + if (nodep->sizeMattersLhs()) ensureCast(nodep->lhsp()); + if (nodep->sizeMattersRhs()) ensureCast(nodep->rhsp()); + if (nodep->sizeMattersThs()) ensureCast(nodep->thsp()); } - virtual void visit(AstCCast* nodep) { + virtual void visit(AstCCast* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureLower32Cast(nodep); + ensureLower32Cast(nodep); nodep->user1(1); } - virtual void visit(AstNegate* nodep) { + virtual void visit(AstNegate* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->user1(nodep->lhsp()->user1()); if (nodep->lhsp()->widthMin()==1) { @@ -137,10 +137,10 @@ private: // out = {32{a out = - (alhsp(), castSize(nodep)); } else { - insureCast(nodep->lhsp()); + ensureCast(nodep->lhsp()); } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (!nodep->lvalue() && !VN_IS(nodep->backp(), CCast) && VN_IS(nodep->backp(), NodeMath) @@ -153,7 +153,7 @@ private: } nodep->user1(1); } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { // Constants are of unknown size if smaller than 33 bits, because // we're too lazy to wrap every constant in the universe in // ((IData)#). @@ -161,11 +161,11 @@ private: } // NOPs - virtual void visit(AstVar* nodep) {} + virtual void visit(AstVar* nodep) VL_OVERRIDE {} //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Cdc.cpp b/src/V3Cdc.cpp index 0e840947e..0ffa208c5 100644 --- a/src/V3Cdc.cpp +++ b/src/V3Cdc.cpp @@ -136,7 +136,7 @@ private: std::ofstream* m_ofp; // Output file string m_prefix; - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { *m_ofp<user3()) *m_ofp<<" %%"; else *m_ofp<<" "; @@ -170,7 +170,7 @@ private: int m_maxLineno; size_t m_maxFilenameLen; - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); // Keeping line+filename lengths separate is much faster than calling ascii().length() if (nodep->fileline()->lineno() >= m_maxLineno) { @@ -608,19 +608,22 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(4," SCOPE "<varScopep(); @@ -659,72 +662,72 @@ private: } } } - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { m_inDly = true; iterateChildren(nodep); m_inDly = false; } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { // Note we look at only AstSenItems, not AstSenGate's // The gating term of a AstSenGate is normal logic m_inSenItem = true; iterateChildren(nodep); m_inSenItem = false; } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { // CDC doesn't care about public variables } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { // First handle the clock part will be handled in a minute by visit AstSenItem // The logic gating term is dealt with as logic iterateNewStmt(nodep); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } // Math that shouldn't cause us to clear hazard - virtual void visit(AstConst* nodep) { } - virtual void visit(AstReplicate* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { } + virtual void visit(AstReplicate* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstNot* nodep) { + virtual void visit(AstNot* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { if (!VN_IS(nodep->lsbp(), Const)) setNodeHazard(nodep); iterateChildren(nodep); } - virtual void visit(AstNodeSel* nodep) { + virtual void visit(AstNodeSel* nodep) VL_OVERRIDE { if (!VN_IS(nodep->bitp(), Const)) setNodeHazard(nodep); iterateChildren(nodep); } // Ignores - virtual void visit(AstInitial* nodep) { } - virtual void visit(AstTraceInc* nodep) { } - virtual void visit(AstCoverToggle* nodep) { } - virtual void visit(AstNodeDType* nodep) { } + virtual void visit(AstInitial* nodep) VL_OVERRIDE { } + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { } + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { } + virtual void visit(AstNodeDType* nodep) VL_OVERRIDE { } //-------------------- // Default - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { setNodeHazard(nodep); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Changed.cpp b/src/V3Changed.cpp index 9b51f8487..6501030f1 100644 --- a/src/V3Changed.cpp +++ b/src/V3Changed.cpp @@ -148,13 +148,13 @@ private: m_statep->m_numStmts += visitor.count(); } - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { newChangeDet(); } - virtual void visit(AstPackArrayDType* nodep) { + virtual void visit(AstPackArrayDType* nodep) VL_OVERRIDE { newChangeDet(); } - virtual void visit(AstUnpackArrayDType* nodep) { + virtual void visit(AstUnpackArrayDType* nodep) VL_OVERRIDE { for (int index=0; index < nodep->elementsConst(); ++index) { AstNode* origVEp = m_varEqnp; AstNode* origNLEp = m_newLvEqnp; @@ -175,7 +175,7 @@ private: m_newRvEqnp = origNREp; } } - virtual void visit(AstNodeUOrStructDType* nodep) { + virtual void visit(AstNodeUOrStructDType* nodep) VL_OVERRIDE { if (nodep->packedUnsup()) { newChangeDet(); } else { @@ -185,7 +185,7 @@ private: <varp()->prettyNameQ()); } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); if (debug()) nodep->dumpTree(cout, "-DETECTARRAY-general-"); m_vscp->v3warn(E_DETECTARRAY, "Unsupported: Can't detect changes on complex variable" @@ -247,7 +247,7 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<isTop()) { m_statep->m_topModp = nodep; @@ -255,7 +255,7 @@ private: iterateChildren(nodep); } - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { UINFO(4," TS "<isCircular()) { UINFO(8," CIRC "<user1SetOnce()) { @@ -287,12 +287,12 @@ private: } } } - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { // Short-circuit } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Clean.cpp b/src/V3Clean.cpp index e59c909d7..6581ec37e 100644 --- a/src/V3Clean.cpp +++ b/src/V3Clean.cpp @@ -135,15 +135,15 @@ private: cleanp->dtypeFrom(nodep); // Otherwise the AND normally picks LHS relinkHandle.relink(cleanp); } - void insureClean(AstNode* nodep) { + void ensureClean(AstNode* nodep) { computeCppWidth(nodep); if (!isClean(nodep)) insertClean(nodep); } - void insureCleanAndNext(AstNode* nodep) { + void ensureCleanAndNext(AstNode* nodep) { // Editing list, careful looping! for (AstNode* exprp = nodep; exprp; ) { AstNode* nextp = exprp->nextp(); - insureClean(exprp); + ensureClean(exprp); exprp = nextp; } } @@ -153,10 +153,10 @@ private: iterateChildren(nodep); computeCppWidth(nodep); if (nodep->cleanLhs()) { - insureClean(nodep->lhsp()); + ensureClean(nodep->lhsp()); } if (nodep->cleanRhs()) { - insureClean(nodep->rhsp()); + ensureClean(nodep->rhsp()); } //no setClean.. must do it in each user routine. } @@ -164,70 +164,73 @@ private: iterateChildren(nodep); computeCppWidth(nodep); if (nodep->cleanLhs()) { - insureClean(nodep->lhsp()); + ensureClean(nodep->lhsp()); } if (nodep->cleanRhs()) { - insureClean(nodep->rhsp()); + ensureClean(nodep->rhsp()); } if (nodep->cleanThs()) { - insureClean(nodep->thsp()); + ensureClean(nodep->thsp()); } //no setClean.. must do it in each user routine. } // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { iterateChildren(nodep); computeCppWidth(nodep); if (nodep->cleanLhs()) { - insureClean(nodep->lhsp()); + ensureClean(nodep->lhsp()); } setClean(nodep, nodep->cleanOut()); } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { operandBiop(nodep); setClean(nodep, nodep->cleanOut()); } - virtual void visit(AstAnd* nodep) { + virtual void visit(AstAnd* nodep) VL_OVERRIDE { operandBiop(nodep); setClean(nodep, isClean(nodep->lhsp()) || isClean(nodep->rhsp())); } - virtual void visit(AstXor* nodep) { + virtual void visit(AstXor* nodep) VL_OVERRIDE { operandBiop(nodep); setClean(nodep, isClean(nodep->lhsp()) && isClean(nodep->rhsp())); } - virtual void visit(AstOr* nodep) { + virtual void visit(AstOr* nodep) VL_OVERRIDE { operandBiop(nodep); setClean(nodep, isClean(nodep->lhsp()) && isClean(nodep->rhsp())); } - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { iterateChildren(nodep); computeCppWidth(nodep); setClean(nodep, nodep->cleanOut()); } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { iterateChildren(nodep); computeCppWidth(nodep); if (nodep->cleanRhs()) { - insureClean(nodep->rhsp()); + ensureClean(nodep->rhsp()); } } - virtual void visit(AstText* nodep) { + virtual void visit(AstText* nodep) VL_OVERRIDE { setClean(nodep, true); } - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { setClean(nodep, true); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { operandTriop(nodep); setClean(nodep, nodep->cleanOut()); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { iterateChildren(nodep); computeCppWidth(nodep); setClean(nodep, false); @@ -235,66 +238,66 @@ private: if (!VN_IS(nodep->backp(), And)) { insertClean(nodep); } - insureCleanAndNext(nodep->bodysp()); + ensureCleanAndNext(nodep->bodysp()); } - virtual void visit(AstTraceDecl* nodep) { + virtual void visit(AstTraceDecl* nodep) VL_OVERRIDE { // No cleaning, or would loose pointer to enum iterateChildren(nodep); } - virtual void visit(AstTraceInc* nodep) { + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureCleanAndNext(nodep->valuep()); + ensureCleanAndNext(nodep->valuep()); } - virtual void visit(AstTypedef* nodep) { + virtual void visit(AstTypedef* nodep) VL_OVERRIDE { // No cleaning, or would loose pointer to enum iterateChildren(nodep); } - virtual void visit(AstParamTypeDType* nodep) { + virtual void visit(AstParamTypeDType* nodep) VL_OVERRIDE { // No cleaning, or would loose pointer to enum iterateChildren(nodep); } // Control flow operators - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureClean(nodep->condp()); + ensureClean(nodep->condp()); setClean(nodep, isClean(nodep->expr1p()) && isClean(nodep->expr2p())); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureClean(nodep->condp()); + ensureClean(nodep->condp()); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureClean(nodep->condp()); + ensureClean(nodep->condp()); } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureCleanAndNext(nodep->exprsp()); + ensureCleanAndNext(nodep->exprsp()); setClean(nodep, true); // generates a string, so not relevant } - virtual void visit(AstUCStmt* nodep) { + virtual void visit(AstUCStmt* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureCleanAndNext(nodep->bodysp()); + ensureCleanAndNext(nodep->bodysp()); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureCleanAndNext(nodep->argsp()); + ensureCleanAndNext(nodep->argsp()); setClean(nodep, true); } - virtual void visit(AstCMethodHard* nodep) { + virtual void visit(AstCMethodHard* nodep) VL_OVERRIDE { iterateChildren(nodep); - insureCleanAndNext(nodep->pinsp()); + ensureCleanAndNext(nodep->pinsp()); setClean(nodep, true); } - virtual void visit(AstIntfRef* nodep) { + virtual void visit(AstIntfRef* nodep) VL_OVERRIDE { iterateChildren(nodep); setClean(nodep, true); // generates a string, so not relevant } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); computeCppWidth(nodep); } diff --git a/src/V3Clock.cpp b/src/V3Clock.cpp index 39d6fc889..66d579e2c 100644 --- a/src/V3Clock.cpp +++ b/src/V3Clock.cpp @@ -189,7 +189,7 @@ private: } // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { UINFO(4," TOPSCOPE "<scopep(); @@ -254,13 +254,16 @@ private: m_topScopep = NULL; m_scopep = NULL; } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { //UINFO(4," MOD "<fileline(), nodep->typeName(), true); nodep->replaceWith(cmtp); if (AstNode* stmtsp = nodep->bodysp()) { @@ -280,7 +283,7 @@ private: } VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstAlwaysPost* nodep) { + virtual void visit(AstAlwaysPost* nodep) VL_OVERRIDE { AstNode* cmtp = new AstComment(nodep->fileline(), nodep->typeName(), true); nodep->replaceWith(cmtp); if (AstNode* stmtsp = nodep->bodysp()) { @@ -289,7 +292,7 @@ private: } VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { //nodep->dumpTree(cout, "ct:"); //COVERTOGGLE(INC, ORIG, CHANGE) -> // IF(ORIG ^ CHANGE) { INC; CHANGE = ORIG; } @@ -309,7 +312,7 @@ private: origp->cloneTree(false))); nodep->replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { AstNode* cmtp = new AstComment(nodep->fileline(), nodep->typeName(), true); nodep->replaceWith(cmtp); if (AstNode* stmtsp = nodep->bodysp()) { @@ -318,7 +321,7 @@ private: } VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { iterateChildren(nodep); // Link to global function if (nodep->formCallTree()) { @@ -328,7 +331,7 @@ private: m_finalFuncp->addStmtsp(callp); } } - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { // Delete it later; Actives still pointing to it nodep->unlinkFrBack(); pushDeletep(nodep); @@ -342,7 +345,7 @@ private: void addToInitial(AstNode* stmtsp) { m_initFuncp->addStmtsp(stmtsp); // add to top level function } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { // Careful if adding variables here, ACTIVES can be under other ACTIVES // Need to save and restore any member state in AstUntilStable block if (!m_topScopep || !nodep->stmtsp()) { @@ -410,7 +413,7 @@ private: VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } } - virtual void visit(AstExecGraph* nodep) { + virtual void visit(AstExecGraph* nodep) VL_OVERRIDE { for (m_mtaskBodyp = VN_CAST(nodep->op1p(), MTaskBody); m_mtaskBodyp; m_mtaskBodyp = VN_CAST(m_mtaskBodyp->nextp(), MTaskBody)) { @@ -427,7 +430,7 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Combine.cpp b/src/V3Combine.cpp index b8ae192ad..73d92c786 100644 --- a/src/V3Combine.cpp +++ b/src/V3Combine.cpp @@ -66,7 +66,7 @@ protected: static bool emptyFunctionDeletion() { return true; } static bool duplicateFunctionCombine() { return true; } // Note this is disabled, it still needed work - // Also repair it for DPI functions; when make __common need to insure proper + // Also repair it for DPI functions; when make __common need to ensure proper // flags get inherited from the old to new AstCFunc, and that AstText doesn't // get split between functions causing the text to have a dangling reference. bool statementCombine() { return false; } // duplicateFunctionCombine(); @@ -131,13 +131,13 @@ public: } private: // VISITORS - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { addCall(nodep); } // Speed things up - virtual void visit(AstNodeAssign* nodep) {} - virtual void visit(AstNodeMath* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE {} + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -160,7 +160,7 @@ private: // OUTPUT: // AstNode::user3() -> bool. True to indicate duplicated // VISITORS - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { nodep->user3(true); iterateChildren(nodep); } @@ -389,7 +389,7 @@ private: } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Track all callers of each function m_call.main(nodep); // @@ -398,7 +398,7 @@ private: // Required so that a module instantiating another can benefit from collapsing. iterateChildrenBackwards(nodep); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<dontCombine()) { if (m_state == STATE_HASH) { @@ -438,7 +438,7 @@ private: } m_funcp = NULL; } - virtual void visit(AstNodeStmt* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { if (!nodep->isStatement()) { iterateChildren(nodep); return; @@ -453,10 +453,10 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstVar*) {} - virtual void visit(AstTraceDecl*) {} - virtual void visit(AstTraceInc*) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} + virtual void visit(AstTraceDecl*) VL_OVERRIDE {} + virtual void visit(AstTraceInc*) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Config.cpp b/src/V3Config.cpp index 8a1568d60..0528ca921 100644 --- a/src/V3Config.cpp +++ b/src/V3Config.cpp @@ -165,7 +165,7 @@ typedef V3ConfigWildcardResolver V3ConfigFTaskResolver; // Modules have tasks, variables, named blocks and properties class V3ConfigModule { - typedef std::unordered_set StringSet; + typedef vl_unordered_set StringSet; V3ConfigFTaskResolver m_tasks; // Functions/tasks in module V3ConfigVarResolver m_vars; // Variables in module @@ -290,8 +290,10 @@ class V3ConfigFile { } public: - V3ConfigFile() { m_lastIgnore = {-1, m_ignLines.begin()}; } - + V3ConfigFile() { + m_lastIgnore.lineno = -1; + m_lastIgnore.it = m_ignLines.begin(); + } void update(const V3ConfigFile& file) { // Copy in all Attributes for (LineAttrMap::const_iterator it = file.m_lineAttrs.begin(); @@ -455,7 +457,7 @@ void V3Config::addVarAttr(FileLine* fl, const string& module, const string& ftas if (ftask.empty()) { mod.vars().at(var).push_back(V3ConfigVarAttr(attr, sensep)); } else { - mod.ftasks().at(ftask).vars().at(var).push_back({attr, sensep}); + mod.ftasks().at(ftask).vars().at(var).push_back(V3ConfigVarAttr(attr, sensep)); } } } diff --git a/src/V3Const.cpp b/src/V3Const.cpp index 668fbb34c..2ae16580a 100644 --- a/src/V3Const.cpp +++ b/src/V3Const.cpp @@ -46,10 +46,10 @@ class ConstVarMarkVisitor : public AstNVisitor { // AstVar::user4p -> bool, Var marked, 0=not set yet private: // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp()) nodep->varp()->user4(1); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -68,10 +68,10 @@ class ConstVarFindVisitor : public AstNVisitor { bool m_found; private: // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp() && nodep->varp()->user4()) m_found = true; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -1282,23 +1282,26 @@ private: //---------------------------------------- // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Iterate modules backwards, in bottom-up order. That's faster iterateChildrenBackwards(nodep); } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { // No ASSIGNW removals under funcs, we've long eliminated INITIALs // (We should perhaps rename the assignw's to just assigns) m_wremove = false; iterateChildren(nodep); m_wremove = true; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { // No ASSIGNW removals under scope, we've long eliminated INITIALs m_scopep = nodep; m_wremove = false; @@ -1371,16 +1374,16 @@ private: } // Special cases - virtual void visit(AstConst* nodep) {} // Already constant + virtual void visit(AstConst* nodep) VL_OVERRIDE {} // Already constant - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { if (m_params) { iterateAndNextNull(nodep->paramsp()); } else { iterateChildren(nodep); } } - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -1568,14 +1571,14 @@ private: nodep->replaceWith(fromp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstAttrOf* nodep) { + virtual void visit(AstAttrOf* nodep) VL_OVERRIDE { AstAttrOf* oldAttr = m_attrp; m_attrp = nodep; iterateChildren(nodep); m_attrp = oldAttr; } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->bitp()); if (VN_IS(nodep->bitp(), Const) && VN_IS(nodep->fromp(), VarRef) @@ -1601,7 +1604,7 @@ private: } m_selp = NULL; } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { iterateChildren(nodep); UASSERT_OBJ(nodep->varp(), nodep, "Not linked"); bool did = false; @@ -1652,7 +1655,7 @@ private: <varp()->prettyNameQ()); } } - virtual void visit(AstEnumItemRef* nodep) { + virtual void visit(AstEnumItemRef* nodep) VL_OVERRIDE { iterateChildren(nodep); UASSERT_OBJ(nodep->itemp(), nodep, "Not linked"); bool did = false; @@ -1677,7 +1680,7 @@ private: } } - // virtual void visit(AstCvtPackString* nodep) { + // virtual void visit(AstCvtPackString* nodep) VL_OVERRIDE { // Not constant propagated (for today) because AstNodeMath::isOpaque is set // Someday if lower is constant, convert to quoted "string". @@ -1685,7 +1688,7 @@ private: // Only one if it's not in a list return (!nodep->nextp() && nodep->backp()->nextp() != nodep); } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doNConst && (VN_IS(nodep->sensp(), Const) @@ -1727,7 +1730,7 @@ private: "Null sensitivity variable"); } } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { iterateChildren(nodep); if (AstConst* constp = VN_CAST(nodep->rhsp(), Const)) { if (constp->isZero()) { @@ -1779,7 +1782,7 @@ private: } }; - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doExpensive) { //cout<dumpTree(cout, "ssin: "); @@ -1788,7 +1791,7 @@ private: // SENTREE(... SENITEM(x), SENGATE(SENITEM(x),*) ...) => SENITEM(x) // Do we need the SENITEM's to be identical? No because we're - // ORing between them; we just need to insure that the result is at + // ORing between them; we just need to ensure that the result is at // least as frequently activating. So we simply // SENGATE(SENITEM(x)) -> SENITEM(x), then let it collapse with the // other SENITEM(x). @@ -1890,17 +1893,17 @@ private: //----- // Zero elimination - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doNConst && replaceNodeAssign(nodep)) return; } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // Don't perform any optimizations, keep the alias around } - virtual void visit(AstAssignVarScope* nodep) { + virtual void visit(AstAssignVarScope* nodep) VL_OVERRIDE { // Don't perform any optimizations, the node won't be linked yet } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doNConst && replaceNodeAssign(nodep)) return; AstNodeVarRef* varrefp = VN_CAST(nodep->lhsp(), VarRef); // Not VarXRef, as different refs may set different values to each hierarchy @@ -1927,7 +1930,7 @@ private: } } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doNConst) { if (const AstConst* constp = VN_CAST(nodep->condp(), Const)) { @@ -2006,7 +2009,7 @@ private: } } - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { // DISPLAY(SFORMAT(text1)),DISPLAY(SFORMAT(text2)) -> DISPLAY(SFORMAT(text1+text2)) iterateChildren(nodep); if (stmtDisplayDisplay(nodep)) return; @@ -2051,7 +2054,7 @@ private: VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); return true; } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { // Substitute constants into displays. The main point of this is to // simplify assertion methodologies which call functions with display's. // This eliminates a pile of wide temps, and makes the C a whole lot more readable. @@ -2114,17 +2117,17 @@ private: } } - virtual void visit(AstFuncRef* nodep) { + virtual void visit(AstFuncRef* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_params) { // Only parameters force us to do constant function call propagation replaceWithSimulation(nodep); } } - virtual void visit(AstArg* nodep) { + virtual void visit(AstArg* nodep) VL_OVERRIDE { // replaceWithSimulation on the Arg's parent FuncRef replaces these iterateChildren(nodep); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { bool oldHasJumpGo = m_hasJumpGo; m_hasJumpGo = false; { @@ -2150,19 +2153,19 @@ private: } } } - virtual void visit(AstInitArray* nodep) { + virtual void visit(AstInitArray* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstInitItem* nodep) { + virtual void visit(AstInitItem* nodep) VL_OVERRIDE { iterateChildren(nodep); } // These are converted by V3Param. Don't constify as we don't want the // from() VARREF to disappear, if any. // If output of a presel didn't get consted, chances are V3Param didn't visit properly - virtual void visit(AstNodePreSel* nodep) {} + virtual void visit(AstNodePreSel* nodep) VL_OVERRIDE {} // Ignored, can eliminate early - virtual void visit(AstSysIgnore* nodep) { + virtual void visit(AstSysIgnore* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_doNConst) { VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); @@ -2170,7 +2173,7 @@ private: } // Simplify - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->cvtRangeConst(); } @@ -2178,7 +2181,7 @@ private: //----- // Jump elimination - virtual void visit(AstJumpGo* nodep) { + virtual void visit(AstJumpGo* nodep) VL_OVERRIDE { iterateChildren(nodep); m_hasJumpGo = true; if (m_doExpensive) { @@ -2197,7 +2200,7 @@ private: } } - virtual void visit(AstJumpLabel* nodep) { + virtual void visit(AstJumpLabel* nodep) VL_OVERRIDE { // Because JumpLabels disable many optimizations, // remove JumpLabels that are not pointed to by any AstJumpGos // Note this assumes all AstJumpGos are underneath the given label; V3Broken asserts this @@ -2543,7 +2546,7 @@ private: // Note we can't convert EqCase/NeqCase to Eq/Neq here because that would break 3'b1x1==3'b101 //----- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate if (m_required) { if (VN_IS(nodep, NodeDType) || VN_IS(nodep, Range)) { diff --git a/src/V3Coverage.cpp b/src/V3Coverage.cpp index bdd8bb914..c1f8ef3e7 100644 --- a/src/V3Coverage.cpp +++ b/src/V3Coverage.cpp @@ -149,17 +149,21 @@ private: +"_"+type; } // VISITORS - BOTH - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - m_inModOff = nodep->isTop(); // Ignore coverage on top module; it's a shell we created - m_fileps.clear(); - iterateChildren(nodep); - m_modp = NULL; - m_inModOff = true; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + bool origInModOff = m_inModOff; + { + m_modp = nodep; + m_inModOff = nodep->isTop(); // Ignore coverage on top module; it's a shell we created + m_fileps.clear(); + iterateChildren(nodep); + } + m_modp = origModp; + m_inModOff = origInModOff; } // VISITORS - TOGGLE COVERAGE - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { bool oldtog = m_inToggleOff; { m_inToggleOff = true; @@ -167,7 +171,7 @@ private: } m_inToggleOff = oldtog; } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_modp && !m_inModOff && !m_inToggleOff && nodep->fileline()->coverageOn() && v3Global.opt.coverageToggle()) { @@ -303,7 +307,7 @@ private: } // VISITORS - LINE COVERAGE - virtual void visit(AstIf* nodep) { // Note not AstNodeIf; other types don't get covered + virtual void visit(AstIf* nodep) VL_OVERRIDE { // Note not AstNodeIf; other types don't get covered UINFO(4," IF: "<fileline()->coverageOn() && v3Global.opt.coverageLine()) { @@ -353,7 +357,7 @@ private: m_checkBlock = true; // Reset as a child may have cleared it } } - virtual void visit(AstCover* nodep) { + virtual void visit(AstCover* nodep) VL_OVERRIDE { UINFO(4," COVER: "<pragType() == AstPragmaType::COVERAGE_BLOCK_OFF) { // Skip all NEXT nodes under this block, and skip this if/case branch UINFO(4," OFF: "<modp()->user1Inc(-1); } //----- - virtual void visit(AstNodeMath* nodep) {} // Accelerate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -133,20 +133,23 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - if (!nodep->dead()) { - iterateChildren(nodep); - checkAll(nodep); + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + if (!nodep->dead()) { + iterateChildren(nodep); + checkAll(nodep); + } } - m_modp = NULL; + m_modp = origModp; } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->scopep()) nodep->scopep()->user1Inc(); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->aboveScopep()) nodep->aboveScopep()->user1Inc(); @@ -155,14 +158,14 @@ private: m_scopesp.push_back(nodep); } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); m_cellsp.push_back(nodep); nodep->modp()->user1Inc(); } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->varScopep()) { @@ -177,7 +180,7 @@ private: else nodep->packagep()->user1Inc(); } } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->packagep()) { @@ -185,7 +188,7 @@ private: else nodep->packagep()->user1Inc(); } } - virtual void visit(AstRefDType* nodep) { + virtual void visit(AstRefDType* nodep) VL_OVERRIDE { iterateChildren(nodep); checkDType(nodep); checkAll(nodep); @@ -194,12 +197,12 @@ private: else nodep->packagep()->user1Inc(); } } - virtual void visit(AstNodeDType* nodep) { + virtual void visit(AstNodeDType* nodep) VL_OVERRIDE { iterateChildren(nodep); checkDType(nodep); checkAll(nodep); } - virtual void visit(AstEnumItemRef* nodep) { + virtual void visit(AstEnumItemRef* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->packagep()) { @@ -208,7 +211,7 @@ private: } checkAll(nodep); } - virtual void visit(AstModport* nodep) { + virtual void visit(AstModport* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_elimCells) { if (!nodep->varsp()) { @@ -218,7 +221,7 @@ private: } checkAll(nodep); } - virtual void visit(AstTypedef* nodep) { + virtual void visit(AstTypedef* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_elimCells && !nodep->attrPublic()) { VL_DO_DANGLING(pushDeletep(nodep->unlinkFrBack()), nodep); @@ -229,7 +232,7 @@ private: // Normal modules may disappear, e.g. if they are parameterized then removed if (nodep->attrPublic() && m_modp && VN_IS(m_modp, Package)) m_modp->user1Inc(); } - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->scopep()) nodep->scopep()->user1Inc(); @@ -237,7 +240,7 @@ private: m_vscsp.push_back(nodep); } } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { iterateChildren(nodep); checkAll(nodep); if (nodep->isSigPublic() && m_modp && VN_IS(m_modp, Package)) m_modp->user1Inc(); @@ -245,7 +248,7 @@ private: m_varsp.push_back(nodep); } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { // See if simple assignments to variables may be eliminated because // that variable is never used. // Similar code in V3Life @@ -265,7 +268,7 @@ private: } //----- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { if (nodep->isOutputter()) m_sideEffect = true; iterateChildren(nodep); checkAll(nodep); diff --git a/src/V3Delayed.cpp b/src/V3Delayed.cpp index 7844db7bd..75ac8f17c 100644 --- a/src/V3Delayed.cpp +++ b/src/V3Delayed.cpp @@ -348,22 +348,22 @@ private: } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { //VV***** We reset all userp() on the netlist m_modVarMap.clear(); iterateChildren(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(4," MOD "<hasInitial(); @@ -371,7 +371,7 @@ private: iterateChildren(nodep); m_inInitial = oldinit; } - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { m_inDly = true; m_nextDlyp = VN_CAST(nodep->nextp(), AssignDly); // Next assignment in same block, maybe NULL. if (m_cfuncp) nodep->v3error("Unsupported: Delayed assignment inside public function/task"); @@ -395,7 +395,7 @@ private: m_nextDlyp = NULL; } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (!nodep->user2Inc()) { // Not done yet if (m_inDly && nodep->lvalue()) { UINFO(4,"AssignDlyVar: "<v3fatalSrc("For statements should have been converted to while statements in V3Begin"); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { bool oldloop = m_inLoop; m_inLoop = true; iterateChildren(nodep); @@ -456,7 +456,7 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Depth.cpp b/src/V3Depth.cpp index 51e1f07a0..59fb8214a 100644 --- a/src/V3Depth.cpp +++ b/src/V3Depth.cpp @@ -82,14 +82,17 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<isStatement()) { iterateChildren(nodep); } else { @@ -111,9 +114,9 @@ private: } } // Operators - virtual void visit(AstNodeTermop* nodep) { + virtual void visit(AstNodeTermop* nodep) VL_OVERRIDE { } - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { // We have some operator defines that use 2 parens, so += 2. m_depth += 2; if (m_depth>m_maxdepth) m_maxdepth = m_depth; @@ -140,19 +143,19 @@ private: m_funcp->isStatic(false); } } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { needNonStaticFunc(nodep); iterateChildren(nodep); } - virtual void visit(AstUCStmt* nodep) { + virtual void visit(AstUCStmt* nodep) VL_OVERRIDE { needNonStaticFunc(nodep); visitStmt(nodep); } //-------------------- // Default: Just iterate - virtual void visit(AstVar* nodep) {} // Don't hit varrefs under vars - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} // Don't hit varrefs under vars + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3DepthBlock.cpp b/src/V3DepthBlock.cpp index 4a9abc27d..f924703e0 100644 --- a/src/V3DepthBlock.cpp +++ b/src/V3DepthBlock.cpp @@ -71,14 +71,17 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<isStatement()) { iterateChildren(nodep); } else { @@ -114,11 +117,11 @@ private: } } - virtual void visit(AstNodeMath* nodep) {} // Accelerate + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} // Accelerate //-------------------- // Default: Just iterate - virtual void visit(AstVar* nodep) {} // Don't hit varrefs under vars - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} // Don't hit varrefs under vars + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Descope.cpp b/src/V3Descope.cpp index 5d49b29c0..5a1635586 100644 --- a/src/V3Descope.cpp +++ b/src/V3Descope.cpp @@ -44,18 +44,18 @@ private: // NODE STATE // Cleared entire netlist // AstCFunc::user() // bool. Indicates processing completed - AstUser1InUse m_inuser1; + AstUser1InUse m_inuser1; // TYPES - typedef std::multimap FuncMmap; + typedef std::multimap FuncMmap; // STATE - AstNodeModule* m_modp; // Current module - AstScope* m_scopep; // Current scope - bool m_modSingleton; // m_modp is only instanced once - bool m_allowThis; // Allow function non-static - bool m_needThis; // Make function non-static - FuncMmap m_modFuncs; // Name of public functions added + AstNodeModule* m_modp; // Current module + AstScope* m_scopep; // Current scope + bool m_modSingleton; // m_modp is only instanced once + bool m_allowThis; // Allow function non-static + bool m_needThis; // Make function non-static + FuncMmap m_modFuncs; // Name of public functions added // METHODS VL_DEBUG_FUNC; // Declare debug() @@ -63,7 +63,7 @@ private: static bool modIsSingleton(AstNodeModule* modp) { // True iff there's exactly one instance of this module in the design. int instances = 0; - for (AstNode* stmtp = modp->stmtsp(); stmtp; stmtp=stmtp->nextp()) { + for (AstNode* stmtp = modp->stmtsp(); stmtp; stmtp = stmtp->nextp()) { if (VN_IS(stmtp, Scope)) { if (++instances > 1) { return false; } } @@ -81,8 +81,7 @@ private: // Sets 'hierThisr' true if the object is local to this scope // (and could be made into a function-local later in V3Localize), // false if the object is in another scope. - string descopedName(const AstScope* scopep, bool& hierThisr, - const AstVar* varp=NULL) { + string descopedName(const AstScope* scopep, bool& hierThisr, const AstVar* varp = NULL) { UASSERT(scopep, "Var/Func not scoped"); hierThisr = (scopep == m_scopep); @@ -97,7 +96,6 @@ private: // // Static functions can't use this if (!m_allowThis) relativeRefOk = false; - // // Use absolute refs in top-scoped routines, keep them static. // The DPI callback registration depends on representing top-level @@ -106,18 +104,15 @@ private: // // V3Combine wouldn't likely be able to combine top-level // routines anyway, so there's no harm in keeping these static. - if (m_modp->isTop()) { - relativeRefOk = false; - } + UASSERT_OBJ(m_modp, scopep, "Scope not under module"); + if (m_modp->isTop()) relativeRefOk = false; // // Use absolute refs if this scope is the only instance of the module. // Saves a bit of overhead on passing the 'this' pointer, and there's no // need to be nice to V3Combine when we have only a single instance. // The risk that this prevents combining identical logic from differently- // named but identical modules seems low. - if (m_modSingleton) { - relativeRefOk = false; - } + if (m_modSingleton) relativeRefOk = false; if (varp && varp->isFuncLocal()) { hierThisr = true; @@ -130,23 +125,21 @@ private: // Reference to scope of cell directly under this module, can just "cell->" string name = scopep->name(); string::size_type pos; - if ((pos = name.rfind('.')) != string::npos) { - name.erase(0, pos+1); - } + if ((pos = name.rfind('.')) != string::npos) name.erase(0, pos + 1); m_needThis = true; - return name+"->"; + return name + "->"; } else { // Reference to something elsewhere, or relative references // are disabled. Use global variable - UINFO(8," Descope "<name()<name()<name() << endl); + UINFO(8, " under " << m_scopep->name() << endl); if (!scopep->aboveScopep()) { // Top // We could also return "vlSymsp->TOPp->" here, but GCC would // suspect aliases. return "vlTOPp->"; } else { - return scopep->nameVlSym()+"."; + return scopep->nameVlSym() + "."; } } } @@ -155,64 +148,64 @@ private: // We recorded all public functions in m_modFuncs. // If for any given name only one function exists, we can use that function directly. // If multiple functions exist, we need to select the appropriate scope. - for (FuncMmap::iterator it = m_modFuncs.begin(); it!=m_modFuncs.end(); ++it) { + for (FuncMmap::iterator it = m_modFuncs.begin(); it != m_modFuncs.end(); ++it) { string name = it->first; AstCFunc* topFuncp = it->second; - FuncMmap::iterator nextIt1 = it; ++nextIt1; - bool moreOfSame1 = (nextIt1!=m_modFuncs.end() && nextIt1->first == name); + FuncMmap::iterator nextIt1 = it; + ++nextIt1; + bool moreOfSame1 = (nextIt1 != m_modFuncs.end() && nextIt1->first == name); if (moreOfSame1) { // Multiple functions under this name, need a wrapper function - UINFO(6," Wrapping "<cloneTree(false); - if (newfuncp->initsp()) newfuncp->initsp()->unlinkFrBackWithNext()->deleteTree(); - if (newfuncp->stmtsp()) newfuncp->stmtsp()->unlinkFrBackWithNext()->deleteTree(); + if (newfuncp->initsp()) newfuncp->initsp()->unlinkFrBackWithNext()->deleteTree(); + if (newfuncp->stmtsp()) newfuncp->stmtsp()->unlinkFrBackWithNext()->deleteTree(); if (newfuncp->finalsp()) newfuncp->finalsp()->unlinkFrBackWithNext()->deleteTree(); newfuncp->name(name); newfuncp->isStatic(false); newfuncp->addInitsp( new AstCStmt(newfuncp->fileline(), - EmitCBaseVisitor::symClassVar()+" = this->__VlSymsp;\n")); - newfuncp->addInitsp(new AstCStmt(newfuncp->fileline(), - EmitCBaseVisitor::symTopAssign()+"\n")); + EmitCBaseVisitor::symClassVar() + " = this->__VlSymsp;\n")); + newfuncp->addInitsp( + new AstCStmt(newfuncp->fileline(), EmitCBaseVisitor::symTopAssign() + "\n")); topFuncp->addNextHere(newfuncp); // In the body, call each function if it matches the given scope for (FuncMmap::iterator eachIt = it; - eachIt != m_modFuncs.end() && eachIt->first==name; ++eachIt) { + eachIt != m_modFuncs.end() && eachIt->first == name; ++eachIt) { it = eachIt; AstCFunc* funcp = eachIt->second; - FuncMmap::iterator nextIt2 = eachIt; ++nextIt2; - bool moreOfSame = (nextIt2!=m_modFuncs.end() && nextIt2->first == name); + FuncMmap::iterator nextIt2 = eachIt; + ++nextIt2; + bool moreOfSame = (nextIt2 != m_modFuncs.end() && nextIt2->first == name); UASSERT_OBJ(funcp->scopep(), funcp, "Not scoped"); - UINFO(6," Wrapping "<argTypes()<<" und "<argTypes()<argTypes() + << " und " << funcp->argTypes() << endl); funcp->declPrivate(true); AstNode* argsp = NULL; - for (AstNode* stmtp = newfuncp->argsp(); stmtp; stmtp=stmtp->nextp()) { + for (AstNode* stmtp = newfuncp->argsp(); stmtp; stmtp = stmtp->nextp()) { if (AstVar* portp = VN_CAST(stmtp, Var)) { if (portp->isIO() && !portp->isFuncReturn()) { - AstNode* newp = new AstVarRef(portp->fileline(), - portp, portp->isWritable()); - if (argsp) argsp = argsp->addNextNull(newp); - else argsp = newp; + AstNode* newp + = new AstVarRef(portp->fileline(), portp, portp->isWritable()); + argsp = argsp ? argsp->addNextNull(newp) : newp; } } } - AstNode* returnp = new AstCReturn(funcp->fileline(), - new AstCCall(funcp->fileline(), - funcp, argsp)); + AstNode* returnp = new AstCReturn( + funcp->fileline(), new AstCCall(funcp->fileline(), funcp, argsp)); if (moreOfSame) { - AstIf* ifp = new AstIf(funcp->fileline(), - new AstEq(funcp->fileline(), - new AstCMath(funcp->fileline(), - "this", 64), - new AstCMath(funcp->fileline(), - string("&(") - +funcp->scopep()->nameVlSym() - +")", 64)), - returnp, NULL); + AstIf* ifp = new AstIf( + funcp->fileline(), + new AstEq( + funcp->fileline(), new AstCMath(funcp->fileline(), "this", 64), + new AstCMath(funcp->fileline(), + string("&(") + funcp->scopep()->nameVlSym() + ")", + 64)), + returnp, NULL); newfuncp->addStmtsp(ifp); } else { newfuncp->addStmtsp(returnp); @@ -220,68 +213,70 @@ private: } // Not really any way the user could do this, and we'd need // to come up with some return value - //newfuncp->addStmtsp(new AstDisplay(newfuncp->fileline(), + // newfuncp->addStmtsp(new AstDisplay(newfuncp->fileline(), // AstDisplayType::DT_WARNING, - // string("%%Error: ")+name+"() called with bad scope", NULL)); - //newfuncp->addStmtsp(new AstStop(newfuncp->fileline())); - if (debug()>=9) newfuncp->dumpTree(cout, " newfunc: "); + // string("%%Error: ")+name+"() called with bad + // scope", NULL)); + // newfuncp->addStmtsp(new AstStop(newfuncp->fileline())); + if (debug() >= 9) newfuncp->dumpTree(cout, " newfunc: "); } else { // Only a single function under this name, we can simply rename it - UINFO(6," Wrapping "<name(name); } } } // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - m_modFuncs.clear(); - m_modSingleton = modIsSingleton(m_modp); - iterateChildren(nodep); - makePublicFuncWrappers(); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + m_modFuncs.clear(); + m_modSingleton = modIsSingleton(m_modp); + iterateChildren(nodep); + makePublicFuncWrappers(); + } + m_modp = origModp; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { m_scopep = nodep; iterateChildren(nodep); m_scopep = NULL; } - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { // Delete the varscope when we're finished nodep->unlinkFrBack(); pushDeletep(nodep); } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { iterateChildren(nodep); // Convert the hierch name UASSERT_OBJ(m_scopep, nodep, "Node not under scope"); bool hierThis; - nodep->hiername(descopedName(nodep->varScopep()->scopep(), hierThis/*ref*/, + nodep->hiername(descopedName(nodep->varScopep()->scopep(), hierThis /*ref*/, nodep->varScopep()->varp())); nodep->hierThis(hierThis); nodep->varScopep(NULL); } - virtual void visit(AstCCall* nodep) { - //UINFO(9," "<funcp()->scopep(), nodep, "CFunc not under scope"); bool hierThis; - nodep->hiername(descopedName(nodep->funcp()->scopep(), hierThis/*ref*/)); + nodep->hiername(descopedName(nodep->funcp()->scopep(), hierThis /*ref*/)); // Can't do this, as we may have more calls later // nodep->funcp()->scopep(NULL); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!nodep->user1()) { m_needThis = false; m_allowThis = nodep->isStatic().falseU(); // Non-static or unknown if static iterateChildren(nodep); nodep->user1(true); - if (m_needThis) { - nodep->isStatic(false); - } + if (m_needThis) nodep->isStatic(false); // If it's under a scope, move it up to the top if (m_scopep) { nodep->unlinkFrBack(); @@ -291,23 +286,22 @@ private: // There may be multiple public functions by the same name; // record for later correction or making of shells m_modFuncs.insert(make_pair(nodep->name(), nodep)); - nodep->name(m_scopep->nameDotless() +"__" + nodep->name()); + nodep->name(m_scopep->nameDotless() + "__" + nodep->name()); } } } } - virtual void visit(AstVar*) {} - virtual void visit(AstNode* nodep) { - iterateChildren(nodep); - } + virtual void visit(AstVar*) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } + public: // CONSTRUCTORS explicit DescopeVisitor(AstNetlist* nodep) - : m_modp(NULL), - m_scopep(NULL), - m_modSingleton(false), - m_allowThis(false), - m_needThis(false) { + : m_modp(NULL) + , m_scopep(NULL) + , m_modSingleton(false) + , m_allowThis(false) + , m_needThis(false) { iterate(nodep); } virtual ~DescopeVisitor() {} diff --git a/src/V3EmitC.cpp b/src/V3EmitC.cpp index fbf661d19..4986c4a45 100644 --- a/src/V3EmitC.cpp +++ b/src/V3EmitC.cpp @@ -150,8 +150,62 @@ public: } } + struct CmpName { + inline bool operator()(const AstNode* lhsp, const AstNode* rhsp) const { + return lhsp->name() < rhsp->name(); + } + }; + void emitIntFuncDecls(AstNodeModule* modp) { + typedef std::vector FuncVec; + FuncVec funcsp; + + for (AstNode* nodep = modp->stmtsp(); nodep; nodep = nodep->nextp()) { + if (const AstCFunc* funcp = VN_CAST(nodep, CFunc)) { + if (!funcp->skipDecl()) { funcsp.push_back(funcp); } + } + } + + stable_sort(funcsp.begin(), funcsp.end(), CmpName()); + + for (FuncVec::iterator it = funcsp.begin(); it != funcsp.end(); ++it) { + const AstCFunc* funcp = *it; + if (!funcp->dpiImport()) { // DPI is prototyped in __Dpi.h + ofp()->putsPrivate(funcp->declPrivate()); + if (!funcp->ifdef().empty()) puts("#ifdef " + funcp->ifdef() + "\n"); + if (funcp->isStatic().trueU()) puts("static "); + puts(funcp->rtnTypeVoid()); + puts(" "); + puts(funcp->nameProtect()); + puts("(" + cFuncArgs(funcp) + ")"); + if (funcp->slow()) puts(" VL_ATTR_COLD"); + puts(";\n"); + if (!funcp->ifdef().empty()) puts("#endif // " + funcp->ifdef() + "\n"); + } + } + + if (modp->isTop() && v3Global.opt.mtasks()) { + // Emit the mtask func prototypes. + AstExecGraph* execGraphp = v3Global.rootp()->execGraphp(); + UASSERT_OBJ(execGraphp, v3Global.rootp(), "Root should have an execGraphp"); + const V3Graph* depGraphp = execGraphp->depGraphp(); + for (const V3GraphVertex* vxp = depGraphp->verticesBeginp(); vxp; + vxp = vxp->verticesNextp()) { + const ExecMTask* mtp = dynamic_cast(vxp); + if (mtp->threadRoot()) { + // Emit function declaration for this mtask + ofp()->putsPrivate(true); + puts("static void "); + puts(protect(mtp->cFuncName())); + puts("(bool even_cycle, void* symtab);\n"); + } + } + // No AstCFunc for this one, as it's synthetic. Just write it: + puts("static void __Vmtask__final(bool even_cycle, void* symtab);\n"); + } + } + // VISITORS - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { bool paren = true; bool decind = false; if (AstSel* selp = VN_CAST(nodep->lhsp(), Sel)) { if (selp->widthMin()==1) { @@ -175,6 +229,14 @@ public: iterateAndNextNull(selp->lsbp()); puts(", "); iterateAndNextNull(selp->fromp()); puts(", "); } + } else if (AstGetcRefN* selp = VN_CAST(nodep->lhsp(), GetcRefN)) { + iterateAndNextNull(selp->lhsp()); + puts(" = "); + putbs("VL_PUTC_N("); + iterateAndNextNull(selp->lhsp()); + puts(", "); + iterateAndNextNull(selp->rhsp()); + puts(", "); } else if (AstVar* varp = AstVar::scVarRecurse(nodep->lhsp())) { putbs("VL_ASSIGN_"); // Set a systemC variable emitScIQW(varp); @@ -216,9 +278,9 @@ public: if (decind) ofp()->blockDec(); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstAlwaysPublic*) { + virtual void visit(AstAlwaysPublic*) VL_OVERRIDE { } - virtual void visit(AstAssocSel* nodep) { + virtual void visit(AstAssocSel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); putbs(".at("); AstAssocArrayDType* adtypep = VN_CAST(nodep->fromp()->dtypep(), AssocArrayDType); @@ -239,7 +301,7 @@ public: puts(".data()"); // Access returned std::array as C array } } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { puts(nodep->hiernameProtect()); puts(nodep->funcp()->nameProtect()); puts("("); @@ -257,7 +319,7 @@ public: puts(");\n"); } } - virtual void visit(AstCMethodHard* nodep) { + virtual void visit(AstCMethodHard* nodep) VL_OVERRIDE { iterate(nodep->fromp()); puts("."); puts(nodep->nameProtect()); @@ -274,15 +336,15 @@ public: UASSERT_OBJ(!nodep->isStatement() || VN_IS(nodep->dtypep(), VoidDType), nodep, "Statement of non-void data type"); } - virtual void visit(AstIntfRef* nodep) { + virtual void visit(AstIntfRef* nodep) VL_OVERRIDE { putsQuoted(VIdProtect::protectWordsIf(AstNode::vcdName(nodep->name()), nodep->protect())); } - virtual void visit(AstNodeCase* nodep) { + virtual void visit(AstNodeCase* nodep) VL_OVERRIDE { // In V3Case... nodep->v3fatalSrc("Case statements should have been reduced out"); } - virtual void visit(AstComment* nodep) { + virtual void visit(AstComment* nodep) VL_OVERRIDE { string at; if (nodep->showAt()) { at = " at "+nodep->fileline()->ascii(); @@ -294,7 +356,7 @@ public: } iterateChildren(nodep); } - virtual void visit(AstCoverDecl* nodep) { + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE { puts("__vlCoverInsert("); // As Declared in emitCoverageDecl puts("&(vlSymsp->__Vcoverage["); puts(cvtToStr(nodep->dataDeclThisp()->binNum())); puts("])"); @@ -313,22 +375,22 @@ public: puts(", "); putsQuoted(protectWordsIf(nodep->comment(), nodep->protect())); puts(");\n"); } - virtual void visit(AstCoverInc* nodep) { + virtual void visit(AstCoverInc* nodep) VL_OVERRIDE { puts("++(vlSymsp->__Vcoverage["); puts(cvtToStr(nodep->declp()->dataDeclThisp()->binNum())); puts("]);\n"); } - virtual void visit(AstCReturn* nodep) { + virtual void visit(AstCReturn* nodep) VL_OVERRIDE { puts("return ("); iterateAndNextNull(nodep->lhsp()); puts(");\n"); } - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { string text = nodep->fmtp()->text(); if (nodep->addNewline()) text += "\n"; displayNode(nodep, nodep->fmtp()->scopeNamep(), text, nodep->fmtp()->exprsp(), false); } - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { // For use under AstCCalls for dpiImports. ScopeNames under // displays are handled in AstDisplay if (!nodep->dpiExport()) { @@ -337,20 +399,20 @@ public: putbs("(&(vlSymsp->"+protect("__Vscope_"+scope)+"))"); } } - virtual void visit(AstSFormat* nodep) { + virtual void visit(AstSFormat* nodep) VL_OVERRIDE { displayNode(nodep, nodep->fmtp()->scopeNamep(), nodep->fmtp()->text(), nodep->fmtp()->exprsp(), false); } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { displayNode(nodep, nodep->scopeNamep(), nodep->text(), nodep->exprsp(), false); } - virtual void visit(AstFScanF* nodep) { + virtual void visit(AstFScanF* nodep) VL_OVERRIDE { displayNode(nodep, NULL, nodep->text(), nodep->exprsp(), true); } - virtual void visit(AstSScanF* nodep) { + virtual void visit(AstSScanF* nodep) VL_OVERRIDE { displayNode(nodep, NULL, nodep->text(), nodep->exprsp(), true); } - virtual void visit(AstValuePlusArgs* nodep) { + virtual void visit(AstValuePlusArgs* nodep) VL_OVERRIDE { puts("VL_VALUEPLUSARGS_IN"); emitIQW(nodep->outp()); puts("("); @@ -362,12 +424,12 @@ public: iterateAndNextNull(nodep->outp()); puts(")"); } - virtual void visit(AstTestPlusArgs* nodep) { + virtual void visit(AstTestPlusArgs* nodep) VL_OVERRIDE { puts("VL_TESTPLUSARGS_I("); putsQuoted(nodep->text()); puts(")"); } - virtual void visit(AstFGetS* nodep) { + virtual void visit(AstFGetS* nodep) VL_OVERRIDE { checkMaxWords(nodep); emitOpName(nodep, nodep->emitC(), nodep->lhsp(), nodep->rhsp(), NULL); } @@ -378,7 +440,7 @@ public: <<" bits exceeds hardcoded limit VL_TO_STRING_MAX_WORDS in verilatedos.h"); } } - virtual void visit(AstFOpen* nodep) { + virtual void visit(AstFOpen* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->filep()); puts(" = VL_FOPEN_"); emitIQW(nodep->filenamep()); @@ -395,7 +457,7 @@ public: iterateAndNextNull(nodep->modep()); puts(");\n"); } - virtual void visit(AstNodeReadWriteMem* nodep) { + virtual void visit(AstNodeReadWriteMem* nodep) VL_OVERRIDE { puts(nodep->cFuncPrefixp()); puts("N("); puts(nodep->isHex() ? "true" : "false"); @@ -433,14 +495,14 @@ public: if (nodep->msbp()) { iterateAndNextNull(nodep->msbp()); } else puts("~VL_ULL(0)"); puts(");\n"); } - virtual void visit(AstFClose* nodep) { + virtual void visit(AstFClose* nodep) VL_OVERRIDE { puts("VL_FCLOSE_I("); iterateAndNextNull(nodep->filep()); puts("); "); iterateAndNextNull(nodep->filep()); // For safety, so user doesn't later WRITE with it. puts(" = 0;\n"); } - virtual void visit(AstFFlush* nodep) { + virtual void visit(AstFFlush* nodep) VL_OVERRIDE { if (!nodep->filep()) { puts("fflush(stdout);\n"); } else { @@ -451,7 +513,7 @@ public: puts(")); }\n"); } } - virtual void visit(AstFSeek* nodep) { + virtual void visit(AstFSeek* nodep) VL_OVERRIDE { puts("(fseek(VL_CVT_I_FP("); iterateAndNextNull(nodep->filep()); puts("),"); @@ -460,17 +522,17 @@ public: iterateAndNextNull(nodep->operation()); puts(")==-1?-1:0)"); } - virtual void visit(AstFTell* nodep) { + virtual void visit(AstFTell* nodep) VL_OVERRIDE { puts("ftell(VL_CVT_I_FP("); iterateAndNextNull(nodep->filep()); puts("))"); } - virtual void visit(AstFRewind* nodep) { + virtual void visit(AstFRewind* nodep) VL_OVERRIDE { puts("(fseek(VL_CVT_I_FP("); iterateAndNextNull(nodep->filep()); puts("), 0, 0)==-1?-1:0)"); } - virtual void visit(AstFRead* nodep) { + virtual void visit(AstFRead* nodep) VL_OVERRIDE { puts("VL_FREAD_I("); puts(cvtToStr(nodep->memp()->widthMin())); // Need real storage width putbs(","); @@ -509,12 +571,12 @@ public: else puts(cvtToStr(array_size)); puts(");\n"); } - virtual void visit(AstSysFuncAsTask* nodep) { + virtual void visit(AstSysFuncAsTask* nodep) VL_OVERRIDE { if (!nodep->lhsp()->isWide()) puts("(void)"); iterateAndNextNull(nodep->lhsp()); if (!nodep->lhsp()->isWide()) puts(";"); } - virtual void visit(AstSystemT* nodep) { + virtual void visit(AstSystemT* nodep) VL_OVERRIDE { puts("(void)VL_SYSTEM_I"); emitIQW(nodep->lhsp()); puts("("); @@ -526,7 +588,7 @@ public: iterateAndNextNull(nodep->lhsp()); puts(");\n"); } - virtual void visit(AstSystemF* nodep) { + virtual void visit(AstSystemF* nodep) VL_OVERRIDE { puts("VL_SYSTEM_I"); emitIQW(nodep->lhsp()); puts("("); @@ -538,17 +600,17 @@ public: iterateAndNextNull(nodep->lhsp()); puts(")"); } - virtual void visit(AstJumpGo* nodep) { + virtual void visit(AstJumpGo* nodep) VL_OVERRIDE { puts("goto __Vlabel"+cvtToStr(nodep->labelp()->labelNum())+";\n"); } - virtual void visit(AstJumpLabel* nodep) { + virtual void visit(AstJumpLabel* nodep) VL_OVERRIDE { nodep->labelNum(++m_labelNum); puts("{\n"); // Make it visually obvious label jumps outside these iterateAndNextNull(nodep->stmtsp()); puts("}\n"); puts("__Vlabel"+cvtToStr(nodep->labelNum())+": ;\n"); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->precondsp()); puts("while ("); iterateAndNextNull(nodep->condp()); @@ -558,7 +620,7 @@ public: iterateAndNextNull(nodep->precondsp()); // Need to recompute before next loop puts("}\n"); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { puts("if ("); if (!nodep->branchPred().unknown()) { puts(nodep->branchPred().ascii()); puts("("); @@ -573,7 +635,7 @@ public: } puts("}\n"); } - virtual void visit(AstStop* nodep) { + virtual void visit(AstStop* nodep) VL_OVERRIDE { puts("VL_STOP_MT("); putsQuoted(protect(nodep->fileline()->filename())); puts(", "); @@ -581,41 +643,41 @@ public: puts(", \"\""); puts(");\n"); } - virtual void visit(AstFinish* nodep) { + virtual void visit(AstFinish* nodep) VL_OVERRIDE { puts("VL_FINISH_MT("); putsQuoted(protect(nodep->fileline()->filename())); puts(", "); puts(cvtToStr(nodep->fileline()->lineno())); puts(", \"\");\n"); } - virtual void visit(AstText* nodep) { + virtual void visit(AstNodeSimpleText* nodep) VL_OVERRIDE { if (nodep->tracking() || m_trackText) { puts(nodep->text()); } else { ofp()->putsNoTracking(nodep->text()); } } - virtual void visit(AstTextBlock* nodep) { - visit(VN_CAST(nodep, Text)); + virtual void visit(AstTextBlock* nodep) VL_OVERRIDE { + visit(VN_CAST(nodep, NodeSimpleText)); for (AstNode* childp = nodep->nodesp(); childp; childp = childp->nextp()) { iterate(childp); if (nodep->commas() && childp->nextp()) puts(", "); } } - virtual void visit(AstCStmt* nodep) { + virtual void visit(AstCStmt* nodep) VL_OVERRIDE { putbs(""); iterateAndNextNull(nodep->bodysp()); } - virtual void visit(AstCMath* nodep) { + virtual void visit(AstCMath* nodep) VL_OVERRIDE { putbs(""); iterateAndNextNull(nodep->bodysp()); } - virtual void visit(AstUCStmt* nodep) { + virtual void visit(AstUCStmt* nodep) VL_OVERRIDE { putsDecoration(ifNoProtect("// $c statement at "+nodep->fileline()->ascii()+"\n")); iterateAndNextNull(nodep->bodysp()); puts("\n"); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { puts("\n"); putsDecoration(ifNoProtect("// $c function at "+nodep->fileline()->ascii()+"\n")); iterateAndNextNull(nodep->bodysp()); @@ -623,10 +685,10 @@ public: } // Operators - virtual void visit(AstNodeTermop* nodep) { + virtual void visit(AstNodeTermop* nodep) VL_OVERRIDE { emitOpName(nodep, nodep->emitC(), NULL, NULL, NULL); } - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { if (emitSimpleOk(nodep)) { putbs("("); puts(nodep->emitSimpleOperator()); puts(" "); iterateAndNextNull(nodep->lhsp()); puts(")"); @@ -634,7 +696,7 @@ public: emitOpName(nodep, nodep->emitC(), nodep->lhsp(), NULL, NULL); } } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { if (emitSimpleOk(nodep)) { putbs("("); iterateAndNextNull(nodep->lhsp()); puts(" "); putbs(nodep->emitSimpleOperator()); puts(" "); @@ -643,11 +705,11 @@ public: emitOpName(nodep, nodep->emitC(), nodep->lhsp(), nodep->rhsp(), NULL); } } - virtual void visit(AstNodeTriop* nodep) { + virtual void visit(AstNodeTriop* nodep) VL_OVERRIDE { UASSERT_OBJ(!emitSimpleOk(nodep), nodep, "Triop cannot be described in a simple way"); emitOpName(nodep, nodep->emitC(), nodep->lhsp(), nodep->rhsp(), nodep->thsp()); } - virtual void visit(AstRedXor* nodep) { + virtual void visit(AstRedXor* nodep) VL_OVERRIDE { if (nodep->lhsp()->isWide()) { visit(VN_CAST(nodep, NodeUniop)); } else { @@ -658,42 +720,42 @@ public: puts(")"); } } - virtual void visit(AstMulS* nodep) { + virtual void visit(AstMulS* nodep) VL_OVERRIDE { if (nodep->widthWords() > VL_MULS_MAX_WORDS) { nodep->v3error("Unsupported: Signed multiply of "<width() <<" bits exceeds hardcoded limit VL_MULS_MAX_WORDS in verilatedos.h"); } visit(VN_CAST(nodep, NodeBiop)); } - virtual void visit(AstPow* nodep) { + virtual void visit(AstPow* nodep) VL_OVERRIDE { if (nodep->widthWords() > VL_MULS_MAX_WORDS) { nodep->v3error("Unsupported: Power of "<width() <<" bits exceeds hardcoded limit VL_MULS_MAX_WORDS in verilatedos.h"); } visit(VN_CAST(nodep, NodeBiop)); } - virtual void visit(AstPowSS* nodep) { + virtual void visit(AstPowSS* nodep) VL_OVERRIDE { if (nodep->widthWords() > VL_MULS_MAX_WORDS) { nodep->v3error("Unsupported: Power of "<width() <<" bits exceeds hardcoded limit VL_MULS_MAX_WORDS in verilatedos.h"); } visit(VN_CAST(nodep, NodeBiop)); } - virtual void visit(AstPowSU* nodep) { + virtual void visit(AstPowSU* nodep) VL_OVERRIDE { if (nodep->widthWords() > VL_MULS_MAX_WORDS) { nodep->v3error("Unsupported: Power of "<width() <<" bits exceeds hardcoded limit VL_MULS_MAX_WORDS in verilatedos.h"); } visit(VN_CAST(nodep, NodeBiop)); } - virtual void visit(AstPowUS* nodep) { + virtual void visit(AstPowUS* nodep) VL_OVERRIDE { if (nodep->widthWords() > VL_MULS_MAX_WORDS) { nodep->v3error("Unsupported: Power of "<width() <<" bits exceeds hardcoded limit VL_MULS_MAX_WORDS in verilatedos.h"); } visit(VN_CAST(nodep, NodeBiop)); } - virtual void visit(AstCCast* nodep) { + virtual void visit(AstCCast* nodep) VL_OVERRIDE { // Extending a value of the same word width is just a NOP. if (nodep->size() <= VL_IDATASIZE) { puts("(IData)("); @@ -703,7 +765,7 @@ public: iterateAndNextNull(nodep->lhsp()); puts(")"); } - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { // Widths match up already, so we'll just use C++'s operator w/o any temps. if (nodep->expr1p()->isWide()) { emitOpName(nodep, nodep->emitC(), nodep->condp(), nodep->expr1p(), nodep->expr2p()); @@ -714,16 +776,16 @@ public: iterateAndNextNull(nodep->expr2p()); puts(")"); } } - virtual void visit(AstNew* nodep) { + virtual void visit(AstNew* nodep) VL_OVERRIDE { puts("std::make_shared<" + nodep->dtypep()->nameProtect() + ">("); iterateChildren(nodep); puts(")"); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { // Note ASSIGN checks for this on a LHS emitOpName(nodep, nodep->emitC(), nodep->fromp(), nodep->lsbp(), nodep->thsp()); } - virtual void visit(AstReplicate* nodep) { + virtual void visit(AstReplicate* nodep) VL_OVERRIDE { if (nodep->lhsp()->widthMin() == 1 && !nodep->isWide()) { UASSERT_OBJ((static_cast(VN_CAST(nodep->rhsp(), Const)->toUInt()) * nodep->lhsp()->widthMin()) == nodep->widthMin(), @@ -741,7 +803,7 @@ public: emitOpName(nodep, nodep->emitC(), nodep->lhsp(), nodep->rhsp(), NULL); } } - virtual void visit(AstStreamL* nodep) { + virtual void visit(AstStreamL* nodep) VL_OVERRIDE { // Attempt to use a "fast" stream function for slice size = power of 2 if (!nodep->isWide()) { uint32_t isPow2 = VN_CAST(nodep->rhsp(), Const)->num().countOnes() == 1; @@ -765,7 +827,7 @@ public: nodep->lhsp(), nodep->rhsp(), NULL); } // Terminals - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { puts(nodep->hiernameProtect()); puts(nodep->varp()->nameProtect()); } @@ -889,7 +951,7 @@ public: emitConstant(constp, NULL, assignString); puts(";\n"); } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { if (nodep->isWide()) { UASSERT_OBJ(m_wideTempRefp, nodep, "Wide Constant w/ no temp"); emitConstant(nodep, m_wideTempRefp, ""); @@ -900,27 +962,27 @@ public: } // Just iterate - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { iterateChildren(nodep); } // NOPs - virtual void visit(AstTypedef*) {} - virtual void visit(AstPragma*) {} - virtual void visit(AstCell*) {} // Handled outside the Visit class - virtual void visit(AstVar*) {} // Handled outside the Visit class - virtual void visit(AstNodeText*) {} // Handled outside the Visit class - virtual void visit(AstTraceDecl*) {} // Handled outside the Visit class - virtual void visit(AstTraceInc*) {} // Handled outside the Visit class - virtual void visit(AstCFile*) {} // Handled outside the Visit class - virtual void visit(AstCellInline*) {} // Handled outside the Visit class (EmitCSyms) + virtual void visit(AstTypedef*) VL_OVERRIDE {} + virtual void visit(AstPragma*) VL_OVERRIDE {} + virtual void visit(AstCell*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstVar*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstNodeText*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstTraceDecl*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstTraceInc*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstCFile*) VL_OVERRIDE {} // Handled outside the Visit class + virtual void visit(AstCellInline*) VL_OVERRIDE {} // Handled outside the Visit class (EmitCSyms) // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { puts(string("\n???? // ")+nodep->prettyTypeName()+"\n"); iterateChildren(nodep); nodep->v3fatalSrc("Unknown node type reached emitter: "<prettyTypeName()); @@ -1041,9 +1103,9 @@ class EmitCImp : EmitCStmts { } V3OutCFile* newOutCFile(AstNodeModule* modp, bool slow, bool source, int filenum=0) { - string filenameNoExt = v3Global.opt.makeDir()+"/"+ modClassName(modp); - if (filenum) filenameNoExt += "__"+cvtToStr(filenum); - filenameNoExt += (slow ? "__Slow":""); + string filenameNoExt = v3Global.opt.makeDir() + "/" + prefixNameProtect(modp); + if (filenum) filenameNoExt += "__" + cvtToStr(filenum); + filenameNoExt += (slow ? "__Slow" : ""); V3OutCFile* ofp = NULL; if (v3Global.opt.lintOnly()) { // Unfortunately we have some lint checks here, so we can't just skip processing. @@ -1150,11 +1212,11 @@ class EmitCImp : EmitCStmts { } } - virtual void visit(AstMTaskBody* nodep) { + virtual void visit(AstMTaskBody* nodep) VL_OVERRIDE { ExecMTask* mtp = nodep->execMTaskp(); puts("\n"); puts("void "); - puts(modClassName(m_modp)+"::"+protect(mtp->cFuncName())); + puts(prefixNameProtect(m_modp) + "::" + protect(mtp->cFuncName())); puts("(bool even_cycle, void* symtab) {\n"); // Declare and set vlSymsp @@ -1169,7 +1231,7 @@ class EmitCImp : EmitCStmts { //--------------------------------------- // VISITORS using EmitCStmts::visit; // Suppress hidden overloaded virtual function warning - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { // TRACE_* and DPI handled elsewhere if (nodep->funcType().isTrace()) return; if (nodep->dpiImport()) return; @@ -1183,14 +1245,13 @@ class EmitCImp : EmitCStmts { if (nodep->ifdef()!="") puts("#ifdef "+nodep->ifdef()+"\n"); if (nodep->isInline()) puts("VL_INLINE_OPT "); puts(nodep->rtnTypeVoid()); puts(" "); - puts(modClassName(m_modp)+"::"+nodep->nameProtect() - +"("+cFuncArgs(nodep)+") {\n"); + puts(prefixNameProtect(m_modp) + "::" + nodep->nameProtect() + "(" + cFuncArgs(nodep) + + ") {\n"); // "+" in the debug indicates a print from the model puts("VL_DEBUG_IF(VL_DBG_MSGF(\"+ "); for (int i=0; ilevel(); ++i) { puts(" "); } - puts(modClassName(m_modp)+"::"+nodep->nameProtect() - +"\\n\"); );\n"); + puts(prefixNameProtect(m_modp) + "::" + nodep->nameProtect() + "\\n\"); );\n"); // Declare and set vlTOPp if (nodep->symProlog()) puts(EmitCBaseVisitor::symTopAssign()+"\n"); @@ -1259,16 +1320,16 @@ class EmitCImp : EmitCStmts { } } - virtual void visit(AstChangeDet* nodep) { + virtual void visit(AstChangeDet* nodep) VL_OVERRIDE { m_blkChangeDetVec.push_back(nodep); } - virtual void visit(AstCReset* nodep) { + virtual void visit(AstCReset* nodep) VL_OVERRIDE { AstVar* varp = nodep->varrefp()->varp(); emitVarReset(varp); } - virtual void visit(AstExecGraph* nodep) { + virtual void visit(AstExecGraph* nodep) VL_OVERRIDE { UASSERT_OBJ(nodep == v3Global.rootp()->execGraphp(), nodep, "ExecGraph should be a singleton!"); // The location of the AstExecGraph within the containing _eval() @@ -1429,8 +1490,8 @@ class EmitCImp : EmitCStmts { void emitDestructorImp(AstNodeModule* modp); void emitSavableImp(AstNodeModule* modp); void emitTextSection(AstType type); - void emitIntFuncDecls(AstNodeModule* modp); // High level + void emitImpTop(AstNodeModule* modp); void emitImp(AstNodeModule* modp); void emitSettleLoop(const std::string& eval_call, bool initial); void emitWrapEval(AstNodeModule* modp); @@ -1896,9 +1957,9 @@ void EmitCImp::emitCtorImp(AstNodeModule* modp) { puts("\n"); bool first = true; if (optSystemC() && modp->isTop()) { - puts("VL_SC_CTOR_IMP("+modClassName(modp)+")"); + puts("VL_SC_CTOR_IMP(" + prefixNameProtect(modp) + ")"); } else { - puts("VL_CTOR_IMP("+modClassName(modp)+")"); + puts("VL_CTOR_IMP(" + prefixNameProtect(modp) + ")"); first = false; // VL_CTOR_IMP includes the first ':' } emitVarCtors(&first); @@ -1954,8 +2015,8 @@ void EmitCImp::emitCtorImp(AstNodeModule* modp) { } void EmitCImp::emitConfigureImp(AstNodeModule* modp) { - puts("\nvoid "+modClassName(modp)+"::"+protect("__Vconfigure") - +"("+symClassName()+"* vlSymsp, bool first) {\n"); + puts("\nvoid " + prefixNameProtect(modp) + "::" + protect("__Vconfigure") + "(" + + symClassName() + "* vlSymsp, bool first) {\n"); puts( "if (0 && first) {} // Prevent unused\n"); puts( "this->__VlSymsp = vlSymsp;\n"); // First, as later stuff needs it. if (v3Global.opt.coverage() ) { @@ -1970,8 +2031,9 @@ void EmitCImp::emitCoverageImp(AstNodeModule* modp) { puts("\n// Coverage\n"); // Rather than putting out VL_COVER_INSERT calls directly, we do it via this function // This gets around gcc slowness constructing all of the template arguments. - puts("void "+modClassName(m_modp)+"::__vlCoverInsert(uint32_t* countp, bool enable," - " const char* filenamep, int lineno, int column,\n"); + puts("void " + prefixNameProtect(m_modp) + + "::__vlCoverInsert(uint32_t* countp, bool enable," + + " const char* filenamep, int lineno, int column,\n"); puts( "const char* hierp, const char* pagep, const char* commentp) {\n"); puts( "static uint32_t fake_zero_count = 0;\n"); // static doesn't need save-restore as constant puts( "if (!enable) countp = &fake_zero_count;\n"); // Used for second++ instantiation of identical bin @@ -1992,7 +2054,7 @@ void EmitCImp::emitCoverageImp(AstNodeModule* modp) { void EmitCImp::emitDestructorImp(AstNodeModule* modp) { puts("\n"); - puts(modClassName(modp)+"::~"+modClassName(modp)+"() {\n"); + puts(prefixNameProtect(modp) + "::~" + prefixNameProtect(modp) + "() {\n"); if (modp->isTop() && v3Global.opt.mtasks()) { puts("delete __Vm_threadPoolp; __Vm_threadPoolp = NULL;\n"); } @@ -2010,8 +2072,9 @@ void EmitCImp::emitSavableImp(AstNodeModule* modp) { string funcname = de ? "__Vdeserialize" : "__Vserialize"; string op = de ? ">>" : "<<"; // NOLINTNEXTLINE(performance-inefficient-string-concatenation) - puts("void "+modClassName(modp)+"::"+protect(funcname)+"("+classname+"& os) {\n"); - // Place a computed checksum to insure proper structure save/restore formatting + puts("void " + prefixNameProtect(modp) + "::" + protect(funcname) + "(" + classname + + "& os) {\n"); + // Place a computed checksum to ensure proper structure save/restore formatting // OK if this hash includes some things we won't dump, since // just looking for loading the wrong model VHashSha256 hash; @@ -2114,7 +2177,8 @@ void EmitCImp::emitCellCtors(AstNodeModule* modp) { } for (AstNode* nodep = modp->stmtsp(); nodep; nodep = nodep->nextp()) { if (AstCell* cellp = VN_CAST(nodep, Cell)) { - puts("VL_CELL("+cellp->nameProtect()+", "+modClassName(cellp->modp())+");\n"); + puts("VL_CELL(" + cellp->nameProtect() + ", " + prefixNameProtect(cellp->modp()) + + ");\n"); } } } @@ -2185,8 +2249,9 @@ void EmitCImp::emitSettleLoop(const std::string& eval_call, bool initial) { } void EmitCImp::emitWrapEval(AstNodeModule* modp) { - puts("\nvoid "+modClassName(modp)+"::eval() {\n"); - puts("VL_DEBUG_IF(VL_DBG_MSGF(\"+++++TOP Evaluate "+modClassName(modp)+"::eval\\n\"); );\n"); + puts("\nvoid " + prefixNameProtect(modp) + "::eval() {\n"); + puts("VL_DEBUG_IF(VL_DBG_MSGF(\"+++++TOP Evaluate " + prefixNameProtect(modp) + + "::eval\\n\"); );\n"); puts(EmitCBaseVisitor::symClassVar()+" = this->__VlSymsp; // Setup global symbol table\n"); puts(EmitCBaseVisitor::symTopAssign()+"\n"); puts("#ifdef VL_DEBUG\n"); @@ -2258,8 +2323,8 @@ void EmitCImp::emitWrapEval(AstNodeModule* modp) { splitSizeInc(10); // - puts("\nvoid "+modClassName(modp)+"::"+protect("_eval_initial_loop") - +"("+EmitCBaseVisitor::symClassVar()+") {\n"); + puts("\nvoid " + prefixNameProtect(modp) + "::" + protect("_eval_initial_loop") + "(" + + EmitCBaseVisitor::symClassVar() + ") {\n"); puts("vlSymsp->__Vm_didInit = true;\n"); puts(protect("_eval_initial")+"(vlSymsp);\n"); if (v3Global.opt.trace()) { @@ -2448,62 +2513,6 @@ void EmitCStmts::emitSortedVarList(const VarVec& anons, } } -struct CmpName { - inline bool operator() (const AstNode* lhsp, const AstNode* rhsp) const { - return lhsp->name() < rhsp->name(); - } -}; - -void EmitCImp::emitIntFuncDecls(AstNodeModule* modp) { - typedef std::vector FuncVec; - FuncVec funcsp; - - for (AstNode* nodep = modp->stmtsp(); nodep; nodep = nodep->nextp()) { - if (const AstCFunc* funcp = VN_CAST(nodep, CFunc)) { - if (!funcp->skipDecl()) { - funcsp.push_back(funcp); - } - } - } - - stable_sort(funcsp.begin(), funcsp.end(), CmpName()); - - for (FuncVec::iterator it = funcsp.begin(); it != funcsp.end(); ++it) { - const AstCFunc* funcp = *it; - if (!funcp->dpiImport()) { // DPI is prototyped in __Dpi.h - ofp()->putsPrivate(funcp->declPrivate()); - if (!funcp->ifdef().empty()) puts("#ifdef " + funcp->ifdef() + "\n"); - if (funcp->isStatic().trueU()) puts("static "); - puts(funcp->rtnTypeVoid()); - puts(" "); - puts(funcp->nameProtect()); - puts("(" + cFuncArgs(funcp) + ")"); - if (funcp->slow()) puts(" VL_ATTR_COLD"); - puts(";\n"); - if (!funcp->ifdef().empty()) puts("#endif // " + funcp->ifdef() + "\n"); - } - } - - if (modp->isTop() && v3Global.opt.mtasks()) { - // Emit the mtask func prototypes. - AstExecGraph* execGraphp = v3Global.rootp()->execGraphp(); - UASSERT_OBJ(execGraphp, v3Global.rootp(), "Root should have an execGraphp"); - const V3Graph* depGraphp = execGraphp->depGraphp(); - for (const V3GraphVertex* vxp = depGraphp->verticesBeginp(); - vxp; vxp = vxp->verticesNextp()) { - const ExecMTask* mtp = dynamic_cast(vxp); - if (mtp->threadRoot()) { - // Emit function declaration for this mtask - ofp()->putsPrivate(true); - puts("static void "); puts(protect(mtp->cFuncName())); - puts("(bool even_cycle, void* symtab);\n"); - } - } - // No AstCFunc for this one, as it's synthetic. Just write it: - puts("static void __Vmtask__final(bool even_cycle, void* symtab);\n"); - } -} - void EmitCImp::emitMTaskState() { ofp()->putsPrivate(true); AstExecGraph* execGraphp = v3Global.rootp()->execGraphp(); @@ -2560,12 +2569,12 @@ void EmitCImp::emitInt(AstNodeModule* modp) { if (v3Global.opt.savable()) v3error("--coverage and --savable not supported together"); } if (v3Global.needHInlines()) { // Set by V3EmitCInlines; should have been called before us - puts("#include \""+topClassName()+"__Inlines.h\"\n"); + puts("#include \"" + topClassName() + "__Inlines.h\"\n"); } if (v3Global.dpi()) { // do this before including our main .h file so that any references to // types defined in svdpi.h are available - puts("#include \""+ topClassName() +"__Dpi.h\"\n"); + puts("#include \"" + topClassName() + "__Dpi.h\"\n"); } puts("\n"); @@ -2574,9 +2583,9 @@ void EmitCImp::emitInt(AstNodeModule* modp) { vl_unordered_set didClassName; for (AstNode* nodep = modp->stmtsp(); nodep; nodep = nodep->nextp()) { if (AstCell* cellp = VN_CAST(nodep, Cell)) { - string className = modClassName(cellp->modp()); - if (didClassName.find(className)==didClassName.end()) { - puts("class "+className+";\n"); + string className = prefixNameProtect(cellp->modp()); + if (didClassName.find(className) == didClassName.end()) { + puts("class " + className + ";\n"); didClassName.insert(className); } } @@ -2589,9 +2598,9 @@ void EmitCImp::emitInt(AstNodeModule* modp) { emitTextSection(AstType::atScHdr); if (optSystemC() && modp->isTop()) { - puts("SC_MODULE("+modClassName(modp)+") {\n"); + puts("SC_MODULE(" + prefixNameProtect(modp) + ") {\n"); } else { - puts("VL_MODULE("+modClassName(modp)+") {\n"); + puts("VL_MODULE(" + prefixNameProtect(modp) + ") {\n"); } ofp()->resetPrivate(); ofp()->putsPrivate(false); // public: @@ -2606,7 +2615,7 @@ void EmitCImp::emitInt(AstNodeModule* modp) { if (modp->isTop()) puts("// Public to allow access to /*verilator_public*/ items;\n"); if (modp->isTop()) puts("// otherwise the application code can consider these internals.\n"); } - puts(modClassName(cellp->modp())+"* "+cellp->nameProtect()+";\n"); + puts(prefixNameProtect(cellp->modp()) + "* " + cellp->nameProtect() + ";\n"); } } } @@ -2674,24 +2683,26 @@ void EmitCImp::emitInt(AstNodeModule* modp) { ofp()->resetPrivate(); // We don't need a private copy constructor, as VerilatedModule has one for us. ofp()->putsPrivate(true); - puts("VL_UNCOPYABLE("+modClassName(modp)+"); ///< Copying not allowed\n"); + puts("VL_UNCOPYABLE(" + prefixNameProtect(modp) + "); ///< Copying not allowed\n"); ofp()->putsPrivate(false); // public: if (optSystemC() && modp->isTop()) { - puts("SC_CTOR("+modClassName(modp)+");\n"); - puts("virtual ~"+modClassName(modp)+"();\n"); + puts("SC_CTOR(" + prefixNameProtect(modp) + ");\n"); + puts("virtual ~" + prefixNameProtect(modp) + "();\n"); } else if (optSystemC()) { - puts("VL_CTOR("+modClassName(modp)+");\n"); - puts("~"+modClassName(modp)+"();\n"); + puts("VL_CTOR(" + prefixNameProtect(modp) + ");\n"); + puts("~" + prefixNameProtect(modp) + "();\n"); } else { if (modp->isTop()) { puts("/// Construct the model; called by application code\n"); puts("/// The special name "" may be used to make a wrapper with a\n"); puts("/// single model invisible with respect to DPI scope names.\n"); } - puts(modClassName(modp)+"(const char* name = \"TOP\");\n"); - if (modp->isTop()) puts("/// Destroy the model; called (often implicitly) by application code\n"); - puts("~"+modClassName(modp)+"();\n"); + puts(prefixNameProtect(modp) + "(const char* name = \"TOP\");\n"); + if (modp->isTop()) { + puts("/// Destroy the model; called (often implicitly) by application code\n"); + } + puts("~" + prefixNameProtect(modp) + "();\n"); } if (v3Global.opt.trace() && modp->isTop()) { puts("/// Trace signals in the model; called by application code\n"); @@ -2750,11 +2761,14 @@ void EmitCImp::emitInt(AstNodeModule* modp) { if (v3Global.opt.savable() && modp->isTop()) { puts("\n"); puts("inline VerilatedSerialize& operator<<(VerilatedSerialize& os, " - +modClassName(modp)+"& rhs) {\n" - "Verilated::quiesce(); rhs."+protect("__Vserialize")+"(os); return os; }\n"); + + prefixNameProtect(modp) + "& rhs) {\n" + + "Verilated::quiesce(); rhs." + + protect("__Vserialize") + "(os); return os; }\n"); puts("inline VerilatedDeserialize& operator>>(VerilatedDeserialize& os, " - +modClassName(modp)+"& rhs) {\n" - "Verilated::quiesce(); rhs."+protect("__Vdeserialize")+"(os); return os; }\n"); + + prefixNameProtect(modp) + + "& rhs) {\n" + + "Verilated::quiesce(); rhs." + + protect("__Vdeserialize") + "(os); return os; }\n"); } // finish up h-file @@ -2763,10 +2777,10 @@ void EmitCImp::emitInt(AstNodeModule* modp) { //---------------------------------------------------------------------- -void EmitCImp::emitImp(AstNodeModule* modp) { +void EmitCImp::emitImpTop(AstNodeModule* fileModp) { puts("\n"); - puts("#include \""+modClassName(modp)+".h\"\n"); - puts("#include \""+symClassName()+".h\"\n"); + puts("#include \"" + prefixNameProtect(fileModp) + ".h\"\n"); + puts("#include \"" + symClassName() + ".h\"\n"); if (v3Global.dpi()) { puts("\n"); @@ -2775,18 +2789,14 @@ void EmitCImp::emitImp(AstNodeModule* modp) { puts("\n"); emitTextSection(AstType::atScImpHdr); +} - if (m_slow && splitFilenum()==0) { +void EmitCImp::emitImp(AstNodeModule* modp) { + if (m_slow) { puts("\n//--------------------\n"); puts("// STATIC VARIABLES\n\n"); - emitVarList(modp->stmtsp(), EVL_CLASS_ALL, modClassName(modp)); - } + emitVarList(modp->stmtsp(), EVL_CLASS_ALL, prefixNameProtect(modp)); - if (m_fast && splitFilenum()==0) { - emitTextSection(AstType::atScImp); - } - - if (m_slow && splitFilenum()==0) { puts("\n//--------------------\n"); emitCtorImp(modp); emitConfigureImp(modp); @@ -2795,7 +2805,9 @@ void EmitCImp::emitImp(AstNodeModule* modp) { emitCoverageImp(modp); } - if (m_fast && splitFilenum()==0) { + if (m_fast) { + emitTextSection(AstType::atScImp); + if (modp->isTop()) { puts("\n//--------------------\n"); puts("\n"); @@ -2806,46 +2818,45 @@ void EmitCImp::emitImp(AstNodeModule* modp) { // Blocks puts("\n//--------------------\n"); puts("// Internal Methods\n"); -} - -//###################################################################### - -void EmitCImp::maybeSplit(AstNodeModule* modp) { - if (splitNeeded()) { - // Close old file - VL_DO_CLEAR(delete m_ofp, m_ofp = NULL); - // Open a new file - m_ofp = newOutCFile(modp, !m_fast, true/*source*/, splitFilenumInc()); - emitImp(modp); - } - splitSizeInc(10); // Even blank functions get a file with a low csplit -} - -void EmitCImp::main(AstNodeModule* modp, bool slow, bool fast) { - // Output a module - m_modp = modp; - m_slow = slow; - m_fast = fast; - - if (debug()>=5) { - UINFO(0," Emitting "<stmtsp(); nodep; nodep = nodep->nextp()) { if (AstCFunc* funcp = VN_CAST(nodep, CFunc)) { maybeSplit(modp); mainDoFunc(funcp); } } +} + +//###################################################################### + +void EmitCImp::maybeSplit(AstNodeModule* fileModp) { + if (splitNeeded()) { + // Close old file + VL_DO_CLEAR(delete m_ofp, m_ofp = NULL); + // Open a new file + m_ofp = newOutCFile(fileModp, !m_fast, true/*source*/, splitFilenumInc()); + emitImpTop(fileModp); + } + splitSizeInc(10); // Even blank functions get a file with a low csplit +} + +void EmitCImp::main(AstNodeModule* modp, bool slow, bool fast) { + // Output a module + AstNodeModule* fileModp = modp; // Filename constructed using this module + m_modp = modp; + m_slow = slow; + m_fast = fast; + + UINFO(5, " Emitting " << prefixNameProtect(modp) << endl); + + if (m_fast) { + m_ofp = newOutCFile(fileModp, !m_fast, false/*source*/); + emitInt(modp); + VL_DO_CLEAR(delete m_ofp, m_ofp = NULL); + } + + m_ofp = newOutCFile(fileModp, !m_fast, true/*source*/); + emitImpTop(fileModp); + emitImp(modp); if (fast && modp->isTop() && v3Global.opt.mtasks()) { // Make a final pass and emit function definitions for the mtasks @@ -3178,14 +3189,14 @@ class EmitCTrace : EmitCStmts { // VISITORS using EmitCStmts::visit; // Suppress hidden overloaded virtual function warning - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Top module only iterate(nodep->topModulep()); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (nodep->slow() != m_slow) return; if (nodep->funcType().isTrace()) { // TRACE_* m_funcp = nodep; @@ -3231,7 +3242,7 @@ class EmitCTrace : EmitCStmts { } m_funcp = NULL; } - virtual void visit(AstTraceDecl* nodep) { + virtual void visit(AstTraceDecl* nodep) VL_OVERRIDE { int enumNum = emitTraceDeclDType(nodep->dtypep()); if (nodep->arrayRange().ranged()) { puts("{int i; for (i=0; i<"+cvtToStr(nodep->arrayRange().elements())+"; i++) {\n"); @@ -3242,7 +3253,7 @@ class EmitCTrace : EmitCStmts { puts("\n"); } } - virtual void visit(AstTraceInc* nodep) { + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { if (nodep->declp()->arrayRange().ranged()) { // It traces faster if we unroll the loop for (int i=0; ideclp()->arrayRange().elements(); i++) { @@ -3252,9 +3263,9 @@ class EmitCTrace : EmitCStmts { emitTraceChangeOne(nodep, -1); } } - virtual void visit(AstCoverDecl* nodep) { + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE { } - virtual void visit(AstCoverInc* nodep) { + virtual void visit(AstCoverInc* nodep) VL_OVERRIDE { } public: @@ -3304,8 +3315,8 @@ void V3EmitC::emitcTrace() { void V3EmitC::emitcFiles() { UINFO(2,__FUNCTION__<<": "<filesp(); filep; - filep = VN_CAST(filep->nextp(), File)) { + for (AstNodeFile* filep = v3Global.rootp()->filesp(); filep; + filep = VN_CAST(filep->nextp(), NodeFile)) { AstCFile* cfilep = VN_CAST(filep, CFile); if (cfilep && cfilep->tblockp()) { V3OutCFile of(cfilep->name()); diff --git a/src/V3EmitCBase.h b/src/V3EmitCBase.h index 28a7c4561..9c844781c 100644 --- a/src/V3EmitCBase.h +++ b/src/V3EmitCBase.h @@ -56,11 +56,12 @@ public: static string symClassVar() { return symClassName()+"* __restrict vlSymsp"; } static string symTopAssign() { return v3Global.opt.prefix()+"* __restrict vlTOPp VL_ATTR_UNUSED = vlSymsp->TOPp;"; } - static string modClassName(AstNodeModule* modp) { // Return name of current module being processed - if (modp->isTop()) { + static string prefixNameProtect(const AstNode* nodep) { // C++ name with prefix + const AstNodeModule* modp = VN_CAST_CONST(nodep, NodeModule); + if (modp && modp->isTop()) { return v3Global.opt.prefix(); } else { - return v3Global.opt.modPrefix()+"_"+protect(modp->name()); + return v3Global.opt.modPrefix() + "_" + protect(nodep->name()); } } static string topClassName() { // Return name of top wrapper module @@ -108,7 +109,7 @@ private: // MEMBERS int m_count; // Number of statements // VISITORS - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { m_count++; iterateChildren(nodep); } diff --git a/src/V3EmitCInlines.cpp b/src/V3EmitCInlines.cpp index 2fb23cd96..0090b880a 100644 --- a/src/V3EmitCInlines.cpp +++ b/src/V3EmitCInlines.cpp @@ -40,51 +40,55 @@ class EmitCInlines : EmitCBaseVisitor { void emitInt(); // VISITORS - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { if (nodep->keyword() == AstBasicDTypeKwd::STRING) { // Request #include via verilated_heavy.h when we create symbol file v3Global.needHeavy(true); } } - virtual void visit(AstAssocArrayDType* nodep) { + virtual void visit(AstAssocArrayDType* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstQueueDType* nodep) { + virtual void visit(AstQueueDType* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstNodeReadWriteMem* nodep) { + virtual void visit(AstNodeReadWriteMem* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstValuePlusArgs* nodep) { + virtual void visit(AstValuePlusArgs* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstAtoN* nodep) { + virtual void visit(AstAtoN* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstPutcN* nodep) { + virtual void visit(AstPutcN* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstGetcN* nodep) { + virtual void visit(AstGetcN* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstSubstrN* nodep) { + virtual void visit(AstGetcRefN* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } - virtual void visit(AstCompareNN* nodep) { + virtual void visit(AstSubstrN* nodep) VL_OVERRIDE { + v3Global.needHeavy(true); + iterateChildren(nodep); + } + virtual void visit(AstCompareNN* nodep) VL_OVERRIDE { v3Global.needHeavy(true); iterateChildren(nodep); } // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } //--------------------------------------- diff --git a/src/V3EmitCMake.cpp b/src/V3EmitCMake.cpp index bed3591e1..4d2a2a79d 100644 --- a/src/V3EmitCMake.cpp +++ b/src/V3EmitCMake.cpp @@ -125,8 +125,8 @@ class CMakeEmitter { *of << "\n### Sources...\n"; std::vector classes_fast, classes_slow, support_fast, support_slow, global; - for (AstFile* nodep = v3Global.rootp()->filesp(); nodep; - nodep = VN_CAST(nodep->nextp(), File)) { + for (AstNodeFile* nodep = v3Global.rootp()->filesp(); nodep; + nodep = VN_CAST(nodep->nextp(), NodeFile)) { AstCFile* cfilep = VN_CAST(nodep, CFile); if (cfilep && cfilep->source()) { if (cfilep->support()) { diff --git a/src/V3EmitCSyms.cpp b/src/V3EmitCSyms.cpp index f1d497a40..5699ac9d5 100644 --- a/src/V3EmitCSyms.cpp +++ b/src/V3EmitCSyms.cpp @@ -244,7 +244,7 @@ class EmitCSyms : EmitCBaseVisitor { } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Collect list of scopes iterateChildren(nodep); varsExpand(); @@ -268,13 +268,16 @@ class EmitCSyms : EmitCBaseVisitor { if (!m_dpiHdrOnly) emitDpiImp(); } } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { nameCheck(nodep); - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstCellInline* nodep) { + virtual void visit(AstCellInline* nodep) VL_OVERRIDE { if (v3Global.opt.vpi()) { string type = (nodep->origModName() == "__BEGIN__") ? "SCOPE_OTHER" : "SCOPE_MODULE"; @@ -284,18 +287,19 @@ class EmitCSyms : EmitCBaseVisitor { name_dedot, type))); } } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { nameCheck(nodep); m_scopes.push_back(make_pair(nodep, m_modp)); if (v3Global.opt.vpi() && !nodep->isTop()) { + string name_dedot = AstNode::dedotName(nodep->shortName()); m_vpiScopeCandidates.insert(make_pair(nodep->name(), ScopeData(scopeSymString(nodep->name()), - nodep->name(), "SCOPE_MODULE"))); + name_dedot, "SCOPE_MODULE"))); } } - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { string name = nodep->scopeSymName(); //UINFO(9,"scnameins sp "<name()<<" sp "<scopePrettySymName()<<" ss "<isSigUserRdPublic() @@ -323,13 +327,13 @@ class EmitCSyms : EmitCBaseVisitor { m_modVars.push_back(make_pair(m_modp, nodep)); } } - virtual void visit(AstCoverDecl* nodep) { + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE { // Assign numbers to all bins, so we know how big of an array to use if (!nodep->dataDeclNullp()) { // else duplicate we don't need code for nodep->binNum(m_coverBins++); } } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { nameCheck(nodep); if (nodep->dpiImport() || nodep->dpiExportWrapper()) { m_dpis.push_back(nodep); @@ -339,9 +343,9 @@ class EmitCSyms : EmitCBaseVisitor { m_funcp = NULL; } // NOPs - virtual void visit(AstConst*) {} + virtual void visit(AstConst*) VL_OVERRIDE {} // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } //--------------------------------------- @@ -387,7 +391,7 @@ void EmitCSyms::emitSymHdr() { puts("\n// INCLUDE MODULE CLASSES\n"); for (AstNodeModule* nodep = v3Global.rootp()->modulesp(); nodep; nodep=VN_CAST(nodep->nextp(), NodeModule)) { - puts("#include \""+modClassName(nodep)+".h\"\n"); + puts("#include \"" + prefixNameProtect(nodep) + ".h\"\n"); } if (v3Global.dpi()) { @@ -418,14 +422,14 @@ void EmitCSyms::emitSymHdr() { puts("\n// SUBCELL STATE\n"); for (std::vector::iterator it = m_scopes.begin(); it != m_scopes.end(); ++it) { - AstScope* scopep = it->first; AstNodeModule* modp = it->second; + AstScope* scopep = it->first; + AstNodeModule* modp = it->second; if (modp->isTop()) { - ofp()->printf("%-30s ", (modClassName(modp)+"*").c_str()); - puts(protectIf(scopep->nameDotless()+"p", scopep->protect())+";\n"); - } - else { - ofp()->printf("%-30s ", (modClassName(modp)+"").c_str()); - puts(protectIf(scopep->nameDotless(), scopep->protect())+";\n"); + ofp()->printf("%-30s ", (prefixNameProtect(modp) + "*").c_str()); + puts(protectIf(scopep->nameDotless() + "p", scopep->protect()) + ";\n"); + } else { + ofp()->printf("%-30s ", (prefixNameProtect(modp) + "").c_str()); + puts(protectIf(scopep->nameDotless(), scopep->protect()) + ";\n"); } } @@ -521,9 +525,9 @@ void EmitCSyms::emitSymImpPreamble() { // Includes puts("#include \""+symClassName()+".h\"\n"); - for (AstNodeModule* nodep = v3Global.rootp()->modulesp(); - nodep; nodep=VN_CAST(nodep->nextp(), NodeModule)) { - puts("#include \""+modClassName(nodep)+".h\"\n"); + for (AstNodeModule* nodep = v3Global.rootp()->modulesp(); nodep; + nodep = VN_CAST(nodep->nextp(), NodeModule)) { + puts("#include \"" + prefixNameProtect(nodep) + ".h\"\n"); } } @@ -579,13 +583,14 @@ void EmitCSyms::emitSymImp() { } puts(" , __Vm_didInit(false)\n"); puts(" // Setup submodule names\n"); - char comma=','; + char comma = ','; for (std::vector::iterator it = m_scopes.begin(); it != m_scopes.end(); ++it) { - AstScope* scopep = it->first; AstNodeModule* modp = it->second; + AstScope* scopep = it->first; + AstNodeModule* modp = it->second; if (modp->isTop()) { } else { - puts(string(" ")+comma+" "+protect(scopep->nameDotless())); - puts("(Verilated::catName(topp->name(),"); + puts(string(" ") + comma + " " + protect(scopep->nameDotless())); + puts("(Verilated::catName(topp->name(), "); // The "." is added by catName putsQuoted(protectWordsIf(scopep->prettyName(), scopep->protect())); puts("))\n"); @@ -599,7 +604,8 @@ void EmitCSyms::emitSymImp() { puts("TOPp = topp;\n"); puts("// Setup each module's pointers to their submodules\n"); for (std::vector::iterator it = m_scopes.begin(); it != m_scopes.end(); ++it) { - AstScope* scopep = it->first; AstNodeModule* modp = it->second; + AstScope* scopep = it->first; + AstNodeModule* modp = it->second; if (!modp->isTop()) { checkSplit(false); string arrow = scopep->name(); @@ -608,10 +614,9 @@ void EmitCSyms::emitSymImp() { arrow.replace(pos, 1, "->"); } if (arrow.substr(0, 5) == "TOP->") arrow.replace(0, 5, "TOPp->"); - string arrowProt = protectWordsIf(arrow, scopep->protect()); - ofp()->printf("%-30s ", arrowProt.c_str()); + ofp()->puts(protectWordsIf(arrow, scopep->protect())); puts(" = &"); - puts(protectIf(scopep->nameDotless(), scopep->protect())+";\n"); + puts(protectIf(scopep->nameDotless(), scopep->protect()) + ";\n"); ++m_numStmts; } } @@ -619,7 +624,8 @@ void EmitCSyms::emitSymImp() { puts("// Setup each module's pointer back to symbol table (for public functions)\n"); puts("TOPp->"+protect("__Vconfigure")+"(this, true);\n"); for (std::vector::iterator it = m_scopes.begin(); it != m_scopes.end(); ++it) { - AstScope* scopep = it->first; AstNodeModule* modp = it->second; + AstScope* scopep = it->first; + AstNodeModule* modp = it->second; if (!modp->isTop()) { checkSplit(false); // first is used by AstCoverDecl's call to __vlCoverInsert @@ -692,7 +698,7 @@ void EmitCSyms::emitSymImp() { puts(protect("__Vscope_"+scopep->scopeSymName())+".exportInsert(__Vfinal, "); putsQuoted(funcp->cname()); // Not protected - user asked for import/export puts(", (void*)(&"); - puts(modClassName(modp)); + puts(prefixNameProtect(modp)); puts("::"); puts(funcp->nameProtect()); puts("));\n"); @@ -774,7 +780,7 @@ void EmitCSyms::emitDpiHdr() { puts("// DESCR" "IPTION: Verilator output: Prototypes for DPI import and export functions.\n"); puts("//\n"); puts("// Verilator includes this file in all generated .cpp files that use DPI functions.\n"); - puts("// Manually include this file where DPI .c import functions are declared to insure\n"); + puts("// Manually include this file where DPI .c import functions are declared to ensure\n"); puts("// the C functions match the expectations of the DPI imports.\n"); puts("\n"); puts("#include \"svdpi.h\"\n"); diff --git a/src/V3EmitMk.cpp b/src/V3EmitMk.cpp index 1831a305c..ad7d91386 100644 --- a/src/V3EmitMk.cpp +++ b/src/V3EmitMk.cpp @@ -55,7 +55,7 @@ public: of.puts("VM_THREADS = "); of.puts(cvtToStr(v3Global.opt.threads())); of.puts("\n"); of.puts("# Tracing output mode? 0/1 (from --trace)\n"); of.puts("VM_TRACE = "); of.puts(v3Global.opt.trace()?"1":"0"); of.puts("\n"); - of.puts("# Tracing threadeds output mode? 0/1 (from --trace-fst-thread)\n"); + of.puts("# Tracing threaded output mode? 0/1 (from --trace-fst-thread)\n"); of.puts("VM_TRACE_THREADED = "); of.puts(v3Global.opt.traceFormat().threaded() ?"1":"0"); of.puts("\n"); @@ -101,8 +101,8 @@ public: else if (support==2 && slow) { } else { - for (AstFile* nodep = v3Global.rootp()->filesp(); - nodep; nodep = VN_CAST(nodep->nextp(), File)) { + for (AstNodeFile* nodep = v3Global.rootp()->filesp(); + nodep; nodep = VN_CAST(nodep->nextp(), NodeFile)) { AstCFile* cfilep = VN_CAST(nodep, CFile); if (cfilep && cfilep->source() && cfilep->slow()==(slow!=0) diff --git a/src/V3EmitV.cpp b/src/V3EmitV.cpp index 9032711b8..a07f6d477 100644 --- a/src/V3EmitV.cpp +++ b/src/V3EmitV.cpp @@ -57,15 +57,15 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstNodeModule* nodep) { - putfs(nodep, nodep->verilogKwd()+" "+modClassName(nodep)+";\n"); + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + putfs(nodep, nodep->verilogKwd() + " " + prefixNameProtect(nodep) + ";\n"); iterateChildren(nodep); - putqs(nodep, "end"+nodep->verilogKwd()+"\n"); + putqs(nodep, "end" + nodep->verilogKwd() + "\n"); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { putfs(nodep, nodep->isFunction() ? "function":"task"); puts(" "); puts(nodep->prettyName()); @@ -75,7 +75,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { putqs(nodep, "end\n"); } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { if (nodep->unnamed()) { putbs("begin\n"); } else { @@ -84,22 +84,22 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateChildren(nodep); puts("end\n"); } - virtual void visit(AstGenerate* nodep) { + virtual void visit(AstGenerate* nodep) VL_OVERRIDE { putfs(nodep, "generate\n"); iterateChildren(nodep); putqs(nodep, "end\n"); } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { putfs(nodep, "final begin\n"); iterateChildren(nodep); putqs(nodep, "end\n"); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { putfs(nodep, "initial begin\n"); iterateChildren(nodep); putqs(nodep, "end\n"); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { putfs(nodep, "always "); if (m_sensesp) iterateAndNextNull(m_sensesp); // In active else iterateAndNextNull(nodep->sensesp()); @@ -107,7 +107,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->bodysp()); putqs(nodep, "end\n"); } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { putfs(nodep, "/*verilator public_flat_rw "); if (m_sensesp) iterateAndNextNull(m_sensesp); // In active else iterateAndNextNull(nodep->sensesp()); @@ -115,37 +115,37 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->bodysp()); putqs(nodep, "*/\n"); } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->lhsp()); putfs(nodep, " "+nodep->verilogKwd()+" "); iterateAndNextNull(nodep->rhsp()); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->lhsp()); putfs(nodep, " <= "); iterateAndNextNull(nodep->rhsp()); puts(";\n"); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { putbs("alias "); iterateAndNextNull(nodep->lhsp()); putfs(nodep, " = "); iterateAndNextNull(nodep->rhsp()); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { putfs(nodep, "assign "); iterateAndNextNull(nodep->lhsp()); putbs(" = "); iterateAndNextNull(nodep->rhsp()); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstBreak* nodep) { + virtual void visit(AstBreak* nodep) VL_OVERRIDE { putbs("break"); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { // AstSenItem is called for dumping in isolation by V3Order putfs(nodep, "@("); for (AstNode* expp=nodep->sensesp(); expp; expp = expp->nextp()) { @@ -154,16 +154,16 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts(")"); } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { emitVerilogFormat(nodep, nodep->emitVerilog(), nodep->sensesp(), nodep->rhsp()); } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { putfs(nodep, ""); puts(nodep->edgeType().verilogKwd()); if (nodep->sensp()) puts(" "); iterateChildren(nodep); } - virtual void visit(AstNodeCase* nodep) { + virtual void visit(AstNodeCase* nodep) VL_OVERRIDE { putfs(nodep, ""); if (const AstCase* casep = VN_CAST(nodep, Case)) { if (casep->priorityPragma()) puts("priority "); @@ -184,7 +184,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->itemsp()); putqs(nodep, "endcase\n"); } - virtual void visit(AstCaseItem* nodep) { + virtual void visit(AstCaseItem* nodep) VL_OVERRIDE { if (nodep->condsp()) { iterateAndNextNull(nodep->condsp()); } else putbs("default"); @@ -192,17 +192,17 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->bodysp()); putqs(nodep, "end\n"); } - virtual void visit(AstComment* nodep) { + virtual void visit(AstComment* nodep) VL_OVERRIDE { puts(string("// ")+nodep->name()+"\n"); iterateChildren(nodep); } - virtual void visit(AstContinue* nodep) { + virtual void visit(AstContinue* nodep) VL_OVERRIDE { putbs("continue"); if (!m_suppressSemi) puts(";\n"); } - virtual void visit(AstCoverDecl*) {} // N/A - virtual void visit(AstCoverInc*) {} // N/A - virtual void visit(AstCoverToggle*) {} // N/A + virtual void visit(AstCoverDecl*) VL_OVERRIDE {} // N/A + virtual void visit(AstCoverInc*) VL_OVERRIDE {} // N/A + virtual void visit(AstCoverToggle*) VL_OVERRIDE {} // N/A void visitNodeDisplay(AstNode* nodep, AstNode* fileOrStrgp, const string& text, AstNode* exprsp) { @@ -216,28 +216,28 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts(");\n"); } - virtual void visit(AstDisable* nodep) { + virtual void visit(AstDisable* nodep) VL_OVERRIDE { putbs("disable "+nodep->name()+";\n"); } - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, nodep->filep(), nodep->fmtp()->text(), nodep->fmtp()->exprsp()); } - virtual void visit(AstElabDisplay* nodep) { + virtual void visit(AstElabDisplay* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, NULL, nodep->fmtp()->text(), nodep->fmtp()->exprsp()); } - virtual void visit(AstFScanF* nodep) { + virtual void visit(AstFScanF* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, nodep->filep(), nodep->text(), nodep->exprsp()); } - virtual void visit(AstSScanF* nodep) { + virtual void visit(AstSScanF* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, nodep->fromp(), nodep->text(), nodep->exprsp()); } - virtual void visit(AstSFormat* nodep) { + virtual void visit(AstSFormat* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, nodep->lhsp(), nodep->fmtp()->text(), nodep->fmtp()->exprsp()); } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { visitNodeDisplay(nodep, NULL, nodep->text(), nodep->exprsp()); } - virtual void visit(AstFOpen* nodep) { + virtual void visit(AstFOpen* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); putbs(" ("); if (nodep->filep()) iterateAndNextNull(nodep->filep()); @@ -247,27 +247,27 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { if (nodep->modep()) iterateAndNextNull(nodep->modep()); puts(");\n"); } - virtual void visit(AstFClose* nodep) { + virtual void visit(AstFClose* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); putbs(" ("); if (nodep->filep()) iterateAndNextNull(nodep->filep()); puts(");\n"); } - virtual void visit(AstFFlush* nodep) { + virtual void visit(AstFFlush* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); putbs(" ("); if (nodep->filep()) iterateAndNextNull(nodep->filep()); puts(");\n"); } - virtual void visit(AstJumpGo* nodep) { + virtual void visit(AstJumpGo* nodep) VL_OVERRIDE { putbs("disable "+cvtToHex(nodep->labelp())+";\n"); } - virtual void visit(AstJumpLabel* nodep) { + virtual void visit(AstJumpLabel* nodep) VL_OVERRIDE { putbs("begin : "+cvtToHex(nodep)+"\n"); if (nodep->stmtsp()) iterateAndNextNull(nodep->stmtsp()); puts("end\n"); } - virtual void visit(AstNodeReadWriteMem* nodep) { + virtual void visit(AstNodeReadWriteMem* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); putbs(" ("); if (nodep->filenamep()) iterateAndNextNull(nodep->filenamep()); @@ -277,17 +277,17 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { if (nodep->msbp()) { putbs(","); iterateAndNextNull(nodep->msbp()); } puts(");\n"); } - virtual void visit(AstSysFuncAsTask* nodep) { + virtual void visit(AstSysFuncAsTask* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->lhsp()); puts(";\n"); } - virtual void visit(AstSysIgnore* nodep) { + virtual void visit(AstSysIgnore* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); putbs(" ("); iterateAndNextNull(nodep->exprsp()); puts(");\n"); } - virtual void visit(AstNodeFor* nodep) { + virtual void visit(AstNodeFor* nodep) VL_OVERRIDE { putfs(nodep, "for ("); m_suppressSemi = true; iterateAndNextNull(nodep->initsp()); @@ -300,14 +300,14 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->bodysp()); putqs(nodep, "end\n"); } - virtual void visit(AstRepeat* nodep) { + virtual void visit(AstRepeat* nodep) VL_OVERRIDE { putfs(nodep, "repeat ("); iterateAndNextNull(nodep->countp()); puts(") begin\n"); iterateAndNextNull(nodep->bodysp()); putfs(nodep, "end\n"); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->precondsp()); putfs(nodep, "while ("); iterateAndNextNull(nodep->condp()); @@ -317,7 +317,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->precondsp()); // Need to recompute before next loop putfs(nodep, "end\n"); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { putfs(nodep, ""); if (const AstIf* ifp = VN_CAST(nodep, If)) { if (ifp->priorityPragma()) puts("priority "); @@ -335,7 +335,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } putqs(nodep, "end\n"); } - virtual void visit(AstPast* nodep) { + virtual void visit(AstPast* nodep) VL_OVERRIDE { putfs(nodep, "$past("); iterateAndNextNull(nodep->exprp()); if (nodep->ticksp()) { @@ -344,49 +344,49 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts(")"); } - virtual void visit(AstReturn* nodep) { + virtual void visit(AstReturn* nodep) VL_OVERRIDE { putfs(nodep, "return "); iterateAndNextNull(nodep->lhsp()); puts(";\n"); } - virtual void visit(AstStop* nodep) { + virtual void visit(AstStop* nodep) VL_OVERRIDE { putfs(nodep, "$stop;\n"); } - virtual void visit(AstFinish* nodep) { + virtual void visit(AstFinish* nodep) VL_OVERRIDE { putfs(nodep, "$finish;\n"); } - virtual void visit(AstText* nodep) { + virtual void visit(AstNodeSimpleText* nodep) VL_OVERRIDE { if (nodep->tracking() || m_trackText) { puts(nodep->text()); } else { putsNoTracking(nodep->text()); } } - virtual void visit(AstTextBlock* nodep) { - visit(VN_CAST(nodep, Text)); + virtual void visit(AstTextBlock* nodep) VL_OVERRIDE { + visit(VN_CAST(nodep, NodeSimpleText)); for (AstNode* childp = nodep->nodesp(); childp; childp = childp->nextp()) { iterate(childp); if (nodep->commas() && childp->nextp()) puts(", "); } } - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { } - virtual void visit(AstCStmt* nodep) { + virtual void visit(AstCStmt* nodep) VL_OVERRIDE { putfs(nodep, "$_CSTMT("); iterateAndNextNull(nodep->bodysp()); puts(");\n"); } - virtual void visit(AstCMath* nodep) { + virtual void visit(AstCMath* nodep) VL_OVERRIDE { putfs(nodep, "$_CMATH("); iterateAndNextNull(nodep->bodysp()); puts(");\n"); } - virtual void visit(AstUCStmt* nodep) { + virtual void visit(AstUCStmt* nodep) VL_OVERRIDE { putfs(nodep, "$c("); iterateAndNextNull(nodep->bodysp()); puts(");\n"); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { putfs(nodep, "$c("); iterateAndNextNull(nodep->bodysp()); puts(")"); @@ -444,19 +444,19 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } } - virtual void visit(AstNodeTermop* nodep) { + virtual void visit(AstNodeTermop* nodep) VL_OVERRIDE { emitVerilogFormat(nodep, nodep->emitVerilog()); } - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { emitVerilogFormat(nodep, nodep->emitVerilog(), nodep->lhsp()); } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { emitVerilogFormat(nodep, nodep->emitVerilog(), nodep->lhsp(), nodep->rhsp()); } - virtual void visit(AstNodeTriop* nodep) { + virtual void visit(AstNodeTriop* nodep) VL_OVERRIDE { emitVerilogFormat(nodep, nodep->emitVerilog(), nodep->lhsp(), nodep->rhsp(), nodep->thsp()); } - virtual void visit(AstAttrOf* nodep) { + virtual void visit(AstAttrOf* nodep) VL_OVERRIDE { putfs(nodep, "$_ATTROF("); iterateAndNextNull(nodep->fromp()); if (nodep->dimp()) { @@ -465,7 +465,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts(")"); } - virtual void visit(AstInitArray* nodep) { + virtual void visit(AstInitArray* nodep) VL_OVERRIDE { putfs(nodep, "`{"); int comma = 0; const AstInitArray::KeyItemMap& mapr = nodep->map(); @@ -479,13 +479,13 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts("}"); } - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { putbs("("); iterateAndNextNull(nodep->condp()); putfs(nodep, " ? "); iterateAndNextNull(nodep->expr1p()); putbs(" : "); iterateAndNextNull(nodep->expr2p()); puts(")"); } - virtual void visit(AstRange* nodep) { + virtual void visit(AstRange* nodep) VL_OVERRIDE { puts("["); if (VN_IS(nodep->msbp(), Const) && VN_IS(nodep->lsbp(), Const)) { // Looks nicer if we print [1:0] rather than [32'sh1:32sh0] @@ -496,7 +496,7 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->rightp()); puts("]"); } } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); puts("["); if (VN_IS(nodep->lsbp(), Const)) { if (nodep->widthp()->isOne()) { @@ -518,44 +518,44 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { } puts("]"); } - virtual void visit(AstSliceSel* nodep) { + virtual void visit(AstSliceSel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); puts(cvtToStr(nodep->declRange())); } - virtual void visit(AstTypedef* nodep) { + virtual void visit(AstTypedef* nodep) VL_OVERRIDE { putfs(nodep, "typedef "); iterateAndNextNull(nodep->dtypep()); puts(" "); puts(nodep->prettyName()); puts(";\n"); } - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { if (nodep->isSigned()) putfs(nodep, "signed "); putfs(nodep, nodep->prettyName()); if (nodep->rangep()) { puts(" "); iterateAndNextNull(nodep->rangep()); puts(" "); } else if (nodep->isRanged()) { puts(" ["); puts(cvtToStr(nodep->msb())); puts(":0] "); } } - virtual void visit(AstConstDType* nodep) { + virtual void visit(AstConstDType* nodep) VL_OVERRIDE { putfs(nodep, "const "); iterate(nodep->subDTypep()); } - virtual void visit(AstNodeArrayDType* nodep) { + virtual void visit(AstNodeArrayDType* nodep) VL_OVERRIDE { iterate(nodep->subDTypep()); iterateAndNextNull(nodep->rangep()); } - virtual void visit(AstNodeUOrStructDType* nodep) { + virtual void visit(AstNodeUOrStructDType* nodep) VL_OVERRIDE { puts(nodep->verilogKwd()+" "); if (nodep->packed()) puts("packed "); puts("\n"); iterateAndNextNull(nodep->membersp()); puts("}"); } - virtual void visit(AstMemberDType* nodep) { + virtual void visit(AstMemberDType* nodep) VL_OVERRIDE { iterate(nodep->subDTypep()); puts(" "); puts(nodep->name()); puts("}"); } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { if (nodep->dotted()!="") { putfs(nodep, nodep->dotted()); puts("."); puts(nodep->prettyName()); } else { putfs(nodep, nodep->prettyName()); } @@ -563,11 +563,11 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { iterateAndNextNull(nodep->pinsp()); puts(")"); } - virtual void visit(AstArg* nodep) { + virtual void visit(AstArg* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->exprp()); } // Terminals - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varScopep()) { putfs(nodep, nodep->varScopep()->prettyName()); } else { @@ -575,43 +575,43 @@ class EmitVBaseVisitor : public EmitCBaseVisitor { puts(nodep->varp()->prettyName()); } } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { putfs(nodep, nodep->dotted()); puts("."); puts(nodep->varp()->prettyName()); } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { putfs(nodep, nodep->num().ascii(true, true)); } // Just iterate - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { putfs(nodep, nodep->verilogKwd()); puts(" "); iterate(nodep->dtypep()); puts(" "); puts(nodep->prettyName()); if (!m_suppressVarSemi) puts(";\n"); else puts("\n"); } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { m_sensesp = nodep->sensesp(); iterateAndNextNull(nodep->stmtsp()); m_sensesp = NULL; } - virtual void visit(AstVarScope*) {} - virtual void visit(AstNodeText*) {} - virtual void visit(AstTraceDecl*) {} - virtual void visit(AstTraceInc*) {} + virtual void visit(AstVarScope*) VL_OVERRIDE {} + virtual void visit(AstNodeText*) VL_OVERRIDE {} + virtual void visit(AstTraceDecl*) VL_OVERRIDE {} + virtual void visit(AstTraceInc*) VL_OVERRIDE {} // NOPs - virtual void visit(AstPragma*) {} - virtual void visit(AstCell*) {} // Handled outside the Visit class + virtual void visit(AstPragma*) VL_OVERRIDE {} + virtual void visit(AstCell*) VL_OVERRIDE {} // Handled outside the Visit class // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { puts(string("\n???? // ")+nodep->prettyTypeName()+"\n"); iterateChildren(nodep); // Not v3fatalSrc so we keep processing @@ -757,12 +757,12 @@ void V3EmitV::emitv() { EmitVFileVisitor visitor (v3Global.rootp(), &of); } else { // Process each module in turn - for (AstNodeModule* modp = v3Global.rootp()->modulesp(); - modp; modp=VN_CAST(modp->nextp(), NodeModule)) { - V3OutVFile of (v3Global.opt.makeDir() - +"/"+EmitCBaseVisitor::modClassName(modp)+"__Vout.v"); + for (AstNodeModule* modp = v3Global.rootp()->modulesp(); modp; + modp = VN_CAST(modp->nextp(), NodeModule)) { + V3OutVFile of(v3Global.opt.makeDir() + "/" + EmitCBaseVisitor::prefixNameProtect(modp) + + "__Vout.v"); of.putsHeader(); - EmitVFileVisitor visitor (modp, &of); + EmitVFileVisitor visitor(modp, &of); } } } @@ -779,8 +779,8 @@ void V3EmitV::verilogPrefixedTree(AstNode* nodep, std::ostream& os, void V3EmitV::emitvFiles() { UINFO(2,__FUNCTION__<<": "<filesp(); filep; - filep = VN_CAST(filep->nextp(), File)) { + for (AstNodeFile* filep = v3Global.rootp()->filesp(); filep; + filep = VN_CAST(filep->nextp(), NodeFile)) { AstVFile* vfilep = VN_CAST(filep, VFile); if (vfilep && vfilep->tblockp()) { V3OutVFile of(vfilep->name()); diff --git a/src/V3EmitXml.cpp b/src/V3EmitXml.cpp index c1f09316c..84076a23b 100644 --- a/src/V3EmitXml.cpp +++ b/src/V3EmitXml.cpp @@ -71,6 +71,7 @@ class EmitXmlFileVisitor : public AstNVisitor { void outputTag(AstNode* nodep, string tag) { if (tag=="") tag = VString::downcase(nodep->typeName()); puts("<"+tag+" "+nodep->fileline()->xml()); + puts(" "+nodep->fileline()->xmlDetailedLocation()); if (VN_IS(nodep, NodeDType)) { puts(" id="); outputId(nodep); } if (nodep->name()!="") { puts(" name="); putsQuoted(nodep->prettyName()); } if (nodep->tag()!="") { puts(" tag="); putsQuoted(nodep->tag()); } @@ -94,22 +95,22 @@ class EmitXmlFileVisitor : public AstNVisitor { } // VISITORS - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { outputTag(nodep, "contassign"); // IEEE: vpiContAssign outputChildrenEnd(nodep, "contassign"); } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { outputTag(nodep, "instance"); // IEEE: vpiInstance puts(" defName="); putsQuoted(nodep->modName()); // IEEE vpiDefName puts(" origName="); putsQuoted(nodep->origName()); outputChildrenEnd(nodep, "instance"); } - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { puts("\n"); iterateChildren(nodep); puts("\n"); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" origName="); putsQuoted(nodep->origName()); if (nodep->level()==1 || nodep->level()==2) // ==2 because we don't add wrapper when in XML mode @@ -117,7 +118,7 @@ class EmitXmlFileVisitor : public AstNVisitor { if (nodep->modPublic()) puts(" public=\"true\""); outputChildrenEnd(nodep, ""); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { AstVarType typ = nodep->varType(); string kw = nodep->verilogKwd(); string vt = nodep->dtypep()->name(); @@ -147,7 +148,7 @@ class EmitXmlFileVisitor : public AstNVisitor { if (nodep->attrSFormat()) puts(" sformat=\"true\""); outputChildrenEnd(nodep, ""); } - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { // What we call a pin in verilator is a port in the IEEE spec. outputTag(nodep, "port"); // IEEE: vpiPort if (nodep->modVarp()->isIO()) { @@ -157,26 +158,26 @@ class EmitXmlFileVisitor : public AstNVisitor { // Children includes vpiHighConn and vpiLowConn; we don't support port bits (yet?) outputChildrenEnd(nodep, "port"); } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" edgeType=\""+cvtToStr(nodep->edgeType().ascii())+"\""); // IEEE vpiTopModule outputChildrenEnd(nodep, ""); } - virtual void visit(AstModportVarRef* nodep) { + virtual void visit(AstModportVarRef* nodep) VL_OVERRIDE { // Dump direction for Modport references string kw = nodep->direction().xmlKwd(); outputTag(nodep, ""); puts(" direction="); putsQuoted(kw); outputChildrenEnd(nodep, ""); } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" dotted="); putsQuoted(nodep->dotted()); outputChildrenEnd(nodep, ""); } // Data types - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { outputTag(nodep, "basicdtype"); if (nodep->isRanged()) { puts(" left=\""+cvtToStr(nodep->left())+"\""); @@ -184,30 +185,30 @@ class EmitXmlFileVisitor : public AstNVisitor { } puts("/>\n"); } - virtual void visit(AstIfaceRefDType* nodep) { + virtual void visit(AstIfaceRefDType* nodep) VL_OVERRIDE { string mpn; outputTag(nodep, ""); if (nodep->isModport()) mpn = nodep->modportName(); puts(" modportname="); putsQuoted(mpn); outputChildrenEnd(nodep, ""); } - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" displaytype="); putsQuoted(nodep->verilogKwd()); outputChildrenEnd(nodep, ""); } - virtual void visit(AstElabDisplay* nodep) { + virtual void visit(AstElabDisplay* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" displaytype="); putsQuoted(nodep->verilogKwd()); outputChildrenEnd(nodep, ""); } - virtual void visit(AstExtend* nodep) { + virtual void visit(AstExtend* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" width="); putsQuoted(cvtToStr(nodep->width())); puts(" widthminv="); putsQuoted(cvtToStr(nodep->lhsp()->widthMinV())); outputChildrenEnd(nodep, ""); } - virtual void visit(AstExtendS* nodep) { + virtual void visit(AstExtendS* nodep) VL_OVERRIDE { outputTag(nodep, ""); puts(" width="); putsQuoted(cvtToStr(nodep->width())); puts(" widthminv="); putsQuoted(cvtToStr(nodep->lhsp()->widthMinV())); @@ -215,7 +216,7 @@ class EmitXmlFileVisitor : public AstNVisitor { } // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { outputTag(nodep, ""); outputChildrenEnd(nodep, ""); } @@ -242,11 +243,11 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Children are iterated backwards to ensure correct compilation order iterateChildrenBackwards(nodep); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Only list modules and interfaces // Assumes modules and interfaces list is already sorted level wise if (!nodep->dead() @@ -256,7 +257,7 @@ private: } } //----- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // All modules are present at root so no need to iterate on children } @@ -293,11 +294,12 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { if (nodep->level() >= 0 && nodep->level() <=2 ) { // ==2 because we don't add wrapper when in XML mode m_os<<"\n"; m_os<<"fileline()->xml() + <<" "<fileline()->xmlDetailedLocation() <<" name=\""<name()<<"\"" <<" submodname=\""<name()<<"\"" <<" hier=\""<name()<<"\""; @@ -312,12 +314,13 @@ private: m_os<<"\n"; } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { if (nodep->modp()->dead()) { return; } if (!m_hasChildren) m_os<<">\n"; m_os<<"fileline()->xml() + <<" "<fileline()->xmlDetailedLocation() <<" name=\""<name()<<"\"" <<" submodname=\""<modName()<<"\"" <<" hier=\""<name()<<"\""; @@ -334,7 +337,7 @@ private: m_hasChildren = true; } //----- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Error.h b/src/V3Error.h index 95bd9e521..16dee3cc1 100644 --- a/src/V3Error.h +++ b/src/V3Error.h @@ -292,8 +292,8 @@ inline void v3errorEndFatal(std::ostringstream& sstr) { // Theses allow errors using << operators: v3error("foo"<<"bar"); // Careful, you can't put () around msg, as you would in most macro definitions -// Note the commas are the comma operator, not separating arguments. These are needed to insure -// evaluation order as otherwise we couldn't insure v3errorPrep is called first. +// Note the commas are the comma operator, not separating arguments. These are needed to ensure +// evaluation order as otherwise we couldn't ensure v3errorPrep is called first. #define v3warnCode(code,msg) \ v3errorEnd((V3Error::v3errorPrep(code), (V3Error::v3errorStr()<user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->isWide()) { @@ -343,7 +343,7 @@ private: return true; } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); // Remember, Sel's may have non-integer rhs, so need to optimize for that! @@ -670,7 +670,7 @@ private: } } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->isWide()) { @@ -714,7 +714,7 @@ private: return true; } - virtual void visit(AstReplicate* nodep) { + virtual void visit(AstReplicate* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->isWide()) { @@ -779,7 +779,7 @@ private: return true; } - virtual void visit(AstChangeXor* nodep) { + virtual void visit(AstChangeXor* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); UINFO(8," Wordize ChangeXor "<user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->lhsp()->isWide()) { @@ -847,7 +847,7 @@ private: VL_DO_DANGLING(replaceWithDelete(nodep, newp), nodep); } } - virtual void visit(AstRedAnd* nodep) { + virtual void visit(AstRedAnd* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->lhsp()->isWide()) { @@ -880,7 +880,7 @@ private: VL_DO_DANGLING(replaceWithDelete(nodep, newp), nodep); } } - virtual void visit(AstRedXor* nodep) { + virtual void visit(AstRedXor* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once iterateChildren(nodep); if (nodep->lhsp()->isWide()) { @@ -899,7 +899,7 @@ private: // which the inlined function does nicely. } - virtual void visit(AstNodeStmt* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once if (!nodep->isStatement()) { iterateChildren(nodep); @@ -909,7 +909,7 @@ private: iterateChildren(nodep); m_stmtp = NULL; } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once m_stmtp = nodep; iterateChildren(nodep); @@ -955,8 +955,8 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstVar*) {} // Don't hit varrefs under vars - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Don't hit varrefs under vars + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3FileLine.cpp b/src/V3FileLine.cpp index b6cceec76..d27440602 100644 --- a/src/V3FileLine.cpp +++ b/src/V3FileLine.cpp @@ -158,6 +158,15 @@ FileLine::FileLine(FileLine::EmptySecret) { } } +const string FileLine::xmlDetailedLocation() const { + return "loc=\"" + + cvtToStr(filenameLetters()) + "," + + cvtToStr(firstLineno()) + "," + + cvtToStr(firstColumn()) + "," + + cvtToStr(lastLineno()) + "," + + cvtToStr(lastColumn()) + "\""; +} + string FileLine::lineDirectiveStrg(int enterExit) const { char numbuf[20]; sprintf(numbuf, "%d", lastLineno()); char levelbuf[20]; sprintf(levelbuf, "%d", enterExit); diff --git a/src/V3FileLine.h b/src/V3FileLine.h index f515a1408..94cb06c6c 100644 --- a/src/V3FileLine.h +++ b/src/V3FileLine.h @@ -183,6 +183,7 @@ public: const string filebasenameNoExt() const; const string profileFuncname() const; const string xml() const { return "fl=\""+filenameLetters()+cvtToStr(lastLineno())+"\""; } + const string xmlDetailedLocation() const; string lineDirectiveStrg(int enterExit) const; // Turn on/off warning messages on this line. diff --git a/src/V3Gate.cpp b/src/V3Gate.cpp index 8f8f70d44..f4db76775 100644 --- a/src/V3Gate.cpp +++ b/src/V3Gate.cpp @@ -207,7 +207,7 @@ private: } } // VISITORS - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { ++m_ops; iterateChildren(nodep); // We only allow a LHS ref for the var being set, and a RHS ref for @@ -235,7 +235,7 @@ private: m_rhsVarRefs.push_back(nodep); } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { m_substTreep = nodep->rhsp(); if (!VN_IS(nodep->lhsp(), NodeVarRef)) { clearSimple("ASSIGN(non-VARREF)"); @@ -258,7 +258,7 @@ private: } //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // *** Special iterator if (!m_isSimple) return; // Fastpath if (++m_ops > v3Global.opt.gateStmts()) { @@ -388,7 +388,7 @@ private: void decomposeClkVectors(); // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildren(nodep); //if (debug()>6) m_graph.dump(); if (debug()>6) m_graph.dumpDotFilePrefixed("gate_pre"); @@ -419,20 +419,23 @@ private: consumedMove(); replaceAssigns(); } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - m_activeReducible = true; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + m_activeReducible = true; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(4," SCOPE "<hasClocked()); // Seq logic outputs aren't reducible @@ -443,7 +446,7 @@ private: m_activep = NULL; m_activeReducible = true; } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { if (m_scopep) { UASSERT_OBJ(m_logicVertexp, nodep, "Var ref not under a logic block"); AstVarScope* varscp = nodep->varScopep(); @@ -469,19 +472,19 @@ private: } } } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { iterateNewStmt(nodep, (nodep->isJustOneBodyStmt()?NULL:"Multiple Stmts"), NULL); } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { bool lastslow = m_inSlow; m_inSlow = true; iterateNewStmt(nodep, "AlwaysPublic", NULL); m_inSlow = lastslow; } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { iterateNewStmt(nodep, "User C Function", "User C Function"); } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { // Note we look at only AstSenItems, not AstSenGate's // The gating term of a AstSenGate is normal logic m_inSenItem = true; @@ -492,33 +495,33 @@ private: } m_inSenItem = false; } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { // First handle the clock part will be handled in a minute by visit AstSenItem // The logic gating term is dealt with as logic iterateNewStmt(nodep, "Clock gater", "Clock gater"); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { bool lastslow = m_inSlow; m_inSlow = true; iterateNewStmt(nodep, (nodep->isJustOneBodyStmt()?NULL:"Multiple Stmts"), NULL); m_inSlow = lastslow; } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { iterateNewStmt(nodep, NULL, NULL); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { iterateNewStmt(nodep, NULL, NULL); } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { iterateNewStmt(nodep, "CoverToggle", "CoverToggle"); } - virtual void visit(AstTraceInc* nodep) { + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { bool lastslow = m_inSlow; m_inSlow = true; iterateNewStmt(nodep, "Tracing", "Tracing"); m_inSlow = lastslow; } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { UASSERT_OBJ(!(VN_IS(nodep->backp(), NodeAssign) && VN_CAST(nodep->backp(), NodeAssign)->lhsp()==nodep), nodep, "Concat on LHS of assignment; V3Const should have deleted it"); @@ -527,7 +530,7 @@ private: //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); if (nodep->isOutputter() && m_logicVertexp) m_logicVertexp->setConsumed("outputter"); } @@ -860,7 +863,7 @@ private: void hashReplace(AstNode* oldp, AstNode* newp); // VISITORS - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { if (nodep->varScopep() == m_elimVarScp) { // Substitute in the new tree // It's possible we substitute into something that will be reduced more later, @@ -887,7 +890,7 @@ private: VL_DO_DANGLING(nodep->deleteTree(), nodep); } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -1066,7 +1069,7 @@ private: bool m_dedupable; // Determined the assign to be dedupable // VISITORS - virtual void visit(AstNodeAssign* assignp) { + virtual void visit(AstNodeAssign* assignp) VL_OVERRIDE { if (m_dedupable) { // I think we could safely dedupe an always block with multiple // non-blocking statements, but erring on side of caution here @@ -1077,7 +1080,7 @@ private: } } } - virtual void visit(AstAlways* alwaysp) { + virtual void visit(AstAlways* alwaysp) VL_OVERRIDE { if (m_dedupable) { if (!m_always) { m_always = true; @@ -1091,7 +1094,7 @@ private: // always @(...) // if (...) // foo = ...; // or foo <= ...; - virtual void visit(AstNodeIf* ifp) { + virtual void visit(AstNodeIf* ifp) VL_OVERRIDE { if (m_dedupable) { if (m_always && !m_ifCondp && !ifp->elsesp()) { //we're under an always, this is the first IF, and there's no else m_ifCondp = ifp->condp(); @@ -1102,10 +1105,10 @@ private: } } - virtual void visit(AstComment*) {} // NOP + virtual void visit(AstComment*) VL_OVERRIDE {} // NOP //-------------------- // Default - virtual void visit(AstNode*) { + virtual void visit(AstNode*) VL_OVERRIDE { m_dedupable = false; } @@ -1425,7 +1428,7 @@ private: bool m_found; // Offset found // VISITORS - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { UINFO(9,"CLK DECOMP Concat search var (off = "<varScopep() == m_vscp && !nodep->user2() && !m_found) { // A concatenation may use the same var multiple times @@ -1437,14 +1440,14 @@ private: } m_offset += nodep->dtypep()->width(); } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { UINFO(9,"CLK DECOMP Concat search (off = "<rhsp()); iterate(nodep->lhsp()); } //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -1617,7 +1620,7 @@ void GateVisitor::decomposeClkVectors() { class GateDeassignVisitor : public GateBaseVisitor { private: // VISITORS - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { if (AstNodeAssign* assp = VN_CAST(nodep->valuep(), NodeAssign)) { UINFO(5," Removeassign "<rhsp(); @@ -1627,9 +1630,9 @@ private: } } // Speedups - virtual void visit(AstVar* nodep) {} - virtual void visit(AstActive* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} + virtual void visit(AstActive* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3GenClk.cpp b/src/V3GenClk.cpp index 52c0b940c..34573f9f1 100644 --- a/src/V3GenClk.cpp +++ b/src/V3GenClk.cpp @@ -83,7 +83,7 @@ private: } // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { AstNode::user2ClearTree(); // user2p() used on entire tree AstScope* scopep = nodep->scopep(); @@ -93,7 +93,7 @@ private: iterateChildren(nodep); } //---- - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Consumption/generation of a variable, AstVarScope* vscp = nodep->varScopep(); UASSERT_OBJ(vscp, nodep, "Scope not assigned"); @@ -109,19 +109,19 @@ private: } } } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { m_activep = nodep; UASSERT_OBJ(nodep->sensesp(), nodep, "Unlinked"); iterateChildren(nodep->sensesp()); // iterateAndNext? m_activep = NULL; iterateChildren(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { iterateChildren(nodep); } //----- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -152,7 +152,7 @@ private: AstNodeModule* m_topModp; // Top module // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { AstNode::user1ClearTree(); // user1p() used on entire tree iterateChildren(nodep); { @@ -161,14 +161,14 @@ private: GenClkRenameVisitor visitor (nodep, m_topModp); } } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Only track the top scopes, not lower level functions if (nodep->isTop()) { m_topModp = nodep; iterateChildren(nodep); } } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!nodep->funcp()->entryPoint()) { // Enter the function and trace it @@ -176,7 +176,7 @@ private: iterate(nodep->funcp()); } } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!m_tracingCall && !nodep->entryPoint()) { // Only consider logic within a CFunc when looking // at the call to it, and not when scanning whatever @@ -188,7 +188,7 @@ private: } //---- - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Consumption/generation of a variable, AstVarScope* vscp = nodep->varScopep(); UASSERT_OBJ(vscp, nodep, "Scope not assigned"); @@ -203,13 +203,13 @@ private: vscp->circular(true); } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { //UINFO(8,"ASS "<sensesp(), nodep, "Unlinked"); @@ -219,8 +219,8 @@ private: } //----- - virtual void visit(AstVar*) {} // Don't want varrefs under it - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Don't want varrefs under it + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3Global.cpp b/src/V3Global.cpp new file mode 100644 index 000000000..62a53f233 --- /dev/null +++ b/src/V3Global.cpp @@ -0,0 +1,86 @@ +// -*- mode: C++; c-file-style: "cc-mode" -*- +//************************************************************************* +// DESCRIPTION: Verilator: Common implemenetations +// +// Code available from: https://verilator.org +// +//************************************************************************* +// +// Copyright 2004-2020 by Wilson Snyder. This program is free software; you can +// redistribute it and/or modify it under the terms of either the GNU +// Lesser General Public License Version 3 or the Perl Artistic License +// Version 2.0. +// +// Verilator is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +//************************************************************************* + +#include "config_build.h" +#include "verilatedos.h" + +#include "V3Global.h" +#include "V3Ast.h" +#include "V3File.h" +#include "V3LinkCells.h" +#include "V3Parse.h" +#include "V3ParseSym.h" +#include "V3Stats.h" + +//###################################################################### +// V3 Class -- top level + +AstNetlist* V3Global::makeNetlist() { + AstNetlist* newp = new AstNetlist(); + newp->addTypeTablep(new AstTypeTable(newp->fileline())); + return newp; +} + +void V3Global::checkTree() { rootp()->checkTree(); } + +void V3Global::clear() { + if (m_rootp) VL_DO_CLEAR(m_rootp->deleteTree(), m_rootp = NULL); +} + +void V3Global::readFiles() { + // NODE STATE + // AstNode::user4p() // VSymEnt* Package and typedef symbol names + AstUser4InUse inuser4; + + VInFilter filter(v3Global.opt.pipeFilter()); + V3ParseSym parseSyms(v3Global.rootp()); // Symbol table must be common across all parsing + + V3Parse parser(v3Global.rootp(), &filter, &parseSyms); + // Read top module + const V3StringList& vFiles = v3Global.opt.vFiles(); + for (V3StringList::const_iterator it = vFiles.begin(); it != vFiles.end(); ++it) { + string filename = *it; + parser.parseFile(new FileLine(FileLine::commandLineFilename()), filename, false, + "Cannot find file containing module: "); + } + + // Read libraries + // To be compatible with other simulators, + // this needs to be done after the top file is read + const V3StringSet& libraryFiles = v3Global.opt.libraryFiles(); + for (V3StringSet::const_iterator it = libraryFiles.begin(); it != libraryFiles.end(); ++it) { + string filename = *it; + parser.parseFile(new FileLine(FileLine::commandLineFilename()), filename, true, + "Cannot find file containing library module: "); + } + // v3Global.rootp()->dumpTreeFile(v3Global.debugFilename("parse.tree")); + V3Error::abortIfErrors(); + + if (!v3Global.opt.preprocOnly()) { + // Resolve all modules cells refer to + V3LinkCells::link(v3Global.rootp(), &filter, &parseSyms); + } +} + +void V3Global::dumpCheckGlobalTree(const string& stagename, int newNumber, bool doDump) { + v3Global.rootp()->dumpTreeFile(v3Global.debugFilename(stagename + ".tree", newNumber), + false, doDump); + if (v3Global.opt.stats()) V3Stats::statsStage(stagename); +} diff --git a/src/V3Graph.h b/src/V3Graph.h index e63541978..2af27c93c 100644 --- a/src/V3Graph.h +++ b/src/V3Graph.h @@ -104,6 +104,7 @@ public: // METHODS void clear(); // Empty it of all vertices/edges, as if making a new object void clearColors(); + bool empty() const { return m_vertices.empty(); } V3GraphVertex* verticesBeginp() const { return m_vertices.begin(); } @@ -270,7 +271,7 @@ class V3GraphEdge { // Wires/variables aren't edges. Edges have only a single to/from vertex public: // ENUMS - enum Cuttable { NOT_CUTABLE = false, CUTABLE = true }; // For passing to V3GraphEdge + enum Cutable { NOT_CUTABLE = false, CUTABLE = true }; // For passing to V3GraphEdge protected: friend class V3Graph; friend class V3GraphVertex; friend class GraphAcyc; friend class GraphAcycEdge; diff --git a/src/V3Hashed.cpp b/src/V3Hashed.cpp index 71a7f8514..ad22028eb 100644 --- a/src/V3Hashed.cpp +++ b/src/V3Hashed.cpp @@ -88,10 +88,10 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstVar*) {} - virtual void visit(AstTypedef*) {} - virtual void visit(AstParamTypeDType*) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} + virtual void visit(AstTypedef*) VL_OVERRIDE {} + virtual void visit(AstParamTypeDType*) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { nodeHashIterate(nodep); } diff --git a/src/V3Inline.cpp b/src/V3Inline.cpp index a38704c9c..68843c59c 100644 --- a/src/V3Inline.cpp +++ b/src/V3Inline.cpp @@ -100,7 +100,8 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + UASSERT_OBJ(!m_modp, nodep, "Unsupported: Recursive modules"); m_modp = nodep; m_allMods.push_back(nodep); m_modp->user2(CIL_MAYBE); @@ -115,12 +116,12 @@ private: iterateChildren(nodep); m_modp = NULL; } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { nodep->modp()->user3Inc(); // Inc refs m_instances[m_modp][nodep->modp()]++; iterateChildren(nodep); } - virtual void visit(AstPragma* nodep) { + virtual void visit(AstPragma* nodep) VL_OVERRIDE { if (nodep->pragType() == AstPragmaType::INLINE_MODULE) { //UINFO(0,"PRAG MARK "<varp(NULL); } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { // Cleanup link until V3LinkDot can correct it if (!nodep->packagep()) nodep->taskp(NULL); iterateChildren(nodep); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { iterateChildren(nodep); m_modp->user4Inc(); // statement count } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { // Don't count assignments, as they'll likely flatten out // Still need to iterate though to nullify VarXRefs int oldcnt = m_modp->user4(); iterateChildren(nodep); m_modp->user4(oldcnt); } - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Build user2, user3, and user4 for all modules. // Also build m_allMods and m_instances. iterateChildren(nodep); @@ -206,7 +207,7 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_modp) { m_modp->user4Inc(); // Inc statement count @@ -242,13 +243,13 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { nodep->user4p(nodep->clonep()); } // Accelerate - virtual void visit(AstNodeStmt* nodep) {} - virtual void visit(AstNodeMath* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE {} + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -280,7 +281,7 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstCellInline* nodep) { + virtual void visit(AstCellInline* nodep) VL_OVERRIDE { // Inlined cell under the inline cell, need to move to avoid conflicts nodep->unlinkFrBack(); m_modp->addInlinesp(nodep); @@ -291,17 +292,17 @@ private: // Do CellInlines under this, but don't move them iterateChildren(nodep); } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { // Cell under the inline cell, need to rename to avoid conflicts string name = m_cellp->name() + "__DOT__" + nodep->name(); nodep->name(name); iterateChildren(nodep); } - virtual void visit(AstModule* nodep) { + virtual void visit(AstModule* nodep) VL_OVERRIDE { m_renamedInterfaces.clear(); iterateChildren(nodep); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { if (nodep->user2p()) { // Make an assignment, so we'll trace it properly // user2p is either a const or a var. @@ -385,17 +386,17 @@ private: if (debug()>=9 && nodep->valuep()) { nodep->valuep()->dumpTree(cout, "varchangei:"); } iterateChildren(nodep); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { // Function under the inline cell, need to rename to avoid conflicts nodep->name(m_cellp->name() + "__DOT__" + nodep->name()); iterateChildren(nodep); } - virtual void visit(AstTypedef* nodep) { + virtual void visit(AstTypedef* nodep) VL_OVERRIDE { // Typedef under the inline cell, need to rename to avoid conflicts nodep->name(m_cellp->name() + "__DOT__" + nodep->name()); iterateChildren(nodep); } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp()->user2p() // It's being converted to an alias. && !nodep->varp()->user3() && !VN_IS(nodep->backp(), AssignAlias)) { // Don't constant propagate aliases (we just made) @@ -416,7 +417,7 @@ private: nodep->name(nodep->varp()->name()); iterateChildren(nodep); } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { // Track what scope it was originally under so V3LinkDot can resolve it string newdots = VString::dot(m_cellp->name(), ".", nodep->inlinedDots()); nodep->inlinedDots(newdots); @@ -435,7 +436,7 @@ private: } iterateChildren(nodep); } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { // Track what scope it was originally under so V3LinkDot can resolve it string newdots = VString::dot(m_cellp->name(), ".", nodep->inlinedDots()); nodep->inlinedDots(newdots); @@ -447,9 +448,9 @@ private: } // Not needed, as V3LinkDot doesn't care about typedefs - //virtual void visit(AstRefDType* nodep) {} + //virtual void visit(AstRefDType* nodep) VL_OVERRIDE {} - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { // If there's a %m in the display text, we add a special node that will contain the name() // Similar code in V3Begin // To keep correct visual order, must add before other Text's @@ -463,12 +464,12 @@ private: if (afterp) nodep->scopeEntrp(afterp); iterateChildren(nodep); } - virtual void visit(AstCoverDecl* nodep) { + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE { // Fix path in coverage statements nodep->hier(VString::dot(m_cellp->prettyName(), ".", nodep->hier())); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -512,11 +513,11 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Iterate modules backwards, in bottom-up order. Required! iterateChildrenBackwards(nodep); } - virtual void visit(AstIfaceRefDType* nodep) { + virtual void visit(AstIfaceRefDType* nodep) VL_OVERRIDE { if (nodep->user5()) { // The cell has been removed so let's make sure we don't leave a reference to it // This dtype may still be in use by the AstAssignVarScope created earlier @@ -524,11 +525,15 @@ private: nodep->cellp(NULL); } } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { if (nodep->modp()->user1()) { // Marked with inline request UINFO(5," Inline CELL "<isTop()) { iterateChildren(nodep); } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { string oldScope = m_scope; if (m_scope.empty()) { m_scope = nodep->name(); @@ -686,7 +691,7 @@ private: m_scope = oldScope; } - virtual void visit(AstAssignVarScope* nodep) { + virtual void visit(AstAssignVarScope* nodep) VL_OVERRIDE { // Reference AstVarRef* reflp = VN_CAST(nodep->lhsp(), VarRef); // What the reference refers to @@ -712,9 +717,9 @@ private: } //-------------------- - virtual void visit(AstNodeMath*) {} // Accelerate - virtual void visit(AstNodeStmt*) {} // Accelerate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeMath*) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNodeStmt*) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Inst.cpp b/src/V3Inst.cpp index 4b58111a2..e12aa53a7 100644 --- a/src/V3Inst.cpp +++ b/src/V3Inst.cpp @@ -54,7 +54,7 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { UINFO(4," CELL "< ASSIGNW(VARXREF(p),expr) (if sub's input) // or ASSIGNW(expr,VARXREF(p)) (if sub's output) UINFO(4," PIN "<unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstUdpTable* nodep) { + virtual void visit(AstUdpTable* nodep) VL_OVERRIDE { if (!v3Global.opt.bboxUnsup()) { // If we support primitives, update V3Undriven to remove special case nodep->v3error("Unsupported: Verilog 1995 UDP Tables. Use --bbox-unsup to ignore tables."); @@ -124,13 +124,13 @@ private: } // Save some time - virtual void visit(AstNodeMath*) {} - virtual void visit(AstNodeAssign*) {} - virtual void visit(AstAlways*) {} + virtual void visit(AstNodeMath*) VL_OVERRIDE {} + virtual void visit(AstNodeAssign*) VL_OVERRIDE {} + virtual void visit(AstAlways*) VL_OVERRIDE {} //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -155,7 +155,7 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { if (VN_IS(nodep->dtypep(), IfaceRefDType)) { UINFO(8," dm-1-VAR "<dtypep(), UnpackArrayDType) && VN_IS(VN_CAST(nodep->dtypep(), UnpackArrayDType)->subDTypep(), IfaceRefDType)) { UINFO(8," dv-vec-VAR "<modp(), nodep, "Unlinked"); @@ -313,7 +313,7 @@ private: } } - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { // Any non-direct pins need reconnection with a part-select if (!nodep->exprp()) return; // No-connect if (m_cellRangep) { @@ -447,10 +447,10 @@ private: } // Save some time - virtual void visit(AstNodeMath*) {} + virtual void visit(AstNodeMath*) VL_OVERRIDE {} //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3InstrCount.cpp b/src/V3InstrCount.cpp index e69146c71..f0d26cd16 100644 --- a/src/V3InstrCount.cpp +++ b/src/V3InstrCount.cpp @@ -124,7 +124,7 @@ private: } // VISITORS - virtual void visit(AstNodeSel* nodep) { + virtual void visit(AstNodeSel* nodep) VL_OVERRIDE { // This covers both AstArraySel and AstWordSel // // If some vector is a bazillion dwords long, and we're selecting 1 @@ -135,7 +135,7 @@ private: VisitBase vb(this, nodep); iterateAndNextNull(nodep->bitp()); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { // Similar to AstNodeSel above, a small select into a large vector // is not expensive. Count the cost of the AstSel itself (scales with // its width) and the cost of the lsbp() and widthp() nodes, but not @@ -144,13 +144,13 @@ private: iterateAndNextNull(nodep->lsbp()); iterateAndNextNull(nodep->widthp()); } - virtual void visit(AstSliceSel* nodep) { + virtual void visit(AstSliceSel* nodep) VL_OVERRIDE { nodep->v3fatalSrc("AstSliceSel unhandled"); } - virtual void visit(AstMemberSel* nodep) { + virtual void visit(AstMemberSel* nodep) VL_OVERRIDE { nodep->v3fatalSrc("AstMemberSel unhandled"); } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { // Nop. // // Ignore concat. The problem with counting concat is that when we @@ -170,7 +170,7 @@ private: // the widths of the operands (ignored here). markCost(nodep); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { VisitBase vb(this, nodep); iterateAndNextNull(nodep->condp()); uint32_t savedCount = m_instrCount; @@ -195,7 +195,7 @@ private: if (nodep->ifsp()) nodep->ifsp()->user4(0); // Don't dump it } } - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { // Just like if/else above, the ternary operator only evaluates // one of the two expressions, so only count the max. VisitBase vb(this, nodep); @@ -220,7 +220,7 @@ private: if (nodep->expr2p()) nodep->expr2p()->user4(0); // Don't dump it } } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { // You'd think that the OrderLogicVertex's would be disjoint trees // of stuff in the AST, but it isn't so: V3Order makes an // OrderLogicVertex for each ACTIVE, and then also makes an @@ -236,14 +236,14 @@ private: markCost(nodep); UASSERT_OBJ(nodep == m_startNodep, nodep, "Multiple actives, or not start node"); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { VisitBase vb(this, nodep); iterateChildren(nodep); m_tracingCall = true; iterate(nodep->funcp()); UASSERT_OBJ(!m_tracingCall, nodep, "visit(AstCFunc) should have cleared m_tracingCall."); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { // Don't count a CFunc other than by tracing a call or counting it // from the root UASSERT_OBJ(m_tracingCall || nodep == m_startNodep, nodep, @@ -257,7 +257,7 @@ private: } m_inCFunc = saved_inCFunc; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { VisitBase vb(this, nodep); iterateChildren(nodep); } @@ -289,7 +289,7 @@ public: private: // METHODS string indent() { return string(m_depth, ':')+" "; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { ++m_depth; if (unsigned costPlus1 = nodep->user4()) { *m_osp <<" "<varScopep(), nodep, "NULL"); @@ -310,7 +310,7 @@ private: VL_DO_DANGLING(m_lifep->varUsageReplace(vscp, nodep), nodep); } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { // Collect any used variables first, as lhs may also be on rhs // Similar code in V3Dead vluint64_t lastEdit = AstNode::editCountGbl(); // When it was last edited @@ -330,13 +330,13 @@ private: iterateAndNextNull(nodep->lhsp()); } } - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { // Don't treat as normal assign; V3Life doesn't understand time sense iterateChildren(nodep); } //---- Track control flow changes - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { UINFO(4," IF "<condp()); @@ -362,7 +362,7 @@ private: VL_DO_DANGLING(delete elseLifep, elseLifep); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { // While's are a problem, as we don't allow loops in the graph. We // may go around the cond/body multiple times. Thus a // lifelication just in the body is ok, but we can't delete an @@ -391,7 +391,7 @@ private: VL_DO_DANGLING(delete condLifep, condLifep); VL_DO_DANGLING(delete bodyLifep, bodyLifep); } - virtual void visit(AstJumpLabel* nodep) { + virtual void visit(AstJumpLabel* nodep) VL_OVERRIDE { // As with While's we can't predict if a JumpGo will kill us or not // It's worse though as an IF(..., JUMPGO) may change the control flow. // Just don't optimize blocks with labels; they're rare - so far. @@ -410,7 +410,7 @@ private: bodyLifep->lifeToAbove(); VL_DO_DANGLING(delete bodyLifep, bodyLifep); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { //UINFO(4," CCALL "<funcp()); } } - virtual void visit(AstCFunc* nodep) { - //UINFO(4," CCALL "<entryPoint()) return; m_tracingCall = false; if (nodep->dpiImport() && !nodep->pure()) { @@ -428,17 +428,17 @@ private: } iterateChildren(nodep); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { m_sideEffect = true; // If appears on assign RHS, don't ever delete the assignment iterateChildren(nodep); } - virtual void visit(AstCMath* nodep) { + virtual void visit(AstCMath* nodep) VL_OVERRIDE { m_sideEffect = true; // If appears on assign RHS, don't ever delete the assignment iterateChildren(nodep); } - virtual void visit(AstVar*) {} // Don't want varrefs under it - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Don't want varrefs under it + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -472,28 +472,28 @@ private: LifeState* m_statep; // Current state // VISITORS - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (nodep->entryPoint()) { // Usage model 1: Simulate all C code, doing lifetime analysis LifeVisitor visitor (nodep, m_statep); } } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { // Usage model 2: Cleanup basic blocks LifeVisitor visitor (nodep, m_statep); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { // Usage model 2: Cleanup basic blocks LifeVisitor visitor (nodep, m_statep); } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { // Usage model 2: Cleanup basic blocks LifeVisitor visitor (nodep, m_statep); } - virtual void visit(AstVar*) {} // Accelerate - virtual void visit(AstNodeStmt*) {} // Accelerate - virtual void visit(AstNodeMath*) {} // Accelerate - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNodeStmt*) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNodeMath*) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3LifePost.cpp b/src/V3LifePost.cpp index 5f7744d0a..eb321b2da 100644 --- a/src/V3LifePost.cpp +++ b/src/V3LifePost.cpp @@ -58,7 +58,7 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { AstVarScope* vscp = nodep->varScopep(); UASSERT_OBJ(vscp, nodep, "Scope not assigned"); if (AstVarScope* newvscp = reinterpret_cast(vscp->user4p())) { @@ -68,11 +68,11 @@ private: VL_DO_DANGLING(nodep->deleteTree(), nodep); } } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Only track the top scopes, not lower level functions if (nodep->isTop()) iterateChildren(nodep); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!nodep->funcp()->entryPoint()) { // Enter the function and trace it @@ -80,18 +80,18 @@ private: iterate(nodep->funcp()); } } - virtual void visit(AstExecGraph* nodep) { + virtual void visit(AstExecGraph* nodep) VL_OVERRIDE { // Can just iterate across the MTask bodies in any order. Order // isn't important for LifePostElimVisitor's simple substitution. iterateChildren(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!m_tracingCall && !nodep->entryPoint()) return; m_tracingCall = false; iterateChildren(nodep); } - virtual void visit(AstVar*) {} // Don't want varrefs under it - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Don't want varrefs under it + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -259,7 +259,7 @@ private: } // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { AstNode::user4ClearTree(); // user4p() used on entire tree // First, build maps of every location (mtask and sequence @@ -284,7 +284,7 @@ private: // Replace any node4p varscopes with the new scope LifePostElimVisitor visitor (nodep); } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Consumption/generation of a variable, AstVarScope* vscp = nodep->varScopep(); UASSERT_OBJ(vscp, nodep, "Scope not assigned"); @@ -296,14 +296,14 @@ private: m_reads[vscp].insert(loc); } } - virtual void visit(AstAssignPre* nodep) { + virtual void visit(AstAssignPre* nodep) VL_OVERRIDE { // Do not record varrefs within assign pre. // // The pre-assignment into the dly var should not count as its // first write; we only want to consider reads and writes that // would still happen if the dly var were eliminated. } - virtual void visit(AstAssignPost* nodep) { + virtual void visit(AstAssignPost* nodep) VL_OVERRIDE { // Don't record ASSIGNPOST in the read/write maps, record them in a // separate map if (AstVarRef* rhsp = VN_CAST(nodep->rhsp(), VarRef)) { @@ -315,11 +315,11 @@ private: m_assignposts[dlyVarp] = LifePostLocation(loc, nodep); } } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Only track the top scopes, not lower level functions if (nodep->isTop()) iterateChildren(nodep); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!nodep->funcp()->entryPoint()) { // Enter the function and trace it @@ -327,7 +327,7 @@ private: iterate(nodep->funcp()); } } - virtual void visit(AstExecGraph* nodep) { + virtual void visit(AstExecGraph* nodep) VL_OVERRIDE { // Treat the ExecGraph like a call to each mtask body m_mtasksGraphp = nodep->depGraphp(); for (V3GraphVertex* mtaskVxp = m_mtasksGraphp->verticesBeginp(); @@ -339,14 +339,14 @@ private: } m_execMTaskp = NULL; } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!m_tracingCall && !nodep->entryPoint()) return; m_tracingCall = false; iterateChildren(nodep); } //----- - virtual void visit(AstVar*) {} // Don't want varrefs under it - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar*) VL_OVERRIDE {} // Don't want varrefs under it + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3LinkCells.cpp b/src/V3LinkCells.cpp index a9b783897..1a49d5855 100644 --- a/src/V3LinkCells.cpp +++ b/src/V3LinkCells.cpp @@ -158,7 +158,7 @@ private: } // VISITs - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { AstNode::user1ClearTree(); readModNames(); iterateChildren(nodep); @@ -190,45 +190,49 @@ private: v3error("Specified --top-module '"<fileline()->filebasenameNoExt() != nodep->prettyName() - && !v3Global.opt.isLibraryFile(nodep->fileline()->filename()) - && !nodep->recursiveClone() - && !nodep->internal()) { - // We only complain once per file, otherwise library-like files - // have a huge mess of warnings - if (m_declfnWarned.find(nodep->fileline()->filename()) == m_declfnWarned.end()) { - m_declfnWarned.insert(nodep->fileline()->filename()); - nodep->v3warn(DECLFILENAME, "Filename '"<fileline()->filebasenameNoExt() - <<"' does not match "<typeName() - <<" name: "<prettyNameQ()); + AstNodeModule* oldModp = m_modp; + { + m_modp = nodep; + UINFO(2, "Link Module: " << nodep << endl); + if (nodep->fileline()->filebasenameNoExt() != nodep->prettyName() + && !v3Global.opt.isLibraryFile(nodep->fileline()->filename()) + && !nodep->recursiveClone() && !nodep->internal()) { + // We only complain once per file, otherwise library-like files + // have a huge mess of warnings + if (m_declfnWarned.find(nodep->fileline()->filename()) == m_declfnWarned.end()) { + m_declfnWarned.insert(nodep->fileline()->filename()); + nodep->v3warn(DECLFILENAME, "Filename '" + << nodep->fileline()->filebasenameNoExt() + << "' does not match " << nodep->typeName() + << " name: " << nodep->prettyNameQ()); + } } + if (VN_IS(nodep, Iface) || VN_IS(nodep, Package)) { + nodep->inLibrary(true); // Interfaces can't be at top, unless asked + } + bool topMatch = (v3Global.opt.topModule() == nodep->prettyName()); + if (topMatch) { + m_topVertexp = vertex(nodep); + UINFO(2, "Link --top-module: " << nodep << endl); + nodep->inLibrary(false); // Safer to make sure it doesn't disappear + } + if (v3Global.opt.topModule() == "" ? nodep->inLibrary() // Library cells are lower + : !topMatch) { // Any non-specified module is lower + // Put under a fake vertex so that the graph ranking won't indicate + // this is a top level module + if (!m_libVertexp) m_libVertexp = new LibraryVertex(&m_graph); + new V3GraphEdge(&m_graph, m_libVertexp, vertex(nodep), 1, false); + } + // Note AstBind also has iteration on cells + iterateChildren(nodep); + nodep->checkTree(); } - if (VN_IS(nodep, Iface) || VN_IS(nodep, Package)) nodep->inLibrary(true); // Interfaces can't be at top, unless asked - bool topMatch = (v3Global.opt.topModule()==nodep->prettyName()); - if (topMatch) { - m_topVertexp = vertex(nodep); - UINFO(2,"Link --top-module: "<inLibrary(false); // Safer to make sure it doesn't disappear - } - if (v3Global.opt.topModule()=="" - ? nodep->inLibrary() // Library cells are lower - : !topMatch) { // Any non-specified module is lower - // Put under a fake vertex so that the graph ranking won't indicate - // this is a top level module - if (!m_libVertexp) m_libVertexp = new LibraryVertex(&m_graph); - new V3GraphEdge(&m_graph, m_libVertexp, vertex(nodep), 1, false); - } - // Note AstBind also has iteration on cells - iterateChildren(nodep); - nodep->checkTree(); - m_modp = NULL; + m_modp = oldModp; } - virtual void visit(AstIfaceRefDType* nodep) { + virtual void visit(AstIfaceRefDType* nodep) VL_OVERRIDE { // Cell: Resolve its filename. If necessary, parse it. UINFO(4,"Link IfaceRef: "<packagep(), nodep, "Unlinked package"); // Parser should set packagep new V3GraphEdge(&m_graph, vertex(m_modp), vertex(nodep->packagep()), 1, false); } - virtual void visit(AstBind* nodep) { + virtual void visit(AstBind* nodep) VL_OVERRIDE { // Bind: Has cells underneath that need to be put into the new // module, and cells which need resolution // TODO this doesn't allow bind to dotted hier names, that would require @@ -276,7 +280,7 @@ private: pushDeletep(nodep->unlinkFrBack()); } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { // Cell: Resolve its filename. If necessary, parse it. // Execute only once. Complication is that cloning may result in // user1 being set (for pre-clone) so check if user1() matches the @@ -448,8 +452,8 @@ private: // Accelerate the recursion // Must do statements to support Generates, math though... - virtual void visit(AstNodeMath* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } diff --git a/src/V3LinkDot.cpp b/src/V3LinkDot.cpp index ba05aaf6b..8a73837ac 100644 --- a/src/V3LinkDot.cpp +++ b/src/V3LinkDot.cpp @@ -400,7 +400,7 @@ public: VSymEnt* getScopeSym(AstScope* nodep) { NameScopeSymMap::iterator it = m_nameScopeSymMap.find(nodep->name()); UASSERT_OBJ(it != m_nameScopeSymMap.end(), nodep, - "Scope never assigned a symbol entry?"); + "Scope never assigned a symbol entry '" << nodep->name() << "'"); return it->second; } void implicitOkAdd(AstNodeModule* nodep, const string& varname) { @@ -726,7 +726,7 @@ class LinkDotFindVisitor : public AstNVisitor { } // VISITs - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Process $unit or other packages // Not needed - dotted references not allowed from inside packages //for (AstNodeModule* nodep = v3Global.rootp()->modulesp(); @@ -758,8 +758,8 @@ class LinkDotFindVisitor : public AstNVisitor { m_curSymp = m_modSymp = NULL; } } - virtual void visit(AstTypeTable* nodep) {} - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstTypeTable* nodep) VL_OVERRIDE {} + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Called on top module from Netlist, other modules from the cell creating them, // and packages UINFO(8," "<forScopeCreation(), nodep, "Scopes should only exist right after V3Scope"); // Ignored. Processed in next step } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { UINFO(5," CELL under "<recursive() && m_inRecursion) return; @@ -867,7 +867,7 @@ class LinkDotFindVisitor : public AstNVisitor { m_paramNum = oldParamNum; m_inRecursion = oldRecursion; } - virtual void visit(AstCellInline* nodep) { + virtual void visit(AstCellInline* nodep) VL_OVERRIDE { UINFO(5," CELLINLINE under "<insertInline(aboveSymp, m_modSymp, nodep, nodep->name()); } } - virtual void visit(AstDefParam* nodep) { + virtual void visit(AstDefParam* nodep) VL_OVERRIDE { nodep->user1p(m_curSymp); iterateChildren(nodep); } - virtual void visit(AstGenerate* nodep) { + virtual void visit(AstGenerate* nodep) VL_OVERRIDE { // Begin: ... blocks often replicate under genif/genfor, so simply // suppress duplicate checks. See t_gen_forif.v for an example. bool lastInGen = m_inGenerate; @@ -901,7 +901,7 @@ class LinkDotFindVisitor : public AstNVisitor { } m_inGenerate = lastInGen; } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { UINFO(5," "<forPrimary() && !nodep->user4SetOnce()) { @@ -943,7 +943,7 @@ class LinkDotFindVisitor : public AstNVisitor { m_beginp = oldbegin; m_beginNum = oldNum; } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { // NodeTask: Remember its name for later resolution UINFO(5," "<insertSym(m_curSymp, nodep->name(), nodep, m_packagep); } - virtual void visit(AstParamTypeDType* nodep) { - UASSERT_OBJ(m_curSymp, nodep, "Parameter type not under module?"); + virtual void visit(AstParamTypeDType* nodep) VL_OVERRIDE { + UASSERT_OBJ(m_curSymp, nodep, "Parameter type not under module/package/$unit"); iterateChildren(nodep); m_statep->insertSym(m_curSymp, nodep->name(), nodep, m_packagep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { // For dotted resolution, ignore all AstVars under functions, otherwise shouldn't exist UASSERT_OBJ(!m_statep->forScopeCreation(), nodep, "No CFuncs expected in tree yet"); } - virtual void visit(AstEnumItem* nodep) { + virtual void visit(AstEnumItem* nodep) VL_OVERRIDE { // EnumItem: Remember its name for later resolution iterateChildren(nodep); // Find under either a task or the module's vars @@ -1150,7 +1149,7 @@ class LinkDotFindVisitor : public AstNVisitor { m_statep->insertSym(m_curSymp, nodep->name(), nodep, m_packagep); } } - virtual void visit(AstPackageImport* nodep) { + virtual void visit(AstPackageImport* nodep) VL_OVERRIDE { UINFO(4," Link: "<getNodeSym(nodep->packagep()); if (nodep->name()=="*") { @@ -1168,7 +1167,7 @@ class LinkDotFindVisitor : public AstNVisitor { UINFO(9," Link Done: "<getNodeSym(nodep->packagep()); if (nodep->name()!="*") { @@ -1182,13 +1181,13 @@ class LinkDotFindVisitor : public AstNVisitor { UINFO(9," Link Done: "<exportStarStar(m_statep->symsp()); // No longer needed, but can't delete until any multi-instantiated modules are expanded } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -1253,8 +1252,8 @@ private: } // VISITs - virtual void visit(AstTypeTable* nodep) {} - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstTypeTable* nodep) VL_OVERRIDE {} + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(5," "<dead() || !nodep->user4()) { UINFO(4,"Mark dead module "<exprp()); } } - virtual void visit(AstDefParam* nodep) { + virtual void visit(AstDefParam* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->v3warn(DEFPARAM, "Suggest replace defparam assignment with Verilog 2001 #(." <prettyName()<<"(...etc...))"); @@ -1302,7 +1301,7 @@ private: VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } } - virtual void visit(AstPort* nodep) { + virtual void visit(AstPort* nodep) VL_OVERRIDE { // Port: Stash the pin number // Need to set pin numbers after varnames are created // But before we do the final resolution based on names @@ -1329,14 +1328,14 @@ private: // Ports not needed any more VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { // Deal with implicit definitions // We used to nodep->allowImplicit() here, but it turns out // normal "assigns" can also make implicit wires. Yuk. pinImplicitExprRecurse(nodep->lhsp()); iterateChildren(nodep); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // tran gates need implicit creation // As VarRefs don't exist in forPrimary, sanity check UASSERT_OBJ(!m_statep->forPrimary(), nodep, "Assign aliases unexpected pre-dot"); @@ -1348,13 +1347,13 @@ private: } iterateChildren(nodep); } - virtual void visit(AstImplicit* nodep) { + virtual void visit(AstImplicit* nodep) VL_OVERRIDE { // Unsupported gates need implicit creation pinImplicitExprRecurse(nodep); // We're done with implicit gates VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -1384,11 +1383,11 @@ class LinkDotScopeVisitor : public AstNVisitor { int debug() { return LinkDotState::debug(); } // VISITs - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Recurse..., backward as must do packages before using packages iterateChildrenBackwards(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(8," SCOPE "<forScopeCreation(), nodep, "Scopes should only exist right after V3Scope"); @@ -1400,7 +1399,7 @@ class LinkDotScopeVisitor : public AstNVisitor { m_modSymp = NULL; m_scopep = NULL; } - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { if (!nodep->varp()->isFuncLocal()) { VSymEnt* varSymp = m_statep->insertSym(m_modSymp, nodep->varp()->name(), nodep, NULL); if (nodep->varp()->isIfaceRef() @@ -1434,12 +1433,12 @@ class LinkDotScopeVisitor : public AstNVisitor { } } } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { VSymEnt* symp = m_statep->insertBlock(m_modSymp, nodep->name(), nodep, NULL); symp->fallbackp(m_modSymp); // No recursion, we don't want to pick up variables } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // Track aliases created by V3Inline; if we get a VARXREF(aliased_from) // we'll need to replace it with a VARXREF(aliased_to) if (debug()>=9) nodep->dumpTree(cout, "- alias: "); @@ -1449,7 +1448,7 @@ class LinkDotScopeVisitor : public AstNVisitor { fromVscp->user2p(toVscp); iterateChildren(nodep); } - virtual void visit(AstAssignVarScope* nodep) { + virtual void visit(AstAssignVarScope* nodep) VL_OVERRIDE { UINFO(5,"ASSIGNVARSCOPE "<=9) nodep->dumpTree(cout, "- avs: "); VSymEnt* rhsSymp; @@ -1501,10 +1500,10 @@ class LinkDotScopeVisitor : public AstNVisitor { } // For speed, don't recurse things that can't have scope // Note we allow AstNodeStmt's as generates may be under them - virtual void visit(AstCell*) {} - virtual void visit(AstVar*) {} - virtual void visit(AstNodeMath*) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstCell*) VL_OVERRIDE {} + virtual void visit(AstVar*) VL_OVERRIDE {} + virtual void visit(AstNodeMath*) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -1534,7 +1533,7 @@ class LinkDotIfaceVisitor : public AstNVisitor { int debug() { return LinkDotState::debug(); } // VISITs - virtual void visit(AstModport* nodep) { + virtual void visit(AstModport* nodep) VL_OVERRIDE { // Modport: Remember its name for later resolution UINFO(5," fiv: "<isExport()) nodep->v3error("Unsupported: modport export"); @@ -1568,7 +1567,7 @@ class LinkDotIfaceVisitor : public AstNVisitor { nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } } - virtual void visit(AstModportVarRef* nodep) { + virtual void visit(AstModportVarRef* nodep) VL_OVERRIDE { UINFO(5," fiv: "<findIdFallback(nodep->name()); @@ -1592,7 +1591,7 @@ class LinkDotIfaceVisitor : public AstNVisitor { nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -1769,12 +1768,12 @@ private: } // VISITs - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Recurse..., backward as must do packages before using packages iterateChildrenBackwards(nodep); } - virtual void visit(AstTypeTable* nodep) {} - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstTypeTable* nodep) VL_OVERRIDE {} + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { if (nodep->dead()) return; checkNoDot(nodep); UINFO(8," "<forScopeCreation() && !v3Global.opt.vpi()) { nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { // Cell: Recurse inside or cleanup not founds checkNoDot(nodep); m_cellp = nodep; @@ -1833,7 +1832,7 @@ private: // Parent module inherits child's publicity // This is done bottom up in the LinkBotupVisitor stage } - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { // Pin: Link to submodule's port checkNoDot(nodep); iterateChildren(nodep); @@ -1875,7 +1874,7 @@ private: } // Early return() above when deleted } - virtual void visit(AstDot* nodep) { + virtual void visit(AstDot* nodep) VL_OVERRIDE { // Legal under a DOT: AstDot, AstParseRef, AstPackageRef, AstNodeSel // also a DOT can be part of an expression, but only above plus // AstFTaskRef are legal children @@ -1941,7 +1940,7 @@ private: m_ds.m_dotp = lastStates.m_dotp; } } - virtual void visit(AstParseRef* nodep) { + virtual void visit(AstParseRef* nodep) VL_OVERRIDE { if (nodep->user3SetOnce()) return; UINFO(9," linkPARSEREF "<user3SetOnce()) return; iterateAndNextNull(nodep->lhsp()); if (m_ds.m_dotPos == DP_SCOPE) { // Already under dot, so this is {modulepart} DOT {modulepart} @@ -2428,7 +2427,7 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } } - virtual void visit(AstNodePreSel* nodep) { + virtual void visit(AstNodePreSel* nodep) VL_OVERRIDE { // Excludes simple AstSelBit, see above if (nodep->user3SetOnce()) return; if (m_ds.m_dotPos == DP_SCOPE) { // Already under dot, so this is {modulepart} DOT {modulepart} @@ -2446,11 +2445,11 @@ private: } m_ds = lastStates; } - virtual void visit(AstMemberSel* nodep) { + virtual void visit(AstMemberSel* nodep) VL_OVERRIDE { // checkNoDot not appropriate, can be under a dot iterateChildren(nodep); } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { UINFO(5," "<user3SetOnce()) return; if (m_ds.m_dotp && m_ds.m_dotPos == DP_PACKAGE) { @@ -2488,7 +2487,8 @@ private: } else { checkNoDot(nodep); } - if (!nodep->defp()) { + if (nodep->typeofp()) { // Really is a typeof not a reference + } else if (!nodep->defp()) { VSymEnt* foundp; if (nodep->packagep()) { foundp = m_statep->getNodeSym(nodep->packagep())->findIdFlat(nodep->name()); @@ -2510,7 +2510,7 @@ private: } iterateChildren(nodep); } - virtual void visit(AstDpiExport* nodep) { + virtual void visit(AstDpiExport* nodep) VL_OVERRIDE { // AstDpiExport: Make sure the function referenced exists, then dump it iterateChildren(nodep); checkNoDot(nodep); @@ -2527,35 +2527,35 @@ private: } VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstPackageImport* nodep) { + virtual void visit(AstPackageImport* nodep) VL_OVERRIDE { // No longer needed checkNoDot(nodep); VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstPackageExport* nodep) { + virtual void visit(AstPackageExport* nodep) VL_OVERRIDE { // No longer needed checkNoDot(nodep); VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstPackageExportStarStar* nodep) { + virtual void visit(AstPackageExportStarStar* nodep) VL_OVERRIDE { // No longer needed checkNoDot(nodep); VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstCellRef* nodep) { + virtual void visit(AstCellRef* nodep) VL_OVERRIDE { UINFO(5," AstCellRef: "<dead()) return; - m_modp = nodep; - m_repeatNum = 0; - iterateChildren(nodep); - m_modp = NULL; + AstNodeModule* origModp = m_modp; + int origRepeatNum = m_modRepeatNum; + { + m_modp = nodep; + m_modRepeatNum = 0; + iterateChildren(nodep); + } + m_modp = origModp; + m_modRepeatNum = origRepeatNum; } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { m_ftaskp = nodep; iterateChildren(nodep); m_ftaskp = NULL; } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { UINFO(8," "< loop=count,WHILE(loop>0) { body, loop-- } // Note var can be signed or unsigned based on original number. AstNode* countp = nodep->countp()->unlinkFrBackWithNext(); - string name = string("__Vrepeat")+cvtToStr(m_repeatNum++); + string name = string("__Vrepeat")+cvtToStr(m_modRepeatNum++); // Spec says value is integral, if negative is ignored AstVar* varp = new AstVar(nodep->fileline(), AstVarType::BLOCKTEMP, name, nodep->findSigned32DType()); @@ -158,7 +163,7 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { // Don't need to track AstRepeat/AstFor as they have already been converted AstWhile* lastLoopp = m_loopp; bool lastInc = m_loopInc; @@ -172,7 +177,7 @@ private: m_loopInc = lastInc; m_loopp = lastLoopp; } - virtual void visit(AstReturn* nodep) { + virtual void visit(AstReturn* nodep) VL_OVERRIDE { iterateChildren(nodep); AstFunc* funcp = VN_CAST(m_ftaskp, Func); if (!m_ftaskp) { @@ -195,7 +200,7 @@ private: } nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstBreak* nodep) { + virtual void visit(AstBreak* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!m_loopp) { nodep->v3error("break isn't underneath a loop"); } else { @@ -205,7 +210,7 @@ private: } nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstContinue* nodep) { + virtual void visit(AstContinue* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!m_loopp) { nodep->v3error("continue isn't underneath a loop"); } else { @@ -216,7 +221,7 @@ private: } nodep->unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstDisable* nodep) { + virtual void visit(AstDisable* nodep) VL_OVERRIDE { UINFO(8," DISABLE "<unlinkFrBack(); VL_DO_DANGLING(pushDeletep(nodep), nodep); //if (debug()>=9) { UINFO(0,"\n"); beginp->dumpTree(cout, " labelo: "); } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (m_loopInc && nodep->varp()) nodep->varp()->usedLoopIdx(true); } - virtual void visit(AstConst* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -254,7 +259,7 @@ public: m_ftaskp = NULL; m_loopp = NULL; m_loopInc = false; - m_repeatNum = 0; + m_modRepeatNum = 0; iterate(nodep); } virtual ~LinkJumpVisitor() {} diff --git a/src/V3LinkLValue.cpp b/src/V3LinkLValue.cpp index f00c604c8..e8f178ac8 100644 --- a/src/V3LinkLValue.cpp +++ b/src/V3LinkLValue.cpp @@ -50,7 +50,7 @@ private: // VISITs // Result handing - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { // VarRef: LValue its reference if (m_setRefLvalue) { nodep->lvalue(true); @@ -66,7 +66,7 @@ private: } // Nodes that start propagating down lvalues - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { if (nodep->modVarp() && nodep->modVarp()->isWritable()) { // When the varref's were created, we didn't know the I/O state // Now that we do, and it's from a output, we know it's a lvalue @@ -77,7 +77,7 @@ private: iterateChildren(nodep); } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -87,7 +87,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFOpen* nodep) { + virtual void visit(AstFOpen* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -98,7 +98,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFClose* nodep) { + virtual void visit(AstFClose* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -106,7 +106,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFFlush* nodep) { + virtual void visit(AstFFlush* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -114,7 +114,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFGetC* nodep) { + virtual void visit(AstFGetC* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -122,7 +122,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFGetS* nodep) { + virtual void visit(AstFGetS* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -131,7 +131,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFRead* nodep) { + virtual void visit(AstFRead* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -140,7 +140,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFScanF* nodep) { + virtual void visit(AstFScanF* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -149,7 +149,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstFUngetC* nodep) { + virtual void visit(AstFUngetC* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -157,7 +157,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstSScanF* nodep) { + virtual void visit(AstSScanF* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -165,13 +165,13 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstSysIgnore* nodep) { + virtual void visit(AstSysIgnore* nodep) VL_OVERRIDE { // Can't know if lvalue or not; presume so as stricter bool last_setRefLvalue = m_setRefLvalue; iterateChildren(nodep); m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstReadMem* nodep) { + virtual void visit(AstReadMem* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -183,7 +183,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstValuePlusArgs* nodep) { + virtual void visit(AstValuePlusArgs* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = false; @@ -193,7 +193,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstSFormat* nodep) { + virtual void visit(AstSFormat* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { m_setRefLvalue = true; @@ -205,7 +205,7 @@ private: } // Nodes that change LValue state - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { iterateAndNextNull(nodep->lhsp()); @@ -216,7 +216,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstNodeSel* nodep) { + virtual void visit(AstNodeSel* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { // Only set lvalues on the from iterateAndNextNull(nodep->lhsp()); @@ -225,7 +225,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstCellArrayRef* nodep) { + virtual void visit(AstCellArrayRef* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { // selp is not an lvalue m_setRefLvalue = false; @@ -233,7 +233,7 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstNodePreSel* nodep) { + virtual void visit(AstNodePreSel* nodep) VL_OVERRIDE { bool last_setRefLvalue = m_setRefLvalue; { // Only set lvalues on the from iterateAndNextNull(nodep->lhsp()); @@ -243,12 +243,12 @@ private: } m_setRefLvalue = last_setRefLvalue; } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { m_ftaskp = nodep; iterateChildren(nodep); m_ftaskp = NULL; } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { AstNode* pinp = nodep->pinsp(); AstNodeFTask* taskp = nodep->taskp(); // We'll deal with mismatching pins later @@ -270,7 +270,7 @@ private: } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } diff --git a/src/V3LinkParse.cpp b/src/V3LinkParse.cpp index ce049fa8f..f5b6bdfc9 100644 --- a/src/V3LinkParse.cpp +++ b/src/V3LinkParse.cpp @@ -106,7 +106,7 @@ private: } // VISITs - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { V3Config::applyFTask(m_modp, nodep); if (!nodep->user1SetOnce()) { // Process only once. @@ -116,7 +116,7 @@ private: m_ftaskp = NULL; } } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { if (!nodep->user1SetOnce()) { // Process only once. cleanFileline(nodep); UINFO(5," "<name() == "") { nodep->name(nameFromTypedef(nodep)); // Might still remain "" } visitIterateNodeDType(nodep); } - virtual void visit(AstNodeUOrStructDType* nodep) { + virtual void visit(AstNodeUOrStructDType* nodep) VL_OVERRIDE { if (nodep->name() == "") { nodep->name(nameFromTypedef(nodep)); // Might still remain "" } visitIterateNodeDType(nodep); } - virtual void visit(AstEnumItem* nodep) { + virtual void visit(AstEnumItem* nodep) VL_OVERRIDE { // Expand ranges cleanFileline(nodep); iterateChildren(nodep); @@ -173,7 +173,7 @@ private: } } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { cleanFileline(nodep); if (VN_IS(nodep->subDTypep(), ParseTypeDType)) { // It's a parameter type. Use a different node type for this. @@ -255,7 +255,7 @@ private: } } - virtual void visit(AstAttrOf* nodep) { + virtual void visit(AstAttrOf* nodep) VL_OVERRIDE { cleanFileline(nodep); iterateChildren(nodep); if (nodep->attrType() == AstAttrType::DT_PUBLIC) { @@ -322,7 +322,7 @@ private: } } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { // AlwaysPublic was attached under a var, but it's a statement that should be // at the same level as the var cleanFileline(nodep); @@ -337,7 +337,7 @@ private: } } - virtual void visit(AstDefImplicitDType* nodep) { + virtual void visit(AstDefImplicitDType* nodep) VL_OVERRIDE { cleanFileline(nodep); UINFO(8," DEFIMPLICIT "<deleteTree(), nodep); } - virtual void visit(AstTypedefFwd* nodep) { + virtual void visit(AstTypedefFwd* nodep) VL_OVERRIDE { // We only needed the forward declaration in order to parse correctly. // We won't even check it was ever really defined, as it might have been in a header // file referring to a module we never needed VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } - virtual void visit(AstForeach* nodep) { + virtual void visit(AstForeach* nodep) VL_OVERRIDE { // FOREACH(array,loopvars,body) // -> BEGIN(declare vars, loopa=lowest; WHILE(loopa<=highest, ... body)) //nodep->dumpTree(cout, "-foreach-old:"); @@ -443,17 +443,20 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { V3Config::applyModule(nodep); - // Module: Create sim table for entire module and iterate - cleanFileline(nodep); - // - m_modp = nodep; + AstNodeModule* origModp = m_modp; + { + // Module: Create sim table for entire module and iterate + cleanFileline(nodep); + // + m_modp = nodep; + m_valueModp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; m_valueModp = nodep; - iterateChildren(nodep); - m_modp = NULL; - m_valueModp = NULL; } void visitIterateNoValueMod(AstNode* nodep) { // Iterate a node which shouldn't have any local variables moved to an Initial @@ -464,36 +467,36 @@ private: iterateChildren(nodep); m_valueModp = upperValueModp; } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { visitIterateNoValueMod(nodep); } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { visitIterateNoValueMod(nodep); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { m_inAlways = true; visitIterateNoValueMod(nodep); m_inAlways = false; } - virtual void visit(AstCover* nodep) { + virtual void visit(AstCover* nodep) VL_OVERRIDE { visitIterateNoValueMod(nodep); } - virtual void visit(AstRestrict* nodep) { + virtual void visit(AstRestrict* nodep) VL_OVERRIDE { visitIterateNoValueMod(nodep); } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { V3Config::applyCoverageBlock(m_modp, nodep); cleanFileline(nodep); iterateChildren(nodep); } - virtual void visit(AstCase* nodep) { + virtual void visit(AstCase* nodep) VL_OVERRIDE { V3Config::applyCase(nodep); cleanFileline(nodep); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate cleanFileline(nodep); iterateChildren(nodep); diff --git a/src/V3LinkResolve.cpp b/src/V3LinkResolve.cpp index 122acc27a..3180646af 100644 --- a/src/V3LinkResolve.cpp +++ b/src/V3LinkResolve.cpp @@ -65,16 +65,21 @@ private: // TODO: Most of these visitors are here for historical reasons. // TODO: ExpectDecriptor can move to data type resolution, and the rest // TODO: could move to V3LinkParse to get them out of the way of elaboration - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Module: Create sim table for entire module and iterate UINFO(8,"MODULE "<dead()) return; - m_modp = nodep; - m_senitemCvtNum = 0; - iterateChildren(nodep); - m_modp = NULL; + AstNodeModule* origModp = m_modp; + int origSenitemCvtNum = m_senitemCvtNum; + { + m_modp = nodep; + m_senitemCvtNum = 0; + iterateChildren(nodep); + } + m_modp = origModp; + m_senitemCvtNum = origSenitemCvtNum; } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { iterateChildren(nodep); // Initial assignments under function/tasks can just be simple // assignments without the initial @@ -82,14 +87,14 @@ private: VL_DO_DANGLING(nodep->replaceWith(nodep->bodysp()->unlinkFrBackWithNext()), nodep); } } - virtual void visit(AstNodeCoverOrAssert* nodep) { + virtual void visit(AstNodeCoverOrAssert* nodep) VL_OVERRIDE { if (m_assertp) nodep->v3error("Assert not allowed under another assert"); m_assertp = nodep; iterateChildren(nodep); m_assertp = NULL; } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_ftaskp) nodep->funcLocal(true); if (nodep->isSigModPublic()) { @@ -98,7 +103,7 @@ private: } } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { // VarRef: Resolve its reference if (nodep->varp()) { nodep->varp()->usedParam(true); @@ -106,7 +111,7 @@ private: iterateChildren(nodep); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { // NodeTask: Remember its name for later resolution // Remember the existing symbol table scope m_ftaskp = nodep; @@ -116,14 +121,14 @@ private: nodep->scopeNamep(new AstScopeName(nodep->fileline())); } } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { iterateChildren(nodep); if (nodep->taskp() && (nodep->taskp()->dpiContext() || nodep->taskp()->dpiExport())) { nodep->scopeNamep(new AstScopeName(nodep->fileline())); } } - virtual void visit(AstSenItem* nodep) { + virtual void visit(AstSenItem* nodep) VL_OVERRIDE { // Remove bit selects, and bark if it's not a simple variable iterateChildren(nodep); if (nodep->isClocked()) { @@ -190,11 +195,11 @@ private: nodep->v3error("Unsupported: Complex statement in sensitivity list"); } } - virtual void visit(AstSenGate* nodep) { + virtual void visit(AstSenGate* nodep) VL_OVERRIDE { nodep->v3fatalSrc("SenGates shouldn't be in tree yet"); } - virtual void visit(AstNodePreSel* nodep) { + virtual void visit(AstNodePreSel* nodep) VL_OVERRIDE { if (!nodep->attrp()) { iterateChildren(nodep); // Constification may change the fromp() to a constant, which will lose the @@ -226,7 +231,7 @@ private: } } - virtual void visit(AstCaseItem* nodep) { + virtual void visit(AstCaseItem* nodep) VL_OVERRIDE { // Move default caseItems to the bottom of the list // That saves us from having to search each case list twice, for non-defaults and defaults iterateChildren(nodep); @@ -238,7 +243,7 @@ private: } } - virtual void visit(AstPragma* nodep) { + virtual void visit(AstPragma* nodep) VL_OVERRIDE { if (nodep->pragType() == AstPragmaType::PUBLIC_MODULE) { UASSERT_OBJ(m_modp, nodep, "PUBLIC_MODULE not under a module"); m_modp->modPublic(true); @@ -359,31 +364,31 @@ private: if (filep && filep->varp()) filep->varp()->attrFileDescr(true); } - virtual void visit(AstFOpen* nodep) { + virtual void visit(AstFOpen* nodep) VL_OVERRIDE { iterateChildren(nodep); expectDescriptor(nodep, VN_CAST(nodep->filep(), NodeVarRef)); } - virtual void visit(AstFClose* nodep) { + virtual void visit(AstFClose* nodep) VL_OVERRIDE { iterateChildren(nodep); expectDescriptor(nodep, VN_CAST(nodep->filep(), NodeVarRef)); } - virtual void visit(AstFEof* nodep) { + virtual void visit(AstFEof* nodep) VL_OVERRIDE { iterateChildren(nodep); expectDescriptor(nodep, VN_CAST(nodep->filep(), NodeVarRef)); } - virtual void visit(AstFRead* nodep) { + virtual void visit(AstFRead* nodep) VL_OVERRIDE { iterateChildren(nodep); expectDescriptor(nodep, VN_CAST(nodep->filep(), NodeVarRef)); } - virtual void visit(AstFScanF* nodep) { + virtual void visit(AstFScanF* nodep) VL_OVERRIDE { iterateChildren(nodep); expectFormat(nodep, nodep->text(), nodep->exprsp(), true); } - virtual void visit(AstSScanF* nodep) { + virtual void visit(AstSScanF* nodep) VL_OVERRIDE { iterateChildren(nodep); expectFormat(nodep, nodep->text(), nodep->exprsp(), true); } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { iterateChildren(nodep); // Cleanup old-school displays without format arguments if (!nodep->hasFormat()) { @@ -405,7 +410,7 @@ private: } } - virtual void visit(AstUdpTable* nodep) { + virtual void visit(AstUdpTable* nodep) VL_OVERRIDE { UINFO(5,"UDPTABLE "<modPublic(true); iterateChildren(nodep); } - virtual void visit(AstScDtor* nodep) { + virtual void visit(AstScDtor* nodep) VL_OVERRIDE { // Destructor info means the module must remain public m_modp->modPublic(true); iterateChildren(nodep); } - virtual void visit(AstScInt* nodep) { + virtual void visit(AstScInt* nodep) VL_OVERRIDE { // Special class info means the module must remain public m_modp->modPublic(true); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } @@ -484,24 +489,27 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITs - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Iterate modules backwards, in bottom-up order. iterateChildrenBackwards(nodep); } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { // Parent module inherits child's publicity if (nodep->modp()->modPublic()) m_modp->modPublic(true); //** No iteration for speed } - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { // Speedup } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } diff --git a/src/V3Localize.cpp b/src/V3Localize.cpp index 2a2969c41..f5ce6e1d3 100644 --- a/src/V3Localize.cpp +++ b/src/V3Localize.cpp @@ -77,14 +77,14 @@ private: // See above // METHODS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { VarFlags flags (nodep->varp()); if (flags.m_done) { nodep->hiername(""); // Remove this-> nodep->hierThis(true); } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -151,11 +151,11 @@ private: } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildren(nodep); moveVars(); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { UINFO(4," CFUNC "<argsp()); @@ -186,7 +186,7 @@ private: } } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { if (!nodep->isSigPublic() && !nodep->isPrimaryIO() && !m_cfuncp) { // Not already inside a function @@ -195,7 +195,7 @@ private: } // No iterate; Don't want varrefs under it } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (!VarFlags(nodep->varp()).m_notOpt) { if (!m_cfuncp) { // Not in function, can't optimize clearOptimizable(nodep->varp(), "BVnofunc"); @@ -224,7 +224,7 @@ private: } // No iterate; Don't want varrefs under it } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3Name.cpp b/src/V3Name.cpp index fc4694d82..1992d1b06 100644 --- a/src/V3Name.cpp +++ b/src/V3Name.cpp @@ -59,6 +59,7 @@ private: if (addPvt) { string newname = string("__PVT__")+nodep->name(); nodep->name(newname); + nodep->editCountInc(); } else { string rsvd = m_words.isKeyword(nodep->name()); if (rsvd != "") { @@ -66,6 +67,7 @@ private: +": "<prettyNameQ()); string newname = string("__SYM__")+nodep->name(); nodep->name(newname); + nodep->editCountInc(); } } nodep->user1(1); @@ -73,50 +75,53 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } // Add __PVT__ to names of local signals - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { // Don't iterate... Don't need temps for RANGES under the Var. rename(nodep, (!m_modp->isTop() && !nodep->isSigPublic() && !nodep->isFuncLocal() // Isn't exposed, and would mess up dpi import wrappers && !nodep->isTemp())); // Don't bother to rename internal signals } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!nodep->user1()) { iterateChildren(nodep); rename(nodep, false); } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp()) { iterate(nodep->varp()); nodep->name(nodep->varp()->name()); } } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { if (!nodep->user1()) { rename(nodep, !nodep->modp()->modPublic()); iterateChildren(nodep); } } - virtual void visit(AstMemberDType* nodep) { + virtual void visit(AstMemberDType* nodep) VL_OVERRIDE { if (!nodep->user1()) { rename(nodep, false); iterateChildren(nodep); } } - virtual void visit(AstMemberSel* nodep) { + virtual void visit(AstMemberSel* nodep) VL_OVERRIDE { if (!nodep->user1()) { rename(nodep, false); iterateChildren(nodep); } } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { if (!nodep->user1SetOnce()) { if (nodep->aboveScopep()) iterate(nodep->aboveScopep()); if (nodep->aboveCellp()) iterate(nodep->aboveCellp()); @@ -129,7 +134,7 @@ private: } //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3Number.cpp b/src/V3Number.cpp index f90b80e91..5bf498ae0 100644 --- a/src/V3Number.cpp +++ b/src/V3Number.cpp @@ -32,7 +32,6 @@ #include #define MAX_SPRINTF_DOUBLE_SIZE 100 // Maximum characters with a sprintf %e/%f/%g (probably < 30) -#define MAX_WIDTH 5*1024 // Maximum width before error // Number operations build output in-place so can't call e.g. foo.opX(foo) #define NUM_ASSERT_OP_ARGS1(arg1) \ @@ -125,10 +124,11 @@ void V3Number::V3NumberCreate(AstNode* nodep, const char* sourcep, FileLine* fl) value_startp = cp; if (atoi(widthn.c_str())) { - if (atoi(widthn.c_str()) < 0 || atoi(widthn.c_str()) > MAX_WIDTH) { + if (atoi(widthn.c_str()) < 0 || atoi(widthn.c_str()) > v3Global.opt.maxNumWidth()) { // atoi might convert large number to negative, so can't tell which - v3error("Unsupported: Width of number exceeds implementation limit: "<v3fatal("Unknown --make system specified: '"<rhsp(), VarRef)) { this->visit(varrefp); @@ -316,7 +316,7 @@ private: } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (m_inAss && nodep->varp()->attrClocker() == VVarAttrClocker::CLOCKER_YES) { if (m_inClocked) { nodep->v3warn(CLKDATA, @@ -329,7 +329,7 @@ private: } } } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { if (m_inAss) { iterateAndNextNull(nodep->lhsp()); int lw = m_childClkWidth; @@ -338,20 +338,20 @@ private: m_childClkWidth = lw + rw; // Pass up } } - virtual void visit(AstNodeSel* nodep) { + virtual void visit(AstNodeSel* nodep) VL_OVERRIDE { if (m_inAss) { iterateChildren(nodep); // Pass up result width if (m_childClkWidth > nodep->width()) m_childClkWidth = nodep->width(); } } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { if (m_inAss) { iterateChildren(nodep); if (m_childClkWidth > nodep->width()) m_childClkWidth = nodep->width(); } } - virtual void visit(AstReplicate* nodep) { + virtual void visit(AstReplicate* nodep) VL_OVERRIDE { if (m_inAss) { iterateChildren(nodep); if (VN_IS(nodep->rhsp(), Const)) { @@ -361,12 +361,12 @@ private: } } } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { m_inClocked = nodep->hasClocked(); iterateChildren(nodep); m_inClocked = false; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -394,7 +394,7 @@ private: bool m_clkAss; // There is signals marked as clocker in the assignment // METHODS VL_DEBUG_FUNC; // Declare debug() - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { if (const AstVarRef* varrefp = VN_CAST(nodep->lhsp(), VarRef)) { if (varrefp->varp()->attrClocker() == VVarAttrClocker::CLOCKER_YES) { m_clkAss = true; @@ -403,13 +403,13 @@ private: } iterateChildren(nodep->rhsp()); } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Previous versions checked attrClocker() here, but this breaks // the updated t_clocker VCD test. // If reenable this visitor note AstNodeMath short circuit below } - virtual void visit(AstNodeMath* nodep) {} // Accelerate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -973,7 +973,7 @@ private: } } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { { AstUser4InUse m_inuser4; // Used only when building tree, so below iterateChildren(nodep); @@ -981,7 +981,7 @@ private: // We're finished, complete the topscopes if (m_topScopep) { process(); m_topScopep=NULL; } } - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { // Process the last thing we're finishing UASSERT_OBJ(!m_topScopep, nodep, "Only one topscope should ever be created"); UINFO(2," Loading tree...\n"); @@ -1020,12 +1020,15 @@ private: AstNode::user3ClearTree(); AstNode::user4ClearTree(); } - virtual void visit(AstNodeModule* nodep) { - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + { + m_modp = nodep; + iterateChildren(nodep); + } + m_modp = origModp; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(4," SCOPE "<isTop() && nodep->varp()->isNonOutput()) { OrderVarVertex* varVxp = newVarUserVertex(nodep, WV_STD); new OrderEdge(&m_graph, m_inputsVxp, varVxp, WEIGHT_INPUT); } } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { if (m_scopep) { AstVarScope* varscp = nodep->varScopep(); UASSERT_OBJ(varscp, nodep, "Var didn't get varscoped in V3Scope.cpp"); @@ -1187,7 +1191,7 @@ private: } } } - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { // Having a node derived from the sentree isn't required for // correctness, it merely makes the graph better connected // and improves graph algorithmic performance @@ -1202,27 +1206,27 @@ private: m_inSenTree = false; } } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstAlwaysPost* nodep) { + virtual void visit(AstAlwaysPost* nodep) VL_OVERRIDE { m_inPost = true; iterateNewStmt(nodep); m_inPost = false; } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { OrderClkAssVisitor visitor(nodep); m_inClkAss = visitor.isClkAss(); iterateNewStmt(nodep); m_inClkAss = false; } - virtual void visit(AstAssignPre* nodep) { + virtual void visit(AstAssignPre* nodep) VL_OVERRIDE { OrderClkAssVisitor visitor(nodep); m_inClkAss = visitor.isClkAss(); m_inPre = true; @@ -1230,7 +1234,7 @@ private: m_inPre = false; m_inClkAss = false; } - virtual void visit(AstAssignPost* nodep) { + virtual void visit(AstAssignPost* nodep) VL_OVERRIDE { OrderClkAssVisitor visitor(nodep); m_inClkAss = visitor.isClkAss(); m_inPost = true; @@ -1238,15 +1242,15 @@ private: m_inPost = false; m_inClkAss = false; } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { iterateNewStmt(nodep); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { // We use initials to setup parameters and static consts's which may be referenced // in user initial blocks. So use ordering to sort them all out. iterateNewStmt(nodep); } - virtual void visit(AstCFunc*) { + virtual void visit(AstCFunc*) VL_OVERRIDE { // Ignore for now // We should detect what variables are set in the function, and make // settlement code for them, then set a global flag, so we call "settle" @@ -1254,7 +1258,7 @@ private: } //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -1479,7 +1483,7 @@ void OrderVisitor::processCircular() { for (V3GraphEdge* edgep = vvertexp->outBeginp(); edgep; edgep=edgep->outNextp()) { if (edgep->weight()==0) { // was cut OrderEdge* oedgep = dynamic_cast(edgep); - UASSERT_OBJ(oedgep, vvertexp->varScp(), "Cuttable edge not of proper type"); + UASSERT_OBJ(oedgep, vvertexp->varScp(), "Cutable edge not of proper type"); UINFO(6," CutCircularO: "<name()<inBeginp(); edgep; edgep = edgep->inNextp()) { if (edgep->weight()==0) { // was cut OrderEdge* oedgep = dynamic_cast(edgep); - UASSERT_OBJ(oedgep, vvertexp->varScp(), "Cuttable edge not of proper type"); + UASSERT_OBJ(oedgep, vvertexp->varScp(), "Cutable edge not of proper type"); UINFO(6," CutCircularI: "<name()<dead()) { UINFO(4," MOD-dead. "<recursiveClone()) { @@ -288,7 +288,7 @@ private: UINFO(4," MOD-dead? "<user5p(genHierNamep); @@ -296,7 +296,7 @@ private: } // Make sure all parameters are constantified - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { if (!nodep->user5SetOnce()) { // Process once iterateChildren(nodep); if (nodep->isParam()) { @@ -322,7 +322,7 @@ private: } } // Make sure varrefs cause vars to constify before things above - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->varp()) iterate(nodep->varp()); } bool ifaceParamReplace(AstVarXRef* nodep, AstNode* candp) { @@ -342,7 +342,7 @@ private: } return false; } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { // Check to see if the scope is just an interface because interfaces are special string dotted = nodep->dotted(); if (!dotted.empty() && nodep->varp() && nodep->varp()->isParam()) { @@ -382,7 +382,7 @@ private: nodep->varp(NULL); // Needs relink, as may remove pointed-to var } - virtual void visit(AstUnlinkedRef* nodep) { + virtual void visit(AstUnlinkedRef* nodep) VL_OVERRIDE { AstVarXRef* varxrefp = VN_CAST(nodep->op1p(), VarXRef); AstNodeFTaskRef* taskrefp = VN_CAST(nodep->op1p(), NodeFTaskRef); if (varxrefp) { @@ -403,7 +403,7 @@ private: nodep->replaceWith(nodep->op1p()->unlinkFrBack()); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstCellArrayRef* nodep) { + virtual void visit(AstCellArrayRef* nodep) VL_OVERRIDE { V3Const::constifyParamsEdit(nodep->selp()); if (const AstConst* constp = VN_CAST(nodep->selp(), Const)) { string index = AstNode::encodeNumber(constp->toSInt()); @@ -424,7 +424,7 @@ private: } // Generate Statements - virtual void visit(AstGenerate* nodep) { + virtual void visit(AstGenerate* nodep) VL_OVERRIDE { if (debug()>=9) nodep->dumpTree(cout, "-genin: "); iterateChildren(nodep); // After expanding the generate, all statements under it can be moved @@ -438,7 +438,7 @@ private: } VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstGenIf* nodep) { + virtual void visit(AstGenIf* nodep) VL_OVERRIDE { UINFO(9," GENIF "<condp()); // We suppress errors when widthing params since short-circuiting in @@ -468,7 +468,7 @@ private: //! @todo Unlike generated IF, we don't have to worry about short-circuiting the conditional //! expression, since this is currently restricted to simple comparisons. If we ever do //! move to more generic constant expressions, such code will be needed here. - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { if (nodep->genforp()) { AstGenFor* forp = VN_CAST(nodep->genforp(), GenFor); UASSERT_OBJ(forp, nodep, "Non-GENFOR under generate-for BEGIN"); @@ -477,7 +477,7 @@ private: UINFO(9," BEGIN "<v3fatalSrc("GENFOR should have been wrapped in BEGIN"); } - virtual void visit(AstGenCase* nodep) { + virtual void visit(AstGenCase* nodep) VL_OVERRIDE { UINFO(9," GENCASE "<exprp()); @@ -557,7 +557,7 @@ private: } // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Partition.cpp b/src/V3Partition.cpp index 99a3615fb..e6fbc3cfd 100644 --- a/src/V3Partition.cpp +++ b/src/V3Partition.cpp @@ -1766,7 +1766,7 @@ private: // METHODS VL_DEBUG_FUNC; - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (!m_tracingCall) return; m_tracingCall = false; if (nodep->dpiImportWrapper()) { @@ -1777,13 +1777,13 @@ private: } iterateChildren(nodep); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { iterateChildren(nodep); // Enter the function and trace it m_tracingCall = true; iterate(nodep->funcp()); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Premit.cpp b/src/V3Premit.cpp index 93d2ec935..50d1b010c 100644 --- a/src/V3Premit.cpp +++ b/src/V3Premit.cpp @@ -55,14 +55,14 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { //AstNode::user4ClearTree(); // Implied by AstUser4InUse // LHS first as fewer varrefs iterateAndNextNull(nodep->lhsp()); // Now find vars marked as lhs iterateAndNextNull(nodep->rhsp()); } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // it's LHS var is used so need a deep temporary if (nodep->lvalue()) { nodep->varp()->user4(true); @@ -73,7 +73,7 @@ private: } } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } @@ -197,14 +197,17 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<precondsp()); @@ -226,7 +229,7 @@ private: iterateAndNextNull(nodep->incsp()); m_stmtp = NULL; } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { startStatement(nodep); { bool noopt = PremitAssignVisitor(nodep).noOpt(); @@ -242,7 +245,7 @@ private: m_assignLhs = false; m_stmtp = NULL; } - virtual void visit(AstNodeStmt* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { if (!nodep->isStatement()) { iterateChildren(nodep); return; @@ -252,7 +255,7 @@ private: iterateChildren(nodep); m_stmtp = NULL; } - virtual void visit(AstTraceInc* nodep) { + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { startStatement(nodep); m_inTracep = nodep; iterateChildren(nodep); @@ -306,29 +309,29 @@ private: } iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstShiftL* nodep) { + virtual void visit(AstShiftL* nodep) VL_OVERRIDE { visitShift(nodep); } - virtual void visit(AstShiftR* nodep) { + virtual void visit(AstShiftR* nodep) VL_OVERRIDE { visitShift(nodep); } - virtual void visit(AstShiftRS* nodep) { + virtual void visit(AstShiftRS* nodep) VL_OVERRIDE { visitShift(nodep); } // Operators - virtual void visit(AstNodeTermop* nodep) { + virtual void visit(AstNodeTermop* nodep) VL_OVERRIDE { iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); { // Only the 'from' is part of the assignment LHS bool prevAssign = m_assignLhs; @@ -339,7 +342,7 @@ private: } checkNode(nodep); } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); { // Only the 'from' is part of the assignment LHS bool prevAssign = m_assignLhs; @@ -349,7 +352,7 @@ private: } checkNode(nodep); } - virtual void visit(AstAssocSel* nodep) { + virtual void visit(AstAssocSel* nodep) VL_OVERRIDE { iterateAndNextNull(nodep->fromp()); { // Only the 'from' is part of the assignment LHS bool prevAssign = m_assignLhs; @@ -359,10 +362,10 @@ private: } checkNode(nodep); } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { iterateChildren(nodep); checkNode(nodep); } - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { iterateChildren(nodep); if (nodep->expr1p()->isWide() && !VN_IS(nodep->condp(), Const) @@ -375,7 +378,7 @@ private: } // Autoflush - virtual void visit(AstDisplay* nodep) { + virtual void visit(AstDisplay* nodep) VL_OVERRIDE { startStatement(nodep); iterateChildren(nodep); m_stmtp = NULL; @@ -393,7 +396,7 @@ private: } } } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { iterateChildren(nodep); // Any strings sent to a display must be var of string data type, // to avoid passing a pointer to a temporary. @@ -408,8 +411,8 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstVar* nodep) {} // Don't hit varrefs under vars - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} // Don't hit varrefs under vars + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3ProtectLib.cpp b/src/V3ProtectLib.cpp index 434eae0f2..b44edf500 100644 --- a/src/V3ProtectLib.cpp +++ b/src/V3ProtectLib.cpp @@ -68,7 +68,7 @@ class ProtectVisitor : public AstNVisitor { bool m_foundTop; // Have seen the top module // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { m_vfilep = new AstVFile(nodep->fileline(), v3Global.opt.makeDir()+"/"+m_libName+".sv"); nodep->addFilesp(m_vfilep); @@ -78,7 +78,7 @@ class ProtectVisitor : public AstNVisitor { iterateChildren(nodep); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { if (!nodep->isTop()) { return; } else { @@ -347,7 +347,7 @@ class ProtectVisitor : public AstNVisitor { m_cfilep->tblockp(txtp); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { if (!nodep->isIO()) return; if (VN_IS(nodep->dtypep(), UnpackArrayDType)) { nodep->v3error("Unsupported: unpacked arrays with protect-lib on "<prettyNameQ()); @@ -366,7 +366,7 @@ class ProtectVisitor : public AstNVisitor { } } - virtual void visit(AstNode* nodep) { } + virtual void visit(AstNode* nodep) VL_OVERRIDE { } string cInputConnection(AstVar* varp) { string frstmt; diff --git a/src/V3Reloop.cpp b/src/V3Reloop.cpp index 9d0f9b61b..602299d03 100644 --- a/src/V3Reloop.cpp +++ b/src/V3Reloop.cpp @@ -148,12 +148,12 @@ private: } // VISITORS - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { m_cfuncp = nodep; iterateChildren(nodep); m_cfuncp = NULL; } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { if (!m_cfuncp) return; // Left select WordSel or ArraySel @@ -227,9 +227,9 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstVar* nodep) {} // Speedup - virtual void visit(AstNodeMath* nodep) {} // Speedup - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} // Speedup + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE {} // Speedup + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Scope.cpp b/src/V3Scope.cpp index ba05669d8..315394e48 100644 --- a/src/V3Scope.cpp +++ b/src/V3Scope.cpp @@ -88,7 +88,7 @@ private: } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { AstNodeModule* modp = nodep->topModulep(); if (!modp) { nodep->v3error("No top level module found"); return; } // Operate starting at the top of the hierarchy @@ -97,7 +97,7 @@ private: iterate(modp); cleanupVarRefs(); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Create required blocks and add to module string scopename; if (!m_aboveScopep) scopename = "TOP"; @@ -151,13 +151,13 @@ private: // ***Note m_scopep is passed back to the caller of the routine (above) } - virtual void visit(AstCellInline* nodep) { + virtual void visit(AstCellInline* nodep) VL_OVERRIDE { nodep->scopep(m_scopep); } - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { nodep->v3fatalSrc("Actives now made after scoping"); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -165,7 +165,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -173,7 +173,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -181,7 +181,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstAssignVarScope* nodep) { + virtual void visit(AstAssignVarScope* nodep) VL_OVERRIDE { // Copy under the scope but don't recurse UINFO(4," Move "<cloneTree(false); @@ -189,7 +189,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -197,7 +197,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -205,7 +205,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -213,7 +213,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," Move "<cloneTree(false); @@ -221,7 +221,7 @@ private: m_scopep->addActivep(clonep); iterateChildren(clonep); // We iterate under the *clone* } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," CFUNC "<cloneTree(false); @@ -231,7 +231,7 @@ private: // We iterate under the *clone* iterateChildren(clonep); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { // Add to list of blocks under this scope UINFO(4," FTASK "<cloneTree(false); @@ -240,7 +240,7 @@ private: // We iterate under the *clone* iterateChildren(clonep); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { // Make new scope variable // This is called cross-module by AstVar, so we cannot trust any m_ variables if (!nodep->user1p()) { @@ -259,7 +259,7 @@ private: m_scopep->addVarp(varscp); } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // VarRef needs to point to VarScope // Make sure variable has made user1p. UASSERT_OBJ(nodep->varp(), nodep, "Unlinked"); @@ -272,7 +272,7 @@ private: m_varRefScopes.insert(make_pair(nodep, m_scopep)); } } - virtual void visit(AstScopeName* nodep) { + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { // If there's a %m in the display text, we add a special node that will contain the name() string prefix = string("__DOT__")+m_scopep->name(); // TOP and above will be the user's name(). @@ -288,13 +288,13 @@ private: if (afterp) nodep->scopeEntrp(afterp); iterateChildren(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { // Scope that was made by this module for different cell; // Want to ignore blocks under it, so just do nothing } //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -322,7 +322,7 @@ private: VL_DEBUG_FUNC; // Declare debug() // VISITORS - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { // Want to ignore blocks under it m_scopep = nodep; iterateChildren(nodep); @@ -341,42 +341,42 @@ private: } } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstFinal* nodep) { + virtual void visit(AstFinal* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstAssignAlias* nodep) { + virtual void visit(AstAssignAlias* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstAssignVarScope* nodep) { + virtual void visit(AstAssignVarScope* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstAlwaysPublic* nodep) { + virtual void visit(AstAlwaysPublic* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstCoverToggle* nodep) { + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { movedDeleteOrIterate(nodep); } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { // The crossrefs are dealt with in V3LinkDot nodep->varp(NULL); } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { // The crossrefs are dealt with in V3LinkDot UINFO(9," Old pkg-taskref "<packagep()) { @@ -392,7 +392,7 @@ private: } iterateChildren(nodep); } - virtual void visit(AstModportFTaskRef* nodep) { + virtual void visit(AstModportFTaskRef* nodep) VL_OVERRIDE { // The crossrefs are dealt with in V3LinkDot nodep->ftaskp(NULL); iterateChildren(nodep); @@ -400,7 +400,7 @@ private: //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3SenTree.h b/src/V3SenTree.h index c5e2658dc..7c7911ff6 100644 --- a/src/V3SenTree.h +++ b/src/V3SenTree.h @@ -105,29 +105,29 @@ private: // VISITORS VL_DEBUG_FUNC; // Declare debug() - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { // Only do the top if (nodep->isTop()) { iterateChildren(nodep); } } - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { m_topscopep = nodep; iterateChildren(nodep); // Don't clear topscopep, the namer persists beyond this visit } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { // But no SenTrees under TopScope's scope } // Memorize existing block names - virtual void visit(AstActive* nodep) { + virtual void visit(AstActive* nodep) VL_OVERRIDE { // Don't grab SenTrees under Actives, only those that are global (under Scope directly) iterateChildren(nodep); } - virtual void visit(AstSenTree* nodep) { m_trees.add(nodep); } + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { m_trees.add(nodep); } // Empty visitors, speed things up - virtual void visit(AstNodeStmt* nodep) { } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { } + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } // METHODS diff --git a/src/V3Simulate.h b/src/V3Simulate.h index 280cf1f3c..f97876d6b 100644 --- a/src/V3Simulate.h +++ b/src/V3Simulate.h @@ -378,15 +378,15 @@ private: } // VISITORS - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; checkNodeInfo(nodep); iterateChildren(nodep); } - virtual void visit(AstSenTree* nodep) { + virtual void visit(AstSenTree* nodep) VL_OVERRIDE { // Sensitivities aren't inputs per se; we'll keep our tree under the same sens. } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; if (!optimizable()) return; // Accelerate UASSERT_OBJ(nodep->varp(), nodep, "Unlinked"); @@ -451,12 +451,12 @@ private: } } } - virtual void visit(AstVarXRef* nodep) { + virtual void visit(AstVarXRef* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; if (m_scoped) { badNodeType(nodep); return; } else { clearOptimizable(nodep, "Language violation: Dotted hierarchical references not allowed in constant functions"); } } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; if (!m_params) { badNodeType(nodep); return; } if (nodep->dpiImport()) { @@ -465,7 +465,7 @@ private: checkNodeInfo(nodep); iterateChildren(nodep); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; UINFO(5, " IF "<itemp(), nodep, "Not linked"); if (!m_checkOnly && optimizable()) { @@ -509,7 +509,7 @@ private: } } } - virtual void visit(AstNodeUniop* nodep) { + virtual void visit(AstNodeUniop* nodep) VL_OVERRIDE { if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); iterateChildren(nodep); @@ -518,7 +518,7 @@ private: fetchConst(nodep->lhsp())->num()); } } - virtual void visit(AstNodeBiop* nodep) { + virtual void visit(AstNodeBiop* nodep) VL_OVERRIDE { if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); iterateChildren(nodep); @@ -528,7 +528,7 @@ private: fetchConst(nodep->rhsp())->num()); } } - virtual void visit(AstNodeTriop* nodep) { + virtual void visit(AstNodeTriop* nodep) VL_OVERRIDE { if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); iterateChildren(nodep); @@ -539,7 +539,7 @@ private: fetchConst(nodep->thsp())->num()); } } - virtual void visit(AstLogAnd* nodep) { + virtual void visit(AstLogAnd* nodep) VL_OVERRIDE { // Need to short circuit if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); @@ -557,7 +557,7 @@ private: } } } - virtual void visit(AstLogOr* nodep) { + virtual void visit(AstLogOr* nodep) VL_OVERRIDE { // Need to short circuit if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); @@ -575,7 +575,7 @@ private: } } } - virtual void visit(AstLogIf* nodep) { + virtual void visit(AstLogIf* nodep) VL_OVERRIDE { // Need to short circuit, same as (!A || B) if (!optimizable()) return; // Accelerate checkNodeInfo(nodep); @@ -594,7 +594,7 @@ private: } } } - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { // We could use above visit(AstNodeTriop), but need to do short circuiting. // It's also slower even O(n^2) to evaluate both sides when we // really only need to evaluate one side. @@ -716,7 +716,7 @@ private: } } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; if (!optimizable()) return; // Accelerate if (VN_IS(nodep, AssignDly)) { @@ -751,7 +751,7 @@ private: } m_inDlyAssign = false; } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { checkNodeInfo(nodep); iterateChildren(nodep); if (AstInitArray* initp = VN_CAST(fetchValueNull(nodep->fromp()), InitArray)) { @@ -768,11 +768,11 @@ private: clearOptimizable(nodep, "Array select of non-array"); } } - virtual void visit(AstBegin* nodep) { + virtual void visit(AstBegin* nodep) VL_OVERRIDE { checkNodeInfo(nodep); iterateChildren(nodep); } - virtual void visit(AstNodeCase* nodep) { + virtual void visit(AstNodeCase* nodep) VL_OVERRIDE { if (jumpingOver(nodep)) return; UINFO(5, " CASE "<user1() && !VN_IS(nodep, AssignAlias)) { @@ -157,7 +157,7 @@ class SliceVisitor : public AstNVisitor { } } - virtual void visit(AstInitArray* nodep) { + virtual void visit(AstInitArray* nodep) VL_OVERRIDE { UASSERT_OBJ(!m_assignp, nodep, "Array initialization should have been removed earlier"); } @@ -171,11 +171,11 @@ class SliceVisitor : public AstNVisitor { if (AstUnpackArrayDType* adtypep = VN_CAST(fromDtp, UnpackArrayDType)) { AstNodeBiop* logp = NULL; if (!VN_IS(nodep->lhsp()->dtypep()->skipRefp(), NodeArrayDType)) { - nodep->lhsp()->v3error("Slice operatator "<lhsp()->prettyTypeName() + nodep->lhsp()->v3error("Slice operator "<lhsp()->prettyTypeName() <<" on non-slicable (e.g. non-vector) left-hand-side operand"); } else if (!VN_IS(nodep->rhsp()->dtypep()->skipRefp(), NodeArrayDType)) { - nodep->rhsp()->v3error("Slice operatator "<rhsp()->prettyTypeName() + nodep->rhsp()->v3error("Slice operator "<rhsp()->prettyTypeName() <<" on non-slicable (e.g. non-vector) right-hand-side operand"); } else { @@ -216,20 +216,20 @@ class SliceVisitor : public AstNVisitor { iterateChildren(nodep); } } - virtual void visit(AstEq* nodep) { + virtual void visit(AstEq* nodep) VL_OVERRIDE { expandBiOp(nodep); } - virtual void visit(AstNeq* nodep) { + virtual void visit(AstNeq* nodep) VL_OVERRIDE { expandBiOp(nodep); } - virtual void visit(AstEqCase* nodep) { + virtual void visit(AstEqCase* nodep) VL_OVERRIDE { expandBiOp(nodep); } - virtual void visit(AstNeqCase* nodep) { + virtual void visit(AstNeqCase* nodep) VL_OVERRIDE { expandBiOp(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Default: Just iterate iterateChildren(nodep); } diff --git a/src/V3Split.cpp b/src/V3Split.cpp index 388b7307f..f7eedfee3 100644 --- a/src/V3Split.cpp +++ b/src/V3Split.cpp @@ -346,19 +346,19 @@ protected: virtual void makeRvalueEdges(SplitVarStdVertex* vstdp) = 0; // VISITORS - virtual void visit(AstAlways* nodep) = 0; - virtual void visit(AstNodeIf* nodep) = 0; + virtual void visit(AstAlways* nodep) VL_OVERRIDE = 0; + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE = 0; // We don't do AstNodeFor/AstWhile loops, due to the standard question // of what is before vs. after - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { m_inDly = true; UINFO(4," ASSIGNDLY "<varScopep(); UASSERT_OBJ(vscp, nodep, "Not linked"); @@ -422,7 +422,7 @@ protected: } } - virtual void visit(AstJumpGo* nodep) { + virtual void visit(AstJumpGo* nodep) VL_OVERRIDE { // Jumps will disable reordering at all levels // This is overly pessimistic; we could treat jumps as barriers, and // reorder everything between jumps/labels, however jumps are rare @@ -434,7 +434,7 @@ protected: //-------------------- // Default - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // **** SPECIAL default type that sets PLI_ORDERING if (!m_stmtStackps.empty() && !nodep->isPure()) { UINFO(9," NotSplittable "<user3p(oldBlockUser3); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { UINFO(4," ALW "<=9) nodep->dumpTree(cout, " alwIn:: "); scoreboardClear(); @@ -614,7 +614,7 @@ protected: if (debug()>=9) nodep->dumpTree(cout, " alwOut: "); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { UINFO(4," IF "<condp()); processBlock(nodep->ifsp()); @@ -672,13 +672,13 @@ private: } protected: - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { m_ifStack.push_back(nodep); trackNode(nodep); iterateChildren(nodep); m_ifStack.pop_back(); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { trackNode(nodep); iterateChildren(nodep); } @@ -746,7 +746,7 @@ protected: return new AstSplitPlaceholder(m_origAlwaysp->fileline()); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { // Anything that's not an if/else we assume is a leaf // (that is, something we won't split.) Don't visit further // into the leaf. @@ -768,7 +768,7 @@ protected: m_addAfter[color] = clonedp; } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { const ColorSet& colors = m_ifColorp->colors(nodep); typedef vl_unordered_map CloneMap; CloneMap clones; @@ -829,10 +829,10 @@ public: } } virtual ~RemovePlaceholdersVisitor() {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstSplitPlaceholder* nodep) { + virtual void visit(AstSplitPlaceholder* nodep) VL_OVERRIDE { m_removeSet.insert(nodep); } private: @@ -876,7 +876,7 @@ public: // METHODS protected: - void makeRvalueEdges(SplitVarStdVertex* vstdp) { + virtual void makeRvalueEdges(SplitVarStdVertex* vstdp) VL_OVERRIDE { // Each 'if' depends on rvalues in its own conditional ONLY, // not rvalues in the if/else bodies. for (VStack::const_iterator it = m_stmtStackps.begin(); it != m_stmtStackps.end(); ++it) { @@ -955,7 +955,7 @@ protected: if (debug()>=9) m_graph.dumpDotFilePrefixed("splitg_colored", false); } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { // build the scoreboard scoreboardClear(); scanBlock(nodep->bodysp()); @@ -988,7 +988,7 @@ protected: emitSplit.go(); } } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { UINFO(4," IF "<condp()); diff --git a/src/V3SplitAs.cpp b/src/V3SplitAs.cpp index c9a78b02e..bc37cb0fa 100644 --- a/src/V3SplitAs.cpp +++ b/src/V3SplitAs.cpp @@ -55,13 +55,13 @@ private: AstVarScope* m_splitVscp; // Variable we want to split // METHODS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->lvalue() && !m_splitVscp && nodep->varp()->attrIsolateAssign()) { m_splitVscp = nodep->varScopep(); } } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -87,7 +87,7 @@ private: bool m_matches; // Statement below has matching lvalue reference // METHODS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (nodep->lvalue()) { if (nodep->varScopep()==m_splitVscp) { UINFO(6," CL VAR "<isStatement()) { iterateChildren(nodep); return; @@ -121,7 +121,7 @@ private: m_keepStmt = oldKeep || m_keepStmt; UINFO(9," upKeep="<dtypep()) { @@ -114,7 +114,7 @@ private: } } } - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { allNodes(nodep); iterateChildrenConst(nodep); if (m_counting) { @@ -123,7 +123,7 @@ private: } } } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { UINFO(4," IF i="<funcp()->entryPoint()) { @@ -186,7 +186,7 @@ private: iterate(nodep->funcp()); } } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { if (m_fast) { if (!m_tracingCall && !nodep->entryPoint()) return; m_tracingCall = false; @@ -196,11 +196,11 @@ private: iterateChildrenConst(nodep); m_cfuncp = NULL; } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { allNodes(nodep); iterateChildrenConst(nodep); } - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { if (m_fast && nodep->evalp()) { m_instrs = 0; m_counting = true; diff --git a/src/V3Subst.cpp b/src/V3Subst.cpp index 9e283e6cd..a63bd64d5 100644 --- a/src/V3Subst.cpp +++ b/src/V3Subst.cpp @@ -193,7 +193,7 @@ private: return reinterpret_cast(nodep->varp()->user1p()); // Might be NULL } // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { SubstVarEntry* entryp = findEntryp(nodep); if (entryp) { // Don't sweat it. We assign a new temp variable for every new assignment, @@ -206,8 +206,8 @@ private: } } } - virtual void visit(AstConst* nodep) {} // Accelerate - virtual void visit(AstNode* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE {} // Accelerate + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -261,7 +261,7 @@ private: } // VISITORS - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { m_ops = 0; m_assignStep++; iterateAndNextNull(nodep->rhsp()); @@ -311,7 +311,7 @@ private: VL_DO_DANGLING(pushDeletep(nodep), nodep); ++m_statSubsts; } - virtual void visit(AstWordSel* nodep) { + virtual void visit(AstWordSel* nodep) VL_OVERRIDE { iterate(nodep->rhsp()); AstVarRef* varrefp = VN_CAST(nodep->lhsp(), VarRef); AstConst* constp = VN_CAST(nodep->rhsp(), Const); @@ -338,7 +338,7 @@ private: iterate(nodep->lhsp()); } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Any variable if (nodep->lvalue()) { m_assignStep++; @@ -366,9 +366,9 @@ private: } } } - virtual void visit(AstVar* nodep) {} - virtual void visit(AstConst* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE {} + virtual void visit(AstConst* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { m_ops++; if (!nodep->isSubstOptimizable()) { m_ops = SUBST_MAX_OPS_NA; diff --git a/src/V3Table.cpp b/src/V3Table.cpp index 67817b87e..5c3710e65 100644 --- a/src/V3Table.cpp +++ b/src/V3Table.cpp @@ -80,7 +80,8 @@ private: // State cleared on each module AstNodeModule* m_modp; // Current MODULE int m_modTables; // Number of tables created in this module - std::deque m_modTableVscs; // All tables created + typedef std::deque ModTableVector; + ModTableVector m_modTableVscs; // All tables created // State cleared on each scope AstScope* m_scopep; // Current SCOPE @@ -423,37 +424,44 @@ private: // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildren(nodep); } - virtual void visit(AstNodeModule* nodep) { - m_modTables = 0; - m_modTableVscs.clear(); - m_modp = nodep; - iterateChildren(nodep); - m_modp = NULL; + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { + AstNodeModule* origModp = m_modp; + int origModTables = m_modTables; + ModTableVector origModTableVscs = m_modTableVscs; + { + m_modp = nodep; + m_modTables = 0; + m_modTableVscs.clear(); + iterateChildren(nodep); + } + m_modp = origModp; + m_modTables = origModTables; + m_modTableVscs = origModTableVscs; } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { UINFO(4," SCOPE "<taskp(), nodep, "Unlinked task"); new TaskEdge(&m_callGraph, m_curVxp, getFTaskVertex(nodep->taskp())); } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { UINFO(9," TASK "<pragType() == AstPragmaType::NO_INLINE_TASK) { // Just mark for the next steps, and we're done with it. m_curVxp->noInline(true); @@ -219,11 +219,11 @@ private: iterateChildren(nodep); } } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { iterateChildren(nodep); nodep->user4p(m_curVxp); // Remember what task it's under } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { iterateChildren(nodep); if (nodep->varp()->user4u().toGraphVertex() != m_curVxp) { if (m_curVxp->pure() @@ -234,7 +234,7 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -264,7 +264,7 @@ private: // AstVar::user2p // AstVarScope* to replace varref with // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { // Similar code in V3Inline if (nodep->varp()->user2p()) { // It's being converted to an alias. UINFO(9, " relinkVar "<varp()->user2p())<<" "<taskp(), nodep, "Unlinked?"); iterateIntoFTask(nodep->taskp()); // First, do hierarchical funcs UINFO(4," FTask REF "<v3fatalSrc("For statements should have been converted to while statements in V3Begin.cpp"); } - virtual void visit(AstNodeStmt* nodep) { + virtual void visit(AstNodeStmt* nodep) VL_OVERRIDE { if (!nodep->isStatement()) { iterateChildren(nodep); return; @@ -1283,7 +1288,7 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Trace.cpp b/src/V3Trace.cpp index f1954221f..864010e45 100644 --- a/src/V3Trace.cpp +++ b/src/V3Trace.cpp @@ -613,7 +613,7 @@ private: } // VISITORS - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { m_code = 1; // Multiple TopScopes will require fixing how code#s // are assigned as duplicate varscopes must result in the same tracing code#. @@ -641,17 +641,17 @@ private: assignActivity(); putTracesIntoTree(); } - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { if (nodep->isTop()) m_topModp = nodep; iterateChildren(nodep); } - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { AstScope* scopep = nodep->scopep(); UASSERT_OBJ(scopep, nodep, "No scope found on top level"); m_highScopep = scopep; iterateChildren(nodep); } - virtual void visit(AstCCall* nodep) { + virtual void visit(AstCCall* nodep) VL_OVERRIDE { UINFO(8," CCALL "<user2()) { // See if there are other calls in same statement list; @@ -669,7 +669,7 @@ private: } iterateChildren(nodep); } - virtual void visit(AstCFunc* nodep) { + virtual void visit(AstCFunc* nodep) VL_OVERRIDE { UINFO(8," CFUNC "<funcType() == AstCFuncType::TRACE_INIT) { m_initFuncp = nodep; @@ -693,7 +693,7 @@ private: iterateChildren(nodep); m_funcp = NULL; } - virtual void visit(AstTraceInc* nodep) { + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE { UINFO(8," TRACE "<unlinkFrBack(); @@ -706,7 +706,7 @@ private: iterateChildren(nodep); m_tracep = NULL; } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (m_tracep) { UASSERT_OBJ(nodep->varScopep(), nodep, "No var scope?"); UASSERT_OBJ(!nodep->lvalue(), nodep, "Lvalue in trace? Should be const."); @@ -732,7 +732,7 @@ private: } } //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3TraceDecl.cpp b/src/V3TraceDecl.cpp index 3b8ef8919..2ab19efc4 100644 --- a/src/V3TraceDecl.cpp +++ b/src/V3TraceDecl.cpp @@ -143,7 +143,7 @@ private: } // VISITORS - virtual void visit(AstTopScope* nodep) { + virtual void visit(AstTopScope* nodep) VL_OVERRIDE { m_scopetopp = nodep->scopep(); // Make containers for TRACEDECLs first m_initFuncp = newCFunc(AstCFuncType::TRACE_INIT, "traceInitThis", true); @@ -154,7 +154,7 @@ private: // And find variables iterateChildren(nodep); } - virtual void visit(AstScope* nodep) { + virtual void visit(AstScope* nodep) VL_OVERRIDE { AstCell* cellp = VN_CAST(nodep->aboveCellp(), Cell); if (cellp && VN_IS(cellp->modp(), Iface)) { AstCFunc* origSubFunc = m_initSubFuncp; @@ -192,7 +192,7 @@ private: iterateChildren(nodep); } } - virtual void visit(AstVarScope* nodep) { + virtual void visit(AstVarScope* nodep) VL_OVERRIDE { iterateChildren(nodep); // Prefilter - things that get through this if will either get // traced or get a comment as to why not traced. @@ -224,7 +224,7 @@ private: else m_traValuep = new AstVarRef(nodep->fileline(), nodep, false); { // Recurse into data type of the signal; the visitors will call addTraceDecl() - iterate(varp->dtypeSkipRefp()); + iterate(varp->dtypep()->skipRefToEnump()); } // Cleanup if (m_traValuep) VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = NULL); @@ -235,33 +235,33 @@ private: } } // VISITORS - Data types when tracing - virtual void visit(AstConstDType* nodep) { + virtual void visit(AstConstDType* nodep) VL_OVERRIDE { if (m_traVscp) { - iterate(nodep->subDTypep()->skipRefp()); + iterate(nodep->subDTypep()->skipRefToEnump()); } } - virtual void visit(AstRefDType* nodep) { + virtual void visit(AstRefDType* nodep) VL_OVERRIDE { if (m_traVscp) { - iterate(nodep->subDTypep()->skipRefp()); + iterate(nodep->subDTypep()->skipRefToEnump()); } } - virtual void visit(AstUnpackArrayDType* nodep) { + virtual void visit(AstUnpackArrayDType* nodep) VL_OVERRIDE { // Note more specific dtypes above if (m_traVscp) { if (static_cast(nodep->arrayUnpackedElements()) > v3Global.opt.traceMaxArray()) { addIgnore("Wide memory > --trace-max-array ents"); - } else if (VN_IS(nodep->subDTypep()->skipRefp(), BasicDType) // Nothing lower than this array - && m_traVscp->dtypep()->skipRefp() == nodep) { // Nothing above this array + } else if (VN_IS(nodep->subDTypep()->skipRefToEnump(), BasicDType) // Nothing lower than this array + && m_traVscp->dtypep()->skipRefToEnump() == nodep) { // Nothing above this array // Simple 1-D array, use existing V3EmitC runtime loop rather than unrolling // This will put "(index)" at end of signal name for us - if (m_traVscp->dtypep()->skipRefp()->isString()) { + if (m_traVscp->dtypep()->skipRefToEnump()->isString()) { addIgnore("Unsupported: strings"); } else { addTraceDecl(nodep->declRange(), 0); } } else { // Unroll now, as have no other method to get right signal names - AstNodeDType* subtypep = nodep->subDTypep()->skipRefp(); + AstNodeDType* subtypep = nodep->subDTypep()->skipRefToEnump(); for (int i=nodep->lsb(); i<=nodep->msb(); ++i) { string oldShowname = m_traShowname; AstNode* oldValuep = m_traValuep; @@ -271,6 +271,7 @@ private: m_traValuep->cloneTree(true), i - nodep->lsb()); + m_traValuep->dtypep(subtypep); iterate(subtypep); VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = NULL); } @@ -280,7 +281,7 @@ private: } } } - virtual void visit(AstPackArrayDType* nodep) { + virtual void visit(AstPackArrayDType* nodep) VL_OVERRIDE { if (m_traVscp) { if (!v3Global.opt.traceStructs()) { // Everything downstream is packed, so deal with as one trace unit. @@ -288,7 +289,7 @@ private: // a much faster way to trace addTraceDecl(VNumRange(), nodep->width()); } else { - AstNodeDType* subtypep = nodep->subDTypep()->skipRefp(); + AstNodeDType* subtypep = nodep->subDTypep()->skipRefToEnump(); for (int i=nodep->lsb(); i<=nodep->msb(); ++i) { string oldShowname = m_traShowname; AstNode* oldValuep = m_traValuep; @@ -297,6 +298,7 @@ private: m_traValuep = new AstSel(nodep->fileline(), m_traValuep->cloneTree(true), (i - nodep->lsb())*subtypep->width(), subtypep->width()); + m_traValuep->dtypep(subtypep); iterate(subtypep); VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = NULL); } @@ -306,7 +308,7 @@ private: } } } - virtual void visit(AstNodeUOrStructDType* nodep) { + virtual void visit(AstNodeUOrStructDType* nodep) VL_OVERRIDE { if (m_traVscp) { if (nodep->packed() && !v3Global.opt.traceStructs()) { // Everything downstream is packed, so deal with as one trace unit @@ -319,7 +321,7 @@ private: } else { for (AstMemberDType* itemp = nodep->membersp(); itemp; itemp=VN_CAST(itemp->nextp(), MemberDType)) { - AstNodeDType* subtypep = itemp->subDTypep()->skipRefp(); + AstNodeDType* subtypep = itemp->subDTypep()->skipRefToEnump(); string oldShowname = m_traShowname; AstNode* oldValuep = m_traValuep; { @@ -328,6 +330,7 @@ private: m_traValuep = new AstSel(nodep->fileline(), m_traValuep->cloneTree(true), itemp->lsb(), subtypep->width()); + m_traValuep->dtypep(subtypep); iterate(subtypep); VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = NULL); } else { // Else union, replicate fields @@ -341,7 +344,7 @@ private: } } } - virtual void visit(AstBasicDType* nodep) { + virtual void visit(AstBasicDType* nodep) VL_OVERRIDE { if (m_traVscp) { if (nodep->isString()) { addIgnore("Unsupported: strings"); @@ -350,14 +353,17 @@ private: } } } - virtual void visit(AstNodeDType* nodep) { + virtual void visit(AstEnumDType* nodep) VL_OVERRIDE { + iterate(nodep->skipRefp()); + } + virtual void visit(AstNodeDType* nodep) VL_OVERRIDE { // Note more specific dtypes above if (!m_traVscp) return; addIgnore("Unsupported: data type"); } //-------------------- - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Tristate.cpp b/src/V3Tristate.cpp index 587aa572c..85cba19b8 100644 --- a/src/V3Tristate.cpp +++ b/src/V3Tristate.cpp @@ -136,6 +136,7 @@ public: // CONSTRUCTORS TristateGraph() { clear(); } virtual ~TristateGraph() { clear(); } + VL_UNCOPYABLE(TristateGraph); private: // METHODS @@ -212,6 +213,7 @@ private: public: // METHODS + bool empty() const { return m_graph.empty(); } void clear() { for (V3GraphVertex* itp = m_graph.verticesBeginp(); itp; itp=itp->verticesNextp()) { TristateVertex* vvertexp = static_cast(itp); @@ -286,7 +288,7 @@ class TristatePinVisitor : public TristateBaseVisitor { TristateGraph& m_tgraph; bool m_lvalue; // Flip to be an LVALUE // VISITORS - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (m_lvalue && !nodep->lvalue()) { UINFO(9," Flip-to-LValue "<lvalue(true); @@ -298,17 +300,17 @@ class TristatePinVisitor : public TristateBaseVisitor { m_tgraph.setTristate(nodep->varp()); } } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { // Doesn't work because we'd set lvalue on the array index's var UASSERT_OBJ(!m_lvalue, nodep, "ArraySel conversion to output, under tristate node"); iterateChildren(nodep); } - virtual void visit(AstSliceSel* nodep) { + virtual void visit(AstSliceSel* nodep) VL_OVERRIDE { // Doesn't work because we'd set lvalue on the array index's var UASSERT_OBJ(!m_lvalue, nodep, "SliceSel conversion to output, under tristate node"); iterateChildren(nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: @@ -646,7 +648,7 @@ class TristateVisitor : public TristateBaseVisitor { } // VISITORS - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { UINFO(9,dbgState()<num().hasZ()) { @@ -682,7 +684,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstCond* nodep) { + virtual void visit(AstCond* nodep) VL_OVERRIDE { if (m_graphing) { iterateChildren(nodep); if (m_alhs) { @@ -725,7 +727,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { if (m_graphing) { iterateChildren(nodep); if (m_alhs) { @@ -763,7 +765,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { if (m_graphing) { iterateChildren(nodep); if (m_alhs) { @@ -813,7 +815,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstBufIf1* nodep) { + virtual void visit(AstBufIf1* nodep) VL_OVERRIDE { // For BufIf1, the enable is the LHS expression iterateChildren(nodep); UINFO(9,dbgState()<user1p(NULL); } } - virtual void visit(AstAnd* nodep) { + virtual void visit(AstAnd* nodep) VL_OVERRIDE { visitAndOr(nodep, true); } - virtual void visit(AstOr* nodep) { + virtual void visit(AstOr* nodep) VL_OVERRIDE { visitAndOr(nodep, false); } @@ -939,10 +941,10 @@ class TristateVisitor : public TristateBaseVisitor { m_alhs = false; } } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { visitAssign(nodep); } - virtual void visit(AstAssign* nodep) { + virtual void visit(AstAssign* nodep) VL_OVERRIDE { visitAssign(nodep); } @@ -993,20 +995,20 @@ class TristateVisitor : public TristateBaseVisitor { return; } } - virtual void visit(AstEqCase* nodep) { + virtual void visit(AstEqCase* nodep) VL_OVERRIDE { visitCaseEq(nodep, false); } - virtual void visit(AstNeqCase* nodep) { + virtual void visit(AstNeqCase* nodep) VL_OVERRIDE { visitCaseEq(nodep, true); } - virtual void visit(AstEqWild* nodep) { + virtual void visit(AstEqWild* nodep) VL_OVERRIDE { visitEqNeqWild(nodep); } - virtual void visit(AstNeqWild* nodep) { + virtual void visit(AstNeqWild* nodep) VL_OVERRIDE { visitEqNeqWild(nodep); } - virtual void visit(AstPull* nodep) { + virtual void visit(AstPull* nodep) VL_OVERRIDE { UINFO(9,dbgState()<lhsp(), VarRef)) { @@ -1083,7 +1085,7 @@ class TristateVisitor : public TristateBaseVisitor { // __out(to-resolver-only) // const inout Spec says illegal // const output Unsupported; Illegal? - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { if (m_graphing) { if (nodep->user2() & U2_GRAPHING) return; // This pin is already expanded nodep->user2(U2_GRAPHING); @@ -1238,7 +1240,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { UINFO(9,dbgState()<lvalue()) { @@ -1272,7 +1274,7 @@ class TristateVisitor : public TristateBaseVisitor { } } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { iterateChildren(nodep); UINFO(9,dbgState()<bodysp()); } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { m_cellp = nodep; m_alhs = false; iterateChildren(nodep); m_cellp = NULL; } - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { iterateChildrenBackwards(nodep); } // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); checkUnhandled(nodep); } diff --git a/src/V3Undriven.cpp b/src/V3Undriven.cpp index 0ca8e06a7..59c85dc9c 100644 --- a/src/V3Undriven.cpp +++ b/src/V3Undriven.cpp @@ -274,7 +274,7 @@ private: } // VISITORS - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { for (int usr=1; usr<(m_alwaysCombp?3:2); ++usr) { // For assigns and non-combo always, do just usr==1, to look // for module-wide undriven etc. @@ -299,15 +299,15 @@ private: // Discover variables used in bit definitions, etc iterateChildren(nodep); } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { // Arrays are rarely constant assigned, so for now we punt and do all entries iterateChildren(nodep); } - virtual void visit(AstSliceSel* nodep) { + virtual void visit(AstSliceSel* nodep) VL_OVERRIDE { // Arrays are rarely constant assigned, so for now we punt and do all entries iterateChildren(nodep); } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { AstNodeVarRef* varrefp = VN_CAST(nodep->fromp(), NodeVarRef); AstConst* constp = VN_CAST(nodep->lsbp(), Const); if (varrefp && constp && !constp->num().isFourState()) { @@ -330,7 +330,7 @@ private: iterateChildren(nodep); } } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { // Any variable if (nodep->lvalue() && !VN_IS(nodep, VarXRef)) { // Ignore interface variables and similar ugly items @@ -363,14 +363,14 @@ private: } // Don't know what black boxed calls do, assume in+out - virtual void visit(AstSysIgnore* nodep) { + virtual void visit(AstSysIgnore* nodep) VL_OVERRIDE { bool prevMark = m_inBBox; m_inBBox = true; iterateChildren(nodep); m_inBBox = prevMark; } - virtual void visit(AstAssign* nodep) { + virtual void visit(AstAssign* nodep) VL_OVERRIDE { bool prevProc = m_inProcAssign; { m_inProcAssign = true; @@ -378,7 +378,7 @@ private: } m_inProcAssign = prevProc; } - virtual void visit(AstAssignDly* nodep) { + virtual void visit(AstAssignDly* nodep) VL_OVERRIDE { bool prevProc = m_inProcAssign; { m_inProcAssign = true; @@ -386,7 +386,7 @@ private: } m_inProcAssign = prevProc; } - virtual void visit(AstAssignW* nodep) { + virtual void visit(AstAssignW* nodep) VL_OVERRIDE { bool prevCont = m_inContAssign; { m_inContAssign = true; @@ -394,7 +394,7 @@ private: } m_inContAssign = prevCont; } - virtual void visit(AstAlways* nodep) { + virtual void visit(AstAlways* nodep) VL_OVERRIDE { AstAlways* prevAlwp = m_alwaysCombp; { AstNode::user2ClearTree(); @@ -407,7 +407,7 @@ private: m_alwaysCombp = prevAlwp; } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { AstNodeFTask* prevTaskp = m_taskp; m_taskp = nodep; iterateChildren(nodep); @@ -415,18 +415,18 @@ private: } // Until we support tables, primitives will have undriven and unused I/Os - virtual void visit(AstPrimitive* nodep) {} + virtual void visit(AstPrimitive* nodep) VL_OVERRIDE {} // Coverage artifacts etc shouldn't count as a sink - virtual void visit(AstCoverDecl* nodep) {} - virtual void visit(AstCoverInc* nodep) {} - virtual void visit(AstCoverToggle* nodep) {} - virtual void visit(AstTraceDecl* nodep) {} - virtual void visit(AstTraceInc* nodep) {} + virtual void visit(AstCoverDecl* nodep) VL_OVERRIDE {} + virtual void visit(AstCoverInc* nodep) VL_OVERRIDE {} + virtual void visit(AstCoverToggle* nodep) VL_OVERRIDE {} + virtual void visit(AstTraceDecl* nodep) VL_OVERRIDE {} + virtual void visit(AstTraceInc* nodep) VL_OVERRIDE {} // iterate - virtual void visit(AstConst* nodep) {} - virtual void visit(AstNode* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE {} + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } public: diff --git a/src/V3Unknown.cpp b/src/V3Unknown.cpp index 34d6cb2a7..fb299cb0f 100644 --- a/src/V3Unknown.cpp +++ b/src/V3Unknown.cpp @@ -145,30 +145,33 @@ private: } // VISITORS - virtual void visit(AstNodeModule* nodep) { + virtual void visit(AstNodeModule* nodep) VL_OVERRIDE { UINFO(4," MOD "<condsp()); m_constXCvt = true; iterateAndNextNull(nodep->bodysp()); } - virtual void visit(AstNodeDType* nodep) { + virtual void visit(AstNodeDType* nodep) VL_OVERRIDE { m_constXCvt = false; // Avoid losing the X's in casex iterateChildren(nodep); m_constXCvt = true; @@ -240,19 +243,19 @@ private: } } - virtual void visit(AstEqCase* nodep) { + virtual void visit(AstEqCase* nodep) VL_OVERRIDE { visitEqNeqCase(nodep); } - virtual void visit(AstNeqCase* nodep) { + virtual void visit(AstNeqCase* nodep) VL_OVERRIDE { visitEqNeqCase(nodep); } - virtual void visit(AstEqWild* nodep) { + virtual void visit(AstEqWild* nodep) VL_OVERRIDE { visitEqNeqWild(nodep); } - virtual void visit(AstNeqWild* nodep) { + virtual void visit(AstNeqWild* nodep) VL_OVERRIDE { visitEqNeqWild(nodep); } - virtual void visit(AstIsUnknown* nodep) { + virtual void visit(AstIsUnknown* nodep) VL_OVERRIDE { iterateChildren(nodep); // Ahh, we're two state, so this is easy UINFO(4," ISUNKNOWN->0 "<replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { if (m_constXCvt && nodep->num().isFourState()) { UINFO(4," CONST4 "<user1SetOnce()) { // Guard against reading/writing past end of bit vector array @@ -376,7 +379,7 @@ private: // visit(AstSliceSel) not needed as its bounds are constant and checked // in V3Width. - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { iterateChildren(nodep); if (!nodep->user1SetOnce()) { if (debug()==9) nodep->dumpTree(cout, "-in: "); @@ -454,7 +457,7 @@ private: } //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } diff --git a/src/V3Unroll.cpp b/src/V3Unroll.cpp index 44e6ace30..8888aed55 100644 --- a/src/V3Unroll.cpp +++ b/src/V3Unroll.cpp @@ -124,6 +124,12 @@ private: if (VN_IS(nodep, GenFor) && !m_forVarp->isGenVar()) { nodep->v3error("Non-genvar used in generate for: "<prettyNameQ()<isGenVar()) { + nodep->v3error("Genvar not legal in non-generate for (IEEE 2017 27.4): " + << m_forVarp->prettyNameQ() << endl + << nodep->warnMore() + << "... Suggest move for loop upwards to generate-level scope."); + } if (m_generate) V3Const::constifyParamsEdit(initAssp->rhsp()); // rhsp may change // This check shouldn't be needed when using V3Simulate @@ -367,7 +373,7 @@ private: return true; } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { iterateChildren(nodep); if (m_varModeCheck || m_varModeReplace) { } else { @@ -396,7 +402,7 @@ private: } } } - virtual void visit(AstGenFor* nodep) { + virtual void visit(AstGenFor* nodep) VL_OVERRIDE { if (!m_generate || m_varModeReplace) { iterateChildren(nodep); } // else V3Param will recursively call each for loop to be unrolled for us @@ -424,7 +430,7 @@ private: } } } - virtual void visit(AstNodeFor* nodep) { + virtual void visit(AstNodeFor* nodep) VL_OVERRIDE { if (m_generate) { // Ignore for's when expanding genfor's iterateChildren(nodep); } else { @@ -432,7 +438,7 @@ private: } } - virtual void visit(AstVarRef* nodep) { + virtual void visit(AstVarRef* nodep) VL_OVERRIDE { if (m_varModeCheck && nodep->varp() == m_forVarp && nodep->varScopep() == m_forVscp @@ -453,7 +459,7 @@ private: //-------------------- // Default: Just iterate - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { if (m_varModeCheck && nodep == m_ignoreIncp) { // Ignore subtree that is the increment } else { diff --git a/src/V3Width.cpp b/src/V3Width.cpp index bc325c313..d29b0a75d 100644 --- a/src/V3Width.cpp +++ b/src/V3Width.cpp @@ -220,121 +220,121 @@ private: // _Ox=anything // Widths: 1 bit out, lhs 1 bit; Real: converts via compare with 0 - virtual void visit(AstLogNot* nodep) { visit_log_not(nodep); } + virtual void visit(AstLogNot* nodep) VL_OVERRIDE { visit_log_not(nodep); } // Widths: 1 bit out, lhs 1 bit, rhs 1 bit; Real: converts via compare with 0 - virtual void visit(AstLogAnd* nodep) { visit_log_and_or(nodep); } - virtual void visit(AstLogOr* nodep) { visit_log_and_or(nodep); } - virtual void visit(AstLogEq* nodep) { visit_log_and_or(nodep); } // Conversion from real not in IEEE, but a fallout - virtual void visit(AstLogIf* nodep) { visit_log_and_or(nodep); } // Conversion from real not in IEEE, but a fallout + virtual void visit(AstLogAnd* nodep) VL_OVERRIDE { visit_log_and_or(nodep); } + virtual void visit(AstLogOr* nodep) VL_OVERRIDE { visit_log_and_or(nodep); } + virtual void visit(AstLogEq* nodep) VL_OVERRIDE { visit_log_and_or(nodep); } // Conversion from real not in IEEE, but a fallout + virtual void visit(AstLogIf* nodep) VL_OVERRIDE { visit_log_and_or(nodep); } // Conversion from real not in IEEE, but a fallout // Widths: 1 bit out, Any width lhs - virtual void visit(AstRedAnd* nodep) { visit_red_and_or(nodep); } - virtual void visit(AstRedOr* nodep) { visit_red_and_or(nodep); } - virtual void visit(AstRedXnor* nodep){ visit_red_and_or(nodep); } - virtual void visit(AstRedXor* nodep) { visit_red_and_or(nodep); } - virtual void visit(AstOneHot* nodep) { visit_red_and_or(nodep); } - virtual void visit(AstOneHot0* nodep) { visit_red_and_or(nodep); } - virtual void visit(AstIsUnknown* nodep) { visit_red_unknown(nodep); } // Allow real + virtual void visit(AstRedAnd* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstRedOr* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstRedXnor* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstRedXor* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstOneHot* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstOneHot0* nodep) VL_OVERRIDE { visit_red_and_or(nodep); } + virtual void visit(AstIsUnknown* nodep) VL_OVERRIDE { visit_red_unknown(nodep); } // Allow real // These have different node types, as they operate differently // Must add to case statement below, // Widths: 1 bit out, lhs width == rhs width. real if lhs|rhs real - virtual void visit(AstEq* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstNeq* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstGt* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstGte* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstLt* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstLte* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstGtS* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstGteS* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstLtS* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstLteS* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstEqCase* nodep) { visit_cmp_eq_gt(nodep, true); } - virtual void visit(AstNeqCase* nodep) { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstEq* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstNeq* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstGt* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstGte* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstLt* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstLte* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstGtS* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstGteS* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstLtS* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstLteS* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstEqCase* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } + virtual void visit(AstNeqCase* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, true); } // ... These comparisons don't allow reals - virtual void visit(AstEqWild* nodep) { visit_cmp_eq_gt(nodep, false); } - virtual void visit(AstNeqWild* nodep) { visit_cmp_eq_gt(nodep, false); } + virtual void visit(AstEqWild* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, false); } + virtual void visit(AstNeqWild* nodep) VL_OVERRIDE { visit_cmp_eq_gt(nodep, false); } // ... Real compares - virtual void visit(AstEqD* nodep) { visit_cmp_real(nodep); } - virtual void visit(AstNeqD* nodep) { visit_cmp_real(nodep); } - virtual void visit(AstLtD* nodep) { visit_cmp_real(nodep); } - virtual void visit(AstLteD* nodep) { visit_cmp_real(nodep); } - virtual void visit(AstGtD* nodep) { visit_cmp_real(nodep); } - virtual void visit(AstGteD* nodep) { visit_cmp_real(nodep); } + virtual void visit(AstEqD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } + virtual void visit(AstNeqD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } + virtual void visit(AstLtD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } + virtual void visit(AstLteD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } + virtual void visit(AstGtD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } + virtual void visit(AstGteD* nodep) VL_OVERRIDE { visit_cmp_real(nodep); } // ... String compares - virtual void visit(AstEqN* nodep) { visit_cmp_string(nodep); } - virtual void visit(AstNeqN* nodep) { visit_cmp_string(nodep); } - virtual void visit(AstLtN* nodep) { visit_cmp_string(nodep); } - virtual void visit(AstLteN* nodep) { visit_cmp_string(nodep); } - virtual void visit(AstGtN* nodep) { visit_cmp_string(nodep); } - virtual void visit(AstGteN* nodep) { visit_cmp_string(nodep); } + virtual void visit(AstEqN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } + virtual void visit(AstNeqN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } + virtual void visit(AstLtN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } + virtual void visit(AstLteN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } + virtual void visit(AstGtN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } + virtual void visit(AstGteN* nodep) VL_OVERRIDE { visit_cmp_string(nodep); } // Widths: out width = lhs width = rhs width // Signed: Output signed iff LHS & RHS signed. // Real: Not allowed - virtual void visit(AstAnd* nodep) { visit_boolmath_and_or(nodep); } - virtual void visit(AstOr* nodep) { visit_boolmath_and_or(nodep); } - virtual void visit(AstXnor* nodep) { visit_boolmath_and_or(nodep); } - virtual void visit(AstXor* nodep) { visit_boolmath_and_or(nodep); } - virtual void visit(AstBufIf1* nodep) { visit_boolmath_and_or(nodep); } // Signed behavior changing in 3.814 + virtual void visit(AstAnd* nodep) VL_OVERRIDE { visit_boolmath_and_or(nodep); } + virtual void visit(AstOr* nodep) VL_OVERRIDE { visit_boolmath_and_or(nodep); } + virtual void visit(AstXnor* nodep) VL_OVERRIDE { visit_boolmath_and_or(nodep); } + virtual void visit(AstXor* nodep) VL_OVERRIDE { visit_boolmath_and_or(nodep); } + virtual void visit(AstBufIf1* nodep) VL_OVERRIDE { visit_boolmath_and_or(nodep); } // Signed behavior changing in 3.814 // Width: Max(Lhs,Rhs) sort of. // Real: If either side real // Signed: If both sides real - virtual void visit(AstAdd* nodep) { visit_add_sub_replace(nodep, true); } - virtual void visit(AstSub* nodep) { visit_add_sub_replace(nodep, true); } - virtual void visit(AstDiv* nodep) { visit_add_sub_replace(nodep, true); } - virtual void visit(AstMul* nodep) { visit_add_sub_replace(nodep, true); } + virtual void visit(AstAdd* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, true); } + virtual void visit(AstSub* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, true); } + virtual void visit(AstDiv* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, true); } + virtual void visit(AstMul* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, true); } // These can't promote to real - virtual void visit(AstModDiv* nodep) { visit_add_sub_replace(nodep, false); } - virtual void visit(AstModDivS* nodep) { visit_add_sub_replace(nodep, false); } - virtual void visit(AstMulS* nodep) { visit_add_sub_replace(nodep, false); } - virtual void visit(AstDivS* nodep) { visit_add_sub_replace(nodep, false); } + virtual void visit(AstModDiv* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, false); } + virtual void visit(AstModDivS* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, false); } + virtual void visit(AstMulS* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, false); } + virtual void visit(AstDivS* nodep) VL_OVERRIDE { visit_add_sub_replace(nodep, false); } // Widths: out width = lhs width, but upper matters // Signed: Output signed iff LHS signed; unary operator // Unary promote to real - virtual void visit(AstNegate* nodep) { visit_negate_not(nodep, true); } + virtual void visit(AstNegate* nodep) VL_OVERRIDE { visit_negate_not(nodep, true); } // Unary never real - virtual void visit(AstNot* nodep) { visit_negate_not(nodep, false); } + virtual void visit(AstNot* nodep) VL_OVERRIDE { visit_negate_not(nodep, false); } // Real: inputs and output real - virtual void visit(AstAddD* nodep) { visit_real_add_sub(nodep); } - virtual void visit(AstSubD* nodep) { visit_real_add_sub(nodep); } - virtual void visit(AstDivD* nodep) { visit_real_add_sub(nodep); } - virtual void visit(AstMulD* nodep) { visit_real_add_sub(nodep); } - virtual void visit(AstPowD* nodep) { visit_real_add_sub(nodep); } - virtual void visit(AstNodeSystemBiop* nodep) { visit_real_add_sub(nodep); } + virtual void visit(AstAddD* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } + virtual void visit(AstSubD* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } + virtual void visit(AstDivD* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } + virtual void visit(AstMulD* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } + virtual void visit(AstPowD* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } + virtual void visit(AstNodeSystemBiop* nodep) VL_OVERRIDE { visit_real_add_sub(nodep); } // Real: Output real - virtual void visit(AstNegateD* nodep) { visit_real_neg_ceil(nodep); } - virtual void visit(AstNodeSystemUniop* nodep) { visit_real_neg_ceil(nodep); } + virtual void visit(AstNegateD* nodep) VL_OVERRIDE { visit_real_neg_ceil(nodep); } + virtual void visit(AstNodeSystemUniop* nodep) VL_OVERRIDE { visit_real_neg_ceil(nodep); } // Widths: out signed/unsigned width = lhs width, input un|signed - virtual void visit(AstSigned* nodep) { + virtual void visit(AstSigned* nodep) VL_OVERRIDE { visit_signed_unsigned(nodep, AstNumeric::SIGNED); } - virtual void visit(AstUnsigned* nodep) { + virtual void visit(AstUnsigned* nodep) VL_OVERRIDE { visit_signed_unsigned(nodep, AstNumeric::UNSIGNED); } // Widths: Output width from lhs, rhs<33 bits // Signed: If lhs signed - virtual void visit(AstShiftL* nodep) { visit_shift(nodep); } - virtual void visit(AstShiftR* nodep) { visit_shift(nodep); } + virtual void visit(AstShiftL* nodep) VL_OVERRIDE { visit_shift(nodep); } + virtual void visit(AstShiftR* nodep) VL_OVERRIDE { visit_shift(nodep); } // ShiftRS converts to ShiftR, but not vice-versa - virtual void visit(AstShiftRS* nodep) { visit_shift(nodep); } + virtual void visit(AstShiftRS* nodep) VL_OVERRIDE { visit_shift(nodep); } //======== // Widths: Output real, input integer signed - virtual void visit(AstBitsToRealD* nodep) { visit_Or_Lu64(nodep); } - virtual void visit(AstIToRD* nodep) { visit_Or_Ls32(nodep); } + virtual void visit(AstBitsToRealD* nodep) VL_OVERRIDE { visit_Or_Lu64(nodep); } + virtual void visit(AstIToRD* nodep) VL_OVERRIDE { visit_Or_Ls32(nodep); } // Widths: Output integer signed, input real - virtual void visit(AstRToIS* nodep) { visit_Os32_Lr(nodep); } - virtual void visit(AstRToIRoundS* nodep) { visit_Os32_Lr(nodep); } + virtual void visit(AstRToIS* nodep) VL_OVERRIDE { visit_Os32_Lr(nodep); } + virtual void visit(AstRToIRoundS* nodep) VL_OVERRIDE { visit_Os32_Lr(nodep); } // Widths: Output integer unsigned, input real - virtual void visit(AstRealToBits* nodep) { visit_Ou64_Lr(nodep); } + virtual void visit(AstRealToBits* nodep) VL_OVERRIDE { visit_Ou64_Lr(nodep); } // Output integer, input string - virtual void visit(AstLenN* nodep) { visit_Os32_string(nodep); } - virtual void visit(AstPutcN* nodep) { + virtual void visit(AstLenN* nodep) VL_OVERRIDE { visit_Os32_string(nodep); } + virtual void visit(AstPutcN* nodep) VL_OVERRIDE { // CALLER: str.putc() UASSERT_OBJ(nodep->rhsp() && nodep->thsp(), nodep, "For ternary ops only!"); if (m_vup && m_vup->prelim()) { @@ -345,7 +345,7 @@ private: nodep->dtypeSetString(); //AstPutcN returns the new string to be assigned by AstAssign } } - virtual void visit(AstGetcN* nodep) { + virtual void visit(AstGetcN* nodep) VL_OVERRIDE { // CALLER: str.getc() UASSERT_OBJ(nodep->rhsp(), nodep, "For binary ops only!"); if (m_vup && m_vup->prelim()) { @@ -355,7 +355,17 @@ private: nodep->dtypeSetBitSized(8, AstNumeric::UNSIGNED); } } - virtual void visit(AstSubstrN* nodep) { + virtual void visit(AstGetcRefN* nodep) VL_OVERRIDE { + // CALLER: str.getc() + UASSERT_OBJ(nodep->rhsp(), nodep, "For binary ops only!"); + if (m_vup && m_vup->prelim()) { + // See similar handling in visit_cmp_eq_gt where created + iterateCheckString(nodep, "LHS", nodep->lhsp(), BOTH); + iterateCheckSigned32(nodep, "RHS", nodep->rhsp(), BOTH); + nodep->dtypeSetBitSized(8, AstNumeric::UNSIGNED); + } + } + virtual void visit(AstSubstrN* nodep) VL_OVERRIDE { // CALLER: str.substr() UASSERT_OBJ(nodep->rhsp() && nodep->thsp(), nodep, "For ternary ops only!"); if (m_vup && m_vup->prelim()) { @@ -366,7 +376,7 @@ private: nodep->dtypeSetString(); } } - virtual void visit(AstCompareNN* nodep) { + virtual void visit(AstCompareNN* nodep) VL_OVERRIDE { // CALLER: str.compare(), str.icompare() // Widths: 32 bit out UASSERT_OBJ(nodep->rhsp(), nodep, "For binary ops only!"); @@ -377,7 +387,7 @@ private: nodep->dtypeSetSigned32(); } } - virtual void visit(AstAtoN* nodep) { + virtual void visit(AstAtoN* nodep) VL_OVERRIDE { // CALLER: str.atobin(), atoi(), atohex(), atooct(), atoreal() // Width: 64bit floating point for atoreal(), 32bit out for the others if (m_vup->prelim()) { @@ -392,13 +402,13 @@ private: } // Widths: Constant, terminal - virtual void visit(AstTime* nodep) { nodep->dtypeSetUInt64(); } - virtual void visit(AstTimeD* nodep) { nodep->dtypeSetDouble(); } - virtual void visit(AstTestPlusArgs* nodep) { nodep->dtypeSetSigned32(); } - virtual void visit(AstScopeName* nodep) { nodep->dtypeSetUInt64(); } // A pointer, but not that it matters + virtual void visit(AstTime* nodep) VL_OVERRIDE { nodep->dtypeSetUInt64(); } + virtual void visit(AstTimeD* nodep) VL_OVERRIDE { nodep->dtypeSetDouble(); } + virtual void visit(AstTestPlusArgs* nodep) VL_OVERRIDE { nodep->dtypeSetSigned32(); } + virtual void visit(AstScopeName* nodep) VL_OVERRIDE { nodep->dtypeSetUInt64(); } // A pointer, but not that it matters // Special cases. So many.... - virtual void visit(AstNodeCond* nodep) { + virtual void visit(AstNodeCond* nodep) VL_OVERRIDE { // op=cond?expr1:expr2 // Signed: Output signed iff RHS & THS signed (presumed, not in IEEE) // See IEEE-2012 11.4.11 and Table 11-21. @@ -437,7 +447,7 @@ private: iterateCheck(nodep, "Conditional False", nodep->expr2p(), CONTEXT, FINAL, subDTypep, EXTEND_EXP); } } - virtual void visit(AstConcat* nodep) { + virtual void visit(AstConcat* nodep) VL_OVERRIDE { // Real: Not allowed (assumed) // Signed: unsigned output, input either (assumed) // IEEE-2012 Table 11-21, and 11.8.1: @@ -449,7 +459,8 @@ private: if (vdtypep && (VN_IS(vdtypep, AssocArrayDType) || VN_IS(vdtypep, AssocArrayDType) || VN_IS(vdtypep, QueueDType))) { - nodep->v3error("Unsupported: Concatenation to form "<prettyTypeName()); + nodep->v3error("Unsupported: Concatenation to form " + << vdtypep->prettyDTypeNameQ() << "data type"); } iterateCheckSizedSelf(nodep, "LHS", nodep->lhsp(), SELF, BOTH); @@ -490,7 +501,7 @@ private: } } } - virtual void visit(AstConcatN* nodep) { + virtual void visit(AstConcatN* nodep) VL_OVERRIDE { // String concatenate. // Already did AstConcat simplifications if (m_vup->prelim()) { @@ -506,28 +517,29 @@ private: } } } - virtual void visit(AstToLowerN* nodep) { + virtual void visit(AstToLowerN* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckString(nodep, "LHS", nodep->lhsp(), BOTH); nodep->dtypeSetString(); } } - virtual void visit(AstToUpperN* nodep) { + virtual void visit(AstToUpperN* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckString(nodep, "LHS", nodep->lhsp(), BOTH); nodep->dtypeSetString(); } } - virtual void visit(AstReplicate* nodep) { + virtual void visit(AstReplicate* nodep) VL_OVERRIDE { // IEEE-2012 Table 11-21: // LHS, RHS is self-determined // width: value(LHS) * width(RHS) if (m_vup->prelim()) { AstNodeDType* vdtypep = m_vup->dtypeNullp(); - if (vdtypep && (VN_IS(vdtypep, AssocArrayDType) - || VN_IS(vdtypep, QueueDType) - || VN_IS(vdtypep, UnpackArrayDType))) { - nodep->v3error("Unsupported: Replication to form "<prettyTypeName()); + if (vdtypep + && (VN_IS(vdtypep, AssocArrayDType) || VN_IS(vdtypep, QueueDType) + || VN_IS(vdtypep, UnpackArrayDType))) { + nodep->v3error("Unsupported: Replication to form " << vdtypep->prettyDTypeNameQ() + << " data type"); } iterateCheckSizedSelf(nodep, "LHS", nodep->lhsp(), SELF, BOTH); iterateCheckSizedSelf(nodep, "RHS", nodep->rhsp(), SELF, BOTH); @@ -559,7 +571,7 @@ private: } } } - virtual void visit(AstReplicateN* nodep) { + virtual void visit(AstReplicateN* nodep) VL_OVERRIDE { // Replicate with string if (m_vup->prelim()) { iterateCheckString(nodep, "LHS", nodep->lhsp(), BOTH); @@ -581,7 +593,7 @@ private: } } } - virtual void visit(AstNodeStream* nodep) { + virtual void visit(AstNodeStream* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckSizedSelf(nodep, "LHS", nodep->lhsp(), SELF, BOTH); iterateCheckSizedSelf(nodep, "RHS", nodep->rhsp(), SELF, BOTH); @@ -609,7 +621,7 @@ private: } } } - virtual void visit(AstRange* nodep) { + virtual void visit(AstRange* nodep) VL_OVERRIDE { // Real: Not allowed // Signed: unsigned output, input either // Convert all range values to constants @@ -643,7 +655,7 @@ private: } } - virtual void visit(AstSel* nodep) { + virtual void visit(AstSel* nodep) VL_OVERRIDE { // Signed: always unsigned; Real: Not allowed // LSB is self-determined (IEEE 2012 11.5.1) // We also use SELs to shorten a signed constant etc, in this case they are signed. @@ -748,7 +760,7 @@ private: } } - virtual void visit(AstArraySel* nodep) { + virtual void visit(AstArraySel* nodep) VL_OVERRIDE { // Signed/Real: Output signed iff LHS signed/real; binary operator // Note by contrast, bit extract selects are unsigned // LSB is self-determined (IEEE 2012 11.5.1) @@ -807,7 +819,7 @@ private: } } - virtual void visit(AstAssocSel* nodep) { + virtual void visit(AstAssocSel* nodep) VL_OVERRIDE { // Signed/Real: Output type based on array-declared type; binary operator if (m_vup->prelim()) { AstNodeDType* fromDtp = nodep->fromp()->dtypep()->skipRefp(); @@ -821,7 +833,7 @@ private: } } - virtual void visit(AstSliceSel* nodep) { + virtual void visit(AstSliceSel* nodep) VL_OVERRIDE { // Always creates as output an unpacked array if (m_vup->prelim()) { userIterateAndNext(nodep->fromp(), WidthVP(SELF, BOTH).p()); @@ -861,7 +873,7 @@ private: } } - virtual void visit(AstSelBit* nodep) { + virtual void visit(AstSelBit* nodep) VL_OVERRIDE { // Just a quick check as after V3Param these nodes instead are AstSel's userIterateAndNext(nodep->fromp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->rhsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel @@ -871,7 +883,7 @@ private: if (selp!=nodep) { nodep = NULL; userIterate(selp, m_vup); return; } nodep->v3fatalSrc("AstSelBit should disappear after widthSel"); } - virtual void visit(AstSelExtract* nodep) { + virtual void visit(AstSelExtract* nodep) VL_OVERRIDE { // Just a quick check as after V3Param these nodes instead are AstSel's userIterateAndNext(nodep->fromp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->rhsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel @@ -881,7 +893,7 @@ private: if (selp!=nodep) { nodep = NULL; userIterate(selp, m_vup); return; } nodep->v3fatalSrc("AstSelExtract should disappear after widthSel"); } - virtual void visit(AstSelPlus* nodep) { + virtual void visit(AstSelPlus* nodep) VL_OVERRIDE { userIterateAndNext(nodep->fromp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->rhsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->thsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel @@ -890,7 +902,7 @@ private: if (selp!=nodep) { nodep = NULL; userIterate(selp, m_vup); return; } nodep->v3fatalSrc("AstSelPlus should disappear after widthSel"); } - virtual void visit(AstSelMinus* nodep) { + virtual void visit(AstSelMinus* nodep) VL_OVERRIDE { userIterateAndNext(nodep->fromp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->rhsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel userIterateAndNext(nodep->thsp(), WidthVP(CONTEXT, PRELIM).p()); // FINAL in AstSel @@ -900,13 +912,13 @@ private: nodep->v3fatalSrc("AstSelMinus should disappear after widthSel"); } - virtual void visit(AstExtend* nodep) { + virtual void visit(AstExtend* nodep) VL_OVERRIDE { // Only created by this process, so we know width from here down is correct. } - virtual void visit(AstExtendS* nodep) { + virtual void visit(AstExtendS* nodep) VL_OVERRIDE { // Only created by this process, so we know width from here down is correct. } - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { // The node got setup with the signed/real state of the node. // However a later operation may have changed the node->signed w/o changing // the number's sign. So we don't: nodep->dtypeChgSigned(nodep->num().isSigned()); @@ -922,7 +934,7 @@ private: // We don't size the constant until we commit the widths, as need parameters // to remain unsized, and numbers to remain unsized to avoid backp() warnings } - virtual void visit(AstPast* nodep) { + virtual void visit(AstPast* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckSizedSelf(nodep, "LHS", nodep->exprp(), SELF, BOTH); nodep->dtypeFrom(nodep->exprp()); @@ -945,15 +957,21 @@ private: } } } - virtual void visit(AstRand* nodep) { + virtual void visit(AstSampled* nodep) VL_OVERRIDE { + if (m_vup->prelim()) { + iterateCheckSizedSelf(nodep, "LHS", nodep->exprp(), SELF, BOTH); + nodep->dtypeFrom(nodep->exprp()); + } + } + virtual void visit(AstRand* nodep) VL_OVERRIDE { if (m_vup->prelim()) { nodep->dtypeSetSigned32(); // Says the spec } } - virtual void visit(AstUnbounded* nodep) { + virtual void visit(AstUnbounded* nodep) VL_OVERRIDE { nodep->v3error("Unsupported/illegal unbounded ('$') in this context."); } - virtual void visit(AstUCFunc* nodep) { + virtual void visit(AstUCFunc* nodep) VL_OVERRIDE { // Give it the size the user wants. if (m_vup && m_vup->prelim()) { nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::UNSIGNED); // We don't care @@ -966,13 +984,13 @@ private: if (nodep->width()>64) nodep->v3error("Unsupported: $c can't generate wider than 64 bits"); } } - virtual void visit(AstCLog2* nodep) { + virtual void visit(AstCLog2* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckSizedSelf(nodep, "LHS", nodep->lhsp(), SELF, BOTH); nodep->dtypeSetSigned32(); } } - virtual void visit(AstPow* nodep) { + virtual void visit(AstPow* nodep) VL_OVERRIDE { // Pow is special, output sign only depends on LHS sign, but // function result depends on both signs // RHS is self-determined (IEEE) @@ -1016,25 +1034,25 @@ private: } } } - virtual void visit(AstPowSU* nodep) { + virtual void visit(AstPowSU* nodep) VL_OVERRIDE { // POWSU/SS/US only created here, dtype already determined, so // nothing to do in this function userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->rhsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstPowSS* nodep) { + virtual void visit(AstPowSS* nodep) VL_OVERRIDE { // POWSU/SS/US only created here, dtype already determined, so // nothing to do in this function userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->rhsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstPowUS* nodep) { + virtual void visit(AstPowUS* nodep) VL_OVERRIDE { // POWSU/SS/US only created here, dtype already determined, so // nothing to do in this function userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->rhsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstCountOnes* nodep) { + virtual void visit(AstCountOnes* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckSizedSelf(nodep, "LHS", nodep->lhsp(), SELF, BOTH); // If it's a 32 bit number, we need a 6 bit number as we need to return '32'. @@ -1042,12 +1060,12 @@ private: nodep->dtypeSetLogicSized(selwidth, AstNumeric::UNSIGNED); // Spec doesn't indicate if an integer } } - virtual void visit(AstCvtPackString* nodep) { + virtual void visit(AstCvtPackString* nodep) VL_OVERRIDE { // Opaque returns, so arbitrary userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); // Type set in constructor } - virtual void visit(AstAttrOf* nodep) { + virtual void visit(AstAttrOf* nodep) VL_OVERRIDE { AstAttrOf* oldAttr = m_attrp; m_attrp = nodep; userIterateAndNext(nodep->fromp(), WidthVP(SELF, BOTH).p()); @@ -1148,6 +1166,13 @@ private: } break; } + case AstAttrType::TYPENAME: { + UASSERT_OBJ(nodep->fromp(), nodep, "Unprovided expression"); + string result = nodep->fromp()->dtypep()->prettyDTypeName(); + AstNode* newp = new AstConst(nodep->fileline(), AstConst::String(), result); + nodep->replaceWith(newp); VL_DO_DANGLING(nodep->deleteTree(), nodep); + break; + } default: { // Everything else resolved earlier nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::UNSIGNED); // Approximation, unsized 32 @@ -1158,16 +1183,16 @@ private: } m_attrp = oldAttr; } - virtual void visit(AstPull* nodep) { + virtual void visit(AstPull* nodep) VL_OVERRIDE { // May have select underneath, let seek natural size userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); } - virtual void visit(AstText* nodep) { + virtual void visit(AstText* nodep) VL_OVERRIDE { // Only used in CStmts which don't care.... } // DTYPES - virtual void visit(AstNodeArrayDType* nodep) { + virtual void visit(AstNodeArrayDType* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); // Iterate into subDTypep() to resolve that type and update pointer. @@ -1184,7 +1209,7 @@ private: } UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); if (nodep->keyChildDTypep()) nodep->keyDTypep(moveDTypeEdit(nodep, nodep->keyChildDTypep())); @@ -1194,7 +1219,7 @@ private: nodep->dtypep(nodep); // The array itself, not subDtype UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); // Iterate into subDTypep() to resolve that type and update pointer. @@ -1205,7 +1230,7 @@ private: } UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); // Iterate into subDTypep() to resolve that type and update pointer. @@ -1214,7 +1239,7 @@ private: nodep->dtypep(nodep); // The array itself, not subDtype UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->generic()) return; // Already perfect if (nodep->rangep()) { @@ -1239,7 +1264,7 @@ private: // Instead for now doing this in V3WidthCommit UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed // Move any childDTypep to instead be in global AstTypeTable. // This way if this node gets deleted and some other dtype points to it @@ -1252,7 +1277,7 @@ private: nodep->widthFromSub(nodep->subDTypep()); UINFO(4,"dtWidthed "<doingWidth()) { // Early exit if have circular parameter definition nodep->v3error("Typedef's type is circular: "<prettyName()); nodep->dtypeSetLogicBool(); @@ -1261,6 +1286,15 @@ private: } if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed nodep->doingWidth(true); + if (nodep->typeofp()) { // type(typeofp_expression) + // Type comes from expression's type + userIterateAndNext(nodep->typeofp(), WidthVP(SELF, BOTH).p()); + AstNode* typeofp = nodep->typeofp(); + nodep->refDTypep(typeofp->dtypep()); + VL_DO_DANGLING(typeofp->unlinkFrBack()->deleteTree(), typeofp); + // We had to use AstRefDType for this construct as pointers to this type + // in type table are still correct (which they wouldn't be if we replaced the node) + } userIterateChildren(nodep, NULL); if (nodep->subDTypep()) nodep->refDTypep(iterateEditDTypep(nodep, nodep->subDTypep())); // Effectively nodep->dtypeFrom(nodep->dtypeSkipRefp()); @@ -1272,20 +1306,20 @@ private: UINFO(4,"dtWidthed "<doingWidth(false); } - virtual void visit(AstTypedef* nodep) { + virtual void visit(AstTypedef* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->dtypep(moveChildDTypeEdit(nodep)); userIterateChildren(nodep, NULL); nodep->dtypep(iterateEditDTypep(nodep, nodep->subDTypep())); } - virtual void visit(AstParamTypeDType* nodep) { + virtual void visit(AstParamTypeDType* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->dtypep(moveChildDTypeEdit(nodep)); userIterateChildren(nodep, NULL); nodep->dtypep(iterateEditDTypep(nodep, nodep->subDTypep())); nodep->widthFromSub(nodep->subDTypep()); } - virtual void visit(AstCastParse* nodep) { + virtual void visit(AstCastParse* nodep) VL_OVERRIDE { // nodep->dtp could be data type, or a primary_constant // Don't iterate lhsp, will deal with that once convert the type V3Const::constifyParamsEdit(nodep->dtp()); // itemp may change @@ -1301,7 +1335,7 @@ private: nodep->replaceWith(nodep->lhsp()->unlinkFrBack()); } } - virtual void visit(AstCast* nodep) { + virtual void visit(AstCast* nodep) VL_OVERRIDE { if (nodep->childDTypep()) nodep->dtypep(moveChildDTypeEdit(nodep)); nodep->dtypep(iterateEditDTypep(nodep, nodep->dtypep())); //if (debug()) nodep->dumpTree(cout, " CastPre: "); @@ -1341,7 +1375,7 @@ private: VL_DO_DANGLING(pushDeletep(nodep), nodep); //if (debug()) newp->dumpTree(cout, " CastOut: "); } - virtual void visit(AstCastSize* nodep) { + virtual void visit(AstCastSize* nodep) VL_OVERRIDE { // IEEE: Signedness of result is same as self-determined signedness // However, the result is same as BITSEL, so we do not sign extend the LHS UASSERT_OBJ(VN_IS(nodep->rhsp(), Const), nodep, @@ -1391,7 +1425,7 @@ private: } //if (debug()) nodep->dumpTree(cout, " CastSizeOut: "); } - virtual void visit(AstVar* nodep) { + virtual void visit(AstVar* nodep) VL_OVERRIDE { //if (debug()) nodep->dumpTree(cout, " InitPre: "); // Must have deterministic constant width // We can't skip this step when width()!=0, as creating a AstVar @@ -1492,7 +1526,7 @@ private: nodep->didWidth(true); nodep->doingWidth(false); } - virtual void visit(AstNodeVarRef* nodep) { + virtual void visit(AstNodeVarRef* nodep) VL_OVERRIDE { if (nodep->didWidth()) return; if (!nodep->varp()) { if (m_paramsOnly && VN_IS(nodep, VarXRef)) { @@ -1526,7 +1560,7 @@ private: nodep->didWidth(true); } - virtual void visit(AstEnumDType* nodep) { + virtual void visit(AstEnumDType* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed UINFO(5," ENUMDTYPE "<childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); @@ -1584,7 +1618,7 @@ private: num.opAdd(one, constp->num()); } } - virtual void visit(AstEnumItem* nodep) { + virtual void visit(AstEnumItem* nodep) VL_OVERRIDE { UINFO(5," ENUMITEM "<dtypep(); UASSERT_OBJ(vdtypep, nodep, "ENUMITEM not under ENUM"); @@ -1597,7 +1631,7 @@ private: iterateCheck(nodep, "Enum value", nodep->valuep(), CONTEXT, FINAL, nodep->dtypep(), EXTEND_EXP); } } - virtual void visit(AstEnumItemRef* nodep) { + virtual void visit(AstEnumItemRef* nodep) VL_OVERRIDE { if (!nodep->itemp()->didWidth()) { // We need to do the whole enum en-mass AstNode* enump = nodep->itemp(); @@ -1610,10 +1644,10 @@ private: } nodep->dtypeFrom(nodep->itemp()); } - virtual void visit(AstInitItem* nodep) { + virtual void visit(AstInitItem* nodep) VL_OVERRIDE { userIterateChildren(nodep, m_vup); } - virtual void visit(AstInitArray* nodep) { + virtual void visit(AstInitArray* nodep) VL_OVERRIDE { // InitArray has type of the array; children are array values if (m_vup->prelim()) { // First stage evaluation AstNodeDType* vdtypep = m_vup->dtypep(); @@ -1626,7 +1660,7 @@ private: } } } - virtual void visit(AstInside* nodep) { + virtual void visit(AstInside* nodep) VL_OVERRIDE { userIterateAndNext(nodep->exprp(), WidthVP(CONTEXT, PRELIM).p()); for (AstNode* nextip, *itemp = nodep->itemsp(); itemp; itemp=nextip) { nextip = itemp->nextp(); // Prelim may cause the node to get replaced @@ -1676,14 +1710,14 @@ private: if (debug()>=9) newp->dumpTree(cout, "-inside-out: "); nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - virtual void visit(AstInsideRange* nodep) { + virtual void visit(AstInsideRange* nodep) VL_OVERRIDE { // Just do each side; AstInside will rip these nodes out later userIterateAndNext(nodep->lhsp(), m_vup); userIterateAndNext(nodep->rhsp(), m_vup); nodep->dtypeFrom(nodep->lhsp()); } - virtual void visit(AstIfaceRefDType* nodep) { + virtual void visit(AstIfaceRefDType* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed UINFO(5," IFACEREF "<widthForce(1, 1); // Not really relevant UINFO(4,"dtWidthed "<didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed UINFO(5," NODECLASS "<=9) nodep->dumpTree("-class-in--"); @@ -1723,7 +1757,7 @@ private: nodep->widthForce(width, width); // Signing stays as-is, as parsed from declaration //if (debug()>=9) nodep->dumpTree("-class-out-"); } - virtual void visit(AstMemberDType* nodep) { + virtual void visit(AstMemberDType* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; // This node is a dtype & not both PRELIMed+FINALed if (nodep->childDTypep()) nodep->refDTypep(moveChildDTypeEdit(nodep)); // Iterate into subDTypep() to resolve that type and update pointer. @@ -1731,7 +1765,7 @@ private: nodep->dtypep(nodep); // The member itself, not subDtype nodep->widthFromSub(nodep->subDTypep()); } - virtual void visit(AstMemberSel* nodep) { + virtual void visit(AstMemberSel* nodep) VL_OVERRIDE { UINFO(5," MEMBERSEL "<=9) nodep->dumpTree("-mbs-in: "); userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); @@ -1788,12 +1822,12 @@ private: return false; } - virtual void visit(AstCMethodHard* nodep) { + virtual void visit(AstCMethodHard* nodep) VL_OVERRIDE { // Never created before V3Width, so no need to redo it UASSERT_OBJ(nodep->dtypep(), nodep, "CMETHODCALLs should have already been sized"); } - virtual void visit(AstMethodCall* nodep) { + virtual void visit(AstMethodCall* nodep) VL_OVERRIDE { UINFO(5," METHODSEL "<didWidth()) return; if (debug()>=9) nodep->dumpTree("-mts-in: "); @@ -1896,11 +1930,24 @@ private: if (nodep->name() == "name") { methodOkArguments(nodep, 0, 0); + } else if (nodep->pinsp() + && !(VN_IS(VN_CAST(nodep->pinsp(), Arg)->exprp(), Const))) { + nodep->pinsp()->v3fatalSrc("Unsupported: enum next/prev with non-const argument"); } else if (nodep->pinsp() && !(VN_IS(VN_CAST(nodep->pinsp(), Arg)->exprp(), Const) && VN_CAST(VN_CAST(nodep->pinsp(), Arg)->exprp(), Const)->toUInt() == 1 && !nodep->pinsp()->nextp())) { - nodep->v3error("Unsupported: Arguments passed to enum.next method"); + // Unroll of enumVar.next(k) to enumVar.next(1).next(k - 1) + AstMethodCall* clonep = nodep->cloneTree(false); + VN_CAST(VN_CAST(clonep->pinsp(), Arg)->exprp(), Const)->num().setLong(1); + uint32_t stepWidth = VN_CAST(VN_CAST(nodep->pinsp(), Arg)->exprp(), Const)->toUInt(); + AstConst* constp = new AstConst(nodep->fileline(), stepWidth - 1); + AstArg* argp = new AstArg(nodep->fileline(), "", constp); + AstMethodCall* newp = new AstMethodCall(nodep->fileline(), clonep, + nodep->name(), argp); + nodep->replaceWith(newp); + VL_DO_DANGLING(nodep->deleteTree(), nodep); + return; } // Need a runtime lookup table. Yuk. // Most enums unless overridden are 32 bits, so we size array @@ -1917,7 +1964,7 @@ private: if (vconstp->toUQuad() >= msbdim) msbdim = vconstp->toUQuad(); } if (adtypep->itemsp()->width() > 64 || msbdim >= (1 << 16)) { - nodep->v3error("Unsupported; enum next/prev method on enum with > 10 bits"); + nodep->v3error("Unsupported: enum next/prev method on enum with > 10 bits"); return; } } @@ -2239,7 +2286,7 @@ private: } } - virtual void visit(AstNew* nodep) { + virtual void visit(AstNew* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); AstClassRefDType* refp = VN_CAST(m_vup->dtypeNullp(), ClassRefDType); @@ -2251,7 +2298,7 @@ private: nodep->dtypep(refp); } - virtual void visit(AstPattern* nodep) { + virtual void visit(AstPattern* nodep) VL_OVERRIDE { if (nodep->didWidthAndSet()) return; UINFO(9,"PATTERN "<childDTypep()) nodep->dtypep(moveChildDTypeEdit(nodep)); // data_type '{ pattern } @@ -2291,9 +2338,10 @@ private: patp->unlinkFrBack(&relinkHandle); while (AstNode* movep = patp->lhssp()->nextp()) { movep->unlinkFrBack(); // Not unlinkFrBackWithNext, just one + AstNode* newkeyp = NULL; + if (patp->keyp()) newkeyp = patp->keyp()->cloneTree(true); AstPatMember* newp - = new AstPatMember(patp->fileline(), movep, - patp->keyp()->cloneTree(true), NULL); + = new AstPatMember(patp->fileline(), movep, newkeyp, NULL); patp->addNext(newp); } relinkHandle.relink(patp); @@ -2321,8 +2369,8 @@ private: && VN_CAST(dtypep, BasicDType)->isRanged()) { VL_DO_DANGLING(patternBasic(nodep, dtypep, defaultp), nodep); } else { - nodep->v3error("Unsupported: Assignment pattern applies against non struct/union: " - <prettyTypeName()); + nodep->v3error("Unsupported: Assignment pattern applies against non struct/union data type: " + << dtypep->prettyDTypeNameQ()); } } } @@ -2550,7 +2598,7 @@ private: //if (debug()>=9) newp->dumpTree("-apat-out: "); VL_DO_DANGLING(pushDeletep(nodep), nodep); // Deletes defaultp also, if present } - virtual void visit(AstPatMember* nodep) { + virtual void visit(AstPatMember* nodep) VL_OVERRIDE { AstNodeDType* vdtypep = m_vup->dtypeNullp(); UASSERT_OBJ(vdtypep, nodep, "Pattern member type not assigned by AstPattern visitor"); nodep->dtypep(vdtypep); @@ -2575,7 +2623,7 @@ private: return times; } - virtual void visit(AstPropClocked* nodep) { + virtual void visit(AstPropClocked* nodep) VL_OVERRIDE { if (m_vup->prelim()) { // First stage evaluation iterateCheckBool(nodep, "Property", nodep->propp(), BOTH); userIterateAndNext(nodep->sensesp(), NULL); @@ -2589,7 +2637,7 @@ private: //-------------------- // Top levels - virtual void visit(AstNodeCase* nodep) { + virtual void visit(AstNodeCase* nodep) VL_OVERRIDE { // IEEE-2012 12.5: // Width: MAX(expr, all items) // Signed: Only if expr, and all items signed @@ -2630,7 +2678,7 @@ private: } } } - virtual void visit(AstNodeFor* nodep) { + virtual void visit(AstNodeFor* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->initsp(), NULL); iterateCheckBool(nodep, "For Test Condition", nodep->condp(), BOTH); // it's like an if() condition. @@ -2638,19 +2686,19 @@ private: userIterateAndNext(nodep->incsp(), NULL); } - virtual void visit(AstRepeat* nodep) { + virtual void visit(AstRepeat* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->countp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->bodysp(), NULL); } - virtual void visit(AstWhile* nodep) { + virtual void visit(AstWhile* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->precondsp(), NULL); iterateCheckBool(nodep, "For Test Condition", nodep->condp(), BOTH); // it's like an if() condition. userIterateAndNext(nodep->bodysp(), NULL); userIterateAndNext(nodep->incsp(), NULL); } - virtual void visit(AstNodeIf* nodep) { + virtual void visit(AstNodeIf* nodep) VL_OVERRIDE { assertAtStatement(nodep); //if (debug()) nodep->dumpTree(cout, " IfPre: "); if (!VN_IS(nodep, GenIf)) { // for m_paramsOnly @@ -2661,7 +2709,7 @@ private: //if (debug()) nodep->dumpTree(cout, " IfOut: "); } - virtual void visit(AstNodeAssign* nodep) { + virtual void visit(AstNodeAssign* nodep) VL_OVERRIDE { // IEEE-2012 10.7, 11.8.2, 11.8.3, 11.5: (Careful of 11.8.1 which is // only one step; final dtype depends on assign LHS.) // Determine RHS type width and signing @@ -2689,7 +2737,7 @@ private: } } - virtual void visit(AstSFormatF* nodep) { + virtual void visit(AstSFormatF* nodep) VL_OVERRIDE { // Excludes NodeDisplay, see below if (m_vup && !m_vup->prelim()) return; // Can be called as statement or function // Just let all arguments seek their natural sizes @@ -2792,7 +2840,7 @@ private: nodep->text(newFormat); UINFO(9," Display out "<text()<filep()) { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); @@ -2800,7 +2848,7 @@ private: // Just let all arguments seek their natural sizes userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); } - virtual void visit(AstElabDisplay* nodep) { + virtual void visit(AstElabDisplay* nodep) VL_OVERRIDE { assertAtStatement(nodep); // Just let all arguments seek their natural sizes userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); @@ -2824,64 +2872,64 @@ private: VL_DO_DANGLING(nodep->unlinkFrBack()->deleteTree(), nodep); } } - virtual void visit(AstFOpen* nodep) { + virtual void visit(AstFOpen* nodep) VL_OVERRIDE { // Although a system function in IEEE, here a statement which sets the file pointer (MCD) assertAtStatement(nodep); iterateCheckFileDesc(nodep, nodep->filep(), BOTH); userIterateAndNext(nodep->filenamep(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->modep(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstFClose* nodep) { + virtual void visit(AstFClose* nodep) VL_OVERRIDE { assertAtStatement(nodep); iterateCheckFileDesc(nodep, nodep->filep(), BOTH); } - virtual void visit(AstFEof* nodep) { + virtual void visit(AstFEof* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::SIGNED); // Spec says integer return } } - virtual void visit(AstFFlush* nodep) { + virtual void visit(AstFFlush* nodep) VL_OVERRIDE { assertAtStatement(nodep); if (nodep->filep()) { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); } } - virtual void visit(AstFRewind* nodep) { + virtual void visit(AstFRewind* nodep) VL_OVERRIDE { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::SIGNED); // Spec says integer return } - virtual void visit(AstFTell* nodep) { + virtual void visit(AstFTell* nodep) VL_OVERRIDE { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::SIGNED); // Spec says integer return } - virtual void visit(AstFSeek* nodep) { + virtual void visit(AstFSeek* nodep) VL_OVERRIDE { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); iterateCheckSigned32(nodep, "$fseek offset", nodep->offset(), BOTH); iterateCheckSigned32(nodep, "$fseek operation", nodep->operation(), BOTH); nodep->dtypeSetLogicUnsized(32, 1, AstNumeric::SIGNED); // Spec says integer return } - virtual void visit(AstFGetC* nodep) { + virtual void visit(AstFGetC* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); nodep->dtypeSetLogicUnsized(32, 8, AstNumeric::SIGNED); // Spec says integer return } } - virtual void visit(AstFGetS* nodep) { + virtual void visit(AstFGetS* nodep) VL_OVERRIDE { if (m_vup->prelim()) { nodep->dtypeSetSigned32(); // Spec says integer return iterateCheckFileDesc(nodep, nodep->filep(), BOTH); userIterateAndNext(nodep->strgp(), WidthVP(SELF, BOTH).p()); } } - virtual void visit(AstFUngetC* nodep) { + virtual void visit(AstFUngetC* nodep) VL_OVERRIDE { if (m_vup->prelim()) { iterateCheckFileDesc(nodep, nodep->filep(), BOTH); iterateCheckSigned32(nodep, "$fungetc character", nodep->charp(), BOTH); nodep->dtypeSetLogicUnsized(32, 8, AstNumeric::SIGNED); // Spec says integer return } } - virtual void visit(AstFRead* nodep) { + virtual void visit(AstFRead* nodep) VL_OVERRIDE { if (m_vup->prelim()) { nodep->dtypeSetSigned32(); // Spec says integer return userIterateAndNext(nodep->memp(), WidthVP(SELF, BOTH).p()); @@ -2894,38 +2942,38 @@ private: } } } - virtual void visit(AstFScanF* nodep) { + virtual void visit(AstFScanF* nodep) VL_OVERRIDE { if (m_vup->prelim()) { nodep->dtypeSetSigned32(); // Spec says integer return iterateCheckFileDesc(nodep, nodep->filep(), BOTH); userIterateAndNext(nodep->exprsp(), WidthVP(SELF, BOTH).p()); } } - virtual void visit(AstSScanF* nodep) { + virtual void visit(AstSScanF* nodep) VL_OVERRIDE { if (m_vup->prelim()) { nodep->dtypeSetSigned32(); // Spec says integer return userIterateAndNext(nodep->fromp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->exprsp(), WidthVP(SELF, BOTH).p()); } } - virtual void visit(AstSysIgnore* nodep) { + virtual void visit(AstSysIgnore* nodep) VL_OVERRIDE { userIterateAndNext(nodep->exprsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstSystemF* nodep) { + virtual void visit(AstSystemF* nodep) VL_OVERRIDE { if (m_vup->prelim()) { userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); nodep->dtypeSetSigned32(); // Spec says integer return } } - virtual void visit(AstSysFuncAsTask* nodep) { + virtual void visit(AstSysFuncAsTask* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstSystemT* nodep) { + virtual void visit(AstSystemT* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->lhsp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstNodeReadWriteMem* nodep) { + virtual void visit(AstNodeReadWriteMem* nodep) VL_OVERRIDE { assertAtStatement(nodep); userIterateAndNext(nodep->filenamep(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->memp(), WidthVP(SELF, BOTH).p()); @@ -2954,34 +3002,34 @@ private: userIterateAndNext(nodep->lsbp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->msbp(), WidthVP(SELF, BOTH).p()); } - virtual void visit(AstValuePlusArgs* nodep) { + virtual void visit(AstValuePlusArgs* nodep) VL_OVERRIDE { if (m_vup->prelim()) { userIterateAndNext(nodep->searchp(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->outp(), WidthVP(SELF, BOTH).p()); nodep->dtypeChgWidthSigned(32, 1, AstNumeric::SIGNED); // Spec says integer return } } - virtual void visit(AstUCStmt* nodep) { + virtual void visit(AstUCStmt* nodep) VL_OVERRIDE { // Just let all arguments seek their natural sizes assertAtStatement(nodep); userIterateChildren(nodep, WidthVP(SELF, BOTH).p()); } - virtual void visit(AstAssert* nodep) { + virtual void visit(AstAssert* nodep) VL_OVERRIDE { assertAtStatement(nodep); iterateCheckBool(nodep, "Property", nodep->propp(), BOTH); // it's like an if() condition. userIterateAndNext(nodep->passsp(), NULL); userIterateAndNext(nodep->failsp(), NULL); } - virtual void visit(AstCover* nodep) { + virtual void visit(AstCover* nodep) VL_OVERRIDE { assertAtStatement(nodep); iterateCheckBool(nodep, "Property", nodep->propp(), BOTH); // it's like an if() condition. userIterateAndNext(nodep->passsp(), NULL); } - virtual void visit(AstRestrict* nodep) { + virtual void visit(AstRestrict* nodep) VL_OVERRIDE { assertAtStatement(nodep); iterateCheckBool(nodep, "Property", nodep->propp(), BOTH); // it's like an if() condition. } - virtual void visit(AstPin* nodep) { + virtual void visit(AstPin* nodep) VL_OVERRIDE { //if (debug()) nodep->dumpTree(cout, "- PinPre: "); // TOP LEVEL NODE if (nodep->modVarp() && nodep->modVarp()->isGParam()) { @@ -3031,9 +3079,9 @@ private: if (nodep->modVarp()->direction() == VDirection::REF) { nodep->v3error("Ref connection "<modVarp()->prettyNameQ() <<" requires matching types;" - <<" ref requires "<prettyTypeName() - <<" but connection is " - <prettyTypeName()<<"."<prettyDTypeNameQ() + <<" data type but connection is " + <prettyDTypeNameQ()<<" data type."<modVarp()->isTristate()) { if (pinwidth != conwidth) { nodep->v3error("Unsupported: "<prettyOperatorName()) @@ -3086,7 +3134,7 @@ private: } //if (debug()) nodep->dumpTree(cout, "- PinOut: "); } - virtual void visit(AstCell* nodep) { + virtual void visit(AstCell* nodep) VL_OVERRIDE { if (!m_paramsOnly) { if (VN_IS(nodep->modp(), NotFoundModule)) { // We've resolved parameters and hit a module that we couldn't resolve. It's @@ -3105,7 +3153,7 @@ private: userIterateAndNext(nodep->paramsp(), NULL); m_cellRangep = NULL; } - virtual void visit(AstGatePin* nodep) { + virtual void visit(AstGatePin* nodep) VL_OVERRIDE { if (m_vup->prelim()) { userIterateAndNext(nodep->rangep(), WidthVP(SELF, BOTH).p()); userIterateAndNext(nodep->exprp(), WidthVP(CONTEXT, PRELIM).p()); @@ -3131,7 +3179,7 @@ private: VL_DO_DANGLING(pushDeletep(nodep), nodep); } } - virtual void visit(AstNodeFTask* nodep) { + virtual void visit(AstNodeFTask* nodep) VL_OVERRIDE { // Grab width from the output variable (if it's a function) if (nodep->didWidth()) return; if (nodep->doingWidth()) { @@ -3159,7 +3207,7 @@ private: nodep->dpiOpenParentInc(); // Mark so V3Task will wait for a child to build calling func } } - virtual void visit(AstReturn* nodep) { + virtual void visit(AstReturn* nodep) VL_OVERRIDE { // IEEE: Assignment-like context assertAtStatement(nodep); if (!m_funcp) { @@ -3177,12 +3225,12 @@ private: } } - virtual void visit(AstFuncRef* nodep) { + virtual void visit(AstFuncRef* nodep) VL_OVERRIDE { visit(VN_CAST(nodep, NodeFTaskRef)); nodep->dtypeFrom(nodep->taskp()); //if (debug()) nodep->dumpTree(cout, " FuncOut: "); } - virtual void visit(AstNodeFTaskRef* nodep) { + virtual void visit(AstNodeFTaskRef* nodep) VL_OVERRIDE { // For arguments, is assignment-like context; see IEEE rules in AstNodeAssign // Function hasn't been widthed, so make it so. UINFO(5, " FTASKREF "<didWidth(true); } - virtual void visit(AstInitial* nodep) { + virtual void visit(AstInitial* nodep) VL_OVERRIDE { assertAtStatement(nodep); m_initialp = nodep; userIterateChildren(nodep, NULL); m_initialp = NULL; } - virtual void visit(AstNetlist* nodep) { + virtual void visit(AstNetlist* nodep) VL_OVERRIDE { // Iterate modules backwards, in bottom-up order. That's faster userIterateChildrenBackwards(nodep, NULL); } //-------------------- // Default - virtual void visit(AstNodeMath* nodep) { + virtual void visit(AstNodeMath* nodep) VL_OVERRIDE { if (!nodep->didWidth()) { nodep->v3fatalSrc("Visit function missing? Widthed function missing for math node: " <lhsp()->widthMin(), nodep->rhsp()->widthMin()); AstNodeDType* subDTypep = nodep->findLogicDType(width, ewidth, AstNumeric::fromBool(signedFl)); + bool warnOn = true; + if (!signedFl && width == 32) { + // Waive on unsigned < or <= if RHS is narrower, since can't give wrong answer + if ((VN_IS(nodep, Lt) || VN_IS(nodep, Lte)) + && (nodep->lhsp()->width() >= nodep->rhsp()->widthMin())) { + warnOn = false; + } + // Waive on unsigned > or >= if RHS is wider, since can't give wrong answer + if ((VN_IS(nodep, Gt) || VN_IS(nodep, Gte)) + && (nodep->lhsp()->widthMin() >= nodep->rhsp()->width())) { + warnOn = false; + } + } iterateCheck(nodep, "LHS", nodep->lhsp(), CONTEXT, FINAL, subDTypep, - signedFl ? EXTEND_LHS:EXTEND_ZERO); + (signedFl ? EXTEND_LHS : EXTEND_ZERO), warnOn); iterateCheck(nodep, "RHS", nodep->rhsp(), CONTEXT, FINAL, subDTypep, - signedFl ? EXTEND_LHS:EXTEND_ZERO); + (signedFl ? EXTEND_LHS : EXTEND_ZERO), warnOn); } nodep->dtypeSetLogicBool(); } @@ -4175,7 +4236,7 @@ private: AstNode* spliceCvtD(AstNode* nodep) { // For integer used in REAL context, convert to real // We don't warn here, "2.0 * 2" is common and reasonable - if (nodep && !nodep->isDouble()) { + if (nodep && !nodep->dtypep()->skipRefp()->isDouble()) { UINFO(6," spliceCvtD: "<unlinkFrBack(&linker); @@ -4189,7 +4250,7 @@ private: AstNode* spliceCvtS(AstNode* nodep, bool warnOn) { // IEEE-2012 11.8.1: Signed: Type coercion creates signed // 11.8.2: Argument to convert is self-determined - if (nodep && nodep->isDouble()) { + if (nodep && nodep->dtypep()->skipRefp()->isDouble()) { UINFO(6," spliceCvtS: "<unlinkFrBack(&linker); diff --git a/src/V3WidthCommit.h b/src/V3WidthCommit.h index d8be52295..853c0cb78 100644 --- a/src/V3WidthCommit.h +++ b/src/V3WidthCommit.h @@ -39,13 +39,13 @@ class WidthRemoveVisitor : public AstNVisitor { private: // VISITORS - virtual void visit(AstSigned* nodep) { + virtual void visit(AstSigned* nodep) VL_OVERRIDE { VL_DO_DANGLING(replaceWithSignedVersion(nodep, nodep->lhsp()->unlinkFrBack()), nodep); } - virtual void visit(AstUnsigned* nodep) { + virtual void visit(AstUnsigned* nodep) VL_OVERRIDE { VL_DO_DANGLING(replaceWithSignedVersion(nodep, nodep->lhsp()->unlinkFrBack()), nodep); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); } void replaceWithSignedVersion(AstNode* nodep, AstNode* newp) { @@ -114,7 +114,7 @@ private: return nodep; } // VISITORS - virtual void visit(AstConst* nodep) { + virtual void visit(AstConst* nodep) VL_OVERRIDE { UASSERT_OBJ(nodep->dtypep(), nodep, "No dtype"); iterate(nodep->dtypep()); // Do datatype first if (AstConst* newp = newIfConstCommitSize(nodep)) { @@ -126,15 +126,15 @@ private: } editDType(nodep); } - virtual void visit(AstNodeDType* nodep) { + virtual void visit(AstNodeDType* nodep) VL_OVERRIDE { visitIterateNodeDType(nodep); } - virtual void visit(AstNodeUOrStructDType* nodep) { + virtual void visit(AstNodeUOrStructDType* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once visitIterateNodeDType(nodep); nodep->clearCache(); } - virtual void visit(AstParamTypeDType* nodep) { + virtual void visit(AstParamTypeDType* nodep) VL_OVERRIDE { if (nodep->user1SetOnce()) return; // Process once visitIterateNodeDType(nodep); // Move to type table as all dtype pointers must resolve there @@ -153,11 +153,11 @@ private: nodep->virtRefDTypep(editOneDType(nodep->virtRefDTypep())); nodep->virtRefDType2p(editOneDType(nodep->virtRefDType2p())); } - virtual void visit(AstNodePreSel* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstNodePreSel* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE // This check could go anywhere after V3Param nodep->v3fatalSrc("Presels should have been removed before this point"); } - virtual void visit(AstNode* nodep) { + virtual void visit(AstNode* nodep) VL_OVERRIDE { iterateChildren(nodep); editDType(nodep); } diff --git a/src/V3WidthSel.cpp b/src/V3WidthSel.cpp index 7610d550a..d6e866185 100644 --- a/src/V3WidthSel.cpp +++ b/src/V3WidthSel.cpp @@ -66,10 +66,10 @@ private: // RETURN TYPE struct FromData { - AstNode* m_errp; // Node that was found, for error reporting if not known type + AstNodeDType* m_errp; // Node that was found, for error reporting if not known type AstNodeDType* m_dtypep; // Data type for the 'from' slice VNumRange m_fromRange; // Numeric range bounds for the 'from' slice - FromData(AstNode* errp, AstNodeDType* dtypep, const VNumRange& fromRange) + FromData(AstNodeDType* errp, AstNodeDType* dtypep, const VNumRange& fromRange) { m_errp = errp; m_dtypep = dtypep; m_fromRange = fromRange; } ~FromData() {} }; @@ -86,7 +86,7 @@ private: } UASSERT_OBJ(basefromp && basefromp->dtypep(), nodep, "Select with no from dtype"); AstNodeDType* ddtypep = basefromp->dtypep()->skipRefp(); - AstNode* errp = ddtypep; + AstNodeDType* errp = ddtypep; UINFO(9," fromData.ddtypep = "<declRange(); @@ -99,20 +99,21 @@ private: fromRange = adtypep->declRange(); } else if (AstBasicDType* adtypep = VN_CAST(ddtypep, BasicDType)) { - if (adtypep->isRanged()) { + if (adtypep->isString() && VN_IS(nodep, SelBit)) { + } else if (adtypep->isRanged()) { UASSERT_OBJ(!(adtypep->rangep() && (!VN_IS(adtypep->rangep()->msbp(), Const) || !VN_IS(adtypep->rangep()->lsbp(), Const))), nodep, "Non-constant variable range; errored earlier"); // in constifyParam(bfdtypep) fromRange = adtypep->declRange(); } else { - nodep->v3error("Illegal bit or array select; type does not have a bit range, or bad dimension: type is " - <prettyName()); + nodep->v3error("Illegal bit or array select; type does not have a bit range, or " + << "bad dimension: data type is " << errp->prettyDTypeNameQ()); } } else { - nodep->v3error("Illegal bit or array select; type already selected, or bad dimension: type is " - <prettyName()); + nodep->v3error("Illegal bit or array select; type already selected, or bad dimension: " + << "data type is " << errp->prettyDTypeNameQ()); } return FromData(errp, ddtypep, fromRange); } @@ -194,9 +195,9 @@ private: } // VISITORS - // If adding new visitors, insure V3Width's visit(TYPE) calls into here + // If adding new visitors, ensure V3Width's visit(TYPE) calls into here - virtual void visit(AstSelBit* nodep) { + virtual void visit(AstSelBit* nodep) VL_OVERRIDE { // Select of a non-width specified part of an array, i.e. "array[2]" // This select style has a lsb and msb (no user specified width) UINFO(6,"SELBIT "<=9) newp->dumpTree(cout, "--SELBTq: "); nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } - else if (VN_IS(ddtypep, BasicDType)) { + else if (VN_IS(ddtypep, BasicDType) && ddtypep->isString()) { + // SELBIT(string, index) -> GETC(string, index) + AstNodeVarRef* varrefp = VN_CAST(fromp, NodeVarRef); + if (!varrefp) nodep->v3error("Unsupported: String array operation on non-variable"); + AstNode* newp; + if (varrefp && varrefp->lvalue()) { + newp = new AstGetcRefN(nodep->fileline(), fromp, rhsp); + } else { + newp = new AstGetcN(nodep->fileline(), fromp, rhsp); + } + UINFO(6, " new " << newp << endl); + nodep->replaceWith(newp); + VL_DO_DANGLING(pushDeletep(nodep), nodep); + } else if (VN_IS(ddtypep, BasicDType)) { // SELBIT(range, index) -> SEL(array, index, 1) AstSel* newp = new AstSel(nodep->fileline(), fromp, @@ -293,14 +307,15 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } else { // NULL=bad extract, or unknown node type - nodep->v3error("Illegal bit or array select; type already selected, or bad dimension: type is" - <prettyName()); + nodep->v3error("Illegal bit or array select; type already selected, or bad dimension: " + << "data type is" << fromdata.m_errp->prettyDTypeNameQ()); // How to recover? We'll strip a dimension. - nodep->replaceWith(fromp); VL_DO_DANGLING(pushDeletep(nodep), nodep); + nodep->replaceWith(fromp); + VL_DO_DANGLING(pushDeletep(nodep), nodep); } if (!rhsp->backp()) { VL_DO_DANGLING(pushDeletep(rhsp), rhsp); } } - virtual void visit(AstSelExtract* nodep) { + virtual void visit(AstSelExtract* nodep) VL_OVERRIDE { // Select of a range specified part of an array, i.e. "array[2:3]" // SELEXTRACT(from,msb,lsb) -> SEL(from, lsb, 1+msb-lsb) // This select style has a (msb or lsb) and width @@ -409,11 +424,12 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } else { // NULL=bad extract, or unknown node type - nodep->v3error("Illegal range select; type already selected, or bad dimension: type is " - <prettyName()); - UINFO(1," Related ddtype: "<v3error("Illegal range select; type already selected, or bad dimension: " + << "data type is " << fromdata.m_errp->prettyDTypeNameQ()); + UINFO(1, " Related ddtype: " << ddtypep << endl); // How to recover? We'll strip a dimension. - nodep->replaceWith(fromp); VL_DO_DANGLING(pushDeletep(nodep), nodep); + nodep->replaceWith(fromp); + VL_DO_DANGLING(pushDeletep(nodep), nodep); } // delete whatever we didn't use in reconstruction if (!fromp->backp()) { VL_DO_DANGLING(pushDeletep(fromp), fromp); } @@ -482,27 +498,28 @@ private: nodep->replaceWith(newp); VL_DO_DANGLING(pushDeletep(nodep), nodep); } else { // NULL=bad extract, or unknown node type - nodep->v3error("Illegal +: or -: select; type already selected, or bad dimension: type is " - <prettyTypeName()); + nodep->v3error("Illegal +: or -: select; type already selected, or bad dimension: " + << "data type is " << fromdata.m_errp->prettyDTypeNameQ()); // How to recover? We'll strip a dimension. - nodep->replaceWith(fromp); VL_DO_DANGLING(pushDeletep(nodep), nodep); + nodep->replaceWith(fromp); + VL_DO_DANGLING(pushDeletep(nodep), nodep); } // delete whatever we didn't use in reconstruction if (!fromp->backp()) { VL_DO_DANGLING(pushDeletep(fromp), fromp); } if (!rhsp->backp()) { VL_DO_DANGLING(pushDeletep(rhsp), rhsp); } if (!widthp->backp()) { VL_DO_DANGLING(pushDeletep(widthp), widthp); } } - virtual void visit(AstSelPlus* nodep) { + virtual void visit(AstSelPlus* nodep) VL_OVERRIDE { replaceSelPlusMinus(nodep); } - virtual void visit(AstSelMinus* nodep) { + virtual void visit(AstSelMinus* nodep) VL_OVERRIDE { replaceSelPlusMinus(nodep); } - // If adding new visitors, insure V3Width's visit(TYPE) calls into here + // If adding new visitors, ensure V3Width's visit(TYPE) calls into here //-------------------- // Default - virtual void visit(AstNode* nodep) { // LCOV_EXCL_LINE + virtual void visit(AstNode* nodep) VL_OVERRIDE { // LCOV_EXCL_LINE // See notes above; we never iterate nodep->v3fatalSrc("Shouldn't iterate in V3WidthSel"); } diff --git a/src/Verilator.cpp b/src/Verilator.cpp index 3c474f83a..68ee170b0 100644 --- a/src/Verilator.cpp +++ b/src/Verilator.cpp @@ -101,67 +101,7 @@ V3Global v3Global; -//###################################################################### -// V3 Class -- top level - -AstNetlist* V3Global::makeNetlist() { - AstNetlist* newp = new AstNetlist(); - newp->addTypeTablep(new AstTypeTable(newp->fileline())); - return newp; -} - -void V3Global::checkTree() { rootp()->checkTree(); } - -void V3Global::clear() { - if (m_rootp) VL_DO_CLEAR(m_rootp->deleteTree(), m_rootp = NULL); -} - -void V3Global::readFiles() { - // NODE STATE - // AstNode::user4p() // VSymEnt* Package and typedef symbol names - AstUser4InUse inuser4; - - VInFilter filter (v3Global.opt.pipeFilter()); - V3ParseSym parseSyms (v3Global.rootp()); // Symbol table must be common across all parsing - - V3Parse parser (v3Global.rootp(), &filter, &parseSyms); - // Read top module - const V3StringList& vFiles = v3Global.opt.vFiles(); - for (V3StringList::const_iterator it = vFiles.begin(); it != vFiles.end(); ++it) { - string filename = *it; - parser.parseFile(new FileLine(FileLine::commandLineFilename()), - filename, false, - "Cannot find file containing module: "); - } - - // Read libraries - // To be compatible with other simulators, - // this needs to be done after the top file is read - const V3StringSet& libraryFiles = v3Global.opt.libraryFiles(); - for (V3StringSet::const_iterator it = libraryFiles.begin(); it != libraryFiles.end(); ++it) { - string filename = *it; - parser.parseFile(new FileLine(FileLine::commandLineFilename()), - filename, true, - "Cannot find file containing library module: "); - } - //v3Global.rootp()->dumpTreeFile(v3Global.debugFilename("parse.tree")); - V3Error::abortIfErrors(); - - if (!v3Global.opt.preprocOnly()) { - // Resolve all modules cells refer to - V3LinkCells::link(v3Global.rootp(), &filter, &parseSyms); - } -} - -void V3Global::dumpCheckGlobalTree(const string& stagename, int newNumber, bool doDump) { - v3Global.rootp()->dumpTreeFile(v3Global.debugFilename(stagename+".tree", newNumber), - false, doDump); - if (v3Global.opt.stats()) V3Stats::statsStage(stagename); -} - -//###################################################################### - -void process() { +static void process() { // Sort modules by level so later algorithms don't need to care V3LinkLevel::modSortByLevel(); V3Error::abortIfErrors(); diff --git a/src/astgen b/src/astgen index 184f329f4..ed42a54bf 100644 --- a/src/astgen +++ b/src/astgen @@ -30,6 +30,15 @@ if (! GetOptions( read_types("$Opt_I[0]/V3Ast.h"); read_types("$Opt_I[0]/V3AstNodes.h"); +foreach my $type (sort (keys %Classes)) { + # Check all leaves are not AstNode* and non-leaves are AstNode* + my @children = children_of($type); + if ($type =~ /^Node/) { + @children || die "Error: Final AstNode subclasses must not be named AstNode*: Ast$type" + } else { + !@children || die "Error: Non-final AstNode subclasses must be named AstNode*: Ast$type" + } +} read_stages("$Opt_I[0]/Verilator.cpp"); read_refs(glob("$Opt_I[0]/*.y"), glob("$Opt_I[0]/*.h"), glob("$Opt_I[0]/*.cpp")); if ($opt_report) { @@ -39,9 +48,9 @@ if ($opt_classes) { write_report("V3Ast__gen_report.txt"); write_classes("V3Ast__gen_classes.h"); write_visitor("V3Ast__gen_visitor.h"); - write_intf("V3Ast__gen_interface.h"); write_impl("V3Ast__gen_impl.h"); write_types("V3Ast__gen_types.h"); + write_header("V3AstNodes__gen.h"); } foreach my $cpt (@Opt_Cpt) { Cpt::process(in_filename=>"$Opt_I[0]/${cpt}.cpp", out_filename=>"${cpt}__gen.cpp"); @@ -235,74 +244,152 @@ sub write_visitor { $fh->close(); } -sub write_intf { +sub write_impl { my $fh = open_file(@_); print $fh "\n"; - print $fh " // These for use by VN_IS macro only\n"; + + print $fh " // These for use by VN_IS only\n"; foreach my $type (sort (keys %Classes)) { - print $fh " static bool privateIs",$type,"(const AstNode* nodep);\n"; + print $fh "template<> inline bool AstNode::privateIs(const AstNode* nodep) { "; + if ($type eq "Node") { + print $fh "return nodep != NULL; "; + } else { + print $fh "return nodep && "; + if ($type =~ /^Node/) { + print $fh "(static_cast(nodep->type()) >= static_cast(AstType::first",$type,")) && "; + print $fh "(static_cast(nodep->type()) <= static_cast(AstType::last",$type,")); "; + } else { + print $fh "(static_cast(nodep->type()) == static_cast(AstType::at",$type,")); "; + } + } + print $fh "}\n" } - print $fh "\n"; print $fh " // These for use by VN_CAST macro only\n"; foreach my $type (sort (keys %Classes)) { - print $fh " static Ast",$type,"* privateCast",$type,"(AstNode* nodep);\n"; + print $fh "template<> inline Ast",$type,"* AstNode::privateCast(AstNode* nodep) { "; + if ($type eq "Node") { + print $fh "return nodep; "; + } else { + print $fh "return AstNode::privateIs(nodep) ? "; + print $fh "reinterpret_cast(nodep) : NULL; "; + } + print $fh "}\n"; } + + print $fh " // These for use by VN_CAST_CONST macro only\n"; foreach my $type (sort (keys %Classes)) { - print $fh " static const Ast",$type,"* privateConstCast",$type,"(const AstNode* nodep);\n"; + print $fh "template<> inline const Ast",$type,"* AstNode::privateConstCast(const AstNode* nodep) { "; + if ($type eq "Node") { + print $fh "return nodep; "; + } else { + print $fh "return AstNode::privateIs(nodep) ? "; + print $fh "reinterpret_cast(nodep) : NULL; "; + } + print $fh "}\n"; } $fh->close(); } -sub write_impl { - my $fh = open_file(@_); +sub write_type_enum { + my $fh = shift; + my $type = shift; + my $idx = shift; + my $processed = shift; + my $kind = shift; + my $indent = shift; - print $fh "\n"; - print $fh " // These for use by VN_IS macro only\n"; - foreach my $type (sort (keys %Classes)) { - if (children_of($type)) { - print $fh "inline bool AstNode::privateIs",$type,"(const AstNode* nodep) { return (bool)(dynamic_cast(nodep)); }\n"; - } else { - print $fh "inline bool AstNode::privateIs",$type,"(const AstNode* nodep) { return nodep && nodep->type() == AstType::at",$type,"; }\n"; + # Skip this if it has already been processed + return $idx if (exists $processed->{$type}); + + # Mark processed + $processed->{$type} = 1; + + # The last used index + my $last; + + if ($type !~ /^Node/) { + $last = $idx; + if ($kind eq "concrete-enum") { + print $fh " "x($indent*4), "at",$type," = ",$idx,",\n"; + } elsif ($kind eq "concrete-ascii") { + print $fh " "x($indent*4), "\"", uc $type, "\",\n"; } + $idx += 1; + } elsif ($kind eq "abstract-enum") { + print $fh " "x($indent*4), "first",$type," = ",$idx,",\n"; } - foreach my $type (sort (keys %Classes)) { - print $fh "inline Ast",$type,"* AstNode::privateCast",$type,"(AstNode* nodep) { return dynamic_cast(nodep); }\n"; - } - foreach my $type (sort (keys %Classes)) { - print $fh "inline const Ast",$type,"* AstNode::privateConstCast",$type,"(const AstNode* nodep) { return dynamic_cast(nodep); }\n"; + foreach my $child (sort keys %{$::Children{$type}}) { + ($idx, $last) = write_type_enum($fh, $child, $idx, $processed, $kind, $indent); } - $fh->close(); + if ($type =~ /^Node/ && ($kind eq "abstract-enum")) { + print $fh " "x($indent*4), "last",$type," = ",$last,",\n"; + } + + return $idx, $last; } sub write_types { my $fh = open_file(@_); printf $fh " enum en {\n"; - # Add "at" prefix to avoid conflicting with FOPEN and other macros in include files - foreach my $type (sort (keys %Classes)) { - next if $type =~ /^Node/; - print $fh "\tat",$type,",\n"; - } - printf $fh "\t_ENUM_END\n"; + (my $final, undef) = write_type_enum($fh, "Node", 0, {}, "concrete-enum", 2); + printf $fh " _ENUM_END = $final\n"; printf $fh " };\n"; + + printf $fh " enum bounds {\n"; + write_type_enum($fh, "Node", 0, {}, "abstract-enum", 2); + printf $fh " _BOUNDS_END\n"; + printf $fh " };\n"; + printf $fh " const char* ascii() const {\n"; - printf $fh " const char* const names[] = {\n"; - foreach my $type (sort (keys %Classes)) { - next if $type =~ /^Node/; - print $fh "\t\"", uc $type, "\",\n"; - } - printf $fh "\t\"_ENUM_END\"\n"; + printf $fh " static const char* const names[_ENUM_END + 1] = {\n"; + write_type_enum($fh, "Node", 0, {}, "concrete-ascii", 3); + printf $fh " \"_ENUM_END\"\n"; printf $fh " };\n"; printf $fh " return names[m_e];\n"; printf $fh " };\n"; $fh->close(); } +sub write_header { + my $fh = open_file(@_); + + my $type = "None"; + my $base = "None"; + + my $in_filename = "V3AstNodes.h"; + my $ifile = "$Opt_I[0]/$in_filename"; + my $ifh = IO::File->new($ifile) or die "%Error: $! $ifile,"; + + $fh->print("#line 1 \"../$in_filename\"\n"); + + while (defined (my $line = $ifh->getline())) { + # Drop expanded macro definitions - but keep empty line so compiler + # message locations are accurate + $line =~ s/^\s*#(define|undef)\s+ASTGEN_.*$//; + + # Track current node type and base class + if ($line =~ /^\s*class\s*Ast(\S+)\s*:\s*(public)?\s*(AstNode\S*)/) { + $type = $1; + $base = $3; + } + + # Substitute macros + $line =~ s/\bASTGEN_SUPER\s*\(/$base(AstType::at$type, /; + + # Emit the line + print $fh $line; + } + + $ifh->close(); + $fh->close(); +} + ####################################################################### package Cpt; @@ -618,7 +705,7 @@ sub tree_base { # saves one comparison. if ($out_for_type_sc[0]) { # Short-circuited types $self->print(" // Generated by astgen with short-circuiting\n", - " virtual void visit(Ast${type}* nodep) {\n", + " virtual void visit(Ast${type}* nodep) VL_OVERRIDE {\n", " iterateAndNextNull(nodep->lhsp());\n", @out_for_type_sc); $self->print(" iterateAndNextNull(nodep->rhsp());\n", @@ -629,8 +716,9 @@ sub tree_base { } elsif ($out_for_type[0]) { # Other types with something to print my $skip = $self->{tree_skip_visit}{$type}; my $gen = $skip ? "Gen" : ""; + my $override = $skip ? "" : " VL_OVERRIDE"; $self->print(" // Generated by astgen\n", - " virtual void visit$gen(Ast${type}* nodep) {\n", + " virtual void visit$gen(Ast${type}* nodep)${override} {\n", ($skip?"": " iterateChildren(nodep);\n"), @out_for_type, diff --git a/src/bisonpre b/src/bisonpre index b6c1f9322..4db7d0bf6 100755 --- a/src/bisonpre +++ b/src/bisonpre @@ -392,7 +392,8 @@ sub clean_input { } elsif ($needmore) { # Bison doesn't have a #line directive, so we need somewhere to insert into $line =~ s!^\s*//.*$!!; - ($line =~ m/^\s*$/) or die "%Error: $filename:$l: Need $needmore more blank lines to insure line numbers are constant\n"; + ($line =~ m/^\s*$/) + or die "%Error: $filename:$l: Need $needmore more blank lines to keep line numbers are constant\n"; $needmore--; } else { push @lines, $line; diff --git a/src/verilog.l b/src/verilog.l index 2cbdc58a3..46fc1dd59 100644 --- a/src/verilog.l +++ b/src/verilog.l @@ -234,6 +234,7 @@ vnum {vnum1}|{vnum2}|{vnum3}|{vnum4}|{vnum5} "$rtoi" { FL; return yD_RTOI; } "$setup" { FL; return yaTIMINGSPEC; } "$setuphold" { FL; return yaTIMINGSPEC; } + "$sampled" { FL; return yD_SAMPLED; } "$sformat" { FL; return yD_SFORMAT; } "$sformatf" { FL; return yD_SFORMATF; } "$shortrealtobits" { FL; return yD_SHORTREALTOBITS; } @@ -251,6 +252,7 @@ vnum {vnum1}|{vnum2}|{vnum3}|{vnum4}|{vnum5} "$test$plusargs" { FL; return yD_TESTPLUSARGS; } "$time" { FL; return yD_TIME; } "$timeskew" { FL; return yaTIMINGSPEC; } + "$typename" { FL; return yD_TYPENAME; } "$ungetc" { FL; return yD_UNGETC; } "$value$plusargs" { FL; return yD_VALUEPLUSARGS; } "$width" { FL; return yaTIMINGSPEC; } diff --git a/src/verilog.y b/src/verilog.y index 328fbc9ba..c7ee27ba1 100644 --- a/src/verilog.y +++ b/src/verilog.y @@ -591,6 +591,7 @@ class AstSenTree; %token yD_REWIND "$rewind" %token yD_RIGHT "$right" %token yD_RTOI "$rtoi" +%token yD_SAMPLED "$sampled" %token yD_SFORMAT "$sformat" %token yD_SFORMATF "$sformatf" %token yD_SHORTREALTOBITS "$shortrealtobits" @@ -608,6 +609,7 @@ class AstSenTree; %token yD_TANH "$tanh" %token yD_TESTPLUSARGS "$test$plusargs" %token yD_TIME "$time" +%token yD_TYPENAME "$typename" %token yD_UNGETC "$ungetc" %token yD_UNIT "$unit" %token yD_UNPACKED_DIMENSIONS "$unpacked_dimensions" @@ -1567,7 +1569,7 @@ data_typeNoRef: // ==IEEE: data_type, excluding class_type etc referenc // // instead see data_typeVar | yVIRTUAL__INTERFACE yINTERFACE id/*interface*/ { $$ = NULL; BBUNSUP($1, "Unsupported: virtual interface"); } | yVIRTUAL__anyID id/*interface*/ { $$ = NULL; BBUNSUP($1, "Unsupported: virtual data type"); } - //UNSUP type_reference { UNSUP } + | type_reference { $$ = $1; } // // IEEE: class_scope: see data_type above // // IEEE: class_type: see data_type above // // IEEE: ps_covergroup: see data_type above @@ -1584,9 +1586,9 @@ var_data_type: // ==IEEE: var_data_type | yVAR implicit_typeE { $$ = $2; } ; -//UNSUP type_reference: // ==IEEE: type_reference -//UNSUP yTYPE '(' exprOrDataType ')' { UNSUP } -//UNSUP ; +type_reference: // ==IEEE: type_reference + yTYPE '(' exprOrDataType ')' { $$ = new AstRefDType($1, AstRefDType::FlagTypeOfExpr(), $3); } + ; struct_unionDecl: // IEEE: part of data_type // // packedSigningE is NOP for unpacked @@ -3265,6 +3267,7 @@ system_f_call_or_t: // IEEE: part of system_tf_call (can be task or func) | yD_RIGHT '(' exprOrDataType ')' { $$ = new AstAttrOf($1,AstAttrType::DIM_RIGHT,$3,NULL); } | yD_RIGHT '(' exprOrDataType ',' expr ')' { $$ = new AstAttrOf($1,AstAttrType::DIM_RIGHT,$3,$5); } | yD_RTOI '(' expr ')' { $$ = new AstRToIS($1,$3); } + | yD_SAMPLED '(' expr ')' { $$ = new AstSampled($1, $3); } | yD_SFORMATF '(' str commaEListE ')' { $$ = new AstSFormatF($1,*$3,false,$4); } | yD_SHORTREALTOBITS '(' expr ')' { $$ = new AstRealToBits($1,$3); UNSUPREAL($1); } | yD_SIGNED '(' expr ')' { $$ = new AstSigned($1,$3); } @@ -3279,6 +3282,7 @@ system_f_call_or_t: // IEEE: part of system_tf_call (can be task or func) | yD_TANH '(' expr ')' { $$ = new AstTanhD($1,$3); } | yD_TESTPLUSARGS '(' str ')' { $$ = new AstTestPlusArgs($1,*$3); } | yD_TIME parenE { $$ = new AstTime($1); } + | yD_TYPENAME '(' exprOrDataType ')' { $$ = new AstAttrOf($1, AstAttrType::TYPENAME, $3); } | yD_UNGETC '(' expr ',' expr ')' { $$ = new AstFUngetC($1, $5, $3); } // Arg swap to file first | yD_UNPACKED_DIMENSIONS '(' exprOrDataType ')' { $$ = new AstAttrOf($1,AstAttrType::DIM_UNPK_DIMENSIONS,$3); } | yD_UNSIGNED '(' expr ')' { $$ = new AstUnsigned($1,$3); } diff --git a/test_regress/Makefile b/test_regress/Makefile index 46c13973f..82fff4a4d 100644 --- a/test_regress/Makefile +++ b/test_regress/Makefile @@ -24,12 +24,12 @@ include $(VERILATOR_ROOT)/include/verilated.mk ###################################################################### ifneq ($(VCS_HOME),) -#Default to off, even with vcs; not all tests are insured to be working +#Default to off, even with vcs; not all tests are ensured to be working #PRODUCTS += --vcs endif ifneq ($(NC_ROOT),) -#Default to off, even with vcs; not all tests are insured to be working +#Default to off, even with vcs; not all tests are ensured to be working #PRODUCTS += --nc endif diff --git a/test_regress/driver.pl b/test_regress/driver.pl index c65327582..abc61c93f 100755 --- a/test_regress/driver.pl +++ b/test_regress/driver.pl @@ -1057,6 +1057,7 @@ sub compile { if (!$param{fails} && $param{verilator_make_gmake}) { $self->oprint("Running make (gmake)\n") if $self->{verbose}; $self->_run(logfile => "$self->{obj_dir}/vlt_gcc.log", + entering => "$self->{obj_dir}", cmd => ["make", "-C ".$self->{obj_dir}, "-f ".$::RealBin."/Makefile_obj", @@ -1416,7 +1417,8 @@ sub run { } sub _run { my $self = (ref $_[0]? shift : $Self); - my %param = (tee=>1, + my %param = (tee => 1, + #entering => # Print entering directory information @_); my $command = join(' ',@{$param{cmd}}); $command = "time $command" if $opt_benchmark && $command !~ /^cd /; @@ -1438,6 +1440,8 @@ sub _run { my $pid=fork(); if ($pid) { # Parent close CHILDWR; + print "driver: Entering directory '", + File::Spec->rel2abs($param{entering}), "'\n" if $param{entering}; while (1) { my $buf = ''; my $got = sysread PARENTRD,$buf,10000; @@ -1447,6 +1451,8 @@ sub _run { } close PARENTRD; close $logfh if $logfh; + print "driver: Leaving directory '", + File::Spec->rel2abs($param{entering}), "'\n" if $param{entering}; } else { # Child close PARENTRD; diff --git a/test_regress/t/t_array_pattern_unpacked.v b/test_regress/t/t_array_pattern_unpacked.v index 9aea2cb6a..903c8eaae 100644 --- a/test_regress/t/t_array_pattern_unpacked.v +++ b/test_regress/t/t_array_pattern_unpacked.v @@ -7,14 +7,18 @@ module t (/*AUTOARG*/); logic [3:0] array_simp [1:0] [3:0]; // big endian array + int irep[1:2][1:6]; + initial begin array_simp[0] = '{ 4'd3, 4'd2, 4'd1, 4'd0}; - if ({array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} !== 16'h3210) $stop; + if ({array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} + !== 16'h3210) $stop; // verilator lint_off WIDTH array_simp[0] = '{ 3 ,2 ,1, 0 }; // verilator lint_on WIDTH - if ({array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} !== 16'h3210) $stop; + if ({array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} + !== 16'h3210) $stop; // Doesn't seem to work for unpacked arrays in other simulators //array_simp[0] = '{ 1:4'd3, default:13 }; @@ -22,21 +26,31 @@ module t (/*AUTOARG*/); array_simp = '{ '{ 4'd3, 4'd2, 4'd1, 4'd0 }, '{ 4'd1, 4'd2, 4'd3, 4'd4 }}; if ({array_simp[1][3],array_simp[1][2],array_simp[1][1],array_simp[1][0], - array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} !== 32'h3210_1234) $stop; + array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} + !== 32'h3210_1234) $stop; // Doesn't seem to work for unpacked arrays in other simulators array_simp = '{2{ '{4'd3, 4'd2, 4'd1, 4'd0 } }}; if ({array_simp[1][3],array_simp[1][2],array_simp[1][1],array_simp[1][0], - array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} !== 32'h3210_3210) $stop; + array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} + !== 32'h3210_3210) $stop; array_simp = '{2{ '{4{ 4'd3 }} }}; if ({array_simp[1][3],array_simp[1][2],array_simp[1][1],array_simp[1][0], - array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} !== 32'h3333_3333) $stop; + array_simp[0][3],array_simp[0][2],array_simp[0][1],array_simp[0][0]} + !== 32'h3333_3333) $stop; // Not legal in other simulators - replication doesn't match // However IEEE suggests this is legal. //array_simp = '{2{ '{2{ 4'd3, 4'd2 }} }}; // Note it's not '{3,2} + // Replication + irep = '{2{ '{3 {4, 5}}}}; + if ({irep[1][1], irep[1][2], irep[1][3], irep[1][4], irep[1][5], irep[1][6]} + != {32'h4, 32'h5, 32'h4, 32'h5, 32'h4, 32'h5}) $stop; + if ({irep[2][1], irep[2][2], irep[2][3], irep[2][4], irep[2][5], irep[2][6]} + != {32'h4, 32'h5, 32'h4, 32'h5, 32'h4, 32'h5}) $stop; + $write("*-* All Finished *-*\n"); $finish; end diff --git a/test_regress/t/t_assert_synth.v b/test_regress/t/t_assert_synth.v index d48d5ccb0..4e090850b 100644 --- a/test_regress/t/t_assert_synth.v +++ b/test_regress/t/t_assert_synth.v @@ -18,7 +18,7 @@ module t (/*AUTOARG*/ wire a_l = ~a; wire b_oc_l = ~b_oc; - // Note we must insure that full, parallel, etc, only fire during + // Note we must ensure that full, parallel, etc, only fire during // edges (not mid-cycle), and must provide a way to turn them off. // SystemVerilog provides: $asserton and $assertoff. diff --git a/test_regress/t/t_assoc_pattern_unsup.out b/test_regress/t/t_assoc_pattern_unsup.out index 33981b55b..51f4430cd 100644 --- a/test_regress/t/t_assoc_pattern_unsup.out +++ b/test_regress/t/t_assoc_pattern_unsup.out @@ -1,4 +1,4 @@ -%Error: t/t_assoc_pattern_unsup.v:18: Unsupported: Assignment pattern applies against non struct/union: ASSOCARRAYDTYPE +%Error: t/t_assoc_pattern_unsup.v:18: Unsupported: Assignment pattern applies against non struct/union data type: 'string[string]' : ... In instance t a = '{ "f": "fooed", "b": "bared", default: "defaulted" }; ^~ diff --git a/test_regress/t/t_bitsel_const_bad.out b/test_regress/t/t_bitsel_const_bad.out index 7637f6435..1bcbf6c61 100644 --- a/test_regress/t/t_bitsel_const_bad.out +++ b/test_regress/t/t_bitsel_const_bad.out @@ -1,4 +1,4 @@ -%Error: t/t_bitsel_const_bad.v:20: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_bitsel_const_bad.v:20: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t assign a = b[0]; ^ diff --git a/test_regress/t/t_clk_concat.pl b/test_regress/t/t_clk_concat.pl index abe880617..fd7224cbf 100755 --- a/test_regress/t/t_clk_concat.pl +++ b/test_regress/t/t_clk_concat.pl @@ -16,9 +16,9 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_clk_concat_vlt.pl b/test_regress/t/t_clk_concat_vlt.pl index 965daacd9..8c882f901 100755 --- a/test_regress/t/t_clk_concat_vlt.pl +++ b/test_regress/t/t_clk_concat_vlt.pl @@ -17,10 +17,10 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_dedupe_clk_gate.pl b/test_regress/t/t_dedupe_clk_gate.pl index 99b5982d1..85b870fb2 100755 --- a/test_regress/t/t_dedupe_clk_gate.pl +++ b/test_regress/t/t_dedupe_clk_gate.pl @@ -16,7 +16,7 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); file_grep($Self->{stats}, qr/Optimizations, Gate sigs deduped\s+(\d+)/i, 4); } diff --git a/test_regress/t/t_display_signed.v b/test_regress/t/t_display_signed.v index bdbe69923..cd4a5fa18 100644 --- a/test_regress/t/t_display_signed.v +++ b/test_regress/t/t_display_signed.v @@ -4,14 +4,21 @@ // without warranty, 2003 by Wilson Snyder. module t; - reg signed [20:0] longp; initial longp = 21'shbbccc; - reg signed [20:0] longn; initial longn = 21'shbbccc; initial longn[20]=1'b1; - reg signed [40:0] quadp; initial quadp = 41'sh1_bbbb_cccc; - reg signed [40:0] quadn; initial quadn = 41'sh1_bbbb_cccc; initial quadn[40]=1'b1; - reg signed [80:0] widep; initial widep = 81'shbc_1234_5678_1234_5678; - reg signed [80:0] widen; initial widen = 81'shbc_1234_5678_1234_5678; initial widen[40]=1'b1; + reg signed [20:0] longp; + reg signed [20:0] longn; + reg signed [40:0] quadp; + reg signed [40:0] quadn; + reg signed [80:0] widep; + reg signed [80:0] widen; initial begin + longp = 21'shbbccc; + longn = 21'shbbccc; longn[20] = 1'b1; + quadp = 41'sh1_bbbb_cccc; + quadn = 41'sh1_bbbb_cccc; quadn[40] = 1'b1; + widep = 81'shbc_1234_5678_1234_5678; + widen = 81'shbc_1234_5678_1234_5678; widen[40] = 1'b1; + // Display formatting $display("[%0t] lp %%x=%x %%x=%x %%o=%o %%b=%b %%0d=%0d %%d=%d %%p=%p %%0p=%0p", $time, longp, longp, longp, longp, longp, longp, longp, longp); diff --git a/test_regress/t/t_dpi_var.pl b/test_regress/t/t_dpi_var.pl index 652a9657f..48029f606 100755 --- a/test_regress/t/t_dpi_var.pl +++ b/test_regress/t/t_dpi_var.pl @@ -17,10 +17,10 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_dpi_var_vlt.pl b/test_regress/t/t_dpi_var_vlt.pl index bc0af71ca..a6004fdc2 100755 --- a/test_regress/t/t_dpi_var_vlt.pl +++ b/test_regress/t/t_dpi_var_vlt.pl @@ -19,10 +19,10 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_enum_type_methods.v b/test_regress/t/t_enum_type_methods.v index 27139526c..8433a389d 100644 --- a/test_regress/t/t_enum_type_methods.v +++ b/test_regress/t/t_enum_type_methods.v @@ -34,10 +34,15 @@ module t (/*AUTOARG*/ `checkh(e.next, E04); `checkh(e.next(), E04); `checkh(e.next(1), E04); - //Unsup: `checkh(e.next(2), E01); + `checkh(e.next(1).next(1), E01); + `checkh(e.next(2), E01); + `checkh(e.next(1).next(1).next(1), E03); + `checkh(e.next(1).next(2), E03); + `checkh(e.next(3), E03); `checkh(e.prev, E01); `checkh(e.prev(1), E01); - //Unsup: `checkh(e.prev(2), E04); + `checkh(e.prev(1).prev(1), E04); + `checkh(e.prev(2), E04); `checkh(e.num, 3); `checks(e.name, "E03"); // @@ -61,30 +66,30 @@ module t (/*AUTOARG*/ `checks(e.name, "E01"); `checkh(e.next, E03); `checkh(e.next(1), E03); - //Unsup: `checkh(e.next(2), E04); + `checkh(e.next(2), E04); `checkh(e.prev, E04); `checkh(e.prev(1), E04); - //Unsup: `checkh(e.prev(2), E03); + `checkh(e.prev(2), E03); e <= E03; end else if (cyc==2) begin `checks(e.name, "E03"); `checkh(e.next, E04); `checkh(e.next(1), E04); - //Unsup: `checkh(e.next(2), E01); + `checkh(e.next(2), E01); `checkh(e.prev, E01); `checkh(e.prev(1), E01); - //Unsup: `checkh(e.prev(2), E04); + `checkh(e.prev(2), E04); e <= E04; end else if (cyc==3) begin `checks(e.name, "E04"); `checkh(e.next, E01); `checkh(e.next(1), E01); - //Unsup: `checkh(e.next(2), E03); + `checkh(e.next(2), E03); `checkh(e.prev, E03); `checkh(e.prev(1), E03); - //Unsup: `checkh(e.prev(2), E01); + `checkh(e.prev(2), E01); e <= E01; end else if (cyc==99) begin diff --git a/test_regress/t/t_enum_type_methods_bad.out b/test_regress/t/t_enum_type_methods_bad.out new file mode 100644 index 000000000..ca262cefa --- /dev/null +++ b/test_regress/t/t_enum_type_methods_bad.out @@ -0,0 +1,5 @@ +%Error: Internal Error: t/t_enum_type_methods_bad.v:23: ../V3Width.cpp:#: Unsupported: enum next/prev with non-const argument + : ... In instance t + e.next(increment); + ^~~~~~~~~ + ... See the manual and https://verilator.org for more assistance. diff --git a/test_regress/t/t_enum_type_methods_bad.pl b/test_regress/t/t_enum_type_methods_bad.pl new file mode 100755 index 000000000..45ec8147c --- /dev/null +++ b/test_regress/t/t_enum_type_methods_bad.pl @@ -0,0 +1,18 @@ +#!/usr/bin/perl +if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; } +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2003 by Wilson Snyder. This program is free software; you can +# redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. + +scenarios(simulator => 1); + +compile( + fails => 1, + expect_filename => $Self->{golden_filename} + ); + +ok(1); +1; diff --git a/test_regress/t/t_enum_type_methods_bad.v b/test_regress/t/t_enum_type_methods_bad.v new file mode 100644 index 000000000..f65f1b146 --- /dev/null +++ b/test_regress/t/t_enum_type_methods_bad.v @@ -0,0 +1,27 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2014 by Wilson Snyder. + +module t (/*AUTOARG*/ + // Inputs + clk, increment + ); + input clk; + input [1:0] increment; + + typedef enum [3:0] { + E01 = 1, + E03 = 3, + E04 = 4, + E05 = 5 + } my_t; + + my_t e; + + always @ (posedge clk) begin + e.next(increment); + $finish; + end + +endmodule diff --git a/test_regress/t/t_func_dotted_inl0.pl b/test_regress/t/t_func_dotted_inl0.pl index de41c1dc4..f1ece27d9 100755 --- a/test_regress/t/t_func_dotted_inl0.pl +++ b/test_regress/t/t_func_dotted_inl0.pl @@ -17,10 +17,10 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_func_dotted_inl0_vlt.pl b/test_regress/t/t_func_dotted_inl0_vlt.pl index b8c833d2c..92a4a7d81 100755 --- a/test_regress/t/t_func_dotted_inl0_vlt.pl +++ b/test_regress/t/t_func_dotted_inl0_vlt.pl @@ -17,10 +17,10 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_func_dotted_inl2.pl b/test_regress/t/t_func_dotted_inl2.pl index 9784092cd..c6355044c 100755 --- a/test_regress/t/t_func_dotted_inl2.pl +++ b/test_regress/t/t_func_dotted_inl2.pl @@ -17,8 +17,8 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_func_dotted_inl2_vlt.pl b/test_regress/t/t_func_dotted_inl2_vlt.pl index 32a36011f..a2c0873b2 100755 --- a/test_regress/t/t_func_dotted_inl2_vlt.pl +++ b/test_regress/t/t_func_dotted_inl2_vlt.pl @@ -17,8 +17,8 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_fuzz_eqne_bad.out b/test_regress/t/t_fuzz_eqne_bad.out index 599558e7f..528089125 100644 --- a/test_regress/t/t_fuzz_eqne_bad.out +++ b/test_regress/t/t_fuzz_eqne_bad.out @@ -1,4 +1,4 @@ -%Error: t/t_fuzz_eqne_bad.v:11: Slice operatator VARREF 't.b' on non-slicable (e.g. non-vector) right-hand-side operand +%Error: t/t_fuzz_eqne_bad.v:11: Slice operator VARREF 't.b' on non-slicable (e.g. non-vector) right-hand-side operand : ... In instance t.b initial c = (a != &b); ^ diff --git a/test_regress/t/t_fuzz_negwidth_bad.out b/test_regress/t/t_fuzz_negwidth_bad.out new file mode 100644 index 000000000..c9637baf3 --- /dev/null +++ b/test_regress/t/t_fuzz_negwidth_bad.out @@ -0,0 +1,4 @@ +%Error: t/t_fuzz_negwidth_bad.v:8: Unsupported: Width of number exceeds implementation limit: 1231232312312312'd1 (IEEE 2017 6.9.1) +int c = 1231232312312312'd1; + ^~~~~~~~~~~~~~~~~~~ +%Error: Exiting due to diff --git a/test_regress/t/t_fuzz_negwidth_bad.pl b/test_regress/t/t_fuzz_negwidth_bad.pl index fd7324fbf..b09f43e8b 100755 --- a/test_regress/t/t_fuzz_negwidth_bad.pl +++ b/test_regress/t/t_fuzz_negwidth_bad.pl @@ -11,6 +11,7 @@ scenarios(linter => 1); lint( fails => 1, + expect_filename => $Self->{golden_filename}, ); ok(1); diff --git a/test_regress/t/t_fuzz_negwidth_bad.v b/test_regress/t/t_fuzz_negwidth_bad.v index 730712a5c..245e36a71 100644 --- a/test_regress/t/t_fuzz_negwidth_bad.v +++ b/test_regress/t/t_fuzz_negwidth_bad.v @@ -4,4 +4,5 @@ // without warranty, 2019 by Wilson Snyder. int a = -12'd1; -int b = 1231232312312312'd1; +int b = 65536'd1; +int c = 1231232312312312'd1; diff --git a/test_regress/t/t_genvar_for_bad.out b/test_regress/t/t_genvar_for_bad.out new file mode 100644 index 000000000..bc1e2f800 --- /dev/null +++ b/test_regress/t/t_genvar_for_bad.out @@ -0,0 +1,5 @@ +%Error: t/t_genvar_for_bad.v:22: Genvar not legal in non-generate for (IEEE 2017 27.4): 't.i' + : ... Suggest move for loop upwards to generate-level scope. + for (i=0; i 1); + +lint( + fails => 1, + expect_filename => $Self->{golden_filename}, + ); + +ok(1); +1; diff --git a/test_regress/t/t_genvar_for_bad.v b/test_regress/t/t_genvar_for_bad.v new file mode 100644 index 000000000..846878bba --- /dev/null +++ b/test_regress/t/t_genvar_for_bad.v @@ -0,0 +1,27 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2020 by Wilson Snyder. + +module t (/*AUTOARG*/ + // Outputs + ov, + // Inputs + clk, iv + ); + + parameter N = 4; + + input clk; + input [63:0] iv[N-1:0]; + output logic [63:0] ov[N-1:0]; + + genvar i; + generate + always @(posedge clk) begin + for (i=0; i{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_inst_tree_inl1_pub0.pl b/test_regress/t/t_inst_tree_inl1_pub0.pl index c30155c2b..fe4c65c1e 100755 --- a/test_regress/t/t_inst_tree_inl1_pub0.pl +++ b/test_regress/t/t_inst_tree_inl1_pub0.pl @@ -17,9 +17,9 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_inst_tree_inl1_pub1.pl b/test_regress/t/t_inst_tree_inl1_pub1.pl index abd93f9a5..7124a2dce 100755 --- a/test_regress/t/t_inst_tree_inl1_pub1.pl +++ b/test_regress/t/t_inst_tree_inl1_pub1.pl @@ -18,9 +18,9 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_lint_numwidth.pl b/test_regress/t/t_lint_numwidth.pl new file mode 100755 index 000000000..adf0894d6 --- /dev/null +++ b/test_regress/t/t_lint_numwidth.pl @@ -0,0 +1,17 @@ +#!/usr/bin/perl +if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; } +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2008 by Wilson Snyder. This program is free software; you can +# redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. + +scenarios(linter => 1); + +lint( + verilator_flags2 => ["--max-num-width 131072"], + ); + +ok(1); +1; diff --git a/test_regress/t/t_lint_numwidth.v b/test_regress/t/t_lint_numwidth.v new file mode 100644 index 000000000..ff0d77aa3 --- /dev/null +++ b/test_regress/t/t_lint_numwidth.v @@ -0,0 +1,8 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2010 by Wilson Snyder. + +logic [65535:0] a = 65536'd1; +logic [65536:0] b = 65537'd1; +logic [131071:0] c = 131072'd1; diff --git a/test_regress/t/t_lint_width.v b/test_regress/t/t_lint_width.v index 06635b68f..80e03b89d 100644 --- a/test_regress/t/t_lint_width.v +++ b/test_regress/t/t_lint_width.v @@ -12,4 +12,10 @@ module t (); wire [4:0] sumb = 1'b1 + five; wire [4:0] sumc = five - 1'b1; + // Relatively harmless < or <= compared with something less wide + localparam [1:0] THREE = 3; + int a; + initial for (a = 0; a < THREE; ++a) $display(a); + initial for (a = 0; a <= THREE; ++a) $display(a); + endmodule diff --git a/test_regress/t/t_lint_width_bad.out b/test_regress/t/t_lint_width_bad.out index c85d13f09..e3fde1e3a 100644 --- a/test_regress/t/t_lint_width_bad.out +++ b/test_regress/t/t_lint_width_bad.out @@ -3,7 +3,7 @@ localparam [3:0] XS = 'hx; ^~ ... Use "/* verilator lint_off WIDTH */" and lint_on around source to disable this message. -%Warning-WIDTH: t/t_lint_width_bad.v:38: Operator ASSIGNW expects 5 bits on the Assign RHS, but Assign RHS's VARREF 'in' generates 4 bits. +%Warning-WIDTH: t/t_lint_width_bad.v:44: Operator ASSIGNW expects 5 bits on the Assign RHS, but Assign RHS's VARREF 'in' generates 4 bits. : ... In instance t.p4 wire [4:0] out = in; ^ @@ -31,4 +31,12 @@ : ... In instance t wire [2:0] cnt = (one + one + one + one); ^ +%Warning-WIDTH: t/t_lint_width_bad.v:36: Operator GT expects 41 bits on the LHS, but LHS's VARREF 'a' generates 32 bits. + : ... In instance t + initial for (a = 0; a > THREE; ++a) $display(a); + ^ +%Warning-WIDTH: t/t_lint_width_bad.v:37: Operator GTE expects 41 bits on the LHS, but LHS's VARREF 'a' generates 32 bits. + : ... In instance t + initial for (a = 0; a >= THREE; ++a) $display(a); + ^~ %Error: Exiting due to diff --git a/test_regress/t/t_lint_width_bad.v b/test_regress/t/t_lint_width_bad.v index 3496242ec..396f85ddb 100644 --- a/test_regress/t/t_lint_width_bad.v +++ b/test_regress/t/t_lint_width_bad.v @@ -30,6 +30,12 @@ module t (); wire one = 1; wire [2:0] cnt = (one + one + one + one); + // Not harmless > or >= compared with something wider (as different results if "a" wider) + localparam [40:0] THREE = 3; + int a; + initial for (a = 0; a > THREE; ++a) $display(a); + initial for (a = 0; a >= THREE; ++a) $display(a); + endmodule module p diff --git a/test_regress/t/t_mem_multi_ref_bad.out b/test_regress/t/t_mem_multi_ref_bad.out index edca2a8f7..e12873d3e 100644 --- a/test_regress/t/t_mem_multi_ref_bad.out +++ b/test_regress/t/t_mem_multi_ref_bad.out @@ -1,4 +1,4 @@ -%Error: t/t_mem_multi_ref_bad.v:14: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_mem_multi_ref_bad.v:14: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t dimn[1:0] = 0; ^ @@ -6,7 +6,7 @@ : ... In instance t dimn[1:0] = 0; ^ -%Error: t/t_mem_multi_ref_bad.v:15: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_mem_multi_ref_bad.v:15: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t dim0[1][1] = 0; ^ @@ -15,7 +15,7 @@ dim0[1][1] = 0; ^ ... Use "/* verilator lint_off SELRANGE */" and lint_on around source to disable this message. -%Error: t/t_mem_multi_ref_bad.v:16: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_mem_multi_ref_bad.v:16: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t dim1[1][1][1] = 0; ^ @@ -23,11 +23,11 @@ : ... In instance t dim1[1][1][1] = 0; ^ -%Error: t/t_mem_multi_ref_bad.v:18: Illegal +: or -: select; type already selected, or bad dimension: type is UNPACKARRAYDTYPE +%Error: t/t_mem_multi_ref_bad.v:18: Illegal +: or -: select; type already selected, or bad dimension: data type is 'logic[1:0]$[1:0][1:0]' : ... In instance t dim2[0 +: 1][1] = 0; ^ -%Error: t/t_mem_multi_ref_bad.v:22: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_mem_multi_ref_bad.v:22: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t dim0nv[1][1] = 0; ^ diff --git a/test_regress/t/t_past.v b/test_regress/t/t_past.v index 610e0fb5e..ed7f0add8 100644 --- a/test_regress/t/t_past.v +++ b/test_regress/t/t_past.v @@ -75,6 +75,8 @@ module Test (/*AUTOARG*/ if (dly0 != $past(in)) $stop; if (dly0 != $past(in,1)) $stop; if (dly1 != $past(in,2)) $stop; + // $sampled(expression) -> expression + if (in != $sampled(in)) $stop; end assert property (@(posedge clk) dly0 == $past(in)); diff --git a/test_regress/t/t_preproc.v b/test_regress/t/t_preproc.v index 035188082..c1c645c31 100644 --- a/test_regress/t/t_preproc.v +++ b/test_regress/t/t_preproc.v @@ -400,7 +400,7 @@ EXP: This is fooed_2 `ifdef TEMP `error "bad0" `endif Line_Preproc_Check `__LINE__ //====================================================================== -// Quoted multiline - track line numbers, and insure \\n gets propagated +// Quoted multiline - track line numbers, and ensure \\n gets propagated `define MULQUOTE "FOO \ BAR " `define MULQUOTE2(mq) `MULQUOTE mq `MULQUOTE diff --git a/test_regress/t/t_preproc_comments.out b/test_regress/t/t_preproc_comments.out index 1618f90ff..37d76bdcc 100644 --- a/test_regress/t/t_preproc_comments.out +++ b/test_regress/t/t_preproc_comments.out @@ -652,7 +652,7 @@ hello4hello4hello4hello4 Line_Preproc_Check 401 //====================================================================== -// Quoted multiline - track line numbers, and insure \\n gets propagated +// Quoted multiline - track line numbers, and ensure \\n gets propagated diff --git a/test_regress/t/t_queue_unsup_bad.out b/test_regress/t/t_queue_unsup_bad.out index b3c20486b..2be8b4f3c 100644 --- a/test_regress/t/t_queue_unsup_bad.out +++ b/test_regress/t/t_queue_unsup_bad.out @@ -1,4 +1,4 @@ -%Error: t/t_queue_unsup_bad.v:20: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:20: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {"q", "b", "c", "d", "e", "f"}; ^ @@ -10,23 +10,23 @@ : ... In instance t q.insert(2, "ins2"); ^~~~~~ -%Error: t/t_queue_unsup_bad.v:33: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:33: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {q, "f1"}; ^ -%Error: t/t_queue_unsup_bad.v:34: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:34: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {q, "f2"}; ^ -%Error: t/t_queue_unsup_bad.v:35: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:35: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {"b1", q}; ^ -%Error: t/t_queue_unsup_bad.v:36: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:36: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {"b2", q}; ^ -%Error: t/t_queue_unsup_bad.v:37: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:37: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = {q[0], q[2:$]}; ^ @@ -42,19 +42,19 @@ : ... In instance t q = {q[0], q[2:$]}; ^ -%Error: t/t_queue_unsup_bad.v:37: Illegal range select; type already selected, or bad dimension: type is +%Error: t/t_queue_unsup_bad.v:37: Illegal range select; type already selected, or bad dimension: data type is 'string[$]' : ... In instance t q = {q[0], q[2:$]}; ^ -%Error: t/t_queue_unsup_bad.v:41: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:41: Unsupported: Replication to form 'string[$]' data type : ... In instance t string ai[$] = { "Foo", "Bar" }; ^ -%Error: t/t_queue_unsup_bad.v:46: Unsupported: Assignment pattern applies against non struct/union: QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:46: Unsupported: Assignment pattern applies against non struct/union data type: 'string[$]' : ... In instance t q = '{ "BB", "CC" }; ^~ -%Error: t/t_queue_unsup_bad.v:49: Unsupported: Replication to form QUEUEDTYPE +%Error: t/t_queue_unsup_bad.v:49: Unsupported: Replication to form 'string[$]' data type : ... In instance t q = { "BB", "CC" }; ^ diff --git a/test_regress/t/t_string.v b/test_regress/t/t_string.v index 33107286f..e06cb2a2e 100644 --- a/test_regress/t/t_string.v +++ b/test_regress/t/t_string.v @@ -4,7 +4,7 @@ // without warranty, 2014 by Wilson Snyder. `define checkh(gotv,expv) do if ((gotv) !== (expv)) begin $write("%%Error: %s:%0d: got='h%x exp='h%x\n", `__FILE__,`__LINE__, (gotv), (expv)); $stop; end while(0); -`define checks(gotv,expv) do if ((gotv) !== (expv)) begin $write("%%Error: %s:%0d: got=\"%s\" exp=\"%s\"\n", `__FILE__,`__LINE__, (gotv), (expv)); $stop; end while(0); +`define checks(gotv,expv) do if ((gotv) != (expv)) begin $write("%%Error: %s:%0d: got=\"%s\" exp=\"%s\"\n", `__FILE__,`__LINE__, (gotv), (expv)); $stop; end while(0); module t (/*AUTOARG*/ // Inputs @@ -20,6 +20,8 @@ module t (/*AUTOARG*/ string s3; reg eq; + byte unpack1[0:4]; + // Operators == != < <= > >= {a,b} {a{b}} a[b] // a.len, a.putc, a.getc, a.toupper, a.tolower, a.compare, a.icompare, a.substr // a.atoi, a.atohex, a.atooct, a.atobin, a.atoreal, @@ -44,6 +46,20 @@ module t (/*AUTOARG*/ `checkh(s < "b", 1'b1); `checkh(s <= " ", 1'b0); `checkh(s <= "a", 1'b1); + +`ifndef VCS +`ifndef VERILATOR +`ifndef NC + // IEEE 1800-2017 5.9 assignment to byte array + unpack1 = "five"; + `checkh(unpack1[0], "f"); + `checkh(unpack1[1], "i"); + `checkh(unpack1[2], "v"); + `checkh(unpack1[3], "e"); + `checkh(unpack1[4], 8'h0); +`endif +`endif +`endif end // Test loop @@ -82,6 +98,19 @@ module t (/*AUTOARG*/ `checkh(s <= " ", 1'b0); `checkh(s <= "a", 1'b1); end + // String character references + else if (cyc==10) begin + s2 = "astring"; + end + else if (cyc==11) begin + `checks(s2, "astring"); + `checkh(s2.len(), 7); + `checkh(s2[1], "s"); + s2[0] = "0"; + s2[3] = "3"; + `checks(s2, "0st3ing"); + end + // else if (cyc==99) begin $write("*-* All Finished *-*\n"); $finish; diff --git a/test_regress/t/t_trace_complex.out b/test_regress/t/t_trace_complex.out index e3693b40b..1c37ae59f 100644 --- a/test_regress/t/t_trace_complex.out +++ b/test_regress/t/t_trace_complex.out @@ -1,35 +1,36 @@ $version Generated by VerilatedVcd $end -$date Wed Jan 8 07:23:20 2020 +$date Tue Jan 21 18:15:27 2020 $end $timescale 1ns $end $scope module top $end - $var wire 1 /" clk $end + $var wire 1 7" clk $end $scope module $unit $end $var wire 1 # global_bit $end $upscope $end $scope module t $end - $var wire 1 /" clk $end + $var wire 1 7" clk $end $var wire 32 + cyc [31:0] $end - $var wire 8 h" unpacked_array(-1) [7:0] $end - $var wire 8 g" unpacked_array(-2) [7:0] $end - $var wire 8 i" unpacked_array(0) [7:0] $end + $var wire 8 p" unpacked_array(-1) [7:0] $end + $var wire 8 o" unpacked_array(-2) [7:0] $end + $var wire 8 q" unpacked_array(0) [7:0] $end $var real 64 E! v_arr_real(0) $end $var real 64 G! v_arr_real(1) $end $var wire 2 [ v_arrp [2:1] $end $var wire 4 c v_arrp_arrp [3:0] $end $var wire 4 k v_arrp_strp [3:0] $end - $var wire 1 7" v_arru(1) $end - $var wire 1 8" v_arru(2) $end + $var wire 1 ?" v_arru(1) $end + $var wire 1 @" v_arru(2) $end $var wire 2 s v_arru_arrp(3) [2:1] $end $var wire 2 t v_arru_arrp(4) [2:1] $end - $var wire 1 G" v_arru_arru(3)(1) $end - $var wire 1 O" v_arru_arru(3)(2) $end - $var wire 1 W" v_arru_arru(4)(1) $end - $var wire 1 _" v_arru_arru(4)(2) $end + $var wire 1 O" v_arru_arru(3)(1) $end + $var wire 1 W" v_arru_arru(3)(2) $end + $var wire 1 _" v_arru_arru(4)(1) $end + $var wire 1 g" v_arru_arru(4)(2) $end $var wire 2 %! v_arru_strp(3) [1:0] $end $var wire 2 -! v_arru_strp(4) [1:0] $end $var wire 3 u! v_enumb [2:0] $end + $var wire 6 }! v_enumb2_str [5:0] $end $var wire 32 e! v_enumed [31:0] $end $var wire 32 m! v_enumed2 [31:0] $end $var real 64 5! v_real $end @@ -38,15 +39,15 @@ $timescale 1ns $end $var wire 4 K v_strp_strp [3:0] $end $var wire 2 S v_unip_strp [1:0] $end $scope module p2 $end - $var wire 32 !# PARAM [31:0] $end - $upscope $end - $scope module p3 $end $var wire 32 )# PARAM [31:0] $end $upscope $end + $scope module p3 $end + $var wire 32 1# PARAM [31:0] $end + $upscope $end $scope module unnamedblk1 $end - $var wire 32 }! b [31:0] $end + $var wire 32 '" b [31:0] $end $scope module unnamedblk2 $end - $var wire 32 '" a [31:0] $end + $var wire 32 /" a [31:0] $end $upscope $end $upscope $end $upscope $end @@ -74,20 +75,21 @@ r0 G! b00000000000000000000000000000000 e! b00000000000000000000000000000000 m! b000 u! -b00000000000000000000000000000000 }! +b000000 }! b00000000000000000000000000000000 '" -0/" +b00000000000000000000000000000000 /" 07" -08" -0G" +0?" +0@" 0O" 0W" 0_" -b00000000 g" -b00000000 h" -b00000000 i" -b00000000000000000000000000000010 !# -b00000000000000000000000000000011 )# +0g" +b00000000 o" +b00000000 p" +b00000000 q" +b00000000000000000000000000000010 )# +b00000000000000000000000000000011 1# #10 b00000000000000000000000000000001 + b0000000000000000000000000000000100000000000000000000000011111110 3 @@ -107,11 +109,11 @@ r0.3 G! b00000000000000000000000000000001 e! b00000000000000000000000000000010 m! b111 u! -b00000000000000000000000000000101 }! b00000000000000000000000000000101 '" -1/" +b00000000000000000000000000000101 /" +17" #15 -0/" +07" #20 b00000000000000000000000000000010 + b0000000000000000000000000000001000000000000000000000000011111101 3 @@ -131,9 +133,10 @@ r0.6 G! b00000000000000000000000000000010 e! b00000000000000000000000000000100 m! b110 u! -1/" +b111111 }! +17" #25 -0/" +07" #30 b00000000000000000000000000000011 + b0000000000000000000000000000001100000000000000000000000011111100 3 @@ -153,9 +156,10 @@ r0.8999999999999999 G! b00000000000000000000000000000011 e! b00000000000000000000000000000110 m! b101 u! -1/" +b110110 }! +17" #35 -0/" +07" #40 b00000000000000000000000000000100 + b0000000000000000000000000000010000000000000000000000000011111011 3 @@ -175,9 +179,10 @@ r1.2 G! b00000000000000000000000000000100 e! b00000000000000000000000000001000 m! b100 u! -1/" +b101101 }! +17" #45 -0/" +07" #50 b00000000000000000000000000000101 + b0000000000000000000000000000010100000000000000000000000011111010 3 @@ -197,9 +202,10 @@ r1.5 G! b00000000000000000000000000000101 e! b00000000000000000000000000001010 m! b011 u! -1/" +b100100 }! +17" #55 -0/" +07" #60 b00000000000000000000000000000110 + b0000000000000000000000000000011000000000000000000000000011111001 3 @@ -219,4 +225,5 @@ r1.8 G! b00000000000000000000000000000110 e! b00000000000000000000000000001100 m! b010 u! -1/" +b011011 }! +17" diff --git a/test_regress/t/t_trace_complex.v b/test_regress/t/t_trace_complex.v index 803148e86..bf8e184ea 100644 --- a/test_regress/t/t_trace_complex.v +++ b/test_regress/t/t_trace_complex.v @@ -64,6 +64,11 @@ module t (clk); enumed_t v_enumed2; typedef enum logic [2:0] { BZERO=0, BONE, BTWO, BTHREE } enumb_t; enumb_t v_enumb; + typedef struct packed { + enumb_t a; + enumb_t b; + } enumb2_str_t; + enumb2_str_t v_enumb2_str; logic [7:0] unpacked_array[-2:0]; @@ -85,6 +90,7 @@ module t (clk); v_enumed <= v_enumed + 1; v_enumed2 <= v_enumed2 + 2; v_enumb <= v_enumb - 1; + v_enumb2_str <= {v_enumb, v_enumb}; for (integer b=3; b<=4; b++) begin v_arru[b] <= ~v_arru[b]; v_arru_strp[b] <= ~v_arru_strp[b]; diff --git a/test_regress/t/t_trace_complex_fst.out b/test_regress/t/t_trace_complex_fst.out index 09140eaf7..57e86c1b7 100644 --- a/test_regress/t/t_trace_complex_fst.out +++ b/test_regress/t/t_trace_complex_fst.out @@ -1,5 +1,5 @@ $date - Wed Jan 8 07:26:16 2020 + Tue Jan 21 18:08:49 2020 $end $version @@ -41,24 +41,25 @@ $var logic 32 8 v_enumed2 $end $attrbegin misc 07 t.enumb_t 4 BZERO BONE BTWO BTHREE 000 001 010 011 2 $end $attrbegin misc 07 "" 2 $end $var logic 3 9 v_enumb $end -$var logic 8 : unpacked_array(-2) $end -$var logic 8 ; unpacked_array(-1) $end -$var logic 8 < unpacked_array(0) $end +$var logic 6 : v_enumb2_str $end +$var logic 8 ; unpacked_array(-2) $end +$var logic 8 < unpacked_array(-1) $end +$var logic 8 = unpacked_array(0) $end $scope module unnamedblk1 $end -$var integer 32 = b $end +$var integer 32 > b $end $scope module unnamedblk2 $end -$var integer 32 > a $end +$var integer 32 ? a $end $upscope $end $upscope $end $scope module p2 $end -$var parameter 32 ? PARAM $end +$var parameter 32 @ PARAM $end $upscope $end $scope module p3 $end -$var parameter 32 @ PARAM $end +$var parameter 32 A PARAM $end $upscope $end $upscope $end $scope module $unit $end -$var bit 1 A global_bit $end +$var bit 1 B global_bit $end $upscope $end $upscope $end $enddefinitions $end @@ -88,17 +89,19 @@ b0000000000000000000000000000000000000000000000000000000011111111 6 b00000000000000000000000000000000 7 b00000000000000000000000000000000 8 b000 9 -b00000000 : +b000000 : b00000000 ; b00000000 < -b00000000000000000000000000000000 = +b00000000 = b00000000000000000000000000000000 > -b00000000000000000000000000000010 ? -b00000000000000000000000000000011 @ -1A +b00000000000000000000000000000000 ? +b00000000000000000000000000000010 @ +b00000000000000000000000000000011 A +1B #10 +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b000000 : b111 9 b00000000000000000000000000000010 8 b00000000000000000000000000000001 7 @@ -140,14 +143,16 @@ b0000000000000000000000000000001000000000000000000000000011111101 6 b00000000000000000000000000000010 7 b00000000000000000000000000000100 8 b110 9 -b00000000000000000000000000000101 = +b111111 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? #25 0! #30 1! +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b110110 : b101 9 b00000000000000000000000000000110 8 b00000000000000000000000000000011 7 @@ -188,14 +193,16 @@ b0000000000000000000000000000010000000000000000000000000011111011 6 b00000000000000000000000000000100 7 b00000000000000000000000000001000 8 b100 9 -b00000000000000000000000000000101 = +b101101 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? #45 0! #50 1! +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b100100 : b011 9 b00000000000000000000000000001010 8 b00000000000000000000000000000101 7 @@ -236,5 +243,6 @@ b0000000000000000000000000000011000000000000000000000000011111001 6 b00000000000000000000000000000110 7 b00000000000000000000000000001100 8 b010 9 -b00000000000000000000000000000101 = +b011011 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? diff --git a/test_regress/t/t_trace_complex_params.out b/test_regress/t/t_trace_complex_params.out index ca5eeb36d..aacfd2769 100644 --- a/test_regress/t/t_trace_complex_params.out +++ b/test_regress/t/t_trace_complex_params.out @@ -1,35 +1,36 @@ $version Generated by VerilatedVcd $end -$date Wed Jan 8 07:26:16 2020 +$date Tue Jan 21 18:15:28 2020 $end $timescale 1ns $end $scope module top $end - $var wire 1 /" clk $end + $var wire 1 7" clk $end $scope module $unit $end $var wire 1 # global_bit $end $upscope $end $scope module t $end - $var wire 1 /" clk $end + $var wire 1 7" clk $end $var wire 32 + cyc [31:0] $end - $var wire 8 h" unpacked_array(-1) [7:0] $end - $var wire 8 g" unpacked_array(-2) [7:0] $end - $var wire 8 i" unpacked_array(0) [7:0] $end + $var wire 8 p" unpacked_array(-1) [7:0] $end + $var wire 8 o" unpacked_array(-2) [7:0] $end + $var wire 8 q" unpacked_array(0) [7:0] $end $var real 64 E! v_arr_real(0) $end $var real 64 G! v_arr_real(1) $end $var wire 2 [ v_arrp [2:1] $end $var wire 4 c v_arrp_arrp [3:0] $end $var wire 4 k v_arrp_strp [3:0] $end - $var wire 1 7" v_arru(1) $end - $var wire 1 8" v_arru(2) $end + $var wire 1 ?" v_arru(1) $end + $var wire 1 @" v_arru(2) $end $var wire 2 s v_arru_arrp(3) [2:1] $end $var wire 2 t v_arru_arrp(4) [2:1] $end - $var wire 1 G" v_arru_arru(3)(1) $end - $var wire 1 O" v_arru_arru(3)(2) $end - $var wire 1 W" v_arru_arru(4)(1) $end - $var wire 1 _" v_arru_arru(4)(2) $end + $var wire 1 O" v_arru_arru(3)(1) $end + $var wire 1 W" v_arru_arru(3)(2) $end + $var wire 1 _" v_arru_arru(4)(1) $end + $var wire 1 g" v_arru_arru(4)(2) $end $var wire 2 %! v_arru_strp(3) [1:0] $end $var wire 2 -! v_arru_strp(4) [1:0] $end $var wire 3 u! v_enumb [2:0] $end + $var wire 6 }! v_enumb2_str [5:0] $end $var wire 32 e! v_enumed [31:0] $end $var wire 32 m! v_enumed2 [31:0] $end $var real 64 5! v_real $end @@ -38,15 +39,15 @@ $timescale 1ns $end $var wire 4 K v_strp_strp [3:0] $end $var wire 2 S v_unip_strp [1:0] $end $scope module p2 $end - $var wire 32 !# PARAM [31:0] $end - $upscope $end - $scope module p3 $end $var wire 32 )# PARAM [31:0] $end $upscope $end + $scope module p3 $end + $var wire 32 1# PARAM [31:0] $end + $upscope $end $scope module unnamedblk1 $end - $var wire 32 }! b [31:0] $end + $var wire 32 '" b [31:0] $end $scope module unnamedblk2 $end - $var wire 32 '" a [31:0] $end + $var wire 32 /" a [31:0] $end $upscope $end $upscope $end $upscope $end @@ -74,20 +75,21 @@ r0 G! b00000000000000000000000000000000 e! b00000000000000000000000000000000 m! b000 u! -b00000000000000000000000000000000 }! +b000000 }! b00000000000000000000000000000000 '" -0/" +b00000000000000000000000000000000 /" 07" -08" -0G" +0?" +0@" 0O" 0W" 0_" -b00000000 g" -b00000000 h" -b00000000 i" -b00000000000000000000000000000010 !# -b00000000000000000000000000000011 )# +0g" +b00000000 o" +b00000000 p" +b00000000 q" +b00000000000000000000000000000010 )# +b00000000000000000000000000000011 1# #10 b00000000000000000000000000000001 + b0000000000000000000000000000000100000000000000000000000011111110 3 @@ -107,11 +109,11 @@ r0.3 G! b00000000000000000000000000000001 e! b00000000000000000000000000000010 m! b111 u! -b00000000000000000000000000000101 }! b00000000000000000000000000000101 '" -1/" +b00000000000000000000000000000101 /" +17" #15 -0/" +07" #20 b00000000000000000000000000000010 + b0000000000000000000000000000001000000000000000000000000011111101 3 @@ -131,9 +133,10 @@ r0.6 G! b00000000000000000000000000000010 e! b00000000000000000000000000000100 m! b110 u! -1/" +b111111 }! +17" #25 -0/" +07" #30 b00000000000000000000000000000011 + b0000000000000000000000000000001100000000000000000000000011111100 3 @@ -153,9 +156,10 @@ r0.8999999999999999 G! b00000000000000000000000000000011 e! b00000000000000000000000000000110 m! b101 u! -1/" +b110110 }! +17" #35 -0/" +07" #40 b00000000000000000000000000000100 + b0000000000000000000000000000010000000000000000000000000011111011 3 @@ -175,9 +179,10 @@ r1.2 G! b00000000000000000000000000000100 e! b00000000000000000000000000001000 m! b100 u! -1/" +b101101 }! +17" #45 -0/" +07" #50 b00000000000000000000000000000101 + b0000000000000000000000000000010100000000000000000000000011111010 3 @@ -197,9 +202,10 @@ r1.5 G! b00000000000000000000000000000101 e! b00000000000000000000000000001010 m! b011 u! -1/" +b100100 }! +17" #55 -0/" +07" #60 b00000000000000000000000000000110 + b0000000000000000000000000000011000000000000000000000000011111001 3 @@ -219,4 +225,5 @@ r1.8 G! b00000000000000000000000000000110 e! b00000000000000000000000000001100 m! b010 u! -1/" +b011011 }! +17" diff --git a/test_regress/t/t_trace_complex_params_fst.out b/test_regress/t/t_trace_complex_params_fst.out index 366add463..1dc90cb57 100644 --- a/test_regress/t/t_trace_complex_params_fst.out +++ b/test_regress/t/t_trace_complex_params_fst.out @@ -1,5 +1,5 @@ $date - Wed Jan 8 07:26:17 2020 + Tue Jan 21 18:15:28 2020 $end $version @@ -41,24 +41,25 @@ $var logic 32 8 v_enumed2 $end $attrbegin misc 07 t.enumb_t 4 BZERO BONE BTWO BTHREE 000 001 010 011 2 $end $attrbegin misc 07 "" 2 $end $var logic 3 9 v_enumb $end -$var logic 8 : unpacked_array(-2) $end -$var logic 8 ; unpacked_array(-1) $end -$var logic 8 < unpacked_array(0) $end +$var logic 6 : v_enumb2_str $end +$var logic 8 ; unpacked_array(-2) $end +$var logic 8 < unpacked_array(-1) $end +$var logic 8 = unpacked_array(0) $end $scope module unnamedblk1 $end -$var integer 32 = b $end +$var integer 32 > b $end $scope module unnamedblk2 $end -$var integer 32 > a $end +$var integer 32 ? a $end $upscope $end $upscope $end $scope module p2 $end -$var parameter 32 ? PARAM $end +$var parameter 32 @ PARAM $end $upscope $end $scope module p3 $end -$var parameter 32 @ PARAM $end +$var parameter 32 A PARAM $end $upscope $end $upscope $end $scope module $unit $end -$var bit 1 A global_bit $end +$var bit 1 B global_bit $end $upscope $end $upscope $end $enddefinitions $end @@ -88,17 +89,19 @@ b0000000000000000000000000000000000000000000000000000000011111111 6 b00000000000000000000000000000000 7 b00000000000000000000000000000000 8 b000 9 -b00000000 : +b000000 : b00000000 ; b00000000 < -b00000000000000000000000000000000 = +b00000000 = b00000000000000000000000000000000 > -b00000000000000000000000000000010 ? -b00000000000000000000000000000011 @ -1A +b00000000000000000000000000000000 ? +b00000000000000000000000000000010 @ +b00000000000000000000000000000011 A +1B #10 +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b000000 : b111 9 b00000000000000000000000000000010 8 b00000000000000000000000000000001 7 @@ -140,14 +143,16 @@ b0000000000000000000000000000001000000000000000000000000011111101 6 b00000000000000000000000000000010 7 b00000000000000000000000000000100 8 b110 9 -b00000000000000000000000000000101 = +b111111 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? #25 0! #30 1! +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b110110 : b101 9 b00000000000000000000000000000110 8 b00000000000000000000000000000011 7 @@ -188,14 +193,16 @@ b0000000000000000000000000000010000000000000000000000000011111011 6 b00000000000000000000000000000100 7 b00000000000000000000000000001000 8 b100 9 -b00000000000000000000000000000101 = +b101101 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? #45 0! #50 1! +b00000000000000000000000000000101 ? b00000000000000000000000000000101 > -b00000000000000000000000000000101 = +b100100 : b011 9 b00000000000000000000000000001010 8 b00000000000000000000000000000101 7 @@ -236,5 +243,6 @@ b0000000000000000000000000000011000000000000000000000000011111001 6 b00000000000000000000000000000110 7 b00000000000000000000000000001100 8 b010 9 -b00000000000000000000000000000101 = +b011011 : b00000000000000000000000000000101 > +b00000000000000000000000000000101 ? diff --git a/test_regress/t/t_trace_complex_structs.out b/test_regress/t/t_trace_complex_structs.out index ba955aa5e..3344bd9e1 100644 --- a/test_regress/t/t_trace_complex_structs.out +++ b/test_regress/t/t_trace_complex_structs.out @@ -1,40 +1,40 @@ $version Generated by VerilatedVcd $end -$date Wed Jan 8 07:26:19 2020 +$date Tue Jan 21 18:55:13 2020 $end $timescale 1ns $end $scope module top $end - $var wire 1 )# clk $end + $var wire 1 9# clk $end $scope module $unit $end $var wire 1 # global_bit $end $upscope $end $scope module t $end - $var wire 1 )# clk $end + $var wire 1 9# clk $end $var wire 32 + cyc [31:0] $end - $var wire 8 b# unpacked_array(-1) [7:0] $end - $var wire 8 a# unpacked_array(-2) [7:0] $end - $var wire 8 c# unpacked_array(0) [7:0] $end + $var wire 8 r# unpacked_array(-1) [7:0] $end + $var wire 8 q# unpacked_array(-2) [7:0] $end + $var wire 8 s# unpacked_array(0) [7:0] $end $var real 64 ?" v_arr_real(0) $end $var real 64 A" v_arr_real(1) $end $var wire 2 %! v_arrp [2:1] $end - $var wire 2 -! v_arrp_arrp(3) [1:0] $end - $var wire 2 5! v_arrp_arrp(4) [1:0] $end - $var wire 1 1# v_arru(1) $end - $var wire 1 2# v_arru(2) $end + $var wire 2 -! v_arrp_arrp(3) [2:1] $end + $var wire 2 5! v_arrp_arrp(4) [2:1] $end + $var wire 1 A# v_arru(1) $end + $var wire 1 B# v_arru(2) $end $var wire 2 ]! v_arru_arrp(3) [2:1] $end $var wire 2 ^! v_arru_arrp(4) [2:1] $end - $var wire 1 A# v_arru_arru(3)(1) $end - $var wire 1 I# v_arru_arru(3)(2) $end - $var wire 1 Q# v_arru_arru(4)(1) $end - $var wire 1 Y# v_arru_arru(4)(2) $end + $var wire 1 Q# v_arru_arru(3)(1) $end + $var wire 1 Y# v_arru_arru(3)(2) $end + $var wire 1 a# v_arru_arru(4)(1) $end + $var wire 1 i# v_arru_arru(4)(2) $end $var wire 3 o" v_enumb [2:0] $end $var wire 32 _" v_enumed [31:0] $end $var wire 32 g" v_enumed2 [31:0] $end $var real 64 /" v_real $end $scope module unnamedblk1 $end - $var wire 32 w" b [31:0] $end + $var wire 32 )# b [31:0] $end $scope module unnamedblk2 $end - $var wire 32 !# a [31:0] $end + $var wire 32 1# a [31:0] $end $upscope $end $upscope $end $scope module v_arrp_strp(3) $end @@ -53,6 +53,10 @@ $timescale 1ns $end $var wire 1 '" b0 $end $var wire 1 }! b1 $end $upscope $end + $scope module v_enumb2_str $end + $var wire 3 w" a [2:0] $end + $var wire 3 !# b [2:0] $end + $upscope $end $scope module v_str32x2(0) $end $var wire 32 3 data [31:0] $end $upscope $end @@ -120,18 +124,20 @@ r0 A" b00000000000000000000000000000000 _" b00000000000000000000000000000000 g" b000 o" -b00000000000000000000000000000000 w" -b00000000000000000000000000000000 !# -0)# -01# -02# +b000 w" +b000 !# +b00000000000000000000000000000000 )# +b00000000000000000000000000000000 1# +09# 0A# -0I# +0B# 0Q# 0Y# -b00000000 a# -b00000000 b# -b00000000 c# +0a# +0i# +b00000000 q# +b00000000 r# +b00000000 s# #10 b00000000000000000000000000000001 + b00000000000000000000000011111110 3 @@ -163,11 +169,11 @@ r0.3 A" b00000000000000000000000000000001 _" b00000000000000000000000000000010 g" b111 o" -b00000000000000000000000000000101 w" -b00000000000000000000000000000101 !# -1)# +b00000000000000000000000000000101 )# +b00000000000000000000000000000101 1# +19# #15 -0)# +09# #20 b00000000000000000000000000000010 + b00000000000000000000000011111101 3 @@ -199,9 +205,11 @@ r0.6 A" b00000000000000000000000000000010 _" b00000000000000000000000000000100 g" b110 o" -1)# +b111 w" +b111 !# +19# #25 -0)# +09# #30 b00000000000000000000000000000011 + b00000000000000000000000011111100 3 @@ -233,9 +241,11 @@ r0.8999999999999999 A" b00000000000000000000000000000011 _" b00000000000000000000000000000110 g" b101 o" -1)# +b110 w" +b110 !# +19# #35 -0)# +09# #40 b00000000000000000000000000000100 + b00000000000000000000000011111011 3 @@ -267,9 +277,11 @@ r1.2 A" b00000000000000000000000000000100 _" b00000000000000000000000000001000 g" b100 o" -1)# +b101 w" +b101 !# +19# #45 -0)# +09# #50 b00000000000000000000000000000101 + b00000000000000000000000011111010 3 @@ -301,9 +313,11 @@ r1.5 A" b00000000000000000000000000000101 _" b00000000000000000000000000001010 g" b011 o" -1)# +b100 w" +b100 !# +19# #55 -0)# +09# #60 b00000000000000000000000000000110 + b00000000000000000000000011111001 3 @@ -335,4 +349,6 @@ r1.8 A" b00000000000000000000000000000110 _" b00000000000000000000000000001100 g" b010 o" -1)# +b011 w" +b011 !# +19# diff --git a/test_regress/t/t_trace_complex_structs_fst.out b/test_regress/t/t_trace_complex_structs_fst.out index a3e68df29..fd26fc14c 100644 --- a/test_regress/t/t_trace_complex_structs_fst.out +++ b/test_regress/t/t_trace_complex_structs_fst.out @@ -1,5 +1,5 @@ $date - Wed Jan 8 07:26:20 2020 + Tue Jan 21 18:55:14 2020 $end $version @@ -81,18 +81,24 @@ $var logic 32 D v_enumed2 $end $attrbegin misc 07 t.enumb_t 4 BZERO BONE BTWO BTHREE 000 001 010 011 2 $end $attrbegin misc 07 "" 2 $end $var logic 3 E v_enumb $end -$var logic 8 F unpacked_array(-2) $end -$var logic 8 G unpacked_array(-1) $end -$var logic 8 H unpacked_array(0) $end +$scope module v_enumb2_str $end +$attrbegin misc 07 "" 2 $end +$var logic 3 F a $end +$attrbegin misc 07 "" 2 $end +$var logic 3 G b $end +$upscope $end +$var logic 8 H unpacked_array(-2) $end +$var logic 8 I unpacked_array(-1) $end +$var logic 8 J unpacked_array(0) $end $scope module unnamedblk1 $end -$var integer 32 I b $end +$var integer 32 K b $end $scope module unnamedblk2 $end -$var integer 32 J a $end +$var integer 32 L a $end $upscope $end $upscope $end $upscope $end $scope module $unit $end -$var bit 1 K global_bit $end +$var bit 1 M global_bit $end $upscope $end $upscope $end $enddefinitions $end @@ -134,15 +140,19 @@ b00000000000000000000000000000000 B b00000000000000000000000000000000 C b00000000000000000000000000000000 D b000 E -b00000000 F -b00000000 G +b000 F +b000 G b00000000 H -b00000000000000000000000000000000 I -b00000000000000000000000000000000 J -1K +b00000000 I +b00000000 J +b00000000000000000000000000000000 K +b00000000000000000000000000000000 L +1M #10 -b00000000000000000000000000000101 J -b00000000000000000000000000000101 I +b00000000000000000000000000000101 L +b00000000000000000000000000000101 K +b000 G +b000 F b111 E b00000000000000000000000000000010 D b00000000000000000000000000000001 C @@ -208,14 +218,18 @@ b00000000000000000000000000000010 B b00000000000000000000000000000010 C b00000000000000000000000000000100 D b110 E -b00000000000000000000000000000101 I -b00000000000000000000000000000101 J +b111 F +b111 G +b00000000000000000000000000000101 K +b00000000000000000000000000000101 L #25 0! #30 1! -b00000000000000000000000000000101 J -b00000000000000000000000000000101 I +b00000000000000000000000000000101 L +b00000000000000000000000000000101 K +b110 G +b110 F b101 E b00000000000000000000000000000110 D b00000000000000000000000000000011 C @@ -280,14 +294,18 @@ b00000000000000000000000000000100 B b00000000000000000000000000000100 C b00000000000000000000000000001000 D b100 E -b00000000000000000000000000000101 I -b00000000000000000000000000000101 J +b101 F +b101 G +b00000000000000000000000000000101 K +b00000000000000000000000000000101 L #45 0! #50 1! -b00000000000000000000000000000101 J -b00000000000000000000000000000101 I +b00000000000000000000000000000101 L +b00000000000000000000000000000101 K +b100 G +b100 F b011 E b00000000000000000000000000001010 D b00000000000000000000000000000101 C @@ -352,5 +370,7 @@ b00000000000000000000000000000110 B b00000000000000000000000000000110 C b00000000000000000000000000001100 D b010 E -b00000000000000000000000000000101 I -b00000000000000000000000000000101 J +b011 F +b011 G +b00000000000000000000000000000101 K +b00000000000000000000000000000101 L diff --git a/test_regress/t/t_trace_public_sig_vlt.pl b/test_regress/t/t_trace_public_sig_vlt.pl index 68c888339..e8140045a 100755 --- a/test_regress/t/t_trace_public_sig_vlt.pl +++ b/test_regress/t/t_trace_public_sig_vlt.pl @@ -19,7 +19,7 @@ compile( ); if ($Self->{vlt_all}) { - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_type.pl b/test_regress/t/t_type.pl new file mode 100755 index 000000000..b1acebe26 --- /dev/null +++ b/test_regress/t/t_type.pl @@ -0,0 +1,20 @@ +#!/usr/bin/perl +if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; } +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2004 by Wilson Snyder. This program is free software; you can +# redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. + +scenarios(simulator => 1); + +compile( + ); + +execute( + check_finished => 1, + ); + +ok(1); +1; diff --git a/test_regress/t/t_type.v b/test_regress/t/t_type.v new file mode 100644 index 000000000..f0f0e029f --- /dev/null +++ b/test_regress/t/t_type.v @@ -0,0 +1,21 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2020 by Wilson Snyder. + +module t(/*AUTOARG*/); + + real x; + real y; + var type(x+y) z; + + initial begin + x = 1.2; + y = 2.3; + z = x + y; + if (z != (1.2+2.3)) $stop; + $write("*-* All Finished *-*\n"); + $finish; + end + +endmodule diff --git a/test_regress/t/t_typename.pl b/test_regress/t/t_typename.pl new file mode 100755 index 000000000..b1acebe26 --- /dev/null +++ b/test_regress/t/t_typename.pl @@ -0,0 +1,20 @@ +#!/usr/bin/perl +if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; } +# DESCRIPTION: Verilator: Verilog Test driver/expect definition +# +# Copyright 2004 by Wilson Snyder. This program is free software; you can +# redistribute it and/or modify it under the terms of either the GNU +# Lesser General Public License Version 3 or the Perl Artistic License +# Version 2.0. + +scenarios(simulator => 1); + +compile( + ); + +execute( + check_finished => 1, + ); + +ok(1); +1; diff --git a/test_regress/t/t_typename.v b/test_regress/t/t_typename.v new file mode 100644 index 000000000..7edda4a3a --- /dev/null +++ b/test_regress/t/t_typename.v @@ -0,0 +1,34 @@ +// DESCRIPTION: Verilator: Verilog Test module +// +// This file ONLY is placed into the Public Domain, for any use, +// without warranty, 2020 by Wilson Snyder. + +`define checks(gotv,expv) do if ((gotv) != (expv)) begin $write("%%Error: %s:%0d: got='%s' exp='%s'\n", `__FILE__,`__LINE__, (gotv), (expv)); $stop; end while(0); + +module t(/*AUTOARG*/); + + real r; + logic l; + typedef bit mybit_t; + mybit_t [2:0] bitp20; + mybit_t bitu32 [3:2]; + mybit_t bitu31 [3:1][4:5]; + + initial begin + `checks($typename(real), "real"); + `checks($typename(bit), "bit"); + `checks($typename(int), "int"); + `checks($typename(logic), "logic"); + `checks($typename(string), "string"); + + `checks($typename(r), "real"); + `checks($typename(l), "logic"); + `checks($typename(mybit_t), "bit"); + `checks($typename(bitp20), "bit[2:0]"); + `checks($typename(bitu32), "bit$[3:2]"); + `checks($typename(bitu31), "bit$[3:1][4:5]"); + $write("*-* All Finished *-*\n"); + $finish; + end + +endmodule diff --git a/test_regress/t/t_unopt_combo_isolate.pl b/test_regress/t/t_unopt_combo_isolate.pl index d43183607..874c44f07 100755 --- a/test_regress/t/t_unopt_combo_isolate.pl +++ b/test_regress/t/t_unopt_combo_isolate.pl @@ -18,11 +18,11 @@ compile( if ($Self->{vlt_all}) { file_grep($Self->{stats}, qr/Optimizations, isolate_assignments blocks\s+5/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_unopt_combo_isolate_vlt.pl b/test_regress/t/t_unopt_combo_isolate_vlt.pl index 855ac8b0e..25cf700f7 100755 --- a/test_regress/t/t_unopt_combo_isolate_vlt.pl +++ b/test_regress/t/t_unopt_combo_isolate_vlt.pl @@ -18,11 +18,11 @@ compile( if ($Self->{vlt_all}) { file_grep($Self->{stats}, qr/Optimizations, isolate_assignments blocks\s+5/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); - file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); + file_grep("$out_filename", qr/\/i); } execute( diff --git a/test_regress/t/t_unpacked_concat_bad.out b/test_regress/t/t_unpacked_concat_bad.out index a1f4b32d9..53dcbfdee 100644 --- a/test_regress/t/t_unpacked_concat_bad.out +++ b/test_regress/t/t_unpacked_concat_bad.out @@ -1,4 +1,4 @@ -%Error: t/t_unpacked_concat_bad.v:16: Unsupported: Replication to form UNPACKARRAYDTYPE +%Error: t/t_unpacked_concat_bad.v:16: Unsupported: Replication to form 'bit[31:0]$[1:0]' data type : ... In instance t localparam bit_int_t count_bits [1:0] = {2{$bits(count_t)}}; ^ @@ -7,7 +7,7 @@ localparam bit_int_t count_bits [1:0] = {2{$bits(count_t)}}; ^~~~~ ... Use "/* verilator lint_off WIDTHCONCAT */" and lint_on around source to disable this message. -%Error: t/t_unpacked_concat_bad.v:17: Unsupported: Replication to form UNPACKARRAYDTYPE +%Error: t/t_unpacked_concat_bad.v:17: Unsupported: Replication to form 'bit[31:0]$[1:0]' data type : ... In instance t localparam bit_int_t count_bitsc [1:0] = {$bits(count_t), $bits(count_t)}; ^ diff --git a/test_regress/t/t_unroll_signed.v b/test_regress/t/t_unroll_signed.v index 45f99561c..38f287b80 100644 --- a/test_regress/t/t_unroll_signed.v +++ b/test_regress/t/t_unroll_signed.v @@ -27,7 +27,7 @@ module t (/*AUTOARG*/ integer i; reg [31:0] iu; - reg [31:0] dly_to_insure_was_unrolled [1:0]; + reg [31:0] dly_to_ensure_was_unrolled [1:0]; reg [2:0] i3; integer cyc; initial cyc=0; @@ -39,7 +39,7 @@ module t (/*AUTOARG*/ total = 0; for (i=5; i>=0; i=i-1) begin total = total - i -1; - dly_to_insure_was_unrolled[i] <= i; + dly_to_ensure_was_unrolled[i] <= i; end if (total != -21) $stop; end @@ -48,7 +48,7 @@ module t (/*AUTOARG*/ total = 0; for (i=5; i>0; i=i-1) begin total = total - i -1; - dly_to_insure_was_unrolled[i] <= i; + dly_to_ensure_was_unrolled[i] <= i; end if (total != -20) $stop; end @@ -57,7 +57,7 @@ module t (/*AUTOARG*/ total = 0; for (i=1; i<5; i=i+1) begin total = total - i -1; - dly_to_insure_was_unrolled[i] <= i; + dly_to_ensure_was_unrolled[i] <= i; end if (total != -14) $stop; end @@ -66,7 +66,7 @@ module t (/*AUTOARG*/ total = 0; for (i=1; i<=5; i=i+1) begin total = total - i -1; - dly_to_insure_was_unrolled[i] <= i; + dly_to_ensure_was_unrolled[i] <= i; end if (total != -20) $stop; end @@ -76,7 +76,7 @@ module t (/*AUTOARG*/ total = 0; for (iu=5; iu>=1; iu=iu-1) begin total = total - iu -1; - dly_to_insure_was_unrolled[iu] <= iu; + dly_to_ensure_was_unrolled[iu] <= iu; end if (total != -20) $stop; end @@ -85,7 +85,7 @@ module t (/*AUTOARG*/ total = 0; for (iu=5; iu>1; iu=iu-1) begin total = total - iu -1; - dly_to_insure_was_unrolled[iu] <= iu; + dly_to_ensure_was_unrolled[iu] <= iu; end if (total != -18) $stop; end @@ -94,7 +94,7 @@ module t (/*AUTOARG*/ total = 0; for (iu=1; iu<5; iu=iu+1) begin total = total - iu -1; - dly_to_insure_was_unrolled[iu] <= iu; + dly_to_ensure_was_unrolled[iu] <= iu; end if (total != -14) $stop; end @@ -103,7 +103,7 @@ module t (/*AUTOARG*/ total = 0; for (iu=1; iu<=5; iu=iu+1) begin total = total - iu -1; - dly_to_insure_was_unrolled[iu] <= iu; + dly_to_ensure_was_unrolled[iu] <= iu; end if (total != -20) $stop; end @@ -113,7 +113,7 @@ module t (/*AUTOARG*/ total = 0; for (i3=3'd0; i3<3'd7; i3=i3+3'd1) begin total = total - {29'd0,i3} -1; - dly_to_insure_was_unrolled[i3[0]] <= 0; + dly_to_ensure_was_unrolled[i3[0]] <= 0; end if (total != -28) $stop; end @@ -123,7 +123,7 @@ module t (/*AUTOARG*/ total = 0; for (i3=0; i3<3'd7; i3=i3+3'd1) begin total = total - {29'd0,i3} -1; - dly_to_insure_was_unrolled[i3[0]] <= 0; + dly_to_ensure_was_unrolled[i3[0]] <= 0; end if (total != -28) $stop; end @@ -133,7 +133,7 @@ module t (/*AUTOARG*/ total = 0; for (i3=3'd0; i3<7; i3=i3+1) begin total = total - {29'd0,i3} -1; - dly_to_insure_was_unrolled[i3[0]] <= 0; + dly_to_ensure_was_unrolled[i3[0]] <= 0; end if (total != -28) $stop; end diff --git a/test_regress/t/t_var_local.v b/test_regress/t/t_var_local.v index 543bf1a8d..4128e7912 100644 --- a/test_regress/t/t_var_local.v +++ b/test_regress/t/t_var_local.v @@ -43,7 +43,7 @@ module t; end end tsk; - tsk; // Second time to insure we reinit the initial value + tsk; // Second time to ensure we reinit the initial value $write("*-* All Finished *-*\n"); $finish; end diff --git a/test_regress/t/t_var_ref_bad1.out b/test_regress/t/t_var_ref_bad1.out index 09c425e98..32bece252 100644 --- a/test_regress/t/t_var_ref_bad1.out +++ b/test_regress/t/t_var_ref_bad1.out @@ -1,4 +1,4 @@ -%Error: t/t_var_ref_bad1.v:13: Ref connection 'bad_sub_ref' requires matching types; ref requires BASICDTYPE 'real' but connection is BASICDTYPE 'bit'. +%Error: t/t_var_ref_bad1.v:13: Ref connection 'bad_sub_ref' requires matching types; ref requires 'real' data type but connection is 'bit' data type. : ... In instance t (.bad_sub_ref(bad_parent)); ^~~~~~~~~~~ diff --git a/test_regress/t/t_var_types_bad.out b/test_regress/t/t_var_types_bad.out index 8bb622363..9dbd0471d 100644 --- a/test_regress/t/t_var_types_bad.out +++ b/test_regress/t/t_var_types_bad.out @@ -1,16 +1,16 @@ -%Error: t/t_var_types_bad.v:38: Illegal bit or array select; type does not have a bit range, or bad dimension: type is bit +%Error: t/t_var_types_bad.v:38: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'bit' : ... In instance t d_bitz[0] = 1'b1; ^ -%Error: t/t_var_types_bad.v:39: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_var_types_bad.v:39: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t d_logicz[0] = 1'b1; ^ -%Error: t/t_var_types_bad.v:40: Illegal bit or array select; type does not have a bit range, or bad dimension: type is logic +%Error: t/t_var_types_bad.v:40: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'logic' : ... In instance t d_regz[0] = 1'b1; ^ -%Error: t/t_var_types_bad.v:45: Illegal bit or array select; type does not have a bit range, or bad dimension: type is real +%Error: t/t_var_types_bad.v:45: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'real' : ... In instance t d_real[0] = 1'b1; ^ @@ -22,7 +22,7 @@ d_real[0] = 1'b1; ^~~~~~ ... Use "/* verilator lint_off REALCVT */" and lint_on around source to disable this message. -%Error: t/t_var_types_bad.v:46: Illegal bit or array select; type does not have a bit range, or bad dimension: type is real +%Error: t/t_var_types_bad.v:46: Illegal bit or array select; type does not have a bit range, or bad dimension: data type is 'real' : ... In instance t d_realtime[0] = 1'b1; ^ diff --git a/test_regress/t/t_xml_first.out b/test_regress/t/t_xml_first.out index d40bc7c59..5e4edbca8 100644 --- a/test_regress/t/t_xml_first.out +++ b/test_regress/t/t_xml_first.out @@ -11,75 +11,75 @@ - - - + + + - - - - - - - - + + + + + + + + - - + + - - + + - - - + + + - - + + - - + + - - - + + + - - - - - + + + + + - - - - + + + + - - - + + + - - - - - - - + + + + + + + - - - - + + + + diff --git a/test_regress/t/t_xml_output.out b/test_regress/t/t_xml_output.out index 51ce46889..52a262c06 100644 --- a/test_regress/t/t_xml_output.out +++ b/test_regress/t/t_xml_output.out @@ -11,14 +11,14 @@ - + - - + + - - + + diff --git a/test_regress/t/t_xml_tag.out b/test_regress/t/t_xml_tag.out index 3b7dab8cd..e192a9b65 100644 --- a/test_regress/t/t_xml_tag.out +++ b/test_regress/t/t_xml_tag.out @@ -11,72 +11,72 @@ - - + + - - - - - - - - - - - - + + + + + + + + + + + + - - - - - - + + + + + + - - - - - + + + + + - - - - + + + + - - - - - - - - - + + + + + + + + + - - - - - - - - - + + + + + + + + + - - + +