blob: cadbfe80db7fb658e49796fac94773fd6df764f8 [file] [log] [blame]
Deokgyu Yang2c7e86b2020-04-28 10:56:11 +09001/*
2 * piFace.:
3 * Copyright (c) 2012-2016 Gordon Henderson
4 *
5 * This file to interface with the PiFace peripheral device which
6 * has an MCP23S17 GPIO device connected via the SPI bus.
7 ***********************************************************************
8 * This file is part of wiringPi:
9 * https://projects.drogon.net/raspberry-pi/wiringpi/
10 *
11 * wiringPi is free software: you can redistribute it and/or modify
12 * it under the terms of the GNU Lesser General Public License as
13 * published by the Free Software Foundation, either version 3 of the
14 * License, or (at your option) any later version.
15 *
16 * wiringPi is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License for more details.
20 *
21 * You should have received a copy of the GNU Lesser General Public
22 * License along with wiringPi.
23 * If not, see <http://www.gnu.org/licenses/>.
24 ***********************************************************************
25 */
26
27
28#include <stdio.h>
29#include <stdint.h>
30
31#include <wiringPi.h>
32#include <wiringPiSPI.h>
33
34#include "../wiringPi/mcp23x0817.h"
35
36#include "piFace.h"
37
38#define PIFACE_SPEED 4000000
39#define PIFACE_DEVNO 0
40
41
42
43/*
44 * writeByte:
45 * Write a byte to a register on the MCP23S17 on the SPI bus.
46 *********************************************************************************
47 */
48
49static void writeByte (uint8_t reg, uint8_t data)
50{
51 uint8_t spiData [4] ;
52
53 spiData [0] = CMD_WRITE ;
54 spiData [1] = reg ;
55 spiData [2] = data ;
56
57 wiringPiSPIDataRW (PIFACE_DEVNO, spiData, 3) ;
58}
59
60/*
61 * readByte:
62 * Read a byte from a register on the MCP23S17 on the SPI bus.
63 *********************************************************************************
64 */
65
66static uint8_t readByte (uint8_t reg)
67{
68 uint8_t spiData [4] ;
69
70 spiData [0] = CMD_READ ;
71 spiData [1] = reg ;
72
73 wiringPiSPIDataRW (PIFACE_DEVNO, spiData, 3) ;
74
75 return spiData [2] ;
76}
77
78
79/*
80 * myDigitalWrite:
81 * Perform the digitalWrite function on the PiFace board
82 *********************************************************************************
83 */
84
85void myDigitalWrite (struct wiringPiNodeStruct *node, int pin, int value)
86{
87 uint8_t mask, old ;
88
89 pin -= node->pinBase ;
90 mask = 1 << pin ;
91 old = readByte (MCP23x17_GPIOA) ;
92
93 if (value == 0)
94 old &= (~mask) ;
95 else
96 old |= mask ;
97
98 writeByte (MCP23x17_GPIOA, old) ;
99}
100
101
102/*
103 * myDigitalRead:
104 * Perform the digitalRead function on the PiFace board
105 *********************************************************************************
106 */
107
108int myDigitalRead (struct wiringPiNodeStruct *node, int pin)
109{
110 uint8_t mask, reg ;
111
112 mask = 1 << ((pin - node->pinBase) & 7) ;
113
114 if (pin < 8)
115 reg = MCP23x17_GPIOB ; // Input regsiter
116 else
117 reg = MCP23x17_OLATA ; // Output latch regsiter
118
119 if ((readByte (reg) & mask) != 0)
120 return HIGH ;
121 else
122 return LOW ;
123}
124
125
126/*
127 * myPullUpDnControl:
128 * Perform the pullUpDnControl function on the PiFace board
129 *********************************************************************************
130 */
131
132void myPullUpDnControl (struct wiringPiNodeStruct *node, int pin, int pud)
133{
134 uint8_t mask, old ;
135
136 mask = 1 << (pin - node->pinBase) ;
137 old = readByte (MCP23x17_GPPUB) ;
138
139 if (pud == 0)
140 old &= (~mask) ;
141 else
142 old |= mask ;
143
144 writeByte (MCP23x17_GPPUB, old) ;
145}
146
147
148/*
149 * piFaceSetup
150 * Setup the SPI interface and initialise the MCP23S17 chip
151 * We create one node with 16 pins - each if the first 8 pins being read
152 * and write - although the operations actually go to different
153 * hardware ports. The top 8 let you read the state of the output register.
154 *********************************************************************************
155 */
156
157int piFaceSetup (const int pinBase)
158{
159 int x ;
160 struct wiringPiNodeStruct *node ;
161
162 if ((x = wiringPiSPISetup (PIFACE_DEVNO, PIFACE_SPEED)) < 0)
163 return x ;
164
165// Setup the MCP23S17
166
167 writeByte (MCP23x17_IOCON, IOCON_INIT) ;
168 writeByte (MCP23x17_IODIRA, 0x00) ; // Port A -> Outputs
169 writeByte (MCP23x17_IODIRB, 0xFF) ; // Port B -> Inputs
170
171 node = wiringPiNewNode (pinBase, 16) ;
172 node->digitalRead = myDigitalRead ;
173 node->digitalWrite = myDigitalWrite ;
174 node->pullUpDnControl = myPullUpDnControl ;
175
176 return 0 ;
177}