unix/modusocket: Initial implementation of socket.settimeout().
@@ -93,6 +93,11 @@ STATIC mp_uint_t socket_read(mp_obj_t o_in, void *buf, mp_uint_t size, int *errc
mp_int_t r = read(o->fd, buf, size);
if (r == -1) {
*errcode = errno;
+
+ if (*errcode == EAGAIN) {
+ *errcode = MP_ETIMEDOUT;
+ }
+
return MP_STREAM_ERROR;
}
return r;
@@ -103,6 +108,11 @@ STATIC mp_uint_t socket_write(mp_obj_t o_in, const void *buf, mp_uint_t size, in
mp_int_t r = write(o->fd, buf, size);
if (r == -1) {
*errcode = errno;
+
+ if (*errcode == EAGAIN) {
+ *errcode = MP_ETIMEDOUT;
+ }
+
return MP_STREAM_ERROR;
}
return r;
@@ -314,6 +324,28 @@ STATIC mp_obj_t socket_setblocking(mp_obj_t self_in, mp_obj_t flag_in) {
}
STATIC MP_DEFINE_CONST_FUN_OBJ_2(socket_setblocking_obj, socket_setblocking);
+STATIC mp_obj_t socket_settimeout(mp_obj_t self_in, mp_obj_t timeout_in) {
+ mp_obj_socket_t *self = MP_OBJ_TO_PTR(self_in);
+ struct timeval tv = {0,};
+ if (timeout_in == mp_const_none) {
+ setsockopt(self->fd, SOL_SOCKET, SO_RCVTIMEO, NULL, 0);
+ setsockopt(self->fd, SOL_SOCKET, SO_SNDTIMEO, NULL, 0);
+ } else {
+ tv.tv_sec = mp_obj_get_int(timeout_in);
+
+ #if MICROPY_PY_BUILTINS_FLOAT
+ tv.tv_usec = (mp_obj_get_float(timeout_in) - tv.tv_sec) * 1000000;
+ #endif
+
+ setsockopt(self->fd, SOL_SOCKET, SO_RCVTIMEO,
+ &tv, sizeof(struct timeval));
+ setsockopt(self->fd, SOL_SOCKET, SO_SNDTIMEO,
+ &tv, sizeof(struct timeval));
+ }
+ return mp_const_none;
+}
+STATIC MP_DEFINE_CONST_FUN_OBJ_2(socket_settimeout_obj, socket_settimeout);
+
STATIC mp_obj_t socket_makefile(size_t n_args, const mp_obj_t *args) {
// TODO: CPython explicitly says that closing returned object doesn't close
// the original socket (Python2 at all says that fd is dup()ed). But we
@@ -369,6 +401,7 @@ STATIC const mp_rom_map_elem_t usocket_locals_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_sendto), MP_ROM_PTR(&socket_sendto_obj) },
{ MP_ROM_QSTR(MP_QSTR_setsockopt), MP_ROM_PTR(&socket_setsockopt_obj) },
{ MP_ROM_QSTR(MP_QSTR_setblocking), MP_ROM_PTR(&socket_setblocking_obj) },
+ { MP_ROM_QSTR(MP_QSTR_settimeout), MP_ROM_PTR(&socket_settimeout_obj) },
{ MP_ROM_QSTR(MP_QSTR_close), MP_ROM_PTR(&mp_stream_close_obj) },
};
