diff options
author | Jerry Zhao <jerryz123@berkeley.edu> | 2022-10-25 11:37:44 -0700 |
---|---|---|
committer | Jerry Zhao <jerryz123@berkeley.edu> | 2022-10-25 11:49:33 -0700 |
commit | b265325d19fe9eb9145c65fe110735ff03c1b90c (patch) | |
tree | 5d1826b2eb8f1e0af019c7d1f833880da256f26a | |
parent | cefccba8cf1008691a1bb5d36bd318e281ffc635 (diff) | |
download | riscv-isa-sim-b265325d19fe9eb9145c65fe110735ff03c1b90c.zip riscv-isa-sim-b265325d19fe9eb9145c65fe110735ff03c1b90c.tar.gz riscv-isa-sim-b265325d19fe9eb9145c65fe110735ff03c1b90c.tar.bz2 |
Remove set_target_endianness | add --big-endian flag
Set target endianess in constructors
-rw-r--r-- | fesvr/elfloader.cc | 8 | ||||
-rw-r--r-- | fesvr/memif.h | 5 | ||||
-rw-r--r-- | riscv/cfg.h | 3 | ||||
-rw-r--r-- | riscv/mmu.cc | 7 | ||||
-rw-r--r-- | riscv/mmu.h | 11 | ||||
-rw-r--r-- | riscv/processor.cc | 3 | ||||
-rw-r--r-- | riscv/processor.h | 2 | ||||
-rw-r--r-- | riscv/sim.cc | 30 | ||||
-rw-r--r-- | riscv/sim.h | 1 | ||||
-rw-r--r-- | spike_main/spike-log-parser.cc | 2 | ||||
-rw-r--r-- | spike_main/spike.cc | 3 |
11 files changed, 35 insertions, 40 deletions
diff --git a/fesvr/elfloader.cc b/fesvr/elfloader.cc index 1bdccd3..7357b47 100644 --- a/fesvr/elfloader.cc +++ b/fesvr/elfloader.cc @@ -98,7 +98,9 @@ std::map<std::string, uint64_t> load_elf(const char* fn, memif_t* memif, reg_t* } while (0) if (IS_ELFLE(*eh64)) { - memif->set_target_endianness(memif_endianness_little); + if (memif->get_target_endianness() != memif_endianness_little) { + throw std::invalid_argument("Specified ELF is little endian, but system uses a big-endian memory system. Rerun without --big-endian"); + } if (IS_ELF32(*eh64)) LOAD_ELF(Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr, Elf32_Sym, from_le); else @@ -107,7 +109,9 @@ std::map<std::string, uint64_t> load_elf(const char* fn, memif_t* memif, reg_t* #ifndef RISCV_ENABLE_DUAL_ENDIAN throw std::invalid_argument("Specified ELF is big endian. Configure with --enable-dual-endian to enable support"); #else - memif->set_target_endianness(memif_endianness_big); + if (memif->get_target_endianness() != memif_endianness_big) { + throw std::invalid_argument("Specified ELF is big endian, but system uses a little-endian memory system. Rerun with --big-endian"); + } if (IS_ELF32(*eh64)) LOAD_ELF(Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr, Elf32_Sym, from_be); else diff --git a/fesvr/memif.h b/fesvr/memif.h index 7a005f2..e641d21 100644 --- a/fesvr/memif.h +++ b/fesvr/memif.h @@ -27,8 +27,6 @@ public: virtual size_t chunk_align() = 0; virtual size_t chunk_max_size() = 0; - virtual void set_target_endianness(memif_endianness_t) {} - virtual memif_endianness_t get_target_endianness() const { return memif_endianness_little; } @@ -71,9 +69,6 @@ public: virtual void write_int64(addr_t addr, target_endian<int64_t> val); // endianness - virtual void set_target_endianness(memif_endianness_t endianness) { - cmemif->set_target_endianness(endianness); - } virtual memif_endianness_t get_target_endianness() const { return cmemif->get_target_endianness(); } diff --git a/riscv/cfg.h b/riscv/cfg.h index dbdb58b..f0f88e4 100644 --- a/riscv/cfg.h +++ b/riscv/cfg.h @@ -61,6 +61,7 @@ public: const char *default_bootargs, const char *default_isa, const char *default_priv, const char *default_varch, + const memif_endianness_t default_endianness, const reg_t default_pmpregions, const std::vector<mem_cfg_t> &default_mem_layout, const std::vector<int> default_hartids, @@ -70,6 +71,7 @@ public: isa(default_isa), priv(default_priv), varch(default_varch), + endianness(default_endianness), pmpregions(default_pmpregions), mem_layout(default_mem_layout), hartids(default_hartids), @@ -82,6 +84,7 @@ public: cfg_arg_t<const char *> isa; cfg_arg_t<const char *> priv; cfg_arg_t<const char *> varch; + memif_endianness_t endianness; reg_t pmpregions; cfg_arg_t<std::vector<mem_cfg_t>> mem_layout; std::optional<reg_t> start_pc; diff --git a/riscv/mmu.cc b/riscv/mmu.cc index 3f9b5e9..a966180 100644 --- a/riscv/mmu.cc +++ b/riscv/mmu.cc @@ -5,16 +5,19 @@ #include "simif.h" #include "processor.h" -mmu_t::mmu_t(simif_t* sim, processor_t* proc) +mmu_t::mmu_t(simif_t* sim, memif_endianness_t endianness, processor_t* proc) : sim(sim), proc(proc), #ifdef RISCV_ENABLE_DUAL_ENDIAN - target_big_endian(false), + target_big_endian(endianness == memif_endianness_big), #endif check_triggers_fetch(false), check_triggers_load(false), check_triggers_store(false), matched_trigger(NULL) { +#ifndef RISCV_ENABLE_DUAL_ENDIAN + assert(endianness == memif_endianness_little); +#endif flush_tlb(); yield_load_reservation(); } diff --git a/riscv/mmu.h b/riscv/mmu.h index 19105e3..cee93e3 100644 --- a/riscv/mmu.h +++ b/riscv/mmu.h @@ -46,7 +46,7 @@ private: std::map<reg_t, reg_t> alloc_cache; std::vector<std::pair<reg_t, reg_t >> addr_tbl; public: - mmu_t(simif_t* sim, processor_t* proc); + mmu_t(simif_t* sim, memif_endianness_t endianness, processor_t* proc); ~mmu_t(); #define RISCV_XLATE_VIRT (1U << 0) @@ -298,15 +298,6 @@ public: #endif } - void set_target_big_endian(bool enable) - { -#ifdef RISCV_ENABLE_DUAL_ENDIAN - target_big_endian = enable; -#else - assert(enable == false); -#endif - } - bool is_target_big_endian() { return target_big_endian; diff --git a/riscv/processor.cc b/riscv/processor.cc index 9262199..f9a451e 100644 --- a/riscv/processor.cc +++ b/riscv/processor.cc @@ -29,6 +29,7 @@ processor_t::processor_t(const isa_parser_t *isa, const char* varch, simif_t* sim, uint32_t id, bool halt_on_reset, + memif_endianness_t endianness, FILE* log_file, std::ostream& sout_) : debug(false), halt_request(HR_NONE), isa(isa), sim(sim), id(id), xlen(0), histogram_enabled(false), log_commits_enabled(false), @@ -48,7 +49,7 @@ processor_t::processor_t(const isa_parser_t *isa, const char* varch, parse_varch_string(varch); register_base_instructions(); - mmu = new mmu_t(sim, this); + mmu = new mmu_t(sim, endianness, this); disassembler = new disassembler_t(isa); for (auto e : isa->get_extensions()) diff --git a/riscv/processor.h b/riscv/processor.h index 95043ea..06a92b1 100644 --- a/riscv/processor.h +++ b/riscv/processor.h @@ -16,6 +16,7 @@ #include "csrs.h" #include "isa_parser.h" #include "triggers.h" +#include "memif.h" class processor_t; class mmu_t; @@ -225,6 +226,7 @@ class processor_t : public abstract_device_t public: processor_t(const isa_parser_t *isa, const char* varch, simif_t* sim, uint32_t id, bool halt_on_reset, + memif_endianness_t endianness, FILE *log_file, std::ostream& sout_); // because of command line option --log and -s we need both ~processor_t(); diff --git a/riscv/sim.cc b/riscv/sim.cc index 71ac452..ffb20e4 100644 --- a/riscv/sim.cc +++ b/riscv/sim.cc @@ -74,11 +74,21 @@ sim_t::sim_t(const cfg_t *cfg, bool halted, debug_module.add_device(&bus); - debug_mmu = new mmu_t(this, NULL); +#ifndef RISCV_ENABLE_DUAL_ENDIAN + if (cfg->endianness != memif_endianness_little) { + fputs("Big-endian support has not been prroperly enabled; " + "please rebuild the riscv-isa-sim project using " + "\"configure --enable-dual-endian\".\n", + stderr); + abort(); + } +#endif + + debug_mmu = new mmu_t(this, cfg->endianness, NULL); for (size_t i = 0; i < cfg->nprocs(); i++) { procs[i] = new processor_t(&isa, cfg->varch(), this, cfg->hartids()[i], halted, - log_file.get(), sout_); + cfg->endianness, log_file.get(), sout_); } make_dtb(); @@ -432,22 +442,6 @@ void sim_t::write_chunk(addr_t taddr, size_t len, const void* src) debug_mmu->store<uint64_t>(taddr, debug_mmu->from_target(data)); } -void sim_t::set_target_endianness(memif_endianness_t endianness) -{ -#ifdef RISCV_ENABLE_DUAL_ENDIAN - assert(endianness == memif_endianness_little || endianness == memif_endianness_big); - - bool enable = endianness == memif_endianness_big; - debug_mmu->set_target_big_endian(enable); - for (size_t i = 0; i < procs.size(); i++) { - procs[i]->get_mmu()->set_target_big_endian(enable); - procs[i]->reset(); - } -#else - assert(endianness == memif_endianness_little); -#endif -} - memif_endianness_t sim_t::get_target_endianness() const { return debug_mmu->is_target_big_endian()? memif_endianness_big : memif_endianness_little; diff --git a/riscv/sim.h b/riscv/sim.h index a2ffeee..8ca06fe 100644 --- a/riscv/sim.h +++ b/riscv/sim.h @@ -166,7 +166,6 @@ private: void write_chunk(addr_t taddr, size_t len, const void* src); size_t chunk_align() { return 8; } size_t chunk_max_size() { return 8; } - void set_target_endianness(memif_endianness_t endianness); memif_endianness_t get_target_endianness() const; public: diff --git a/spike_main/spike-log-parser.cc b/spike_main/spike-log-parser.cc index 10a3209..efe6955 100644 --- a/spike_main/spike-log-parser.cc +++ b/spike_main/spike-log-parser.cc @@ -28,7 +28,7 @@ int main(int UNUSED argc, char** argv) parser.parse(argv); isa_parser_t isa(isa_string, DEFAULT_PRIV); - processor_t p(&isa, DEFAULT_VARCH, 0, 0, false, nullptr, cerr); + processor_t p(&isa, DEFAULT_VARCH, 0, 0, false, memif_endianness_little, nullptr, cerr); if (extension) { p.register_extension(extension()); } diff --git a/spike_main/spike.cc b/spike_main/spike.cc index 20afac9..3d9da02 100644 --- a/spike_main/spike.cc +++ b/spike_main/spike.cc @@ -44,6 +44,7 @@ static void help(int exit_code = 1) fprintf(stderr, " --ic=<S>:<W>:<B> Instantiate a cache model with S sets,\n"); fprintf(stderr, " --dc=<S>:<W>:<B> W ways, and B-byte blocks (with S and\n"); fprintf(stderr, " --l2=<S>:<W>:<B> B both powers of 2).\n"); + fprintf(stderr, " --big-endian Use a big-endian memory system.\n"); fprintf(stderr, " --device=<P,B,A> Attach MMIO plugin device from an --extlib library\n"); fprintf(stderr, " P -- Name of the MMIO plugin\n"); fprintf(stderr, " B -- Base memory address of the device\n"); @@ -287,6 +288,7 @@ int main(int argc, char** argv) /*default_isa=*/DEFAULT_ISA, /*default_priv=*/DEFAULT_PRIV, /*default_varch=*/DEFAULT_VARCH, + /*default_endianness*/memif_endianness_little, /*default_pmpregions=*/16, /*default_mem_layout=*/parse_mem_layout("2048"), /*default_hartids=*/std::vector<int>(), @@ -357,6 +359,7 @@ int main(int argc, char** argv) parser.option(0, "ic", 1, [&](const char* s){ic.reset(new icache_sim_t(s));}); parser.option(0, "dc", 1, [&](const char* s){dc.reset(new dcache_sim_t(s));}); parser.option(0, "l2", 1, [&](const char* s){l2.reset(cache_sim_t::construct(s, "L2$"));}); + parser.option(0, "big-endian", 0, [&](const char UNUSED *s){cfg.endianness = memif_endianness_big;}); parser.option(0, "log-cache-miss", 0, [&](const char UNUSED *s){log_cache = true;}); parser.option(0, "isa", 1, [&](const char* s){cfg.isa = s;}); parser.option(0, "pmpregions", 1, [&](const char* s){cfg.pmpregions = atoul_safe(s);}); |