Skip to content

Commit

Permalink
mimxrt: Combined files and changes for using the esp_hosted driver.
Browse files Browse the repository at this point in the history
At first with the board files for MIMXRT1020 only.

MIMXRT1010 does not build due to RAM shortage.

Signed-off-by: robert-hh <robert@hammelrath.com>
  • Loading branch information
robert-hh committed Sep 17, 2023
1 parent 5473200 commit 72cb34c
Show file tree
Hide file tree
Showing 16 changed files with 297 additions and 25 deletions.
1 change: 0 additions & 1 deletion drivers/esp-hosted/esp_hosted_wifi.c
Original file line number Diff line number Diff line change
Expand Up @@ -446,7 +446,6 @@ int esp_hosted_wifi_init(uint32_t itf) {
if (esp_hosted_hal_init(ESP_HOSTED_MODE_WIFI) != 0) {
return -1;
}

// Allow polling the bus.
esp_state.flags |= ESP_HOSTED_FLAGS_INIT;

Expand Down
2 changes: 1 addition & 1 deletion lib/mynewt-nimble
12 changes: 11 additions & 1 deletion ports/mimxrt/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -108,8 +108,9 @@ SRC_TINYUSB_C += \
lib/tinyusb/src/portable/chipidea/ci_hs/dcd_ci_hs.c \
lib/tinyusb/src/tusb.c

# All settings for Ethernet support are controller by the value of MICROPY_PY_LWIP
# All settings for Ethernet support are controller by the value of MICROPY_PY_LWIP and the supported MCUs
ifeq ($(MICROPY_PY_LWIP),1)
ifeq ($(MCU_SERIES),$(filter $(MCU_SERIES), MIMXRT1021 MIMXRT1052 MIMXRT1062 MIMXRT1064 MIMXRT1176))
SRC_ETH_C += \
$(MCU_DIR)/drivers/fsl_enet.c \
hal/phy/device/phydp83825/fsl_phydp83825.c \
Expand All @@ -119,6 +120,7 @@ SRC_ETH_C += \
hal/phy/device/phyrtl8211f/fsl_phyrtl8211f.c \
hal/phy/mdio/enet/fsl_enet_mdio.c
endif
endif

# NXP SDK sources
SRC_HAL_IMX_C += \
Expand Down Expand Up @@ -237,6 +239,14 @@ SHARED_SRC_C += \
shared/runtime/sys_stdio_mphal.c \
shared/timeutils/timeutils.c \

ifeq ($(MICROPY_PY_BLUETOOTH),1)
SRC_C += mpbthciport.c
endif

ifeq ($(MICROPY_BLUETOOTH_NIMBLE),1)
SRC_C += mpnimbleport.c
endif

# Set flash driver name, base address and internal flash flag, based on the flash type.
ifeq ($(MICROPY_HW_FLASH_TYPE),$(filter $(MICROPY_HW_FLASH_TYPE),qspi_nor_flash))
MICROPY_HW_FLASH_BASE = 0x60000000
Expand Down
2 changes: 2 additions & 0 deletions ports/mimxrt/boards/MIMXRT1020_EVK/manifest.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
include("../manifest.py")

require("bundle-networking")
# Bluetooth
require("aioble")
8 changes: 8 additions & 0 deletions ports/mimxrt/boards/MIMXRT1020_EVK/mbedtls_config_board.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
#ifndef MICROPY_INCLUDED_MBEDTLS_CONFIG_BOARD_H
#define MICROPY_INCLUDED_MBEDTLS_CONFIG_BOARD_H

#define MBEDTLS_ECP_NIST_OPTIM

#include "ports/mimxrt/mbedtls/mbedtls_config.h"

#endif /* MICROPY_INCLUDED_MBEDTLS_CONFIG_BOARD_H */
26 changes: 26 additions & 0 deletions ports/mimxrt/boards/MIMXRT1020_EVK/mpconfigboard.h
Original file line number Diff line number Diff line change
Expand Up @@ -185,3 +185,29 @@
{ IOMUXC_GPIO_AD_B0_15_ENET_TDATA01, 0, 0xB0E9u }, \
{ IOMUXC_GPIO_EMC_40_ENET_MDIO, 0, 0xB0E9u }, \
{ IOMUXC_GPIO_EMC_41_ENET_MDC, 0, 0xB0E9u },


// Bluetooth config.
#define MICROPY_HW_BLE_UART_ID (1)
// D11 pin_GPIO_AD_B0_12
#define MICROPY_HW_BLE_UART_RTS (&pin_GPIO_AD_B0_12)
#define MICROPY_HW_BLE_UART_BAUDRATE (460800)
#define MICROPY_HW_BLE_UART_BAUDRATE_SECONDARY (460800)

// WiFi config.
#define MICROPY_HW_WIFI_SPI_ID (0)
#define MICROPY_HW_WIFI_SPI_BAUDRATE (8 * 1000 * 1000)
// D10 pin_GPIO_AD_B0_11
#define MICROPY_HW_WIFI_SPI_CS (&pin_GPIO_AD_B0_11)
// D6 pin_GPIO_AD_B0_14
#define MICROPY_HW_WIFI_DATAREADY (&pin_GPIO_AD_B0_14)
// D7 pin_GPIO_AD_B1_06
#define MICROPY_HW_WIFI_HANDSHAKE (&pin_GPIO_AD_B1_06)

// ESP hosted control pins
// D5 pin_GPIO_AD_B0_06
#define MICROPY_HW_ESP_HOSTED_RESET (&pin_GPIO_AD_B0_06)
// D6 pin_GPIO_AD_B0_14
#define MICROPY_HW_ESP_HOSTED_GPIO0 (&pin_GPIO_AD_B0_14)

#define MICROPY_HW_ESP_HOSTED_SHARED_PINS (1)
11 changes: 11 additions & 0 deletions ports/mimxrt/boards/MIMXRT1020_EVK/mpconfigboard.mk
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,17 @@ MICROPY_PY_LWIP = 1
MICROPY_PY_SSL = 1
MICROPY_SSL_MBEDTLS = 1

MICROPY_PY_NETWORK = 1
MICROPY_PY_NETWORK_ESP_HOSTED = 1
CFLAGS += -DMICROPY_PY_NETWORK=$(MICROPY_PY_NETWORK)

MICROPY_PY_BLUETOOTH = 1
CFLAGS += -DMICROPY_PY_BLUETOOTH=$(MICROPY_PY_BLUETOOTH)
MICROPY_BLUETOOTH_NIMBLE = 1
MICROPY_BLUETOOTH_BTSTACK = 0

MBEDTLS_CONFIG_FILE = '"$(BOARD_DIR)/mbedtls_config_board.h"'

FROZEN_MANIFEST ?= $(BOARD_DIR)/manifest.py

JLINK_PATH ?= /media/RT1020-EVK/
Expand Down
175 changes: 175 additions & 0 deletions ports/mimxrt/esp_hosted_hal.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,175 @@
/*
* This file is part of the MicroPython project, http://micropython.org/
*
* The MIT License (MIT)
*
* Copyright (c) 2023 Arduino SA
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* ESP-Hosted WiFi HAL.
*/

#include "py/mphal.h"

#if MICROPY_PY_NETWORK_ESP_HOSTED

#include <stdint.h>
#include <string.h>

#include "py/runtime.h"
#include "modmachine.h"
#include "extmod/machine_spi.h"
#include "mpconfigboard.h"

#include "esp_hosted_hal.h"
#include "esp_hosted_wifi.h"

#ifndef MICROPY_HW_WIFI_IRQ
#define MICROPY_HW_WIFI_IRQ MICROPY_HW_WIFI_HANDSHAKE
#endif

static mp_hal_pin_obj_t micropy_hw_esp_hosted_reset;
static mp_hal_pin_obj_t micropy_hw_esp_hosted_gpio0;
static mp_hal_pin_obj_t micropy_hw_wifi_dataready;
static mp_hal_pin_obj_t micropy_hw_wifi_handshake;
static mp_hal_pin_obj_t micropy_hw_wifi_spi_cs;
static mp_hal_pin_obj_t micropy_hw_wifi_irq;


STATIC mp_obj_t esp_hosted_pin_irq_callback(mp_obj_t self_in) {
extern void mod_network_poll_events(void);
mod_network_poll_events();
return mp_const_none;
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(esp_hosted_pin_irq_callback_obj, esp_hosted_pin_irq_callback);

int esp_hosted_hal_init(uint32_t mode) {

micropy_hw_wifi_dataready = MICROPY_HW_WIFI_DATAREADY;
micropy_hw_wifi_handshake = MICROPY_HW_WIFI_HANDSHAKE;
micropy_hw_wifi_irq = MICROPY_HW_WIFI_IRQ;
micropy_hw_wifi_spi_cs = MICROPY_HW_WIFI_SPI_CS;
micropy_hw_esp_hosted_reset = MICROPY_HW_ESP_HOSTED_RESET;
micropy_hw_esp_hosted_gpio0 = MICROPY_HW_ESP_HOSTED_GPIO0;

// Perform a hard reset and set pins to their defaults.
esp_hosted_hal_deinit();

if (mode == ESP_HOSTED_MODE_BT) {
// For Bluetooth mode, init is done.
return 0;
}

mp_hal_pin_input(micropy_hw_wifi_handshake);
mp_hal_pin_input(micropy_hw_wifi_dataready);

// Enable Pin-IRQ for the handshake PIN to call esp_hosted_wifi_poll()
mp_obj_t irq_trigger_attr[2];
mp_load_method_maybe((mp_obj_t)micropy_hw_wifi_irq, MP_QSTR_IRQ_RISING, irq_trigger_attr);

if (irq_trigger_attr[0] != MP_OBJ_NULL && irq_trigger_attr[1] == MP_OBJ_NULL) { // value for IRQ rising found
mp_obj_t pin_args[] = {
NULL, // Method pointer
(mp_obj_t)micropy_hw_wifi_irq, // Pin object
(mp_obj_t)&esp_hosted_pin_irq_callback_obj, // Callback function object
NULL, // The Rising edge value is set below.
mp_const_true, // Hard IRQ, since the actual polling is scheduled.
};
pin_args[3] = irq_trigger_attr[0];
mp_load_method_maybe((mp_obj_t)micropy_hw_wifi_irq, MP_QSTR_irq, pin_args);
if (pin_args[0] != MP_OBJ_NULL && pin_args[1] != MP_OBJ_NULL) {
mp_call_method_n_kw(3, 0, pin_args);
}
}

// Initialize SPI.
mp_obj_t spi_args[] = {
MP_OBJ_NEW_SMALL_INT(MICROPY_HW_WIFI_SPI_ID),
MP_OBJ_NEW_SMALL_INT(MICROPY_HW_WIFI_SPI_BAUDRATE),
MP_OBJ_NEW_QSTR(MP_QSTR_polarity), MP_OBJ_NEW_SMALL_INT(1),
};

MP_STATE_PORT(mp_wifi_spi) =
MP_OBJ_TYPE_GET_SLOT(&machine_spi_type, make_new)((mp_obj_t)&machine_spi_type, 2, 1, spi_args);

// SPI might change the direction/mode of CS pin,
// set it to GPIO again just in case.
mp_hal_pin_output(micropy_hw_wifi_spi_cs);
mp_hal_pin_write(micropy_hw_wifi_spi_cs, 1);
return 0;
}

int esp_hosted_hal_deinit(void) {

// Disable Pin-IRQ for the handshake PIN
mp_obj_t pin_args[] = {
NULL, // Method pointer
(mp_obj_t)micropy_hw_wifi_handshake, // Pin object
mp_const_none // Set to None
};
mp_load_method_maybe((mp_obj_t)micropy_hw_wifi_handshake, MP_QSTR_irq, pin_args);
if (pin_args[0] && pin_args[1]) {
mp_call_method_n_kw(1, 0, pin_args);
}

mp_hal_pin_output(micropy_hw_esp_hosted_reset);
mp_hal_pin_output(micropy_hw_esp_hosted_gpio0);

// mp_hal_pin_output(micropy_hw_wifi_spi_cs);
// mp_hal_pin_write(micropy_hw_wifi_spi_cs, 1);

// Perform a hard reset
mp_hal_pin_write(micropy_hw_esp_hosted_gpio0, 1);
mp_hal_pin_write(micropy_hw_esp_hosted_reset, 0);
mp_hal_delay_ms(100);
mp_hal_pin_write(micropy_hw_esp_hosted_reset, 1);
mp_hal_delay_ms(500);

MP_STATE_PORT(mp_wifi_spi) = MP_OBJ_NULL;
return 0;
}

bool esp_hosted_hal_data_ready(void) {
return mp_hal_pin_read(micropy_hw_wifi_dataready) && mp_hal_pin_read(micropy_hw_wifi_handshake);
}

int esp_hosted_hal_spi_transfer(const uint8_t *tx_buf, uint8_t *rx_buf, uint32_t size) {
mp_obj_t mp_wifi_spi = MP_STATE_PORT(mp_wifi_spi);
const mp_machine_spi_p_t *spi_proto = MP_OBJ_TYPE_GET_SLOT(&machine_spi_type, protocol);

// Wait for handshake pin to go high.
for (mp_uint_t start = mp_hal_ticks_ms(); ; mp_hal_delay_ms(1)) {
if (mp_hal_pin_read(micropy_hw_wifi_handshake)) {
break;
}
if ((mp_hal_ticks_ms() - start) >= 1000) {
error_printf("timeout waiting for handshake\n");
return -1;
}
}

mp_hal_pin_write(micropy_hw_wifi_spi_cs, 0);
mp_hal_delay_ms(1);
spi_proto->transfer(mp_wifi_spi, size, tx_buf, rx_buf);
mp_hal_pin_write(micropy_hw_wifi_spi_cs, 1);
return 0;
}

#endif // MICROPY_PY_NETWORK_NINAW10
24 changes: 10 additions & 14 deletions ports/mimxrt/machine_uart.c
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,8 @@
#include "py/mphal.h"
#include "ticks.h"
#include "fsl_common.h"
#include "fsl_lpuart.h"
#include "fsl_iomuxc.h"
#include "fsl_lpuart.h"
#include CLOCK_CONFIG_H
#include "modmachine.h"
#include "pin.h"
Expand Down Expand Up @@ -64,6 +64,15 @@ typedef struct _machine_uart_obj_t {
bool new;
} machine_uart_obj_t;

#define DEFAULT_UART_BAUDRATE (115200)
#define DEFAULT_BUFFER_SIZE (256)
#define MIN_BUFFER_SIZE (32)
#define MAX_BUFFER_SIZE (32766)

#define UART_INVERT_TX (1)
#define UART_INVERT_RX (2)
#define UART_INVERT_MASK (UART_INVERT_TX | UART_INVERT_RX)

typedef struct _iomux_table_t {
uint32_t muxRegister;
uint32_t muxMode;
Expand Down Expand Up @@ -153,24 +162,12 @@ static void machine_uart_ensure_active(machine_uart_obj_t *uart) {
}
}

#if !defined(MIMXRT117x_SERIES)
static inline void uart_set_clock_divider(uint32_t baudrate) {
// For baud rates < 460800 divide the clock by 10, supporting baud rates down to 50 baud.
if (baudrate >= 460800) {
CLOCK_SetDiv(kCLOCK_UartDiv, 0);
} else {
CLOCK_SetDiv(kCLOCK_UartDiv, 9);
}
}
#endif

void machine_uart_set_baudrate(mp_obj_t uart_in, uint32_t baudrate) {
machine_uart_obj_t *uart = MP_OBJ_TO_PTR(uart_in);
#if defined(MIMXRT117x_SERIES)
// Use the Lpuart1 clock value, which is set for All UART devices.
LPUART_SetBaudRate(uart->lpuart, baudrate, CLOCK_GetRootClockFreq(kCLOCK_Root_Lpuart1));
#else
uart_set_clock_divider(baudrate);
LPUART_SetBaudRate(uart->lpuart, baudrate, CLOCK_GetClockRootFreq(kCLOCK_UartClkRoot));
#endif
}
Expand Down Expand Up @@ -315,7 +312,6 @@ STATIC mp_obj_t machine_uart_init_helper(machine_uart_obj_t *self, size_t n_args
// Use the Lpuart1 clock value, which is set for All UART devices.
LPUART_Init(self->lpuart, &self->config, CLOCK_GetRootClockFreq(kCLOCK_Root_Lpuart1));
#else
uart_set_clock_divider(self->config.baudRate_Bps);
LPUART_Init(self->lpuart, &self->config, CLOCK_GetClockRootFreq(kCLOCK_UartClkRoot));
#endif
LPUART_TransferCreateHandle(self->lpuart, &self->handle, LPUART_UserCallback, self);
Expand Down
Loading

0 comments on commit 72cb34c

Please sign in to comment.