Skip to content

Add time modification support to SPIFFS #3730

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions cores/esp8266/FS.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,13 @@ size_t File::position() const {
return _p->position();
}

time_t File::getLastWrite() {
if (!_p)
return 0;

return _p->getLastWrite();
}

size_t File::size() const {
if (!_p)
return 0;
Expand Down
1 change: 1 addition & 0 deletions cores/esp8266/FS.h
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ class File : public Stream
int read() override;
int peek() override;
void flush() override;
time_t getLastWrite();
size_t readBytes(char *buffer, size_t length) override {
return read((uint8_t*)buffer, length);
}
Expand Down
1 change: 1 addition & 0 deletions cores/esp8266/FSImpl.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ class FileImpl {
virtual bool seek(uint32_t pos, SeekMode mode) = 0;
virtual size_t position() const = 0;
virtual size_t size() const = 0;
virtual time_t getLastWrite() = 0;
virtual void close() = 0;
virtual const char* name() const = 0;
};
Expand Down
2 changes: 1 addition & 1 deletion cores/esp8266/spiffs/spiffs_config.h
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ typedef uint8_t u8_t;
// logical_page_size - (SPIFFS_OBJ_NAME_LEN + sizeof(spiffs_page_header) +
// spiffs_object_ix_header fields + at least some LUT entries)
#ifndef SPIFFS_OBJ_META_LEN
#define SPIFFS_OBJ_META_LEN (0)
#define SPIFFS_OBJ_META_LEN (4)
#endif

// Size of buffer allocated on stack used when copying data.
Expand Down
10 changes: 10 additions & 0 deletions cores/esp8266/spiffs_api.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,16 @@ FileImplPtr SPIFFSImpl::open(const char* path, OpenMode openMode, AccessMode acc
fd, path, openMode, accessMode, _fs.err_code);
return FileImplPtr();
}
#if SPIFFS_OBJ_META_LEN > 0
if (!(mode & SPIFFS_O_RDONLY))
{
time_t t = time(NULL);
struct tm tmr;
localtime_r(&t, &tmr);
time_t meta = mktime(&tmr);
SPIFFS_fupdate_meta(&_fs, fd, &meta);
}
#endif
return std::make_shared<SPIFFSFileImpl>(this, fd);
}

Expand Down
13 changes: 13 additions & 0 deletions cores/esp8266/spiffs_api.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,9 @@
#include "spiffs/spiffs.h"
#include "debug.h"
#include "flash_utils.h"
#if SPIFFS_OBJ_META_LEN > 0
#include <time.h>
#endif

using namespace fs;

Expand Down Expand Up @@ -375,6 +378,16 @@ class SPIFFSFileImpl : public FileImpl
return (const char*) _stat.name;
}

time_t getLastWrite()
{
time_t t =0;
#if SPIFFS_OBJ_META_LEN > 0
_getStat() ;
memcpy(&t, _stat.meta, sizeof(time_t));
#endif
return t;
}

protected:
void _getStat() const
{
Expand Down
163 changes: 163 additions & 0 deletions libraries/ESP8266WiFi/examples/SPIFFS_time/SPIFFS_time.ino
Original file line number Diff line number Diff line change
@@ -0,0 +1,163 @@
#include "FS.h"
#include <time.h>
#include <ESP8266WiFi.h>

const char* ssid = "your-ssid";
const char* password = "your-password";

long timezone = 2;
byte daysavetime = 1;


bool getLocalTime(struct tm * info, uint32_t ms)
{
uint32_t count = ms / 10;
time_t now;

time(&now);
localtime_r(&now, info);

if(info->tm_year > (2016 - 1900)){
return true;
}

while(count--) {
delay(10);
time(&now);
localtime_r(&now, info);
if(info->tm_year > (2016 - 1900)){
return true;
}
}
return false;
}


void listDir(const char * dirname){
Serial.printf("Listing directory: %s\n", dirname);

Dir root = SPIFFS.openDir(dirname);

while(root.next()){
File file = root.openFile("r");
Serial.print(" FILE: ");
Serial.print(root.fileName());
Serial.print(" SIZE: ");
Serial.print(file.size());
time_t t= file.getLastWrite();
struct tm * tmstruct = localtime(&t);
file.close();
Serial.printf(" LAST WRITE: %d-%02d-%02d %02d:%02d:%02d\n",(tmstruct->tm_year)+1900,( tmstruct->tm_mon)+1, tmstruct->tm_mday,tmstruct->tm_hour , tmstruct->tm_min, tmstruct->tm_sec);
}
}


void readFile(const char * path){
Serial.printf("Reading file: %s\n", path);

File file = SPIFFS.open(path, "r");
if(!file){
Serial.println("Failed to open file for reading");
return;
}

Serial.print("Read from file: ");
while(file.available()){
Serial.write(file.read());
}
file.close();
}

void writeFile(const char * path, const char * message){
Serial.printf("Writing file: %s\n", path);

File file = SPIFFS.open(path, "w");
if(!file){
Serial.println("Failed to open file for writing");
return;
}
if(file.print(message)){
Serial.println("File written");
} else {
Serial.println("Write failed");
}
file.close();
}

void appendFile(const char * path, const char * message){
Serial.printf("Appending to file: %s\n", path);

File file = SPIFFS.open(path, "a");
if(!file){
Serial.println("Failed to open file for appending");
return;
}
if(file.print(message)){
Serial.println("Message appended");
} else {
Serial.println("Append failed");
}
file.close();
}

void renameFile(const char * path1, const char * path2){
Serial.printf("Renaming file %s to %s\n", path1, path2);
if (SPIFFS.rename(path1, path2)) {
Serial.println("File renamed");
} else {
Serial.println("Rename failed");
}
}

void deleteFile(const char * path){
Serial.printf("Deleting file: %s\n", path);
if(SPIFFS.remove(path)){
Serial.println("File deleted");
} else {
Serial.println("Delete failed");
}
}

void setup(){
Serial.begin(115200);
// We start by connecting to a WiFi network
Serial.println();
Serial.println();
Serial.print("Connecting to ");
Serial.println(ssid);

WiFi.begin(ssid, password);

while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("WiFi connected");
Serial.println("IP address: ");
Serial.println(WiFi.localIP());
Serial.println("Contacting Time Server");
configTime(3600*timezone, daysavetime*3600, "time.nist.gov", "0.pool.ntp.org", "1.pool.ntp.org");
struct tm tmstruct ;
delay(2000);
tmstruct.tm_year = 0;
getLocalTime(&tmstruct, 5000);
Serial.printf("\nNow is : %d-%02d-%02d %02d:%02d:%02d\n",(tmstruct.tm_year)+1900,( tmstruct.tm_mon)+1, tmstruct.tm_mday,tmstruct.tm_hour , tmstruct.tm_min, tmstruct.tm_sec);
Serial.println("");

if(!SPIFFS.begin()){
Serial.println("Card Mount Failed");
return;
}

listDir("/");
deleteFile("/hello.txt");
writeFile("/hello.txt", "Hello ");
appendFile("/hello.txt", "World!\n");
listDir("/");
}

void loop(){

}