Production Test Program (PTP) for the LPC4088 Experiment Base Board

Dependencies:   EALib I2S LM75B SDFileSystem mbed

Committer:
embeddedartists
Date:
Wed Aug 27 14:24:59 2014 +0000
Revision:
1:47680ec5d783
Child:
7:48375cb50f3a
Got the display and touch to work. Only audio tests missing

Who changed what in which revision?

UserRevisionLine numberNew contents of line
embeddedartists 1:47680ec5d783 1 /*
embeddedartists 1:47680ec5d783 2 * Copyright 2013 Embedded Artists AB
embeddedartists 1:47680ec5d783 3 *
embeddedartists 1:47680ec5d783 4 * Licensed under the Apache License, Version 2.0 (the "License");
embeddedartists 1:47680ec5d783 5 * you may not use this file except in compliance with the License.
embeddedartists 1:47680ec5d783 6 * You may obtain a copy of the License at
embeddedartists 1:47680ec5d783 7 *
embeddedartists 1:47680ec5d783 8 * http://www.apache.org/licenses/LICENSE-2.0
embeddedartists 1:47680ec5d783 9 *
embeddedartists 1:47680ec5d783 10 * Unless required by applicable law or agreed to in writing, software
embeddedartists 1:47680ec5d783 11 * distributed under the License is distributed on an "AS IS" BASIS,
embeddedartists 1:47680ec5d783 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
embeddedartists 1:47680ec5d783 13 * See the License for the specific language governing permissions and
embeddedartists 1:47680ec5d783 14 * limitations under the License.
embeddedartists 1:47680ec5d783 15 */
embeddedartists 1:47680ec5d783 16
embeddedartists 1:47680ec5d783 17 /******************************************************************************
embeddedartists 1:47680ec5d783 18 * Includes
embeddedartists 1:47680ec5d783 19 *****************************************************************************/
embeddedartists 1:47680ec5d783 20
embeddedartists 1:47680ec5d783 21 #include "mbed.h"
embeddedartists 1:47680ec5d783 22 #include "mbed_debug.h"
embeddedartists 1:47680ec5d783 23
embeddedartists 1:47680ec5d783 24 #include "AR1021I2C.h"
embeddedartists 1:47680ec5d783 25
embeddedartists 1:47680ec5d783 26 /******************************************************************************
embeddedartists 1:47680ec5d783 27 * Defines and typedefs
embeddedartists 1:47680ec5d783 28 *****************************************************************************/
embeddedartists 1:47680ec5d783 29
embeddedartists 1:47680ec5d783 30 #define AR1021_REG_TOUCH_THRESHOLD (0x02)
embeddedartists 1:47680ec5d783 31 #define AR1021_REG_SENS_FILTER (0x03)
embeddedartists 1:47680ec5d783 32 #define AR1021_REG_SAMPLING_FAST (0x04)
embeddedartists 1:47680ec5d783 33 #define AR1021_REG_SAMPLING_SLOW (0x05)
embeddedartists 1:47680ec5d783 34 #define AR1021_REG_ACC_FILTER_FAST (0x06)
embeddedartists 1:47680ec5d783 35 #define AR1021_REG_ACC_FILTER_SLOW (0x07)
embeddedartists 1:47680ec5d783 36 #define AR1021_REG_SPEED_THRESHOLD (0x08)
embeddedartists 1:47680ec5d783 37 #define AR1021_REG_SLEEP_DELAY (0x0A)
embeddedartists 1:47680ec5d783 38 #define AR1021_REG_PEN_UP_DELAY (0x0B)
embeddedartists 1:47680ec5d783 39 #define AR1021_REG_TOUCH_MODE (0x0C)
embeddedartists 1:47680ec5d783 40 #define AR1021_REG_TOUCH_OPTIONS (0x0D)
embeddedartists 1:47680ec5d783 41 #define AR1021_REG_CALIB_INSETS (0x0E)
embeddedartists 1:47680ec5d783 42 #define AR1021_REG_PEN_STATE_REPORT_DELAY (0x0F)
embeddedartists 1:47680ec5d783 43 #define AR1021_REG_TOUCH_REPORT_DELAY (0x11)
embeddedartists 1:47680ec5d783 44
embeddedartists 1:47680ec5d783 45
embeddedartists 1:47680ec5d783 46 #define AR1021_CMD_GET_VERSION (0x10)
embeddedartists 1:47680ec5d783 47 #define AR1021_CMD_ENABLE_TOUCH (0x12)
embeddedartists 1:47680ec5d783 48 #define AR1021_CMD_DISABLE_TOUCH (0x13)
embeddedartists 1:47680ec5d783 49 #define AR1021_CMD_CALIBRATE_MODE (0x14)
embeddedartists 1:47680ec5d783 50 #define AR1021_CMD_REGISTER_READ (0x20)
embeddedartists 1:47680ec5d783 51 #define AR1021_CMD_REGISTER_WRITE (0x21)
embeddedartists 1:47680ec5d783 52 #define AR1021_CMD_REGISTER_START_ADDR_REQUEST (0x22)
embeddedartists 1:47680ec5d783 53 #define AR1021_CMD_REGISTER_WRITE_TO_EEPROM (0x23)
embeddedartists 1:47680ec5d783 54 #define AR1021_CMD_EEPROM_READ (0x28)
embeddedartists 1:47680ec5d783 55 #define AR1021_CMD_EEPROM_WRITE (0x29)
embeddedartists 1:47680ec5d783 56 #define AR1021_CMD_EEPROM_WRITE_TO_REGISTERS (0x2B)
embeddedartists 1:47680ec5d783 57
embeddedartists 1:47680ec5d783 58 #define AR1021_RESP_STAT_OK (0x00)
embeddedartists 1:47680ec5d783 59 #define AR1021_RESP_STAT_CMD_UNREC (0x01)
embeddedartists 1:47680ec5d783 60 #define AR1021_RESP_STAT_HDR_UNREC (0x03)
embeddedartists 1:47680ec5d783 61 #define AR1021_RESP_STAT_TIMEOUT (0x04)
embeddedartists 1:47680ec5d783 62 #define AR1021_RESP_STAT_CANCEL_CALIB (0xFC)
embeddedartists 1:47680ec5d783 63
embeddedartists 1:47680ec5d783 64
embeddedartists 1:47680ec5d783 65 #define AR1021_ERR_NO_HDR (-1000)
embeddedartists 1:47680ec5d783 66 #define AR1021_ERR_INV_LEN (-1001)
embeddedartists 1:47680ec5d783 67 #define AR1021_ERR_INV_RESP (-1002)
embeddedartists 1:47680ec5d783 68 #define AR1021_ERR_INV_RESPLEN (-1003)
embeddedartists 1:47680ec5d783 69 #define AR1021_ERR_TIMEOUT (-1004)
embeddedartists 1:47680ec5d783 70
embeddedartists 1:47680ec5d783 71 // bit 7 is always 1 and bit 0 defines pen up or down
embeddedartists 1:47680ec5d783 72 #define AR1021_PEN_MASK (0x81)
embeddedartists 1:47680ec5d783 73
embeddedartists 1:47680ec5d783 74 #define AR1021_NUM_CALIB_POINTS (4)
embeddedartists 1:47680ec5d783 75
embeddedartists 1:47680ec5d783 76 #define AR1021_ADDR (0x4D << 1)
embeddedartists 1:47680ec5d783 77
embeddedartists 1:47680ec5d783 78 #define AR1021_TIMEOUT 1000 //how many ms to wait for responce
embeddedartists 1:47680ec5d783 79 #define AR1021_RETRY 5 //how many times to retry sending command
embeddedartists 1:47680ec5d783 80
embeddedartists 1:47680ec5d783 81
embeddedartists 1:47680ec5d783 82 AR1021I2C::AR1021I2C(PinName sda, PinName scl, PinName siq) :
embeddedartists 1:47680ec5d783 83 _i2c(sda, scl), _siq(siq), _siqIrq(siq)
embeddedartists 1:47680ec5d783 84 {
embeddedartists 1:47680ec5d783 85 _i2c.frequency(200000);
embeddedartists 1:47680ec5d783 86
embeddedartists 1:47680ec5d783 87 // default calibration inset is 25 -> (25/2 = 12.5%)
embeddedartists 1:47680ec5d783 88 _inset = 25;
embeddedartists 1:47680ec5d783 89
embeddedartists 1:47680ec5d783 90 // make sure _calibPoint has an invalid value to begin with
embeddedartists 1:47680ec5d783 91 // correct value is set in calibrateStart()
embeddedartists 1:47680ec5d783 92 _calibPoint = AR1021_NUM_CALIB_POINTS+1;
embeddedartists 1:47680ec5d783 93
embeddedartists 1:47680ec5d783 94 _x = 0;
embeddedartists 1:47680ec5d783 95 _y = 0;
embeddedartists 1:47680ec5d783 96 _pen = 0;
embeddedartists 1:47680ec5d783 97
embeddedartists 1:47680ec5d783 98 _initialized = false;
embeddedartists 1:47680ec5d783 99 }
embeddedartists 1:47680ec5d783 100
embeddedartists 1:47680ec5d783 101
embeddedartists 1:47680ec5d783 102 bool AR1021I2C::read(touchCoordinate_t &coord) {
embeddedartists 1:47680ec5d783 103
embeddedartists 1:47680ec5d783 104 if (!_initialized) return false;
embeddedartists 1:47680ec5d783 105
embeddedartists 1:47680ec5d783 106 coord.x = _x * _width/4095;
embeddedartists 1:47680ec5d783 107 coord.y = _y * _height/4095;
embeddedartists 1:47680ec5d783 108 coord.z = _pen;
embeddedartists 1:47680ec5d783 109
embeddedartists 1:47680ec5d783 110 return true;
embeddedartists 1:47680ec5d783 111 }
embeddedartists 1:47680ec5d783 112
embeddedartists 1:47680ec5d783 113
embeddedartists 1:47680ec5d783 114 bool AR1021I2C::init(uint16_t width, uint16_t height) {
embeddedartists 1:47680ec5d783 115 int result = 0;
embeddedartists 1:47680ec5d783 116 bool ok = false;
embeddedartists 1:47680ec5d783 117 int attempts = 0;
embeddedartists 1:47680ec5d783 118
embeddedartists 1:47680ec5d783 119 _width = width;
embeddedartists 1:47680ec5d783 120 _height = height;
embeddedartists 1:47680ec5d783 121
embeddedartists 1:47680ec5d783 122 while (1) {
embeddedartists 1:47680ec5d783 123
embeddedartists 1:47680ec5d783 124 do {
embeddedartists 1:47680ec5d783 125 // disable touch
embeddedartists 1:47680ec5d783 126 result = cmd(AR1021_CMD_DISABLE_TOUCH, NULL, 0, NULL, 0);
embeddedartists 1:47680ec5d783 127 if (result != 0) {
embeddedartists 1:47680ec5d783 128 debug("disable touch failed (%d)\n", result);
embeddedartists 1:47680ec5d783 129 break;
embeddedartists 1:47680ec5d783 130 }
embeddedartists 1:47680ec5d783 131
embeddedartists 1:47680ec5d783 132 char regOffset = 0;
embeddedartists 1:47680ec5d783 133 int regOffLen = 1;
embeddedartists 1:47680ec5d783 134 result = cmd(AR1021_CMD_REGISTER_START_ADDR_REQUEST, NULL, 0,
embeddedartists 1:47680ec5d783 135 &regOffset, &regOffLen);
embeddedartists 1:47680ec5d783 136 if (result != 0) {
embeddedartists 1:47680ec5d783 137 debug("register offset request failed (%d)\n", result);
embeddedartists 1:47680ec5d783 138 break;
embeddedartists 1:47680ec5d783 139 }
embeddedartists 1:47680ec5d783 140
embeddedartists 1:47680ec5d783 141 // enable calibrated coordinates
embeddedartists 1:47680ec5d783 142 // high, low address, len, value
embeddedartists 1:47680ec5d783 143 char toptions[4] = {0x00, AR1021_REG_TOUCH_OPTIONS+regOffset, 0x01, 0x01};
embeddedartists 1:47680ec5d783 144 result = cmd(AR1021_CMD_REGISTER_WRITE, toptions, 4, NULL, 0);
embeddedartists 1:47680ec5d783 145 if (result != 0) {
embeddedartists 1:47680ec5d783 146 debug("register write request failed (%d)\n", result);
embeddedartists 1:47680ec5d783 147 break;
embeddedartists 1:47680ec5d783 148 }
embeddedartists 1:47680ec5d783 149
embeddedartists 1:47680ec5d783 150 // save registers to eeprom
embeddedartists 1:47680ec5d783 151 result = cmd(AR1021_CMD_REGISTER_WRITE_TO_EEPROM, NULL, 0, NULL, 0);
embeddedartists 1:47680ec5d783 152 if (result != 0) {
embeddedartists 1:47680ec5d783 153 debug("register write to eeprom failed (%d)\n", result);
embeddedartists 1:47680ec5d783 154 break;
embeddedartists 1:47680ec5d783 155 }
embeddedartists 1:47680ec5d783 156
embeddedartists 1:47680ec5d783 157 // enable touch
embeddedartists 1:47680ec5d783 158 result = cmd(AR1021_CMD_ENABLE_TOUCH, NULL, 0, NULL, 0);
embeddedartists 1:47680ec5d783 159 if (result != 0) {
embeddedartists 1:47680ec5d783 160 debug("enable touch failed (%d)\n", result);
embeddedartists 1:47680ec5d783 161 break;
embeddedartists 1:47680ec5d783 162 }
embeddedartists 1:47680ec5d783 163
embeddedartists 1:47680ec5d783 164 _siqIrq.rise(this, &AR1021I2C::readTouchIrq);
embeddedartists 1:47680ec5d783 165
embeddedartists 1:47680ec5d783 166 _initialized = true;
embeddedartists 1:47680ec5d783 167 ok = true;
embeddedartists 1:47680ec5d783 168
embeddedartists 1:47680ec5d783 169 } while(0);
embeddedartists 1:47680ec5d783 170
embeddedartists 1:47680ec5d783 171 if (ok) break;
embeddedartists 1:47680ec5d783 172
embeddedartists 1:47680ec5d783 173 // try to run the initialize sequence at most 2 times
embeddedartists 1:47680ec5d783 174 if(++attempts >= 2) break;
embeddedartists 1:47680ec5d783 175 }
embeddedartists 1:47680ec5d783 176
embeddedartists 1:47680ec5d783 177
embeddedartists 1:47680ec5d783 178 return ok;
embeddedartists 1:47680ec5d783 179 }
embeddedartists 1:47680ec5d783 180
embeddedartists 1:47680ec5d783 181 bool AR1021I2C::calibrateStart() {
embeddedartists 1:47680ec5d783 182 bool ok = false;
embeddedartists 1:47680ec5d783 183 int result = 0;
embeddedartists 1:47680ec5d783 184 int attempts = 0;
embeddedartists 1:47680ec5d783 185
embeddedartists 1:47680ec5d783 186 if (!_initialized) return false;
embeddedartists 1:47680ec5d783 187
embeddedartists 1:47680ec5d783 188 _siqIrq.rise(NULL);
embeddedartists 1:47680ec5d783 189
embeddedartists 1:47680ec5d783 190 while(1) {
embeddedartists 1:47680ec5d783 191
embeddedartists 1:47680ec5d783 192 do {
embeddedartists 1:47680ec5d783 193 // disable touch
embeddedartists 1:47680ec5d783 194 result = cmd(AR1021_CMD_DISABLE_TOUCH, NULL, 0, NULL, 0);
embeddedartists 1:47680ec5d783 195 if (result != 0) {
embeddedartists 1:47680ec5d783 196 debug("disable touch failed (%d)\n", result);
embeddedartists 1:47680ec5d783 197 break;
embeddedartists 1:47680ec5d783 198 }
embeddedartists 1:47680ec5d783 199
embeddedartists 1:47680ec5d783 200 char regOffset = 0;
embeddedartists 1:47680ec5d783 201 int regOffLen = 1;
embeddedartists 1:47680ec5d783 202 result = cmd(AR1021_CMD_REGISTER_START_ADDR_REQUEST, NULL, 0,
embeddedartists 1:47680ec5d783 203 &regOffset, &regOffLen);
embeddedartists 1:47680ec5d783 204 if (result != 0) {
embeddedartists 1:47680ec5d783 205 debug("register offset request failed (%d)\n", result);
embeddedartists 1:47680ec5d783 206 break;
embeddedartists 1:47680ec5d783 207 }
embeddedartists 1:47680ec5d783 208
embeddedartists 1:47680ec5d783 209 // set insets
embeddedartists 1:47680ec5d783 210 // enable calibrated coordinates
embeddedartists 1:47680ec5d783 211 // high, low address, len, value
embeddedartists 1:47680ec5d783 212 char insets[4] = {0x00, AR1021_REG_CALIB_INSETS+regOffset, 0x01, _inset};
embeddedartists 1:47680ec5d783 213 result = cmd(AR1021_CMD_REGISTER_WRITE, insets, 4, NULL, 0);
embeddedartists 1:47680ec5d783 214 if (result != 0) {
embeddedartists 1:47680ec5d783 215 debug("register write request failed (%d)\n", result);
embeddedartists 1:47680ec5d783 216 break;
embeddedartists 1:47680ec5d783 217 }
embeddedartists 1:47680ec5d783 218
embeddedartists 1:47680ec5d783 219 // calibration mode
embeddedartists 1:47680ec5d783 220 char calibType = 4;
embeddedartists 1:47680ec5d783 221 result = cmd(AR1021_CMD_CALIBRATE_MODE, &calibType, 1, NULL, 0, false);
embeddedartists 1:47680ec5d783 222 if (result != 0) {
embeddedartists 1:47680ec5d783 223 debug("calibration mode failed (%d)\n", result);
embeddedartists 1:47680ec5d783 224 break;
embeddedartists 1:47680ec5d783 225 }
embeddedartists 1:47680ec5d783 226
embeddedartists 1:47680ec5d783 227 _calibPoint = 0;
embeddedartists 1:47680ec5d783 228 ok = true;
embeddedartists 1:47680ec5d783 229
embeddedartists 1:47680ec5d783 230 } while(0);
embeddedartists 1:47680ec5d783 231
embeddedartists 1:47680ec5d783 232 if (ok) break;
embeddedartists 1:47680ec5d783 233
embeddedartists 1:47680ec5d783 234 // try to run the calibrate mode sequence at most 2 times
embeddedartists 1:47680ec5d783 235 if (++attempts >= 2) break;
embeddedartists 1:47680ec5d783 236 }
embeddedartists 1:47680ec5d783 237
embeddedartists 1:47680ec5d783 238 return ok;
embeddedartists 1:47680ec5d783 239 }
embeddedartists 1:47680ec5d783 240
embeddedartists 1:47680ec5d783 241 bool AR1021I2C::getNextCalibratePoint(uint16_t* x, uint16_t* y) {
embeddedartists 1:47680ec5d783 242
embeddedartists 1:47680ec5d783 243 if (!_initialized) return false;
embeddedartists 1:47680ec5d783 244 if (x == NULL || y == NULL) return false;
embeddedartists 1:47680ec5d783 245
embeddedartists 1:47680ec5d783 246 int xInset = (_width * _inset / 100) / 2;
embeddedartists 1:47680ec5d783 247 int yInset = (_height * _inset / 100) / 2;
embeddedartists 1:47680ec5d783 248
embeddedartists 1:47680ec5d783 249 switch(_calibPoint) {
embeddedartists 1:47680ec5d783 250 case 0:
embeddedartists 1:47680ec5d783 251 *x = xInset;
embeddedartists 1:47680ec5d783 252 *y = yInset;
embeddedartists 1:47680ec5d783 253 break;
embeddedartists 1:47680ec5d783 254 case 1:
embeddedartists 1:47680ec5d783 255 *x = _width - xInset;
embeddedartists 1:47680ec5d783 256 *y = yInset;
embeddedartists 1:47680ec5d783 257 break;
embeddedartists 1:47680ec5d783 258 case 2:
embeddedartists 1:47680ec5d783 259 *x = _width - xInset;
embeddedartists 1:47680ec5d783 260 *y = _height - yInset;
embeddedartists 1:47680ec5d783 261 break;
embeddedartists 1:47680ec5d783 262 case 3:
embeddedartists 1:47680ec5d783 263 *x = xInset;
embeddedartists 1:47680ec5d783 264 *y = _height - yInset;
embeddedartists 1:47680ec5d783 265 break;
embeddedartists 1:47680ec5d783 266 default:
embeddedartists 1:47680ec5d783 267 return false;
embeddedartists 1:47680ec5d783 268 }
embeddedartists 1:47680ec5d783 269
embeddedartists 1:47680ec5d783 270 return true;
embeddedartists 1:47680ec5d783 271 }
embeddedartists 1:47680ec5d783 272
embeddedartists 1:47680ec5d783 273 bool AR1021I2C::waitForCalibratePoint(bool* morePoints, uint32_t timeout) {
embeddedartists 1:47680ec5d783 274 int result = 0;
embeddedartists 1:47680ec5d783 275 bool ret = false;
embeddedartists 1:47680ec5d783 276
embeddedartists 1:47680ec5d783 277 if (!_initialized) return false;
embeddedartists 1:47680ec5d783 278
embeddedartists 1:47680ec5d783 279 do {
embeddedartists 1:47680ec5d783 280 if (morePoints == NULL || _calibPoint >= AR1021_NUM_CALIB_POINTS) {
embeddedartists 1:47680ec5d783 281 break;
embeddedartists 1:47680ec5d783 282 }
embeddedartists 1:47680ec5d783 283
embeddedartists 1:47680ec5d783 284 // wait for response
embeddedartists 1:47680ec5d783 285 result = waitForCalibResponse(timeout);
embeddedartists 1:47680ec5d783 286 if (result != 0) {
embeddedartists 1:47680ec5d783 287 debug("wait for calibration response failed (%d)\n", result);
embeddedartists 1:47680ec5d783 288 break;
embeddedartists 1:47680ec5d783 289 }
embeddedartists 1:47680ec5d783 290
embeddedartists 1:47680ec5d783 291 _calibPoint++;
embeddedartists 1:47680ec5d783 292 *morePoints = (_calibPoint < AR1021_NUM_CALIB_POINTS);
embeddedartists 1:47680ec5d783 293
embeddedartists 1:47680ec5d783 294
embeddedartists 1:47680ec5d783 295 // no more points -> enable touch
embeddedartists 1:47680ec5d783 296 if (!(*morePoints)) {
embeddedartists 1:47680ec5d783 297
embeddedartists 1:47680ec5d783 298 // wait for calibration data to be written to eeprom
embeddedartists 1:47680ec5d783 299 // before enabling touch
embeddedartists 1:47680ec5d783 300 result = waitForCalibResponse(timeout);
embeddedartists 1:47680ec5d783 301 if (result != 0) {
embeddedartists 1:47680ec5d783 302 debug("wait for calibration response failed (%d)\n", result);
embeddedartists 1:47680ec5d783 303 break;
embeddedartists 1:47680ec5d783 304 }
embeddedartists 1:47680ec5d783 305
embeddedartists 1:47680ec5d783 306
embeddedartists 1:47680ec5d783 307 // clear chip-select since calibration is done;
embeddedartists 1:47680ec5d783 308 // _cs = 1;
embeddedartists 1:47680ec5d783 309
embeddedartists 1:47680ec5d783 310 result = cmd(AR1021_CMD_ENABLE_TOUCH, NULL, 0, NULL, 0);
embeddedartists 1:47680ec5d783 311 if (result != 0) {
embeddedartists 1:47680ec5d783 312 debug("enable touch failed (%d)\n", result);
embeddedartists 1:47680ec5d783 313 break;
embeddedartists 1:47680ec5d783 314 }
embeddedartists 1:47680ec5d783 315
embeddedartists 1:47680ec5d783 316 _siqIrq.rise(this, &AR1021I2C::readTouchIrq);
embeddedartists 1:47680ec5d783 317 }
embeddedartists 1:47680ec5d783 318
embeddedartists 1:47680ec5d783 319 ret = true;
embeddedartists 1:47680ec5d783 320
embeddedartists 1:47680ec5d783 321 } while (0);
embeddedartists 1:47680ec5d783 322
embeddedartists 1:47680ec5d783 323
embeddedartists 1:47680ec5d783 324
embeddedartists 1:47680ec5d783 325 if (!ret) {
embeddedartists 1:47680ec5d783 326 // make sure to set chip-select off in case of an error
embeddedartists 1:47680ec5d783 327 // _cs = 1;
embeddedartists 1:47680ec5d783 328 // calibration must restart if an error occurred
embeddedartists 1:47680ec5d783 329 _calibPoint = AR1021_NUM_CALIB_POINTS+1;
embeddedartists 1:47680ec5d783 330 }
embeddedartists 1:47680ec5d783 331
embeddedartists 1:47680ec5d783 332
embeddedartists 1:47680ec5d783 333
embeddedartists 1:47680ec5d783 334 return ret;
embeddedartists 1:47680ec5d783 335 }
embeddedartists 1:47680ec5d783 336
embeddedartists 1:47680ec5d783 337 int AR1021I2C::cmd(char cmd, char* data, int len, char* respBuf, int* respLen,
embeddedartists 1:47680ec5d783 338 bool setCsOff) {
embeddedartists 1:47680ec5d783 339
embeddedartists 1:47680ec5d783 340 int ret = 0;
embeddedartists 1:47680ec5d783 341 char buff[10];
embeddedartists 1:47680ec5d783 342 for (int attempt = 1; attempt <= AR1021_RETRY; attempt++) {
embeddedartists 1:47680ec5d783 343 if (attempt > 1) {
embeddedartists 1:47680ec5d783 344 wait_ms(50);
embeddedartists 1:47680ec5d783 345 }
embeddedartists 1:47680ec5d783 346
embeddedartists 1:47680ec5d783 347 // command request
embeddedartists 1:47680ec5d783 348 // ---------------
embeddedartists 1:47680ec5d783 349 // 0x00 0x55 len cmd data
embeddedartists 1:47680ec5d783 350 // 0x00 = protocol command byte
embeddedartists 1:47680ec5d783 351 // 0x55 = header
embeddedartists 1:47680ec5d783 352 // len = data length + cmd (1)
embeddedartists 1:47680ec5d783 353 // data = data to send
embeddedartists 1:47680ec5d783 354
embeddedartists 1:47680ec5d783 355 _i2c.start();
embeddedartists 1:47680ec5d783 356 _i2c.write(AR1021_ADDR); //send write address
embeddedartists 1:47680ec5d783 357 _i2c.write(0x00);
embeddedartists 1:47680ec5d783 358 _i2c.write(0x55); //header
embeddedartists 1:47680ec5d783 359 _i2c.write(len+1); //message length
embeddedartists 1:47680ec5d783 360 _i2c.write(cmd);
embeddedartists 1:47680ec5d783 361 for (int i = 0; i < len; i++) {
embeddedartists 1:47680ec5d783 362 _i2c.write(data[i]);
embeddedartists 1:47680ec5d783 363 }
embeddedartists 1:47680ec5d783 364 wait_us(60);
embeddedartists 1:47680ec5d783 365 _i2c.stop();
embeddedartists 1:47680ec5d783 366
embeddedartists 1:47680ec5d783 367 // wait for response (siq goes high when response is available)
embeddedartists 1:47680ec5d783 368 Timer t;
embeddedartists 1:47680ec5d783 369 t.start();
embeddedartists 1:47680ec5d783 370 while(_siq.read() != 1 && t.read_ms() < AR1021_TIMEOUT);
embeddedartists 1:47680ec5d783 371
embeddedartists 1:47680ec5d783 372 if (t.read_ms() < AR1021_TIMEOUT) {
embeddedartists 1:47680ec5d783 373
embeddedartists 1:47680ec5d783 374 // command response
embeddedartists 1:47680ec5d783 375 // ---------------
embeddedartists 1:47680ec5d783 376 // 0x55 len status cmd data
embeddedartists 1:47680ec5d783 377 // 0x55 = header
embeddedartists 1:47680ec5d783 378 // len = number of bytes following the len byte
embeddedartists 1:47680ec5d783 379 // status = status
embeddedartists 1:47680ec5d783 380 // cmd = command ID
embeddedartists 1:47680ec5d783 381 // data = data to receive
embeddedartists 1:47680ec5d783 382 _i2c.start();
embeddedartists 1:47680ec5d783 383 _i2c.write(AR1021_ADDR + 1); //send read address
embeddedartists 1:47680ec5d783 384 char header = _i2c.read(1); //header should always be 0x55
embeddedartists 1:47680ec5d783 385 char length = _i2c.read(1); //data length
embeddedartists 1:47680ec5d783 386
embeddedartists 1:47680ec5d783 387 //we need to send a NACK on the last read.
embeddedartists 1:47680ec5d783 388 int i;
embeddedartists 1:47680ec5d783 389 for (i = 0; i < (length-1); i++) {
embeddedartists 1:47680ec5d783 390 buff[i] = _i2c.read(1);
embeddedartists 1:47680ec5d783 391 }
embeddedartists 1:47680ec5d783 392 buff[i] = _i2c.read(0); //last returned data byte
embeddedartists 1:47680ec5d783 393 _i2c.stop();
embeddedartists 1:47680ec5d783 394
embeddedartists 1:47680ec5d783 395
embeddedartists 1:47680ec5d783 396 if (header != 0x55) {
embeddedartists 1:47680ec5d783 397 ret = AR1021_ERR_NO_HDR;
embeddedartists 1:47680ec5d783 398 continue;
embeddedartists 1:47680ec5d783 399 }
embeddedartists 1:47680ec5d783 400 if (length < 2) {
embeddedartists 1:47680ec5d783 401 ret = AR1021_ERR_INV_LEN;
embeddedartists 1:47680ec5d783 402 continue;
embeddedartists 1:47680ec5d783 403 }
embeddedartists 1:47680ec5d783 404 if (buff[0] != AR1021_RESP_STAT_OK) {
embeddedartists 1:47680ec5d783 405 ret = -buff[0];
embeddedartists 1:47680ec5d783 406 continue;
embeddedartists 1:47680ec5d783 407 }
embeddedartists 1:47680ec5d783 408 if (buff[1] != cmd) {
embeddedartists 1:47680ec5d783 409 ret = AR1021_ERR_INV_RESP;
embeddedartists 1:47680ec5d783 410 continue;
embeddedartists 1:47680ec5d783 411 }
embeddedartists 1:47680ec5d783 412
embeddedartists 1:47680ec5d783 413 // copy data into response
embeddedartists 1:47680ec5d783 414 if (respLen != NULL && respBuf != NULL) {
embeddedartists 1:47680ec5d783 415 if ((length - 2) > *respLen) {
embeddedartists 1:47680ec5d783 416 // respBuf too small, only copy what fits
embeddedartists 1:47680ec5d783 417 for (i = 0; i < *respLen; i++) {
embeddedartists 1:47680ec5d783 418 respBuf[i] = buff[i+2];
embeddedartists 1:47680ec5d783 419 }
embeddedartists 1:47680ec5d783 420 } else {
embeddedartists 1:47680ec5d783 421 // respBuf large enough, copy all
embeddedartists 1:47680ec5d783 422 for (i = 0; i < (length-2); i++) {
embeddedartists 1:47680ec5d783 423 respBuf[i] = buff[i+2];
embeddedartists 1:47680ec5d783 424 }
embeddedartists 1:47680ec5d783 425 *respLen = (length-2);
embeddedartists 1:47680ec5d783 426 }
embeddedartists 1:47680ec5d783 427 }
embeddedartists 1:47680ec5d783 428
embeddedartists 1:47680ec5d783 429 // success
embeddedartists 1:47680ec5d783 430 ret = 0;
embeddedartists 1:47680ec5d783 431 break;
embeddedartists 1:47680ec5d783 432
embeddedartists 1:47680ec5d783 433 } else {
embeddedartists 1:47680ec5d783 434 ret = AR1021_ERR_TIMEOUT;
embeddedartists 1:47680ec5d783 435 continue;
embeddedartists 1:47680ec5d783 436 }
embeddedartists 1:47680ec5d783 437 }
embeddedartists 1:47680ec5d783 438
embeddedartists 1:47680ec5d783 439 return ret;
embeddedartists 1:47680ec5d783 440 }
embeddedartists 1:47680ec5d783 441
embeddedartists 1:47680ec5d783 442 int AR1021I2C::waitForCalibResponse(uint32_t timeout) {
embeddedartists 1:47680ec5d783 443 Timer t;
embeddedartists 1:47680ec5d783 444 int ret = 0;
embeddedartists 1:47680ec5d783 445
embeddedartists 1:47680ec5d783 446 t.start();
embeddedartists 1:47680ec5d783 447
embeddedartists 1:47680ec5d783 448 // wait for siq
embeddedartists 1:47680ec5d783 449 while (_siq.read() != 1 &&
embeddedartists 1:47680ec5d783 450 (timeout == 0 || (uint32_t)t.read_ms() < (int)timeout));
embeddedartists 1:47680ec5d783 451
embeddedartists 1:47680ec5d783 452
embeddedartists 1:47680ec5d783 453 do {
embeddedartists 1:47680ec5d783 454
embeddedartists 1:47680ec5d783 455 if (timeout > 0 && (uint32_t)t.read_ms() >= timeout) {
embeddedartists 1:47680ec5d783 456 ret = AR1021_ERR_TIMEOUT;
embeddedartists 1:47680ec5d783 457 break;
embeddedartists 1:47680ec5d783 458 }
embeddedartists 1:47680ec5d783 459
embeddedartists 1:47680ec5d783 460 // command response
embeddedartists 1:47680ec5d783 461 // ---------------
embeddedartists 1:47680ec5d783 462 // 0x55 len status cmd data
embeddedartists 1:47680ec5d783 463 // 0x55 = header
embeddedartists 1:47680ec5d783 464 // len = number of bytes following the len byte (should be 2)
embeddedartists 1:47680ec5d783 465 // status = status
embeddedartists 1:47680ec5d783 466 // cmd = command ID
embeddedartists 1:47680ec5d783 467 _i2c.start();
embeddedartists 1:47680ec5d783 468 _i2c.write(AR1021_ADDR + 1); //send read address
embeddedartists 1:47680ec5d783 469 char header = _i2c.read(1); //header should always be 0x55
embeddedartists 1:47680ec5d783 470 char length = _i2c.read(1); //data length
embeddedartists 1:47680ec5d783 471
embeddedartists 1:47680ec5d783 472 if (header != 0x55) {
embeddedartists 1:47680ec5d783 473 ret = AR1021_ERR_NO_HDR;
embeddedartists 1:47680ec5d783 474 break;
embeddedartists 1:47680ec5d783 475 }
embeddedartists 1:47680ec5d783 476 if (length < 2) {
embeddedartists 1:47680ec5d783 477 ret = AR1021_ERR_INV_LEN;
embeddedartists 1:47680ec5d783 478 break;
embeddedartists 1:47680ec5d783 479 }
embeddedartists 1:47680ec5d783 480 char status = _i2c.read(1); //status
embeddedartists 1:47680ec5d783 481 char cmd = _i2c.read(0); //command, should be NACK'ed
embeddedartists 1:47680ec5d783 482 _i2c.stop();
embeddedartists 1:47680ec5d783 483 if (status != AR1021_RESP_STAT_OK) {
embeddedartists 1:47680ec5d783 484 ret = -status;
embeddedartists 1:47680ec5d783 485 break;
embeddedartists 1:47680ec5d783 486 }
embeddedartists 1:47680ec5d783 487 if (cmd != AR1021_CMD_CALIBRATE_MODE) {
embeddedartists 1:47680ec5d783 488 ret = AR1021_ERR_INV_RESP;
embeddedartists 1:47680ec5d783 489 break;
embeddedartists 1:47680ec5d783 490 }
embeddedartists 1:47680ec5d783 491
embeddedartists 1:47680ec5d783 492 // success
embeddedartists 1:47680ec5d783 493 ret = 0;
embeddedartists 1:47680ec5d783 494
embeddedartists 1:47680ec5d783 495 } while (0);
embeddedartists 1:47680ec5d783 496
embeddedartists 1:47680ec5d783 497 return ret;
embeddedartists 1:47680ec5d783 498 }
embeddedartists 1:47680ec5d783 499
embeddedartists 1:47680ec5d783 500
embeddedartists 1:47680ec5d783 501 void AR1021I2C::readTouchIrq() {
embeddedartists 1:47680ec5d783 502 while(_siq.read() == 1) {
embeddedartists 1:47680ec5d783 503
embeddedartists 1:47680ec5d783 504 // touch coordinates are sent in a 5-byte data packet
embeddedartists 1:47680ec5d783 505 _i2c.start();
embeddedartists 1:47680ec5d783 506 _i2c.write(AR1021_ADDR + 1); //send read address
embeddedartists 1:47680ec5d783 507 int pen = _i2c.read(1);
embeddedartists 1:47680ec5d783 508 int xlo = _i2c.read(1);
embeddedartists 1:47680ec5d783 509 int xhi = _i2c.read(1);
embeddedartists 1:47680ec5d783 510 int ylo = _i2c.read(1);
embeddedartists 1:47680ec5d783 511 int yhi = _i2c.read(0);
embeddedartists 1:47680ec5d783 512 _i2c.stop();
embeddedartists 1:47680ec5d783 513
embeddedartists 1:47680ec5d783 514 // pen down
embeddedartists 1:47680ec5d783 515 if ((pen&AR1021_PEN_MASK) == (1<<7|1<<0)) {
embeddedartists 1:47680ec5d783 516 _pen = 1;
embeddedartists 1:47680ec5d783 517 }
embeddedartists 1:47680ec5d783 518 // pen up
embeddedartists 1:47680ec5d783 519 else if ((pen&AR1021_PEN_MASK) == (1<<7)){
embeddedartists 1:47680ec5d783 520 _pen = 0;
embeddedartists 1:47680ec5d783 521 }
embeddedartists 1:47680ec5d783 522 // invalid value
embeddedartists 1:47680ec5d783 523 else {
embeddedartists 1:47680ec5d783 524 continue;
embeddedartists 1:47680ec5d783 525 }
embeddedartists 1:47680ec5d783 526
embeddedartists 1:47680ec5d783 527 _x = ((xhi<<7)|xlo);
embeddedartists 1:47680ec5d783 528 _y = ((yhi<<7)|ylo);
embeddedartists 1:47680ec5d783 529 }
embeddedartists 1:47680ec5d783 530 }
embeddedartists 1:47680ec5d783 531
embeddedartists 1:47680ec5d783 532 bool AR1021I2C::info(int* verHigh, int* verLow, int* resBits, int* type)
embeddedartists 1:47680ec5d783 533 {
embeddedartists 1:47680ec5d783 534 char buff[3] = {0,0,0};
embeddedartists 1:47680ec5d783 535 int read = 3;
embeddedartists 1:47680ec5d783 536 int res = cmd(AR1021_CMD_GET_VERSION, NULL, 0, buff, &read);
embeddedartists 1:47680ec5d783 537 if (res == 0) {
embeddedartists 1:47680ec5d783 538 *verHigh = buff[0];
embeddedartists 1:47680ec5d783 539 *verLow = buff[1];
embeddedartists 1:47680ec5d783 540 switch(buff[2] & 3) {
embeddedartists 1:47680ec5d783 541 case 0:
embeddedartists 1:47680ec5d783 542 *resBits = 8;
embeddedartists 1:47680ec5d783 543 break;
embeddedartists 1:47680ec5d783 544 case 1:
embeddedartists 1:47680ec5d783 545 *resBits = 10;
embeddedartists 1:47680ec5d783 546 break;
embeddedartists 1:47680ec5d783 547 case 2:
embeddedartists 1:47680ec5d783 548 *resBits = 12;
embeddedartists 1:47680ec5d783 549 break;
embeddedartists 1:47680ec5d783 550 case 3:
embeddedartists 1:47680ec5d783 551 *resBits = 12;
embeddedartists 1:47680ec5d783 552 break;
embeddedartists 1:47680ec5d783 553 default:
embeddedartists 1:47680ec5d783 554 res = 25;
embeddedartists 1:47680ec5d783 555 printf("Invalid resolution %d\n", buff[2]&3);
embeddedartists 1:47680ec5d783 556 break;
embeddedartists 1:47680ec5d783 557 }
embeddedartists 1:47680ec5d783 558 *type = buff[2]>>2;
embeddedartists 1:47680ec5d783 559 }
embeddedartists 1:47680ec5d783 560 return (res == 0);
embeddedartists 1:47680ec5d783 561 }
embeddedartists 1:47680ec5d783 562