LEER TAG
Dependents: NFC_HTM_READ EMULAR_TAGS Escribir_tag NFC_HTM_READ-WRITE
PN532_SPI.cpp@1:a549ef8b142a, 2015-04-24 (annotated)
- Committer:
- mauroar211
- Date:
- Fri Apr 24 19:02:44 2015 +0000
- Revision:
- 1:a549ef8b142a
- Parent:
- 0:b805b487fbef
SE RESTAURARON LOS ARCHIVO DE LA LIBRER?A;
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
mauroar211 | 0:b805b487fbef | 1 | |
mauroar211 | 0:b805b487fbef | 2 | #include "PN532_SPI.h" |
mauroar211 | 0:b805b487fbef | 3 | #include "PN532_debug.h" |
mauroar211 | 1:a549ef8b142a | 4 | #include "mbed.h" |
mauroar211 | 0:b805b487fbef | 5 | |
mauroar211 | 0:b805b487fbef | 6 | #define STATUS_READ 2 |
mauroar211 | 0:b805b487fbef | 7 | #define DATA_WRITE 1 |
mauroar211 | 0:b805b487fbef | 8 | #define DATA_READ 3 |
mauroar211 | 0:b805b487fbef | 9 | |
mauroar211 | 0:b805b487fbef | 10 | PN532_SPI::PN532_SPI(SPI &spi, PinName ss) : _ss(ss) |
mauroar211 | 0:b805b487fbef | 11 | { |
mauroar211 | 0:b805b487fbef | 12 | command = 0; |
mauroar211 | 0:b805b487fbef | 13 | _spi = &spi; |
mauroar211 | 0:b805b487fbef | 14 | _spi->format(8, 0); |
mauroar211 | 0:b805b487fbef | 15 | _spi->frequency(2000000); |
mauroar211 | 0:b805b487fbef | 16 | |
mauroar211 | 0:b805b487fbef | 17 | _ss = 1; |
mauroar211 | 1:a549ef8b142a | 18 | }/* |
mauroar211 | 0:b805b487fbef | 19 | PN532_SPI::PN532_SPI(SPI *spi, PinName ss) : _ss(ss) |
mauroar211 | 0:b805b487fbef | 20 | { |
mauroar211 | 0:b805b487fbef | 21 | command = 0; |
mauroar211 | 0:b805b487fbef | 22 | _spi = spi; |
mauroar211 | 0:b805b487fbef | 23 | _spi->format(8, 0); |
mauroar211 | 0:b805b487fbef | 24 | _spi->frequency(2000000); |
mauroar211 | 0:b805b487fbef | 25 | |
mauroar211 | 0:b805b487fbef | 26 | _ss = 1; |
mauroar211 | 1:a549ef8b142a | 27 | }*/ |
mauroar211 | 0:b805b487fbef | 28 | void PN532_SPI::begin() |
mauroar211 | 0:b805b487fbef | 29 | { |
mauroar211 | 0:b805b487fbef | 30 | |
mauroar211 | 0:b805b487fbef | 31 | } |
mauroar211 | 0:b805b487fbef | 32 | |
mauroar211 | 0:b805b487fbef | 33 | void PN532_SPI::wakeup() |
mauroar211 | 0:b805b487fbef | 34 | { |
mauroar211 | 0:b805b487fbef | 35 | _ss = 0; |
mauroar211 | 0:b805b487fbef | 36 | wait_ms(2); |
mauroar211 | 0:b805b487fbef | 37 | _ss = 1; |
mauroar211 | 0:b805b487fbef | 38 | } |
mauroar211 | 0:b805b487fbef | 39 | |
mauroar211 | 0:b805b487fbef | 40 | int8_t PN532_SPI::writeCommand(const uint8_t *header, uint8_t hlen, const uint8_t *body, uint8_t blen) |
mauroar211 | 0:b805b487fbef | 41 | { |
mauroar211 | 0:b805b487fbef | 42 | command = header[0]; |
mauroar211 | 0:b805b487fbef | 43 | writeFrame(header, hlen, body, blen); |
mauroar211 | 0:b805b487fbef | 44 | |
mauroar211 | 0:b805b487fbef | 45 | uint8_t timeout = PN532_ACK_WAIT_TIME; |
mauroar211 | 0:b805b487fbef | 46 | while (!isReady()) { |
mauroar211 | 0:b805b487fbef | 47 | wait_ms(1); |
mauroar211 | 0:b805b487fbef | 48 | timeout--; |
mauroar211 | 0:b805b487fbef | 49 | if (0 == timeout) { |
mauroar211 | 0:b805b487fbef | 50 | DMSG("Time out when waiting for ACK\n"); |
mauroar211 | 0:b805b487fbef | 51 | return -2; |
mauroar211 | 0:b805b487fbef | 52 | } |
mauroar211 | 0:b805b487fbef | 53 | } |
mauroar211 | 0:b805b487fbef | 54 | if (readAckFrame()) { |
mauroar211 | 0:b805b487fbef | 55 | DMSG("Invalid ACK\n"); |
mauroar211 | 0:b805b487fbef | 56 | return PN532_INVALID_ACK; |
mauroar211 | 0:b805b487fbef | 57 | } |
mauroar211 | 0:b805b487fbef | 58 | return 0; |
mauroar211 | 0:b805b487fbef | 59 | } |
mauroar211 | 0:b805b487fbef | 60 | |
mauroar211 | 0:b805b487fbef | 61 | int16_t PN532_SPI::readResponse(uint8_t buf[], uint8_t len, uint16_t timeout) |
mauroar211 | 0:b805b487fbef | 62 | { |
mauroar211 | 0:b805b487fbef | 63 | uint16_t time = 0; |
mauroar211 | 0:b805b487fbef | 64 | while (!isReady()) { |
mauroar211 | 0:b805b487fbef | 65 | wait_ms(1); |
mauroar211 | 0:b805b487fbef | 66 | time++; |
mauroar211 | 0:b805b487fbef | 67 | if (timeout > 0 && time > timeout) { |
mauroar211 | 0:b805b487fbef | 68 | return PN532_TIMEOUT; |
mauroar211 | 0:b805b487fbef | 69 | } |
mauroar211 | 0:b805b487fbef | 70 | } |
mauroar211 | 0:b805b487fbef | 71 | |
mauroar211 | 0:b805b487fbef | 72 | _ss = 0; |
mauroar211 | 0:b805b487fbef | 73 | wait_ms(1); |
mauroar211 | 0:b805b487fbef | 74 | |
mauroar211 | 0:b805b487fbef | 75 | int16_t result; |
mauroar211 | 0:b805b487fbef | 76 | do { |
mauroar211 | 0:b805b487fbef | 77 | write(DATA_READ); |
mauroar211 | 0:b805b487fbef | 78 | |
mauroar211 | 0:b805b487fbef | 79 | if (0x00 != read() || // PREAMBLE |
mauroar211 | 0:b805b487fbef | 80 | 0x00 != read() || // STARTCODE1 |
mauroar211 | 0:b805b487fbef | 81 | 0xFF != read() // STARTCODE2 |
mauroar211 | 0:b805b487fbef | 82 | ) { |
mauroar211 | 0:b805b487fbef | 83 | |
mauroar211 | 0:b805b487fbef | 84 | result = PN532_INVALID_FRAME; |
mauroar211 | 0:b805b487fbef | 85 | break; |
mauroar211 | 0:b805b487fbef | 86 | } |
mauroar211 | 0:b805b487fbef | 87 | |
mauroar211 | 0:b805b487fbef | 88 | uint8_t length = read(); |
mauroar211 | 0:b805b487fbef | 89 | if (0 != (uint8_t)(length + read())) { // checksum of length |
mauroar211 | 0:b805b487fbef | 90 | result = PN532_INVALID_FRAME; |
mauroar211 | 0:b805b487fbef | 91 | break; |
mauroar211 | 0:b805b487fbef | 92 | } |
mauroar211 | 0:b805b487fbef | 93 | |
mauroar211 | 0:b805b487fbef | 94 | uint8_t cmd = command + 1; // response command |
mauroar211 | 0:b805b487fbef | 95 | if (PN532_PN532TOHOST != read() || (cmd) != read()) { |
mauroar211 | 0:b805b487fbef | 96 | result = PN532_INVALID_FRAME; |
mauroar211 | 0:b805b487fbef | 97 | break; |
mauroar211 | 0:b805b487fbef | 98 | } |
mauroar211 | 0:b805b487fbef | 99 | |
mauroar211 | 0:b805b487fbef | 100 | DMSG("read: "); |
mauroar211 | 0:b805b487fbef | 101 | DMSG_HEX(cmd); |
mauroar211 | 0:b805b487fbef | 102 | |
mauroar211 | 0:b805b487fbef | 103 | length -= 2; |
mauroar211 | 0:b805b487fbef | 104 | if (length > len) { |
mauroar211 | 0:b805b487fbef | 105 | for (uint8_t i = 0; i < length; i++) { |
mauroar211 | 0:b805b487fbef | 106 | DMSG_HEX(read()); // dump message |
mauroar211 | 0:b805b487fbef | 107 | } |
mauroar211 | 0:b805b487fbef | 108 | DMSG("\nNot enough space\n"); |
mauroar211 | 0:b805b487fbef | 109 | read(); |
mauroar211 | 0:b805b487fbef | 110 | read(); |
mauroar211 | 0:b805b487fbef | 111 | result = PN532_NO_SPACE; // not enough space |
mauroar211 | 0:b805b487fbef | 112 | break; |
mauroar211 | 0:b805b487fbef | 113 | } |
mauroar211 | 0:b805b487fbef | 114 | |
mauroar211 | 0:b805b487fbef | 115 | uint8_t sum = PN532_PN532TOHOST + cmd; |
mauroar211 | 0:b805b487fbef | 116 | for (uint8_t i = 0; i < length; i++) { |
mauroar211 | 0:b805b487fbef | 117 | buf[i] = read(); |
mauroar211 | 0:b805b487fbef | 118 | sum += buf[i]; |
mauroar211 | 0:b805b487fbef | 119 | |
mauroar211 | 0:b805b487fbef | 120 | DMSG_HEX(buf[i]); |
mauroar211 | 0:b805b487fbef | 121 | } |
mauroar211 | 0:b805b487fbef | 122 | DMSG("\n"); |
mauroar211 | 0:b805b487fbef | 123 | |
mauroar211 | 0:b805b487fbef | 124 | uint8_t checksum = read(); |
mauroar211 | 0:b805b487fbef | 125 | if (0 != (uint8_t)(sum + checksum)) { |
mauroar211 | 0:b805b487fbef | 126 | DMSG("checksum is not ok\n"); |
mauroar211 | 0:b805b487fbef | 127 | result = PN532_INVALID_FRAME; |
mauroar211 | 0:b805b487fbef | 128 | break; |
mauroar211 | 0:b805b487fbef | 129 | } |
mauroar211 | 0:b805b487fbef | 130 | read(); // POSTAMBLE |
mauroar211 | 0:b805b487fbef | 131 | |
mauroar211 | 0:b805b487fbef | 132 | result = length; |
mauroar211 | 0:b805b487fbef | 133 | } while (0); |
mauroar211 | 0:b805b487fbef | 134 | |
mauroar211 | 0:b805b487fbef | 135 | _ss = 1; |
mauroar211 | 0:b805b487fbef | 136 | |
mauroar211 | 0:b805b487fbef | 137 | return result; |
mauroar211 | 0:b805b487fbef | 138 | } |
mauroar211 | 0:b805b487fbef | 139 | |
mauroar211 | 0:b805b487fbef | 140 | bool PN532_SPI::isReady() |
mauroar211 | 0:b805b487fbef | 141 | { |
mauroar211 | 0:b805b487fbef | 142 | _ss = 0; |
mauroar211 | 0:b805b487fbef | 143 | |
mauroar211 | 0:b805b487fbef | 144 | write(STATUS_READ); |
mauroar211 | 0:b805b487fbef | 145 | uint8_t status = read() & 1; |
mauroar211 | 0:b805b487fbef | 146 | _ss = 1; |
mauroar211 | 0:b805b487fbef | 147 | return status; |
mauroar211 | 0:b805b487fbef | 148 | } |
mauroar211 | 0:b805b487fbef | 149 | |
mauroar211 | 0:b805b487fbef | 150 | void PN532_SPI::writeFrame(const uint8_t *header, uint8_t hlen, const uint8_t *body, uint8_t blen) |
mauroar211 | 0:b805b487fbef | 151 | { |
mauroar211 | 0:b805b487fbef | 152 | _ss = 0; |
mauroar211 | 0:b805b487fbef | 153 | wait_ms(2); // wake up PN532 |
mauroar211 | 0:b805b487fbef | 154 | |
mauroar211 | 0:b805b487fbef | 155 | write(DATA_WRITE); |
mauroar211 | 0:b805b487fbef | 156 | write(PN532_PREAMBLE); |
mauroar211 | 0:b805b487fbef | 157 | write(PN532_STARTCODE1); |
mauroar211 | 0:b805b487fbef | 158 | write(PN532_STARTCODE2); |
mauroar211 | 0:b805b487fbef | 159 | |
mauroar211 | 0:b805b487fbef | 160 | uint8_t length = hlen + blen + 1; // length of data field: TFI + DATA |
mauroar211 | 0:b805b487fbef | 161 | write(length); |
mauroar211 | 0:b805b487fbef | 162 | write(~length + 1); // checksum of length |
mauroar211 | 0:b805b487fbef | 163 | |
mauroar211 | 0:b805b487fbef | 164 | write(PN532_HOSTTOPN532); |
mauroar211 | 0:b805b487fbef | 165 | uint8_t sum = PN532_HOSTTOPN532; // sum of TFI + DATA |
mauroar211 | 0:b805b487fbef | 166 | |
mauroar211 | 0:b805b487fbef | 167 | DMSG("write: "); |
mauroar211 | 0:b805b487fbef | 168 | |
mauroar211 | 0:b805b487fbef | 169 | for (uint8_t i = 0; i < hlen; i++) { |
mauroar211 | 0:b805b487fbef | 170 | write(header[i]); |
mauroar211 | 0:b805b487fbef | 171 | sum += header[i]; |
mauroar211 | 0:b805b487fbef | 172 | |
mauroar211 | 0:b805b487fbef | 173 | DMSG_HEX(header[i]); |
mauroar211 | 0:b805b487fbef | 174 | } |
mauroar211 | 0:b805b487fbef | 175 | for (uint8_t i = 0; i < blen; i++) { |
mauroar211 | 0:b805b487fbef | 176 | write(body[i]); |
mauroar211 | 0:b805b487fbef | 177 | sum += body[i]; |
mauroar211 | 0:b805b487fbef | 178 | |
mauroar211 | 0:b805b487fbef | 179 | DMSG_HEX(header[i]); |
mauroar211 | 0:b805b487fbef | 180 | } |
mauroar211 | 0:b805b487fbef | 181 | |
mauroar211 | 0:b805b487fbef | 182 | uint8_t checksum = ~sum + 1; // checksum of TFI + DATA |
mauroar211 | 0:b805b487fbef | 183 | write(checksum); |
mauroar211 | 0:b805b487fbef | 184 | write(PN532_POSTAMBLE); |
mauroar211 | 0:b805b487fbef | 185 | |
mauroar211 | 0:b805b487fbef | 186 | _ss = 1; |
mauroar211 | 0:b805b487fbef | 187 | |
mauroar211 | 0:b805b487fbef | 188 | DMSG("\n"); |
mauroar211 | 0:b805b487fbef | 189 | } |
mauroar211 | 0:b805b487fbef | 190 | |
mauroar211 | 0:b805b487fbef | 191 | int8_t PN532_SPI::readAckFrame() |
mauroar211 | 0:b805b487fbef | 192 | { |
mauroar211 | 0:b805b487fbef | 193 | const uint8_t PN532_ACK[] = {0, 0, 0xFF, 0, 0xFF, 0}; |
mauroar211 | 0:b805b487fbef | 194 | |
mauroar211 | 0:b805b487fbef | 195 | uint8_t ackBuf[sizeof(PN532_ACK)]; |
mauroar211 | 0:b805b487fbef | 196 | |
mauroar211 | 0:b805b487fbef | 197 | _ss = 0; |
mauroar211 | 0:b805b487fbef | 198 | wait_ms(1); |
mauroar211 | 0:b805b487fbef | 199 | write(DATA_READ); |
mauroar211 | 0:b805b487fbef | 200 | |
mauroar211 | 0:b805b487fbef | 201 | for (uint8_t i = 0; i < sizeof(PN532_ACK); i++) { |
mauroar211 | 0:b805b487fbef | 202 | ackBuf[i] = read(); |
mauroar211 | 0:b805b487fbef | 203 | } |
mauroar211 | 0:b805b487fbef | 204 | |
mauroar211 | 0:b805b487fbef | 205 | _ss = 1; |
mauroar211 | 0:b805b487fbef | 206 | |
mauroar211 | 0:b805b487fbef | 207 | return memcmp(ackBuf, PN532_ACK, sizeof(PN532_ACK)); |
mauroar211 | 0:b805b487fbef | 208 | } |