I am using stm32f105 to control 5 I2C buses and some other peripheral circuits. The problem is that I used all dedicated I2C pins by other peripheral circuits. Is it possible I change a GPIO (General purpose I/O) pins as I2C.
For that purpose, a pin must be output for a while and than change to input (for SDA). i.e. a pin must be output and load the address, then change to input and receive the ACK from slave, then again read or receive data from slave, then finally change back to output.
I am wondering is it practical? is there any source code for that any where ?
Best Answer
Yes, it's possible. Set both pins to open drain output in
GPIOx_CRL
orGPIOx_CRH
, and you don't have to worry about switching the pin direction. If the port bit is1
, then the wire is pulled up by the external resitor, and you can read back1
inGPIOx_IDR
, or the slave pulls it low, and you'll have0
inGPIOx_IDR
.There is a straightforward software implementation on Wikipedia. Use
TIM6
orTIM7
for the delay, orDWT->CYCCNT
if there are no timers left available. Leave out thearbitration_lost
parts if you are the only master on the bus.