Hi guys,

My accelerometer is connected to spidev2.0 (pins 1, 3, 28, 29, 30, 31). 
Overlays are loaded correctly, HDMI is turned off, ports are tested using 
Molloy's spidev_test.c and to this point things are good.I have a problem 
with reading the data from accelerometer ADXL345 via SPI port using Python 
code I found on http://www.havnemark.dk/?p=148  
<http://www.havnemark.dk/?p=148>*('Read the ADXL345 accelerometer with 
Raspberry Pi, using SPI bus'). *Main problem is that I don't know how to 
use spidev Python library and I am not sure how SPI communication goes, 
although I am aware of the SPI principle thats says "if you want to send 
the data to read the data". It would be much easier for me if you can 
explain me what and how to send and how to read data.


I successfully connected sensor via I2C port and was able to read the 
accelerations. Everything worked perfectly and I get the idea behind I2C, 
which goes like this (please correct me if I am wrong): Device has its 
address (ADXL345 has 0x53 or 0x1d, it was 0x1d in my case). First, by going 
to address you go to a register which has 64 bytes. In register every byte 
is used for controlling sensor or for storing data that sensor acquires. 
Every one of these bytes has its position from 0x00 to 0x3f, and some 
values are stored in these bytes. For example, device ID is stored in byte 
at position 0x00, and value of device ID is always 0xe5. On the other hand 
at position 0x2d we can turn on or turn off accelerometar by writing a 
desired value to this byte, value of 0x08 will set the accelerometar in 
measurement mode. And then we need to read bytes from position 0x32 to 
position 0x37 to read the accelerations. For every axis (X, Y, Z) value of 
acceleration is stored in 2 bytes (because we have resoultions of 10 or 13 
bits. After reading these bytes we combine values to get voltage and after 
that by using some math we can get accelerations in m/s^2 or g's or 
whatever we like. 

And I know that I must to do similar things when communicating via SPI but 
I don't know how to read or write the register values. So my questions are:

1) How to read the register data using spidev package. How would line of 
code that says "Go to address XxXX and read the value at the position YxYY" 
look like?

2) By using code from question 1 how would line that returns device ID look 
like.

3) How to write the data to the register? How would line of code that says 
"Go to address XxXX and write the value ZxZZ at the position YxYY" look 
like?

4) By using code from question 3 how to set the accelerometer in the 
measurement mode

5) How to combine bytes where the values of accelerations are stored? For 
example if I have 10 bit resolution I would have to combine first byte with 
last two bits of second byte. Then by multiplying the value of combination 
of bytes with 3.3 and then dividing with 1024 I would get a voltage. And 
then by knowing the range of measurement I can translate that in 
acceleration. How to do whole proccess?

Here is the code I used:

#!/usr/bin/python
# -*- coding: utf-8 -*-
# Example on how to read the ADXL345 accelerometer.
# Kim H. Rasmussen, 2014
import time
import spidev

# Setup SPI
spi = spidev.SpiDev()
#spi.mode = 3    <-- Important: Do not do this! Or SPI won't work as intended, 
or even at all.
spi.open(2,0)
spi.mode = 3

spi.max_speed_hz = 3500000

# Read the Device ID (should be xE5)
id = spi.xfer2([128,0])
print 'Device ID (Should be 0xE5):\n'+str(hex(id[1])) + '\n'

# Read the offsets
xoffset = spi.xfer2([30 | 128,0])
yoffset = spi.xfer2([31 | 128,0])
zoffset = spi.xfer2([32 | 128,0])
print 'Offsets: '
print xoffset[1]
print yoffset[1]
print str(zoffset[1]) + "\n\nRead the ADXL345 every half second:"

# Initialize the ADXL345
def initadxl345():
    # Enter power saving state
    spi.xfer2([45, 0])

    # Set data rate to 100 Hz
    spi.xfer2([44, 10])

    # Enable full range (10 bits resolution) and +/- 16g 4 LSB
    spi.xfer2([49, 16])

    # Enable measurement
    spi.xfer2([45, 8])

# Read the ADXL x-y-z axia
def readadxl345():
    rx = spi.xfer2([242,0,0,0,0,0,0])

    # 
    out = [rx[1] | (rx[2] << 8),rx[3] | (rx[4] << 8),rx[5] | (rx[6] << 8)]
    # Format x-axis
    if (out[0] & (1<<16 - 1 )):
        out[0] = out[0] - (1<<16)
    out[0] = out[0] * 0.004 * 9.82
    # Format y-axis
    if (out[1] & (1<<16 - 1 )):
        out[1] = out[1] - (1<<16)
    out[1] = out[1] * 0.004 * 9.82
    # Format z-axis
    if (out[2] & (1<<16 - 1 )):
        out[2] = out[2] - (1<<16)
    out[2] = out[2] * 0.004 * 9.82

    return out

# Initialize the ADXL345 accelerometer
initadxl345()

# Read the ADXL345 every half second
timeout = 0.5
while(1):
    axia = readadxl345()
    # Print the reading
    print axia[0]
    print axia[1]
    print str(axia[2]) + '\n'

    elapsed = time.clock()
    current = 0
    while(current < timeout):
        current = time.clock() - elapsed

Things go wrong from the very beginning: 

# Read the Device ID (should be xE5)
id = spi.xfer2([128,0])
print 'Device ID (Should be 0xE5):\n'+str(hex(id[1])) + '\n'

This line returns me device ID id[1] = 0xf2, and I am confused. Also I don't 
know how this xfer2 works, and why is there 128 (0x80).
By looking at the Arduino libraries for ADXL345 it seems to me like that is the 
address of device and I don't know how was this number obtained.

Also I think that the guy whose code this is made a mistake in function 
initadxl345(). 10 bit is not full resolution of device, it is 13 bit and 13 bit 
resolution is available only in +-16g mode. 

To turn that mode on value in register at the position 0x31 should be bin 
00001011 = dec 11 = hex 0x0b. 

I bet there are also mistakes I am not fully aware of.

Please help me in answering questions above, it would help me a lot.


-- 
For more options, visit http://beagleboard.org/discuss
--- 
You received this message because you are subscribed to the Google Groups 
"BeagleBoard" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/beagleboard/d387ef4a-d9a2-494d-9c59-d589c6037f96%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to