diff options
-rw-r--r-- | stmhal/Makefile | 1 | ||||
-rw-r--r-- | stmhal/fatfs/src/ff.c | 27 | ||||
-rw-r--r-- | stmhal/fatfs/src/ff.h | 2 | ||||
-rw-r--r-- | stmhal/ffconf.c | 69 | ||||
-rw-r--r-- | stmhal/ffconf.h | 2 | ||||
-rw-r--r-- | stmhal/main.c | 58 | ||||
-rw-r--r-- | stmhal/modos.c | 91 | ||||
-rw-r--r-- | stmhal/modpyb.c | 2 | ||||
-rw-r--r-- | stmhal/qstrdefsport.h | 10 |
9 files changed, 202 insertions, 60 deletions
diff --git a/stmhal/Makefile b/stmhal/Makefile index 64e38e122a..892ed74b3a 100644 --- a/stmhal/Makefile +++ b/stmhal/Makefile @@ -104,6 +104,7 @@ SRC_C = \ file.c \ sdcard.c \ diskio.c \ + ffconf.c \ lcd.c \ accel.c \ servo.c \ diff --git a/stmhal/fatfs/src/ff.c b/stmhal/fatfs/src/ff.c index 75b58718b4..5b0ba240c6 100644 --- a/stmhal/fatfs/src/ff.c +++ b/stmhal/fatfs/src/ff.c @@ -106,6 +106,8 @@ / Fixed f_open(), f_mkdir() and f_setlabel() can return incorrect error code.
/---------------------------------------------------------------------------*/
+#include <string.h>
+
#include "ff.h" /* Declarations of FatFs API */
#include "diskio.h" /* Declarations of disk I/O functions */
@@ -485,7 +487,7 @@ static WORD Fsid; /* File system mount ID */
#if _FS_RPATH && _VOLUMES >= 2
-static
+//static
BYTE CurrVol; /* Current drive */
#endif
@@ -1992,6 +1994,8 @@ void get_fileinfo ( /* No return code */ /* Get logical drive number from path name */
/*-----------------------------------------------------------------------*/
+/* now implemented by us for configurability of path names */
+#if 0
static
int get_ldnumber ( /* Returns logical drive number (-1:invalid drive) */
const TCHAR** path /* Pointer to pointer to the path name */
@@ -2016,7 +2020,7 @@ int get_ldnumber ( /* Returns logical drive number (-1:invalid drive) */ return vol;
}
-
+#endif
@@ -2131,7 +2135,7 @@ FRESULT find_volume ( /* FR_OK(0): successful, !=0: any error occurred */ /* Get logical drive number from the path name */
*rfs = 0;
- vol = get_ldnumber(path);
+ vol = ff_get_ldnumber(path);
if (vol < 0) return FR_INVALID_DRIVE;
/* Check if the file system object is valid or not */
@@ -2326,7 +2330,7 @@ FRESULT f_mount ( FRESULT res;
const TCHAR *rp = path;
- vol = get_ldnumber(&rp);
+ vol = ff_get_ldnumber(&rp);
if (vol < 0) return FR_INVALID_DRIVE;
cfs = FatFs[vol]; /* Pointer to fs object */
@@ -2813,7 +2817,7 @@ FRESULT f_chdrive ( int vol;
- vol = get_ldnumber(&path);
+ vol = ff_get_ldnumber(&path);
if (vol < 0) return FR_INVALID_DRIVE;
CurrVol = (BYTE)vol;
@@ -2912,11 +2916,22 @@ FRESULT f_getcwd ( tp = buff;
if (res == FR_OK) {
#if _VOLUMES >= 2
+ #if 0
*tp++ = '0' + CurrVol; /* Put drive number */
*tp++ = ':';
+ #endif
+ if (CurrVol == 0) {
+ memcpy(tp, "/flash", 6);
+ tp += 6;
+ } else {
+ memcpy(tp, "/sd", 3);
+ tp += 3;
+ }
#endif
if (i == len) { /* Root-directory */
+ #if 0
*tp++ = '/';
+ #endif
} else { /* Sub-directroy */
do /* Add stacked path str */
*tp++ = buff[i++];
@@ -3937,7 +3952,7 @@ FRESULT f_mkfs ( /* Check mounted drive and clear work area */
- vol = get_ldnumber(&path);
+ vol = ff_get_ldnumber(&path);
if (vol < 0) return FR_INVALID_DRIVE;
if (sfd > 1) return FR_INVALID_PARAMETER;
if (au & (au - 1)) return FR_INVALID_PARAMETER;
diff --git a/stmhal/fatfs/src/ff.h b/stmhal/fatfs/src/ff.h index 726d899a97..a56161da49 100644 --- a/stmhal/fatfs/src/ff.h +++ b/stmhal/fatfs/src/ff.h @@ -288,6 +288,8 @@ int ff_del_syncobj (_SYNC_t sobj); /* Delete a sync object */ #endif
+/* Returns logical drive number (-1:invalid drive) */
+int ff_get_ldnumber(const TCHAR** path);
/*--------------------------------------------------------------*/
diff --git a/stmhal/ffconf.c b/stmhal/ffconf.c new file mode 100644 index 0000000000..8f24ae822e --- /dev/null +++ b/stmhal/ffconf.c @@ -0,0 +1,69 @@ +/* + * This file is part of the Micro Python project, http://micropython.org/ + * + * The MIT License (MIT) + * + * Copyright (c) 2013, 2014 Damien P. George + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +#include <string.h> + +#include "mpconfigport.h" +#include "ff.h" +#include "ffconf.h" + +extern BYTE CurrVol; + +// "path" is the path to lookup; will advance this pointer beyond the volume name. +// Returns logical drive number (-1 means invalid path). +int ff_get_ldnumber (const TCHAR** path) { + if (!(*path)) { + return -1; + } + + if (**path != '/') { +#if _FS_RPATH + return CurrVol; +#else + return -1; +#endif + } else if (strncmp(*path, "/flash", 6) == 0) { + if ((*path)[6] == '/') { + *path += 6; + } else if ((*path)[6] == '\0') { + *path = "/"; + } else { + return -1; + } + return 0; + } else if (strncmp(*path, "/sd", 3) == 0) { + if ((*path)[3] == '/') { + *path += 3; + } else if ((*path)[3] == '\0') { + *path = "/"; + } else { + return -1; + } + return 1; + } else { + return -1; + } +} diff --git a/stmhal/ffconf.h b/stmhal/ffconf.h index 955d4e505e..4e01423ef8 100644 --- a/stmhal/ffconf.h +++ b/stmhal/ffconf.h @@ -143,7 +143,7 @@ / This option has no effect when _LFN_UNICODE is 0. */ -#define _FS_RPATH 0 /* 0 to 2 */ +#define _FS_RPATH 2 /* 0 to 2 */ /* The _FS_RPATH option configures relative path feature. / / 0: Disable relative path feature and remove related functions. diff --git a/stmhal/main.c b/stmhal/main.c index 2cc463462d..183f11b7a0 100644 --- a/stmhal/main.c +++ b/stmhal/main.c @@ -332,8 +332,9 @@ soft_reset: qstr_init(); mp_init(); mp_obj_list_init(mp_sys_path, 0); - mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR_0_colon__slash_)); - mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR_0_colon__slash_lib)); + mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR_)); // current dir (or base dir of the script) + mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR__slash_flash)); + mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR__slash_flash_slash_lib)); mp_obj_list_init(mp_sys_argv, 0); readline_init(); @@ -344,7 +345,7 @@ soft_reset: // local filesystem init { // try to mount the flash - FRESULT res = f_mount(&fatfs0, "0:", 1); + FRESULT res = f_mount(&fatfs0, "/flash", 1); if (reset_mode == 3 || res == FR_NO_FILESYSTEM) { // no filesystem, or asked to reset it, so create a fresh one @@ -352,7 +353,7 @@ soft_reset: led_state(PYB_LED_R2, 1); uint32_t start_tick = HAL_GetTick(); - res = f_mkfs("0:", 0, 0); + res = f_mkfs("/flash", 0, 0); if (res == FR_OK) { // success creating fresh LFS } else { @@ -361,19 +362,19 @@ soft_reset: // create empty main.py FIL fp; - f_open(&fp, "0:/main.py", FA_WRITE | FA_CREATE_ALWAYS); + f_open(&fp, "/flash/main.py", FA_WRITE | FA_CREATE_ALWAYS); UINT n; f_write(&fp, fresh_main_py, sizeof(fresh_main_py) - 1 /* don't count null terminator */, &n); // TODO check we could write n bytes f_close(&fp); // create .inf driver file - f_open(&fp, "0:/pybcdc.inf", FA_WRITE | FA_CREATE_ALWAYS); + f_open(&fp, "/flash/pybcdc.inf", FA_WRITE | FA_CREATE_ALWAYS); f_write(&fp, fresh_pybcdc_inf, sizeof(fresh_pybcdc_inf) - 1 /* don't count null terminator */, &n); f_close(&fp); // create readme file - f_open(&fp, "0:/README.txt", FA_WRITE | FA_CREATE_ALWAYS); + f_open(&fp, "/flash/README.txt", FA_WRITE | FA_CREATE_ALWAYS); f_write(&fp, fresh_readme_txt, sizeof(fresh_readme_txt) - 1 /* don't count null terminator */, &n); f_close(&fp); @@ -387,14 +388,14 @@ soft_reset: } } - // make sure we have a 0:/boot.py + // make sure we have a /flash/boot.py { FILINFO fno; #if _USE_LFN fno.lfname = NULL; fno.lfsize = 0; #endif - FRESULT res = f_stat("0:/boot.py", &fno); + FRESULT res = f_stat("/flash/boot.py", &fno); if (res == FR_OK) { if (fno.fattrib & AM_DIR) { // exists as a directory @@ -411,7 +412,7 @@ soft_reset: uint32_t start_tick = HAL_GetTick(); FIL fp; - f_open(&fp, "0:/boot.py", FA_WRITE | FA_CREATE_ALWAYS); + f_open(&fp, "/flash/boot.py", FA_WRITE | FA_CREATE_ALWAYS); UINT n; f_write(&fp, fresh_boot_py, sizeof(fresh_boot_py) - 1 /* don't count null terminator */, &n); // TODO check we could write n bytes @@ -424,21 +425,25 @@ soft_reset: } // root device defaults to internal flash filesystem - uint root_device = 0; + f_chdrive("/flash"); #if defined(USE_DEVICE_MODE) usb_storage_medium_t usb_medium = USB_STORAGE_MEDIUM_FLASH; #endif #if MICROPY_HW_HAS_SDCARD - // if an SD card is present then mount it on 1:/ + // if an SD card is present then mount it on /sd/ if (reset_mode == 1 && sdcard_is_present()) { - FRESULT res = f_mount(&fatfs1, "1:", 1); + FRESULT res = f_mount(&fatfs1, "/sd", 1); if (res != FR_OK) { printf("[SD] could not mount SD card\n"); } else { // use SD card as root device - root_device = 1; + f_chdrive("/sd"); + + // TODO these should go before the /flash entries in the path + mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR__slash_sd)); + mp_obj_list_append(mp_sys_path, MP_OBJ_NEW_QSTR(MP_QSTR__slash_sd_slash_lib)); if (first_soft_reset) { // use SD card as medium for the USB MSD @@ -453,17 +458,12 @@ soft_reset: (void)first_soft_reset; #endif - // run <root>:/boot.py, if it exists + // run boot.py, if it exists if (reset_mode == 1) { - const char *boot_file; - if (root_device == 0) { - boot_file = "0:/boot.py"; - } else { - boot_file = "1:/boot.py"; - } - FRESULT res = f_stat(boot_file, NULL); + const char *boot_py = "boot.py"; + FRESULT res = f_stat(boot_py, NULL); if (res == FR_OK) { - if (!pyexec_file(boot_file)) { + if (!pyexec_file(boot_py)) { flash_error(4); } } @@ -518,20 +518,18 @@ soft_reset: // now that everything is initialised, run main script if (reset_mode == 1 && pyexec_mode_kind == PYEXEC_MODE_FRIENDLY_REPL) { - vstr_t *vstr = vstr_new(); - vstr_printf(vstr, "%d:/", root_device); + const char *main_py; if (pyb_config_main == MP_OBJ_NULL) { - vstr_add_str(vstr, "main.py"); + main_py = "main.py"; } else { - vstr_add_str(vstr, mp_obj_str_get_str(pyb_config_main)); + main_py = mp_obj_str_get_str(pyb_config_main); } - FRESULT res = f_stat(vstr_str(vstr), NULL); + FRESULT res = f_stat(main_py, NULL); if (res == FR_OK) { - if (!pyexec_file(vstr_str(vstr))) { + if (!pyexec_file(main_py)) { flash_error(3); } } - vstr_free(vstr); } #if MICROPY_HW_ENABLE_CC3K diff --git a/stmhal/modos.c b/stmhal/modos.c index 35979ae972..67daf92504 100644 --- a/stmhal/modos.c +++ b/stmhal/modos.c @@ -38,22 +38,64 @@ #include "storage.h" #include "ff.h" #include "file.h" +#include "sdcard.h" #include "portmodules.h" #if _USE_LFN static char lfn[_MAX_LFN + 1]; /* Buffer to store the LFN */ #endif +STATIC mp_obj_t os_chdir(mp_obj_t path_in) { + const char *path; + path = mp_obj_str_get_str(path_in); + + FRESULT res = f_chdrive(path); + + if (res == FR_OK) { + res = f_chdir(path); + } + + if (res != FR_OK) { + // TODO should be mp_type_FileNotFoundError + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_OSError, "No such file or directory: '%s'", path)); + } + + return mp_const_none; +} +STATIC MP_DEFINE_CONST_FUN_OBJ_1(os_chdir_obj, os_chdir); + +STATIC mp_obj_t os_getcwd(void) { + char buf[MICROPY_ALLOC_PATH_MAX + 1]; + FRESULT res = f_getcwd(buf, sizeof buf); + + if (res != FR_OK) { + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_OSError, MP_OBJ_NEW_SMALL_INT(fresult_to_errno_table[res]))); + } + + return mp_obj_new_str(buf, strlen(buf), false); +} +STATIC MP_DEFINE_CONST_FUN_OBJ_0(os_getcwd_obj, os_getcwd); + STATIC mp_obj_t os_listdir(uint n_args, const mp_obj_t *args) { - const mp_obj_type_t *local_str_type = &mp_type_str; + bool is_str_type = true; const char *path; if (n_args == 1) { if (mp_obj_get_type(args[0]) == &mp_type_bytes) { - local_str_type = &mp_type_bytes; + is_str_type = false; } path = mp_obj_str_get_str(args[0]); } else { - path = "0:"; + path = ""; + } + + // "hack" to list root directory + if (path[0] == '/' && path[1] == '\0') { + mp_obj_t dir_list = mp_obj_new_list(0, NULL); + mp_obj_list_append(dir_list, MP_OBJ_NEW_QSTR(MP_QSTR_flash)); + if (sdcard_is_present()) { // TODO this is not the correct logic to check for /sd + mp_obj_list_append(dir_list, MP_OBJ_NEW_QSTR(MP_QSTR_sd)); + } + return dir_list; } FRESULT res; @@ -72,11 +114,6 @@ STATIC mp_obj_t os_listdir(uint n_args, const mp_obj_t *args) { mp_obj_t dir_list = mp_obj_new_list(0, NULL); - uint path_len = strlen(path); - if (path[path_len - 1] == '/') { - path_len--; - } - 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 */ @@ -89,20 +126,24 @@ STATIC mp_obj_t os_listdir(uint n_args, const mp_obj_t *args) { char *fn = fno.fname; #endif - if (fno.fattrib & AM_DIR) { /* It is a directory */ - } else { /* It is a file. */ + /* + if (fno.fattrib & AM_DIR) { + // dir + } else { + // file } + */ // make a string object for this entry - byte *data; - uint fn_len = strlen(fn); - mp_obj_t entry_o = mp_obj_str_builder_start(local_str_type, path_len + 1 + fn_len, &data); - memcpy(data, path, path_len); - data[path_len] = '/'; - memcpy(data + path_len + 1, fn, fn_len); + 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, mp_obj_str_builder_end(entry_o)); + mp_obj_list_append(dir_list, entry_o); } f_closedir(&dir); @@ -161,9 +202,17 @@ STATIC mp_obj_t os_stat(mp_obj_t path_in) { fno.lfsize = 0; #endif - FRESULT res = f_stat(path, &fno); - if (res != FR_OK) { - nlr_raise(mp_obj_new_exception_arg1(&mp_type_OSError, MP_OBJ_NEW_SMALL_INT(fresult_to_errno_table[res]))); + if (path[0] == '/' && path[1] == '\0') { + // stat root directory + fno.fsize = 0; + fno.fdate = 0; + fno.ftime = 0; + fno.fattrib = AM_DIR; + } else { + FRESULT res = f_stat(path, &fno); + if (res != FR_OK) { + nlr_raise(mp_obj_new_exception_arg1(&mp_type_OSError, MP_OBJ_NEW_SMALL_INT(fresult_to_errno_table[res]))); + } } mp_obj_tuple_t *t = mp_obj_new_tuple(10, NULL); @@ -216,6 +265,8 @@ STATIC MP_DEFINE_CONST_FUN_OBJ_1(os_urandom_obj, os_urandom); STATIC const mp_map_elem_t os_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR___name__), MP_OBJ_NEW_QSTR(MP_QSTR_os) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_chdir), (mp_obj_t)&os_chdir_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_getcwd), (mp_obj_t)&os_getcwd_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_listdir), (mp_obj_t)&os_listdir_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_mkdir), (mp_obj_t)&os_mkdir_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_remove), (mp_obj_t)&os_remove_obj }, diff --git a/stmhal/modpyb.c b/stmhal/modpyb.c index ace0020f77..4b81d51e32 100644 --- a/stmhal/modpyb.c +++ b/stmhal/modpyb.c @@ -141,7 +141,7 @@ STATIC mp_obj_t pyb_info(uint n_args, const mp_obj_t *args) { { DWORD nclst; FATFS *fatfs; - f_getfree("0:", &nclst, &fatfs); + f_getfree("/flash", &nclst, &fatfs); printf("LFS free: %u bytes\n", (uint)(nclst * fatfs->csize * 512)); } diff --git a/stmhal/qstrdefsport.h b/stmhal/qstrdefsport.h index f1f84999f5..719a81d124 100644 --- a/stmhal/qstrdefsport.h +++ b/stmhal/qstrdefsport.h @@ -63,8 +63,10 @@ Q(SDcard) Q(FileIO) Q(flush) // Entries for sys.path -Q(0:/) -Q(0:/lib) +Q(/flash) +Q(/flash/lib) +Q(/sd) +Q(/sd/lib) Q(millis) // for file class @@ -239,6 +241,10 @@ Q(speed) // for os module Q(os) Q(/) +Q(flash) +Q(sd) +Q(chdir) +Q(getcwd) Q(listdir) Q(mkdir) Q(remove) |