Skip to content

Commit 4378f51

Browse files
committed
Fixes after the review
1 parent c0177c8 commit 4378f51

14 files changed

Lines changed: 67 additions & 211 deletions

File tree

locale/circuitpython.pot

Lines changed: 1 addition & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -647,10 +647,6 @@ msgstr ""
647647
msgid "Baudrate not supported by peripheral"
648648
msgstr ""
649649

650-
#: ports/espressif/common-hal/qspibus/QSPIBus.c
651-
msgid "Begin transaction first"
652-
msgstr ""
653-
654650
#: shared-module/busdisplay/BusDisplay.c
655651
#: shared-module/framebufferio/FramebufferDisplay.c
656652
msgid "Below minimum frame rate"
@@ -717,10 +713,6 @@ msgstr ""
717713
msgid "Buffer too small"
718714
msgstr ""
719715

720-
#: ports/espressif/common-hal/qspibus/QSPIBus.c
721-
msgid "Bus in display transaction"
722-
msgstr ""
723-
724716
#: ports/atmel-samd/common-hal/paralleldisplaybus/ParallelBus.c
725717
#: ports/espressif/common-hal/paralleldisplaybus/ParallelBus.c
726718
#: ports/nordic/common-hal/paralleldisplaybus/ParallelBus.c
@@ -1253,6 +1245,7 @@ msgstr ""
12531245
msgid "Internal define error"
12541246
msgstr ""
12551247

1248+
#: ports/espressif/common-hal/qspibus/QSPIBus.c
12561249
#: shared-bindings/pwmio/PWMOut.c supervisor/shared/settings.c
12571250
msgid "Internal error"
12581251
msgstr ""
@@ -1611,10 +1604,6 @@ msgstr ""
16111604
msgid "No out in program"
16121605
msgstr ""
16131606

1614-
#: ports/espressif/common-hal/qspibus/QSPIBus.c
1615-
msgid "No pending command"
1616-
msgstr ""
1617-
16181607
#: ports/atmel-samd/common-hal/busio/I2C.c
16191608
#: ports/espressif/common-hal/busio/I2C.c
16201609
#: ports/mimxrt10xx/common-hal/busio/I2C.c ports/nordic/common-hal/busio/I2C.c

ports/espressif/boards/waveshare_esp32_s3_amoled_241/board.c

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
#include "supervisor/board.h"
66
#include "mpconfigboard.h"
77
#include "shared-bindings/microcontroller/Pin.h"
8+
#include "shared-bindings/digitalio/DigitalInOut.h"
89

910
#include "shared-bindings/qspibus/QSPIBus.h"
1011
#include "shared-bindings/busdisplay/BusDisplay.h"
@@ -42,6 +43,15 @@ static uint8_t display_init_sequence[] = {
4243
};
4344

4445
void board_init(void) {
46+
// 0. Enable display power before any bus/display init.
47+
digitalio_digitalinout_obj_t power_pin;
48+
power_pin.base.type = &digitalio_digitalinout_type;
49+
common_hal_digitalio_digitalinout_construct(&power_pin, CIRCUITPY_LCD_POWER);
50+
common_hal_digitalio_digitalinout_set_value(&power_pin, true);
51+
common_hal_digitalio_digitalinout_never_reset(&power_pin);
52+
// Allow power rail to settle before reset/init.
53+
mp_hal_delay_ms(200);
54+
4555
// 1. Allocate and construct QSPI bus
4656
qspibus_qspibus_obj_t *bus = &allocate_display_bus_or_raise()->qspi_bus;
4757
bus->base.type = &qspibus_qspibus_type;

ports/espressif/boards/waveshare_esp32_s3_amoled_241/mpconfigboard.h

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -7,19 +7,13 @@
77
#define MICROPY_HW_BOARD_NAME "Waveshare ESP32-S3-Touch-AMOLED-2.41"
88
#define MICROPY_HW_MCU_NAME "ESP32S3"
99

10-
// USB identifiers
11-
#define USB_VID 0x303A
12-
#define USB_PID 0x8278
13-
#define USB_MANUFACTURER "Waveshare"
14-
#define USB_PRODUCT "ESP32-S3-Touch-AMOLED-2.41"
15-
1610
// I2C bus - Disabled on boot to avoid conflicts. User must manually initialize I2C.
1711
#define CIRCUITPY_BOARD_I2C (0)
1812
#define CIRCUITPY_BOARD_I2C_PIN {{.scl = &pin_GPIO48, .sda = &pin_GPIO47}}
1913

20-
// QSPI display refresh buffer: 2048 uint32_t words = 8KB on stack.
14+
// Display refresh buffer: 2048 uint32_t words = 8KB on stack.
2115
// ESP32-S3 main task stack is 24KB; verified safe with this board.
22-
#define CIRCUITPY_QSPI_DISPLAY_AREA_BUFFER_SIZE (2048)
16+
#define CIRCUITPY_DISPLAY_AREA_BUFFER_SIZE (2048)
2317

2418
// AMOLED Display (displayio + qspibus path) - initialized in board_init()
2519
#define CIRCUITPY_BOARD_DISPLAY (1)
@@ -31,7 +25,6 @@
3125
#define CIRCUITPY_LCD_D3 (&pin_GPIO14)
3226
#define CIRCUITPY_LCD_RESET (&pin_GPIO21)
3327
#define CIRCUITPY_LCD_POWER (&pin_GPIO16)
34-
#define CIRCUITPY_LCD_POWER_ON_LEVEL (1) // GPIO level: 1=high, 0=low
3528

3629
// No default SPI bus — SD card uses SDIO, display uses QSPI.
3730
#define CIRCUITPY_BOARD_SPI (0)

ports/espressif/boards/waveshare_esp32_s3_amoled_241/mpconfigboard.mk

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,6 @@
22
# SPDX-FileCopyrightText: Copyright (c) 2026 Przemyslaw Patrick Socha
33
# SPDX-License-Identifier: MIT
44

5-
CIRCUITPY_CREATOR_ID = 0x57415645 # 'WAVE' (Waveshare)
6-
CIRCUITPY_CREATION_ID = 0x41323431 # 'A241' (AMOLED 2.41)
7-
85
USB_VID = 0x303A
96
USB_PID = 0x8278
107
USB_MANUFACTURER = "Waveshare"
Lines changed: 0 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -1,39 +1,3 @@
11
#
22
# Configuration file for the Waveshare ESP32-S3 Touch AMOLED 2.41
33
#
4-
5-
# PSRAM Configuration
6-
CONFIG_SPIRAM=y
7-
CONFIG_SPIRAM_BOOT_INIT=y
8-
CONFIG_SPIRAM_USE_MALLOC=y
9-
CONFIG_SPIRAM_MODE_OCT=y
10-
CONFIG_SPIRAM_FETCH_INSTRUCTIONS=y
11-
CONFIG_SPIRAM_RODATA=y
12-
CONFIG_SPIRAM_SPEED_80M=y
13-
CONFIG_SPIRAM_MEMTEST=n
14-
CONFIG_SPIRAM_CLK_IO=39
15-
CONFIG_SPIRAM_CS_IO=38
16-
17-
# Performance and Cache
18-
CONFIG_ESP_DEFAULT_CPU_FREQ_MHZ_240=y
19-
CONFIG_ESP32S3_DATA_CACHE_LINE_64B=y
20-
21-
# Default flash settings for this board
22-
CONFIG_ESPTOOLPY_FLASHSIZE_16MB=y
23-
CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="esp-idf-config/partitions-16MB.csv"
24-
CONFIG_PARTITION_TABLE_FILENAME="esp-idf-config/partitions-16MB.csv"
25-
26-
# Networking
27-
CONFIG_LWIP_LOCAL_HOSTNAME="waveshare-esp32-s3-amoled"
28-
29-
# Disable USB-Serial/JTAG console - CircuitPython uses TinyUSB (USB OTG) for REPL
30-
CONFIG_ESP_CONSOLE_USB_SERIAL_JTAG=n
31-
32-
# Workaround: NimBLE BLE_STATIC_TO_DYNAMIC=y (default in IDF 5.5.3) causes
33-
# ble_gap_vars to be a dynamically allocated pointer (NULL before ble_gap_init).
34-
# CircuitPython calls ble_gap_adv_active() before NimBLE init → NULL deref → bootloop.
35-
# Reverting to static allocation avoids the crash.
36-
CONFIG_BT_NIMBLE_STATIC_TO_DYNAMIC=n
37-
38-
# Enable .app_desc structure
39-
CONFIG_APP_RETRIEVE_LEN_ELF_SHA=16

ports/espressif/common-hal/qspibus/QSPIBus.c

Lines changed: 16 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -25,14 +25,6 @@
2525
#define QSPI_DMA_BUFFER_COUNT (2U)
2626
#define QSPI_DMA_BUFFER_SIZE (16U * 1024U)
2727
#define QSPI_COLOR_TIMEOUT_MS (1000U)
28-
#if defined(CIRCUITPY_LCD_POWER)
29-
#define CIRCUITPY_QSPIBUS_PANEL_POWER_PIN CIRCUITPY_LCD_POWER
30-
#endif
31-
32-
#ifndef CIRCUITPY_LCD_POWER_ON_LEVEL
33-
#define CIRCUITPY_LCD_POWER_ON_LEVEL (1)
34-
#endif
35-
3628
static void qspibus_release_dma_buffers(qspibus_qspibus_obj_t *self) {
3729
for (size_t i = 0; i < QSPI_DMA_BUFFER_COUNT; i++) {
3830
if (self->dma_buffer[i] != NULL) {
@@ -279,7 +271,6 @@ void common_hal_qspibus_qspibus_construct(
279271
self->cs_pin = cs->number;
280272
self->dcx_pin = (dcx != NULL) ? dcx->number : -1;
281273
self->reset_pin = (reset != NULL) ? reset->number : -1;
282-
self->power_pin = -1;
283274
self->frequency = frequency;
284275
self->bus_initialized = false;
285276
self->in_transaction = false;
@@ -319,7 +310,7 @@ void common_hal_qspibus_qspibus_construct(
319310
qspibus_release_dma_buffers(self);
320311
vSemaphoreDelete(self->transfer_done_sem);
321312
self->transfer_done_sem = NULL;
322-
mp_raise_OSError_msg_varg(MP_ERROR_TEXT("%q failure: %d"), MP_QSTR_SPI, (int)err);
313+
mp_raise_ValueError_varg(MP_ERROR_TEXT("%q in use"), MP_QSTR_SPI);
323314
}
324315

325316
const esp_lcd_panel_io_spi_config_t io_config = {
@@ -358,21 +349,6 @@ void common_hal_qspibus_qspibus_construct(
358349
gpio_set_level((gpio_num_t)self->dcx_pin, 1);
359350
}
360351

361-
#ifdef CIRCUITPY_QSPIBUS_PANEL_POWER_PIN
362-
const mcu_pin_obj_t *power = CIRCUITPY_QSPIBUS_PANEL_POWER_PIN;
363-
if (power != NULL) {
364-
if (!common_hal_mcu_pin_is_free(power)) {
365-
mp_raise_ValueError_varg(MP_ERROR_TEXT("%q in use"), MP_QSTR_LCD_POWER);
366-
}
367-
self->power_pin = power->number;
368-
claim_pin(power);
369-
gpio_set_direction((gpio_num_t)self->power_pin, GPIO_MODE_OUTPUT);
370-
gpio_set_level((gpio_num_t)self->power_pin, CIRCUITPY_LCD_POWER_ON_LEVEL ? 1 : 0);
371-
// Panel power rail needs extra settle time before reset/init commands.
372-
vTaskDelay(pdMS_TO_TICKS(200));
373-
}
374-
#endif
375-
376352
if (reset != NULL) {
377353
claim_pin(reset);
378354

@@ -420,9 +396,6 @@ void common_hal_qspibus_qspibus_deinit(qspibus_qspibus_obj_t *self) {
420396
if (self->dcx_pin >= 0) {
421397
reset_pin_number(self->dcx_pin);
422398
}
423-
if (self->power_pin >= 0) {
424-
reset_pin_number(self->power_pin);
425-
}
426399
if (self->reset_pin >= 0) {
427400
reset_pin_number(self->reset_pin);
428401
}
@@ -446,7 +419,7 @@ void common_hal_qspibus_qspibus_write_command(
446419
raise_deinited_error();
447420
}
448421
if (self->in_transaction) {
449-
mp_raise_RuntimeError(MP_ERROR_TEXT("Bus in display transaction"));
422+
mp_raise_RuntimeError(MP_ERROR_TEXT("Internal error"));
450423
}
451424

452425
// If caller stages command-only operations repeatedly, flush the previous
@@ -467,7 +440,7 @@ void common_hal_qspibus_qspibus_write_data(
467440
raise_deinited_error();
468441
}
469442
if (self->in_transaction) {
470-
mp_raise_RuntimeError(MP_ERROR_TEXT("Bus in display transaction"));
443+
mp_raise_RuntimeError(MP_ERROR_TEXT("Internal error"));
471444
}
472445
if (len == 0) {
473446
if (self->has_pending_command) {
@@ -477,7 +450,7 @@ void common_hal_qspibus_qspibus_write_data(
477450
return;
478451
}
479452
if (!self->has_pending_command) {
480-
mp_raise_ValueError(MP_ERROR_TEXT("No pending command"));
453+
mp_raise_RuntimeError(MP_ERROR_TEXT("Internal error"));
481454
}
482455

483456
if (qspibus_is_color_payload_command(self->pending_command)) {
@@ -545,7 +518,7 @@ void common_hal_qspibus_qspibus_send(
545518
raise_deinited_error();
546519
}
547520
if (!self->in_transaction) {
548-
mp_raise_RuntimeError(MP_ERROR_TEXT("Begin transaction first"));
521+
mp_raise_RuntimeError(MP_ERROR_TEXT("Internal error"));
549522
}
550523

551524
if (data_type == DISPLAY_COMMAND) {
@@ -564,7 +537,7 @@ void common_hal_qspibus_qspibus_send(
564537
// Zero-length data write after a no-data command is benign.
565538
return;
566539
}
567-
mp_raise_ValueError(MP_ERROR_TEXT("No pending command"));
540+
mp_raise_RuntimeError(MP_ERROR_TEXT("Internal error"));
568541
}
569542

570543
if (data_length == 0) {
@@ -593,6 +566,16 @@ void common_hal_qspibus_qspibus_end_transaction(mp_obj_t obj) {
593566
self->in_transaction = false;
594567
}
595568

569+
void common_hal_qspibus_qspibus_flush(mp_obj_t obj) {
570+
qspibus_qspibus_obj_t *self = MP_OBJ_TO_PTR(obj);
571+
if (!self->bus_initialized) {
572+
return;
573+
}
574+
if (!qspibus_wait_all_transfers_done(self, pdMS_TO_TICKS(QSPI_COLOR_TIMEOUT_MS))) {
575+
qspibus_reset_transfer_state(self);
576+
}
577+
}
578+
596579
void common_hal_qspibus_qspibus_collect_ptrs(mp_obj_t obj) {
597580
(void)obj;
598581
}

ports/espressif/common-hal/qspibus/QSPIBus.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,6 @@ typedef struct {
3333
int8_t cs_pin;
3434
int8_t dcx_pin; // -1 when optional DCX line is not provided.
3535
int8_t reset_pin; // -1 when reset line is not provided.
36-
int8_t power_pin; // -1 when board has no explicit display power pin.
3736

3837
uint32_t frequency;
3938
bool bus_initialized;

py/circuitpy_mpconfig.h

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -394,25 +394,13 @@ typedef long mp_off_t;
394394
#define CIRCUITPY_DISPLAY_LIMIT (1)
395395
#endif
396396

397-
// Framebuffer area size in bytes. Rounded down to power of four for alignment.
397+
// Display area buffer size in uint32_t words for _refresh_area() VLA.
398+
// Allocated on stack; boards with larger displays can override per-board.
399+
// Default 128 words = 512 bytes.
398400
#ifndef CIRCUITPY_DISPLAY_AREA_BUFFER_SIZE
399401
#define CIRCUITPY_DISPLAY_AREA_BUFFER_SIZE (128)
400402
#endif
401403

402-
// QSPI display buffer size in uint32_t words for _refresh_area() VLA.
403-
// Allocated on stack; boards should verify sufficient stack headroom.
404-
// Default 512 words = 2KB. Override per-board for larger buffers.
405-
#ifndef CIRCUITPY_QSPI_DISPLAY_AREA_BUFFER_SIZE
406-
#define CIRCUITPY_QSPI_DISPLAY_AREA_BUFFER_SIZE (512)
407-
#endif
408-
409-
// Port-level upper bound for the QSPI display buffer (uint32_t words).
410-
// The _Static_assert in BusDisplay.c enforces this at compile time.
411-
// Ports with larger stacks can raise this in mpconfigport.h.
412-
#ifndef CIRCUITPY_QSPI_DISPLAY_AREA_BUFFER_SIZE_MAX
413-
#define CIRCUITPY_QSPI_DISPLAY_AREA_BUFFER_SIZE_MAX (2048)
414-
#endif
415-
416404
#else
417405
#define CIRCUITPY_DISPLAY_LIMIT (0)
418406
#define CIRCUITPY_DISPLAY_AREA_BUFFER_SIZE (0)

shared-bindings/displayio/__init__.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,4 +49,5 @@ typedef bool (*display_bus_begin_transaction)(mp_obj_t bus);
4949
typedef void (*display_bus_send)(mp_obj_t bus, display_byte_type_t byte_type,
5050
display_chip_select_behavior_t chip_select, const uint8_t *data, uint32_t data_length);
5151
typedef void (*display_bus_end_transaction)(mp_obj_t bus);
52+
typedef void (*display_bus_flush)(mp_obj_t bus);
5253
typedef void (*display_bus_collect_ptrs)(mp_obj_t bus);

shared-bindings/qspibus/QSPIBus.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,4 +49,5 @@ void common_hal_qspibus_qspibus_send(
4949
const uint8_t *data,
5050
uint32_t data_length);
5151
void common_hal_qspibus_qspibus_end_transaction(mp_obj_t obj);
52+
void common_hal_qspibus_qspibus_flush(mp_obj_t obj);
5253
void common_hal_qspibus_qspibus_collect_ptrs(mp_obj_t obj);

0 commit comments

Comments
 (0)