Последняя активность 1 month ago

EFM8 C2 Write Port to Arduino

c2write.ino Исходник
1/**
2 Based on https://github.com/jaromir-sukuba/efm8prog/
3 Use his SW to program EFM8 using arduino.
4 This needs some work though (but it works)
5**/
6#define C2D 2
7#define C2CK 3
8#define LED 13
9
10#define INBUSY 0x02
11#define OUTREADY 0x01
12
13void c2_send_bits (unsigned char data, unsigned char len);
14void c2_pulse_clk (void);
15unsigned char c2_read_bits (unsigned char len);
16
17void c2_rst (void);
18void c2_write_addr (unsigned char addr);
19unsigned char c2_read_addr (void);
20unsigned char c2_read_data (void);
21void c2_write_data (unsigned char addr);
22
23unsigned char c2_init_PI (void);
24unsigned char c2_read_flash_block (unsigned int addr, unsigned char * data, unsigned char len);
25unsigned char c2_poll_bit_low (unsigned char mask);
26unsigned char c2_poll_bit_high (unsigned char mask);
27unsigned char c2_write_flash_block (unsigned int addr, unsigned char * data, unsigned char len);
28unsigned char c2_erase_device (void);
29
30
31void c2_rst() {
32 digitalWrite(C2CK, LOW);
33 delayMicroseconds(100);
34 digitalWrite(C2CK, HIGH);
35 delayMicroseconds(100);
36}
37
38void c2_pulse_clk() {
39 pinMode(C2CK, OUTPUT);
40 digitalWrite(C2CK, LOW);
41 digitalWrite(C2CK, LOW);
42 digitalWrite(C2CK, LOW);
43 digitalWrite(C2CK, LOW);
44 digitalWrite(C2CK, HIGH);
45}
46
47unsigned char c2_read_bits (unsigned char len) {
48 unsigned char i, data, mask;
49 mask = 0x01 << (len-1);
50 data = 0;
51 pinMode(C2D, INPUT);
52 for (i=0;i<len;i++) {
53 c2_pulse_clk();
54 data = data >> 1;
55 if (digitalRead(C2D) == HIGH) {
56 data = data | mask;
57 }
58 }
59 pinMode(C2D, OUTPUT);
60
61 return data;
62}
63
64void c2_send_bits (unsigned char data, unsigned char len) {
65 unsigned char i;
66 pinMode(C2D, OUTPUT);
67 for (i=0;i<len;i++) {
68 if (data&0x01) {
69 digitalWrite(C2D, HIGH);
70 } else {
71 digitalWrite(C2D, LOW);
72 }
73 c2_pulse_clk();
74 data = data >> 1;
75 }
76}
77
78void c2_write_data (unsigned char data) {
79 unsigned char retval;
80 c2_send_bits(0x0, 1);
81 c2_send_bits(0x1, 2);
82 c2_send_bits(0x0, 2);
83 c2_send_bits(data, 8);
84 retval = 0;
85 while (retval == 0) {
86 retval = c2_read_bits(1);
87 }
88 c2_send_bits(0x0, 1);
89}
90
91unsigned char c2_poll_bit_high (unsigned char mask) {
92 unsigned char retval;
93 retval = c2_read_addr();
94 while ((retval&mask)==0) retval = c2_read_addr();
95}
96
97unsigned char c2_poll_bit_low (unsigned char mask) {
98 unsigned char retval;
99 retval = c2_read_addr();
100 while (retval&mask) retval = c2_read_addr();
101}
102
103unsigned char c2_read_flash_block (unsigned int addr, unsigned char * data, unsigned char len) {
104 unsigned char retval,i;
105 c2_write_addr(0xB4);
106 c2_write_data(0x06);
107 c2_poll_bit_low(INBUSY);
108 c2_poll_bit_high(OUTREADY);
109 retval = c2_read_data();
110 c2_write_data(addr>>8);
111 c2_poll_bit_low(INBUSY);
112 c2_write_data(addr&0xFF);
113 c2_poll_bit_low(INBUSY);
114 c2_write_data(len);
115 c2_poll_bit_low(INBUSY);
116 c2_poll_bit_high(OUTREADY);
117 retval = c2_read_data();
118 for (i=0;i<len;i++) {
119 c2_poll_bit_high(OUTREADY);
120 retval = c2_read_data();
121 data[i] = retval;
122 }
123 return i;
124}
125
126unsigned char c2_write_flash_block (unsigned int addr, unsigned char * data, unsigned char len) {
127 unsigned char retval,i;
128 c2_write_addr(0xB4);
129 c2_write_data(0x07);
130 c2_poll_bit_low(INBUSY);
131 c2_poll_bit_high(OUTREADY);
132 retval = c2_read_data();
133 c2_write_data(addr>>8);
134 c2_poll_bit_low(INBUSY);
135 c2_write_data(addr&0xFF);
136 c2_poll_bit_low(INBUSY);
137 c2_write_data(len);
138 c2_poll_bit_low(INBUSY);
139 c2_poll_bit_high(OUTREADY);
140 retval = c2_read_data();
141 for (i=0;i<len;i++) {
142 c2_write_data(data[i] );
143 c2_poll_bit_low(INBUSY);
144 }
145 c2_poll_bit_high(OUTREADY);
146}
147
148unsigned char c2_erase_device (void) {
149 unsigned char retval;
150 c2_write_addr(0xB4);
151 c2_write_data(0x03);
152 c2_poll_bit_low(INBUSY);
153 c2_poll_bit_high(OUTREADY);
154 retval = c2_read_data();
155 c2_write_data(0xDE);
156 c2_poll_bit_low(INBUSY);
157 c2_write_data(0xAD);
158 c2_poll_bit_low(INBUSY);
159 c2_write_data(0xA5);
160 c2_poll_bit_low(INBUSY);
161 c2_poll_bit_high(OUTREADY);
162 retval = c2_read_data();
163}
164
165unsigned char c2_init_PI (void) {
166 c2_rst();
167 c2_write_addr(0x02);
168 c2_write_data(0x02);
169 c2_write_data(0x04);
170 c2_write_data(0x01);
171 delay(20);
172 return 0;
173}
174
175unsigned char c2_read_data() {
176 unsigned char retval;
177 c2_send_bits(0x0, 1);
178 c2_send_bits(0x0, 2);
179 c2_send_bits(0x0, 2);
180 retval = 0;
181 while (retval == 0) {
182 retval = c2_read_bits(1);
183 }
184 retval = c2_read_bits(8);
185 c2_send_bits(0x0, 1);
186 return retval;
187}
188
189unsigned char c2_read_addr() {
190 unsigned char retval;
191 c2_send_bits(0x0, 1);
192 c2_send_bits(0x2, 2);
193 retval = c2_read_bits(8);
194 c2_send_bits(0x0, 1);
195 return retval;
196}
197
198void c2_write_addr(unsigned char addr) {
199 c2_send_bits(0x0,1);
200 c2_send_bits(0x3,2);
201 c2_send_bits(addr,8);
202 c2_send_bits(0x0,1);
203}
204
205void setup() {
206 Serial.begin(38400);
207 pinMode(C2CK, OUTPUT);
208 pinMode(C2D, OUTPUT);
209 digitalWrite(LED, LOW);
210 digitalWrite(C2CK, HIGH);
211 delay(300);
212}
213
214unsigned int i;
215unsigned char retval;
216unsigned char flash_array[34],flash_array2[34],flash_array3[34];
217unsigned char rx_message[250],rx_message_ptr;
218unsigned char rx,main_state,bytes_to_receive,rx_state;
219unsigned char flash_buffer[130];
220unsigned long addr;
221
222unsigned char rx_state_machine (unsigned char state, unsigned char rx_char) {
223 if (state==0) {
224 rx_message_ptr = 0;
225 rx_message[rx_message_ptr++] = rx_char;
226 return 1;
227 }
228 if (state==1) {
229 bytes_to_receive = rx_char;
230 rx_message[rx_message_ptr++] = rx_char;
231 if (bytes_to_receive==0) return 3;
232 return 2;
233 }
234 if (state==2) {
235 rx_message[rx_message_ptr++] = rx_char;
236 bytes_to_receive--;
237 if (bytes_to_receive==0) return 3;
238 }
239 return state;
240}
241
242void loop() {
243 if (Serial.available()) {
244 rx = Serial.read();
245 rx_state = rx_state_machine(rx_state, rx);
246 if (rx_state == 3) {
247 switch (rx_message[0]) {
248 case 0x01:
249 c2_init_PI();
250 Serial.write(0x81);
251 digitalWrite(LED, HIGH);
252 rx_state = 0;
253 break;
254 case 0x02:
255 c2_rst();
256 Serial.write(0x82);
257 digitalWrite(LED, LOW);
258 rx_state = 0;
259 break;
260 case 0x03:
261 addr = (((unsigned long)(rx_message[3]))<<16) + (((unsigned long)(rx_message[4]))<<8) + (((unsigned long)(rx_message[5]))<<0);
262 for (i=0;i<rx_message[2];i++) {
263 flash_buffer[i] = rx_message[i+6];
264 }
265 c2_write_flash_block(addr,flash_buffer,rx_message[2]);
266 Serial.write(0x83);
267 rx_state = 0;
268 break;
269 case 0x04:
270 c2_erase_device();
271 Serial.write(0x84);
272 rx_state = 0;
273 break;
274 case 0x05:
275 Serial.write(0x85);
276 addr = (((unsigned long)(rx_message[3]))<<16) + (((unsigned long)(rx_message[4]))<<8) + (((unsigned long)(rx_message[5]))<<0);
277 c2_read_flash_block(addr,flash_buffer,rx_message[2]);
278 for (i=0;i<rx_message[2];i++) {
279 Serial.write(flash_buffer[i]);
280 }
281 rx_state = 0;
282 break;
283 case 0x06:
284 c2_write_addr(rx_message[3]);
285 c2_write_data(rx_message[4]);
286 Serial.write(0x86);
287 rx_state = 0;
288 break;
289 case 0x07:
290 c2_write_addr(rx_message[3]);
291 Serial.write(c2_read_data());
292 Serial.write(0x87);
293 rx_state = 0;
294 break;
295 }
296 }
297 }
298}