The Perl Toolchain Summit needs more sponsors. If your company depends on Perl, please support this very important event.


<HTML>
<head>
 <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
 <title>HiPi::Interface::MCP23S17</title></head>

<BODY TOPMARGIN=4 BGCOLOR=#FFFFFF TEXT=#000000 VLINK=#0000CC LINK=#0000CC ALINK=#0000CC>
<FONT FACE="Arial, Lucida, Helvetica" >

<TABLE WIDTH="100%" ALIGN=CENTER CELLPADDING=1 CELLSPACING=0>
<TR>
<TD WIDTH="100%" ALIGN=CENTER>


<A HREF="contents.htm"><img align=center src="home.png" BORDER=0 ALT="Contents"></A>


<A HREF="mod_interface.htm"><img align=center src="up.png" BORDER=0 ALT="Up"></A>

<A HREF="mod_interface_mcp23017.htm"><img align=center src="back.png" BORDER=0 ALT="Previous"></A>

<A HREF="mod_interface_mcp49xx.htm"><img align=center src="forward.png" BORDER=0 ALT="Next"></A>
</TD>
</TR>
<TR>
<TD COLSPAN=2 HEIGHT=2 BGCOLOR="#C0C0C0">
</TD>
</TR>
</TABLE>

<H2>HiPi::Interface::MCP23S17</H2><p>This module provides an interface to the popular MCP23S17 GPIO extender with SPI interface.</p>
<p>It uses <A HREF="mod_device_spi.htm">HiPi::Device::SPI</A> as a backend</p>
<p>An interface is also provided for the <A HREF="mod_interface_mcp23017.htm">MCP23017 I2C version</A> of this extender</p>

<h2>Object Constructor and Methods</h2>
<pre>
The module exports the following constants using tag mcp23017

    use HiPi::Interface::MCP23S17 qw( :mcp23S17 );
    
    # exports constants

    # for bit positions in the IOCON register byte
    MCP23S17_BANK
    MCP23S17_MIRROR
    MCP23S17_SEQOP
    MCP23S17_DISSLW
    MCP23S17_HAEN
    MCP23S17_ODR
    MCP23S17_INTPOL
    
    # for defining pin direction in the IODIRA/IODIRB registers
    MCP23S17_INPUT
    MCP23S17_OUTPUT

    # if you like constants for pin levels
    MCP23S17_HIGH
    MCP23S17_LOW
 
Note that you can also export tag mcp23017 with all the above tags renamed
e.g MCP23017_BANK == MCP23S17_BANK

The i2c version of this extender provides identical methods.
 </pre> 
<h5>my $ext = HiPi::Interface::MCP23S17->new( %params );</h5>
<pre>    Returns a new instance of the HiPi::Interface::MCP23S17 class.

    Optional key => values pairs in %params and their defaults

    devicename  => '/dev/spidev0.0',
    
    address     => 0,

    Example overriding defaults
    
    my $ext = HiPi::Interface::MCP23S17->new(
        devicename => '/dev/spidev0.1',
        address    => 7,
    );
    
    The address corresponds to the device hardware address as controlled
    by the 3 address pins and the IOCON.HAEN configuration bit on the
    MCP23S17. There are 8 possible hardware addresses from 0 to 7.

    The value is set on the MCP23S17 by the high / low bias of the 3 address
    pins.

    AD2 AD1 AD0   HiPi Address
     0   0   1         0
     0   1   0         2
     ...................
     1   1   1         7

    Note that unless you set the IOCON.HAEN bit, then the device address is
    always the default 0 ( zero ) regardless of the bias on the address pins.
 
</pre>
<h5>my @bits = $ext->read_register_bits( $register, $numbytes );</h5>
<pre>    Read an array of bit values ( 0 or 1 ) from the specified register.
    
    $numbytes is the number of bytes to read - defaults to 1
    You can usefully read 2 bytes if the controller is in
    default sequential mode.
    
    # 1 byte ( 8 bits )
    bits are populated according to bit numbers as described in
    the MCP23017 / MCP23S17 documentation
    $bits[0] is populated from register bit 0 from the first byte
    $bits[7] is populated from register bit 7 from the first byte
    # 2 bytes ( 16 bits )
    $bits[8] is populated from register bit 0 from the second byte

    $register is a string containing the register name.
    Valid values are:

    'IODIRA', 'IPOLA', 'GPINTENA', 'DEFVALA', 'INTCONA',
    'IOCON',  'GPPUA', 'INTFA',    'INTCAPA', 'GPIOA',
    'OLATA',  'IODIRB','IPOLB',    'GPINTENB','DEFVALB', 
    'INTCONB','GPPUB', 'INTFB',    'INTCAPB', 'GPIOB',
    'OLATB'
    
    Examples:
    
    # get the value ( 1 or 0 ) for pin A0
    
    my @bits = $ext->read_register_bits('GPIOA');
    my $a0value = $bits[0];

    # get the value ( 1 or 0 ) for pin B6

    my @bits = $ext->read_register_bits('GPIOB');
    my $b6value = $bits[6];

    # get the values for all 16 pins when registers
    # are sequential
    # i.e. ($ext->read_register_bits('IOCON'))[MCP23017_BANK] == 0;

    my @bits = $ext->read_register_bits('GPIOA', 2);
    
    # $bits[3]  will contain value for pin A3
    # $bits[10] will contain value for pin B2

    # note that you can return all the values from
    # the entire MCP23S17 register assuming
    # default sequential read mode with

    my @bits = $ext->read_register_bits('IODIRA', 22 );

    # which values are in which bits will depend
    # on the current IOCON.BANK value
    # i.e. ($ext->read_register_bits('IOCON'))[MCP23017_BANK]
    # consult the MCP23S17 data sheet</pre>
    
<h5>$ext->write_register_bits( $register, @bits );</h5>
<pre>    Write an array of bit values ( 0 or 1 ) to the specified register.
    $bits[0] is written to register bit 0
    $bits[7] is written to register bit 7
    
    You can usefully write 8 or 16 bits if the controller is in
    default sequential mode.

    @bits can contain between 1 x 8 and 22 x 8 values
    but writing the correct values for 22 * 8 bits 
    at once seems an unlikely thing to want to do.
    
    $register is a string containing the register name.
    Valid values are:

    'IODIRA', 'IPOLA', 'GPINTENA', 'DEFVALA', 'INTCONA',
    'IOCON',  'GPPUA', 'INTFA',    'INTCAPA', 'GPIOA',
    'OLATA',  'IODIRB','IPOLB',    'GPINTENB','DEFVALB', 
    'INTCONB','GPPUB', 'INTFB',    'INTCAPB', 'GPIOB',
    'OLATB'

    Examples :

    # starting in default power on mode, set pin B3 as an
    # output and set its value high.
    # note that when writing single values, each operation
    # is essentially a read / write
    
    # first set B3 as output
    my @bits = $ext->read_register_bits( 'IODIRB' );
 
    $bits[3] = 0; # the module provides the exported
                  # constants MCP23S17_OUTPUT and MCP23S17_INPUT
                  # which are very useful if you find using
                  # 0 to define an output pin and 1 to
                  # define an input pin confusing

    $ext->write_register_bits( 'IODIRB', @bits );

    # then set its value high
    @bits = $ext->read_register_bits( 'GPIOB' );
    $bits[3] = MCP23S17_HIGH;
    $ext->write_register_bits( 'OLATB', @bits );

 
    # switch mode to IOCON.BANK=1 - segregated registers
    my @bits = $ext->read_register_bits( 'IOCON' );
    $bits[MCP23S17_BANK] = 1;
    $ext->write_register_bits( 'IOCON', @bits );

    # ensure A5 is an input and apply pull up resistor
    my @bits = $ext->read_register_bits( 'IODIRA' );
    $bits[5] = MCP23S17_INPUT;
    $ext->write_register_bits( 'IODIRA', @bits );
    @bits = $ext->read_register_bits( 'GPPUA' );
    $bits[5] = 1;
    $ext->write_register_bits( 'GPPUA', @bits );</pre>
<h5>my @bytes = $ext->read_register_bytes( $register, $numbytes );</h5>
<pre>    Read an array of bytes starting at the specified register.
    $numbytes is the number of bytes to read - defaults to 1

    $register is a string containing the register name.
    Valid values are:

    'IODIRA', 'IPOLA', 'GPINTENA', 'DEFVALA', 'INTCONA',
    'IOCON',  'GPPUA', 'INTFA',    'INTCAPA', 'GPIOA',
    'OLATA',  'IODIRB','IPOLB',    'GPINTENB','DEFVALB', 
    'INTCONB','GPPUB', 'INTFB',    'INTCAPB', 'GPIOB',
    'OLATB'
    
    It is often more convenient to use read_register_bits
    which calls read_register_bytes internally and separates
    the returned values into ordered bit values.
    Calling read_register_bytes may be quicker if your
    handling of the return values is more efficient than
    read_register_bits.</pre>
<h5>$ext->write_register_bytes( $register, @bytes );</h5>
<pre>    Write an array of  1 or more bytes starting at the 
    specified register.
    
    $register is a string containing the register name.
    Valid values are:

    'IODIRA', 'IPOLA', 'GPINTENA', 'DEFVALA', 'INTCONA',
    'IOCON',  'GPPUA', 'INTFA',    'INTCAPA', 'GPIOA',
    'OLATA',  'IODIRB','IPOLB',    'GPINTENB','DEFVALB', 
    'INTCONB','GPPUB', 'INTFB',    'INTCAPB', 'GPIOB',
    'OLATB'

    It is often more convenient to use write_register_bits
    which calls write_register_bytes internally.
    Calling write_register_bytes may be quicker if your
    creating of the byte values is more efficient than
    write_register_bits.
</pre>
<h2>Configuration Methods</h2>
<h5>$ext->iocon_bank( $bitval );</h5>
<pre>    A convenience method to set and get the BANK
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_mirror( $bitval );</h5>
<pre>    A convenience method to set and get the MIRROR
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_seqop( $bitval );</h5>
<pre>    A convenience method to set and get the SEQOP
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_disslw( $bitval );</h5>
<pre>    A convenience method to set and get the DISSLW
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_haen( $bitval );</h5>
<pre>    A convenience method to set and get the HAEN
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_odr( $bitval );</h5>
<pre>    A convenience method to set and get the ODR
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h5>$ext->iocon_intpol( $bitval );</h5>
<pre>    A convenience method to set and get the INTPOL
    value from the IOCON register.
    If the optional $bitval is provided ( 0 or 1 ) the 
    IOCON register bit is set to that value.
    The method returns the value of the IOCON bit.
</pre>

<h2>Pin Methods</h2>

The pin methods provide convenient access to the register values for individual pins. Pins are described by string constants. You can export the string constants and use those, or use the string values directly in your code. To export pin constants:<pre>
    use HiPi::Interface::MCP23S17 qw( :mcppin );
    
    # exports pin description constants

    MCP_PIN_A0     = 'A0'
    MCP_PIN_A1     = 'A1'
    MCP_PIN_A2     = 'A2'
    MCP_PIN_A3     = 'A3'
    MCP_PIN_A4     = 'A4'
    MCP_PIN_A5     = 'A5'
    MCP_PIN_A6     = 'A6'
    MCP_PIN_A7     = 'A7'
    MCP_PIN_B1     = 'B0'
    MCP_PIN_B2     = 'B1'
    MCP_PIN_B3     = 'B2'
    MCP_PIN_B4     = 'B3'
    MCP_PIN_B5     = 'B4'
    MCP_PIN_B6     = 'B5'
    MCP_PIN_B7     = 'B6'
    MCP_PIN_B8     = 'B7'

    # then
    my $val = $mcp->pin_value( MCP_PIN_A5 );
    # or
    my $val = $mcp->pin_value( 'A5' );
</pre>

<h5>$mcp->pin_value( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the GPIO register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the OLAT register.
    The constants MCP23S17_HIGH and MCP23S17_LOW ( 1 and 0 ) may be used
    for the $bitval if preferred.
</pre>

<h5>$mcp->pin_mode( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the IODIR register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the IODIR register.
    The constants MCP23S17_INPUT and MCP23S17_OUTPUT ( 1 and 0 ) may be used
    for the $bitval if preferred.
</pre>

<h5>$mcp->pin_pull_up( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the GPPU register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the GPPU register.
</pre>

<h5>$mcp->pin_polarity( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the IPOL register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the IPOL register.
</pre>

<h5>$mcp->pin_interrupt_enable( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the GPINTEN register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the GPINTEN register.
</pre>

<h5>$mcp->pin_interrupt_default( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the DEFVAL register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the DEFVAL register.
</pre>

<h5>$mcp->pin_interrupt_control( $pinname, $bitval );</h5>
<pre>    Read the value of the pin named in $pinname from the INTCON register.
    If the optional $bitval is provided the value will be written to the 
    appropriate bit in the INTCON register.
</pre>

</FONT>
<br>
<p>
<br>
<hr>
<br>
<center>
<A HREF="contents.htm"><img align=center src="home.png" BORDER=0 ALT="Contents"></A>


<A HREF="mod_interface.htm"><img align=center src="up.png" BORDER=0 ALT="Up"></A>

<A HREF="mod_interface_mcp23017.htm"><img align=center src="back.png" BORDER=0 ALT="Previous"></A>

<A HREF="mod_interface_mcp49xx.htm"><img align=center src="forward.png" BORDER=0 ALT="Next"></A>
</center>

<HR>
<br>
<center><FONT FACE="Arial, Lucida, Helvetica" size="2" color="#000080">HiPi Modules Copyright &#169; 2013 - 2016 Mark Dootson</font></center>
</BODY></HTML>