-
Notifications
You must be signed in to change notification settings - Fork 2.2k
/
Copy pathpuya_core2_4_x.patch
149 lines (143 loc) · 5.69 KB
/
puya_core2_4_x.patch
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
diff -urN 2.3.0.orig/cores/esp8266/Esp.cpp 2.3.0/cores/esp8266/Esp.cpp
--- 2.3.0.orig/cores/esp8266/Esp.cpp 2016-06-21 08:06:45.000000000 +0000
+++ 2.3.0/cores/Esp.cpp 2019-01-04 16:59:09.627740200 +0100
@@ -205,7 +205,16 @@
uint32_t EspClass::getFlashChipId(void)
{
- return spi_flash_get_id();
+ static uint32_t flash_chip_id = 0;
+ if (flash_chip_id == 0) {
+ flash_chip_id = spi_flash_get_id();
+ }
+ return flash_chip_id;
+}
+
+uint8_t EspClass::getFlashChipVendorId(void)
+{
+ return (getFlashChipId() & 0x000000ff);
}
uint32_t EspClass::getFlashChipRealSize(void)
@@ -508,9 +517,61 @@
return rc == 0;
}
+#if PUYA_SUPPORT
+static int spi_flash_write_puya(uint32_t offset, uint32_t *data, size_t size) {
+ if (data == nullptr) {
+ return 1; // SPI_FLASH_RESULT_ERR
+ }
+ // PUYA flash chips need to read existing data, update in memory and write modified data again.
+ static uint32_t *flash_write_puya_buf = nullptr;
+ int rc = 0;
+ uint32_t* ptr = data;
+
+ if (flash_write_puya_buf == nullptr) {
+ flash_write_puya_buf = (uint32_t*) malloc(PUYA_BUFFER_SIZE);
+ // No need to ever free this, since the flash chip will never change at runtime.
+ if (flash_write_puya_buf == nullptr) {
+ // Memory could not be allocated.
+ return 1; // SPI_FLASH_RESULT_ERR
+ }
+ }
+ size_t bytesLeft = size;
+ uint32_t pos = offset;
+ while (bytesLeft > 0 && rc == 0) {
+ size_t bytesNow = bytesLeft;
+ if (bytesNow > PUYA_BUFFER_SIZE) {
+ bytesNow = PUYA_BUFFER_SIZE;
+ bytesLeft -= PUYA_BUFFER_SIZE;
+ } else {
+ bytesLeft = 0;
+ }
+ rc = spi_flash_read(pos, flash_write_puya_buf, bytesNow);
+ if (rc != 0) {
+ return rc;
+ }
+ for (size_t i = 0; i < bytesNow / 4; ++i) {
+ flash_write_puya_buf[i] &= *ptr;
+ ++ptr;
+ }
+ rc = spi_flash_write(pos, flash_write_puya_buf, bytesNow);
+ pos += bytesNow;
+ }
+ return rc;
+}
+#endif
+
bool EspClass::flashWrite(uint32_t offset, uint32_t *data, size_t size) {
ets_isr_mask(FLASH_INT_MASK);
- int rc = spi_flash_write(offset, (uint32_t*) data, size);
+ int rc = 0;
+#if PUYA_SUPPORT
+ if (getFlashChipVendorId() == SPI_FLASH_VENDOR_PUYA) {
+ rc = spi_flash_write_puya(offset, data, size);
+ }
+ else
+#endif
+ {
+ rc = spi_flash_write(offset, data, size);
+ }
ets_isr_unmask(FLASH_INT_MASK);
return rc == 0;
}
diff -urN 2.3.0.orig/cores/esp8266/Esp.h 2.3.0/cores/esp8266/Esp.h
--- 2.3.0.orig/cores/esp8266/Esp.h 2016-06-21 08:06:45.000000000 +0000
+++ 2.3.0/cores/esp8266/Esp.h 2019-01-04 16:59:09.628715800 +0100
@@ -23,6 +23,53 @@
#include <Arduino.h>
+
+#ifndef PUYA_SUPPORT
+ #define PUYA_SUPPORT 0
+#endif
+#ifndef PUYA_BUFFER_SIZE
+ // Good alternative for buffer size is: SPI_FLASH_SEC_SIZE (= 4k)
+ // Always use a multiple of flash page size (256 bytes)
+ #define PUYA_BUFFER_SIZE 256
+#endif
+
+// Vendor IDs taken from Flashrom project
+// https://review.coreboot.org/cgit/flashrom.git/tree/flashchips.h?h=1.0.x
+typedef enum {
+ SPI_FLASH_VENDOR_ALLIANCE = 0x52, /* Alliance Semiconductor */
+ SPI_FLASH_VENDOR_AMD = 0x01, /* AMD */
+ SPI_FLASH_VENDOR_AMIC = 0x37, /* AMIC */
+ SPI_FLASH_VENDOR_ATMEL = 0x1F, /* Atmel (now used by Adesto) */
+ SPI_FLASH_VENDOR_BRIGHT = 0xAD, /* Bright Microelectronics */
+ SPI_FLASH_VENDOR_CATALYST = 0x31, /* Catalyst */
+ SPI_FLASH_VENDOR_EON = 0x1C, /* EON Silicon Devices, missing 0x7F prefix */
+ SPI_FLASH_VENDOR_ESMT = 0x8C, /* Elite Semiconductor Memory Technology (ESMT) / EFST Elite Flash Storage */
+ SPI_FLASH_VENDOR_EXCEL = 0x4A, /* ESI, missing 0x7F prefix */
+ SPI_FLASH_VENDOR_FIDELIX = 0xF8, /* Fidelix */
+ SPI_FLASH_VENDOR_FUJITSU = 0x04, /* Fujitsu */
+ SPI_FLASH_VENDOR_GIGADEVICE = 0xC8, /* GigaDevice */
+ SPI_FLASH_VENDOR_HYUNDAI = 0xAD, /* Hyundai */
+ SPI_FLASH_VENDOR_INTEL = 0x89, /* Intel */
+ SPI_FLASH_VENDOR_ISSI = 0xD5, /* ISSI Integrated Silicon Solutions, see also PMC. */
+ SPI_FLASH_VENDOR_MACRONIX = 0xC2, /* Macronix (MX) */
+ SPI_FLASH_VENDOR_NANTRONICS = 0xD5, /* Nantronics, missing prefix */
+ SPI_FLASH_VENDOR_PMC = 0x9D, /* PMC, missing 0x7F prefix */
+ SPI_FLASH_VENDOR_PUYA = 0x85, /* Puya semiconductor (shanghai) co. ltd */
+ SPI_FLASH_VENDOR_SANYO = 0x62, /* Sanyo */
+ SPI_FLASH_VENDOR_SHARP = 0xB0, /* Sharp */
+ SPI_FLASH_VENDOR_SPANSION = 0x01, /* Spansion, same ID as AMD */
+ SPI_FLASH_VENDOR_SST = 0xBF, /* SST */
+ SPI_FLASH_VENDOR_ST = 0x20, /* ST / SGS/Thomson / Numonyx (later acquired by Micron) */
+ SPI_FLASH_VENDOR_SYNCMOS_MVC = 0x40, /* SyncMOS (SM) and Mosel Vitelic Corporation (MVC) */
+ SPI_FLASH_VENDOR_TENX = 0x5E, /* Tenx Technologies */
+ SPI_FLASH_VENDOR_TI = 0x97, /* Texas Instruments */
+ SPI_FLASH_VENDOR_TI_OLD = 0x01, /* TI chips from last century */
+ SPI_FLASH_VENDOR_WINBOND = 0xDA, /* Winbond */
+ SPI_FLASH_VENDOR_WINBOND_NEX = 0xEF, /* Winbond (ex Nexcom) serial flashes */
+
+ SPI_FLASH_VENDOR_UNKNOWN = 0xFF
+} SPI_FLASH_VENDOR_t;
+
/**
* AVR macros for WDT managment
*/
@@ -116,6 +163,7 @@
uint8_t getCpuFreqMHz();
uint32_t getFlashChipId();
+ uint8_t getFlashChipVendorId();
//gets the actual chip size based on the flash id
uint32_t getFlashChipRealSize();
//gets the size of the flash as set by the compiler