From e95da5b784b290c81cf670b7094d4ea8ea754bc5 Mon Sep 17 00:00:00 2001 From: Damien George Date: Tue, 15 Apr 2014 19:24:13 +0100 Subject: [PATCH] stmhal: Add I2C.scan method, to scan all devices on the bus. Simple way to find the address of an attached I2C device. --- stmhal/i2c.c | 25 +++++++++++++++++++++++-- stmhal/qstrdefsport.h | 1 + 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/stmhal/i2c.c b/stmhal/i2c.c index 65bc3600ef..c0d53c9a92 100644 --- a/stmhal/i2c.c +++ b/stmhal/i2c.c @@ -98,14 +98,13 @@ STATIC mp_obj_t pyb_i2c_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const return (mp_obj_t)i2c_obj; } +// Check if an I2C device responds to the given address. STATIC mp_obj_t pyb_i2c_is_ready(mp_obj_t self_in, mp_obj_t i2c_addr_o) { pyb_i2c_obj_t *self = self_in; machine_uint_t i2c_addr = mp_obj_get_int(i2c_addr_o) << 1; - //printf("IsDeviceReady\n"); for (int i = 0; i < 10; i++) { HAL_StatusTypeDef status = HAL_I2C_IsDeviceReady(self->i2c_handle, i2c_addr, 10, 200); - //printf(" got %d\n", status); if (status == HAL_OK) { return mp_const_true; } @@ -116,6 +115,27 @@ STATIC mp_obj_t pyb_i2c_is_ready(mp_obj_t self_in, mp_obj_t i2c_addr_o) { STATIC MP_DEFINE_CONST_FUN_OBJ_2(pyb_i2c_is_ready_obj, pyb_i2c_is_ready); +// Scan all I2C addresses from 0x01 to 0x7f and return a list of those that respond. +STATIC mp_obj_t pyb_i2c_scan(mp_obj_t self_in) { + pyb_i2c_obj_t *self = self_in; + + mp_obj_t list = mp_obj_new_list(0, NULL); + + for (uint addr = 1; addr <= 127; addr++) { + for (int i = 0; i < 10; i++) { + HAL_StatusTypeDef status = HAL_I2C_IsDeviceReady(self->i2c_handle, addr << 1, 10, 200); + if (status == HAL_OK) { + mp_obj_list_append(list, mp_obj_new_int(addr)); + break; + } + } + } + + return list; +} + +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pyb_i2c_scan_obj, pyb_i2c_scan); + STATIC mp_obj_t pyb_i2c_mem_read(uint n_args, const mp_obj_t *args) { pyb_i2c_obj_t *self = args[0]; machine_uint_t i2c_addr = mp_obj_get_int(args[1]) << 1; @@ -166,6 +186,7 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pyb_i2c_mem_write_obj, 4, 4, pyb_i2c_ STATIC const mp_map_elem_t pyb_i2c_locals_dict_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR_is_ready), (mp_obj_t)&pyb_i2c_is_ready_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_scan), (mp_obj_t)&pyb_i2c_scan_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_mem_read), (mp_obj_t)&pyb_i2c_mem_read_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_mem_write), (mp_obj_t)&pyb_i2c_mem_write_obj }, }; diff --git a/stmhal/qstrdefsport.h b/stmhal/qstrdefsport.h index 0dd8c2b61b..ab59699d7d 100644 --- a/stmhal/qstrdefsport.h +++ b/stmhal/qstrdefsport.h @@ -82,6 +82,7 @@ Q(MODE_EVT_RISING_FALLING) // for I2C object Q(I2C) Q(is_ready) +Q(scan) Q(mem_read) Q(mem_write)