burner.c00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00074 #include <sys/ports.h>
00075
00076 typedef void __attribute__ ((noreturn)) (* func)();
00077
00078 static unsigned short get_char (void);
00079 static unsigned char* get_addr (void);
00080 static volatile int __attribute__((noreturn)) main ();
00081 static void flush (void);
00082 void eeprom_write_byte (unsigned char *p, const unsigned char value);
00083 void udelay_10ms (void);
00084
00085 void
00086 _start()
00087 {
00088 __asm__ __volatile__ ("bra main");
00089
00090 }
00091
00092 static void
00093 flush ()
00094 {
00095 while (!(_io_ports[M6811_SCSR] & M6811_TDRE))
00096 continue;
00097 }
00098
00099 static void
00100 put_char (unsigned char c)
00101 {
00102 flush ();
00103 _io_ports[M6811_SCDR] = c;
00104 _io_ports[M6811_SCCR2] |= M6811_TE;
00105 }
00106
00107 static volatile int
00108 main ()
00109 {
00110 unsigned char* addr;
00111 unsigned char c;
00112
00113 while (1)
00114 {
00115
00116 put_char ('\n');
00117 put_char ('>');
00118
00119
00120 c = get_char ();
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133 if (c == 'M')
00134 {
00135 unsigned char size;
00136
00137 addr = get_addr ();
00138 size = get_char ();
00139 do
00140 {
00141 *addr = get_char ();
00142 eeprom_write_byte (addr, get_char ());
00143 put_char (*addr);
00144 }
00145 while (--size != 0);
00146 }
00147
00148
00149
00150
00151
00152
00153
00154 else if (c == 'G')
00155 {
00156 func handler;
00157
00158 addr = get_addr ();
00159 put_char ('G');
00160 put_char ('\n');
00161 flush ();
00162
00163 handler = (func) addr;
00164 handler ();
00165 }
00166
00167
00168 else
00169 {
00170 put_char ('?');
00171 }
00172 }
00173 }
00174
00175 void
00176 udelay_10ms ()
00177 {
00178 unsigned short tmp = 40000;
00179
00180 __asm__ __volatile__ ("1: subd #1\n"
00181 " bne 1b" : "=d"(tmp) : "d"(tmp));
00182 }
00183
00193 void
00194 eeprom_write_byte (unsigned char *p, const unsigned char value)
00195 {
00196 unsigned char diff;
00197
00198 diff = *p ^ value;
00199 if (diff)
00200 {
00201 if (diff & value)
00202 {
00203
00204 diff = *p ^ value;
00205 if (diff == 0)
00206 return;
00207
00208 _io_ports[M6811_PPROG] = M6811_EELAT | M6811_ERASE | M6811_BYTE;
00209 *p = value;
00210 _io_ports[M6811_PPROG] = M6811_EELAT | M6811_ERASE
00211 | M6811_BYTE | M6811_EEPGM;
00212
00213
00214 udelay_10ms ();
00215 _io_ports[M6811_PPROG] = M6811_EELAT | M6811_ERASE | M6811_BYTE;
00216 }
00217
00218
00219 _io_ports[M6811_PPROG] = M6811_EELAT;
00220 *p = value;
00221 _io_ports[M6811_PPROG] = M6811_EELAT | M6811_EEPGM;
00222
00223
00224 udelay_10ms ();
00225 _io_ports[M6811_PPROG] = M6811_EELAT;
00226 _io_ports[M6811_PPROG] = 0;
00227 }
00228 }
00229
00230 static unsigned char*
00231 get_addr ()
00232 {
00233 unsigned short c1, c2;
00234
00235 c1 = get_char ();
00236 c2 = get_char ();
00237 return (unsigned char*) (((unsigned short) c1 << 8) | ((unsigned short) c2));
00238 }
00239
00240 static unsigned short
00241 get_char ()
00242 {
00243 unsigned char c;
00244 volatile unsigned char* ports = &_io_ports[0];
00245
00246 while (1)
00247 {
00248 c = ports[M6811_SCSR];
00249
00250 if (c & M6811_RDRF)
00251 break;
00252 }
00253 return ports[M6811_SCDR];
00254 }
|