I2C Working
- JonHylands
- Posts: 69
- Joined: Sun Dec 29, 2013 1:33 am
I2C Working
I don't know if anyone has played with the general I2C library, but I have been able to successfully talk to an L3GD20 3-axis gyro using SCL2/SDA2 on my MicroPython board. The mma sensor on the PYBv4 uses its own i2c code, for some reason. I really like how simple it is to use, and how it handles the transitions from writing to reading seamlessly.
- Jon
- Jon
Re: I2C Working
Would be glad to see a code snippet. This way we could test the code formatting of the forum too
Re: I2C Working
There's a set of useful I2C specific functions built on top as a python library here:
https://github.com/Neon22/micropython-I2C
Needs testing on a board...
here's a code snippet for torvag
Looks like no syntax highlighting... (I expect we need python and C highlighting)
https://github.com/Neon22/micropython-I2C
Needs testing on a board...
here's a code snippet for torvag
Code: Select all
class I2C_lib(pyb_I2C):
""" Extend i2c interface
Existing methods are:
- start()
- write(byte) # send byte
- read() # read byte
- readAndStop()
- stop()
"""
def __init__(self, port, dev_addr):
" nothing more to add "
#super().__init__(port, dev_addr) # python 3 form
super(I2C_lib, self).__init__(port, dev_addr) # python 2.7 - not needed
Re: I2C Working
Hello, first time poster, long time admired of micropython! Apologies if this isn't in the appropriate section.
I've also been communicating with the 3-axis L3GD20 unit. The I2C interface has been working like a charm!
Initially I was pulling 6 bytes out (3 axis, higher and lower bytes) from the device.
a = [0]*6
for i in range(0,6):
a = i2c.mem_read(1,device,subaddress+i)
But a much better a less ugly way is:
a = i2c.mem_read(6,device,subaddress) # read in a single call
HOWEVER
As a kickstarter backer I was using the firmware which came installed (sorry didn't note the firmware number...). I wondered if the math.asin function had been added in the most recent firmware so I installed pybv10-2014-08-09-v1.2-84-g590b2ab.dfu. Unfortunately the I2C routine now seemed to be causing me problems, but only when I read multiple bytes in one block and then only *sometimes*.
It turned out cases like this (below) now cause a problem (where they didn't previously before the firmware upgrade). A problematic byte string might be something like:
b'\xff\x8e\xfe}\xfd\x7f'
which has a length of "6" but element 5 can't be reached (index out of range). However if I read each byte in individually, there is no problem. The same byte string in Python 2.7.6 is handled correctly. To my slightly newbish eye it looks like the '}' may be causing an issue with the indexing function in the byte string?
I will roll back to a previously uPy version and see if it fixes itself.
Would be interested in any helpful thoughts and hope this helps someone else!
I've also been communicating with the 3-axis L3GD20 unit. The I2C interface has been working like a charm!
Initially I was pulling 6 bytes out (3 axis, higher and lower bytes) from the device.
a = [0]*6
for i in range(0,6):
a = i2c.mem_read(1,device,subaddress+i)
But a much better a less ugly way is:
a = i2c.mem_read(6,device,subaddress) # read in a single call
HOWEVER
As a kickstarter backer I was using the firmware which came installed (sorry didn't note the firmware number...). I wondered if the math.asin function had been added in the most recent firmware so I installed pybv10-2014-08-09-v1.2-84-g590b2ab.dfu. Unfortunately the I2C routine now seemed to be causing me problems, but only when I read multiple bytes in one block and then only *sometimes*.
It turned out cases like this (below) now cause a problem (where they didn't previously before the firmware upgrade). A problematic byte string might be something like:
b'\xff\x8e\xfe}\xfd\x7f'
which has a length of "6" but element 5 can't be reached (index out of range). However if I read each byte in individually, there is no problem. The same byte string in Python 2.7.6 is handled correctly. To my slightly newbish eye it looks like the '}' may be causing an issue with the indexing function in the byte string?
I will roll back to a previously uPy version and see if it fixes itself.
Would be interested in any helpful thoughts and hope this helps someone else!
Re: I2C Working
I'd guess that this has something to do with Unicode support and someplace using chars where it should be using bytes.
-
- Posts: 288
- Joined: Sun May 04, 2014 8:54 am
Re: I2C Working
I see this behavior all the time, some bytes get print as their ASCII equivalents.
I use struct.unpack to get ints from those bytes and it doesn't care about the chars, returns correct numbers nevertheless. So you'd read 2 bytes at once and then unpack it.
i.E.
ax, ay and az are now integers, made from two bytes.
the '<h' - part defines type. < or > is little or big endian, h is singned and H is unsigned int.
I use struct.unpack to get ints from those bytes and it doesn't care about the chars, returns correct numbers nevertheless. So you'd read 2 bytes at once and then unpack it.
i.E.
Code: Select all
ax = struct.unpack('<h',i2c.mem_read(2,device,subaddress))[0]
ay = struct.unpack('<h',i2c.mem_read(2,device,subaddress+2))[0]
az = struct.unpack('<h',i2c.mem_read(2,device,subaddress+4))[0]
the '<h' - part defines type. < or > is little or big endian, h is singned and H is unsigned int.
Re: I2C Working
I filed the following issue: https://github.com/micropython/micropython/issues/795
Re: I2C Working
This bug was fixed in git.
Awesome MicroPython list
Pycopy - A better MicroPython https://github.com/pfalcon/micropython
MicroPython standard library for all ports and forks - https://github.com/pfalcon/micropython-lib
More up to date docs - http://pycopy.readthedocs.io/
Pycopy - A better MicroPython https://github.com/pfalcon/micropython
MicroPython standard library for all ports and forks - https://github.com/pfalcon/micropython-lib
More up to date docs - http://pycopy.readthedocs.io/
Re: I2C Working
I have some issues making the I2C work, bassically i get an Oserror: 12 and with another board an oserror: 5 when trying to do I2C comunication with mem_read. iic.scan() delivers [] and hangs up on the other (custom) board after i initialized I2c twice.
Does anyone has an idea? Would be really helpfull.
Does anyone has an idea? Would be really helpfull.