Binary to update ESP8266 firmware to Espressif firmware. Requires user to press buttons.

Dependencies:   BufferedSerial mbed

Fork of ESPQuickFlash by Christopher Haster

How to Use

This program will update the firmware on a connected ESP8266 to the Espressif Firmware. The user will need to put the ESP8266 board into FW Update mode and follow instructions as given on the serial console.

Between each block transfer power cycle the ESP8266 and put back into FW Update mode. On the Seeed Grove Serial WiFi module this requires a short press followed by a long press on the esp8266 reset button untill the light on the module goes red.

Terminal Settings

9600 baud 8-N-1

Video of how its done

Committer:
mbedAustin
Date:
Mon Apr 18 21:23:56 2016 +0000
Revision:
1:7cb29c3c51ac
Parent:
0:d84cdaf22096
Updated example to use 2wire board (Seeed Grove serial WiFi module) and ask for user input between files.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
geky 0:d84cdaf22096 1 #ifndef ESP_COMMAND_H
geky 0:d84cdaf22096 2 #define ESP_COMMAND_H
geky 0:d84cdaf22096 3
geky 0:d84cdaf22096 4 #include "slip.h"
geky 0:d84cdaf22096 5
geky 0:d84cdaf22096 6
geky 0:d84cdaf22096 7 #define FLASH_BLOCK_SIZE 0x400
geky 0:d84cdaf22096 8 #define RESET_WAIT_MS 250
geky 0:d84cdaf22096 9
geky 0:d84cdaf22096 10 enum esp_commands {
geky 0:d84cdaf22096 11 ESP_FLASH_START = 0x02,
geky 0:d84cdaf22096 12 ESP_FLASH_DATA = 0x03,
geky 0:d84cdaf22096 13 ESP_FLASH_FINISH = 0x04,
geky 0:d84cdaf22096 14 ESP_RAM_START = 0x05,
geky 0:d84cdaf22096 15 ESP_RAM_DATA = 0x07,
geky 0:d84cdaf22096 16 ESP_RAM_FINISH = 0x06,
geky 0:d84cdaf22096 17 ESP_SYNC_FRAME = 0x08,
geky 0:d84cdaf22096 18 ESP_WRITE_REG = 0x09,
geky 0:d84cdaf22096 19 ESP_READ_REG = 0x0a,
geky 0:d84cdaf22096 20 ESP_SPI_CONFIG = 0x0b,
geky 0:d84cdaf22096 21 };
geky 0:d84cdaf22096 22
geky 0:d84cdaf22096 23
geky 0:d84cdaf22096 24
geky 0:d84cdaf22096 25
geky 0:d84cdaf22096 26 // Commands follow the following format
geky 0:d84cdaf22096 27 // request:
geky 0:d84cdaf22096 28 // [- 0x00 -|- command -|- size -|- value -|-- body --]
geky 0:d84cdaf22096 29 // 1 1 2 4 size
geky 0:d84cdaf22096 30 //
geky 0:d84cdaf22096 31 // response:
geky 0:d84cdaf22096 32 // [- 0x01 -|- command -|- size -|- value -|-- body --|- status -|- error -]
geky 0:d84cdaf22096 33 // 1 1 2 4 size-error 1 1
geky 0:d84cdaf22096 34 //
geky 0:d84cdaf22096 35 template <typename SERIAL>
geky 0:d84cdaf22096 36 class ESPCommand {
geky 0:d84cdaf22096 37 private:
geky 0:d84cdaf22096 38 SLIPPacket<SERIAL> _slip;
mbedAustin 1:7cb29c3c51ac 39 DigitalIn _button;
geky 0:d84cdaf22096 40
geky 0:d84cdaf22096 41 public:
mbedAustin 1:7cb29c3c51ac 42 ESPCommand(PinName tx, PinName rx, PinName button) :
mbedAustin 1:7cb29c3c51ac 43 _slip(tx, rx), _button(button){}
geky 0:d84cdaf22096 44
geky 0:d84cdaf22096 45 private:
geky 0:d84cdaf22096 46 bool command_start(char cmd, uint16_t len) {
geky 0:d84cdaf22096 47 len -= 4; // First word not included in length
geky 0:d84cdaf22096 48
geky 0:d84cdaf22096 49 return _slip.req_start() &&
geky 0:d84cdaf22096 50 _slip.putc(0x00) &&
geky 0:d84cdaf22096 51 _slip.putc(cmd) &&
geky 0:d84cdaf22096 52 _slip.send(&len, 2);
geky 0:d84cdaf22096 53 }
geky 0:d84cdaf22096 54
geky 0:d84cdaf22096 55 bool command_flush() {
geky 0:d84cdaf22096 56 uint16_t len;
geky 0:d84cdaf22096 57
geky 0:d84cdaf22096 58 return _slip.resp_start() &&
geky 0:d84cdaf22096 59 _slip.getc() == 0x01 &&
geky 0:d84cdaf22096 60 _slip.getc() >= 0 &&
geky 0:d84cdaf22096 61 _slip.recv(&len, 2) &&
geky 0:d84cdaf22096 62 _slip.recv(0, 4+len-2) &&
geky 0:d84cdaf22096 63 _slip.getc() == 0x00 &&
geky 0:d84cdaf22096 64 _slip.getc() >= 0 &&
geky 0:d84cdaf22096 65 _slip.resp_finish();
geky 0:d84cdaf22096 66 }
geky 0:d84cdaf22096 67
geky 0:d84cdaf22096 68 bool command_finish() {
geky 0:d84cdaf22096 69 return _slip.req_finish() &&
geky 0:d84cdaf22096 70 command_flush();
geky 0:d84cdaf22096 71 }
geky 0:d84cdaf22096 72
geky 0:d84cdaf22096 73 public:
geky 0:d84cdaf22096 74 bool sync() {
geky 0:d84cdaf22096 75 #ifdef LED_STATUS
geky 0:d84cdaf22096 76 led_green = 0; // Show progress
geky 0:d84cdaf22096 77 #endif
geky 0:d84cdaf22096 78 while (true) {
geky 0:d84cdaf22096 79 if (sync_frame()) {
geky 0:d84cdaf22096 80 #ifdef LED_STATUS
geky 0:d84cdaf22096 81 led_green = 1; // Show progress
geky 0:d84cdaf22096 82 #endif
geky 0:d84cdaf22096 83 return true;
geky 0:d84cdaf22096 84 }
geky 0:d84cdaf22096 85 }
geky 0:d84cdaf22096 86 }
geky 0:d84cdaf22096 87
geky 0:d84cdaf22096 88 bool sync_frame() {
geky 0:d84cdaf22096 89
geky 0:d84cdaf22096 90 // Flush serial line
geky 0:d84cdaf22096 91 _slip.flush();
geky 0:d84cdaf22096 92
mbedAustin 1:7cb29c3c51ac 93 printf("\r\nPower cycle ESP, put into FW Update mode, push user button\r\n");
mbedAustin 1:7cb29c3c51ac 94 int temp_button = _button;
mbedAustin 1:7cb29c3c51ac 95 while( temp_button == _button){;} // wait for button press
mbedAustin 1:7cb29c3c51ac 96 printf("\r\nContinuing Now\r\n");
mbedAustin 1:7cb29c3c51ac 97
geky 0:d84cdaf22096 98 // Send sync frame
geky 0:d84cdaf22096 99 uint32_t x = 0;
geky 0:d84cdaf22096 100
geky 0:d84cdaf22096 101 if (!(command_start(ESP_SYNC_FRAME, 2*4 + 32) &&
geky 0:d84cdaf22096 102 _slip.send(&x, 4) &&
geky 0:d84cdaf22096 103 _slip.putc(0x07) &&
geky 0:d84cdaf22096 104 _slip.putc(0x07) &&
geky 0:d84cdaf22096 105 _slip.putc(0x12) &&
geky 0:d84cdaf22096 106 _slip.putc(0x20)))
geky 0:d84cdaf22096 107 return false;
geky 0:d84cdaf22096 108
geky 0:d84cdaf22096 109 for (int i = 0; i < 32; i++) {
geky 0:d84cdaf22096 110 if (!_slip.putc(0x55))
geky 0:d84cdaf22096 111 return false;
geky 0:d84cdaf22096 112 }
geky 0:d84cdaf22096 113
geky 0:d84cdaf22096 114 if (!command_finish())
geky 0:d84cdaf22096 115 return false;
geky 0:d84cdaf22096 116
geky 0:d84cdaf22096 117 for (int i = 0; i < 7; i++) {
geky 0:d84cdaf22096 118 if (!command_flush())
geky 0:d84cdaf22096 119 return false;
geky 0:d84cdaf22096 120 }
geky 0:d84cdaf22096 121
geky 0:d84cdaf22096 122 return true;
geky 0:d84cdaf22096 123 }
geky 0:d84cdaf22096 124
geky 0:d84cdaf22096 125 bool flash_start(uint32_t blocks, uint32_t block_size, uint32_t address) {
geky 0:d84cdaf22096 126 uint32_t x = 0;
geky 0:d84cdaf22096 127 uint32_t size = blocks * block_size;
geky 0:d84cdaf22096 128
geky 0:d84cdaf22096 129 return command_start(ESP_FLASH_START, 5*4) &&
geky 0:d84cdaf22096 130 _slip.send(&x, 4) &&
geky 0:d84cdaf22096 131 _slip.send(&size, 4) &&
geky 0:d84cdaf22096 132 _slip.send(&blocks, 4) &&
geky 0:d84cdaf22096 133 _slip.send(&block_size, 4) &&
geky 0:d84cdaf22096 134 _slip.send(&address, 4) &&
geky 0:d84cdaf22096 135 command_finish();
geky 0:d84cdaf22096 136 }
geky 0:d84cdaf22096 137
geky 0:d84cdaf22096 138 bool flash_data(const char *data, uint32_t len, uint32_t n) {
geky 0:d84cdaf22096 139 uint32_t zero = 0;
geky 0:d84cdaf22096 140
geky 0:d84cdaf22096 141 uint32_t x = 0xef;
geky 0:d84cdaf22096 142 for (int i = 0; i < len; i++) {
geky 0:d84cdaf22096 143 x ^= data[i];
geky 0:d84cdaf22096 144 }
geky 0:d84cdaf22096 145
geky 0:d84cdaf22096 146 return command_start(ESP_FLASH_DATA, 5*4 + len) &&
geky 0:d84cdaf22096 147 _slip.send(&x, 4) &&
geky 0:d84cdaf22096 148 _slip.send(&len, 4) &&
geky 0:d84cdaf22096 149 _slip.send(&n, 4) &&
geky 0:d84cdaf22096 150 _slip.send(&zero, 4) &&
geky 0:d84cdaf22096 151 _slip.send(&zero, 4) &&
geky 0:d84cdaf22096 152 _slip.send(data, len) &&
geky 0:d84cdaf22096 153 command_finish();
geky 0:d84cdaf22096 154 }
geky 0:d84cdaf22096 155
geky 0:d84cdaf22096 156 bool flash_finish() {
geky 0:d84cdaf22096 157 uint32_t x = 0;
geky 0:d84cdaf22096 158
geky 0:d84cdaf22096 159 return command_start(ESP_FLASH_FINISH, 2*4) &&
geky 0:d84cdaf22096 160 _slip.send(&x, 4) &&
geky 0:d84cdaf22096 161 _slip.send(&x, 4) &&
geky 0:d84cdaf22096 162 command_finish();
geky 0:d84cdaf22096 163 }
geky 0:d84cdaf22096 164
geky 0:d84cdaf22096 165 bool flash_write(uint32_t address, const char *data, uint32_t size) {
geky 0:d84cdaf22096 166 uint32_t blocks = (size-1)/FLASH_BLOCK_SIZE + 1;
geky 0:d84cdaf22096 167
geky 0:d84cdaf22096 168 printf("Synching...\r\n");
geky 0:d84cdaf22096 169 if (!sync())
geky 0:d84cdaf22096 170 error("Sync error!");
geky 0:d84cdaf22096 171
geky 0:d84cdaf22096 172 printf("Starting transfer 0x%05x - 0x%05x\r\n", address, address + blocks*FLASH_BLOCK_SIZE);
geky 0:d84cdaf22096 173 if (!flash_start(blocks, FLASH_BLOCK_SIZE, address))
geky 0:d84cdaf22096 174 return false;
geky 0:d84cdaf22096 175
geky 0:d84cdaf22096 176 for (int i = 0; i < blocks; i++) {
geky 0:d84cdaf22096 177 printf("Flashing address 0x%05x\r\n", address + i*FLASH_BLOCK_SIZE);
geky 0:d84cdaf22096 178 if (!flash_data(&data[i*FLASH_BLOCK_SIZE], FLASH_BLOCK_SIZE, i))
geky 0:d84cdaf22096 179 return false;
geky 0:d84cdaf22096 180 }
geky 0:d84cdaf22096 181
geky 0:d84cdaf22096 182 printf("Finishing transfer\r\n");
geky 0:d84cdaf22096 183 if (!flash_finish())
geky 0:d84cdaf22096 184 return false;
geky 0:d84cdaf22096 185
geky 0:d84cdaf22096 186 wait_ms(250);
geky 0:d84cdaf22096 187 return true;
geky 0:d84cdaf22096 188 }
geky 0:d84cdaf22096 189 };
geky 0:d84cdaf22096 190
geky 0:d84cdaf22096 191 #endif