Steen Jørgensen / MCP23S17

Dependents:   relaekort_til_motorstyring Nucleo_MCP23S17_Test BSM02 POT_V_1_1

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers MCP23S17.h Source File

MCP23S17.h

00001 /* mbed MCP23S17 Library, for driving the MCP23S17 16-Bit I/O Expander with Serial Interface (SPI)
00002  * Copyright (c) 2015, Created by Steen Joergensen (stjo2809) inspired by Romilly Cocking MCP23S17 library
00003  *
00004  * Permission is hereby granted, free of charge, to any person obtaining a copy
00005  * of this software and associated documentation files (the "Software"), to deal
00006  * in the Software without restriction, including without limitation the rights
00007  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
00008  * copies of the Software, and to permit persons to whom the Software is
00009  * furnished to do so, subject to the following conditions:
00010  *
00011  * The above copyright notice and this permission notice shall be included in
00012  * all copies or substantial portions of the Software.
00013  *
00014  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
00015  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
00016  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
00017  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
00018  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
00019  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
00020  * THE SOFTWARE.
00021  */
00022  
00023 #include "mbed.h"
00024 
00025 #ifndef MBED_MCP23S17_H
00026 #define MBED_MCP23S17_H
00027 
00028 //=============================================================================
00029 // All Registers and there Address if BANK = 0
00030 //=============================================================================
00031 
00032 #define IODIRA_ADDR   0x00       // Controls the direction of the data I/O on Port A       
00033 #define IODIRB_ADDR   0x01       // Controls the direction of the data I/O on Port B
00034 #define IPOLA_ADDR    0x02       // Configure the polarity on the corresponding GPIO (Port A)
00035 #define IPOLB_ADDR    0x03       // Configure the polarity on the corresponding GPIO (Port B)
00036 #define GPINTENA_ADDR 0x04       // Controls the interrupt-on change feature for each pin for Port A
00037 #define GPINTENB_ADDR 0x05       // Controls the interrupt-on change feature for each pin for Port B
00038 #define DEFVALA_ADDR  0x06       // The default comparison value if the INTCONA is set to "1" for Port A
00039 #define DEFVALB_ADDR  0x07       // The default comparison value if the INTCONA is set to "1" for Port B
00040 #define INTCONA_ADDR  0x08       // Controls how the associated pin value is compared for the interrupt-on-change feature for Port A
00041 #define INTCONB_ADDR  0x09       // Controls how the associated pin value is compared for the interrupt-on-change feature for Port B
00042 #define IOCON_ADDR    0x0A       // Contains several bits for configuring the device
00043 #define GPPUA_ADDR    0x0C       // Controls the pull-up resistors for the port pins for port A
00044 #define GPPUB_ADDR    0x0D       // Controls the pull-up resistors for the port pins for port B
00045 #define INTFA_ADDR    0x0E       // READ ONLY // reflects the interrupt condition on port A pins of any pin that is enabled for interrupts via the GPINTEN register.
00046 #define INTFB_ADDR    0x0F       // READ ONLY // reflects the interrupt condition on port B pins of any pin that is enabled for interrupts via the GPINTEN register.
00047 #define INTCAPA_ADDR  0x10       // READ ONLY // captures the GPIO port A value at the time the interrupt occurred
00048 #define INTCAPB_ADDR  0x11       // READ ONLY // captures the GPIO port B value at the time the interrupt occurred
00049 #define GPIOA_ADDR    0x12       // Reflects the value on the port A (doing write function it only read input)
00050 #define GPIOB_ADDR    0x13       // Reflects the value on the port B (doing write function it only read input)
00051 #define OLATA_ADDR    0x14       // A write to this register modifies the output latches that modifies the pins configured as outputs for Port A
00052 #define OLATB_ADDR    0x15       // A write to this register modifies the output latches that modifies the pins configured as outputs for Port B
00053 
00054 //=============================================================================
00055 // Declaration of variables & custom #defines
00056 //=============================================================================
00057 
00058 #define INTERRUPT_MIRROR_BIT   0x40
00059 #define INTERRUPT_POLARITY_BIT 0x02
00060 
00061 
00062 //=============================================================================
00063 // Functions Declaration
00064 //=============================================================================
00065 
00066 /** Interface to the MCP23S17 16-Bit I/O Expander with Serial Interface (SPI) 
00067  *
00068  *  Using the driver:
00069  *   - remenber to setup SPI in main routine.
00070  *   - remenber to setup interrupt pin or pins in main routine (if you are using interrupts).
00071  *
00072  *  Defaults in this driver:
00073  *   - as default is hardware adressing "On" and if disable use "0" in hardwareaddress when creating the instance.
00074  *   - as default is interrupt pins "Active High".
00075  *   - as default is INTA is associated with PortA and INTB is associated with PortB. 
00076  *
00077  *  Limitations of using this driver:
00078  *   - can't use Open-Drain output.
00079  *   - can't use Sequential Operation mode bit.
00080  *   - can't use BANK 1 addressing.
00081  *
00082  */
00083 class MCP23S17 {
00084 public:
00085     /** Create an instance of the MCP23S17 connected via specfied SPI instance, with the specified address.
00086      *
00087      * @param hardwareaddress The SPI hardware address 0-7 for this MCP23S17.
00088      * @param spi The mbed SPI instance (make in main routine)
00089      * @param nCs The SPI chip select pin.
00090      * @param nReset The Hardware reset pin.
00091      */
00092     MCP23S17(int hardwareaddress, SPI& spi, PinName nCs, PinName nReset);
00093     
00094     /** Create an instance of the MCP23S17 connected via specfied SPI instance, with the specified address, and Global reset only.
00095      *
00096      * @param hardwareaddress The SPI hardware address 0-7 for this MCP23S17.
00097      * @param spi The mbed SPI instance (make in main routine)
00098      * @param nCs The SPI chip select pin.
00099      */
00100     MCP23S17(int hardwareaddress, SPI& spi, PinName nCs);
00101     
00102 
00103     /** Read an Register address.
00104      *
00105      * @param reg_address The selected register to read from.
00106      * @return The 8 bits read, but if GPIO register only the value of the inputs (outputs is read as "0").
00107      */
00108     char read(char reg_address);
00109 
00110     /** Write to Register address.
00111      *
00112      * @param reg_adress The selected register to write to.
00113      * @param data The 8 bits to write to the register, but if GPIO only the output will change.
00114      */
00115     void write(char reg_address, char data);
00116     
00117     /** Write to Bit in a register.
00118      *
00119      * @param reg_adress The selected register to write to.
00120      * @param bit The bit with to write in, values from 1 to 8 
00121      * @param high_low The value to write the bit True = '1' and False = '0'.
00122      */
00123     void bit(char reg_address, int bitnumber, bool high_low);
00124 
00125     /** Resetting the MCP23S17.
00126      *
00127      * Reset has to be pull down for min. 1uS to insure correct reset.
00128      * This function pull down the reset pin for 5uS.
00129      */
00130     void reset();
00131     
00132     /** Read IODIRA.
00133      *
00134      * I/O DIRECTION REGISTER 
00135      * Controls the direction of the data I/O.
00136      *
00137      * @return The 8 bits read.
00138      */
00139     char iodira();
00140 
00141      /** Write to IODIRA.
00142      *
00143      * I/O DIRECTION REGISTER 
00144      * Controls the direction of the data I/O.
00145      *
00146      * @param data The 8 bits to write to IODIRA register.
00147      */
00148     void iodira(char data);
00149    
00150     /** Read IODIRB.
00151      *
00152      * I/O DIRECTION REGISTER 
00153      * Controls the direction of the data I/O.
00154      *
00155      * @return The 8 bits read.
00156      */
00157     char iodirb();
00158 
00159      /** Write to IODIRB.
00160      *
00161      * I/O DIRECTION REGISTER 
00162      * Controls the direction of the data I/O.
00163      *
00164      * @param data The 8 bits to write to IODIRB register.
00165      */
00166     void iodirb(char data);
00167     
00168     /** Read IPOLA.
00169      *
00170      * INPUT POLARITY REGISTER
00171      * This register allows the user to configure the polarity on the corresponding GPIO port bits.
00172      *
00173      * @return The 8 bits read.
00174      */
00175     char ipola();
00176 
00177      /** Write to IPOLA.
00178      *
00179      * INPUT POLARITY REGISTER
00180      * This register allows the user to configure the polarity on the corresponding GPIO port bits.
00181      *
00182      * @param data The 8 bits to write to IPOLA register.
00183      */
00184     void ipola(char data);    
00185     
00186     /** Read IPOLB.
00187      *
00188      * INPUT POLARITY REGISTER
00189      * This register allows the user to configure the polarity on the corresponding GPIO port bits.
00190      *
00191      * @return The 8 bits read.
00192      */
00193     char ipolb();
00194 
00195      /** Write to IPOLB.
00196      *
00197      * INPUT POLARITY REGISTER
00198      * This register allows the user to configure the polarity on the corresponding GPIO port bits.
00199      *
00200      * @param data The 8 bits to write to IPOLB register.
00201      */
00202     void ipolb(char data);
00203     
00204     /** Read GPINTENA.
00205      *
00206      * INTERRUPT-ON-CHANGE CONTROL REGISTER
00207      * The GPINTEN register controls the interrupt-onchange feature for each pin.
00208      *
00209      * @return The 8 bits read.
00210      */
00211     char gpintena();
00212 
00213      /** Write to GPINTENA.
00214      *
00215      * INTERRUPT-ON-CHANGE CONTROL REGISTER
00216      * The GPINTEN register controls the interrupt-onchange feature for each pin.
00217      *
00218      * @param data The 8 bits to write to GPINTENA register.
00219      */
00220     void gpintena(char data);
00221 
00222      /** Read GPINTENB.
00223      *
00224      * INTERRUPT-ON-CHANGE CONTROL REGISTER
00225      * The GPINTEN register controls the interrupt-onchange feature for each pin.
00226      *
00227      * @return The 8 bits read.
00228      */
00229     char gpintenb();
00230 
00231      /** Write to GPINTENB.
00232      *
00233      * INTERRUPT-ON-CHANGE CONTROL REGISTER
00234      * The GPINTEN register controls the interrupt-onchange feature for each pin.
00235      *
00236      * @param data The 8 bits to write to GPINTENB register.
00237      */
00238     void gpintenb(char data);
00239     
00240     /** Read DEFVALA.
00241      *
00242      * DEFAULT COMPARE REGISTER FOR INTERRUPT-ON-CHANGE
00243      * The default comparison value is configured in the DEFVAL register, If enabled (via GPINTEN and INTCON).
00244      *
00245      * @return The 8 bits read.
00246      */
00247     char defvala();
00248 
00249      /** Write to DEFVALA.
00250      *
00251      * DEFAULT COMPARE REGISTER FOR INTERRUPT-ON-CHANGE
00252      * The default comparison value is configured in the DEFVAL register, If enabled (via GPINTEN and INTCON).
00253      *
00254      * @param data The 8 bits to write to DEVALA register.
00255      */
00256     void defvala(char data);
00257     
00258     /** Read DEFVALB.
00259      *
00260      * DEFAULT COMPARE REGISTER FOR INTERRUPT-ON-CHANGE
00261      * The default comparison value is configured in the DEFVAL register, If enabled (via GPINTEN and INTCON).
00262      *
00263      * @return The 8 bits read.
00264      */
00265     char defvalb();
00266 
00267      /** Write to DEFVALB.
00268      *
00269      * DEFAULT COMPARE REGISTER FOR INTERRUPT-ON-CHANGE
00270      * The default comparison value is configured in the DEFVAL register, If enabled (via GPINTEN and INTCON).
00271      *
00272      * @param data The 8 bits to write to DEVALB register.
00273      */
00274     void defvalb(char data); 
00275     
00276     /** Read INTCONA.
00277      *
00278      * INTERRUPT CONTROL REGISTER
00279      * The INTCON register controls how the associated pin value is compared for the interrupt-on-change feature.
00280      *
00281      * @return The 8 bits read.
00282      */
00283     char intcona();
00284 
00285      /** Write to INTCONA.
00286      *
00287      * INTERRUPT CONTROL REGISTER
00288      * The INTCON register controls how the associated pin value is compared for the interrupt-on-change feature.
00289      *
00290      * @param data The 8 bits to write to INTCONA register.
00291      */
00292     void intcona(char data);
00293     
00294     /** Read INTCONB.
00295      *
00296      * INTERRUPT CONTROL REGISTER
00297      * The INTCON register controls how the associated pin value is compared for the interrupt-on-change feature.
00298      *
00299      * @return The 8 bits read.
00300      */
00301     char intconb();
00302 
00303      /** Write to INTCONB.
00304      *
00305      * INTERRUPT CONTROL REGISTER
00306      * The INTCON register controls how the associated pin value is compared for the interrupt-on-change feature.
00307      *
00308      * @param data The 8 bits to write to INTCONB register.
00309      */
00310     void intconb(char data);
00311     
00312     /** Read IOCON.
00313      *
00314      * CONFIGURATION REGISTER 
00315      * The IOCON register contains several bits for configuring the device.
00316      *
00317      * @return The 8 bits read.
00318      */
00319     char iocon();
00320 
00321     /** Write to IOCON.
00322      *
00323      * CONFIGURATION REGISTER 
00324      * The IOCON register contains several bits for configuring the device.
00325      *
00326      * @param data The 8 bits to write to IOCON register.
00327      */
00328     void iocon(char data);
00329     
00330      /** Read GPPUA.
00331      *
00332      * PULL-UP RESISTOR CONFIGURATION REGISTER 
00333      * The GPPU register controls the pull-up resistors for the port pins.
00334      *
00335      * @return The 8 bits read.
00336      */
00337     char gppua();
00338 
00339      /** Write to GPPUA.
00340      *
00341      * PULL-UP RESISTOR CONFIGURATION REGISTER 
00342      * The GPPU register controls the pull-up resistors for the port pins.
00343      *
00344      * @param data The 8 bits to write to GPPUA register.
00345      */
00346     void gppua(char data);
00347 
00348      /** Read GPPUB.
00349      *
00350      * PULL-UP RESISTOR CONFIGURATION REGISTER 
00351      * The GPPU register controls the pull-up resistors for the port pins.
00352      *
00353      * @return The 8 bits read.
00354      */
00355     char gppub();
00356 
00357      /** Write to GPPUB.
00358      *
00359      * PULL-UP RESISTOR CONFIGURATION REGISTER 
00360      * The GPPU register controls the pull-up resistors for the port pins.
00361      *
00362      * @param data The 8 bits to write to GPPUB register.
00363      */
00364     void gppub(char data);
00365 
00366      /** Read INTFA.
00367      *
00368      * INTERRUPT FLAG REGISTER - READ ONLY
00369      * The INTF register reflects the interrupt condition on the port pins of any pin that is enabled for interrupts via the GPINTEN register.
00370      *
00371      * @return The 8 bits read.
00372      */
00373     char intfa();
00374     
00375     /** Read INTFB.
00376      *
00377      * INTERRUPT FLAG REGISTER - READ ONLY
00378      * The INTF register reflects the interrupt condition on the port pins of any pin that is enabled for interrupts via the GPINTEN register.
00379      *
00380      * @return The 8 bits read.
00381      */
00382     char intfb();
00383     
00384     /** Read INTCAPA.
00385      *
00386      * INTERRUPT CAPTURE REGISTER - READ ONLY
00387      * The INTCAP register captures the GPIO port value at the time the interrupt occurred. The register is ‘read only’ and is updated only when an interrupt occurs.
00388      *
00389      * @return The 8 bits read.
00390      */
00391     char intcapa();
00392     
00393     /** Read INTCAPB.
00394      *
00395      * INTERRUPT CAPTURE REGISTER - READ ONLY
00396      * The INTCAP register captures the GPIO port value at the time the interrupt occurred. The register is ‘read only’ and is updated only when an interrupt occurs.
00397      *
00398      * @return The 8 bits read.
00399      */
00400     char intcapb();      
00401          
00402      /** Read GPIOA.
00403      *
00404      * PORT REGISTER
00405      * The GPIO register reflects the value on the port. Reading from this register reads the port. Writing to this register modifies the Output Latch (OLAT) register.
00406      *
00407      * @return The 8 bits read.
00408      */
00409     char gpioa();
00410 
00411      /** Write to GPIOA.
00412      *
00413      * PORT REGISTER
00414      * The GPIO register reflects the value on the port. Reading from this register reads the port. Writing to this register modifies the Output Latch (OLAT) register.
00415      *
00416      * @param data The 8 bits to write to GPIOA register.
00417      */
00418     void gpioa(char data);
00419     
00420     /** Read GPIOB.
00421      *
00422      * PORT REGISTER
00423      * The GPIO register reflects the value on the port. Reading from this register reads the port. Writing to this register modifies the Output Latch (OLAT) register.
00424      *
00425      * @return The 8 bits read.
00426      */
00427     char gpiob();
00428 
00429      /** Write to GPIOB.
00430      *
00431      * PORT REGISTER
00432      * The GPIO register reflects the value on the port. Reading from this register reads the port. Writing to this register modifies the Output Latch (OLAT) register.
00433      *
00434      * @param data The 8 bits to write to GPIOB register.
00435      */
00436     void gpiob(char data);
00437     
00438      /** Read OLATA.
00439      *
00440      * OUTPUT LATCH REGISTER
00441      * The OLAT register provides access to the output latches. A read from this register results in a read of the OLAT and not the port itself. A write to this register
00442      * modifies the output latches that modifies the pins configured as outputs.
00443      *
00444      * @return The 8 bits read.
00445      */
00446     char olata();
00447 
00448      /** Write to OLATA.
00449      *
00450      * OUTPUT LATCH REGISTER
00451      * The OLAT register provides access to the output latches. A read from this register results in a read of the OLAT and not the port itself. A write to this register
00452      * modifies the output latches that modifies the pins configured as outputs.
00453      *
00454      * @param data The 8 bits to write to OLATA register.
00455      */
00456     void olata(char data);
00457     
00458     /** Read OLATB.
00459      *
00460      * OUTPUT LATCH REGISTER
00461      * The OLAT register provides access to the output latches. A read from this register results in a read of the OLAT and not the port itself. A write to this register
00462      * modifies the output latches that modifies the pins configured as outputs.
00463      *
00464      * @return The 8 bits read.
00465      */
00466     char olatb();
00467 
00468      /** Write to OLATB.
00469      *
00470      * OUTPUT LATCH REGISTER
00471      * The OLAT register provides access to the output latches. A read from this register results in a read of the OLAT and not the port itself. A write to this register
00472      * modifies the output latches that modifies the pins configured as outputs.
00473      *
00474      * @param data The 8 bits to write to OLATB register.
00475      */
00476     void olatb(char data);
00477     
00478      /** Write to IOCON.MIRROR
00479      *
00480      * IOCON REGISTER - INTERRUPT MIRROR BIT
00481      * 1 = The INT pins are internally connected
00482      * 0 = The INT pins are not connected. INTA is associated with PortA and INTB is associated with PortB
00483      *
00484      * @param mirror write true ('1') or false ('0').
00485      */
00486     void intmirror(bool mirror);
00487     
00488      /** Write to IOCON.INTPOL
00489      *
00490      * IOCON REGISTER - INTERRUPT POLARITY BIT
00491      * This bit sets the polarity of the INT output pin.
00492      * 1 = Active-high.
00493      * 0 = Active-low.
00494      *
00495      * @param polarity write true ('1') or false ('0').
00496      */
00497     void intpol(bool polarity);
00498 
00499 private:
00500     int _hardwareaddress;
00501     SPI& _spi;
00502     DigitalOut _nCs;
00503     DigitalOut _nReset;
00504     char _writeopcode;
00505     char _readopcode;
00506     void _initialization();
00507     void _make_opcode(int _hardwareaddress);
00508     char _read(char address);                          
00509     void _write(char address, char data);             
00510 
00511 };
00512 
00513 #endif