src/adxl345.c
changeset 11 a383e22204f2
equal deleted inserted replaced
10:d485c5b3ab4d 11:a383e22204f2
       
     1 #include "adxl345.h"
       
     2 
       
     3 #include "spi.h"
       
     4 
       
     5 #include <util/delay.h>
       
     6 
       
     7 /*
       
     8  * SPI format
       
     9  */
       
    10 enum adxl345_header_bits {
       
    11     ADXL345_READ        = 0b10000000,
       
    12     ADXL345_WRITE       = 0b00000000,
       
    13 
       
    14     ADXL345_MULTI       = 0b01000000,
       
    15 };
       
    16 
       
    17 enum adxl345_reg {
       
    18     ADXL345_DEVID       = 0x00,
       
    19 
       
    20     ADXL345_POWER_CTL   = 0x2D,
       
    21 
       
    22     ADXL345_DATA_FORMAT = 0x31,
       
    23     ADXL345_DATAX0      = 0x32,
       
    24     ADXL345_DATAX1      = 0x33,
       
    25     ADXL345_DATAY0      = 0x34,
       
    26     ADXL345_DATAY1      = 0x35,
       
    27     ADXL345_DATAZ0      = 0x36,
       
    28     ADXL345_DATAZ1      = 0x37,
       
    29 };
       
    30 
       
    31 enum adxl345_power_ctl {
       
    32     ADXL345_POWER_CTL_LINK          = 0b00100000,
       
    33     ADXL345_POWER_CTL_AUTO_SLEEP    = 0b00010000,
       
    34     ADXL345_POWER_CTL_MEASURE       = 0b00001000,
       
    35     ADXL345_POWER_CTL_SLEEP         = 0b00000100,
       
    36     ADXL345_POWER_CTL_WAKEUP        = 0b00000011,
       
    37 };
       
    38 
       
    39 enum adxl345_power_ctl_wakeup {
       
    40     ADXL345_POWER_CTL_WAKEUP_8      = 0b00000011,
       
    41     ADXL345_POWER_CTL_WAKEUP_4      = 0b00000001,
       
    42     ADXL345_POWER_CTL_WAKEUP_2      = 0b00000010,
       
    43     ADXL345_POWER_CTL_WAKEUP_1      = 0b00000000,
       
    44 };
       
    45 
       
    46 enum adxl345_data_format {
       
    47     ADXL345_DATA_FORMAT_SELF_TEST   = 0b10000000,
       
    48     ADXL345_DATA_FORMAT_SPI         = 0b01000000,
       
    49     ADXL345_DATA_FORMAT_INT_INVERT  = 0b00100000,
       
    50     ADXL345_DATA_FORMAT_FULL_RES    = 0b00001000,
       
    51     ADXL345_DATA_FORMAT_JUSTIFY     = 0b00000100,
       
    52     ADXL345_DATA_FORMAT_RANGE       = 0b00000011,
       
    53 };
       
    54 
       
    55 enum adxl345_data_format_range {
       
    56     ADXL345_DATA_FORMAT_RANGE_2G    = 0b00000000,
       
    57     ADXL345_DATA_FORMAT_RANGE_4G    = 0b00000001,
       
    58     ADXL345_DATA_FORMAT_RANGE_8G    = 0b00000010,
       
    59     ADXL345_DATA_FORMAT_RANGE_16G   = 0b00000011,
       
    60 };
       
    61 
       
    62 #define ADXL345_DDR DDRB
       
    63 #define ADXL345_PORT PORTB
       
    64 #define ADXL345_CS PORTB2
       
    65 
       
    66 void adxl345_init ()
       
    67 {
       
    68     // set CS pin
       
    69     sbi(&ADXL345_DDR,    ADXL345_CS);   // out
       
    70     sbi(&ADXL345_PORT,   ADXL345_CS);   // high (off)
       
    71 }
       
    72 
       
    73 static inline void adxl345_start ()
       
    74 {
       
    75     cbi(&ADXL345_PORT,   ADXL345_CS);    // low (on)
       
    76     _delay_us(1);
       
    77 }
       
    78 
       
    79 static inline void adxl345_stop ()
       
    80 {
       
    81     sbi(&ADXL345_PORT,   ADXL345_CS);    // high (off)
       
    82     _delay_us(100);
       
    83 }
       
    84 
       
    85 static void adxl345_write (enum adxl345_reg reg, byte value)
       
    86 {
       
    87     adxl345_start();
       
    88 
       
    89     spi_readwrite(ADXL345_WRITE | reg);
       
    90     spi_readwrite(value);
       
    91 
       
    92     adxl345_stop();
       
    93 }
       
    94 
       
    95 static byte adxl345_read (enum adxl345_reg reg)
       
    96 {
       
    97     byte value;
       
    98 
       
    99     adxl345_start();
       
   100 
       
   101     spi_readwrite(ADXL345_READ | reg);
       
   102     value = spi_readwrite(0);
       
   103 
       
   104     adxl345_stop();
       
   105 
       
   106     return value;
       
   107 }
       
   108 
       
   109 static int8_t adxl345_read_s8 (enum adxl345_reg reg)
       
   110 {
       
   111     int8_t value = 0;
       
   112 
       
   113     adxl345_start();
       
   114 
       
   115     spi_readwrite(ADXL345_READ | ADXL345_MULTI | reg);
       
   116     value = spi_readwrite(0);
       
   117 
       
   118     adxl345_stop();
       
   119 
       
   120     return value;
       
   121 }
       
   122 
       
   123 static int16_t adxl345_read_s16 (enum adxl345_reg reg)
       
   124 {
       
   125     char v0, v1;
       
   126 
       
   127     adxl345_start();
       
   128 
       
   129     spi_readwrite(ADXL345_READ | ADXL345_MULTI | reg);
       
   130     v0 = spi_readwrite(0);
       
   131     v1 = spi_readwrite(0);
       
   132     adxl345_stop();
       
   133 
       
   134     return ((int) v1 << 8) | (int) v0;
       
   135 }
       
   136 
       
   137 byte adxl345_read_devid ()
       
   138 {
       
   139     return adxl345_read(ADXL345_DEVID);
       
   140 }
       
   141 
       
   142 void adxl345_setup ()
       
   143 {
       
   144     adxl345_write(ADXL345_POWER_CTL,
       
   145             // enable measrurement mode
       
   146             ADXL345_POWER_CTL_MEASURE
       
   147     );
       
   148 
       
   149     /*
       
   150     adxl345_write(ADXL345_DATA_FORMAT,
       
   151             // self-test
       
   152             ADXL345_DATA_FORMAT_SELF_TEST
       
   153     );
       
   154     */
       
   155 }
       
   156 
       
   157 int16_t adxl345_read_x ()
       
   158 {
       
   159     return adxl345_read_s16(ADXL345_DATAX0);
       
   160 }
       
   161 
       
   162 int16_t adxl345_read_y ()
       
   163 {
       
   164     return adxl345_read_s16(ADXL345_DATAY0);
       
   165 }
       
   166 
       
   167 int16_t adxl345_read_z ()
       
   168 {
       
   169     return adxl345_read_s16(ADXL345_DATAZ0);
       
   170 }