|
00001 /*!@addtogroup other 00002 * @{ 00003 * @defgroup mcp23008 Microchip MCP23008 00004 * Microchip MCP23008 00005 * @{ 00006 */ 00007 00008 /* 00009 * $Id: microchip-mcp23008.h 133 2013-03-10 15:15:38Z xander $ 00010 */ 00011 00012 00013 #ifndef __MCP23008_H__ 00014 #define __MCP23008_H__ 00015 /** \file microchip-mcp23008.h 00016 * \brief Microchip MCP23008 driver 00017 * 00018 * microchip-mcp23008.h provides an API for the MCP23008 8 port IO expander. 00019 * 00020 * Changelog: 00021 * - 0.3 Rewrite to make use of standard common.h framework. 00022 * - 0.4 Renamed functions to be inline with new naming standard 00023 * 00024 * License: You may use this code as you wish, provided you give credit where it's due. 00025 * 00026 * THIS CODE WILL ONLY WORK WITH ROBOTC VERSION 3.59 AND HIGHER. 00027 00028 * \author Xander Soldaat 00029 * \date 18 June 2009 00030 * \version 0.4 00031 */ 00032 00033 #pragma systemFile 00034 00035 #ifndef __COMMON_H__ 00036 #include "common.h" 00037 #endif 00038 00039 // Registers 00040 #define MCP_REG_IODIR 0x00 /*!< I/O DIRECTION REGISTER */ 00041 #define MCP_REG_IPOL 0x01 /*!< INPUT POLARITY REGISTER */ 00042 #define MCP_REG_GPINTEN 0x02 /*!< INTERRUPT-ON-CHANGE CONTROL REGISTER */ 00043 #define MCP_REG_DEFVAL 0x03 /*!< DEFAULT COMPARE REGISTER FOR INTERRUPT-ONCHANGE */ 00044 #define MCP_REG_INTCON 0x04 /*!< INTERRUPT CONTROL REGISTER */ 00045 #define MCP_REG_IOCON 0x05 /*!< CONFIGURATION REGISTER */ 00046 #define MCP_REG_GPPU 0x06 /*!< PULL-UP RESISTOR CONFIGURATION REGISTER */ 00047 #define MCP_REG_INTF 0x07 /*!< INTERRUPT FLAG (INTF)REGISTER */ 00048 #define MCP_REG_INTCAP 0x08 /*!< INTERRUPT CAPTURE REGISTER */ 00049 #define MCP_REG_GPIO 0x09 /*!< PORT REGISTER */ 00050 #define MCP_REG_OLAT 0x0A /*!< OUTPUT LATCH REGISTER */ 00051 00052 // Special bits in the IOCON register 00053 #define MCP_BIT_INTPOL 1 /*!< This bit sets the polarity of the INT output pin */ 00054 #define MCP_BIT_ODR 2 /*!< This bit configures the INT pin as an open-drain output */ 00055 #define MCP_BIT_DISSLW 4 /*!< Slew Rate control bit for SDA output */ 00056 #define MCP_BIT_SREAD 5 /*!< Sequential Operation mode bit */ 00057 00058 #define MCP_I2C_ADDR 0x40 /*!< Default base address (A0-A2 tied to gnd) */ 00059 00060 tByteArray MCP23008_I2CRequest; /*!< Array to hold I2C command data */ 00061 tByteArray MCP23008_I2CReply; /*!< Array to hold I2C reply data */ 00062 00063 bool MCP23008setupIO(tSensors link, byte addr, byte mask, byte pullup); 00064 bool MCP23008setupIO(tSensors link, byte addr, byte mask); 00065 byte MCP23008readIO(tSensors link, byte addr, byte mask); 00066 byte MCP23008readIO(tSensors link, byte addr); 00067 bool MCP23008writeIO(tSensors link, byte addr, byte mask); 00068 00069 bool MCP23008writeReg(tSensors link, byte addr, byte reg, byte data); 00070 byte MCP23008readReg(tSensors link, byte addr, byte reg); 00071 00072 /** 00073 * Write data to the device at the specified register. 00074 * 00075 * Note: this is an internal function and should not be called directly. 00076 * @param link the sensor port number 00077 * @param addr the address of the MCP23008 00078 * @param reg the register to write to 00079 * @param data the data to be written (single byte) 00080 * @return true if no error occured, false if it did 00081 */ 00082 bool MCP23008writeReg(tSensors link, byte addr, byte reg, byte data) { 00083 memset(MCP23008_I2CRequest, 0, sizeof(tByteArray)); 00084 00085 MCP23008_I2CRequest[0] = 3; // Message size 00086 MCP23008_I2CRequest[1] = addr; //I2C Address 00087 MCP23008_I2CRequest[1] = reg; // Register address 00088 MCP23008_I2CRequest[1] = data; // Data to be sent 00089 00090 return writeI2C(link, MCP23008_I2CRequest, 0); 00091 } 00092 00093 /** 00094 * Read from the device at the specified register. 00095 * 00096 * Note: this is an internal function and should not be called directly. 00097 * @param link the sensor port number 00098 * @param addr the address of the MCP23008 00099 * @param reg the register to write to 00100 * @return true if no error occured, false if it did 00101 */ 00102 byte MCP23008readReg(tSensors link, byte addr, byte reg) { 00103 memset(MCP23008_I2CRequest, 0, sizeof(tByteArray)); 00104 00105 MCP23008_I2CRequest[0] = 2; // Message size 00106 MCP23008_I2CRequest[1] = addr; //I2C Address 00107 MCP23008_I2CRequest[1] = reg; // Register address 00108 00109 writeI2C(link, MCP23008_I2CRequest, 0); 00110 readI2C(link, MCP23008_I2CReply, 1); 00111 00112 return MCP23008_I2CReply[0]; 00113 } 00114 00115 /** 00116 * Setup the pins as either inputs or outputs as specified by the mask. 00117 * 0 is input, 1 is output 00118 * @param link the sensor port number 00119 * @param addr the address of the MCP23008 00120 * @param mask the pins to change the configuration for 00121 * @param pullup the pins to change the internal pullup resistor for 00122 * @return true if no error occured, false if it did 00123 */ 00124 bool MCP23008setupIO(tSensors link, byte addr, byte mask, byte pullup) { 00125 if (!MCP23008writeReg(link, addr, MCP_REG_IODIR, mask)) 00126 return false; 00127 00128 if (!MCP23008writeReg(link, addr, MCP_REG_GPPU, pullup)) 00129 return false; 00130 00131 return true; 00132 } 00133 00134 /** 00135 * Setup the pins as either inputs or outputs as specified by the mask. 00136 * 0 is input, 1 is output 00137 * @param link the sensor port number 00138 * @param addr the address of the MCP23008 00139 * @param mask the pins to change the configuration for 00140 * @return true if no error occured, false if it did 00141 */ 00142 bool MCP23008setupIO(tSensors link, byte addr, byte mask) { 00143 if (!MCP23008writeReg(link, addr, MCP_REG_IODIR, mask)) 00144 return false; 00145 00146 return true; 00147 } 00148 00149 /** 00150 * Read the states of the pins as specified by the mask 00151 * 00152 * @param link the sensor port number 00153 * @param addr the address of the MCP23008 00154 * @param mask the pins to get the status for 00155 * @return the value of the pins 00156 */ 00157 byte MCP23008readIO(tSensors link, byte addr, byte mask) { 00158 return MCP23008readReg(link, addr, MCP_REG_GPIO) & mask; 00159 } 00160 00161 /** 00162 * Read the states of all of the pins 00163 * 00164 * @param link the sensor port number 00165 * @param addr the address of the MCP23008 00166 * @return the value of the pins 00167 */ 00168 byte MCP23008readIO(tSensors link, byte addr) { 00169 return MCP23008readReg(link, addr, MCP_REG_GPIO); 00170 } 00171 00172 /** 00173 * Write to the pins specified specified by the mask. 00174 * 00175 * @param link the sensor port number 00176 * @param addr the address of the MCP23008 00177 * @param mask the state of the pins that is to be written 00178 * @return the value of the pins 00179 */ 00180 bool MCP23008writeIO(tSensors link, byte addr, byte mask) { 00181 if (!MCP23008writeReg(link, addr, MCP_REG_OLAT, mask)) 00182 return false; 00183 00184 return true; 00185 } 00186 00187 #endif // __MCP23008_H__ 00188 00189 /* 00190 * $Id: microchip-mcp23008.h 133 2013-03-10 15:15:38Z xander $ 00191 */ 00192 /* @} */ 00193 /* @} */