00001
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047 #include "spi_at32ap7000.h"
00048
00049 int getBaudDiv(spi_options_t * options, int cpuHz);
00050
00051
00056 void spi_reset(volatile avr32_spi_t * spi)
00057 {
00058 spi->cr = AVR32_SPI_CR_SWRST_MASK;
00059 }
00060
00061
00072 int spi_initSlave(volatile avr32_spi_t * spi,
00073 unsigned char bits,
00074 unsigned char spi_mode)
00075 {
00076
00077 spi->cr = (1<<AVR32_SPI_CR_SWRST_OFFSET);
00078
00079
00080
00081 if (bits > 16 || bits < 8) {
00082 return SPI_ERROR_ARGUMENT;
00083 }
00084
00085 spi->csr0 = (bits - 8) << AVR32_SPI_CSR0_BITS_OFFSET;
00086
00087 switch(spi_mode) {
00088 case 0:
00089 spi->csr0 |= (1 << AVR32_SPI_CSR0_NCPHA_OFFSET);
00090 case 1:
00091 break;
00092 case 2:
00093 spi->csr0 |= (1<<AVR32_SPI_CSR0_NCPHA_OFFSET);
00094 case 3:
00095 spi->csr0 |= (1<<AVR32_SPI_CSR0_CPOL_OFFSET);
00096 break;
00097 default:
00098 return SPI_ERROR_ARGUMENT;
00099 }
00100
00101 return SPI_OK;
00102 }
00103
00104
00113 int spi_initTest(volatile avr32_spi_t * spi)
00114 {
00115
00116 spi->cr = (1<<AVR32_SPI_CR_SWRST_OFFSET);
00117
00118 spi->mr |= (1<<AVR32_SPI_MR_MSTR_OFFSET);
00119
00120 spi->mr |= (1<<AVR32_SPI_MR_LLB_OFFSET);
00121
00122 return SPI_OK;
00123 }
00124
00125
00135 int spi_initMaster(volatile avr32_spi_t * spi, spi_options_t * options)
00136 {
00137 if (options->modfdis > 1) {
00138 return SPI_ERROR_ARGUMENT;
00139 }
00140
00141 if (options->fdiv > 1) {
00142 return SPI_ERROR_ARGUMENT;
00143 }
00144
00145
00146 spi->cr = AVR32_SPI_CR_SWRST_MASK;
00147
00148
00149 spi->mr = AVR32_SPI_MR_MSTR_MASK|
00150 (options->fdiv<<AVR32_SPI_MR_FDIV_OFFSET)|
00151 (options->modfdis<<AVR32_SPI_MR_MODFDIS_OFFSET);
00152
00153 return SPI_OK;
00154 }
00155
00156
00170 int spi_selectionMode(volatile avr32_spi_t * spi,
00171 unsigned char variable_ps,
00172 unsigned char pcs_decode,
00173 unsigned char delay)
00174 {
00175 if (variable_ps > 1) {
00176 return SPI_ERROR_ARGUMENT;
00177 }
00178
00179 if (pcs_decode > 1) {
00180 return SPI_ERROR_ARGUMENT;
00181 }
00182
00183 spi->mr |=
00184 (variable_ps<<AVR32_SPI_MR_PS_OFFSET)|
00185 (pcs_decode<<AVR32_SPI_MR_PCSDEC_OFFSET)|
00186 (delay<<AVR32_SPI_MR_DLYBCS_OFFSET);
00187
00188 return SPI_OK;
00189 }
00190
00191
00202 int spi_selectChip(volatile avr32_spi_t * spi, unsigned char chip)
00203 {
00204
00205 spi->mr |= (0xF << AVR32_SPI_MR_PCS_OFFSET);
00206
00207 if ((spi->mr & (1<<AVR32_SPI_MR_PCSDEC_OFFSET)) != 0) {
00208
00209 if (chip > 15) {
00210 return SPI_ERROR_ARGUMENT;
00211 }
00212
00213 spi->mr |= chip << AVR32_SPI_MR_PCS_OFFSET;
00214 } else {
00215 if (chip > 3) {
00216 return SPI_ERROR_ARGUMENT;
00217 }
00218
00219 spi->mr &= ~(1<<(AVR32_SPI_MR_PCS_OFFSET + chip));
00220 }
00221
00222 return SPI_OK;
00223 }
00224
00225
00240 int spi_setupChipReg(volatile avr32_spi_t * spi,
00241 spi_options_t * options,
00242 unsigned int cpuHz)
00243 {
00244 unsigned long csr;
00245
00246 if (options->bits > 16 || options->bits < 8) {
00247 return SPI_ERROR_ARGUMENT;
00248 }
00249
00250 if (options->stay_act > 1) {
00251 return SPI_ERROR_ARGUMENT;
00252 }
00253
00254 int baudDiv = getBaudDiv(options, cpuHz);
00255
00256 if (baudDiv < 0) {
00257 return -baudDiv;
00258 }
00259
00260
00261 csr = ((options->bits - 8)<<AVR32_SPI_CSR0_BITS_OFFSET)|
00262 (baudDiv<<AVR32_SPI_CSR0_SCBR_OFFSET)|
00263 (options->spck_delay<<AVR32_SPI_CSR0_DLYBS_OFFSET)|
00264 (options->trans_delay<<AVR32_SPI_CSR0_DLYBCT_OFFSET)|
00265 (options->stay_act<<AVR32_SPI_CSR0_CSAAT_OFFSET);
00266
00267 switch(options->spi_mode) {
00268 case 0:
00269 csr |= (1<<AVR32_SPI_CSR0_NCPHA_OFFSET);
00270 case 1:
00271 break;
00272 case 2:
00273 csr |= (1<<AVR32_SPI_CSR0_NCPHA_OFFSET);
00274 case 3:
00275 csr |= (1<<AVR32_SPI_CSR0_CPOL_OFFSET);
00276 break;
00277 default:
00278 return SPI_ERROR_ARGUMENT;
00279 }
00280
00281 switch(options->reg) {
00282 case 0:
00283 spi->csr0 = csr;
00284 break;
00285 case 1:
00286 spi->csr1 = csr;
00287 break;
00288 case 2:
00289 spi->csr2 = csr;
00290 break;
00291 case 3:
00292 spi->csr3 = csr;
00293 break;
00294 default:
00295 return SPI_ERROR_ARGUMENT;
00296 }
00297
00298 return SPI_OK;
00299 }
00300
00301
00308 void spi_enable(volatile avr32_spi_t * spi)
00309 {
00310 spi->cr = (1<<AVR32_SPI_CR_SPIEN_OFFSET);
00311 }
00312
00313
00321 void spi_disable(volatile avr32_spi_t * spi)
00322 {
00323 spi->cr = (1<<AVR32_SPI_CR_SPIDIS_OFFSET);
00324 }
00325
00326
00337 int spi_write(volatile avr32_spi_t * spi, unsigned short data)
00338 {
00339 unsigned int timeout = SPI_TIMEOUT;
00340
00341 while ((spi->sr & AVR32_SPI_SR_TXEMPTY_MASK) == 0 && timeout > 0) {
00342 --timeout;
00343 }
00344
00345 if (timeout == 0) {
00346 return SPI_ERROR_TIMEOUT;
00347 }
00348
00349 spi->tdr = data & 0x0000FFFF;
00350
00351 return SPI_OK;
00352 }
00353
00354
00372 int spi_variableSlaveWrite(volatile avr32_spi_t * spi, unsigned short data,
00373 unsigned char pcs, unsigned char lastxfer)
00374 {
00375 unsigned int timeout = SPI_TIMEOUT;
00376
00377 if (pcs > 15 || lastxfer > 1)
00378 return SPI_ERROR_ARGUMENT;
00379
00380 while ((spi->sr & AVR32_SPI_SR_TXEMPTY_MASK) == 0 && --timeout) {
00381 }
00382
00383 if (timeout == 0) {
00384 return SPI_ERROR_TIMEOUT;
00385 }
00386
00387 spi->tdr = (data << AVR32_SPI_TDR_TD_OFFSET) |
00388 (pcs << AVR32_SPI_TDR_PCS_OFFSET) |
00389 (lastxfer << AVR32_SPI_TDR_LASTXFER_OFFSET);
00390
00391 return SPI_OK;
00392 }
00393
00394
00403 unsigned char spi_readRegisterFullCheck(volatile avr32_spi_t * spi)
00404 {
00405 if ((spi->sr & AVR32_SPI_SR_RDRF_MASK) != 0) {
00406 return 1;
00407 } else {
00408 return 0;
00409 }
00410 }
00411
00412
00423 int spi_read(volatile avr32_spi_t * spi, unsigned short * data)
00424 {
00425 unsigned int timeout = SPI_TIMEOUT;
00426
00427 do {
00428 --timeout;
00429 } while ((spi->sr & AVR32_SPI_SR_RDRF_MASK) == 0 && timeout > 0);
00430
00431 if (timeout == 0) {
00432 return SPI_ERROR_TIMEOUT;
00433 }
00434
00435 *data = spi->rdr & 0x0000FFFF;
00436
00437 return SPI_OK;
00438 }
00439
00440
00453 unsigned char spi_getStatus(volatile avr32_spi_t * spi)
00454 {
00455 unsigned char ret = 0;
00456
00457 if ((spi->sr & (1<<AVR32_SPI_SR_OVRES_OFFSET)) != 0) {
00458 ret = SPI_ERROR_OVERRUN;
00459 }
00460
00461 if ((spi->sr & (1<<AVR32_SPI_SR_MODF_OFFSET)) != 0) {
00462 ret += SPI_ERROR_MODE_FAULT;
00463 }
00464
00465 if (ret == (SPI_ERROR_OVERRUN + SPI_ERROR_MODE_FAULT)) {
00466 return SPI_ERROR_OVERRUN_AND_MODE_FAULT;
00467 }
00468 else if (ret > 0) {
00469 return ret;
00470 } else {
00471 return SPI_OK;
00472 }
00473 }
00474
00475
00485 int getBaudDiv(spi_options_t * options, int cpuHz) {
00486 int baudDiv = 0;
00487
00488 if (options->fdiv == 0) {
00489 baudDiv = cpuHz / (options->baudrate);
00490 } else {
00491 baudDiv = cpuHz / (32 * options->baudrate);
00492 }
00493
00494 if (baudDiv > 255 || baudDiv <= 0) {
00495 return -SPI_ERROR_ARGUMENT;
00496 }
00497
00498 return baudDiv;
00499 }
00500