Skip to content

Commit 17e24b8

Browse files
committed
i2ctarget: Add deinit() to I2CTargetRequest; remove close()
1 parent 2959f0a commit 17e24b8

File tree

1 file changed

+50
-15
lines changed

1 file changed

+50
-15
lines changed

shared-bindings/i2ctarget/I2CTarget.c

Lines changed: 50 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121

2222
static mp_obj_t mp_obj_new_i2ctarget_i2c_target_request(i2ctarget_i2c_target_obj_t *target, uint8_t address, bool is_read, bool is_restart) {
2323
i2ctarget_i2c_target_request_obj_t *self =
24-
mp_obj_malloc(i2ctarget_i2c_target_request_obj_t, &i2ctarget_i2c_target_request_type);
24+
mp_obj_malloc_with_finaliser(i2ctarget_i2c_target_request_obj_t, &i2ctarget_i2c_target_request_type);
2525
self->target = target;
2626
self->address = address;
2727
self->is_read = is_read;
@@ -200,7 +200,7 @@ static MP_DEFINE_CONST_DICT(i2ctarget_i2c_target_locals_dict, i2ctarget_i2c_targ
200200
MP_DEFINE_CONST_OBJ_TYPE(
201201
i2ctarget_i2c_target_type,
202202
MP_QSTR_I2CTarget,
203-
MP_TYPE_FLAG_NONE,
203+
MP_TYPE_FLAG_HAS_SPECIAL_ACCESSORS,
204204
make_new, i2ctarget_i2c_target_make_new,
205205
locals_dict, &i2ctarget_i2c_target_locals_dict
206206
);
@@ -222,6 +222,26 @@ static mp_obj_t i2ctarget_i2c_target_request_make_new(const mp_obj_type_t *type,
222222
return mp_obj_new_i2ctarget_i2c_target_request(args[0], mp_obj_get_int(args[1]), mp_obj_is_true(args[2]), mp_obj_is_true(args[3]));
223223
}
224224

225+
//| def deinit(self) -> None:
226+
//| """Disconnects from parent `I2CTarget`.
227+
//| Called by `__exit__()` to indicate the `I2CTargetRequest` is no longer useful."""
228+
//| ...
229+
//|
230+
static mp_obj_t i2ctarget_i2c_target_request_deinit(mp_obj_t self_in) {
231+
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
232+
self->target = NULL;
233+
234+
return mp_const_none;
235+
}
236+
MP_DEFINE_CONST_FUN_OBJ_1(i2ctarget_i2c_target_request_deinit_obj, i2ctarget_i2c_target_request_deinit);
237+
238+
static void target_request_check_for_deinit(i2ctarget_i2c_target_request_obj_t *self) {
239+
if (self->target == NULL) {
240+
raise_deinited_error();
241+
}
242+
check_for_deinit(self->target);
243+
}
244+
225245
//| def __enter__(self) -> I2CTargetRequest:
226246
//| """No-op used in Context Managers."""
227247
//| ...
@@ -238,7 +258,7 @@ static mp_obj_t i2ctarget_i2c_target_request_make_new(const mp_obj_type_t *type,
238258
//| """The I2C address of the request."""
239259
static mp_obj_t i2ctarget_i2c_target_request_get_address(mp_obj_t self_in) {
240260
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
241-
check_for_deinit(self->target);
261+
target_request_check_for_deinit(self);
242262

243263
return mp_obj_new_int(self->address);
244264
}
@@ -248,7 +268,7 @@ MP_DEFINE_CONST_PROP_GET(i2ctarget_i2c_target_request_address_obj, i2ctarget_i2c
248268
//| """The I2C main controller is reading from this target."""
249269
static mp_obj_t i2ctarget_i2c_target_request_get_is_read(mp_obj_t self_in) {
250270
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
251-
check_for_deinit(self->target);
271+
target_request_check_for_deinit(self);
252272

253273
return mp_obj_new_bool(self->is_read);
254274
}
@@ -259,7 +279,7 @@ MP_DEFINE_CONST_PROP_GET(i2ctarget_i2c_target_request_is_read_obj, i2ctarget_i2c
259279
//|
260280
static mp_obj_t i2ctarget_i2c_target_request_get_is_restart(mp_obj_t self_in) {
261281
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
262-
check_for_deinit(self->target);
282+
target_request_check_for_deinit(self);
263283

264284
return mp_obj_new_bool(self->is_restart);
265285
}
@@ -276,7 +296,7 @@ MP_DEFINE_CONST_PROP_GET(i2ctarget_i2c_target_request_is_restart_obj, i2ctarget_
276296
//|
277297
static mp_obj_t i2ctarget_i2c_target_request_read(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) {
278298
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(pos_args[0]);
279-
check_for_deinit(self->target);
299+
target_request_check_for_deinit(self);
280300

281301
enum { ARG_n, ARG_ack };
282302
static const mp_arg_t allowed_args[] = {
@@ -335,7 +355,7 @@ MP_DEFINE_CONST_FUN_OBJ_KW(i2ctarget_i2c_target_request_read_obj, 1, i2ctarget_i
335355
//|
336356
static mp_obj_t i2ctarget_i2c_target_request_write(mp_obj_t self_in, mp_obj_t buf_in) {
337357
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
338-
check_for_deinit(self->target);
358+
target_request_check_for_deinit(self);
339359

340360
if (!self->is_read) {
341361
mp_raise_OSError(MP_EACCES);
@@ -370,7 +390,7 @@ static MP_DEFINE_CONST_FUN_OBJ_2(i2ctarget_i2c_target_request_write_obj, i2ctarg
370390
//|
371391
static mp_obj_t i2ctarget_i2c_target_request_ack(uint n_args, const mp_obj_t *args) {
372392
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(args[0]);
373-
check_for_deinit(self->target);
393+
target_request_check_for_deinit(self);
374394

375395
bool ack = (n_args == 1) ? true : mp_obj_is_true(args[1]);
376396

@@ -383,25 +403,40 @@ static mp_obj_t i2ctarget_i2c_target_request_ack(uint n_args, const mp_obj_t *ar
383403
}
384404
MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(i2ctarget_i2c_target_request_ack_obj, 1, 2, i2ctarget_i2c_target_request_ack);
385405

386-
static mp_obj_t i2ctarget_i2c_target_request_close(mp_obj_t self_in) {
387-
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(self_in);
388-
check_for_deinit(self->target);
406+
//| def __enter__(self) -> I2CTargetRequest:
407+
//| """No-op used in Context Managers."""
408+
//| ...
409+
//|
410+
// Provided by context manager helper.
411+
412+
//| def __exit__(self) -> None:
413+
//| """Close and deinit the request."""
414+
//| ...
415+
//|
416+
static mp_obj_t i2ctarget_i2c_target_request__exit__(size_t n_args, const mp_obj_t *args) {
417+
i2ctarget_i2c_target_request_obj_t *self = MP_OBJ_TO_PTR(args[0]);
418+
target_request_check_for_deinit(self);
389419

390-
common_hal_i2ctarget_i2c_target_close(self->target);
420+
i2ctarget_i2c_target_obj_t *target = self->target;
421+
// Deinit target request first in case _close() fails.
422+
i2ctarget_i2c_target_request_deinit(args[0]);
423+
424+
common_hal_i2ctarget_i2c_target_close(target);
391425
return mp_const_none;
392426
}
393-
static MP_DEFINE_CONST_FUN_OBJ_1(i2ctarget_i2c_target_request_close_obj, i2ctarget_i2c_target_request_close);
427+
static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(i2ctarget_i2c_target_request___exit___obj, 4, 4, i2ctarget_i2c_target_request__exit__);
394428

395429
static const mp_rom_map_elem_t i2ctarget_i2c_target_request_locals_dict_table[] = {
396430
{ MP_ROM_QSTR(MP_QSTR___enter__), MP_ROM_PTR(&default___enter___obj) },
397-
{ MP_ROM_QSTR(MP_QSTR___exit__), MP_ROM_PTR(&default___exit___obj) },
431+
{ MP_ROM_QSTR(MP_QSTR___exit__), MP_ROM_PTR(&i2ctarget_i2c_target_request___exit___obj) },
432+
{ MP_ROM_QSTR(MP_QSTR_deinit), MP_ROM_PTR(&i2ctarget_i2c_target_request_deinit_obj) },
433+
{ MP_ROM_QSTR(MP_QSTR__del__), MP_ROM_PTR(&i2ctarget_i2c_target_request_deinit_obj) },
398434
{ MP_ROM_QSTR(MP_QSTR_address), MP_ROM_PTR(&i2ctarget_i2c_target_request_address_obj) },
399435
{ MP_ROM_QSTR(MP_QSTR_is_read), MP_ROM_PTR(&i2ctarget_i2c_target_request_is_read_obj) },
400436
{ MP_ROM_QSTR(MP_QSTR_is_restart), MP_ROM_PTR(&i2ctarget_i2c_target_request_is_restart_obj) },
401437
{ MP_ROM_QSTR(MP_QSTR_read), MP_ROM_PTR(&i2ctarget_i2c_target_request_read_obj) },
402438
{ MP_ROM_QSTR(MP_QSTR_write), MP_ROM_PTR(&i2ctarget_i2c_target_request_write_obj) },
403439
{ MP_ROM_QSTR(MP_QSTR_ack), MP_ROM_PTR(&i2ctarget_i2c_target_request_ack_obj) },
404-
{ MP_ROM_QSTR(MP_QSTR_close), MP_ROM_PTR(&i2ctarget_i2c_target_request_close_obj) },
405440
};
406441

407442
static MP_DEFINE_CONST_DICT(i2ctarget_i2c_target_request_locals_dict, i2ctarget_i2c_target_request_locals_dict_table);

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy