diff --git a/cores/esp8266/FS.cpp b/cores/esp8266/FS.cpp index 7a13dcede8..125ac527cb 100644 --- a/cores/esp8266/FS.cpp +++ b/cores/esp8266/FS.cpp @@ -144,6 +144,14 @@ String Dir::fileName() { return _impl->fileName(); } +size_t Dir::fileSize() { + if (!_impl) { + return 0; + } + + return _impl->fileSize(); +} + bool Dir::next() { if (!_impl) { return false; diff --git a/cores/esp8266/FS.h b/cores/esp8266/FS.h index 3158fd5290..d8d8dedd72 100644 --- a/cores/esp8266/FS.h +++ b/cores/esp8266/FS.h @@ -78,6 +78,7 @@ class Dir { File openFile(const char* mode); String fileName(); + size_t fileSize(); bool next(); protected: diff --git a/cores/esp8266/FSImpl.h b/cores/esp8266/FSImpl.h index 8e48a9fda0..20d886e764 100644 --- a/cores/esp8266/FSImpl.h +++ b/cores/esp8266/FSImpl.h @@ -56,6 +56,7 @@ class DirImpl { virtual ~DirImpl() { } virtual FileImplPtr openFile(OpenMode openMode, AccessMode accessMode) = 0; virtual const char* fileName() = 0; + virtual size_t fileSize() = 0; virtual bool next() = 0; }; diff --git a/cores/esp8266/core_esp8266_noniso.c b/cores/esp8266/core_esp8266_noniso.c index 40fe5e6dd4..d5b9d82f28 100644 --- a/cores/esp8266/core_esp8266_noniso.c +++ b/cores/esp8266/core_esp8266_noniso.c @@ -148,7 +148,8 @@ char* ultoa(unsigned long value, char* result, int base) { } char * dtostrf(double number, signed char width, unsigned char prec, char *s) { - + bool negative = false; + if (isnan(number)) { strcpy(s, "nan"); return s; @@ -158,50 +159,65 @@ char * dtostrf(double number, signed char width, unsigned char prec, char *s) { return s; } - if (number > 4294967040.0 || number < -4294967040.0) { - strcpy(s, "ovf"); - return s; - } - char* out = s; - int signInt_Part = 1; - + + int fillme = width; // how many cells to fill for the integer part + if (prec > 0) { + fillme -= (prec+1); + } + // Handle negative numbers if (number < 0.0) { - signInt_Part = -1; + negative = true; + fillme--; number = -number; } - // calc left over digits - if (prec > 0) - { - width -= (prec + 1); - } - // Round correctly so that print(1.999, 2) prints as "2.00" - double rounding = 0.5; + // I optimized out most of the divisions + double rounding = 2.0; for (uint8_t i = 0; i < prec; ++i) - rounding /= 10.0; + rounding *= 10.0; + rounding = 1.0 / rounding; number += rounding; - - // Extract the integer part of the number and print it - unsigned long int_part = (unsigned long)number; - double remainder = number - (double)int_part; - out += sprintf(out, "%*ld", width, int_part * signInt_Part); - - // Print the decimal point, but only if there are digits beyond - if (prec > 0) { - *out = '.'; - ++out; - - - for (unsigned char decShift = prec; decShift > 0; decShift--) { - remainder *= 10.0; - } - sprintf(out, "%0*d", prec, (int)remainder); + + // Figure out how big our number really is + double tenpow = 1.0; + int digitcount = 1; + while (number >= 10.0 * tenpow) { + tenpow *= 10.0; + digitcount++; + } + + number /= tenpow; + fillme -= digitcount; + + // Pad unused cells with spaces + while (fillme-- > 0) { + *out++ = ' '; + } + + // Handle negative sign + if (negative) *out++ = '-'; + + // Print the digits, and if necessary, the decimal point + digitcount += prec; + int8_t digit = 0; + while (digitcount-- > 0) { + digit = (int8_t)number; + if (digit > 9) digit = 9; // insurance + *out++ = (char)('0' | digit); + if ((digitcount == prec) && (prec > 0)) { + *out++ = '.'; + } + number -= digit; + number *= 10.0; } + // make sure the string is terminated + *out = 0; return s; } + diff --git a/cores/esp8266/spiffs_api.cpp b/cores/esp8266/spiffs_api.cpp index 157ae86bcd..d9c7c618f4 100644 --- a/cores/esp8266/spiffs_api.cpp +++ b/cores/esp8266/spiffs_api.cpp @@ -308,6 +308,13 @@ class SPIFFSDirImpl : public DirImpl { return (const char*) _dirent.name; } + size_t fileSize() override { + if (!_valid) + return 0; + + return _dirent.size; + } + bool next() override { spiffs_dirent* result = SPIFFS_readdir(&_dir, &_dirent); _valid = (result != nullptr);