diff --git a/CMakeLists.txt b/CMakeLists.txt index c465e2f..a2b8292 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,7 @@ cmake_minimum_required(VERSION 3.12) - +############################################################################### +# +############################################################################### project(dbt-rise-tgc VERSION 1.0.0) include(GNUInstallDirs) @@ -61,12 +63,28 @@ elseif(TARGET elfio::elfio) else() message(FATAL_ERROR "No elfio library found, maybe a find_package() call is missing") endif() + set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION} FRAMEWORK FALSE - PUBLIC_HEADER "${LIB_HEADERS}" # specify the public headers ) - +install(TARGETS ${PROJECT_NAME} COMPONENT ${PROJECT_NAME} + EXPORT ${PROJECT_NAME}Targets # for downstream dependencies + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} # static lib + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} # binaries + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} # shared lib + FRAMEWORK DESTINATION ${CMAKE_INSTALL_LIBDIR} # for mac + PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} # headers for mac (note the different component -> different package) + INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} # headers +) +install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/incl/iss COMPONENT ${PROJECT_NAME} + DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} # target directory + FILES_MATCHING # install only matched files + PATTERN "*.h" # select header files + ) +############################################################################### +# +############################################################################### project(tgc-sim) find_package(Boost COMPONENTS program_options thread REQUIRED) @@ -90,16 +108,18 @@ if (Tcmalloc_FOUND) target_link_libraries(${PROJECT_NAME} ${Tcmalloc_LIBRARIES}) endif(Tcmalloc_FOUND) -install(TARGETS dbt-rise-tgc tgc-sim +install(TARGETS tgc-sim EXPORT ${PROJECT_NAME}Targets # for downstream dependencies - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # static lib - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} COMPONENT libs # binaries - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # shared lib - FRAMEWORK DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # for mac - PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} COMPONENT devel # headers for mac (note the different component -> different package) + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} # static lib + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} # binaries + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} # shared lib + FRAMEWORK DESTINATION ${CMAKE_INSTALL_LIBDIR} # for mac + PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} # headers for mac (note the different component -> different package) INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} # headers ) - +############################################################################### +# +############################################################################### project(dbt-rise-tgc_sc VERSION 1.0.0) include(FindSystemCPackage) @@ -121,18 +141,19 @@ if(SystemC_FOUND) target_link_libraries(${PROJECT_NAME} PUBLIC ${llvm_libs}) endif() + set(LIB_HEADERS ${CMAKE_CURRENT_SOURCE_DIR}/incl/sysc/core_complex.h) set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION} FRAMEWORK FALSE PUBLIC_HEADER "${LIB_HEADERS}" # specify the public headers ) - install(TARGETS ${PROJECT_NAME} + install(TARGETS ${PROJECT_NAME} COMPONENT ${PROJECT_NAME} EXPORT ${PROJECT_NAME}Targets # for downstream dependencies - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # static lib - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} COMPONENT libs # binaries - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # shared lib - FRAMEWORK DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT libs # for mac - PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/${PROJECT_NAME} COMPONENT devel # headers for mac (note the different component -> different package) + ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} # static lib + RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} # binaries + LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} # shared lib + FRAMEWORK DESTINATION ${CMAKE_INSTALL_LIBDIR} # for mac + PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/sysc # headers for mac (note the different component -> different package) INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} # headers ) endif() diff --git a/contrib/build.tcl b/contrib/build.tcl new file mode 100644 index 0000000..023815b --- /dev/null +++ b/contrib/build.tcl @@ -0,0 +1,30 @@ +namespace eval Specification { + proc buildproc { args } { + global env + variable installDir + variable compiler + variable compiler [::scsh::get_backend_compiler] + # set target $machine + set target [::scsh::machine] + set linkerOptions "" + set preprocessorOptions "" + set libversion $compiler + switch -exact -- $target { + "linux" { + set install_dir $::env(TGFS_INSTALL_ROOT) + set incldir "${install_dir}/include" + set libdir "${install_dir}/lib64" + set preprocessorOptions [concat $preprocessorOptions "-I${incldir}"] + # Set the Linker paths. + set linkerOptions [concat $linkerOptions "-Wl,-rpath,${libdir} -L${libdir} -ldbt-rise-tgc_sc"] + } + default { + puts stderr "ERROR: \"$target\" is not supported, [::scsh::version]" + return + } + } + ::scsh::cwr_append_ipsimbld_opts preprocessor "$preprocessorOptions" + ::scsh::cwr_append_ipsimbld_opts linker "$linkerOptions" + } + ::scsh::add_build_callback [namespace current]::buildproc +} diff --git a/contrib/tgc_import.cc b/contrib/tgc_import.cc new file mode 100644 index 0000000..809e136 --- /dev/null +++ b/contrib/tgc_import.cc @@ -0,0 +1,4 @@ + +#include "sysc/core_complex.h" + +void modules() { sysc::tgfs::core_complex i_core_complex("core_complex"); } diff --git a/contrib/tgc_import.tcl b/contrib/tgc_import.tcl new file mode 100644 index 0000000..9726408 --- /dev/null +++ b/contrib/tgc_import.tcl @@ -0,0 +1,50 @@ +############################################################################# +# +############################################################################# +proc getScriptDirectory {} { + set dispScriptFile [file normalize [info script]] + set scriptFolder [file dirname $dispScriptFile] + return $scriptFolder +} +if { $::env(SNPS_VP_PRODUCT) == "PAULTRA" } { + set hardware /HARDWARE/HW/HW +} else { + set hardware /HARDWARE +} + +set scriptDir [getScriptDirectory] +set top_design_name core_complex +set clocks clk_i +set resets rst_i +set model_prefix "i_" +set model_postfix "" + +::pct::new_project +::pct::open_library TLM2_PL +::pct::clear_systemc_defines +::pct::clear_systemc_include_path +::pct::add_to_systemc_include_path $::env(TGFS_INSTALL_ROOT)/include +::pct::set_import_protocol_generation_flag false +::pct::set_update_existing_encaps_flag true +::pct::set_dynamic_port_arrays_flag true +::pct::set_import_scml_properties_flag true +::pct::load_modules --set-category modules tgc_import.cc + +# Set Port Protocols correctly +set block ${top_design_name} +foreach clock ${clocks} { + ::pct::set_block_port_protocol --set-category SYSTEM_LIBRARY:$block/${clock} SYSTEM_LIBRARY:CLOCK +} +foreach reset ${resets} { + ::pct::set_block_port_protocol --set-category SYSTEM_LIBRARY:$block/${reset} SYSTEM_LIBRARY:RESET +} +::pct::set_encap_port_array_size SYSTEM_LIBRARY:$block/local_irq_i 16 + +# Set compile settings and look +set block SYSTEM_LIBRARY:${top_design_name} +::pct::set_encap_build_script $block/${top_design_name} $scriptDir/build.tcl +::pct::set_background_color_rgb $block 255 255 255 255 +::pct::create_instance SYSTEM_LIBRARY:${top_design_name} ${hardware} ${model_prefix}${top_design_name}${model_postfix} ${top_design_name} + +# export the result as component +::pct::export_system_library ${top_design_name} ${top_design_name}.xml diff --git a/incl/sysc/core_complex.h b/incl/sysc/core_complex.h index 94029e5..4668837 100644 --- a/incl/sysc/core_complex.h +++ b/incl/sysc/core_complex.h @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (C) 2017, 2018 MINRES Technologies GmbH + * Copyright (C) 2017-2021 MINRES Technologies GmbH * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -30,18 +30,23 @@ * *******************************************************************************/ -#ifndef _SYSC_SIFIVE_FE310_H_ -#define _SYSC_SIFIVE_FE310_H_ +#ifndef _SYSC_CORE_COMPLEX_H_ +#define _SYSC_CORE_COMPLEX_H_ -#include "tlm/scc/initiator_mixin.h" -#include "scc/traceable.h" -#include "scc/utilities.h" -#include "tlm/scc/scv/tlm_rec_initiator_socket.h" +#include +#include +#include +#include +#include +#ifdef CWR_SYSTEMC +#include +#else #include +#endif #include -#include #include #include +#include namespace sysc { @@ -63,8 +68,6 @@ class core_complex : public sc_core::sc_module, public scc::traceable { public: tlm::scc::initiator_mixin> initiator{"intor"}; - sc_core::sc_in clk_i{"clk_i"}; - sc_core::sc_in rst_i{"rst_i"}; sc_core::sc_in global_irq_i{"global_irq_i"}; @@ -75,6 +78,9 @@ public: sc_core::sc_vector> local_irq_i{"local_irq_i", 16}; +#ifndef CWR_SYSTEMC + sc_core::sc_in clk_i{"clk_i"}; + sc_core::sc_port, 1, sc_core::SC_ZERO_OR_MORE_BOUND> mtime_o; cci::cci_param elf_file{"elf_file", ""}; @@ -93,7 +99,47 @@ public: cci::cci_param mhartid{"mhartid", 0}; - core_complex(sc_core::sc_module_name name); + core_complex(sc_core::sc_module_name const& name); + +#else + sc_core::sc_in clk_i{"clk_i"}; + + sc_core::sc_in mtime_i{"mtime_i"}; + + scml_property elf_file{"elf_file", ""}; + + scml_property enable_disass{"enable_disass", false}; + + scml_property reset_address{"reset_address", 0ULL}; + + scml_property core_type{"core_type", "tgc_c"}; + + scml_property backend{"backend", "interp"}; + + scml_property gdb_server_port{"gdb_server_port", 0}; + + scml_property dump_ir{"dump_ir", false}; + + scml_property mhartid{"mhartid", 0}; + + core_complex(sc_core::sc_module_name const& name) + : sc_module(name) + , local_irq_i{"local_irq_i", 16} + , elf_file{"elf_file", ""} + , enable_disass{"enable_disass", false} + , reset_address{"reset_address", 0ULL} + , core_type{"core_type", "tgc_c"} + , backend{"backend", "interp"} + , gdb_server_port{"gdb_server_port", 0} + , dump_ir{"dump_ir", false} + , mhartid{"mhartid", 0} + , read_lut(tlm_dmi_ext()) + , write_lut(tlm_dmi_ext()) + { + init(); + } + +#endif ~core_complex(); @@ -119,11 +165,12 @@ public: bool disass_output(uint64_t pc, const std::string instr); + void set_clock_period(sc_core::sc_time period); protected: void before_end_of_elaboration() override; void start_of_simulation() override; + void forward(); void run(); - void clk_cb(); void rst_cb(); void sw_irq_cb(); void timer_irq_cb(); @@ -132,12 +179,14 @@ protected: util::range_lut read_lut, write_lut; tlm_utils::tlm_quantumkeeper quantum_keeper; std::vector write_buf; - std::unique_ptr cpu; - sc_core::sc_time curr_clk; - std::unique_ptr trc; + core_wrapper* cpu{nullptr}; + sc_core::sc_signal curr_clk; + core_trace* trc{nullptr}; + std::unique_ptr t2t; +private: + void init(); }; - } /* namespace SiFive */ } /* namespace sysc */ -#endif /* _SYSC_SIFIVE_FE310_H_ */ +#endif /* _SYSC_CORE_COMPLEX_H_ */ diff --git a/src/sysc/core_complex.cpp b/src/sysc/core_complex.cpp index 7775d34..622b1f8 100644 --- a/src/sysc/core_complex.cpp +++ b/src/sysc/core_complex.cpp @@ -66,6 +66,12 @@ if (type == STR(CN)) { std::tie(cpu, vm) = create_core(backend using namespace scv_tr; #endif +#ifndef CWR_SYSTEMC +#define GET_PROP_VALUE(P) P.get_value() +#else +#define GET_PROP_VALUE(P) P.getValue() +#endif + namespace sysc { namespace tgfs { using namespace std; @@ -137,6 +143,7 @@ public: } status read_csr(unsigned addr, reg_t &val) override { +#ifndef CWR_SYSTEMC if((addr==arch::time || addr==arch::timeh) && owner->mtime_o.get_interface(0)){ uint64_t time_val; bool ret = owner->mtime_o->nb_peek(time_val); @@ -147,6 +154,17 @@ public: val = static_cast(time_val >> 32); } return ret?Ok:Err; +#else + if((addr==arch::time || addr==arch::timeh)){ + uint64_t time_val = owner->mtime_i.read(); + if (addr == iss::arch::time) { + val = static_cast(time_val); + } else if (addr == iss::arch::timeh) { + if (sizeof(reg_t) != 4) return iss::Err; + val = static_cast(time_val >> 32); + } + return Ok; +#endif } else { return PLAT::read_csr(addr, val); } @@ -297,13 +315,19 @@ struct core_trace { scv_tr_handle tr_handle; }; +SC_HAS_PROCESS(core_complex);// NOLINT +#ifndef CWR_SYSTEMC core_complex::core_complex(sc_module_name name) : sc_module(name) , read_lut(tlm_dmi_ext()) , write_lut(tlm_dmi_ext()) -, trc(new core_trace) { - SC_HAS_PROCESS(core_complex);// NOLINT + init(); +} +#endif + +void core_complex::init(){ + trc=new core_trace(); initiator.register_invalidate_direct_mem_ptr([=](uint64_t start, uint64_t end) -> void { auto lut_entry = read_lut.getEntry(start); if (lut_entry.get_granted_access() != tlm::tlm_dmi::DMI_ACCESS_NONE && end <= lut_entry.get_end_address() + 1) { @@ -316,8 +340,6 @@ core_complex::core_complex(sc_module_name name) }); SC_THREAD(run); - SC_METHOD(clk_cb); - sensitive << clk_i; SC_METHOD(rst_cb); sensitive << rst_i; SC_METHOD(sw_irq_cb); @@ -327,29 +349,48 @@ core_complex::core_complex(sc_module_name name) SC_METHOD(global_irq_cb); sensitive << global_irq_i; trc->m_db=scv_tr_db::get_default_db(); + + SC_METHOD(forward); +#ifndef CWR_SYSTEMC + sensitive<clk_i(clk_i); + t2t->clk_o(curr_clk); +#endif } -core_complex::~core_complex() = default; +core_complex::~core_complex(){ + delete cpu; + delete trc; +} void core_complex::trace(sc_trace_file *trf) const {} void core_complex::before_end_of_elaboration() { - SCCDEBUG(SCMOD)<<"instantiating iss::arch::tgf with "<(this); - cpu->create_cpu(core_type.get_value(), backend.get_value(), gdb_server_port.get_value(), mhartid.get_value()); + SCCDEBUG(SCMOD)<<"instantiating iss::arch::tgf with "<(this); + cpu = new core_wrapper(this); + cpu->create_cpu(GET_PROP_VALUE(core_type), GET_PROP_VALUE(backend), GET_PROP_VALUE(gdb_server_port), GET_PROP_VALUE(mhartid)); sc_assert(cpu->vm!=nullptr); - cpu->vm->setDisassEnabled(enable_disass.get_value() || trc->m_db != nullptr); + cpu->vm->setDisassEnabled(GET_PROP_VALUE(enable_disass) || trc->m_db != nullptr); } void core_complex::start_of_simulation() { quantum_keeper.reset(); - if (elf_file.get_value().size() > 0) { - istringstream is(elf_file.get_value()); + if (GET_PROP_VALUE(elf_file).size() > 0) { + istringstream is(GET_PROP_VALUE(elf_file)); string s; while (getline(is, s, ',')) { std::pair start_addr = cpu->load_file(s); +#ifndef CWR_SYSTEMC if (reset_address.is_default_value() && start_addr.second == true) reset_address.set_value(start_addr.first); +#else + if (start_addr.second == true) + reset_address=start_addr.first; +#endif } } if (trc->m_db != nullptr && trc->stream_handle == nullptr) { @@ -371,9 +412,18 @@ bool core_complex::disass_output(uint64_t pc, const std::string instr_str) { return true; } -void core_complex::clk_cb() { - curr_clk = clk_i.read(); - if (curr_clk == SC_ZERO_TIME) cpu->set_interrupt_execution(true); +void core_complex::forward() { +#ifndef CWR_SYSTEMC + set_clock_period(clk_i.read()); +#else + set_clock_period(curr_clk.read()); + +#endif +} + +void core_complex::set_clock_period(sc_core::sc_time period) { + curr_clk = period; + if (period == SC_ZERO_TIME) cpu->set_interrupt_execution(true); } void core_complex::rst_cb() { @@ -390,11 +440,11 @@ void core_complex::run() { wait(SC_ZERO_TIME); // separate from elaboration phase do { if (rst_i.read()) { - cpu->reset(reset_address.get_value()); + cpu->reset(GET_PROP_VALUE(reset_address)); wait(rst_i.negedge_event()); } - while (clk_i.read() == SC_ZERO_TIME) { - wait(clk_i.value_changed_event()); + while (curr_clk.read() == SC_ZERO_TIME) { + wait(curr_clk.value_changed_event()); } cpu->set_interrupt_execution(false); cpu->start(); @@ -531,6 +581,5 @@ bool core_complex::write_mem_dbg(uint64_t addr, unsigned length, const uint8_t * return initiator->transport_dbg(gp) == length; } } - } /* namespace SiFive */ } /* namespace sysc */