extmod/machine_uart: Factor ports' UART Python bindings to common code.

This is a code factoring to have the Python bindings in one location, and
all the ports use those same bindings.  For all ports except the two listed
below there is no functional change.

The nrf port has UART.sendbreak() removed, but this method previously did
nothing.

The zephyr port has the following methods added:
- UART.init(): supports setting timeout and timeout_char.
- UART.deinit(): does nothing, just returns None.
- UART.flush(): raises OSError(EINVAL) because it's not implemented.
- UART.any() and UART.txdone(): raise NotImplementedError.

Signed-off-by: Damien George <damien@micropython.org>
This commit is contained in:
Damien George
2023-10-10 23:46:07 +11:00
parent 95d8b5fd55
commit 5b4a2baff6
65 changed files with 661 additions and 996 deletions

View File

@@ -3,7 +3,7 @@
*
* The MIT License (MIT)
*
* Copyright (c) 2016 Damien P. George
* Copyright (c) 2016-2023 Damien P. George
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -24,9 +24,8 @@
* THE SOFTWARE.
*/
#include <stdio.h>
#include <stdint.h>
#include <string.h>
// This file is never compiled standalone, it's included directly from
// extmod/machine_uart.c via MICROPY_PY_MACHINE_UART_INCLUDEFILE.
#include "driver/uart.h"
#include "freertos/FreeRTOS.h"
@@ -35,7 +34,6 @@
#include "py/stream.h"
#include "py/mperrno.h"
#include "py/mphal.h"
#include "modmachine.h"
#include "uart.h"
#if SOC_UART_SUPPORT_XTAL_CLK
@@ -75,7 +73,15 @@ STATIC const char *_parity_name[] = {"None", "1", "0"};
/******************************************************************************/
// MicroPython bindings for UART
STATIC void machine_uart_print(const mp_print_t *print, mp_obj_t self_in, mp_print_kind_t kind) {
#define MICROPY_PY_MACHINE_UART_CLASS_CONSTANTS \
{ MP_ROM_QSTR(MP_QSTR_INV_TX), MP_ROM_INT(UART_INV_TX) }, \
{ MP_ROM_QSTR(MP_QSTR_INV_RX), MP_ROM_INT(UART_INV_RX) }, \
{ MP_ROM_QSTR(MP_QSTR_INV_RTS), MP_ROM_INT(UART_INV_RTS) }, \
{ MP_ROM_QSTR(MP_QSTR_INV_CTS), MP_ROM_INT(UART_INV_CTS) }, \
{ MP_ROM_QSTR(MP_QSTR_RTS), MP_ROM_INT(UART_HW_FLOWCTRL_RTS) }, \
{ MP_ROM_QSTR(MP_QSTR_CTS), MP_ROM_INT(UART_HW_FLOWCTRL_CTS) }, \
STATIC void mp_machine_uart_print(const mp_print_t *print, mp_obj_t self_in, mp_print_kind_t kind) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
uint32_t baudrate;
uart_get_baudrate(self->uart_num, &baudrate);
@@ -127,7 +133,7 @@ STATIC void machine_uart_print(const mp_print_t *print, mp_obj_t self_in, mp_pri
mp_printf(print, ")");
}
STATIC void machine_uart_init_helper(machine_uart_obj_t *self, size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) {
STATIC void mp_machine_uart_init_helper(machine_uart_obj_t *self, size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) {
enum { ARG_baudrate, ARG_bits, ARG_parity, ARG_stop, ARG_tx, ARG_rx, ARG_rts, ARG_cts, ARG_txbuf, ARG_rxbuf, ARG_timeout, ARG_timeout_char, ARG_invert, ARG_flow };
static const mp_arg_t allowed_args[] = {
{ MP_QSTR_baudrate, MP_ARG_INT, {.u_int = 0} },
@@ -303,7 +309,7 @@ STATIC void machine_uart_init_helper(machine_uart_obj_t *self, size_t n_args, co
uart_set_hw_flow_ctrl(self->uart_num, self->flowcontrol, UART_FIFO_LEN - UART_FIFO_LEN / 4);
}
STATIC mp_obj_t machine_uart_make_new(const mp_obj_type_t *type, size_t n_args, size_t n_kw, const mp_obj_t *args) {
STATIC mp_obj_t mp_machine_uart_make_new(const mp_obj_type_t *type, size_t n_args, size_t n_kw, const mp_obj_t *args) {
mp_arg_check_num(n_args, n_kw, 1, MP_OBJ_FUN_ARGS_MAX, true);
// get uart id
@@ -372,7 +378,7 @@ STATIC mp_obj_t machine_uart_make_new(const mp_obj_type_t *type, size_t n_args,
mp_map_t kw_args;
mp_map_init_fixed_table(&kw_args, n_kw, args + n_args);
machine_uart_init_helper(self, n_args - 1, args + 1, &kw_args);
mp_machine_uart_init_helper(self, n_args - 1, args + 1, &kw_args);
// Make sure pins are connected.
uart_set_pin(self->uart_num, self->tx, self->rx, self->rts, self->cts);
@@ -380,30 +386,21 @@ STATIC mp_obj_t machine_uart_make_new(const mp_obj_type_t *type, size_t n_args,
return MP_OBJ_FROM_PTR(self);
}
STATIC mp_obj_t machine_uart_init(size_t n_args, const mp_obj_t *args, mp_map_t *kw_args) {
machine_uart_init_helper(args[0], n_args - 1, args + 1, kw_args);
return mp_const_none;
}
MP_DEFINE_CONST_FUN_OBJ_KW(machine_uart_init_obj, 1, machine_uart_init);
STATIC mp_obj_t machine_uart_deinit(mp_obj_t self_in) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
STATIC void mp_machine_uart_deinit(machine_uart_obj_t *self) {
uart_driver_delete(self->uart_num);
return mp_const_none;
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(machine_uart_deinit_obj, machine_uart_deinit);
STATIC mp_obj_t machine_uart_any(mp_obj_t self_in) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
STATIC mp_int_t mp_machine_uart_any(machine_uart_obj_t *self) {
size_t rxbufsize;
uart_get_buffered_data_len(self->uart_num, &rxbufsize);
return MP_OBJ_NEW_SMALL_INT(rxbufsize);
return rxbufsize;
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(machine_uart_any_obj, machine_uart_any);
STATIC mp_obj_t machine_uart_sendbreak(mp_obj_t self_in) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
STATIC bool mp_machine_uart_txdone(machine_uart_obj_t *self) {
return uart_wait_tx_done(self->uart_num, 0) == ESP_OK;
}
STATIC void mp_machine_uart_sendbreak(machine_uart_obj_t *self) {
// Save settings
uint32_t baudrate;
uart_get_baudrate(self->uart_num, &baudrate);
@@ -418,46 +415,9 @@ STATIC mp_obj_t machine_uart_sendbreak(mp_obj_t self_in) {
// Restore original setting
uart_set_baudrate(self->uart_num, baudrate);
return mp_const_none;
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(machine_uart_sendbreak_obj, machine_uart_sendbreak);
STATIC mp_obj_t machine_uart_txdone(mp_obj_t self_in) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
if (uart_wait_tx_done(self->uart_num, 0) == ESP_OK) {
return mp_const_true;
} else {
return mp_const_false;
}
}
STATIC MP_DEFINE_CONST_FUN_OBJ_1(machine_uart_txdone_obj, machine_uart_txdone);
STATIC const mp_rom_map_elem_t machine_uart_locals_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_init), MP_ROM_PTR(&machine_uart_init_obj) },
{ MP_ROM_QSTR(MP_QSTR_deinit), MP_ROM_PTR(&machine_uart_deinit_obj) },
{ MP_ROM_QSTR(MP_QSTR_any), MP_ROM_PTR(&machine_uart_any_obj) },
{ MP_ROM_QSTR(MP_QSTR_flush), MP_ROM_PTR(&mp_stream_flush_obj) },
{ MP_ROM_QSTR(MP_QSTR_read), MP_ROM_PTR(&mp_stream_read_obj) },
{ MP_ROM_QSTR(MP_QSTR_readline), MP_ROM_PTR(&mp_stream_unbuffered_readline_obj) },
{ MP_ROM_QSTR(MP_QSTR_readinto), MP_ROM_PTR(&mp_stream_readinto_obj) },
{ MP_ROM_QSTR(MP_QSTR_write), MP_ROM_PTR(&mp_stream_write_obj) },
{ MP_ROM_QSTR(MP_QSTR_sendbreak), MP_ROM_PTR(&machine_uart_sendbreak_obj) },
{ MP_ROM_QSTR(MP_QSTR_txdone), MP_ROM_PTR(&machine_uart_txdone_obj) },
{ MP_ROM_QSTR(MP_QSTR_INV_TX), MP_ROM_INT(UART_INV_TX) },
{ MP_ROM_QSTR(MP_QSTR_INV_RX), MP_ROM_INT(UART_INV_RX) },
{ MP_ROM_QSTR(MP_QSTR_INV_RTS), MP_ROM_INT(UART_INV_RTS) },
{ MP_ROM_QSTR(MP_QSTR_INV_CTS), MP_ROM_INT(UART_INV_CTS) },
{ MP_ROM_QSTR(MP_QSTR_RTS), MP_ROM_INT(UART_HW_FLOWCTRL_RTS) },
{ MP_ROM_QSTR(MP_QSTR_CTS), MP_ROM_INT(UART_HW_FLOWCTRL_CTS) },
};
STATIC MP_DEFINE_CONST_DICT(machine_uart_locals_dict, machine_uart_locals_dict_table);
STATIC mp_uint_t machine_uart_read(mp_obj_t self_in, void *buf_in, mp_uint_t size, int *errcode) {
STATIC mp_uint_t mp_machine_uart_read(mp_obj_t self_in, void *buf_in, mp_uint_t size, int *errcode) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
// make sure we want at least 1 char
@@ -491,7 +451,7 @@ STATIC mp_uint_t machine_uart_read(mp_obj_t self_in, void *buf_in, mp_uint_t siz
return bytes_read;
}
STATIC mp_uint_t machine_uart_write(mp_obj_t self_in, const void *buf_in, mp_uint_t size, int *errcode) {
STATIC mp_uint_t mp_machine_uart_write(mp_obj_t self_in, const void *buf_in, mp_uint_t size, int *errcode) {
machine_uart_obj_t *self = MP_OBJ_TO_PTR(self_in);
int bytes_written = uart_write_bytes(self->uart_num, buf_in, size);
@@ -505,7 +465,7 @@ STATIC mp_uint_t machine_uart_write(mp_obj_t self_in, const void *buf_in, mp_uin
return bytes_written;
}
STATIC mp_uint_t machine_uart_ioctl(mp_obj_t self_in, mp_uint_t request, uintptr_t arg, int *errcode) {
STATIC mp_uint_t mp_machine_uart_ioctl(mp_obj_t self_in, mp_uint_t request, uintptr_t arg, int *errcode) {
machine_uart_obj_t *self = self_in;
mp_uint_t ret;
if (request == MP_STREAM_POLL) {
@@ -537,20 +497,3 @@ STATIC mp_uint_t machine_uart_ioctl(mp_obj_t self_in, mp_uint_t request, uintptr
}
return ret;
}
STATIC const mp_stream_p_t uart_stream_p = {
.read = machine_uart_read,
.write = machine_uart_write,
.ioctl = machine_uart_ioctl,
.is_text = false,
};
MP_DEFINE_CONST_OBJ_TYPE(
machine_uart_type,
MP_QSTR_UART,
MP_TYPE_FLAG_ITER_IS_STREAM,
make_new, machine_uart_make_new,
print, machine_uart_print,
protocol, &uart_stream_p,
locals_dict, &machine_uart_locals_dict
);