Skip to content
Snippets Groups Projects
Commit 1133e428 authored by davip00's avatar davip00
Browse files

Start work on ESP32 C3 board

parent 4329d049
No related branches found
No related tags found
No related merge requests found
...@@ -13,3 +13,4 @@ CONFIG_SIFIVE_E=y ...@@ -13,3 +13,4 @@ CONFIG_SIFIVE_E=y
CONFIG_SIFIVE_U=y CONFIG_SIFIVE_U=y
CONFIG_RISCV_VIRT=y CONFIG_RISCV_VIRT=y
CONFIG_OPENTITAN=y CONFIG_OPENTITAN=y
CONFIG_ESP32_C3=y
esp32/c3 Reference Platform (``esp32/c3``)
==========================================
...@@ -66,6 +66,7 @@ undocumented; you can get a complete list by running ...@@ -66,6 +66,7 @@ undocumented; you can get a complete list by running
.. toctree:: .. toctree::
:maxdepth: 1 :maxdepth: 1
riscv/esp32-c3
riscv/microchip-icicle-kit riscv/microchip-icicle-kit
riscv/shakti-c riscv/shakti-c
riscv/sifive_u riscv/sifive_u
......
...@@ -6,6 +6,9 @@ config IBEX ...@@ -6,6 +6,9 @@ config IBEX
# RISC-V machines in alphabetical order # RISC-V machines in alphabetical order
config ESP32_C3
bool
config MICROCHIP_PFSOC config MICROCHIP_PFSOC
bool bool
select CADENCE_SDHCI select CADENCE_SDHCI
......
/*
* ESP32-C3-class SoC emulation
*
* Copyright (c) 2023
* Davids Paskevics (davip00@zedat.fu-berlin.de)
* Nicolas Patzelt (nicolas.patzelt@fu-berlin.de)
* Jakob Knitter (jakok07@zedat.fu-berlin.de)
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2 or later, as published by the Free Software Foundation.
*
* This program is distributed in the hope 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.The 0x00001000 address is mapped to ROM with a trampoline code to 0x80000000. AUIPC instruction moves its immediate value 12 bits to the left and adds to the current PC , so t0 = 0(x7ffff<<12)+ 0x1000 = 0x80000000ww.gnu.org/licenses/>.
*/
#include "qemu/osdep.h"
#include "hw/boards.h"
#include "hw/riscv/esp32_c3.h"
#include "qapi/error.h"
#include "qemu/error-report.h"
#include "hw/intc/sifive_plic.h"
#include "hw/intc/riscv_aclint.h"
#include "sysemu/sysemu.h"
#include "hw/qdev-properties.h"
#include "exec/address-spaces.h"
#include "hw/riscv/boot.h"
static const struct MemmapEntry {
hwaddr base;
hwaddr size;
} esp32_c3_memmap[] = {
[ESP32_C3_DROM] = { 0x3FF00000, 0x1FFFF },
[ESP32_C3_IROM] = { 0x40000000, 0x5FFFF },
[ESP32_C3_IRAM] = { 0x4037C000, 0x63FFF },
[ESP32_C3_DRAM] = { 0x3FC80000, 0x5FFFF },
[ESP32_C3_DM] = { 0x20000000, 0x7FFFFFF }
};
static void esp32_c3_machine_state_init(MachineState *mstate)
{
Esp32C3MachineState *sms = RISCV_ESP32_MACHINE(mstate);
MemoryRegion *system_memory = get_system_memory();
/* Allow only ESP32 C3 CPU for this platform */
if (strcmp(mstate->cpu_type, TYPE_RISCV_CPU_ESP32_C3) != 0) {
error_report("This board can only be used with ESP32 C3 CPU");
exit(1);
}
/* Initialize SoC */
object_initialize_child(OBJECT(mstate), "soc", &sms->soc,
TYPE_RISCV_ESP32_SOC);
qdev_realize(DEVICE(&sms->soc), NULL, &error_abort);
/* register RAM */
// TODO: Deal with IRAM vs DRAM
memory_region_add_subregion(system_memory,
esp32_c3_memmap[ESP32_C3_IRAM].base,
mstate->ram);
/* ROM reset vector */
// TODO: Check if this is correct
// TODO: Does this make sense for our board? Code runs from ROM directly.
riscv_setup_rom_reset_vec(mstate, &sms->soc.cpus,
esp32_c3_memmap[ESP32_C3_IRAM].base,
esp32_c3_memmap[ESP32_C3_IROM].base,
esp32_c3_memmap[ESP32_C3_IROM].size, 0x0400, 0);
if (mstate->firmware) {
// We don't have any (separate) firmware to load, as this is an MCU
error_report("This board can't load firmware");
exit(1);
}
}
static void esp32_c3_machine_instance_init(Object *obj)
{
}
static void esp32_c3_machine_class_init(ObjectClass *klass, void *data)
{
MachineClass *mc = MACHINE_CLASS(klass);
mc->desc = "RISC-V Board compatible with ES32-C3 SDK";
mc->init = esp32_c3_machine_state_init;
mc->default_cpu_type = TYPE_RISCV_CPU_ESP32_C3;
mc->default_ram_id = "riscv.esp32.c.ram";
}
static const TypeInfo esp32_c3_machine_type_info = {
.name = TYPE_RISCV_ESP32_MACHINE,
.parent = TYPE_MACHINE,
.class_init = esp32_c3_machine_class_init,
.instance_init = esp32_c3_machine_instance_init,
.instance_size = sizeof(Esp32C3MachineState),
};
static void esp32_c3_machine_type_info_register(void)
{
type_register_static(&esp32_c3_machine_type_info);
}
type_init(esp32_c3_machine_type_info_register)
static void esp32_c3_soc_state_realize(DeviceState *dev, Error **errp)
{
MachineState *ms = MACHINE(qdev_get_machine());
(void)ms;
Esp32C3SoCState *sss = RISCV_ESP32_SOC(dev);
MemoryRegion *system_memory = get_system_memory();
sysbus_realize(SYS_BUS_DEVICE(&sss->cpus), &error_abort);
/* ROM */
// TODO: Deal with IROM vs DROM
memory_region_init_rom(&sss->rom, OBJECT(dev), "riscv.esp32.c.rom",
esp32_c3_memmap[ESP32_C3_IROM].size, &error_fatal);
memory_region_add_subregion(system_memory,
esp32_c3_memmap[ESP32_C3_IROM].base, &sss->rom);
}
static void esp32_c3_soc_class_init(ObjectClass *klass, void *data)
{
DeviceClass *dc = DEVICE_CLASS(klass);
dc->realize = esp32_c3_soc_state_realize;
/*
* Reasons:
* - Creates CPUS in riscv_hart_realize(), and can create unintended
* CPUs
* - Uses serial_hds in realize function, thus can't be used twice
*/
dc->user_creatable = false;
}
static void esp32_c3_soc_instance_init(Object *obj)
{
Esp32C3SoCState *sss = RISCV_ESP32_SOC(obj);
object_initialize_child(obj, "cpus", &sss->cpus, TYPE_RISCV_HART_ARRAY);
/*
* CPU type is fixed and we are not supporting passing from commandline yet.
* So let it be in instance_init. When supported should use ms->cpu_type
* instead of TYPE_RISCV_CPU_ESP32_C3
*/
object_property_set_str(OBJECT(&sss->cpus), "cpu-type",
TYPE_RISCV_CPU_ESP32_C3, &error_abort);
object_property_set_int(OBJECT(&sss->cpus), "num-harts", 1,
&error_abort);
}
static const TypeInfo esp32_c3_type_info = {
.name = TYPE_RISCV_ESP32_SOC,
.parent = TYPE_DEVICE,
.class_init = esp32_c3_soc_class_init,
.instance_init = esp32_c3_soc_instance_init,
.instance_size = sizeof(Esp32C3SoCState),
};
static void esp32_c3_type_info_register(void)
{
type_register_static(&esp32_c3_type_info);
}
type_init(esp32_c3_type_info_register)
...@@ -8,6 +8,7 @@ riscv_ss.add(when: 'CONFIG_SHAKTI_C', if_true: files('shakti_c.c')) ...@@ -8,6 +8,7 @@ riscv_ss.add(when: 'CONFIG_SHAKTI_C', if_true: files('shakti_c.c'))
riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c')) riscv_ss.add(when: 'CONFIG_SIFIVE_E', if_true: files('sifive_e.c'))
riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c')) riscv_ss.add(when: 'CONFIG_SIFIVE_U', if_true: files('sifive_u.c'))
riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c')) riscv_ss.add(when: 'CONFIG_SPIKE', if_true: files('spike.c'))
riscv_ss.add(when: 'CONFIG_ESP32_C3', if_true: files('esp32_c3.c'))
riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c')) riscv_ss.add(when: 'CONFIG_MICROCHIP_PFSOC', if_true: files('microchip_pfsoc.c'))
riscv_ss.add(when: 'CONFIG_ACPI', if_true: files('virt-acpi-build.c')) riscv_ss.add(when: 'CONFIG_ACPI', if_true: files('virt-acpi-build.c'))
......
/*
* ESP32-C3-class SoC emulation
*
* Copyright (c) 2023
* Davids Paskevics (davip00@zedat.fu-berlin.de)
* Nicolas Patzelt (nicolas.patzelt@fu-berlin.de)
* Jakob Knitter (jakok07@zedat.fu-berlin.de)
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2 or later, as published by the Free Software Foundation.
*
* This program is distributed in the hope 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.
*
* You should have received a copy of the GNU General Public License along with
* this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef HW_ESP32_C3_H
#define HW_ESP32_C3_H
#include "hw/riscv/riscv_hart.h"
#include "hw/boards.h"
#define TYPE_RISCV_ESP32_SOC "riscv.esp32.cclass.soc"
#define RISCV_ESP32_SOC(obj) \
OBJECT_CHECK(Esp32C3SoCState, (obj), TYPE_RISCV_ESP32_SOC)
typedef struct Esp32C3SoCState {
/*< private >*/
DeviceState parent_obj;
/*< public >*/
RISCVHartArrayState cpus;
DeviceState *plic;
MemoryRegion rom;
} Esp32C3SoCState;
#define TYPE_RISCV_ESP32_MACHINE MACHINE_TYPE_NAME("esp32_c3")
#define RISCV_ESP32_MACHINE(obj) \
OBJECT_CHECK(Esp32C3MachineState, (obj), TYPE_RISCV_ESP32_MACHINE)
typedef struct Esp32C3MachineState {
/*< private >*/
MachineState parent_obj;
/*< public >*/
Esp32C3SoCState soc;
} Esp32C3MachineState;
enum {
ESP32_C3_DROM,
ESP32_C3_IROM,
ESP32_C3_IRAM,
ESP32_C3_DRAM,
ESP32_C3_DM
};
#endif
...@@ -35,6 +35,7 @@ ...@@ -35,6 +35,7 @@
#define TYPE_RISCV_CPU_BASE128 RISCV_CPU_TYPE_NAME("x-rv128") #define TYPE_RISCV_CPU_BASE128 RISCV_CPU_TYPE_NAME("x-rv128")
#define TYPE_RISCV_CPU_IBEX RISCV_CPU_TYPE_NAME("lowrisc-ibex") #define TYPE_RISCV_CPU_IBEX RISCV_CPU_TYPE_NAME("lowrisc-ibex")
#define TYPE_RISCV_CPU_SHAKTI_C RISCV_CPU_TYPE_NAME("shakti-c") #define TYPE_RISCV_CPU_SHAKTI_C RISCV_CPU_TYPE_NAME("shakti-c")
#define TYPE_RISCV_CPU_ESP32_C3 RISCV_CPU_TYPE_NAME("esp32-c3")
#define TYPE_RISCV_CPU_SIFIVE_E31 RISCV_CPU_TYPE_NAME("sifive-e31") #define TYPE_RISCV_CPU_SIFIVE_E31 RISCV_CPU_TYPE_NAME("sifive-e31")
#define TYPE_RISCV_CPU_SIFIVE_E34 RISCV_CPU_TYPE_NAME("sifive-e34") #define TYPE_RISCV_CPU_SIFIVE_E34 RISCV_CPU_TYPE_NAME("sifive-e34")
#define TYPE_RISCV_CPU_SIFIVE_E51 RISCV_CPU_TYPE_NAME("sifive-e51") #define TYPE_RISCV_CPU_SIFIVE_E51 RISCV_CPU_TYPE_NAME("sifive-e51")
......
...@@ -520,6 +520,15 @@ static void rv32_sifive_u_cpu_init(Object *obj) ...@@ -520,6 +520,15 @@ static void rv32_sifive_u_cpu_init(Object *obj)
cpu->cfg.pmp = true; cpu->cfg.pmp = true;
} }
static void rv32_esp32_c3_cpu_init(Object *obj)
{
CPURISCVState *env = &RISCV_CPU(obj)->env;
set_misa(env, MXL_RV32, RVI | RVM | RVC);
#ifndef CONFIG_USER_ONLY
set_satp_mode_max_supported(RISCV_CPU(obj), VM_1_10_SV32);
#endif
}
static void rv32_sifive_e_cpu_init(Object *obj) static void rv32_sifive_e_cpu_init(Object *obj)
{ {
CPURISCVState *env = &RISCV_CPU(obj)->env; CPURISCVState *env = &RISCV_CPU(obj)->env;
...@@ -1938,6 +1947,7 @@ static const TypeInfo riscv_cpu_type_infos[] = { ...@@ -1938,6 +1947,7 @@ static const TypeInfo riscv_cpu_type_infos[] = {
DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E31, rv32_sifive_e_cpu_init), DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E31, rv32_sifive_e_cpu_init),
DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E34, rv32_imafcu_nommu_cpu_init), DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E34, rv32_imafcu_nommu_cpu_init),
DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_U34, rv32_sifive_u_cpu_init), DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_U34, rv32_sifive_u_cpu_init),
DEFINE_CPU(TYPE_RISCV_CPU_ESP32_C3, rv32_esp32_c3_cpu_init),
#elif defined(TARGET_RISCV64) #elif defined(TARGET_RISCV64)
DEFINE_DYNAMIC_CPU(TYPE_RISCV_CPU_BASE64, rv64_base_cpu_init), DEFINE_DYNAMIC_CPU(TYPE_RISCV_CPU_BASE64, rv64_base_cpu_init),
DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E51, rv64_sifive_e_cpu_init), DEFINE_CPU(TYPE_RISCV_CPU_SIFIVE_E51, rv64_sifive_e_cpu_init),
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment