Skip to content

Commit

Permalink
[i2c] add gpio paramter
Browse files Browse the repository at this point in the history
  • Loading branch information
vamoosebbf committed Jan 12, 2021
1 parent f18990a commit 4b3778b
Show file tree
Hide file tree
Showing 2 changed files with 51 additions and 27 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ typedef struct _machine_hard_i2c_obj_t {
mp_obj_t on_event;
int pin_scl;
int pin_sda;
int gpio_scl;
int gpio_sda;
int us_delay;
} machine_hard_i2c_obj_t;

Expand Down
76 changes: 49 additions & 27 deletions components/micropython/port/src/standard_lib/machine/machine_i2c.c
Original file line number Diff line number Diff line change
Expand Up @@ -77,15 +77,15 @@ STATIC int mp_hal_i2c_scl_release(machine_hard_i2c_obj_t *self) {
uint32_t count = self->timeout;

// mp_hal_pin_od_high(self->pin_scl);
gpiohs_set_drive_mode(self->pin_scl, GPIO_DM_OUTPUT);
gpiohs_set_pin(self->pin_scl, 1);
gpiohs_set_drive_mode(self->gpio_scl, GPIO_DM_OUTPUT);
gpiohs_set_pin(self->gpio_scl, 1);

mp_hal_i2c_delay(self);
// For clock stretching, wait for the SCL pin to be released, with timeout.
gpiohs_set_drive_mode(self->pin_scl, GPIO_DM_INPUT);
gpiohs_set_drive_mode(self->gpio_scl, GPIO_DM_INPUT);

// for (; mp_hal_pin_read(self->pin_scl) == 0 && count; --count) {
for (; gpiohs_get_pin(self->pin_scl) == 0 && count; --count) {
for (; gpiohs_get_pin(self->gpio_scl) == 0 && count; --count) {

mp_hal_delay_us_fast(1);
}
Expand All @@ -99,26 +99,26 @@ STATIC int mp_hal_i2c_scl_release(machine_hard_i2c_obj_t *self) {
STATIC void mp_hal_i2c_scl_low(machine_hard_i2c_obj_t *self) {
// mp_hal_pin_od_low(self->pin_scl);

gpiohs_set_drive_mode(self->pin_scl, GPIO_DM_OUTPUT);
gpiohs_set_pin(self->pin_scl, 0);
gpiohs_set_drive_mode(self->gpio_scl, GPIO_DM_OUTPUT);
gpiohs_set_pin(self->gpio_scl, 0);
}

STATIC void mp_hal_i2c_sda_low(machine_hard_i2c_obj_t *self) {
// mp_hal_pin_od_low(self->pin_sda);
gpiohs_set_pin(self->pin_sda, 0);
gpiohs_set_drive_mode(self->pin_sda, GPIO_DM_OUTPUT);
gpiohs_set_pin(self->gpio_sda, 0);
gpiohs_set_drive_mode(self->gpio_sda, GPIO_DM_OUTPUT);
}

STATIC void mp_hal_i2c_sda_release(machine_hard_i2c_obj_t *self) {
// mp_hal_pin_od_high(self->pin_sda);
gpiohs_set_pin(self->pin_sda, 1);
gpiohs_set_drive_mode(self->pin_sda, GPIO_DM_OUTPUT);
gpiohs_set_drive_mode(self->pin_sda, GPIO_DM_INPUT);
gpiohs_set_pin(self->gpio_sda, 1);
gpiohs_set_drive_mode(self->gpio_sda, GPIO_DM_OUTPUT);
gpiohs_set_drive_mode(self->gpio_sda, GPIO_DM_INPUT);
}

STATIC int mp_hal_i2c_sda_read(machine_hard_i2c_obj_t *self) {
gpiohs_set_drive_mode(self->pin_sda, GPIO_DM_INPUT);
return gpiohs_get_pin(self->pin_sda);
gpiohs_set_drive_mode(self->gpio_sda, GPIO_DM_INPUT);
return gpiohs_get_pin(self->gpio_sda);
// return mp_hal_pin_read(self->pin_sda);
}

Expand Down Expand Up @@ -329,6 +329,15 @@ STATIC bool check_addr_size(uint32_t addr_size)
return true;
}

STATIC bool check_gpio(uint32_t scl, uint32_t sda)
{
if(scl > 31)
return false;
if(sda > 31)
return false;
return true;
}

STATIC bool check_pin(uint32_t scl, uint32_t sda)
{
if(scl > 47)
Expand Down Expand Up @@ -487,8 +496,10 @@ STATIC mp_obj_t machine_i2c_init_helper(machine_hard_i2c_obj_t* self, mp_uint_t
enum {
ARG_id,
ARG_mode,
ARG_scl,
ARG_sda,
ARG_pin_scl,
ARG_pin_sda,
ARG_gpio_scl,
ARG_gpio_sda,
ARG_freq,
ARG_timeout,
ARG_addr,
Expand All @@ -502,6 +513,8 @@ STATIC mp_obj_t machine_i2c_init_helper(machine_hard_i2c_obj_t* self, mp_uint_t
{ MP_QSTR_mode, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_int = MACHINE_I2C_MODE_MASTER} },
{ MP_QSTR_scl, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = MP_OBJ_NULL} },
{ MP_QSTR_sda, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = MP_OBJ_NULL} },
{ MP_QSTR_gscl, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = MP_OBJ_NULL} },
{ MP_QSTR_gsda, MP_ARG_KW_ONLY | MP_ARG_OBJ, {.u_obj = MP_OBJ_NULL} },
{ MP_QSTR_freq, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_int = 400000} },
{ MP_QSTR_timeout, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_int = 1000} },
{ MP_QSTR_addr, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_int = 0} },
Expand Down Expand Up @@ -555,11 +568,21 @@ STATIC mp_obj_t machine_i2c_init_helper(machine_hard_i2c_obj_t* self, mp_uint_t
}
}

if (args[ARG_scl].u_obj != MP_OBJ_NULL || args[ARG_sda].u_obj != MP_OBJ_NULL) {
if( !check_pin( mp_obj_get_int(args[ARG_scl].u_obj), mp_obj_get_int(args[ARG_sda].u_obj) ) )
if (args[ARG_pin_scl].u_obj != MP_OBJ_NULL || args[ARG_pin_sda].u_obj != MP_OBJ_NULL) {
if( !check_pin( mp_obj_get_int(args[ARG_pin_scl].u_obj), mp_obj_get_int(args[ARG_pin_sda].u_obj) ) )
mp_raise_ValueError("[MAIXPY]I2C: pin(scl/sda) error!");
self->pin_scl = mp_obj_get_int(args[ARG_scl].u_obj);
self->pin_sda = mp_obj_get_int(args[ARG_sda].u_obj);
self->pin_scl = mp_obj_get_int(args[ARG_pin_scl].u_obj);
self->pin_sda = mp_obj_get_int(args[ARG_pin_sda].u_obj);
self->gpio_scl = self->pin_scl;
self->gpio_sda = self->pin_sda;
}
if (args[ARG_gpio_scl].u_obj != MP_OBJ_NULL || args[ARG_gpio_sda].u_obj != MP_OBJ_NULL) {
int gscl = mp_obj_get_int(args[ARG_gpio_scl].u_obj) - FUNC_GPIOHS0;
int gsda = mp_obj_get_int(args[ARG_gpio_sda].u_obj) - FUNC_GPIOHS0;
if( !check_gpio(gscl, gsda) )
mp_raise_ValueError("[MAIXPY]I2C: gpio(scl/sda) error!");
self->gpio_scl = gscl;
self->gpio_sda = gsda;
}

// set param
Expand All @@ -578,8 +601,6 @@ STATIC mp_obj_t machine_i2c_init_helper(machine_hard_i2c_obj_t* self, mp_uint_t
|| self->i2c == (i2c_device_number_t)I2C_DEVICE_4
|| self->i2c == (i2c_device_number_t)I2C_DEVICE_5) {
self->mode = MACHINE_I2C_MODE_MASTER_SOFT;
if( mp_obj_get_int(args[ARG_scl].u_obj) >= 32 || mp_obj_get_int(args[ARG_sda].u_obj) >= 32)
mp_raise_ValueError("[MAIXPY]SW_I2C: pin(scl/sda) < GPIOHS_MAX_PINNO(32)!");
}
#endif

Expand Down Expand Up @@ -614,14 +635,15 @@ STATIC mp_obj_t machine_i2c_init_helper(machine_hard_i2c_obj_t* self, mp_uint_t
}
// mp_hal_pin_open_drain(self->scl);
// mp_hal_pin_open_drain(self->sda);

// GPIO_DM_OUTPUT
fpioa_set_function(self->pin_scl, FUNC_GPIOHS0 + self->pin_scl);
gpiohs_set_pin(self->pin_scl, 1);
gpiohs_set_drive_mode(self->pin_scl, GPIO_DM_OUTPUT);
int ret1 = fpioa_set_function(self->pin_scl, FUNC_GPIOHS0 + self->gpio_scl);
gpiohs_set_pin(self->gpio_scl, 1);
gpiohs_set_drive_mode(self->gpio_scl, GPIO_DM_OUTPUT);

fpioa_set_function(self->pin_sda, FUNC_GPIOHS0 + self->pin_sda);
gpiohs_set_pin(self->pin_sda, 1);
gpiohs_set_drive_mode(self->pin_sda, GPIO_DM_OUTPUT);
int ret2 = fpioa_set_function(self->pin_sda, FUNC_GPIOHS0 + self->gpio_sda);
gpiohs_set_pin(self->gpio_sda, 1);
gpiohs_set_drive_mode(self->gpio_sda, GPIO_DM_OUTPUT);

mp_hal_i2c_stop(self); // ignore error
#endif
Expand Down

0 comments on commit 4b3778b

Please sign in to comment.