Added a polled exchange function to the SPI driver model, implemented on LPCxxxx SPI drivers.

git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@2302 35acf78f-673a-0410-8e92-d51de3d6d3f4
This commit is contained in:
gdisirio 2010-10-30 11:18:28 +00:00
parent 0cef5f4877
commit a884e58e2c
19 changed files with 221 additions and 108 deletions

View File

@ -47,7 +47,6 @@ static SPIConfig hs_spicfg = {
IOPORT1,
PA_SSEL1,
CR0_DSS8BIT | CR0_FRFSPI | CR0_CLOCKRATE(0),
0,
2
};
@ -57,7 +56,6 @@ static SPIConfig ls_spicfg = {
IOPORT1,
PA_SSEL1,
CR0_DSS8BIT | CR0_FRFSPI | CR0_CLOCKRATE(0),
0,
254
};

View File

@ -24,7 +24,7 @@
/*
* Conversion table from hex digit to 7 segments encoding, bit 5 controls the
* dot.
* 8 = LU, 4 = RL, 2 = D, 1 = RU, 8 = U, 4 = M, 2 = LL, 1 = L.
* 8 = LU, 4 = RL, 2 = D, 1 = RU, 8 = U, 4 = M, 2 = LL, 1 = L.
*/
static uint8_t digits[32] = {
0x24, 0xAF, 0xE0, 0xA2, 0x2B, 0x32, 0x30, 0xA7,
@ -33,14 +33,9 @@ static uint8_t digits[32] = {
0x00, 0x02, 0x01, 0x18, 0x54, 0x88, 0x50, 0x51
};
static void endsend(SPIDriver *spip) {
spiUnselect(spip);
}
/* Maximum speed SPI configuration (1MHz, CPHA=0, CPOL=0).*/
static SPIConfig spicfg = {
endsend,
NULL,
GPIO1,
GPIO1_SPI0SEL,
CR0_DSS8BIT | CR0_FRFSPI | CR0_CLOCKRATE(0),
@ -52,19 +47,13 @@ static SPIConfig spicfg = {
*/
static WORKING_AREA(waThread1, 128);
static msg_t Thread1(void *arg) {
uint8_t i = 0;
(void)arg;
while (TRUE) {
spiSelect(&SPID1);
spiStartSend(&SPID1, 1, &digits[i]);
palClearPad(GPIO0, GPIO0_LED2);
chThdSleepMilliseconds(500);
spiSelect(&SPID1);
spiStartSend(&SPID1, 1, &digits[i | 0x10]);
palSetPad(GPIO0, GPIO0_LED2);
chThdSleepMilliseconds(500);
i = (i + 1) & 15;
}
return 0;
}
@ -105,6 +94,7 @@ static msg_t Thread2(void *arg) {
* on entry.
*/
int main(int argc, char **argv) {
uint8_t i;
(void)argc;
(void)argv;
@ -122,13 +112,22 @@ int main(int argc, char **argv) {
chThdCreateStatic(waThread2, sizeof(waThread2), NORMALPRIO, Thread2, NULL);
/*
* Normal main() thread activity, in this demo it does nothing except
* sleeping in a loop and check the button state.
* Normal main() thread activity, in this demo it updates the 7-segments
* display on the LPCXpresso main board using the SPI driver.
*/
i = 0;
while (TRUE) {
if (!palReadPad(GPIO0, GPIO0_SW3))
TestThread(&SD1);
spiSelect(&SPID1);
spiSend(&SPID1, 1, &digits[i]); /* Non polled method. */
spiUnselect(&SPID1);
chThdSleepMilliseconds(500);
spiSelect(&SPID1);
spiPolledExchange(&SPID1, digits[i | 0x10]); /* Polled method. */
spiUnselect(&SPID1);
chThdSleepMilliseconds(500);
i = (i + 1) & 15;
}
return 0;
}

View File

@ -33,14 +33,9 @@ static uint8_t digits[32] = {
0x00, 0x02, 0x01, 0x18, 0x54, 0x88, 0x50, 0x51
};
static void endsend(SPIDriver *spip) {
spiUnselect(spip);
}
/* Maximum speed SPI configuration (1MHz, CPHA=0, CPOL=0).*/
static SPIConfig spicfg = {
endsend,
NULL,
GPIO1,
GPIO1_SPI0SEL,
CR0_DSS8BIT | CR0_FRFSPI | CR0_CLOCKRATE(0),
@ -52,19 +47,13 @@ static SPIConfig spicfg = {
*/
static WORKING_AREA(waThread1, 128);
static msg_t Thread1(void *arg) {
uint8_t i = 0;
(void)arg;
while (TRUE) {
spiSelect(&SPID1);
spiStartSend(&SPID1, 1, &digits[i]);
palClearPad(GPIO0, GPIO0_LED2);
chThdSleepMilliseconds(500);
spiSelect(&SPID1);
spiStartSend(&SPID1, 1, &digits[i | 0x10]);
palSetPad(GPIO0, GPIO0_LED2);
chThdSleepMilliseconds(500);
i = (i + 1) & 15;
}
return 0;
}
@ -105,6 +94,7 @@ static msg_t Thread2(void *arg) {
* on entry.
*/
int main(int argc, char **argv) {
uint8_t i;
(void)argc;
(void)argv;
@ -122,13 +112,22 @@ int main(int argc, char **argv) {
chThdCreateStatic(waThread2, sizeof(waThread2), NORMALPRIO, Thread2, NULL);
/*
* Normal main() thread activity, in this demo it does nothing except
* sleeping in a loop and check the button state.
* Normal main() thread activity, in this demo it updates the 7-segments
* display on the LPCXpresso main board using the SPI driver.
*/
i = 0;
while (TRUE) {
if (!palReadPad(GPIO0, GPIO0_SW3))
TestThread(&SD1);
spiSelect(&SPID1);
spiSend(&SPID1, 1, &digits[i]); /* Non polled method. */
spiUnselect(&SPID1);
chThdSleepMilliseconds(500);
spiSelect(&SPID1);
spiPolledExchange(&SPID1, digits[i | 0x10]); /* Polled method. */
spiUnselect(&SPID1);
chThdSleepMilliseconds(500);
i = (i + 1) & 15;
}
return 0;
}

View File

@ -5,7 +5,7 @@ Settings: CLK=48, (3 wait states)
*** ChibiOS/RT test suite
***
*** Kernel: 1.5.5unstable
*** Kernel: 2.1.2unstable
*** GCC Version: 4.3.3
*** Architecture: ARMv6-M
*** Core Variant: Cortex-M0
@ -34,6 +34,9 @@ Settings: CLK=48, (3 wait states)
--- Test Case 2.3 (Semaphores, atomic signal-wait)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 2.4 (Binary Semaphores, functionality)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 3.1 (Mutexes, priority enqueuing test)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -85,6 +88,9 @@ Settings: CLK=48, (3 wait states)
--- Test Case 9.2 (Dynamic APIs, threads creation from memory pool)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 9.3 (Dynamic APIs, registry and references)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 10.1 (Queues, input queues)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -92,55 +98,55 @@ Settings: CLK=48, (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.1 (Benchmark, messages #1)
--- Score : 125437 msgs/S, 250874 ctxswc/S
--- Score : 124135 msgs/S, 248270 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.2 (Benchmark, messages #2)
--- Score : 102120 msgs/S, 204240 ctxswc/S
--- Score : 99992 msgs/S, 199984 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.3 (Benchmark, messages #3)
--- Score : 102120 msgs/S, 204240 ctxswc/S
--- Score : 99992 msgs/S, 199984 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.4 (Benchmark, context switch)
--- Score : 384256 ctxswc/S
--- Score : 380432 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.5 (Benchmark, threads, full cycle)
--- Score : 78221 threads/S
--- Score : 80188 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.6 (Benchmark, threads, create only)
--- Score : 105737 threads/S
--- Score : 111404 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.7 (Benchmark, mass reschedule, 5 threads)
--- Score : 31756 reschedules/S, 190536 ctxswc/S
--- Score : 31034 reschedules/S, 186204 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.8 (Benchmark, round robin context switching)
--- Score : 238060 ctxswc/S
--- Score : 253200 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.9 (Benchmark, I/O Queues throughput)
--- Score : 316568 bytes/S
--- Score : 298992 bytes/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.10 (Benchmark, virtual timers set/reset)
--- Score : 355402 timers/S
--- Score : 350196 timers/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.11 (Benchmark, semaphores wait/signal)
--- Score : 607004 wait+signal/S
--- Score : 591948 wait+signal/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.12 (Benchmark, mutexes lock/unlock)
--- Score : 371272 lock+unlock/S
--- Score : 334860 lock+unlock/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.13 (Benchmark, RAM footprint)
--- System: 340 bytes
--- System: 360 bytes
--- Thread: 68 bytes
--- Timer : 20 bytes
--- Semaph: 12 bytes

View File

@ -5,7 +5,7 @@ Settings: CLK=72, (3 wait states)
*** ChibiOS/RT test suite
***
*** Kernel: 1.5.5unstable
*** Kernel: 2.1.2unstable
*** GCC Version: 4.3.3
*** Architecture: ARMv7-M
*** Core Variant: Cortex-M3
@ -34,6 +34,9 @@ Settings: CLK=72, (3 wait states)
--- Test Case 2.3 (Semaphores, atomic signal-wait)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 2.4 (Binary Semaphores, functionality)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 3.1 (Mutexes, priority enqueuing test)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -85,6 +88,9 @@ Settings: CLK=72, (3 wait states)
--- Test Case 9.2 (Dynamic APIs, threads creation from memory pool)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 9.3 (Dynamic APIs, registry and references)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 10.1 (Queues, input queues)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -92,55 +98,55 @@ Settings: CLK=72, (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.1 (Benchmark, messages #1)
--- Score : 246902 msgs/S, 493804 ctxswc/S
--- Score : 241881 msgs/S, 483762 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.2 (Benchmark, messages #2)
--- Score : 199024 msgs/S, 398048 ctxswc/S
--- Score : 196281 msgs/S, 392562 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.3 (Benchmark, messages #3)
--- Score : 199024 msgs/S, 398048 ctxswc/S
--- Score : 196281 msgs/S, 392562 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.4 (Benchmark, context switch)
--- Score : 797224 ctxswc/S
--- Score : 806072 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.5 (Benchmark, threads, full cycle)
--- Score : 154518 threads/S
--- Score : 155163 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.6 (Benchmark, threads, create only)
--- Score : 212574 threads/S
--- Score : 219028 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.7 (Benchmark, mass reschedule, 5 threads)
--- Score : 65262 reschedules/S, 391572 ctxswc/S
--- Score : 63239 reschedules/S, 379434 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.8 (Benchmark, round robin context switching)
--- Score : 476648 ctxswc/S
--- Score : 473392 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.9 (Benchmark, I/O Queues throughput)
--- Score : 521644 bytes/S
--- Score : 482836 bytes/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.10 (Benchmark, virtual timers set/reset)
--- Score : 674724 timers/S
--- Score : 707908 timers/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.11 (Benchmark, semaphores wait/signal)
--- Score : 977676 wait+signal/S
--- Score : 909504 wait+signal/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.12 (Benchmark, mutexes lock/unlock)
--- Score : 662296 lock+unlock/S
--- Score : 588968 lock+unlock/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.13 (Benchmark, RAM footprint)
--- System: 324 bytes
--- System: 360 bytes
--- Thread: 68 bytes
--- Timer : 20 bytes
--- Semaph: 12 bytes

View File

@ -5,8 +5,8 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
*** ChibiOS/RT test suite
***
*** Kernel: 1.5.7unstable
*** GCC Version: 4.5.0
*** Kernel: 2.1.2unstable
*** GCC Version: 4.5.1
*** Architecture: ARM
*** Core Variant: ARM7TDMI
*** Platform: LPC214x
@ -34,6 +34,9 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Test Case 2.3 (Semaphores, atomic signal-wait)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 2.4 (Binary Semaphores, functionality)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 3.1 (Mutexes, priority enqueuing test)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -95,51 +98,51 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.1 (Benchmark, messages #1)
--- Score : 138220 msgs/S, 276440 ctxswc/S
--- Score : 145385 msgs/S, 290770 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.2 (Benchmark, messages #2)
--- Score : 104419 msgs/S, 208838 ctxswc/S
--- Score : 113890 msgs/S, 227780 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.3 (Benchmark, messages #3)
--- Score : 104419 msgs/S, 208838 ctxswc/S
--- Score : 113890 msgs/S, 227780 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.4 (Benchmark, context switch)
--- Score : 460416 ctxswc/S
--- Score : 493760 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.5 (Benchmark, threads, full cycle)
--- Score : 85707 threads/S
--- Score : 89746 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.6 (Benchmark, threads, create only)
--- Score : 124543 threads/S
--- Score : 128237 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.7 (Benchmark, mass reschedule, 5 threads)
--- Score : 33282 reschedules/S, 199692 ctxswc/S
--- Score : 35380 reschedules/S, 212280 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.8 (Benchmark, round robin context switching)
--- Score : 265316 ctxswc/S
--- Score : 276084 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.9 (Benchmark, I/O Queues throughput)
--- Score : 316988 bytes/S
--- Score : 341980 bytes/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.10 (Benchmark, virtual timers set/reset)
--- Score : 335642 timers/S
--- Score : 333360 timers/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.11 (Benchmark, semaphores wait/signal)
--- Score : 585024 wait+signal/S
--- Score : 607412 wait+signal/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.12 (Benchmark, mutexes lock/unlock)
--- Score : 368620 lock+unlock/S
--- Score : 380408 lock+unlock/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.13 (Benchmark, RAM footprint)

View File

@ -5,8 +5,8 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
*** ChibiOS/RT test suite
***
*** Kernel: 1.5.7unstable
*** GCC Version: 4.5.0
*** Kernel: 2.1.2unstable
*** GCC Version: 4.5.1
*** Architecture: ARM
*** Core Variant: ARM7TDMI
*** Platform: LPC214x
@ -34,6 +34,9 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Test Case 2.3 (Semaphores, atomic signal-wait)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 2.4 (Binary Semaphores, functionality)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 3.1 (Mutexes, priority enqueuing test)
--- Result: SUCCESS
----------------------------------------------------------------------------
@ -95,15 +98,15 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.1 (Benchmark, messages #1)
--- Score : 106460 msgs/S, 212920 ctxswc/S
--- Score : 106223 msgs/S, 212446 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.2 (Benchmark, messages #2)
--- Score : 88195 msgs/S, 176390 ctxswc/S
--- Score : 88032 msgs/S, 176064 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.3 (Benchmark, messages #3)
--- Score : 88195 msgs/S, 176390 ctxswc/S
--- Score : 88032 msgs/S, 176064 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.4 (Benchmark, context switch)
@ -111,23 +114,23 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.5 (Benchmark, threads, full cycle)
--- Score : 69580 threads/S
--- Score : 71990 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.6 (Benchmark, threads, create only)
--- Score : 104828 threads/S
--- Score : 110394 threads/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.7 (Benchmark, mass reschedule, 5 threads)
--- Score : 29580 reschedules/S, 177480 ctxswc/S
--- Score : 29290 reschedules/S, 175740 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.8 (Benchmark, round robin context switching)
--- Score : 221556 ctxswc/S
--- Score : 221560 ctxswc/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.9 (Benchmark, I/O Queues throughput)
--- Score : 261124 bytes/S
--- Score : 261396 bytes/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.10 (Benchmark, virtual timers set/reset)
@ -139,7 +142,7 @@ Settings: CCLK=48, MAMCR=2, MAMTIM=3 (3 wait states)
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.12 (Benchmark, mutexes lock/unlock)
--- Score : 260148 lock+unlock/S
--- Score : 244200 lock+unlock/S
--- Result: SUCCESS
----------------------------------------------------------------------------
--- Test Case 11.13 (Benchmark, RAM footprint)

View File

@ -186,6 +186,21 @@ typedef enum {
spi_lld_receive(spip, n, rxbuf); \
}
/**
* @brief Exchanges one frame using a polled wait.
* @details This synchronous function exchanges one frame using a polled
* synchronization method. This function is useful when exchanging
* small amount of data on high speed channels, usually in this
* situation is much more efficient just wait for completion using
* polling than suspending the thread waiting for an interrupt.
* @note This API is implemented as a macro in order to minimize latency.
*
* @param[in] spip pointer to the @p SPIDriver object
* @param[in] frame the data frame to send over the SPI bus
* @return The received data frame from the SPI bus.
*/
#define spiPolledExchange(spip, frame) spi_lld_polled_exchange(spip, frame)
#if SPI_USE_WAIT || defined(__DOXYGEN__)
/**
* @brief Waits for operation completion.

View File

@ -234,13 +234,15 @@ void spi_lld_start(SPIDriver *spip) {
void spi_lld_stop(SPIDriver *spip) {
if (spip->spd_state != SPI_STOP) {
spip->spd_ssp->CR1 = 0;
spip->spd_ssp->CR0 = 0;
spip->spd_ssp->CPSR = 0;
#if LPC11xx_SPI_USE_SSP0
if (&SPID1 == spip) {
LPC_SYSCON->PRESETCTRL &= ~1;
LPC_SYSCON->SYSAHBCLKCTRL &= ~(1 << 11);
LPC_SYSCON->SSP0CLKDIV = 0;
NVICDisableVector(SSP0_IRQn);
return;
}
#endif
#if LPC11xx_SPI_USE_SSP1
@ -249,12 +251,8 @@ void spi_lld_stop(SPIDriver *spip) {
LPC_SYSCON->SYSAHBCLKCTRL &= ~(1 << 18);
LPC_SYSCON->SSP1CLKDIV = 0;
NVICDisableVector(SSP1_IRQn);
return;
}
#endif
spip->spd_ssp->CR1 = 0;
spip->spd_ssp->CR0 = 0;
spip->spd_ssp->CPSR = 0;
}
}
@ -372,6 +370,26 @@ void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf) {
spip->spd_ssp->IMSC = IMSC_ROR | IMSC_RT | IMSC_TX | IMSC_RX;
}
/**
* @brief Exchanges one frame using a polled wait.
* @details This synchronous function exchanges one frame using a polled
* synchronization method. This function is useful when exchanging
* small amount of data on high speed channels, usually in this
* situation is much more efficient just wait for completion using
* polling than suspending the thread waiting for an interrupt.
*
* @param[in] spip pointer to the @p SPIDriver object
* @param[in] frame the data frame to send over the SPI bus
* @return The received data frame from the SPI bus.
*/
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame) {
spip->spd_ssp->DR = (uint32_t)frame;
while ((spip->spd_ssp->SR & SR_RNE) == 0)
;
return (uint16_t)spip->spd_ssp->DR;
}
#endif /* CH_HAL_USE_SPI */
/** @} */

View File

@ -334,6 +334,7 @@ extern "C" {
const void *txbuf, void *rxbuf);
void spi_lld_send(SPIDriver *spip, size_t n, const void *txbuf);
void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf);
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame);
#ifdef __cplusplus
}
#endif

View File

@ -196,18 +196,17 @@ void spi_lld_start(SPIDriver *spip) {
void spi_lld_stop(SPIDriver *spip) {
if (spip->spd_state != SPI_STOP) {
spip->spd_ssp->CR1 = 0;
spip->spd_ssp->CR0 = 0;
spip->spd_ssp->CPSR = 0;
#if LPC13xx_SPI_USE_SSP0
if (&SPID1 == spip) {
LPC_SYSCON->PRESETCTRL &= ~1;
LPC_SYSCON->SYSAHBCLKCTRL &= ~(1 << 11);
LPC_SYSCON->SSPCLKDIV = 0;
NVICDisableVector(SSP_IRQn);
return;
}
#endif
spip->spd_ssp->CR1 = 0;
spip->spd_ssp->CR0 = 0;
spip->spd_ssp->CPSR = 0;
}
}
@ -325,6 +324,26 @@ void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf) {
spip->spd_ssp->IMSC = IMSC_ROR | IMSC_RT | IMSC_TX | IMSC_RX;
}
/**
* @brief Exchanges one frame using a polled wait.
* @details This synchronous function exchanges one frame using a polled
* synchronization method. This function is useful when exchanging
* small amount of data on high speed channels, usually in this
* situation is much more efficient just wait for completion using
* polling than suspending the thread waiting for an interrupt.
*
* @param[in] spip pointer to the @p SPIDriver object
* @param[in] frame the data frame to send over the SPI bus
* @return The received data frame from the SPI bus.
*/
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame) {
spip->spd_ssp->DR = (uint32_t)frame;
while ((spip->spd_ssp->SR & SR_RNE) == 0)
;
return (uint16_t)spip->spd_ssp->DR;
}
#endif /* CH_HAL_USE_SPI */
/** @} */

View File

@ -334,6 +334,7 @@ extern "C" {
const void *txbuf, void *rxbuf);
void spi_lld_send(SPIDriver *spip, size_t n, const void *txbuf);
void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf);
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame);
#ifdef __cplusplus
}
#endif

View File

@ -99,7 +99,7 @@ static void serve_interrupt(SPIDriver *spip) {
(void)ssp->SSP_DR;
if (--spip->spd_rxcnt == 0) {
chDbgAssert(spip->spd_txcnt == 0,
"chSemResetI(), #1", "counter out of synch");
"spi_serve_interrupt(), #1", "counter out of synch");
/* Stops the IRQ sources.*/
ssp->SSP_IMSC = 0;
/* Portable SPI ISR code defined in the high level driver, note, it is
@ -178,7 +178,7 @@ void spi_lld_start(SPIDriver *spip) {
spip->spd_ssp->SSP_ICR = ICR_RT | ICR_ROR;
spip->spd_ssp->SSP_CR0 = spip->spd_config->spc_cr0;
spip->spd_ssp->SSP_CPSR = spip->spd_config->spc_cpsr;
spip->spd_ssp->SSP_CR1 = spip->spd_config->spc_cr1 | CR1_SSE;
spip->spd_ssp->SSP_CR1 = CR1_SSE;
}
/**
@ -191,16 +191,15 @@ void spi_lld_start(SPIDriver *spip) {
void spi_lld_stop(SPIDriver *spip) {
if (spip->spd_state != SPI_STOP) {
spip->spd_ssp->SSP_CR1 = 0;
spip->spd_ssp->SSP_CR0 = 0;
spip->spd_ssp->SSP_CPSR = 0;
#if LPC214x_SPI_USE_SSP
if (&SPID1 == spip) {
PCONP = (PCONP & PCALL) & ~PCSPI1;
VICIntEnClear = INTMASK(SOURCE_SPI1);
}
#endif
spip->spd_ssp->SSP_CR1 = 0;
spip->spd_ssp->SSP_CR0 = 0;
spip->spd_ssp->SSP_CPSR = 0;
PCONP &= ~PCSPI1;
}
}
@ -318,6 +317,26 @@ void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf) {
spip->spd_ssp->SSP_IMSC = IMSC_ROR | IMSC_RT | IMSC_TX | IMSC_RX;
}
/**
* @brief Exchanges one frame using a polled wait.
* @details This synchronous function exchanges one frame using a polled
* synchronization method. This function is useful when exchanging
* small amount of data on high speed channels, usually in this
* situation is much more efficient just wait for completion using
* polling than suspending the thread waiting for an interrupt.
*
* @param[in] spip pointer to the @p SPIDriver object
* @param[in] frame the data frame to send over the SPI bus
* @return The received data frame from the SPI bus.
*/
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame) {
spip->spd_ssp->SSP_DR = (uint32_t)frame;
while ((spip->spd_ssp->SSP_SR & SR_RNE) == 0)
;
return (uint16_t)spip->spd_ssp->SSP_DR;
}
#endif /* CH_HAL_USE_SPI */
/** @} */

View File

@ -116,10 +116,6 @@ typedef struct {
* @brief SSP CR0 initialization data.
*/
uint16_t spc_cr0;
/**
* @brief SSP CR1 initialization data.
*/
uint16_t spc_cr1;
/**
* @brief SSP CPSR initialization data.
*/
@ -205,6 +201,7 @@ extern "C" {
const void *txbuf, void *rxbuf);
void spi_lld_send(SPIDriver *spip, size_t n, const void *txbuf);
void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf);
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame);
#ifdef __cplusplus
}
#endif

View File

@ -173,6 +173,17 @@
#define MMC_POLLING_DELAY 10
#endif
/**
* @brief Uses the SPI polled API for small data transfers.
* @details Polled transfers usually improve performance because it
* saves two context switches and interrupt servicing. Note
* that this option has no effect on large transfers which
* are always performed using DMAs/IRQs.
*/
#if !defined(MMC_USE_SPI_POLLING) || defined(__DOXYGEN__)
#define MMC_USE_SPI_POLLING TRUE
#endif
/*===========================================================================*/
/* PAL driver related settings. */
/*===========================================================================*/

View File

@ -177,6 +177,22 @@ void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf) {
}
/**
* @brief Exchanges one frame using a polled wait.
* @details This synchronous function exchanges one frame using a polled
* synchronization method. This function is useful when exchanging
* small amount of data on high speed channels, usually in this
* situation is much more efficient just wait for completion using
* polling than suspending the thread waiting for an interrupt.
*
* @param[in] spip pointer to the @p SPIDriver object
* @param[in] frame the data frame to send over the SPI bus
* @return The received data frame from the SPI bus.
*/
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame) {
}
#endif /* CH_HAL_USE_SPI */
/** @} */

View File

@ -132,6 +132,7 @@ extern "C" {
const void *txbuf, void *rxbuf);
void spi_lld_send(SPIDriver *spip, size_t n, const void *txbuf);
void spi_lld_receive(SPIDriver *spip, size_t n, void *rxbuf);
uint16_t spi_lld_polled_exchange(SPIDriver *spip, uint16_t frame);
#ifdef __cplusplus
}
#endif

View File

@ -100,10 +100,13 @@
- NEW: New I2C driver model (not complete and no implementations yet).
- NEW: New SPI driver model, the new model supports both synchronous and
asynchronous operations and, in general, simplifies the implementation of the
low level driver. The state diagram changed slightly changed so be careful.
low level driver. The new driver also specifies a simplified polled exchange
API, useful for efficiently sending small amount of data over high speed
connections. The driver state diagram changed slightly changed so be careful.
- NEW: New ADC driver model, the new model supports both synchronous and
asynchronous operations and, in general, simplifies the implementation of the
low level driver. The state diagram changed slightly changed so be careful.
low level driver. The driver state diagram changed slightly changed so be
careful.
- NEW: Improved PWM driver model, added several macros that helps to setup
configuration structures and to specify pulse widths also as percentages or
degrees using a fixed point notation. Added new pwmEnableChannelI() and

View File

@ -43,10 +43,8 @@ X PDF generation from the documentation system (only separate documents, not
a very similar DMA (waiting for the new STM8L-Discovery kit).
- Add the STM32VL to the official STM32 HAL support (waiting for the new
STM32-Discovery kit).
- Add a spiPolledExchange() API to the SPI driver model.
* Add an optional spiPolledExchange() API to the SPI driver model.
- New STM8S/A SPI driver.
X Evaluate a new API for the SPI driver enabling quick transfers of few bytes
in polled mode.
X Except for the above, bug fixing only until the 2.2.0 release.
Within 2.3.x (hopefully)