#include "config.h"
#include "twi_lib.h"
#include "twi_drv.h"
Go to the source code of this file.
Defines | |
#define | MAX_READ_BUFFER 50 |
Functions | |
void | twi_decode_status () |
Uint16 | twi_getchar (Byte addr) |
* This function can be used to receive an byte from a slave in polling fashion. | |
__interrupt void | twi_interrupt () |
void | twi_lib_init (void) |
This function allows to init the TWI controller. | |
Byte | twi_putchar (Byte addr, Byte b) |
This function can be used to send an byte to a slave in polling fashion. | |
unsigned char | twi_send_message_interrupt (unsigned char slave_addr, bit rw, Length_TWI_frame nbytes, unsigned char *info) |
This function sends TWI message to a slave. | |
unsigned char | twi_send_message_polling (unsigned char slave_addr, bit rw, Length_TWI_frame nbbytes, unsigned char *info) |
This function sends TWI message to a slave. | |
void | twi_slave_interrupt (void) |
This function can be called to be able to answer another master request in interruption fashion. | |
unsigned char | twi_slave_polling (void) |
This function can be called to be able to answer another master request in polling fashion. | |
Variables | |
U8 | data_length |
volatile U8 | flag_receive_buffer |
volatile U8 | flag_repeated_start |
volatile U8 | flag_transmit_buffer |
U8 | read_data_buffer [MAX_READ_BUFFER] |
volatile bit | twi_busy |
volatile unsigned char | twi_err |
volatile TWI_message xdata | twi_message |
volatile Length_TWI_frame | twi_nb_transmited |
volatile unsigned char | twi_recptr |
volatile unsigned char xdata | twi_slave_data [TWI_NB_SLAVE_DATA] |
void twi_decode_status | ( | ) |
Definition at line 101 of file twi_lib.c.
References TWI_message::address, TWI_message::buf, data_length, FALSE, flag_receive_buffer, flag_repeated_start, flag_transmit_buffer, TWI_message::nbbytes, read_data_buffer, TWI_message::rw, TRUE, TWI_ARBITRATION_LOST, TWI_BUS_ERROR, twi_busy, Twi_clear_aa, Twi_clear_si, Twi_clear_start, twi_err, Twi_get_data, Twi_get_status, TWI_HOST_ADR_NACK, twi_message, TWI_NB_SLAVE_DATA, twi_nb_transmited, TWI_OK, TWI_READ, twi_recptr, Twi_repeated_start, Twi_set_aa, Twi_set_data, Twi_set_start, Twi_set_stop, twi_slave_data, and TWI_UNKNOWN.
Referenced by twi_interrupt(), twi_send_message_polling(), and twi_slave_polling().
00102 { 00103 switch ( Twi_get_status() ) // switch (SSTA) 00104 { 00105 // STATE 00h: Bus Error has occurred 00106 // ACTION: Enter not addressed SLV mode and release bus 00107 case 0x00 : 00108 twi_busy = FALSE; 00109 twi_err = TWI_BUS_ERROR; 00110 break; 00111 00112 #ifdef TWI_MASTER 00113 //STATE 08h: A start condition has been sent 00114 //ACTION: SLR+R/W are transmitted, ACK bit received 00115 case 0x08 : 00116 Twi_clear_start(); //Pas besoin fait en hard ??? 00117 Twi_set_data(twi_message.address<<1); 00118 if ( twi_message.rw == TWI_READ ) 00119 { 00120 Twi_set_data(++Twi_get_data()); // Add 1 for Read bit in AdrWord 00121 } 00122 Twi_set_aa(); //from here to 0x18 transmit or 0x40 receive 00123 break; 00124 00125 //STATE 10h: A repeated start condition has been sent 00126 //ACTION: SLR+R/W are transmitted, ACK bit received 00127 case 0x10 : 00128 Twi_clear_start(); // Reset STA bit in SSCON 00129 Twi_set_data(twi_message.address<<1); 00130 if ( twi_message.rw == TWI_READ ) 00131 { 00132 Twi_set_data(++Twi_get_data()); // Add 1 for Read bit in AdrWord 00133 } 00134 Twi_set_aa(); // wait on ACK bit 00135 break; 00136 00137 //STATE 18h: SLR+W was transmitted, ACK bit received 00138 //ACTION: Transmit data byte, ACK bit received 00139 //PREVIOUS STATE: 0x08 or 0x10 00140 case 0x18 : // master transmit, after sending 00141 twi_nb_transmited=0; // slave address, now load data 00142 Twi_set_data(*(twi_message.buf)); // byte and send it 00143 00144 if (twi_message.nbbytes==0) // no datas to transmit 00145 { 00146 Twi_set_stop(); 00147 twi_err = TWI_OK; 00148 twi_busy = FALSE; // transfer complete, clear twi_busy 00149 } 00150 Twi_clear_si(); 00151 break; 00152 00153 //STATE 20h: SLR+W was transmitted, NOT ACK bit received 00154 //ACTION: Transmit STOP 00155 case 0x20 : 00156 Twi_set_stop(); // Twi_set_stop will also clear twiint flag 00157 twi_busy = FALSE; 00158 twi_err = TWI_HOST_ADR_NACK; 00159 break; 00160 00161 //STATE 28h: DATA was transmitted, ACK bit received 00162 //ACTION: If last byte, send STOP, else send more data bytes 00163 case 0x28: // master transmit, after sending ; data byte, ACK received 00164 twi_nb_transmited++; // inc nb data transmit on message 00165 twi_message.buf++; // inc pointer ti data to be transmited 00166 if ( twi_nb_transmited < twi_message.nbbytes ) // if there are still bytes to send 00167 { 00168 Twi_set_data(*(twi_message.buf)); 00169 Twi_set_aa(); // wait on ACK bit 00170 } 00171 else 00172 { 00173 if(flag_repeated_start == 1) 00174 { 00175 //repeated start 00176 Twi_repeated_start(); 00177 00178 //init next transmission 00179 twi_nb_transmited = 0; 00180 twi_message.rw = TWI_READ; 00181 twi_message.nbbytes = data_length; 00182 twi_message.buf = read_data_buffer; 00183 00184 flag_repeated_start = 0; 00185 } 00186 else if(flag_repeated_start == 0) 00187 { 00188 //run out of data, send stop, 00189 Twi_set_stop(); // Twi_set_stop will also clear twiint flag 00190 00191 //end of write command 00192 flag_transmit_buffer = 0; 00193 } 00194 00195 twi_err = TWI_OK; 00196 twi_busy = FALSE; //transfer complete, clear twi_busy 00197 } 00198 break; 00199 00200 //STATE 30h: DATA was transmitted, NOT ACK bit received 00201 //ACTION: Transmit STOP 00202 case 0x30 : 00203 Twi_set_stop(); // Twi_set_stop will also clear twiint flag 00204 twi_busy = FALSE; 00205 twi_err = TWI_HOST_ADR_NACK; 00206 break; 00207 00208 //STATE 38h: Arbitration lost in SLA+W or DATA. 00209 //ACTION: Release bus, enter not addressed SLV mode 00210 // Wait for bus lines to be free 00211 case 0x38 : 00212 twi_busy = FALSE; 00213 twi_err = TWI_ARBITRATION_LOST; 00214 Twi_clear_si(); 00215 // #ifdef USER_TWI_FCT_ARBITRATION_LOST_IN_SLA+W_OR_DATA 00216 // TWI_fct_arb_lostinSLAorDATA(); 00217 // #endif 00218 break; 00219 00220 //MASTER RECEIVER MODE FOLLOWS 00221 //STATE 40h: SLA+R transmitted, ACK received 00222 //ACTION: Receive DATA, ACK to be returned 00223 //PREVIOS STATE: 0x08 or 0x10 00224 case 0x40 : //master receive, after sending 00225 if ( twi_message.nbbytes == 1 ) 00226 { 00227 Twi_clear_aa(); // only one data to receive, noACK to be send after the fisrt incoming data 00228 Twi_clear_si(); 00229 } 00230 else if (!twi_message.nbbytes ) Twi_set_stop(); // special case: no data to read ! clear also twint 00231 else 00232 { 00233 Twi_set_aa(); //wait on ACK bit 00234 twi_nb_transmited=0; //data byte to be received, NOT ACK bit to follow --> 0x58 00235 } 00236 break; 00237 00238 //STATE 48h: SLA+R transmitted, NOT ACK received 00239 //ACTION: Transmit STOP 00240 case 0x48 : 00241 Twi_set_stop(); //clear also twint 00242 twi_busy = FALSE; 00243 twi_err = TWI_HOST_ADR_NACK; 00244 break; 00245 00246 //STATE 50h: Data has been received, ACK returned 00247 //ACTION: Read DATA. If expecting more continue else STOP 00248 case 0x50 : //master receive, received data 00249 //byte and ACK, copy it into 00250 *(twi_message.buf+twi_nb_transmited) = Twi_get_data(); //buffer 00251 twi_nb_transmited++; 00252 if ( twi_nb_transmited < (twi_message.nbbytes-1) ) Twi_set_aa(); // get more bytes 00253 else 00254 { 00255 Twi_clear_aa(); //only one more byte to come 00256 Twi_clear_si(); 00257 } 00258 break; 00259 00260 //STATE 58h: Data has been received, NOT ACK returned 00261 //ACTION: Read DATA. Generate STOP 00262 case 0x58 : 00263 *(twi_message.buf+twi_nb_transmited) = Twi_get_data(); 00264 Twi_set_stop(); 00265 00266 //the receive buffer is ready 00267 flag_receive_buffer = 0; 00268 00269 twi_busy = FALSE; 00270 twi_err = TWI_OK; 00271 break; 00272 #endif 00273 00274 00275 #ifdef TWI_SLAVE 00276 //STATE 60h: Own SLA+W has been received,ACK returned 00277 //ACTION: Read DATA. return ACK 00278 case 0x60 : 00279 Twi_set_aa(); 00280 twi_busy = TRUE; 00281 twi_recptr=0; 00282 break; 00283 00284 //STATE 68h: Arbitration lost in SLA and R/W as MASTER. Own SLA + W has been received. ACK returned 00285 //ACTION: Read DATA. return ACK ;re-start MASTER, 00286 case 0x68 : 00287 Twi_set_start(); 00288 break; 00289 00290 //STATE 70h: General call received, ACK returned 00291 //ACTION: Receive DATA. return ACK 00292 case 0x70 : 00293 Twi_set_aa(); 00294 twi_busy = TRUE; 00295 break; 00296 00297 //STATE 78h: Arbitration lost in SLA+R/W as MASTER. General call has arrived ack returned 00298 //ACTION: Receive DATA. return ACK. Restart master 00299 case 0x78 : 00300 Twi_set_start(); 00301 twi_busy = TRUE; 00302 break; 00303 00304 //STATE 80h: Previously addressed with own SLA. Data received and ACK returned 00305 //ACTION: Read DATA. 00306 case 0x80 : 00307 twi_slave_data[twi_recptr] = Twi_get_data(); 00308 twi_recptr ++; 00309 if ( twi_recptr < TWI_NB_SLAVE_DATA ) Twi_set_aa(); // ACK will be returned 00310 else 00311 { 00312 Twi_clear_aa(); // it was last data not ACK will be returned ( buffer full ) 00313 Twi_clear_si(); 00314 } 00315 break; 00316 00317 //STATE 88h: Previously addressed with own SLA. Data received and NOT ACK returned 00318 //ACTION: Dont' Read DATA. Enter NOT addressed SLV mode 00319 case 0x88 : 00320 //STATE 98h: Previously addressed with general call. Data arrved and NOT ACK returned 00321 //ACTION: Dont Read DATA. Enter NOT addressed SLV mode 00322 case 0x98 : 00323 Twi_set_aa(); // ready to send another ACK if addresed as slave 00324 break; 00325 00326 //STATE 90h: Previously addressed with general call. Data received and ACK returned 00327 //ACTION: Read DATA. 00328 case 0x90 : 00329 twi_slave_data[twi_recptr] = Twi_get_data(); 00330 twi_recptr = twi_recptr + 1; 00331 Twi_clear_si(); 00332 break; 00333 00334 //STATE A0h: A stop or repeated start has arrived, whilst still addressed as SLV/REC or SLV/TRX 00335 //ACTION: Dont Read DATA. Enter NOT addressed SLV mode 00336 case 0xA0 : 00337 Twi_set_aa(); 00338 twi_busy = FALSE; 00339 twi_err = TWI_OK; 00340 break; 00341 00342 //STATE A8h: addressed with own SLA+R 00343 //ACTION: Prepare first data to be transmited 00344 case 0xA8 : 00345 00346 twi_busy = TRUE; 00347 twi_recptr=0; 00348 Twi_set_data(twi_slave_data[0]); // Prepare next data 00349 Twi_set_aa(); 00350 break; 00351 00352 00353 //STATE B8h: Previously addressed with own SLA. Data sent 00354 // and ACK returned 00355 //ACTION: Write DATA. 00356 case 0xB8 : 00357 twi_recptr++; 00358 if ( twi_recptr < TWI_NB_SLAVE_DATA ) Twi_set_data(twi_slave_data[twi_recptr]); 00359 else 00360 Twi_clear_aa(); // it was last data not ACK will be returned ( buffer full ) 00361 Twi_clear_si(); 00362 break; 00363 00364 00365 //STATE C0h: Previously addressed with own SLA. Data sent and NACK returned 00366 //ACTION: It was last data to be sent 00367 case 0xC0 : 00368 twi_busy=FALSE; 00369 twi_err = TWI_OK; 00370 Twi_clear_si(); 00371 break; 00372 #endif 00373 00374 //if we arrived here, unknown state has occurred..... 00375 default : 00376 Twi_set_stop(); 00377 twi_busy = FALSE; 00378 twi_err = TWI_UNKNOWN; 00379 break; 00380 } 00381 }
* This function can be used to receive an byte from a slave in polling fashion.
addr,: | slave to address with this message. |
Definition at line 576 of file twi_lib.c.
References Twi_clear_aa, Twi_clear_si, Twi_clear_start, Twi_get_data, Twi_get_status, TWI_OK, Twi_set_aa, Twi_set_data, Twi_set_start, Twi_set_stop, TWI_UNKNOWN, Twi_wait_event, and Twi_wait_hw_stop.
00577 { 00578 Union16 data ret; 00579 00580 ret.b[0] = TWI_UNKNOWN; 00581 ret.b[1] = 0; 00582 Twi_wait_hw_stop(); 00583 Twi_set_start(); 00584 Twi_wait_event(); 00585 if (Twi_get_status() == 0x08) //start sent 00586 { 00587 Twi_clear_start(); 00588 Twi_set_data((addr<<1)+1); //ADR+R 00589 Twi_set_aa(); //Also clear TWINT 00590 Twi_wait_event(); 00591 if (Twi_get_status() == 0x40) //ADR+R sent 00592 { 00593 Twi_clear_aa(); //only one byte t receive: NACK after 00594 Twi_clear_si(); 00595 Twi_wait_event(); 00596 if (Twi_get_status() == 0x58) //data received 00597 { 00598 ret.b[1] = Twi_get_data(); 00599 Twi_set_stop(); //Also clear TWINT 00600 ret.b[0] = TWI_OK; 00601 } 00602 } 00603 else 00604 { 00605 Twi_clear_start(); 00606 Twi_set_stop(); //Also clear TWINT 00607 } 00608 } 00609 return ret.w; 00610 }
__interrupt void twi_interrupt | ( | ) |
Definition at line 633 of file twi_lib.c.
References twi_decode_status().
00635 { 00636 twi_decode_status(); 00637 // Twi_clear_si(); //REMOVE FROM MAIN LOOP, ADDED IN ALL NECESARY CASE (See JSB /RLE) 00638 }
void twi_lib_init | ( | void | ) |
This function allows to init the TWI controller.
Definition at line 76 of file twi_lib.c.
References FOSC, TWI_CONFIG, Twi_init_hw, and Twi_set_baudrate.
00077 { 00078 Twi_set_baudrate(FOSC/TWI_BAUDRATE); 00079 Twi_init_hw(TWI_CONFIG); 00080 }
This function can be used to send an byte to a slave in polling fashion.
addr,: | slave to address with this message. | |
byte,: | byte to transmit. |
Definition at line 528 of file twi_lib.c.
References Twi_clear_si, Twi_clear_start, Twi_get_status, TWI_OK, Twi_set_aa, Twi_set_data, Twi_set_start, Twi_set_stop, TWI_UNKNOWN, Twi_wait_event, and Twi_wait_hw_stop.
00529 { 00530 Twi_wait_hw_stop(); 00531 Twi_set_start(); 00532 Twi_wait_event(); 00533 if (Twi_get_status() == 0x08) //start sent 00534 { 00535 Twi_clear_start(); 00536 Twi_set_data(addr<<1); 00537 Twi_set_aa(); //Also clear TWINT 00538 Twi_wait_event(); 00539 if (Twi_get_status() == 0x18) //ADR+W sent 00540 { 00541 Twi_set_data(b); 00542 Twi_clear_si(); 00543 Twi_wait_event(); 00544 if (Twi_get_status() == 0x28) //data sent 00545 { 00546 Twi_set_stop(); 00547 Twi_clear_si(); 00548 return TWI_OK; 00549 } 00550 } 00551 else 00552 { 00553 Twi_clear_start(); 00554 Twi_set_stop(); //Also clear TWINT 00555 } 00556 } 00557 Twi_clear_start(); 00558 Twi_clear_si(); 00559 return TWI_UNKNOWN; 00560 }
unsigned char twi_send_message_interrupt | ( | unsigned char | slave_addr, | |
bit | rw, | |||
Length_TWI_frame | nbytes, | |||
Uchar * | info | |||
) |
This function sends TWI message to a slave.
This transmition is managed in interruption fashion.
slave_addr,: | slave to address with this message. | |
rw,: | This field allows to indicate a read or write message
| |
nb_byte,: | This field gives the byte number to read or write. | |
*info,: | pointer to the data to be processed. |
Definition at line 437 of file twi_lib.c.
References TWI_message::address, TWI_message::buf, Enable_twi_interrupt, TWI_message::nbbytes, TWI_message::rw, twi_busy, twi_err, twi_message, twi_nb_transmited, TWI_NOT_FREE, TWI_OK, Twi_set_start, Twi_set_stop, and Twi_wait_hw_stop.
00438 { 00439 twi_message.address = slave_addr; 00440 twi_message.rw = rw; 00441 twi_message.nbbytes = nbytes; 00442 twi_message.buf = info; 00443 Twi_wait_hw_stop(); 00444 twi_nb_transmited=0; 00445 if (!twi_busy) 00446 { 00447 twi_err = TWI_OK; 00448 twi_busy =1; 00449 Enable_twi_interrupt(); 00450 Twi_set_start(); 00451 return twi_err; 00452 } 00453 Twi_set_stop(); 00454 return TWI_NOT_FREE; 00455 }
unsigned char twi_send_message_polling | ( | unsigned char | slave_addr, | |
bit | rw, | |||
Length_TWI_frame | nbytes, | |||
Uchar * | info | |||
) |
This function sends TWI message to a slave.
This transmition is managed in polling fashion.
slave_addr,: | slave to address with this message. | |
rw,: | This field allows to indicate a read or write message
| |
nb_byte,: | This field gives the byte number to read or write. | |
*info,: | pointer to the data to be processed. |
Definition at line 385 of file twi_lib.c.
References TWI_message::address, TWI_message::buf, Disable_twi_interrupt, TWI_message::nbbytes, TWI_message::rw, twi_busy, twi_decode_status(), twi_err, twi_message, twi_nb_transmited, TWI_NOT_FREE, TWI_OK, Twi_set_start, Twi_set_stop, Twi_wait_event, and Twi_wait_hw_stop.
00386 { 00387 twi_message.address = slave_addr; 00388 twi_message.rw = rw; 00389 twi_message.nbbytes = nbbytes; 00390 twi_message.buf = info; 00391 Twi_wait_hw_stop(); 00392 Disable_twi_interrupt(); //FIXME 00393 twi_nb_transmited=0; 00394 if (!twi_busy) 00395 { 00396 twi_busy =1; 00397 twi_err = TWI_OK; 00398 Twi_set_start(); 00399 while (twi_busy) 00400 { 00401 Twi_wait_event(); 00402 twi_decode_status(); 00403 // Twi_clear_si(); //REMOVE FROM MAIN LOOP, ADDED IN ALL NECESARY CASE (See JSB /RLE) 00404 } 00405 // Twi_set_stop(); RLE 00406 return twi_err; 00407 } 00408 Twi_set_stop(); 00409 return TWI_NOT_FREE; 00410 }
void twi_slave_interrupt | ( | void | ) |
This function can be called to be able to answer another master request in interruption fashion.
Definition at line 507 of file twi_lib.c.
References Enable_twi_interrupt.
00508 { 00509 Enable_interrupt(); 00510 Enable_twi_interrupt(); 00511 }
unsigned char twi_slave_polling | ( | void | ) |
This function can be called to be able to answer another master request in polling fashion.
Definition at line 477 of file twi_lib.c.
References twi_busy, Twi_clear_si, twi_decode_status(), twi_err, and Twi_wait_event.
00478 { 00479 Twi_wait_event(); 00480 twi_decode_status(); 00481 Twi_clear_si(); 00482 while (twi_busy) 00483 { 00484 Twi_wait_event(); 00485 twi_decode_status(); 00486 // Twi_clear_si();//REMOVE FROM MAIN LOOP, ADDED IN ALL NECESARY CASE (See JSB /RLE) 00487 } 00488 return twi_err; 00489 }
Referenced by twi_decode_status().
volatile U8 flag_receive_buffer |
Referenced by twi_decode_status().
volatile U8 flag_repeated_start |
Referenced by twi_decode_status().
volatile U8 flag_transmit_buffer |
Referenced by twi_decode_status().
U8 read_data_buffer[MAX_READ_BUFFER] |
Referenced by twi_decode_status().
volatile bit twi_busy |
Definition at line 22 of file twi_lib.c.
Referenced by twi_decode_status(), twi_send_message_interrupt(), twi_send_message_polling(), and twi_slave_polling().
volatile unsigned char twi_err |
Definition at line 23 of file twi_lib.c.
Referenced by twi_decode_status(), twi_send_message_interrupt(), twi_send_message_polling(), and twi_slave_polling().
volatile TWI_message xdata twi_message |
Definition at line 41 of file twi_lib.c.
Referenced by twi_decode_status(), twi_send_message_interrupt(), and twi_send_message_polling().
volatile Length_TWI_frame twi_nb_transmited |
Definition at line 24 of file twi_lib.c.
Referenced by twi_decode_status(), twi_send_message_interrupt(), and twi_send_message_polling().
volatile unsigned char twi_recptr |
volatile unsigned char xdata twi_slave_data[TWI_NB_SLAVE_DATA] |