How-to run code from flash

Posted on
  • After being away for a year it's nice to see all the progress on Espruino!

    I did struggle for quite some time to update my stuff and to get my code working again under V2.01, so I thought I'd write up a quick how-to so I remember the next time I try to do something :-) Maybe it also helps someone else 'cause very little of this is spelled out anywhere that I could find (the best info is at http://www.espruino.com/Saving but that page is not linked to from any other page on http://www.espruino.com!)

    Requirements:

    • I have a bunch of apps that are fairly large and must run from flash.
    • I use local modules.
    • The apps must run auto-run at boot time.
    • I prefer CLI over the IDE.

    I couldn't do an OTA update from pre-V2 of Espruino to V2.x due to a changed flash layout (512 vs 1024KB partitions). I have esp-12e modules with 4MB flash, so I installed the official espressif tool https://github.com/espressif/esptool/ and flashed using:

    esptool -p /dev/ttyUSB0 write_flash --flash_size 4MB-c1 --flash_mode qio 0 espruino_2v01_esp8266_4mb_combined_4096.­bin
    

    In the IDE I had to set the options SAVE_TO_FLASH to 1 and MODULE_AS_FUNCTION to true. But I don't want to use the IDE...

    So I installed the espruino cli:

    • Install node.js version 8 (old!), I'm using Linux and untarred the binary archive from the node.js site in /home/sw/node-v8 (non-std location, use any dir you like)
    • Install espruino using /home/sw/node-v8/bin/npm install espruino

    In order to ensure that I can run the cli using node-v8, I created a little shell script I call espruino-v8:

        #! /bin/bash
    export NODEJS_HOME=/home/sw/node-v8/bin
    export PATH=$NODEJS_HOME:$PATH
    espruino --no-ble --config SAVE_ON_SEND=1 --config MODULE_AS_FUNCTION=true "$@"
    

    To flash an application I have the main file in a projects subdirectory and the modules in a modules subdirectory. I simply require(...) the module in the main file. The flashing command is:

    ./expruino-v8 -p tcp://esp8266.local:23 -w -m projects/foo.js
    

    The -w option means that espruino stays connected and shows me the console output.

    The application uses an onInit() to start and that gets invoked automatically at the end of the upload.

  • @tve - welcome back!

  • I like to save code to Storage and than require it, this save a big amount of vars.

    Tested with tinyMQTT and a strip down of SSD1306 for I2C only (SSD1306_I2C).

    snippet how to store it

    s = require('Storage');
    // min of SSD1306_I2C saved as  SSD1306S 
    s.write('SSD1306S',"function k(b){.......}";
    

    snippet to use it

    I2C1.setup({sda:D2,scl:D4, bitrate:200000});
    oled = require("SSD1306S").connect(I2C1,.......­.);
    
  • Good to hear from you again!

    Thanks for posting that code up - I'm sure that'll be useful to others.

    Saving... but that page is not linked to from any other page on http://www.espruino.com!

    It is actually linked quite a bit (FAQ,Troubleshooting,Quick start, etc). But where did you look where it wasn't mentioned and I'll get a link added.

  • I like to save code to Storage and than require it, this save a big amount of vars.

    @MaBe, can you explain the advantages of your scheme over what I'm using? It's quite a bit of additional work.

    It is actually linked quite a bit (FAQ,Troubleshooting,Quick start, etc). But where did you look where it wasn't mentioned and I'll get a link added.

    Hmmm, my bad. I could swear that typing 'saving' into the search box brought up nothing, but now it does, so I must have been too tired to see it or something... I mainly looked around in the tips&tricks, tutorials, modules, and esp8266 pages.

  • Let me use this snippet and make the difference visible with process.memory().

    • no optimization

      process.memory();
      ={ free: 1267, usage: 333, total: 1600, history: 170,
      gc: 0, gctime: 1.862 }

    • module uploaded as function

      process.memory()
      ={ free: 1265, usage: 335, total: 1600, history: 170,
      gc: 0, gctime: 1.862 }

    • use module from flash

      process.memory()
      ={ free: 1357, usage: 243, total: 1600, history: 60,
      gc: 0, gctime: 1.874 }

    • freeHeap is for all cases 11736

    how many vars you save depends on the size of the module .
    Running SH1106 from storage saves round about 90 vars.

    That should justify the extra effort ;-)

    ESP8266_4MB board has now 48 pages to store any stuff you like, check the build content

    Hint: At the moment storage is only working for the first segment, read issue #1507

    Why not write a script as workaround until someone adds this feature into the WebIDE or command line tool

    • scan modules in source file
    • create a min version of the modules of not exist
    • create a store_modules.js
    • upload store_modules.js
    • upload source and you are done.


  • @tve The approach you are using is basically what I do as well.

    @MaBe

    Tested with tinyMQTT and a strip down of SSD1306 for I2C only (SSD1306_I2C).

    Using Rollup https://github.com/espruino/EspruinoTool­s/blob/f8a5ed8bd565070d33154d9196ad9e51f­8aa3c33/plugins/minify.js#L52-L65 you'll be able to create bundles that only contain the module exports that were actually used in the application.

    My CLI preferred approach is to use the https://github.com/opichals/rollup-plugi­n-espruino-modules to do all the JS magic and use the espruino cli to only 'upload' the resulting bundle to the board just as @tve mentioned.

  • Post a reply
    • Bold
    • Italics
    • Link
    • Image
    • List
    • Quote
    • code
    • Preview
About

How-to run code from flash

Posted by Avatar for tve @tve

Actions