Merge pull request #2626 from dhalbert/stat-for-shortint

avoid os.stat() int overflow on smallint-only builds
This commit is contained in:
Scott Shawcroft 2020-02-18 13:40:52 -08:00 committed by GitHub
commit 52d96ca151
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 23 additions and 11 deletions

View File

@ -345,14 +345,21 @@ STATIC mp_obj_t fat_vfs_stat(mp_obj_t vfs_in, mp_obj_t path_in) {
} else { } else {
mode |= MP_S_IFREG; mode |= MP_S_IFREG;
} }
mp_uint_t seconds = timeutils_seconds_since_epoch( #if MICROPY_LONGINT_IMPL == MICROPY_LONGINT_IMPL_NONE
1980 + ((fno.fdate >> 9) & 0x7f), // On non-longint builds, the number of seconds since 1970 (epoch) is too
(fno.fdate >> 5) & 0x0f, // large to fit in a smallint, so just return 31-DEC-1999 (0).
fno.fdate & 0x1f, mp_obj_t seconds = MP_OBJ_NEW_SMALL_INT(946684800);
(fno.ftime >> 11) & 0x1f, #else
(fno.ftime >> 5) & 0x3f, mp_obj_t seconds = mp_obj_new_int_from_uint(
2 * (fno.ftime & 0x1f) timeutils_seconds_since_epoch(
); 1980 + ((fno.fdate >> 9) & 0x7f),
(fno.fdate >> 5) & 0x0f,
fno.fdate & 0x1f,
(fno.ftime >> 11) & 0x1f,
(fno.ftime >> 5) & 0x3f,
2 * (fno.ftime & 0x1f)
));
#endif
t->items[0] = MP_OBJ_NEW_SMALL_INT(mode); // st_mode t->items[0] = MP_OBJ_NEW_SMALL_INT(mode); // st_mode
t->items[1] = MP_OBJ_NEW_SMALL_INT(0); // st_ino t->items[1] = MP_OBJ_NEW_SMALL_INT(0); // st_ino
t->items[2] = MP_OBJ_NEW_SMALL_INT(0); // st_dev t->items[2] = MP_OBJ_NEW_SMALL_INT(0); // st_dev
@ -360,9 +367,9 @@ STATIC mp_obj_t fat_vfs_stat(mp_obj_t vfs_in, mp_obj_t path_in) {
t->items[4] = MP_OBJ_NEW_SMALL_INT(0); // st_uid t->items[4] = MP_OBJ_NEW_SMALL_INT(0); // st_uid
t->items[5] = MP_OBJ_NEW_SMALL_INT(0); // st_gid t->items[5] = MP_OBJ_NEW_SMALL_INT(0); // st_gid
t->items[6] = mp_obj_new_int_from_uint(fno.fsize); // st_size t->items[6] = mp_obj_new_int_from_uint(fno.fsize); // st_size
t->items[7] = mp_obj_new_int_from_uint(seconds); // st_atime t->items[7] = seconds; // st_atime
t->items[8] = mp_obj_new_int_from_uint(seconds); // st_mtime t->items[8] = seconds; // st_mtime
t->items[9] = mp_obj_new_int_from_uint(seconds); // st_ctime t->items[9] = seconds; // st_ctime
return MP_OBJ_FROM_PTR(t); return MP_OBJ_FROM_PTR(t);
} }

View File

@ -143,6 +143,11 @@ MP_DEFINE_CONST_FUN_OBJ_1(os_rmdir_obj, os_rmdir);
//| //|
//| Get the status of a file or directory. //| Get the status of a file or directory.
//| //|
//| .. note:: On builds without long integers, the number of seconds
//| for contemporary dates will not fit in a small integer.
//| So the time fields return 946684800,
//| which is the number of seconds corresponding to 1999-12-31.
//|
mp_obj_t os_stat(mp_obj_t path_in) { mp_obj_t os_stat(mp_obj_t path_in) {
const char *path = mp_obj_str_get_str(path_in); const char *path = mp_obj_str_get_str(path_in);
return common_hal_os_stat(path); return common_hal_os_stat(path);