From 45a6b03d404c7a43766e94661f43036d9528511d Mon Sep 17 00:00:00 2001 From: Hierophect Date: Tue, 3 Dec 2019 15:30:12 -0500 Subject: [PATCH] copy from busted branch --- .../common-hal/digitalio/DigitalInOut.c | 6 +++--- .../common-hal/neopixel_write/__init__.c | 20 ++++++++++++++----- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/ports/stm32f4/common-hal/digitalio/DigitalInOut.c b/ports/stm32f4/common-hal/digitalio/DigitalInOut.c index 51b1fde738..36c1075e23 100644 --- a/ports/stm32f4/common-hal/digitalio/DigitalInOut.c +++ b/ports/stm32f4/common-hal/digitalio/DigitalInOut.c @@ -47,7 +47,7 @@ digitalinout_result_t common_hal_digitalio_digitalinout_construct( GPIO_InitStruct.Pin = pin_mask(self->pin->number); GPIO_InitStruct.Mode = GPIO_MODE_INPUT; GPIO_InitStruct.Pull = GPIO_NOPULL; - GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW; + GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH; HAL_GPIO_Init(pin_port(self->pin->port), &GPIO_InitStruct); return DIGITALINOUT_OK; @@ -73,7 +73,7 @@ void common_hal_digitalio_digitalinout_switch_to_input( GPIO_InitStruct.Pin = pin_mask(self->pin->number); GPIO_InitStruct.Mode = GPIO_MODE_INPUT; GPIO_InitStruct.Pull = GPIO_NOPULL; - GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW; + GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH; HAL_GPIO_Init(pin_port(self->pin->port), &GPIO_InitStruct); common_hal_digitalio_digitalinout_set_pull(self, pull); @@ -114,7 +114,7 @@ void common_hal_digitalio_digitalinout_set_drive_mode( GPIO_InitStruct.Mode = (drive_mode == DRIVE_MODE_OPEN_DRAIN ? GPIO_MODE_OUTPUT_OD : GPIO_MODE_OUTPUT_PP); GPIO_InitStruct.Pull = GPIO_NOPULL; - GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW; + GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH; HAL_GPIO_Init(pin_port(self->pin->port), &GPIO_InitStruct); } diff --git a/ports/stm32f4/common-hal/neopixel_write/__init__.c b/ports/stm32f4/common-hal/neopixel_write/__init__.c index fd46825d03..23fe7870f5 100644 --- a/ports/stm32f4/common-hal/neopixel_write/__init__.c +++ b/ports/stm32f4/common-hal/neopixel_write/__init__.c @@ -28,6 +28,8 @@ #include "shared-bindings/neopixel_write/__init__.h" #include "tick.h" +#include "py/mperrno.h" +#include "py/runtime.h" #include "common-hal/microcontroller/Pin.h" #include "stm32f4xx_hal.h" #include "stm32f4xx_ll_gpio.h" @@ -40,6 +42,9 @@ uint32_t next_start_tick_us = 1000; #define MAGIC_800_T0H 2800000 // ~0.36 us -> 0.44 field #define MAGIC_800_T1H 1350000 // ~0.74 us -> 0.84 field +#pragma GCC push_options +#pragma GCC optimize ("Os") + void common_hal_neopixel_write (const digitalio_digitalinout_obj_t* digitalinout, uint8_t *pixels, uint32_t numBytes) { uint8_t *p = pixels, *end = p + numBytes, pix = *p++, mask = 0x80; @@ -48,7 +53,7 @@ void common_hal_neopixel_write (const digitalio_digitalinout_obj_t* digitalinout //assumes 800_000Hz frequency //Theoretical values here are 800_000 -> 1.25us, 2500000->0.4us, 1250000->0.8us - //But they don't work, possibly due to bad optimization? Use tested magic values instead + //TODO: try to get dynamic weighting working again uint32_t sys_freq = HAL_RCC_GetSysClockFreq(); uint32_t interval = sys_freq/MAGIC_800_INT; uint32_t t0 = (sys_freq/MAGIC_800_T0H); @@ -63,23 +68,26 @@ void common_hal_neopixel_write (const digitalio_digitalinout_obj_t* digitalinout __disable_irq(); // Enable DWT in debug core. Useable when interrupts disabled, as opposed to Systick->VAL - //ITM->LAR = 0xC5ACCE55; //this should be required but isn't CoreDebug->DEMCR |= CoreDebug_DEMCR_TRCENA_Msk; DWT->CTRL |= DWT_CTRL_CYCCNTENA_Msk; DWT->CYCCNT = 0; for(;;) { + cyc = (pix & mask) ? t1 : t0; start = DWT->CYCCNT; LL_GPIO_SetOutputPin(p_port, p_mask); - cyc = (pix & mask) ? t1 : t0; - while(DWT->CYCCNT - start < cyc); + while((DWT->CYCCNT - start) < cyc) { + __asm__ __volatile__("nop"); + } LL_GPIO_ResetOutputPin(p_port, p_mask); + while((DWT->CYCCNT - start) < interval) { + __asm__ __volatile__("nop"); + } if(!(mask >>= 1)) { if(p >= end) break; pix = *p++; mask = 0x80; } - while(DWT->CYCCNT - start < interval); //wait for interval to finish } // Enable interrupts again @@ -94,3 +102,5 @@ void common_hal_neopixel_write (const digitalio_digitalinout_obj_t* digitalinout next_start_tick_us -= 100; } } + +#pragma GCC pop_options \ No newline at end of file