Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion builder/build.go
Original file line number Diff line number Diff line change
Expand Up @@ -1094,7 +1094,7 @@ func Build(pkgName, outpath, tmpdir string, config *compileopts.Config) (BuildRe
if err != nil {
return result, err
}
case "esp32", "esp32-img", "esp32c3", "esp32s3", "esp32c6", "esp8266":
case "esp32", "esp32-img", "esp32c3", "esp32s3", "esp32c6", "esp32h2", "esp8266":
// Special format for the ESP family of chips (parsed by the ROM
// bootloader).
result.Binary = filepath.Join(tmpdir, "main"+outext)
Expand Down
1 change: 1 addition & 0 deletions builder/builder_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ func TestClangAttributes(t *testing.T) {
"cortex-m7",
"esp32c3",
"esp32c6",
"esp32h2",
"esp32s3",
"fe310",
"gameboy-advance",
Expand Down
4 changes: 3 additions & 1 deletion builder/esp.go
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,7 @@ func makeESPFirmwareImage(infile, outfile, format string) error {
"esp32": 0x0000,
"esp32c3": 0x0005,
"esp32c6": 0x000d,
"esp32h2": 0x0010,
"esp32s3": 0x0009,
}[chip]

Expand All @@ -180,12 +181,13 @@ func makeESPFirmwareImage(infile, outfile, format string) error {
"esp32": 0x1f, // 80MHz=0x0F, 2MB=0x10
"esp32c3": 0x1f, // 80MHz=0x0F, 2MB=0x10
"esp32c6": 0x10, // 80MHz=0x00, 2MB=0x10 (C6 uses different freq encoding)
"esp32h2": 0x1f, // 48MHz=0x0F, 2MB=0x10
"esp32s3": 0x1f, // 80MHz=0x0F, 2MB=0x10
}[chip]

// Image header.
switch chip {
case "esp32", "esp32c3", "esp32s3", "esp32c6":
case "esp32", "esp32c3", "esp32s3", "esp32c6", "esp32h2":
// Header format:
// https://github.com/espressif/esp-idf/blob/v4.3/components/bootloader_support/include/esp_app_format.h#L71
// Note: not adding a SHA256 hash as the binary is modified by
Expand Down
5 changes: 5 additions & 0 deletions make/smoketest.mk
Original file line number Diff line number Diff line change
Expand Up @@ -510,6 +510,11 @@ ifneq ($(XTENSA), 0)
@$(MD5SUM) $(SMOKE_OUT).bin
$(TINYGO) build -size short -o $(SMOKE_OUT).bin -target=xiao-esp32c6 examples/blinkm
@$(MD5SUM) $(SMOKE_OUT).bin
# esp32h2-devkitm-1
$(TINYGO) build -size short -o $(SMOKE_OUT).bin -target=esp32h2-devkitm-1 examples/machinetest
@$(MD5SUM) $(SMOKE_OUT).bin
$(TINYGO) build -size short -o $(SMOKE_OUT).bin -target=esp32h2-devkitm-1 examples/serial
@$(MD5SUM) $(SMOKE_OUT).bin
# xiao-esp32s3
$(TINYGO) build -size short -o $(SMOKE_OUT).bin -target=xiao-esp32s3 examples/blinky1
@$(MD5SUM) $(SMOKE_OUT).bin
Expand Down
15 changes: 8 additions & 7 deletions src/device/esp/esp32c6.S
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
// This is a very minimal bootloader for the ESP32-C6. It only initializes the
// flash and then continues with the generic RISC-V initialization code, which
// in turn will call runtime.main.
// This is a very minimal bootloader for the ESP32-C6 and ESP32-H2. It only
// initializes the flash and then continues with the generic RISC-V
// initialization code, which in turn will call runtime.main.
// It is written in assembly (and not in a higher level language) to make sure
// it is entirely loaded into IRAM and doesn't accidentally call functions
// stored in IROM.
//
// The ESP32-C6 has a unified IRAM/DRAM address space at 0x40800000, and
// separate DROM (0x42800000) / IROM (0x42000000) flash-mapped regions.
// The ESP32-C6 and ESP32-H2 have a unified IRAM/DRAM address space at
// 0x40800000, and separate DROM (0x42800000) / IROM (0x42000000) flash-mapped
// regions.

.section .init
.global call_start_cpu0
Expand All @@ -26,8 +27,8 @@ call_start_cpu0:
call Cache_MMU_Init

// Set up flash mapping (both IROM and DROM).
// On ESP32-C6, Cache_Dbus_MMU_Set is replaced by Cache_MSPI_MMU_Set
// which has an extra "sensitive" parameter.
// On ESP32-C6 and ESP32-H2, Cache_Dbus_MMU_Set is replaced by
// Cache_MSPI_MMU_Set which has an extra "sensitive" parameter.
// C equivalent:
// Cache_MSPI_MMU_Set(0, 0, 0x42000000, 0, 64, 256, 0)
// Maps 16MB starting at 0x42000000, covering both IROM and DROM.
Expand Down
23 changes: 23 additions & 0 deletions src/machine/board_esp32h2-devkitm-1.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
//go:build esp32h2_devkitm_1

// This file contains the pin mappings for the Espressif ESP32-H2-DevKitM-1 board.
//
// - https://docs.espressif.com/projects/esp-dev-kits/en/latest/esp32h2/esp32-h2-devkitm-1/user_guide.html

package machine

// Data pin of the onboard addressable RGB LED. The board has no plain LED.
const (
WS2812 = GPIO8
)

// BOOT button
const (
BUTTON = GPIO9
)

// UART pins
const (
UART_TX_PIN = GPIO24
UART_RX_PIN = GPIO23
)
28 changes: 14 additions & 14 deletions src/machine/machine_esp32c6_usb.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
//go:build esp32c6
//go:build esp32c6 || esp32h2

package machine

Expand All @@ -11,10 +11,10 @@ import (
)

// USB Serial/JTAG Controller
// The ESP32-C6 has the same built-in USB Serial/JTAG hardware IP as the
// ESP32-C3. The only difference at the machine level is how the peripheral
// clock is enabled: C3 uses SYSTEM.PERIP_CLK_EN0, while C6 uses the PCR
// (Peripheral Clock Reset) block.
// The ESP32-C6 and ESP32-H2 have the same built-in USB Serial/JTAG hardware IP
// as the ESP32-C3. The only difference at the machine level is how the
// peripheral clock is enabled: C3 uses SYSTEM.PERIP_CLK_EN0, while C6 and H2
// use the PCR (Peripheral Clock Reset) block.

const cpuInterruptFromUSB = 10

Expand Down Expand Up @@ -51,9 +51,9 @@ type Serialer interface {

var usbConfigured bool

// USBDevice provides a stub USB device for the ESP32-C6. The hardware
// only supports a fixed-function CDC-ACM serial port, so the programmable
// USB device features are no-ops.
// USBDevice provides a stub USB device for the ESP32-C6 and ESP32-H2. The
// hardware only supports a fixed-function CDC-ACM serial port, so the
// programmable USB device features are no-ops.
type USBDevice struct {
initcomplete bool
InitEndpointComplete bool
Expand Down Expand Up @@ -84,8 +84,8 @@ func (usbdev *USB_DEVICE) Configure(config UARTConfig) error {
}
usbConfigured = true

// Enable the USB_DEVICE peripheral clock via PCR (C6 uses PCR instead
// of SYSTEM.PERIP_CLK_EN0 that C3 used).
// Enable the USB_DEVICE peripheral clock via PCR (C6 and H2 use PCR
// instead of SYSTEM.PERIP_CLK_EN0 that C3 used).
esp.PCR.SetUSB_DEVICE_CONF_USB_DEVICE_CLK_EN(1)
esp.PCR.SetUSB_DEVICE_CONF_USB_DEVICE_RST_EN(0)

Expand Down Expand Up @@ -240,16 +240,16 @@ func FlushSerial() {
}
}

// ConfigureUSBEndpoint is a no-op on ESP32-C6 — the hardware does not
// support programmable USB endpoints.
// ConfigureUSBEndpoint is a no-op on ESP32-C6 and ESP32-H2. The hardware does
// not support programmable USB endpoints.
func ConfigureUSBEndpoint(desc descriptor.Descriptor, epSettings []usb.EndpointConfig, setup []usb.SetupConfig) {
}

// SendZlp is a no-op on ESP32-C6.
// SendZlp is a no-op on ESP32-C6 and ESP32-H2.
func SendZlp() {
}

// SendUSBInPacket is a no-op on ESP32-C6.
// SendUSBInPacket is a no-op on ESP32-C6 and ESP32-H2.
func SendUSBInPacket(ep uint32, data []byte) bool {
return false
}
Loading
Loading