8000 py: Tidy up exception matching; allow matching of tuple of exceptions. · comfuture/micropython@4bcd04b · GitHub
[go: up one dir, main page]

Skip to content

Commit 4bcd04b

Browse files
committed
py: Tidy up exception matching; allow matching of tuple of exceptions.
Addresses issue micropython#864.
1 parent 16ef60f commit 4bcd04b

File tree

3 files changed

+24
-13
lines changed

3 files changed

+24
-13
lines changed

py/obj.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -458,7 +458,7 @@ mp_int_t mp_obj_int_get_checked(mp_const_obj_t self_in);
458458
#define mp_obj_is_native_exception_instance(o) (mp_obj_get_type(o)->make_new == mp_obj_exception_make_new)
459459
bool mp_obj_is_exception_type(mp_obj_t self_in);
460460
bool mp_obj_is_exception_instance(mp_obj_t self_in);
461-
bool mp_obj_exception_match(mp_obj_t exc, const mp_obj_type_t *exc_type);
461+
bool mp_obj_exception_match(mp_obj_t exc, mp_const_obj_t exc_type);
462462
void mp_obj_exception_clear_traceback(mp_obj_t self_in);
463463
void mp_obj_exception_add_traceback(mp_obj_t self_in, qstr file, mp_uint_t line, qstr block);
464464
void mp_obj_exception_get_traceback(mp_obj_t self_in, mp_uint_t *n, mp_uint_t **values);

py/objexcept.c

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -403,11 +403,15 @@ bool mp_obj_is_exception_instance(mp_obj_t self_in) {
403403
return mp_obj_is_exception_type(mp_obj_get_type(self_in));
404404
}
405405

406-
// return true if exception (type or instance) is a subclass of given
407-
// exception type.
408-
bool mp_obj_exception_match(mp_obj_t exc, const mp_obj_type_t *exc_type) {
409-
// TODO: move implementation from RT_BINARY_OP_EXCEPTION_MATCH here.
410-
return mp_binary_op(MP_BINARY_OP_EXCEPTION_MATCH, exc, (mp_obj_t)exc_type) == mp_const_true;
406+
// Return true if exception (type or instance) is a subclass of given
407+
// exception type. Assumes exc_type is a subclass of BaseException, as
408+
// defined by mp_obj_is_exception_type(exc_type).
409+
bool mp_obj_exception_match(mp_obj_t exc, mp_const_obj_t exc_type) {
410+
// if exc is an instance of an exception, then extract and use its type
411+
if (mp_obj_is_exception_instance(exc)) {
412+
exc = mp_obj_get_type(exc);
413+
}
414+
return mp_obj_is_subclass_fast(exc, exc_type);
411415
}
412416

413417
// traceback handling functions

py/runtime.c

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -263,18 +263,25 @@ mp_obj_t mp_binary_op(mp_uint_t op, mp_obj_t lhs, mp_obj_t rhs) {
263263
if (op == MP_BINARY_OP_EXCEPTION_MATCH) {
264264
// rhs must be issubclass(rhs, BaseException)
265265
if (mp_obj_is_exception_type(rhs)) {
266-
// if lhs is an instance of an exception, then extract and use its type
267-
if (mp_obj_is_exception_instance(lhs)) {
268-
lhs = mp_obj_get_type(lhs);
269-
}
270-
if (mp_obj_is_subclass_fast(lhs, rhs)) {
266+
if (mp_obj_exception_match(lhs, rhs)) {
271267
return mp_const_true;
272268
} else {
273269
return mp_const_false;
274270
}
271+
} else if (MP_OBJ_IS_TYPE(rhs, &mp_type_tuple)) {
272+
mp_obj_tuple_t *tuple = rhs;
273+
for (mp_uint_t i = 0; i < tuple->len; i++) {
274+
rhs = tuple->items[i];
275+
if (!mp_obj_is_exception_type(rhs)) {
276+
goto unsupported_op;
277+
}
278+
if (mp_obj_exception_match(lhs, rhs)) {
279+
return mp_const_true;
280+
}
281+
}
282+
return mp_const_false;
275283
}
276-
assert(0);
277-
return mp_const_false;
284+
goto unsupported_op;
278285
}
279286

280287
if (MP_OBJ_IS_SMALL_INT(lhs)) {

0 commit comments

Comments
 (0)
0