diff --git a/SoCMakeConfig.cmake b/SoCMakeConfig.cmake index 639c319..8f55cda 100644 --- a/SoCMakeConfig.cmake +++ b/SoCMakeConfig.cmake @@ -35,8 +35,8 @@ include("${CMAKE_CURRENT_LIST_DIR}/cmake/sim/iverilog/iverilog.cmake") # ----- xcelium ------ include("${CMAKE_CURRENT_LIST_DIR}/cmake/sim/cadence/xcelium.cmake") -# ----- modelsim ------ -include("${CMAKE_CURRENT_LIST_DIR}/cmake/sim/modelsim/modelsim.cmake") +# ----- siemens ------ +include("${CMAKE_CURRENT_LIST_DIR}/cmake/sim/siemens/modelsim.cmake") # ----- vcs ------ include("${CMAKE_CURRENT_LIST_DIR}/cmake/sim/synopsys/vcs.cmake") diff --git a/cmake/sim/cadence/xcelium.cmake b/cmake/sim/cadence/xcelium.cmake index 5fddd99..5ef9e93 100644 --- a/cmake/sim/cadence/xcelium.cmake +++ b/cmake/sim/cadence/xcelium.cmake @@ -18,7 +18,7 @@ include_guard(GLOBAL) function(xcelium IP_LIB) - cmake_parse_arguments(ARG "GUI" "" "ARGS" ${ARGN}) + cmake_parse_arguments(ARG "TARGET_PER_IP;NO_RUN_TARGET;GUI" "RUN_TARGET_NAME" "XMVLOG_ARGS;XMVHDL_ARGS;XMELAB_ARGS;RUN_ARGS" ${ARGN}) if(ARG_UNPARSED_ARGUMENTS) message(FATAL_ERROR "${CMAKE_CURRENT_FUNCTION} passed unrecognized argument " "${ARG_UNPARSED_ARGUMENTS}") endif() @@ -28,17 +28,15 @@ function(xcelium IP_LIB) alias_dereference(IP_LIB ${IP_LIB}) get_target_property(BINARY_DIR ${IP_LIB} BINARY_DIR) - get_ip_sources(SOURCES ${IP_LIB} SYSTEMVERILOG VERILOG VHDL) - get_ip_include_directories(INC_DIRS ${IP_LIB} SYSTEMVERILOG VERILOG VHDL) + # get_target_property(LIBRARY ${IP_LIB} LIBRARY) + # if(NOT LIBRARY) + set(LIBRARY worklib) + # endif() - foreach(dir ${INC_DIRS}) - list(APPEND ARG_INCDIRS -incdir ${dir}) - endforeach() - - get_ip_compile_definitions(COMP_DEFS ${IP_LIB} SYSTEMVERILOG VERILOG VHDL) - foreach(def ${COMP_DEFS}) - list(APPEND CMP_DEFS_ARG -define ${def}) - endforeach() + if(NOT ARG_TOP_MODULE) + get_target_property(IP_NAME ${IP_LIB} IP_NAME) + set(ARG_TOP_MODULE ${IP_NAME}) + endif() get_ip_links(IPS_LIST ${IP_LIB}) @@ -50,21 +48,164 @@ function(xcelium IP_LIB) endif() endforeach() - add_custom_target( run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - COMMAND xrun - # Enable parameters without default value - -setenv CADENCE_ENABLE_AVSREQ_44905_PHASE_1=1 -setenv CADENCE_ENABLE_AVSREQ_63188_PHASE_1=1 - -define COMMON_CELLS_ASSERTS_OFF - ${SOURCES} - ${ARG_INCDIRS} - ${CMP_DEFS_ARG} + if(ARG_TARGET_PER_IP) # In case TARGET_PER_IP is passed, a compile target is created per IP block + set(list_comp_libs ${IPS_LIST}) + set(__no_deps_arg NO_DEPS) + else() + set(list_comp_libs ${IP_LIB}) + unset(__no_deps_arg) + endif() + + unset(__comp_tgts) + foreach(ip ${list_comp_libs}) + get_target_property(ip_name ${ip} IP_NAME) + if(ip_name) # If IP_NAME IS set, its SoCMake's IP_LIBRARY + __xcelium_compile_lib(${ip} ${__no_deps_arg} + # OUTDIR ${OUTDIR} + ${ARG_XMVLOG_ARGS} + ${ARG_XMVHDL_ARGS} + ${ARG_XMELAB_ARGS} + ) + list(APPEND __comp_tgts ${ip}_xcelium_complib) + endif() + endforeach() + + + ## XMSIM command for running simulation + set(__xmsim_cmd xmsim ${__lib_args} + ${ARG_RUN_ARGS} + ${LIBRARY}.${ARG_TOP_MODULE} $<$:-gui> - ${ARG_ARGS} - COMMENT "Running ${CMAKE_CURRENT_FUNCTION} on ${IP_LIB}" - DEPENDS ${SOURCES} ${IP_LIB} + + # $<$:-quiet> ) + if(NOT ARG_NO_RUN_TARGET) + if(NOT ARG_RUN_TARGET_NAME) + set(ARG_RUN_TARGET_NAME run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION}) + endif() + set(DESCRIPTION "Run simulation on ${IP_LIB} with ${CMAKE_CURRENT_FUNCTION}") + add_custom_target(${ARG_RUN_TARGET_NAME} + COMMAND ${__xmsim_cmd} + COMMENT ${DESCRIPTION} + DEPENDS ${__comp_tgts} + ) + set_property(TARGET ${ARG_RUN_TARGET_NAME} PROPERTY DESCRIPTION ${DESCRIPTION}) + endif() + set(SIM_RUN_CMD ${__xmsim_cmd} PARENT_SCOPE) endfunction() +function(__xcelium_compile_lib IP_LIB) + cmake_parse_arguments(ARG "NO_DEPS" "OUTDIR;TOP_MODULE;XMVLOG_ARGS;XMVHDL_ARGS;XMELAB_ARGS" "" ${ARGN}) + # Check for any unrecognized arguments + if(ARG_UNPARSED_ARGUMENTS) + message(FATAL_ERROR "${CMAKE_CURRENT_FUNCTION} passed unrecognized argument " "${ARG_UNPARSED_ARGUMENTS}") + endif() + + include("${CMAKE_CURRENT_FUNCTION_LIST_DIR}/../../hwip.cmake") + alias_dereference(IP_LIB ${IP_LIB}) + get_target_property(BINARY_DIR ${IP_LIB} BINARY_DIR) + + # get_target_property(LIBRARY ${IP_LIB} LIBRARY) + # if(NOT LIBRARY) + set(LIBRARY worklib) + # endif() + + if(NOT ARG_TOP_MODULE) + get_target_property(IP_NAME ${IP_LIB} IP_NAME) + set(ARG_TOP_MODULE ${IP_NAME}) + endif() + + # if(NOT ARG_OUTDIR) + # set(OUTDIR ${BINARY_DIR}/${IP_LIB}_xcelium) + # else() + # set(OUTDIR ${ARG_OUTDIR}) + # endif() + + if(ARG_NO_DEPS) + set(ARG_NO_DEPS NO_DEPS) + else() + unset(ARG_NO_DEPS) + endif() + + # SystemVerilog and Verilog files and arguments + get_ip_sources(SV_SOURCES ${IP_LIB} SYSTEMVERILOG VERILOG ${ARG_NO_DEPS}) + if(SV_SOURCES) + get_ip_include_directories(SV_INC_DIRS ${IP_LIB} SYSTEMVERILOG VERILOG) + get_ip_compile_definitions(SV_COMP_DEFS ${IP_LIB} SYSTEMVERILOG VERILOG) + + foreach(dir ${SV_INC_DIRS}) + list(APPEND SV_ARG_INCDIRS -INCDIR ${dir}) + endforeach() + + foreach(def ${SV_COMP_DEFS}) + list(APPEND SV_CMP_DEFS_ARG -DEFINE ${def}) + endforeach() + + set(DESCRIPTION "Compile Verilog and SV files of ${IP_LIB} with xcelium xmvlog in library ${LIBRARY}") + set(__xmvlog_cmd COMMAND xmvlog + -sv + ${ARG_XMVLOG_ARGS} + ${SV_ARG_INCDIRS} + ${SV_CMP_DEFS_ARG} + ${SV_SOURCES} + # -work ${OUTDIR}/${LIBRARY} + ) + endif() + + # VHDL files and arguments + get_ip_sources(VHDL_SOURCES ${IP_LIB} VHDL ${ARG_NO_DEPS}) + if(VHDL_SOURCES) + get_ip_include_directories(VHDL_INC_DIRS ${IP_LIB} VHDL) + get_ip_compile_definitions(VHDL_COMP_DEFS ${IP_LIB} VHDL) + + foreach(dir ${VHDL_INC_DIRS}) + list(APPEND VHDL_ARG_INCDIRS -INCDIR ${dir}) + endforeach() + + foreach(def ${VHDL_COMP_DEFS}) + list(APPEND VHDL_CMP_DEFS_ARG -DEFINE ${def}) + endforeach() + + set(__xmvhdl_cmd COMMAND xmvhdl + ${ARG_XMVHDL_ARGS} + ${VHDL_ARG_INCDIRS} + ${VHDL_CMP_DEFS_ARG} + ${VHDL_SOURCES} + # -work ${OUTDIR}/${LIBRARY} + ) + endif() + + set(__xmelab_cmd COMMAND xmelab + ${ARG_XMELAB_ARGS} + worklib.${IP_NAME} + # -work ${OUTDIR}/${LIBRARY} + ) + + if(NOT TARGET ${IP_LIB}_xcelium_complib) + set(DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with xcelium in library ${LIBRARY}") + set(STAMP_FILE "${BINARY_DIR}/${IP_LIB}_${CMAKE_CURRENT_FUNCTION}.stamp") + add_custom_command( + OUTPUT ${STAMP_FILE} #${OUTDIR}/${LIBRARY} + # COMMAND ${CMAKE_COMMAND} -E make_directory ${OUTDIR} + ${__xmvlog_cmd} + ${__xmvhdl_cmd} + ${__xmelab_cmd} + COMMAND touch ${STAMP_FILE} + DEPENDS ${SV_SOURCES} ${VHDL_SOURCES} + COMMENT ${DESCRIPTION} + ) + + add_custom_target( + ${IP_LIB}_xcelium_complib + DEPENDS ${STAMP_FILE} ${STAMP_FILE_VHDL} ${IP_LIB} + ) + set_property(TARGET ${IP_LIB}_xcelium_complib PROPERTY + DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with xcelium in library ${LIBRARY}") + endif() + + # set(__XCELIUM_IP_LIB_DIR ${OUTDIR} PARENT_SCOPE) + # set(__XCELIUM_IP_LIB_NAME ${LIBRARY} PARENT_SCOPE) +endfunction() diff --git a/cmake/sim/iverilog/iverilog.cmake b/cmake/sim/iverilog/iverilog.cmake index 9bb7b2f..6c9d136 100644 --- a/cmake/sim/iverilog/iverilog.cmake +++ b/cmake/sim/iverilog/iverilog.cmake @@ -18,7 +18,7 @@ include_guard(GLOBAL) # ]]] function(iverilog IP_LIB) # Parse the function arguments - cmake_parse_arguments(ARG "" "TOP_MODULE;OUTDIR;EXECUTABLE;CLI_FLAGS" "" ${ARGN}) + cmake_parse_arguments(ARG "NO_RUN_TARGET" "TOP_MODULE;OUTDIR;EXECUTABLE;RUN_TARGET_NAME" ";IVERILOG_ARGS;RUN_ARGS" ${ARGN}) # Check for any unrecognized arguments if(ARG_UNPARSED_ARGUMENTS) message(FATAL_ERROR "${CMAKE_CURRENT_FUNCTION} passed unrecognized argument " "${ARG_UNPARSED_ARGUMENTS}") @@ -57,38 +57,50 @@ function(iverilog IP_LIB) set(STAMP_FILE "${BINARY_DIR}/${IP_LIB}_${CMAKE_CURRENT_FUNCTION}.stamp") set(DESCRIPTION "Compile ${IP_LIB} with ${CMAKE_CURRENT_FUNCTION}") - # Add a custom command to run iverilog - add_custom_command( - OUTPUT ${ARG_EXECUTABLE} ${STAMP_FILE} - COMMAND ${CMAKE_COMMAND} -E make_directory ${OUTDIR} - COMMAND iverilog - $<$:-s${ARG_TOP_MODULE}> - ${ARG_INCDIRS} - ${CMP_DEFS_ARG} - ${ARG_CLI_FLAGS} - -o ${ARG_EXECUTABLE} - ${SOURCES} - COMMAND touch ${STAMP_FILE} - DEPENDS ${SOURCES} - COMMENT ${DESCRIPTION} - ) + if(NOT TARGET ${IP_LIB}_${CMAKE_CURRENT_FUNCTION}) + # Add a custom command to run iverilog + add_custom_command( + OUTPUT ${ARG_EXECUTABLE} ${STAMP_FILE} + COMMAND ${CMAKE_COMMAND} -E make_directory ${OUTDIR} + COMMAND iverilog + $<$:-s${ARG_TOP_MODULE}> + ${ARG_INCDIRS} + ${CMP_DEFS_ARG} + ${ARG_IVERILOG_ARGS} + -o ${ARG_EXECUTABLE} + ${SOURCES} + COMMAND touch ${STAMP_FILE} + DEPENDS ${SOURCES} + COMMENT ${DESCRIPTION} + ) - # Add a custom target that depends on the executable and stamp file - add_custom_target( - ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - DEPENDS ${ARG_EXECUTABLE} ${STAMP_FILE} ${IP_LIB} - ) - set_property(TARGET ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} PROPERTY DESCRIPTION ${DESCRIPTION}) + # Add a custom target that depends on the executable and stamp file + add_custom_target( + ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} + DEPENDS ${ARG_EXECUTABLE} ${STAMP_FILE} ${IP_LIB} + ) + set_property(TARGET ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} PROPERTY DESCRIPTION ${DESCRIPTION}) + endif() - set(DESCRIPTION "Run ${CMAKE_CURRENT_FUNCTION} testbench compiled from ${IP_LIB}") - # Add a custom target to run the generated executable - add_custom_target( - run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - COMMAND ${ARG_EXECUTABLE} - DEPENDS ${ARG_EXECUTABLE} ${STAMP_FILE} ${SOURCES} ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - COMMENT ${DESCRIPTION} - ) - set_property(TARGET run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} PROPERTY DESCRIPTION ${DESCRIPTION}) + set(__sim_run_cmd + vvp ${ARG_EXECUTABLE} + ${ARG_RUN_ARGS} + ) + if(NOT ${ARG_NO_RUN_TARGET}) + if(NOT ARG_RUN_TARGET_NAME) + set(ARG_RUN_TARGET_NAME run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION}) + endif() + set(DESCRIPTION "Run ${CMAKE_CURRENT_FUNCTION} testbench compiled from ${IP_LIB}") + # Add a custom target to run the generated executable + add_custom_target( + ${ARG_RUN_TARGET_NAME} + COMMAND ${__sim_run_cmd} + DEPENDS ${ARG_EXECUTABLE} ${STAMP_FILE} ${SOURCES} ${IP_LIB}_${CMAKE_CURRENT_FUNCTION} + COMMENT ${DESCRIPTION} + ) + set_property(TARGET ${ARG_RUN_TARGET_NAME} PROPERTY DESCRIPTION ${DESCRIPTION}) + endif() + set(SIM_RUN_CMD ${__sim_run_cmd} PARENT_SCOPE) endfunction() diff --git a/cmake/sim/modelsim/modelsim.cmake b/cmake/sim/siemens/modelsim.cmake similarity index 66% rename from cmake/sim/modelsim/modelsim.cmake rename to cmake/sim/siemens/modelsim.cmake index 02f2fca..9859474 100644 --- a/cmake/sim/modelsim/modelsim.cmake +++ b/cmake/sim/siemens/modelsim.cmake @@ -1,7 +1,7 @@ include_guard(GLOBAL) function(modelsim IP_LIB) - cmake_parse_arguments(ARG "TARGET_PER_IP;QUIET" "TOP_MODULE;OUTDIR;ARGS" "" ${ARGN}) + cmake_parse_arguments(ARG "TARGET_PER_IP;NO_RUN_TARGET;QUIET" "TOP_MODULE;OUTDIR;RUN_TARGET_NAME" "VCOM_ARGS;VLOG_ARGS;RUN_ARGS" ${ARGN}) if(ARG_UNPARSED_ARGUMENTS) message(FATAL_ERROR "${CMAKE_CURRENT_FUNCTION} passed unrecognized argument " "${ARG_UNPARSED_ARGUMENTS}") endif() @@ -55,15 +55,28 @@ function(modelsim IP_LIB) set(list_comp_libs ${IP_LIB}) unset(__no_deps_arg) endif() + + if(ARG_VLOG_ARGS) + set(ARG_VLOG_ARGS VLOG_ARGS ${ARG_VLOG_ARGS}) + endif() + + if(ARG_VCOM_ARGS) + set(ARG_VCOM_ARGS VCOM_ARGS ${ARG_VCOM_ARGS}) + endif() list(APPEND __lib_args -Ldir ${OUTDIR}) foreach(ip ${list_comp_libs}) get_target_property(ip_name ${ip} IP_NAME) if(ip_name) # If IP_NAME IS set, its SoCMake's IP_LIBRARY - __modelsim_compile_lib(${ip} ${__no_deps_arg} OUTDIR ${OUTDIR} ${ARG_QUIET}) - if(NOT ${MODELSIM_IP_LIB_NAME} IN_LIST __libnames) - list(APPEND __lib_args -L ${MODELSIM_IP_LIB_NAME}) - list(APPEND __libnames ${MODELSIM_IP_LIB_NAME}) + __modelsim_compile_lib(${ip} ${__no_deps_arg} + OUTDIR ${OUTDIR} + ${ARG_QUIET} + ${ARG_VLOG_ARGS} + ${ARG_VCOM_ARGS} + ) + if(NOT ${__MODELSIM_IP_LIB_NAME} IN_LIST __libnames) + list(APPEND __lib_args -L ${__MODELSIM_IP_LIB_NAME}) + list(APPEND __libnames ${__MODELSIM_IP_LIB_NAME}) endif() list(APPEND __comp_tgts ${ip}_modelsim_complib) endif() @@ -75,23 +88,30 @@ function(modelsim IP_LIB) list(APPEND CMP_DEFS_ARG +${def}) endforeach() - set(__VSIM_CMD ${MODELSIM_HOME}/bin/vsim + set(__vsim_cmd ${MODELSIM_HOME}/bin/vsim ${__lib_args} ${CMP_DEFS_ARG} + ${ARG_RUN_ARGS} -c ${LIBRARY}.${ARG_TOP_MODULE} -do "run -all\; quit" $<$:-quiet> ) - set(DESCRIPTION "Run ${CMAKE_CURRENT_FUNCTION} testbench compiled from ${IP_LIB}") - add_custom_target( - run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - COMMAND ${__VSIM_CMD} -noautoldlibpath - DEPENDS ${__comp_tgts} - WORKING_DIRECTORY ${MODELSIM_IP_LIB_DIR} - COMMENT ${DESCRIPTION} - VERBATIM - ) - set_property(TARGET run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} PROPERTY DESCRIPTION ${DESCRIPTION}) + if(NOT ARG_NO_RUN_TARGET) + if(NOT ARG_RUN_TARGET_NAME) + set(ARG_RUN_TARGET_NAME run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION}) + endif() + set(DESCRIPTION "Run ${CMAKE_CURRENT_FUNCTION} testbench compiled from ${IP_LIB}") + add_custom_target( + ${ARG_RUN_TARGET_NAME} + COMMAND ${__vsim_cmd} -noautoldlibpath + DEPENDS ${__comp_tgts} + WORKING_DIRECTORY ${__MODELSIM_IP_LIB_DIR} + COMMENT ${DESCRIPTION} + VERBATIM + ) + set_property(TARGET ${ARG_RUN_TARGET_NAME} PROPERTY DESCRIPTION ${DESCRIPTION}) + endif() + set(SIM_RUN_CMD ${__vsim_cmd} PARENT_SCOPE) endfunction() @@ -120,7 +140,7 @@ function(find_modelsim) endfunction() function(__modelsim_compile_lib IP_LIB) - cmake_parse_arguments(ARG "QUIET;NO_DEPS" "OUTDIR;ARGS" "" ${ARGN}) + cmake_parse_arguments(ARG "QUIET;NO_DEPS" "OUTDIR;VLOG_ARGS;VCOM_ARGS" "" ${ARGN}) # Check for any unrecognized arguments if(ARG_UNPARSED_ARGUMENTS) message(FATAL_ERROR "${CMAKE_CURRENT_FUNCTION} passed unrecognized argument " "${ARG_UNPARSED_ARGUMENTS}") @@ -149,7 +169,7 @@ function(__modelsim_compile_lib IP_LIB) endif() # SystemVerilog and Verilog files and arguments - unset(__VLOG_CMD) + unset(__vlog_cmd) get_ip_sources(SV_SOURCES ${IP_LIB} SYSTEMVERILOG VERILOG ${ARG_NO_DEPS} ) if(SV_SOURCES) get_ip_include_directories(SV_INC_DIRS ${IP_LIB} SYSTEMVERILOG VERILOG) @@ -164,11 +184,12 @@ function(__modelsim_compile_lib IP_LIB) endforeach() set(DESCRIPTION "Compile Verilog and SV files of ${IP_LIB} with modelsim vlog in library ${LIBRARY}") - set(__VLOG_CMD COMMAND ${MODELSIM_HOME}/bin/vlog + set(__vlog_cmd COMMAND ${MODELSIM_HOME}/bin/vlog -nologo -sv -sv17compat $<$:-quiet> + ${ARG_VLOG_ARGS} ${SV_ARG_INCDIRS} ${SV_CMP_DEFS_ARG} ${SV_SOURCES} @@ -177,7 +198,7 @@ function(__modelsim_compile_lib IP_LIB) endif() # VHDL files and arguments - unset(__VCOM_CMD) + unset(__vcom_cmd) get_ip_sources(VHDL_SOURCES ${IP_LIB} VHDL ${ARG_NO_DEPS}) if(VHDL_SOURCES) get_ip_include_directories(VHDL_INC_DIRS ${IP_LIB} VHDL) @@ -191,9 +212,10 @@ function(__modelsim_compile_lib IP_LIB) list(APPEND VHDL_CMP_DEFS_ARG +define+${def}) endforeach() - set(__VCOM_CMD COMMAND ${MODELSIM_HOME}/bin/vcom + set(__vcom_cmd COMMAND ${MODELSIM_HOME}/bin/vcom -nologo $<$:-quiet> + ${ARG_VCOM_ARGS} ${VHDL_ARG_INCDIRS} ${VHDL_CMP_DEFS_ARG} ${VHDL_SOURCES} @@ -201,26 +223,28 @@ function(__modelsim_compile_lib IP_LIB) ) endif() - set(DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with modelsim in library ${LIBRARY}") - set(STAMP_FILE "${BINARY_DIR}/${IP_LIB}_${CMAKE_CURRENT_FUNCTION}.stamp") - add_custom_command( - OUTPUT ${STAMP_FILE} ${OUTDIR}/${LIBRARY} - COMMAND ${CMAKE_COMMAND} -E make_directory ${OUTDIR} - ${__VLOG_CMD} - ${__VCOM_CMD} - COMMAND touch ${STAMP_FILE} - DEPENDS ${SV_SOURCES} ${VHDL_SOURCES} - COMMENT ${DESCRIPTION} - ) - - add_custom_target( - ${IP_LIB}_modelsim_complib - DEPENDS ${STAMP_FILE} ${STAMP_FILE_VHDL} ${IP_LIB} - ) - set_property(TARGET ${IP_LIB}_modelsim_complib PROPERTY - DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with modelsim in library ${LIBRARY}") - - - set(MODELSIM_IP_LIB_DIR ${OUTDIR} PARENT_SCOPE) - set(MODELSIM_IP_LIB_NAME ${LIBRARY} PARENT_SCOPE) + if(NOT TARGET ${IP_LIB}_modelsim_complib) + set(DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with modelsim in library ${LIBRARY}") + set(STAMP_FILE "${BINARY_DIR}/${IP_LIB}_${CMAKE_CURRENT_FUNCTION}.stamp") + add_custom_command( + OUTPUT ${STAMP_FILE} ${OUTDIR}/${LIBRARY} + COMMAND ${CMAKE_COMMAND} -E make_directory ${OUTDIR} + ${__vlog_cmd} + ${__vcom_cmd} + COMMAND touch ${STAMP_FILE} + DEPENDS ${SV_SOURCES} ${VHDL_SOURCES} + COMMENT ${DESCRIPTION} + ) + + add_custom_target( + ${IP_LIB}_modelsim_complib + DEPENDS ${STAMP_FILE} ${STAMP_FILE_VHDL} ${IP_LIB} + ) + set_property(TARGET ${IP_LIB}_modelsim_complib PROPERTY + DESCRIPTION "Compile VHDL, SV, and Verilog files for ${IP_LIB} with modelsim in library ${LIBRARY}") + endif() + + + set(__MODELSIM_IP_LIB_DIR ${OUTDIR} PARENT_SCOPE) + set(__MODELSIM_IP_LIB_NAME ${LIBRARY} PARENT_SCOPE) endfunction() diff --git a/cmake/sim/verilator/verilator.cmake b/cmake/sim/verilator/verilator.cmake index 7ecde9f..2511234 100644 --- a/cmake/sim/verilator/verilator.cmake +++ b/cmake/sim/verilator/verilator.cmake @@ -1,7 +1,7 @@ function(verilator IP_LIB) - set(OPTIONS "COVERAGE;TRACE;TRACE_FST;SYSTEMC;TRACE_STRUCTS;MAIN") - set(ONE_PARAM_ARGS "PREFIX;TOP_MODULE;THREADS;TRACE_THREADS;DIRECTORY;EXECUTABLE_NAME") - set(MULTI_PARAM_ARGS "VERILATOR_ARGS;OPT_SLOW;OPT_FAST;OPT_GLOBAL") + set(OPTIONS "COVERAGE;TRACE;TRACE_FST;SYSTEMC;TRACE_STRUCTS;MAIN;NO_RUN_TARGET") + set(ONE_PARAM_ARGS "PREFIX;TOP_MODULE;THREADS;TRACE_THREADS;DIRECTORY;EXECUTABLE_NAME;RUN_TARGET_NAME") + set(MULTI_PARAM_ARGS "VERILATOR_ARGS;OPT_SLOW;OPT_FAST;OPT_GLOBAL;RUN_ARGS") cmake_parse_arguments(ARG "${OPTIONS}" @@ -84,6 +84,16 @@ function(verilator IP_LIB) unset(ARG_MAIN) endif() + if(ARG_RUN_ARGS) + set(__ARG_RUN_ARGS ${ARG_RUN_ARGS}) + unset(ARG_RUN_ARGS) + endif() + + if(ARG_NO_RUN_TARGET) + set(__ARG_NO_RUN_TARGET ${ARG_NO_RUN_TARGET}) + unset(ARG_NO_RUN_TARGET) + endif() + set(PASS_ADDITIONAL_MULTIPARAM SOURCES INCLUDE_DIRS) # Additional parameters to pass set(PASS_ADDITIONAL_ONEPARAM DIRECTORY PREFIX) set(PASS_ADDITIONAL_OPTIONS) @@ -138,83 +148,90 @@ function(verilator IP_LIB) ### set(VERILATE_TARGET ${IP_LIB}_verilate) - include(ExternalProject) - ExternalProject_Add(${VERILATE_TARGET} - DOWNLOAD_COMMAND "" - SOURCE_DIR "${CMAKE_CURRENT_FUNCTION_LIST_DIR}/verilator" - PREFIX ${DIRECTORY} - BINARY_DIR ${DIRECTORY} - LIST_SEPARATOR | - BUILD_ALWAYS 1 - - CMAKE_ARGS - ${ARG_CMAKE_CXX_STANDARD} - -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} - -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER} - -DCMAKE_VERBOSE_MAKEFILE=${CMAKE_VERBOSE_MAKEFILE} - -DCMAKE_RUNTIME_OUTPUT_DIRECTORY=${BINARY_DIR} - - -DTARGET=${ARG_TOP_MODULE} - -DARGUMENTS_LIST=${ARGUMENTS_LIST} - -DEXECUTABLE_NAME=${ARG_EXECUTABLE_NAME} - ${EXT_PRJ_ARGS} - -DVERILATOR_ROOT=${VERILATOR_ROOT} - -DSYSTEMC_ROOT=${SYSTEMC_HOME} - - INSTALL_COMMAND "" - DEPENDS ${IP_LIB} - EXCLUDE_FROM_ALL 1 - COMMENT ${DESCRIPTION} + if(NOT TARGET ${IP_LIB}_verilate) + include(ExternalProject) + ExternalProject_Add(${VERILATE_TARGET} + DOWNLOAD_COMMAND "" + SOURCE_DIR "${CMAKE_CURRENT_FUNCTION_LIST_DIR}/verilator" + PREFIX ${DIRECTORY} + BINARY_DIR ${DIRECTORY} + LIST_SEPARATOR | + BUILD_ALWAYS 1 + + CMAKE_ARGS + ${ARG_CMAKE_CXX_STANDARD} + -DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER} + -DCMAKE_C_COMPILER=${CMAKE_C_COMPILER} + -DCMAKE_VERBOSE_MAKEFILE=${CMAKE_VERBOSE_MAKEFILE} + -DCMAKE_RUNTIME_OUTPUT_DIRECTORY=${BINARY_DIR} + + -DTARGET=${ARG_TOP_MODULE} + -DARGUMENTS_LIST=${ARGUMENTS_LIST} + -DEXECUTABLE_NAME=${ARG_EXECUTABLE_NAME} + ${EXT_PRJ_ARGS} + -DVERILATOR_ROOT=${VERILATOR_ROOT} + -DSYSTEMC_ROOT=${SYSTEMC_HOME} + + INSTALL_COMMAND "" + DEPENDS ${IP_LIB} + EXCLUDE_FROM_ALL 1 + COMMENT ${DESCRIPTION} + ) + + set_property( + TARGET ${VERILATE_TARGET} + APPEND PROPERTY ADDITIONAL_CLEAN_FILES + ${DIRECTORY} + ${EXECUTABLE_PATH} ) + set_property(TARGET ${VERILATE_TARGET} PROPERTY DESCRIPTION ${DESCRIPTION}) + + set(VLT_STATIC_LIB "${DIRECTORY}/lib${ARG_TOP_MODULE}.a") + set(INC_DIR ${DIRECTORY}) + + set(VERILATED_LIB ${IP_LIB}__vlt) + add_library(${VERILATED_LIB} STATIC IMPORTED) + set_target_properties(${VERILATED_LIB} PROPERTIES IMPORTED_GLOBAL TRUE) + add_dependencies(${VERILATED_LIB} ${VERILATE_TARGET}) + set_target_properties(${VERILATED_LIB} PROPERTIES IMPORTED_LOCATION ${VLT_STATIC_LIB}) + + target_include_directories(${VERILATED_LIB} INTERFACE ${INC_DIR}) + target_include_directories(${VERILATED_LIB} INTERFACE + "${VERILATOR_INCLUDE_DIR}" + "${VERILATOR_INCLUDE_DIR}/vltstd") + + set(THREADS_PREFER_PTHREAD_FLAG ON) + find_package(Threads REQUIRED) + + target_link_libraries(${VERILATED_LIB} INTERFACE -pthread) + + # Search for linked libraries that are Shared or Static libraries and link them to the verilated library + get_ip_links(IPS_LIST ${IP_LIB}) + foreach(ip ${IPS_LIST}) + get_target_property(ip_type ${ip} TYPE) + if(ip_type STREQUAL "SHARED_LIBRARY" OR ip_type STREQUAL "STATIC_LIBRARY") + target_link_libraries(${VERILATED_LIB} INTERFACE ${ip}) + endif() + endforeach() + + string(REPLACE "__" "::" ALIAS_NAME "${VERILATED_LIB}") + add_library(${ALIAS_NAME} ALIAS ${VERILATED_LIB}) + endif() - set_property( - TARGET ${VERILATE_TARGET} - APPEND PROPERTY ADDITIONAL_CLEAN_FILES - ${DIRECTORY} - ${EXECUTABLE_PATH} - ) - set_property(TARGET ${VERILATE_TARGET} PROPERTY DESCRIPTION ${DESCRIPTION}) - - set(VLT_STATIC_LIB "${DIRECTORY}/lib${ARG_TOP_MODULE}.a") - set(INC_DIR ${DIRECTORY}) - - set(VERILATED_LIB ${IP_LIB}__vlt) - add_library(${VERILATED_LIB} STATIC IMPORTED) - set_target_properties(${VERILATED_LIB} PROPERTIES IMPORTED_GLOBAL TRUE) - add_dependencies(${VERILATED_LIB} ${VERILATE_TARGET}) - set_target_properties(${VERILATED_LIB} PROPERTIES IMPORTED_LOCATION ${VLT_STATIC_LIB}) - - target_include_directories(${VERILATED_LIB} INTERFACE ${INC_DIR}) - target_include_directories(${VERILATED_LIB} INTERFACE - "${VERILATOR_INCLUDE_DIR}" - "${VERILATOR_INCLUDE_DIR}/vltstd") - - set(THREADS_PREFER_PTHREAD_FLAG ON) - find_package(Threads REQUIRED) - - target_link_libraries(${VERILATED_LIB} INTERFACE -pthread) - - # Search for linked libraries that are Shared or Static libraries and link them to the verilated library - get_ip_links(IPS_LIST ${IP_LIB}) - foreach(ip ${IPS_LIST}) - get_target_property(ip_type ${ip} TYPE) - if(ip_type STREQUAL "SHARED_LIBRARY" OR ip_type STREQUAL "STATIC_LIBRARY") - target_link_libraries(${VERILATED_LIB} INTERFACE ${ip}) + set(__sim_run_cmd ${EXECUTABLE_PATH} ${__ARG_RUN_ARGS}) + if(EXECUTABLE_PATH AND NOT __ARG_NO_RUN_TARGET) + if(NOT ARG_RUN_TARGET_NAME) + set(ARG_RUN_TARGET_NAME run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION}) endif() - endforeach() - - string(REPLACE "__" "::" ALIAS_NAME "${VERILATED_LIB}") - add_library(${ALIAS_NAME} ALIAS ${VERILATED_LIB}) - - if(EXECUTABLE_PATH) set(DESCRIPTION "Run ${CMAKE_CURRENT_FUNCTION} testbench compiled from ${IP_LIB}") # Add a custom target to run the generated executable add_custom_target( - run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} - COMMAND ${EXECUTABLE_PATH} + ${ARG_RUN_TARGET_NAME} + COMMAND ${__sim_run_cmd} DEPENDS ${EXECUTABLE_PATH} ${STAMP_FILE} ${VERILATE_TARGET} COMMENT ${DESCRIPTION} ) - set_property(TARGET run_${IP_LIB}_${CMAKE_CURRENT_FUNCTION} PROPERTY DESCRIPTION ${DESCRIPTION}) + set_property(TARGET ${ARG_RUN_TARGET_NAME} PROPERTY DESCRIPTION ${DESCRIPTION}) endif() + set(SIM_RUN_CMD ${__sim_run_cmd} PARENT_SCOPE) endfunction()