diff options
author | Damien George <damien.p.george@gmail.com> | 2017-05-05 23:32:44 +1000 |
---|---|---|
committer | Damien George <damien.p.george@gmail.com> | 2017-05-10 11:39:28 +1000 |
commit | d4cd4831b01ff87b4a9f84bb88b165e3b156b3b4 (patch) | |
tree | 18675e38292c3b9bb83c1e2e35de08147a23e37f /extmod/vfs_fat_misc.c | |
parent | 87283c1974188707b436eebf2a04d4555a26dcca (diff) | |
download | micropython-d4cd4831b01ff87b4a9f84bb88b165e3b156b3b4.tar.gz micropython-d4cd4831b01ff87b4a9f84bb88b165e3b156b3b4.zip |
extmod/vfs_fat: Replace listdir() with implementation of ilistdir().
VfsFat no longer has the listdir() method. Rather, if listdir()
functionality is needed then one should use uos.listdir() which will call
VfsFat.ilistdir().
Diffstat (limited to 'extmod/vfs_fat_misc.c')
-rw-r--r-- | extmod/vfs_fat_misc.c | 73 |
1 files changed, 43 insertions, 30 deletions
diff --git a/extmod/vfs_fat_misc.c b/extmod/vfs_fat_misc.c index 19db99c7f7..5b906189f2 100644 --- a/extmod/vfs_fat_misc.c +++ b/extmod/vfs_fat_misc.c @@ -34,51 +34,64 @@ #include "extmod/vfs_fat.h" #include "py/lexer.h" -// TODO: actually, the core function should be ilistdir() - -mp_obj_t fat_vfs_listdir2(fs_user_mount_t *vfs, const char *path, bool is_str_type) { - FRESULT res; - FILINFO fno; +typedef struct _mp_vfs_fat_ilistdir_it_t { + mp_obj_base_t base; + mp_fun_1_t iternext; + bool is_str; FF_DIR dir; +} mp_vfs_fat_ilistdir_it_t; - res = f_opendir(&vfs->fatfs, &dir, path); - if (res != FR_OK) { - mp_raise_OSError(fresult_to_errno_table[res]); - } - - mp_obj_t dir_list = mp_obj_new_list(0, NULL); +STATIC mp_obj_t mp_vfs_fat_ilistdir_it_iternext(mp_obj_t self_in) { + mp_vfs_fat_ilistdir_it_t *self = MP_OBJ_TO_PTR(self_in); for (;;) { - res = f_readdir(&dir, &fno); /* Read a directory item */ - if (res != FR_OK || fno.fname[0] == 0) break; /* Break on error or end of dir */ - if (fno.fname[0] == '.' && fno.fname[1] == 0) continue; /* Ignore . entry */ - if (fno.fname[0] == '.' && fno.fname[1] == '.' && fno.fname[2] == 0) continue; /* Ignore .. entry */ - + FILINFO fno; + FRESULT res = f_readdir(&self->dir, &fno); char *fn = fno.fname; + if (res != FR_OK || fn[0] == 0) { + // stop on error or end of dir + break; + } + if (fn[0] == '.' && (fn[1] == 0 || (fn[1] == '.' && fn[2] == 0))) { + // skip . and .. + continue; + } - /* + // make 3-tuple with info about this entry + mp_obj_tuple_t *t = MP_OBJ_TO_PTR(mp_obj_new_tuple(3, NULL)); + if (self->is_str) { + t->items[0] = mp_obj_new_str(fn, strlen(fn), false); + } else { + t->items[0] = mp_obj_new_bytes((const byte*)fn, strlen(fn)); + } if (fno.fattrib & AM_DIR) { // dir + t->items[1] = MP_OBJ_NEW_SMALL_INT(MP_S_IFDIR); } else { // file + t->items[1] = MP_OBJ_NEW_SMALL_INT(MP_S_IFREG); } - */ + t->items[2] = MP_OBJ_NEW_SMALL_INT(0); // no inode number - // make a string object for this entry - mp_obj_t entry_o; - if (is_str_type) { - entry_o = mp_obj_new_str(fn, strlen(fn), false); - } else { - entry_o = mp_obj_new_bytes((const byte*)fn, strlen(fn)); - } - - // add the entry to the list - mp_obj_list_append(dir_list, entry_o); + return MP_OBJ_FROM_PTR(t); } - f_closedir(&dir); + // ignore error because we may be closing a second time + f_closedir(&self->dir); - return dir_list; + return MP_OBJ_STOP_ITERATION; +} + +mp_obj_t fat_vfs_ilistdir2(fs_user_mount_t *vfs, const char *path, bool is_str_type) { + mp_vfs_fat_ilistdir_it_t *iter = m_new_obj(mp_vfs_fat_ilistdir_it_t); + iter->base.type = &mp_type_polymorph_iter; + iter->iternext = mp_vfs_fat_ilistdir_it_iternext; + iter->is_str = is_str_type; + FRESULT res = f_opendir(&vfs->fatfs, &iter->dir, path); + if (res != FR_OK) { + mp_raise_OSError(fresult_to_errno_table[res]); + } + return MP_OBJ_FROM_PTR(iter); } mp_import_stat_t fat_vfs_import_stat(fs_user_mount_t *vfs, const char *path) { |