Commit 7b83bbb2 authored by Arnim Läuger's avatar Arnim Läuger Committed by GitHub
Browse files

Merge pull request #1519 from nodemcu/dev

Next 1.5.4.1 master drop
parents 8e48483c d96d7f23
# FAT File System on SD Card
Accessing files on external SD cards is currently only supported from the `file` module. This imposes the same overall restrictions of internal SPIFFS to SD cards:
- only one file can be opened at a time
- no support for sub-folders
- no timestamps
- no file attributes (read-only, system, etc.)
Work is in progress to extend the `file` API with support for the missing features.
## Enabling FatFs
The FAT file system is implemented by [Chan's FatFs](http://elm-chan.org/fsw/ff/00index_e.html) version [R0.12a](http://elm-chan.org/fsw/ff/ff12a.zip). It's disabled by default to save memory space and has to be enabled before compiling the firmware:
Uncomment `#define BUILD_FATFS` in [`user_config.h`](../../app/include/user_config.h).
## SD Card connection
The SD card is operated in SPI mode, thus the card has to be wired to the respective ESP pins of the HSPI interface. There are several naming schemes used on different adapters - the following list shows alternative terms:
- `CK, CLK, SCLK` to pin5 / GPIO14
- `DO, DAT0, MISO` to pin 6 / GPIO12
- `DI, CMD, MOSI` to pin 7 / GPIO13
- `CS, DAT3, SS` to pin 8 / GPIO15 recommended
- `VCC, VDD` to 3V3 supply
- `VSS, GND` to common ground
Connection of `SS/CS` can be done to any of the GPIOs on pins 1 to 12. This allows coexistence of the SD card with other SPI slaves on the same bus. There's no support for detection of card presence or the write protection switch. These would need to be handled as additional GPIOs in the user application.
!!! caution
The adapter does not require level shifters since SD and ESP are supposed to be powered with the same voltage. If your specific model contains level shifters then make sure that both sides can be operated at 3V3.
![1:1 micro-sd adapter](../img/micro_sd-small.jpg "1:1 micro-sd adapter")
![micro-sd shield](../img/micro_sd_shield-small.jpg "micro-sd shield")
## Lua bindings
Before mounting the volume(s) on the SD card, you need to initialize the SPI interface from Lua.
```lua
spi.setup(1, spi.MASTER, spi.CPOL_LOW, spi.CPHA_LOW, 8, 8)
-- initialize other spi slaves
-- then mount the sd
-- note: the card initialization process during `file.mount()` will set spi divider temporarily to 200 (400 kHz)
-- it's reverted back to the current user setting before `file.mount()` finishes
vol = file.mount("/SD0", 8) -- 2nd parameter is optional for non-standard SS/CS pin
if not vol then
print("retry mounting")
vol = file.mount("/SD0", 8)
if not vol then
error("mount failed")
end
end
file.open("/SD0/path/to/somefile")
print(file.read())
file.close()
```
!!! note
If the card doesn't work when calling `file.mount()` for the first time then re-try the command. It's possible that certain cards time out during the first initialization after power-up.
The logical drives are mounted at the root of a unified directory tree where the mount points distinguish between internal flash (`/FLASH`) and the card's paritions (`/SD0` to `/SD3`). Files are accessed via either the absolute hierarchical path or relative to the current working directory. It defaults to `/FLASH` and can be changed with `file.chdir(path)`.
Subdirectories are supported on FAT volumes only.
## Multiple partitions / multiple cards
The mapping from logical volumes (eg. `/SD0`) to partitions on an SD card is defined in [`fatfs_config.h`](../../app/include/fatfs_config.h). More volumes can be added to the `VolToPart` array with any combination of physical drive number (aka SS/CS pin) and partition number. Their names have to be added to `_VOLUME_STRS` in [`ffconf.h`](../../app/fatfs/ffconf.h) as well.
...@@ -27,11 +27,11 @@ spiffsimg -f <filename> ...@@ -27,11 +27,11 @@ spiffsimg -f <filename>
### Supported operations: ### Supported operations:
* `-f` specifies the filename for the disk image. '%x' will be replaced by the calculated offset of the file system. * `-f` specifies the filename for the disk image. '%x' will be replaced by the calculated offset of the file system (`-U` must also be specified to calculate the offset).
* `-o` specifies the file which is to contain the calculated offset. * `-o` specifies the filename which is to contain the calculated offset.
* `-S` specifies the size of the flash chip. `32m` is 32 mbits, `1MB` is 1 megabyte. * `-S` specifies the size of the flash chip. `32m` is 32 mbits, `4MB` is 4 megabytes.
* `-U` specifies the amount of flash used by the firmware. Decimal or Hex bytes. * `-U` specifies the amount of flash used by the firmware. Decimal or Hex bytes (if starts with 0x).
* `-c` Create a blank disk image of the given size. * `-c` Create a blank disk image of the given size. Decimal or Hex bytes (if starts with 0x).
* `-l` List the contents of the given disk image. * `-l` List the contents of the given disk image.
* `-i` Interactive commands. * `-i` Interactive commands.
* `-r` Scripted commands from filename. * `-r` Scripted commands from filename.
...@@ -73,7 +73,8 @@ f 880 http/favicon.ico ...@@ -73,7 +73,8 @@ f 880 http/favicon.ico
# Technical Details # Technical Details
The SPIFFS configuration is 4k sectors (the only size supported by the SDK) and 8k blocks. 256 byte pages. Magic is enabled and magic_len is also enabled. This allows the firmware to find the start of the filesystem (and also the size). The SPIFFS configuration is 4k sectors (the only size supported by the SDK) and 8k blocks. 256 byte pages. Magic is enabled and magic_len is also enabled. This allows the firmware to find the start of the filesystem (and also the size).
One of the goals is to make the filsystem more persistent across reflashing of the firmware. One of the goals is to make the filsystem more persistent across reflashing of the firmware. However, there are still cases
where spiffs detects a filesystem and uses it when it isn't valid. If you are getting weirdness with the filesystem, then just reformat it.
There are two significant sizes of flash -- the 512K and 4M (or bigger). There are two significant sizes of flash -- the 512K and 4M (or bigger).
...@@ -82,14 +83,20 @@ not much spare space, so a newly formatted file system will start as low as poss ...@@ -82,14 +83,20 @@ not much spare space, so a newly formatted file system will start as low as poss
file system will start on a 64k boundary. A newly formatted file system will start between 64k and 128k from the end of the firmware. This means that the file file system will start on a 64k boundary. A newly formatted file system will start between 64k and 128k from the end of the firmware. This means that the file
system will survive lots of reflashing and at least 64k of firmware growth. system will survive lots of reflashing and at least 64k of firmware growth.
The spiffsimg tool can also be built (from source) in the nodemcu-firmware build tree. If there is any data in the `local/fs` directory tree, then it will The standard build process for the firmware builds the `spiffsimg` tool (found in the `tools/spiffsimg` subdirectory).
be copied into the flash disk image. Two images will normally be created -- one for the 512k flash part and the other for the 4M flash part. If the data doesn't The top level Makfile also checks if
there is any data in the `local/fs` directory tree, and it will then copy these files
into the flash disk image. Two images will normally be created -- one for the 512k flash part and the other for the 4M flash part. If the data doesn't
fit into the 512k part after the firmware is included, then the file will not be generated. fit into the 512k part after the firmware is included, then the file will not be generated.
The disk image file is placed into the `bin` directory and it is named `0x<offset>-<size>.bin` where the offset is the location where it should be The disk image file is placed into the `bin` directory and it is named `0x<offset>-<size>.bin` where the offset is the location where it should be
flashed, and the size is the size of the flash part. It is quite valid (and quicker) to flash the 512k image into a 4M part. However, there will probably be flashed, and the size is the size of the flash part. It is quite valid (and quicker) to flash the 512k image into a 4M part. However, there will probably be
limited space in the file system for creating new files. limited space in the file system for creating new files.
The default configuration will try and build three different file systems for 512KB, 1MB and 4MB flash sizes. The 1MB size is suitable for the ESP8285. This can be overridden by specifying the FLASHSIZE parameter to the makefile.
If the `local/fs` directory is empty, then no flash images will be created (and the ones from the last build will be removed). The `spiffsimg` tool can
then be used to build an image as required.
If no file system is found during platform boot, then a new file system will be formatted. This can take some time on the first boot. If no file system is found during platform boot, then a new file system will be formatted. This can take some time on the first boot.
Note that the last 16k of the flash chip is reserved for the SDK to store parameters (such as the client wifi settings). Note that the last 16k of the flash chip is reserved for the SDK to store parameters (such as the client wifi settings).
......
...@@ -2,8 +2,8 @@ The [issues list on GitHub](https://github.com/nodemcu/nodemcu-firmware/issues) ...@@ -2,8 +2,8 @@ The [issues list on GitHub](https://github.com/nodemcu/nodemcu-firmware/issues)
Which ever site you use you need to make sure the description of the problem is to the point. It should be accompanied by a stripped down version of your Lua source code i.e. create a Minimal, Complete, and Verifiable Example (MCVE). A good resource is [http://stackoverflow.com/help/how-to-ask](http://stackoverflow.com/help/how-to-ask) Which ever site you use you need to make sure the description of the problem is to the point. It should be accompanied by a stripped down version of your Lua source code i.e. create a Minimal, Complete, and Verifiable Example (MCVE). A good resource is [http://stackoverflow.com/help/how-to-ask](http://stackoverflow.com/help/how-to-ask)
## StackOverflow ## Stack Overflow
StackOverflow is the perfect place to ask coding questions. Use one or several of the following tags: [esp8266](http://stackoverflow.com/tags/esp8266), [nodemcu](http://stackoverflow.com/tags/nodemcu) or [Lua](http://stackoverflow.com/tags/lua). Stack Overflow is the perfect place to ask coding questions. Use one or several of the following tags: [esp8266](http://stackoverflow.com/tags/esp8266), [nodemcu](http://stackoverflow.com/tags/nodemcu) or [Lua](http://stackoverflow.com/tags/lua).
## esp8266.com Forums ## esp8266.com Forums
esp8266.com has a few [NodeMCU specific forums](http://www.esp8266.com/viewforum.php?f=17) where a number of our active community members tend to hang out. esp8266.com has a few [NodeMCU specific forums](http://www.esp8266.com/viewforum.php?f=17) where a number of our active community members tend to hang out.
\ No newline at end of file
-- Support HTTP and HTTPS, For example
-- HTTP POST Example with JSON header and body
http.post("http://somewhere.acceptjson.com/",
"Content-Type: application/json\r\n",
"{\"hello\":\"world\"}",
function(code, data)
print(code)
print(data)
end)
-- HTTPS GET Example with NULL header
http.get("https://www.vowstar.com/nodemcu/","",
function(code, data)
print(code)
print(data)
end)
-- You will get
-- > 200
-- hello nodemcu
-- HTTPS DELETE Example with NULL header and body
http.delete("https://10.0.0.2:443","","",
function(code, data)
print(code)
print(data)
end)
-- HTTPS PUT Example with NULL header and body
http.put("https://testput.somewhere/somewhereyouput.php","","",
function(code, data)
print(code)
print(data)
end)
-- HTTP RAW Request Example, use more HTTP/HTTPS request method
http.request("http://www.apple.com:80/library/test/success.html","GET","","",
function(code, data)
print(code)
print(data)
end)
...@@ -26,7 +26,8 @@ pages: ...@@ -26,7 +26,8 @@ pages:
- Home: 'en/index.md' - Home: 'en/index.md'
- Building the firmware: 'en/build.md' - Building the firmware: 'en/build.md'
- Flashing the firmware: 'en/flash.md' - Flashing the firmware: 'en/flash.md'
- Filesystem notes: 'en/spiffs.md' - Internal filesystem notes: 'en/spiffs.md'
- Filesystem on SD card: 'en/sdcard.md'
- Uploading code: 'en/upload.md' - Uploading code: 'en/upload.md'
- FAQs: - FAQs:
- Lua Developer FAQ: 'en/lua-developer-faq.md' - Lua Developer FAQ: 'en/lua-developer-faq.md'
...@@ -78,6 +79,7 @@ pages: ...@@ -78,6 +79,7 @@ pages:
- 'u8g': 'en/modules/u8g.md' - 'u8g': 'en/modules/u8g.md'
- 'uart': 'en/modules/uart.md' - 'uart': 'en/modules/uart.md'
- 'ucg': 'en/modules/ucg.md' - 'ucg': 'en/modules/ucg.md'
- 'websocket': 'en/modules/websocket.md'
- 'wifi': 'en/modules/wifi.md' - 'wifi': 'en/modules/wifi.md'
- 'ws2801': 'en/modules/ws2801.md' - 'ws2801': 'en/modules/ws2801.md'
- 'ws2812': 'en/modules/ws2812.md' - 'ws2812': 'en/modules/ws2812.md'
......
...@@ -4,5 +4,7 @@ ...@@ -4,5 +4,7 @@
#include_next "user_interface.h" #include_next "user_interface.h"
bool wifi_softap_deauth(uint8 mac[6]); bool wifi_softap_deauth(uint8 mac[6]);
uint8 get_fpm_auto_sleep_flag(void);
#endif /* SDK_OVERRIDES_INCLUDE_USER_INTERFACE_H_ */ #endif /* SDK_OVERRIDES_INCLUDE_USER_INTERFACE_H_ */
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
FSSOURCE ?= ../local/fs/ FSSOURCE ?= ../local/fs/
FLASHSIZE ?= 4mb 32mb 8mb FLASHSIZE ?= 4mb 32mb 8mb
SUBDIRS = SUBDIRS =
HOSTCC ?= gcc
OBJDUMP = $(or $(shell which objdump),xtensa-lx106-elf-objdump) OBJDUMP = $(or $(shell which objdump),xtensa-lx106-elf-objdump)
...@@ -28,8 +29,17 @@ FLASH_USED_END = $$((0x`$(OBJDUMP) -t ../app/.output/eagle/debug/image/eagle.app ...@@ -28,8 +29,17 @@ FLASH_USED_END = $$((0x`$(OBJDUMP) -t ../app/.output/eagle/debug/image/eagle.app
all: spiffsscript all: spiffsscript
spiffsscript: remove-image .PHONY: spiffsimg
$(MAKE) -C spiffsimg CC=gcc
.PHONY: spiffsimg/spiffsimg
spiffsimg: spiffsimg/spiffsimg
@echo Built spiffsimg in spiffsimg/spiffsimg
spiffsimg/spiffsimg:
@$(MAKE) -C spiffsimg CC=$(HOSTCC)
spiffsscript: remove-image spiffsimg/spiffsimg
rm -f ./spiffsimg/spiffs.lst rm -f ./spiffsimg/spiffs.lst
echo "" >> ./spiffsimg/spiffs.lst echo "" >> ./spiffsimg/spiffs.lst
@$(foreach f, $(SPIFFSFILES), echo "import $(FSSOURCE)$(f) $(f)" >> ./spiffsimg/spiffs.lst ;) @$(foreach f, $(SPIFFSFILES), echo "import $(FSSOURCE)$(f) $(f)" >> ./spiffsimg/spiffs.lst ;)
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
set -e set -e
echo "Running PR build (all modules, SSL disabled)" echo "Running PR build (all modules, SSL enabled, debug enabled)"
( (
cd "$TRAVIS_BUILD_DIR"/app/include || exit cd "$TRAVIS_BUILD_DIR"/app/include || exit
# uncomment disabled modules e.g. '//#define LUA_USE_MODULES_UCG' -> '#define LUA_USE_MODULES_UCG' # uncomment disabled modules e.g. '//#define LUA_USE_MODULES_UCG' -> '#define LUA_USE_MODULES_UCG'
...@@ -11,11 +11,17 @@ cat user_modules.h ...@@ -11,11 +11,17 @@ cat user_modules.h
# enable SSL # enable SSL
sed -i.bak 's@//#define CLIENT_SSL_ENABLE@#define CLIENT_SSL_ENABLE@' user_config.h sed -i.bak 's@//#define CLIENT_SSL_ENABLE@#define CLIENT_SSL_ENABLE@' user_config.h
# enable debug
sed -E -i.bak 's@// ?#define DEVELOP_VERSION@#define DEVELOP_VERSION@' user_config.h
# enable FATFS
sed -i 's@//#define BUILD_FATFS@#define BUILD_FATFS@' user_config.h
cat user_config.h cat user_config.h
cd "$TRAVIS_BUILD_DIR"/ld || exit cd "$TRAVIS_BUILD_DIR"/ld || exit
# increase irom0_0_seg size for all modules build # increase irom0_0_seg size for all modules build
sed -E -i.bak 's@(.*irom0_0_seg *:.*len *=) *[^,]*(.*)@\1 0xA0000\2@' nodemcu.ld sed -E -i.bak 's@(.*irom0_0_seg *:.*len *=) *[^,]*(.*)@\1 0xC0000\2@' nodemcu.ld
cat nodemcu.ld cat nodemcu.ld
# change to "root" directory no matter where the script was started from # change to "root" directory no matter where the script was started from
......
...@@ -2,7 +2,7 @@ SRCS=\ ...@@ -2,7 +2,7 @@ SRCS=\
main.c \ main.c \
../../app/spiffs/spiffs_cache.c ../../app/spiffs/spiffs_check.c ../../app/spiffs/spiffs_gc.c ../../app/spiffs/spiffs_hydrogen.c ../../app/spiffs/spiffs_nucleus.c ../../app/spiffs/spiffs_cache.c ../../app/spiffs/spiffs_check.c ../../app/spiffs/spiffs_gc.c ../../app/spiffs/spiffs_hydrogen.c ../../app/spiffs/spiffs_nucleus.c
CFLAGS=-g -Wall -Wextra -Wno-unused-parameter -Wno-unused-function -I. -I../../app/spiffs -DNODEMCU_SPIFFS_NO_INCLUDE --include spiffs_typedefs.h CFLAGS=-g -Wall -Wextra -Wno-unused-parameter -Wno-unused-function -I. -I../../app/spiffs -I../../app/include -DNODEMCU_SPIFFS_NO_INCLUDE --include spiffs_typedefs.h
spiffsimg: $(SRCS) spiffsimg: $(SRCS)
$(CC) $(CFLAGS) $^ $(LDFLAGS) -o $@ $(CC) $(CFLAGS) $^ $(LDFLAGS) -o $@
......
...@@ -282,6 +282,12 @@ int main (int argc, char *argv[]) ...@@ -282,6 +282,12 @@ int main (int argc, char *argv[])
} }
sz &= ~(0x1fff); sz &= ~(0x1fff);
if (used == 0) {
if (strchr(fname, '%')) {
die("Unable to calculate where to put the flash image, and % present in filename");
}
}
char fnamebuff[1024]; char fnamebuff[1024];
sprintf(fnamebuff, fname, used); sprintf(fnamebuff, fname, used);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment