Add full pin mux info and use it for I2C
All I2C peripherals should be usable now. This also adds pin in-use tracking and resetting. Part of #5629
This commit is contained in:
parent
b83e09858f
commit
2433c9572c
@ -63,6 +63,7 @@ SRC_C += bindings/videocore/__init__.c \
|
||||
lib/tinyusb/src/portable/synopsys/dwc2/dcd_dwc2.c \
|
||||
peripherals/broadcom/caches.c \
|
||||
peripherals/broadcom/gen/interrupt_handlers.c \
|
||||
peripherals/broadcom/gen/pins.c \
|
||||
peripherals/broadcom/gpio.c \
|
||||
peripherals/broadcom/interrupts.c \
|
||||
peripherals/broadcom/mmu.c \
|
||||
|
34
ports/broadcom/broadcom_peripherals_config.h
Normal file
34
ports/broadcom/broadcom_peripherals_config.h
Normal file
@ -0,0 +1,34 @@
|
||||
/*
|
||||
* This file is part of the Micro Python project, http://micropython.org/
|
||||
*
|
||||
* The MIT License (MIT)
|
||||
*
|
||||
* Copyright (c) 2021 Scott Shawcroft for Adafruit Industries
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "py/obj.h"
|
||||
|
||||
extern const mp_obj_type_t mcu_pin_type;
|
||||
|
||||
#define PIN_PREFIX_VALUES { &mcu_pin_type },
|
||||
#define PIN_PREFIX_FIELDS mp_obj_base_t base;
|
@ -35,35 +35,63 @@
|
||||
#include "peripherals/broadcom/cpu.h"
|
||||
#include "peripherals/broadcom/vcmailbox.h"
|
||||
|
||||
#define NUM_I2C (2)
|
||||
#if BCM_VERSION == 2711
|
||||
#define NUM_I2C (8)
|
||||
STATIC BSC0_Type *i2c[NUM_I2C] = {BSC0, BSC1, NULL, BSC3, BSC4, BSC5, BSC6, NULL};
|
||||
#else
|
||||
#define NUM_I2C (3)
|
||||
STATIC BSC0_Type *i2c[NUM_I2C] = {BSC0, BSC1, NULL};
|
||||
#endif
|
||||
|
||||
STATIC bool never_reset_i2c[NUM_I2C];
|
||||
STATIC bool in_use_i2c[NUM_I2C];
|
||||
STATIC BSC0_Type *i2c[2] = {BSC0, BSC1};
|
||||
STATIC bool i2c_in_use[NUM_I2C];
|
||||
|
||||
void reset_i2c(void) {
|
||||
// BSC2 is dedicated to the first HDMI output.
|
||||
never_reset_i2c[2] = true;
|
||||
i2c_in_use[2] = true;
|
||||
#if BCM_VERSION == 2711
|
||||
// BSC7 is dedicated to the second HDMI output.
|
||||
never_reset_i2c[7] = true;
|
||||
i2c_in_use[7] = true;
|
||||
#endif
|
||||
for (size_t i = 0; i < 2; i++) {
|
||||
if (never_reset_i2c[i]) {
|
||||
continue;
|
||||
}
|
||||
in_use_i2c[i] = false;
|
||||
i2c_in_use[i] = false;
|
||||
i2c[i]->C_b.I2CEN = false;
|
||||
COMPLETE_MEMORY_READS;
|
||||
}
|
||||
}
|
||||
|
||||
void common_hal_busio_i2c_construct(busio_i2c_obj_t *self,
|
||||
const mcu_pin_obj_t *scl, const mcu_pin_obj_t *sda, uint32_t frequency, uint32_t timeout) {
|
||||
size_t instance_index = NUM_I2C;
|
||||
if ((scl == &pin_GPIO1 || scl == &pin_GPIO29 || scl == &pin_GPIO45) &&
|
||||
(sda == &pin_GPIO0 || sda == &pin_GPIO28 || sda == &pin_GPIO44)) {
|
||||
instance_index = 0;
|
||||
} else if ((scl == &pin_GPIO44 || scl == &pin_GPIO3) &&
|
||||
(sda == &pin_GPIO43 || sda == &pin_GPIO2)) {
|
||||
instance_index = 1;
|
||||
uint8_t scl_alt = 0;
|
||||
uint8_t sda_alt = 0;
|
||||
for (scl_alt = 0; scl_alt < 6; scl_alt++) {
|
||||
if (scl->functions[scl_alt].type != PIN_FUNCTION_I2C ||
|
||||
i2c_in_use[scl->functions[scl_alt].index]) {
|
||||
continue;
|
||||
}
|
||||
for (sda_alt = 0; sda_alt < 6; sda_alt++) {
|
||||
if (sda->functions[sda_alt].type != PIN_FUNCTION_I2C ||
|
||||
scl->functions[scl_alt].index != sda->functions[sda_alt].index ||
|
||||
sda->functions[sda_alt].function != I2C_FUNCTION_SDA) {
|
||||
continue;
|
||||
}
|
||||
instance_index = scl->functions[scl_alt].index;
|
||||
break;
|
||||
}
|
||||
if (instance_index != NUM_I2C) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (instance_index == NUM_I2C) {
|
||||
mp_raise_ValueError(translate("Invalid pins"));
|
||||
}
|
||||
in_use_i2c[instance_index] = true;
|
||||
i2c_in_use[instance_index] = true;
|
||||
self->index = instance_index;
|
||||
self->peripheral = i2c[self->index];
|
||||
self->sda_pin = sda;
|
||||
@ -73,8 +101,8 @@ void common_hal_busio_i2c_construct(busio_i2c_obj_t *self,
|
||||
uint16_t clock_divider = source_clock / frequency;
|
||||
self->peripheral->DIV_b.CDIV = clock_divider;
|
||||
|
||||
gpio_set_function(sda->number, GPIO_GPFSEL0_FSEL2_SDA1);
|
||||
gpio_set_function(scl->number, GPIO_GPFSEL0_FSEL3_SCL1);
|
||||
gpio_set_function(sda->number, FSEL_VALUES[sda_alt]);
|
||||
gpio_set_function(scl->number, FSEL_VALUES[scl_alt]);
|
||||
}
|
||||
|
||||
bool common_hal_busio_i2c_deinited(busio_i2c_obj_t *self) {
|
||||
@ -86,6 +114,7 @@ void common_hal_busio_i2c_deinit(busio_i2c_obj_t *self) {
|
||||
return;
|
||||
}
|
||||
never_reset_i2c[self->index] = false;
|
||||
i2c_in_use[self->index] = false;
|
||||
|
||||
common_hal_reset_pin(self->sda_pin);
|
||||
common_hal_reset_pin(self->scl_pin);
|
||||
@ -95,7 +124,6 @@ void common_hal_busio_i2c_deinit(busio_i2c_obj_t *self) {
|
||||
|
||||
bool common_hal_busio_i2c_probe(busio_i2c_obj_t *self, uint8_t addr) {
|
||||
uint8_t result = common_hal_busio_i2c_write(self, addr, NULL, 0, true);
|
||||
// mp_printf(&mp_plat_print, "result %d %d\n", addr, result);
|
||||
return result == 0;
|
||||
}
|
||||
|
||||
|
@ -28,14 +28,41 @@
|
||||
|
||||
#include "peripherals/broadcom/gpio.h"
|
||||
|
||||
STATIC bool pin_in_use[BCM_PIN_COUNT];
|
||||
STATIC bool never_reset_pin[BCM_PIN_COUNT];
|
||||
|
||||
void reset_all_pins(void) {
|
||||
for (size_t i = 0; i < BCM_PIN_COUNT; i++) {
|
||||
if (never_reset_pin[i]) {
|
||||
continue;
|
||||
}
|
||||
reset_pin_number(i);
|
||||
}
|
||||
}
|
||||
|
||||
void never_reset_pin_number(uint8_t pin_number) {
|
||||
never_reset_pin[pin_number] = true;
|
||||
}
|
||||
|
||||
void reset_pin_number(uint8_t pin_number) {
|
||||
gpio_set_function(pin_number, 0);
|
||||
gpio_set_function(pin_number, GPIO_FUNCTION_INPUT);
|
||||
pin_in_use[pin_number] = false;
|
||||
never_reset_pin[pin_number] = false;
|
||||
// Set the pull to match the datasheet.
|
||||
BP_PULL_Enum pull = BP_PULL_NONE;
|
||||
if (pin_number < 9 ||
|
||||
(33 < pin_number && pin_number < 37) ||
|
||||
pin_number > 45) {
|
||||
pull = BP_PULL_UP;
|
||||
} else if (pin_number != 28 &&
|
||||
pin_number != 29 &&
|
||||
pin_number != 44 &&
|
||||
pin_number != 45) {
|
||||
// Most pins are pulled low so we only exclude the four pins that aren't
|
||||
// pulled at all.
|
||||
pull = BP_PULL_DOWN;
|
||||
}
|
||||
gpio_set_pull(pin_number, pull);
|
||||
}
|
||||
|
||||
void common_hal_never_reset_pin(const mcu_pin_obj_t *pin) {
|
||||
@ -47,11 +74,11 @@ void common_hal_reset_pin(const mcu_pin_obj_t *pin) {
|
||||
}
|
||||
|
||||
void claim_pin(const mcu_pin_obj_t *pin) {
|
||||
// Nothing to do because all changes will set the GPIO settings.
|
||||
pin_in_use[pin->number] = true;
|
||||
}
|
||||
|
||||
bool pin_number_is_free(uint8_t pin_number) {
|
||||
return true;
|
||||
return !pin_in_use[pin_number];
|
||||
}
|
||||
|
||||
bool common_hal_mcu_pin_is_free(const mcu_pin_obj_t *pin) {
|
||||
@ -69,71 +96,3 @@ void common_hal_mcu_pin_claim(const mcu_pin_obj_t *pin) {
|
||||
void common_hal_mcu_pin_reset_number(uint8_t pin_no) {
|
||||
reset_pin_number(pin_no);
|
||||
}
|
||||
|
||||
#define PIN(num) \
|
||||
const mcu_pin_obj_t pin_GPIO##num = { \
|
||||
{ &mcu_pin_type }, \
|
||||
.number = num \
|
||||
};
|
||||
|
||||
PIN(0)
|
||||
PIN(1)
|
||||
PIN(2)
|
||||
PIN(3)
|
||||
PIN(4)
|
||||
PIN(5)
|
||||
PIN(6)
|
||||
PIN(7)
|
||||
PIN(8)
|
||||
PIN(9)
|
||||
PIN(10)
|
||||
PIN(11)
|
||||
PIN(12)
|
||||
PIN(13)
|
||||
PIN(14)
|
||||
PIN(15)
|
||||
PIN(16)
|
||||
PIN(17)
|
||||
PIN(18)
|
||||
PIN(19)
|
||||
PIN(20)
|
||||
PIN(21)
|
||||
PIN(22)
|
||||
PIN(23)
|
||||
PIN(24)
|
||||
PIN(25)
|
||||
PIN(26)
|
||||
PIN(27)
|
||||
PIN(28)
|
||||
PIN(29)
|
||||
|
||||
PIN(30)
|
||||
PIN(31)
|
||||
PIN(32)
|
||||
PIN(33)
|
||||
PIN(34)
|
||||
PIN(35)
|
||||
PIN(36)
|
||||
PIN(37)
|
||||
PIN(38)
|
||||
PIN(39)
|
||||
|
||||
PIN(40)
|
||||
PIN(41)
|
||||
PIN(42)
|
||||
PIN(43)
|
||||
PIN(44)
|
||||
PIN(45)
|
||||
PIN(46)
|
||||
PIN(47)
|
||||
PIN(48)
|
||||
PIN(49)
|
||||
|
||||
PIN(50)
|
||||
PIN(51)
|
||||
PIN(52)
|
||||
PIN(53)
|
||||
PIN(54)
|
||||
PIN(55)
|
||||
PIN(56)
|
||||
PIN(57)
|
||||
|
@ -32,74 +32,7 @@
|
||||
|
||||
#include <py/obj.h>
|
||||
|
||||
typedef struct {
|
||||
mp_obj_base_t base;
|
||||
uint8_t number;
|
||||
} mcu_pin_obj_t;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO0;
|
||||
extern const mcu_pin_obj_t pin_GPIO1;
|
||||
extern const mcu_pin_obj_t pin_GPIO2;
|
||||
extern const mcu_pin_obj_t pin_GPIO3;
|
||||
extern const mcu_pin_obj_t pin_GPIO4;
|
||||
extern const mcu_pin_obj_t pin_GPIO5;
|
||||
extern const mcu_pin_obj_t pin_GPIO6;
|
||||
extern const mcu_pin_obj_t pin_GPIO7;
|
||||
extern const mcu_pin_obj_t pin_GPIO8;
|
||||
extern const mcu_pin_obj_t pin_GPIO9;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO10;
|
||||
extern const mcu_pin_obj_t pin_GPIO11;
|
||||
extern const mcu_pin_obj_t pin_GPIO12;
|
||||
extern const mcu_pin_obj_t pin_GPIO13;
|
||||
extern const mcu_pin_obj_t pin_GPIO14;
|
||||
extern const mcu_pin_obj_t pin_GPIO15;
|
||||
extern const mcu_pin_obj_t pin_GPIO16;
|
||||
extern const mcu_pin_obj_t pin_GPIO17;
|
||||
extern const mcu_pin_obj_t pin_GPIO18;
|
||||
extern const mcu_pin_obj_t pin_GPIO19;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO20;
|
||||
extern const mcu_pin_obj_t pin_GPIO21;
|
||||
extern const mcu_pin_obj_t pin_GPIO22;
|
||||
extern const mcu_pin_obj_t pin_GPIO23;
|
||||
extern const mcu_pin_obj_t pin_GPIO24;
|
||||
extern const mcu_pin_obj_t pin_GPIO25;
|
||||
extern const mcu_pin_obj_t pin_GPIO26;
|
||||
extern const mcu_pin_obj_t pin_GPIO27;
|
||||
extern const mcu_pin_obj_t pin_GPIO28;
|
||||
extern const mcu_pin_obj_t pin_GPIO29;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO30;
|
||||
extern const mcu_pin_obj_t pin_GPIO31;
|
||||
extern const mcu_pin_obj_t pin_GPIO32;
|
||||
extern const mcu_pin_obj_t pin_GPIO33;
|
||||
extern const mcu_pin_obj_t pin_GPIO34;
|
||||
extern const mcu_pin_obj_t pin_GPIO35;
|
||||
extern const mcu_pin_obj_t pin_GPIO36;
|
||||
extern const mcu_pin_obj_t pin_GPIO37;
|
||||
extern const mcu_pin_obj_t pin_GPIO38;
|
||||
extern const mcu_pin_obj_t pin_GPIO39;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO40;
|
||||
extern const mcu_pin_obj_t pin_GPIO41;
|
||||
extern const mcu_pin_obj_t pin_GPIO42;
|
||||
extern const mcu_pin_obj_t pin_GPIO43;
|
||||
extern const mcu_pin_obj_t pin_GPIO44;
|
||||
extern const mcu_pin_obj_t pin_GPIO45;
|
||||
extern const mcu_pin_obj_t pin_GPIO46;
|
||||
extern const mcu_pin_obj_t pin_GPIO47;
|
||||
extern const mcu_pin_obj_t pin_GPIO48;
|
||||
extern const mcu_pin_obj_t pin_GPIO49;
|
||||
|
||||
extern const mcu_pin_obj_t pin_GPIO50;
|
||||
extern const mcu_pin_obj_t pin_GPIO51;
|
||||
extern const mcu_pin_obj_t pin_GPIO52;
|
||||
extern const mcu_pin_obj_t pin_GPIO53;
|
||||
extern const mcu_pin_obj_t pin_GPIO54;
|
||||
extern const mcu_pin_obj_t pin_GPIO55;
|
||||
extern const mcu_pin_obj_t pin_GPIO56;
|
||||
extern const mcu_pin_obj_t pin_GPIO57;
|
||||
#include "peripherals/broadcom/pins.h"
|
||||
|
||||
void reset_all_pins(void);
|
||||
// reset_pin_number takes the pin number instead of the pointer so that objects don't
|
||||
|
@ -187,9 +187,11 @@ const mp_rom_map_elem_t mcu_pin_global_dict_table[TOTAL_GPIO_COUNT] = {
|
||||
PIN(51)
|
||||
PIN(52)
|
||||
PIN(53)
|
||||
#if BCM_VERSION == 2711
|
||||
PIN(54)
|
||||
PIN(55)
|
||||
PIN(56)
|
||||
PIN(57)
|
||||
#endif
|
||||
};
|
||||
MP_DEFINE_CONST_DICT(mcu_pin_globals, mcu_pin_global_dict_table);
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit 8057af2d614c27a1e103d5f4300428f341da6bcb
|
||||
Subproject commit 2e7b56bbe941311e54fba66f0b32336bfea4388d
|
Loading…
Reference in New Issue
Block a user