Content originally posted in LPCWare by larryvc on Mon Jan 05 20:30:56 MST 2015 What happens when you bitwise inclusive OR a value with 0?
Many of the I2C code examples in UM10601 pages 340-347 have entries like this where the code is ORing a value with 0. (Also, some of the comments do not match the operations. These are obviously write operations.) Sorry NXP, this is cut and paste without verification, again. :~
LPC_I2C->MSTDAT = (0x23 << 1) | 0; // address and 1 for RWn bit in
// order to read data
LPC_I2C->MSTDAT = (0x23 << 1) | 0; // address and 0 for RWn bit in order to write
// subaddress
Granted, bit 0, the RWn bit, is being cleared by the left shift anyway, but to do this correctly, and to not confuse new users, the code needs to be written like this to clear the RWn bit:
LPC_I2C->MSTDAT = (0x23 << 1) & ~(1<<0);
ORing with 1 for the read operations is correct in the code examples but could also be written as:
LPC_I2C->MSTDAT = (0x23 << 1) | (1<<0);
From the UM: (reformatted for posting)
Table 308. I2C Code example Interrupt handler
void I2c_IRQHandler() {
uint32_t intstat = LPC_I2C->INTSTAT;
uint32_t stat = LPC_I2C->STAT;
if(intstat & I2C_STAT_MSTPENDING) {
uint32_t mst_state = stat & I2C_STAT_MSTSTATE;
if(mst_state == I2C_STAT_MSTST_IDLE) {
LPC_I2C->MSTDAT = (0x23 << 1) | 1; // address and 1 for RWn bit in order to read data
LPC_I2C->MSTCTL = I2C_MSTCTL_MSTSTART; // send start
}
if(mst_state == I2C_STAT_MSTST_RX) {
uint8_t data;
data = LPC_I2C->MSTDAT; // receive data
if(data != 0xdd) abort();
LPC_I2C->MSTDAT = (0x23 << 1) | 0; // address and 1 for RWn bit in order to read data
LPC_I2C->MSTCTL = I2C_MSTCTL_MSTSTART; // repeated start (nack implied)
}
if(mst_state == I2C_STAT_MSTSTX) {
LPC_I2C->MSTCTL = I2C_MSTCTL_MSTSTOP; // stop transaction
LPC_I2C->INTENCLR = I2C_STAT_MSTPENDING;
}
}
}