Mercurial > ~darius > hgwebdir.cgi > avr-lib
comparison ds1307.c @ 8:119688bb743f
Don't spin forever waiting for the TWI hardware to do something.
I _think_ this will help the case where I find the micro is hanging but I
haven't seen an error from it yet.
author | darius@dons.net.au |
---|---|
date | Fri, 01 May 2009 15:21:31 +0930 |
parents | 3da232f97e81 |
children | b5e4591b6570 |
comparison
equal
deleted
inserted
replaced
7:d111f64eb619 | 8:119688bb743f |
---|---|
36 | 36 |
37 #include "ds1307.h" | 37 #include "ds1307.h" |
38 | 38 |
39 // #define TWDEBUG | 39 // #define TWDEBUG |
40 | 40 |
41 /* Helper code to wait for the TWCR to do something */ | |
42 #define WAITFORTWINT() do { \ | |
43 uint8_t i; \ | |
44 for (i = 0; i < 255 && (TWCR & _BV(TWINT)) == 0; i++) \ | |
45 _delay_ms(1); \ | |
46 if (i == 255) \ | |
47 return(IIC_NORESP); \ | |
48 } while (0) | |
49 | |
50 | |
41 /* | 51 /* |
42 * ds1307_init | 52 * ds1307_init |
43 * | 53 * |
44 * Setup TWI interface | 54 * Setup TWI interface |
45 * | 55 * |
85 | 95 |
86 /* Generate START */ | 96 /* Generate START */ |
87 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); | 97 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); |
88 | 98 |
89 /* Spin waiting for START to be generated */ | 99 /* Spin waiting for START to be generated */ |
90 while ((TWCR & _BV(TWINT)) == 0) | 100 WAITFORTWINT(); |
91 ; | 101 |
92 switch (twst = TW_STATUS) { | 102 switch (twst = TW_STATUS) { |
93 case TW_REP_START: /* OK but shouldn't happen */ | 103 case TW_REP_START: /* OK but shouldn't happen */ |
94 case TW_START: | 104 case TW_START: |
95 break; | 105 break; |
96 | 106 |
108 /* Send SLA+W */ | 118 /* Send SLA+W */ |
109 TWDR = sla | TW_WRITE; | 119 TWDR = sla | TW_WRITE; |
110 TWCR = _BV(TWINT) | _BV(TWEN); | 120 TWCR = _BV(TWINT) | _BV(TWEN); |
111 | 121 |
112 /* Spin waiting for a response to be generated */ | 122 /* Spin waiting for a response to be generated */ |
113 while ((TWCR & _BV(TWINT)) == 0) | 123 WAITFORTWINT(); |
114 ; | |
115 | 124 |
116 #ifdef TWDEBUG | 125 #ifdef TWDEBUG |
117 printf_P(PSTR("Sent SLA+W\r\n")); | 126 printf_P(PSTR("Sent SLA+W\r\n")); |
118 #endif | 127 #endif |
119 switch (twst = TW_STATUS) { | 128 switch (twst = TW_STATUS) { |
137 /* Send address */ | 146 /* Send address */ |
138 TWDR = adr; | 147 TWDR = adr; |
139 TWCR = _BV(TWINT) | _BV(TWEN); | 148 TWCR = _BV(TWINT) | _BV(TWEN); |
140 | 149 |
141 /* Spin waiting for a response to be generated */ | 150 /* Spin waiting for a response to be generated */ |
142 while ((TWCR & _BV(TWINT)) == 0) | 151 WAITFORTWINT(); |
143 ; | 152 |
144 #ifdef TWDEBUG | 153 #ifdef TWDEBUG |
145 printf_P(PSTR("Sent address\r\n")); | 154 printf_P(PSTR("Sent address\r\n")); |
146 #endif | 155 #endif |
147 switch ((twst = TW_STATUS)) { | 156 switch ((twst = TW_STATUS)) { |
148 case TW_MT_DATA_ACK: | 157 case TW_MT_DATA_ACK: |
162 return IIC_UNKNOWN; | 171 return IIC_UNKNOWN; |
163 } | 172 } |
164 | 173 |
165 /* Master receive cycle */ | 174 /* Master receive cycle */ |
166 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); | 175 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); |
167 while ((TWCR & _BV(TWINT)) == 0) /* wait for transmission */ | 176 |
168 ; | 177 /* wait for transmission */ |
178 WAITFORTWINT(); | |
169 | 179 |
170 #ifdef TWDEBUG | 180 #ifdef TWDEBUG |
171 printf_P(PSTR("Sent START\r\n")); | 181 printf_P(PSTR("Sent START\r\n")); |
172 #endif | 182 #endif |
173 switch ((twst = TW_STATUS)) { | 183 switch ((twst = TW_STATUS)) { |
187 /* send SLA+R */ | 197 /* send SLA+R */ |
188 TWDR = sla | TW_READ; | 198 TWDR = sla | TW_READ; |
189 TWCR = _BV(TWINT) | _BV(TWEN); /* clear interrupt to start transmission */ | 199 TWCR = _BV(TWINT) | _BV(TWEN); /* clear interrupt to start transmission */ |
190 | 200 |
191 /* Spin waiting for a response to be generated */ | 201 /* Spin waiting for a response to be generated */ |
192 while ((TWCR & _BV(TWINT)) == 0) | 202 WAITFORTWINT(); |
193 ; | 203 |
194 #ifdef TWDEBUG | 204 #ifdef TWDEBUG |
195 printf_P(PSTR("Sent SLA+R\r\n")); | 205 printf_P(PSTR("Sent SLA+R\r\n")); |
196 #endif | 206 #endif |
197 switch ((twst = TW_STATUS)) { | 207 switch ((twst = TW_STATUS)) { |
198 case TW_MR_SLA_ACK: | 208 case TW_MR_SLA_ACK: |
218 /* Send NAK on last byte */ | 228 /* Send NAK on last byte */ |
219 if (len == 1) | 229 if (len == 1) |
220 twcr = _BV(TWINT) | _BV(TWEN); | 230 twcr = _BV(TWINT) | _BV(TWEN); |
221 TWCR = twcr; /* clear int to start transmission */ | 231 TWCR = twcr; /* clear int to start transmission */ |
222 /* Spin waiting for a response to be generated */ | 232 /* Spin waiting for a response to be generated */ |
223 while ((TWCR & _BV(TWINT)) == 0) | 233 WAITFORTWINT(); |
224 ; | 234 |
225 #ifdef TWDEBUG | 235 #ifdef TWDEBUG |
226 printf_P(PSTR("Data request done\r\n")); | 236 printf_P(PSTR("Data request done\r\n")); |
227 #endif | 237 #endif |
228 switch ((twst = TW_STATUS)) { | 238 switch ((twst = TW_STATUS)) { |
229 case TW_MR_DATA_NACK: | 239 case TW_MR_DATA_NACK: |
270 | 280 |
271 /* Generate START */ | 281 /* Generate START */ |
272 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); | 282 TWCR = _BV(TWINT) | _BV(TWSTA) | _BV(TWEN); |
273 | 283 |
274 /* Spin waiting for START to be generated */ | 284 /* Spin waiting for START to be generated */ |
275 while ((TWCR & _BV(TWINT)) == 0) | 285 WAITFORTWINT(); |
276 ; | 286 |
277 switch (twst = TW_STATUS) { | 287 switch (twst = TW_STATUS) { |
278 case TW_REP_START: /* OK but shouldn't happen */ | 288 case TW_REP_START: /* OK but shouldn't happen */ |
279 case TW_START: | 289 case TW_START: |
280 break; | 290 break; |
281 | 291 |
294 /* Send SLA+W */ | 304 /* Send SLA+W */ |
295 TWDR = sla | TW_WRITE; | 305 TWDR = sla | TW_WRITE; |
296 TWCR = _BV(TWINT) | _BV(TWEN); | 306 TWCR = _BV(TWINT) | _BV(TWEN); |
297 | 307 |
298 /* Spin waiting for a response to be generated */ | 308 /* Spin waiting for a response to be generated */ |
299 while ((TWCR & _BV(TWINT)) == 0) | 309 WAITFORTWINT(); |
300 ; | |
301 | 310 |
302 #ifdef TWDEBUG | 311 #ifdef TWDEBUG |
303 printf_P(PSTR("Sent SLA+W\r\n")); | 312 printf_P(PSTR("Sent SLA+W\r\n")); |
304 #endif | 313 #endif |
305 switch (twst = TW_STATUS) { | 314 switch (twst = TW_STATUS) { |
323 /* Send address */ | 332 /* Send address */ |
324 TWDR = adr; | 333 TWDR = adr; |
325 TWCR = _BV(TWINT) | _BV(TWEN); | 334 TWCR = _BV(TWINT) | _BV(TWEN); |
326 | 335 |
327 /* Spin waiting for a response to be generated */ | 336 /* Spin waiting for a response to be generated */ |
328 while ((TWCR & _BV(TWINT)) == 0) | 337 WAITFORTWINT(); |
329 ; | 338 |
330 #ifdef TWDEBUG | 339 #ifdef TWDEBUG |
331 printf_P(PSTR("Sent address\r\n")); | 340 printf_P(PSTR("Sent address\r\n")); |
332 #endif | 341 #endif |
333 switch ((twst = TW_STATUS)) { | 342 switch ((twst = TW_STATUS)) { |
334 case TW_MT_DATA_ACK: | 343 case TW_MT_DATA_ACK: |
352 for (; len > 0; len--) { | 361 for (; len > 0; len--) { |
353 TWDR = *data++; | 362 TWDR = *data++; |
354 TWCR = _BV(TWINT) | _BV(TWEN); | 363 TWCR = _BV(TWINT) | _BV(TWEN); |
355 | 364 |
356 /* Spin waiting for a response to be generated */ | 365 /* Spin waiting for a response to be generated */ |
357 while ((TWCR & _BV(TWINT)) == 0) | 366 WAITFORTWINT(); |
358 ; | 367 |
359 #ifdef TWDEBUG | 368 #ifdef TWDEBUG |
360 printf_P(PSTR("Data sent\r\n")); | 369 printf_P(PSTR("Data sent\r\n")); |
361 #endif | 370 #endif |
362 switch ((twst = TW_STATUS)) { | 371 switch ((twst = TW_STATUS)) { |
363 case TW_MT_DATA_NACK: | 372 case TW_MT_DATA_NACK: |