00001
00038 #include <assert.h>
00039 #include <bitops.h>
00040 #include <spi.h>
00041 #include <board/spi.h>
00042
00066 #ifdef CONFIG_SPI_POLL_MAXLOOPS
00067 # define MAXLOOPS CONFIG_SPI_POLL_MAXLOOPS
00068 #else
00069 # define MAXLOOPS 255
00070 #endif
00071
00078 #if MAXLOOPS < 256
00079 typedef uint8_t maxloops_t;
00080 #else
00081 typedef unsigned int maxloops_t;
00082 #endif
00083
00102 static void spi_poll(struct workqueue_task *task)
00103 {
00104 struct spi_master_polled *spim_poll =
00105 container_of(task, struct spi_master_polled, poll);
00106 struct spi_master *spim = &spim_poll->base;
00107 uint8_t *read;
00108 const uint8_t *write;
00109 uint8_t rx_byte;
00110 uint8_t tx_byte;
00111 maxloops_t i;
00112 size_t residue;
00113 bool read_op;
00114 bool write_op;
00115
00116
00117
00118
00119 residue = spim->residue;
00120 read = spim_poll->read_data;
00121 write = spim_poll->write_data;
00122 read_op = test_bit(SPI_OP_READ, &spim_poll->op);
00123 write_op = test_bit(SPI_OP_WRITE, &spim_poll->op);
00124 i = MAXLOOPS;
00125 tx_byte = 0;
00126
00127
00128 while (residue > 1) {
00129 if (write_op)
00130 tx_byte = *write;
00131 while (i--) {
00132 if (spi_priv_is_int_flag_set(spim)) {
00133 rx_byte = spi_priv_read_data(spim);
00134 spi_priv_write_data(spim, tx_byte);
00135 residue--;
00136 if (read_op)
00137 *read++ = rx_byte;
00138 if (write_op)
00139 write++;
00140 break;
00141 }
00142 }
00143 if (!i)
00144 goto yield;
00145 }
00146
00147
00148 while (i--) {
00149 if (spi_priv_is_int_flag_set(spim)) {
00150 rx_byte = spi_priv_read_data(spim);
00151 if (read_op)
00152 *read = rx_byte;
00153 if (spi_polled_is_buffer_op(spim)) {
00154 spi_polled_sched_next_buffer(spim);
00155 return;
00156 }
00157 spim->residue = 0;
00158 spim->status = STATUS_OK;
00159 workqueue_add_task(&main_workqueue,
00160 spim->nwq.current);
00161 return;
00162 }
00163 }
00164
00165 yield:
00166 spim->residue = residue;
00167 spim_poll->read_data = read;
00168 spim_poll->write_data = write;
00169 spi_polled_sched_poll(spim);
00170 }
00171
00172 static void spi_priv_start(struct spi_master *spim,
00173 uint8_t tx_byte)
00174 {
00175 spi_priv_write_data(spim, tx_byte);
00176 }
00177
00178 void spi_priv_master_setup_device(spi_id_t spi_id, struct spi_device *device,
00179 spi_flags_t flags, unsigned long baud_rate,
00180 board_spi_select_id_t sel_id)
00181 {
00182 spi_priv_master_setup_device_regs(device, flags, baud_rate);
00183 board_spi_init_select(&device->sel, sel_id);
00184 }
00185
00186 void spi_priv_select_device(struct spi_master *master,
00187 struct spi_device *device)
00188 {
00189 spi_priv_select_device_regs(master, device);
00190 board_spi_select_device(master, &device->sel);
00191 }
00192
00193 void spi_priv_deselect_device(struct spi_master *master,
00194 struct spi_device *device)
00195 {
00196 board_spi_deselect_device(master, &device->sel);
00197 spi_priv_deselect_device_regs(master, device);
00198 }
00199
00200 void spi_priv_master_init(spi_id_t spi_id, struct spi_master *spim)
00201 {
00202 spi_polled_master_init(spim, spi_poll, spi_priv_start);
00203 spi_priv_master_init_regs(spi_id, spim);
00204 }
00205