diff options
-rw-r--r-- | drivers/spi/spi_topcliff_pch.c | 502 |
1 files changed, 138 insertions, 364 deletions
diff --git a/drivers/spi/spi_topcliff_pch.c b/drivers/spi/spi_topcliff_pch.c index 58b183f6eec0..97746232741e 100644 --- a/drivers/spi/spi_topcliff_pch.c +++ b/drivers/spi/spi_topcliff_pch.c | |||
@@ -1,8 +1,6 @@ | |||
1 | /* | 1 | /* |
2 | * SPI bus driver for the Topcliff PCH used by Intel SoCs | 2 | * SPI bus driver for the Topcliff PCH used by Intel SoCs |
3 | */ | 3 | * |
4 | |||
5 | /* | ||
6 | * Copyright (C) 2010 OKI SEMICONDUCTOR Co., LTD. | 4 | * Copyright (C) 2010 OKI SEMICONDUCTOR Co., LTD. |
7 | * | 5 | * |
8 | * This program is free software; you can redistribute it and/or modify | 6 | * This program is free software; you can redistribute it and/or modify |
@@ -19,6 +17,7 @@ | |||
19 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. | 17 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. |
20 | */ | 18 | */ |
21 | 19 | ||
20 | #include <linux/delay.h> | ||
22 | #include <linux/pci.h> | 21 | #include <linux/pci.h> |
23 | #include <linux/wait.h> | 22 | #include <linux/wait.h> |
24 | #include <linux/spi/spi.h> | 23 | #include <linux/spi/spi.h> |
@@ -45,17 +44,7 @@ | |||
45 | 44 | ||
46 | #define PCH_RX_THOLD 7 | 45 | #define PCH_RX_THOLD 7 |
47 | #define PCH_RX_THOLD_MAX 15 | 46 | #define PCH_RX_THOLD_MAX 15 |
48 | #define PCH_RX 1 | ||
49 | #define PCH_TX 2 | ||
50 | |||
51 | /* various interrupts */ | ||
52 | #define PCH_TFI 0x1 | ||
53 | #define PCH_RFI 0x2 | ||
54 | #define PCH_FI 0x4 | ||
55 | #define PCH_ORI 0x8 | ||
56 | #define PCH_MDFI 0x10 | ||
57 | 47 | ||
58 | #define PCH_ALL (PCH_TFI|PCH_RFI|PCH_FI|PCH_ORI|PCH_MDFI) | ||
59 | #define PCH_MAX_BAUDRATE 5000000 | 48 | #define PCH_MAX_BAUDRATE 5000000 |
60 | #define PCH_MAX_FIFO_DEPTH 16 | 49 | #define PCH_MAX_FIFO_DEPTH 16 |
61 | 50 | ||
@@ -86,6 +75,8 @@ | |||
86 | #define SPSR_FI_BIT (1 << 2) | 75 | #define SPSR_FI_BIT (1 << 2) |
87 | #define SPBRR_SIZE_BIT (1 << 10) | 76 | #define SPBRR_SIZE_BIT (1 << 10) |
88 | 77 | ||
78 | #define PCH_ALL (SPCR_TFIE_BIT|SPCR_RFIE_BIT|SPCR_FIE_BIT|SPCR_ORIE_BIT|SPCR_MDFIE_BIT) | ||
79 | |||
89 | #define SPCR_RFIC_FIELD 20 | 80 | #define SPCR_RFIC_FIELD 20 |
90 | #define SPCR_TFIC_FIELD 16 | 81 | #define SPCR_TFIC_FIELD 16 |
91 | 82 | ||
@@ -176,16 +167,6 @@ static struct pci_device_id pch_spi_pcidev_id[] = { | |||
176 | {0,} | 167 | {0,} |
177 | }; | 168 | }; |
178 | 169 | ||
179 | static inline void pch_set_bitmsk(u32 *var, u32 bitmask) | ||
180 | { | ||
181 | *var |= bitmask; | ||
182 | } | ||
183 | |||
184 | static inline void pch_clr_bitmsk(u32 *var, u32 bitmask) | ||
185 | { | ||
186 | *var &= (~(bitmask)); | ||
187 | } | ||
188 | |||
189 | /** | 170 | /** |
190 | * pch_spi_writereg() - Performs register writes | 171 | * pch_spi_writereg() - Performs register writes |
191 | * @master: Pointer to struct spi_master. | 172 | * @master: Pointer to struct spi_master. |
@@ -194,9 +175,7 @@ static inline void pch_clr_bitmsk(u32 *var, u32 bitmask) | |||
194 | */ | 175 | */ |
195 | static inline void pch_spi_writereg(struct spi_master *master, int idx, u32 val) | 176 | static inline void pch_spi_writereg(struct spi_master *master, int idx, u32 val) |
196 | { | 177 | { |
197 | |||
198 | struct pch_spi_data *data = spi_master_get_devdata(master); | 178 | struct pch_spi_data *data = spi_master_get_devdata(master); |
199 | |||
200 | iowrite32(val, (data->io_remap_addr + idx)); | 179 | iowrite32(val, (data->io_remap_addr + idx)); |
201 | } | 180 | } |
202 | 181 | ||
@@ -208,19 +187,9 @@ static inline void pch_spi_writereg(struct spi_master *master, int idx, u32 val) | |||
208 | static inline u32 pch_spi_readreg(struct spi_master *master, int idx) | 187 | static inline u32 pch_spi_readreg(struct spi_master *master, int idx) |
209 | { | 188 | { |
210 | struct pch_spi_data *data = spi_master_get_devdata(master); | 189 | struct pch_spi_data *data = spi_master_get_devdata(master); |
211 | |||
212 | return ioread32(data->io_remap_addr + idx); | 190 | return ioread32(data->io_remap_addr + idx); |
213 | } | 191 | } |
214 | 192 | ||
215 | /* ope==true:Set bit, ope==false:Clear bit */ | ||
216 | static inline void pch_spi_setclr_bit(u32 *val, u32 pos, bool ope) | ||
217 | { | ||
218 | if (ope) | ||
219 | *val |= pos; | ||
220 | else | ||
221 | *val &= (~(pos)); | ||
222 | } | ||
223 | |||
224 | static inline void pch_spi_setclr_reg(struct spi_master *master, int idx, | 193 | static inline void pch_spi_setclr_reg(struct spi_master *master, int idx, |
225 | u32 set, u32 clr) | 194 | u32 set, u32 clr) |
226 | { | 195 | { |
@@ -229,7 +198,6 @@ static inline void pch_spi_setclr_reg(struct spi_master *master, int idx, | |||
229 | pch_spi_writereg(master, idx, tmp); | 198 | pch_spi_writereg(master, idx, tmp); |
230 | } | 199 | } |
231 | 200 | ||
232 | |||
233 | static void pch_spi_set_master_mode(struct spi_master *master) | 201 | static void pch_spi_set_master_mode(struct spi_master *master) |
234 | { | 202 | { |
235 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_MSTR_BIT, 0); | 203 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_MSTR_BIT, 0); |
@@ -245,35 +213,6 @@ static void pch_spi_clear_fifo(struct spi_master *master) | |||
245 | pch_spi_setclr_reg(master, PCH_SPCR, 0, SPCR_FICLR_BIT); | 213 | pch_spi_setclr_reg(master, PCH_SPCR, 0, SPCR_FICLR_BIT); |
246 | } | 214 | } |
247 | 215 | ||
248 | /** | ||
249 | * ch_spi_disable_interrupts() - Disables specified interrupts | ||
250 | * @master: Pointer to struct spi_master. | ||
251 | * @interrupt: Interrups to be enabled. | ||
252 | */ | ||
253 | static void pch_spi_disable_interrupts(struct spi_master *master, u8 interrupt) | ||
254 | { | ||
255 | u32 clr_flags = 0; | ||
256 | |||
257 | if (interrupt & PCH_RFI) | ||
258 | clr_flags |= SPCR_RFIE_BIT; | ||
259 | |||
260 | if (interrupt & PCH_TFI) | ||
261 | clr_flags |= SPCR_TFIE_BIT; | ||
262 | |||
263 | if (interrupt & PCH_FI) | ||
264 | clr_flags |= SPCR_FIE_BIT; | ||
265 | |||
266 | if (interrupt & PCH_ORI) | ||
267 | clr_flags |= SPCR_ORIE_BIT; | ||
268 | |||
269 | if (interrupt & PCH_MDFI) | ||
270 | clr_flags |= SPCR_MDFIE_BIT; | ||
271 | |||
272 | pch_spi_setclr_reg(master, PCH_SPCR, 0, clr_flags); | ||
273 | |||
274 | dev_dbg(&master->dev, "%s clearing bits =%x\n", __func__, clr_flags); | ||
275 | } | ||
276 | |||
277 | static void pch_spi_handler_sub(struct pch_spi_data *data, u32 reg_spsr_val, | 216 | static void pch_spi_handler_sub(struct pch_spi_data *data, u32 reg_spsr_val, |
278 | void __iomem *io_remap_addr) | 217 | void __iomem *io_remap_addr) |
279 | { | 218 | { |
@@ -309,9 +248,7 @@ static void pch_spi_handler_sub(struct pch_spi_data *data, u32 reg_spsr_val, | |||
309 | /* disable RFI if not needed */ | 248 | /* disable RFI if not needed */ |
310 | if ((bpw_len - rx_index) <= PCH_MAX_FIFO_DEPTH) { | 249 | if ((bpw_len - rx_index) <= PCH_MAX_FIFO_DEPTH) { |
311 | reg_spcr_val = ioread32(io_remap_addr + PCH_SPCR); | 250 | reg_spcr_val = ioread32(io_remap_addr + PCH_SPCR); |
312 | 251 | reg_spcr_val &= ~SPCR_RFIE_BIT; /* disable RFI */ | |
313 | /* disable RFI */ | ||
314 | pch_clr_bitmsk(®_spcr_val, SPCR_RFIE_BIT); | ||
315 | 252 | ||
316 | /* reset rx threshold */ | 253 | /* reset rx threshold */ |
317 | reg_spcr_val &= MASK_RFIC_SPCR_BITS; | 254 | reg_spcr_val &= MASK_RFIC_SPCR_BITS; |
@@ -329,7 +266,8 @@ static void pch_spi_handler_sub(struct pch_spi_data *data, u32 reg_spsr_val, | |||
329 | /* if transfer complete interrupt */ | 266 | /* if transfer complete interrupt */ |
330 | if (reg_spsr_val & SPSR_FI_BIT) { | 267 | if (reg_spsr_val & SPSR_FI_BIT) { |
331 | /* disable FI & RFI interrupts */ | 268 | /* disable FI & RFI interrupts */ |
332 | pch_spi_disable_interrupts(data->master, PCH_FI | PCH_RFI); | 269 | pch_spi_setclr_reg(data->master, PCH_SPCR, 0, |
270 | SPCR_FIE_BIT | SPCR_TFIE_BIT); | ||
333 | 271 | ||
334 | /* transfer is completed;inform pch_spi_process_messages */ | 272 | /* transfer is completed;inform pch_spi_process_messages */ |
335 | data->transfer_complete = true; | 273 | data->transfer_complete = true; |
@@ -337,7 +275,6 @@ static void pch_spi_handler_sub(struct pch_spi_data *data, u32 reg_spsr_val, | |||
337 | } | 275 | } |
338 | } | 276 | } |
339 | 277 | ||
340 | |||
341 | /** | 278 | /** |
342 | * pch_spi_handler() - Interrupt handler | 279 | * pch_spi_handler() - Interrupt handler |
343 | * @irq: The interrupt number. | 280 | * @irq: The interrupt number. |
@@ -350,7 +287,6 @@ static irqreturn_t pch_spi_handler(int irq, void *dev_id) | |||
350 | void __iomem *spsr; | 287 | void __iomem *spsr; |
351 | void __iomem *io_remap_addr; | 288 | void __iomem *io_remap_addr; |
352 | irqreturn_t ret = IRQ_NONE; | 289 | irqreturn_t ret = IRQ_NONE; |
353 | |||
354 | struct pch_spi_board_data *board_dat = dev_id; | 290 | struct pch_spi_board_data *board_dat = dev_id; |
355 | 291 | ||
356 | if (board_dat->suspend_sts) { | 292 | if (board_dat->suspend_sts) { |
@@ -366,7 +302,6 @@ static irqreturn_t pch_spi_handler(int irq, void *dev_id) | |||
366 | reg_spsr_val = ioread32(spsr); | 302 | reg_spsr_val = ioread32(spsr); |
367 | 303 | ||
368 | /* Check if the interrupt is for SPI device */ | 304 | /* Check if the interrupt is for SPI device */ |
369 | |||
370 | if (reg_spsr_val & (SPSR_FI_BIT | SPSR_RFI_BIT)) { | 305 | if (reg_spsr_val & (SPSR_FI_BIT | SPSR_RFI_BIT)) { |
371 | pch_spi_handler_sub(data, reg_spsr_val, io_remap_addr); | 306 | pch_spi_handler_sub(data, reg_spsr_val, io_remap_addr); |
372 | ret = IRQ_HANDLED; | 307 | ret = IRQ_HANDLED; |
@@ -385,12 +320,9 @@ static irqreturn_t pch_spi_handler(int irq, void *dev_id) | |||
385 | */ | 320 | */ |
386 | static void pch_spi_set_baud_rate(struct spi_master *master, u32 speed_hz) | 321 | static void pch_spi_set_baud_rate(struct spi_master *master, u32 speed_hz) |
387 | { | 322 | { |
388 | u32 n_spbr; | 323 | u32 n_spbr = PCH_CLOCK_HZ / (speed_hz * 2); |
389 | |||
390 | n_spbr = PCH_CLOCK_HZ / (speed_hz * 2); | ||
391 | 324 | ||
392 | /* if baud rate is less than we can support limit it */ | 325 | /* if baud rate is less than we can support limit it */ |
393 | |||
394 | if (n_spbr > PCH_MAX_SPBR) | 326 | if (n_spbr > PCH_MAX_SPBR) |
395 | n_spbr = PCH_MAX_SPBR; | 327 | n_spbr = PCH_MAX_SPBR; |
396 | 328 | ||
@@ -417,106 +349,30 @@ static void pch_spi_set_bits_per_word(struct spi_master *master, | |||
417 | */ | 349 | */ |
418 | static void pch_spi_setup_transfer(struct spi_device *spi) | 350 | static void pch_spi_setup_transfer(struct spi_device *spi) |
419 | { | 351 | { |
420 | u32 reg_spcr_val; | 352 | u32 flags = 0; |
421 | 353 | ||
422 | dev_dbg(&spi->dev, "%s SPBRR content =%x setting baud rate=%d\n", | 354 | dev_dbg(&spi->dev, "%s SPBRR content =%x setting baud rate=%d\n", |
423 | __func__, pch_spi_readreg(spi->master, PCH_SPBRR), | 355 | __func__, pch_spi_readreg(spi->master, PCH_SPBRR), |
424 | spi->max_speed_hz); | 356 | spi->max_speed_hz); |
425 | |||
426 | pch_spi_set_baud_rate(spi->master, spi->max_speed_hz); | 357 | pch_spi_set_baud_rate(spi->master, spi->max_speed_hz); |
427 | 358 | ||
428 | /* set bits per word */ | 359 | /* set bits per word */ |
429 | pch_spi_set_bits_per_word(spi->master, spi->bits_per_word); | 360 | pch_spi_set_bits_per_word(spi->master, spi->bits_per_word); |
430 | 361 | ||
431 | if (spi->mode & SPI_LSB_FIRST) | 362 | if (!(spi->mode & SPI_LSB_FIRST)) |
432 | pch_spi_setclr_reg(spi->master, PCH_SPCR, 0, SPCR_LSBF_BIT); | 363 | flags |= SPCR_LSBF_BIT; |
433 | else | ||
434 | pch_spi_setclr_reg(spi->master, PCH_SPCR, SPCR_LSBF_BIT, 0); | ||
435 | |||
436 | if (spi->mode & SPI_CPOL) | 364 | if (spi->mode & SPI_CPOL) |
437 | pch_spi_setclr_reg(spi->master, PCH_SPCR, SPCR_CPOL_BIT, 0); | 365 | flags |= SPCR_CPOL_BIT; |
438 | else | ||
439 | pch_spi_setclr_reg(spi->master, PCH_SPCR, 0, SPCR_CPOL_BIT); | ||
440 | |||
441 | if (spi->mode & SPI_CPHA) | 366 | if (spi->mode & SPI_CPHA) |
442 | pch_spi_setclr_reg(spi->master, PCH_SPCR, SPCR_CPHA_BIT, 0); | 367 | flags |= SPCR_CPHA_BIT; |
443 | else | 368 | pch_spi_setclr_reg(spi->master, PCH_SPCR, flags, |
444 | pch_spi_setclr_reg(spi->master, PCH_SPCR, 0, SPCR_CPHA_BIT); | 369 | (SPCR_LSBF_BIT | SPCR_CPOL_BIT | SPCR_CPHA_BIT)); |
445 | |||
446 | dev_dbg(&spi->dev, | ||
447 | "%s SPCR content after setting LSB/MSB and MODE= %x\n", | ||
448 | __func__, reg_spcr_val); | ||
449 | 370 | ||
450 | /* Clear the FIFO by toggling FICLR to 1 and back to 0 */ | 371 | /* Clear the FIFO by toggling FICLR to 1 and back to 0 */ |
451 | pch_spi_clear_fifo(spi->master); | 372 | pch_spi_clear_fifo(spi->master); |
452 | } | 373 | } |
453 | 374 | ||
454 | /** | 375 | /** |
455 | * pch_spi_enable_interrupts() - Enables specified interrupts | ||
456 | * @master: Pointer to struct spi_master. | ||
457 | * @interrupt: Interrups to be enabled. | ||
458 | */ | ||
459 | static void pch_spi_enable_interrupts(struct spi_master *master, u8 interrupt) | ||
460 | { | ||
461 | u32 reg_val_spcr; | ||
462 | |||
463 | dev_dbg(&master->dev, "%s SPCR content=%x\n", __func__, reg_val_spcr); | ||
464 | |||
465 | if (interrupt & PCH_RFI) { | ||
466 | /* set RFIE bit in SPCR */ | ||
467 | dev_dbg(&master->dev, "setting RFI in %s\n", __func__); | ||
468 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_RFIE_BIT, 0); | ||
469 | } | ||
470 | |||
471 | if (interrupt & PCH_TFI) { | ||
472 | /* set TFIE bit in SPCR */ | ||
473 | dev_dbg(&master->dev, "setting TFI in %s\n", __func__); | ||
474 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_TFIE_BIT, 0); | ||
475 | } | ||
476 | |||
477 | if (interrupt & PCH_FI) { | ||
478 | /* set FIE bit in SPCR */ | ||
479 | dev_dbg(&master->dev, "setting FI in %s\n", __func__); | ||
480 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_FIE_BIT, 0); | ||
481 | } | ||
482 | |||
483 | if (interrupt & PCH_ORI) { | ||
484 | /* set ORIE bit in SPCR */ | ||
485 | dev_dbg(&master->dev, "setting ORI in %s\n", __func__); | ||
486 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_ORIE_BIT, 0); | ||
487 | } | ||
488 | |||
489 | if (interrupt & PCH_MDFI) { | ||
490 | /* set MODFIE bit in SPCR */ | ||
491 | dev_dbg(&master->dev, "setting MDFI in %s\n", __func__); | ||
492 | pch_spi_setclr_reg(master, PCH_SPCR, SPCR_MDFIE_BIT, 0); | ||
493 | } | ||
494 | } | ||
495 | |||
496 | /** | ||
497 | * pch_spi_set_threshold() - Sets Tx/Rx FIFO thresholds | ||
498 | * @spi: Pointer to struct spi_device. | ||
499 | * @threshold: Threshold value to be set. | ||
500 | * @dir: Rx or Tx threshold to be set. | ||
501 | */ | ||
502 | static void pch_spi_set_threshold(struct spi_device *spi, u32 threshold, u8 dir) | ||
503 | { | ||
504 | |||
505 | if (dir == PCH_RX) { | ||
506 | dev_dbg(&spi->dev, "%s setting Rx threshold\n", __func__); | ||
507 | pch_spi_setclr_reg(spi->master, PCH_SPCR, | ||
508 | threshold << SPCR_RFIC_FIELD, | ||
509 | ~MASK_RFIC_SPCR_BITS); | ||
510 | |||
511 | } else if (dir == PCH_TX) { | ||
512 | dev_dbg(&spi->dev, "%s setting Tx threshold\n", __func__); | ||
513 | pch_spi_setclr_reg(spi->master, PCH_SPCR, | ||
514 | (threshold << SPCR_TFIC_FIELD) , | ||
515 | ~MASK_TFIC_SPCR_BITS); | ||
516 | } | ||
517 | } | ||
518 | |||
519 | /** | ||
520 | * pch_spi_reset() - Clears SPI registers | 376 | * pch_spi_reset() - Clears SPI registers |
521 | * @master: Pointer to struct spi_master. | 377 | * @master: Pointer to struct spi_master. |
522 | */ | 378 | */ |
@@ -532,13 +388,12 @@ static void pch_spi_reset(struct spi_master *master) | |||
532 | static int pch_spi_setup(struct spi_device *pspi) | 388 | static int pch_spi_setup(struct spi_device *pspi) |
533 | { | 389 | { |
534 | /* check bits per word */ | 390 | /* check bits per word */ |
535 | if ((pspi->bits_per_word) == 0) { | 391 | if (pspi->bits_per_word == 0) { |
536 | pspi->bits_per_word = 8; | 392 | pspi->bits_per_word = 8; |
537 | dev_dbg(&pspi->dev, "%s 8 bits per word\n", __func__); | 393 | dev_dbg(&pspi->dev, "%s 8 bits per word\n", __func__); |
538 | } | 394 | } |
539 | 395 | ||
540 | if (((pspi->bits_per_word) != 8) && | 396 | if ((pspi->bits_per_word != 8) && (pspi->bits_per_word != 16)) { |
541 | ((pspi->bits_per_word != 16))) { | ||
542 | dev_err(&pspi->dev, "%s Invalid bits per word\n", __func__); | 397 | dev_err(&pspi->dev, "%s Invalid bits per word\n", __func__); |
543 | return -EINVAL; | 398 | return -EINVAL; |
544 | } | 399 | } |
@@ -550,7 +405,7 @@ static int pch_spi_setup(struct spi_device *pspi) | |||
550 | pspi->max_speed_hz = PCH_MAX_BAUDRATE; | 405 | pspi->max_speed_hz = PCH_MAX_BAUDRATE; |
551 | 406 | ||
552 | dev_dbg(&pspi->dev, "%s MODE = %x\n", __func__, | 407 | dev_dbg(&pspi->dev, "%s MODE = %x\n", __func__, |
553 | ((pspi->mode) & (SPI_CPOL | SPI_CPHA))); | 408 | (pspi->mode) & (SPI_CPOL | SPI_CPHA)); |
554 | 409 | ||
555 | return 0; | 410 | return 0; |
556 | } | 411 | } |
@@ -564,17 +419,15 @@ static int pch_spi_transfer(struct spi_device *pspi, struct spi_message *pmsg) | |||
564 | unsigned long flags; | 419 | unsigned long flags; |
565 | 420 | ||
566 | /* validate spi message and baud rate */ | 421 | /* validate spi message and baud rate */ |
567 | if (unlikely((list_empty(&pmsg->transfers) == 1) || | 422 | if (unlikely(list_empty(&pmsg->transfers) == 1)) { |
568 | (pspi->max_speed_hz == 0))) { | 423 | dev_err(&pspi->dev, "%s list empty\n", __func__); |
569 | if (list_empty(&pmsg->transfers) == 1) | 424 | retval = -EINVAL; |
570 | dev_err(&pspi->dev, "%s list empty\n", __func__); | 425 | goto err_out; |
571 | 426 | } | |
572 | if ((pspi->max_speed_hz) == 0) { | ||
573 | dev_err(&pspi->dev, "%s pch_spi_tranfer maxspeed=%d\n", | ||
574 | __func__, pspi->max_speed_hz); | ||
575 | } | ||
576 | dev_err(&pspi->dev, "%s returning EINVAL\n", __func__); | ||
577 | 427 | ||
428 | if (unlikely(pspi->max_speed_hz == 0)) { | ||
429 | dev_err(&pspi->dev, "%s pch_spi_tranfer maxspeed=%d\n", | ||
430 | __func__, pspi->max_speed_hz); | ||
578 | retval = -EINVAL; | 431 | retval = -EINVAL; |
579 | goto err_out; | 432 | goto err_out; |
580 | } | 433 | } |
@@ -582,32 +435,28 @@ static int pch_spi_transfer(struct spi_device *pspi, struct spi_message *pmsg) | |||
582 | dev_dbg(&pspi->dev, "%s Transfer List not empty. " | 435 | dev_dbg(&pspi->dev, "%s Transfer List not empty. " |
583 | "Transfer Speed is set.\n", __func__); | 436 | "Transfer Speed is set.\n", __func__); |
584 | 437 | ||
585 | spin_lock_irqsave(&data->lock, flags); | ||
586 | |||
587 | /* validate Tx/Rx buffers and Transfer length */ | 438 | /* validate Tx/Rx buffers and Transfer length */ |
588 | list_for_each_entry(transfer, &pmsg->transfers, transfer_list) { | 439 | list_for_each_entry(transfer, &pmsg->transfers, transfer_list) { |
589 | if ((!(transfer->tx_buf)) && (!(transfer->rx_buf))) { | 440 | if (!transfer->tx_buf && !transfer->rx_buf) { |
590 | dev_err(&pspi->dev, | 441 | dev_err(&pspi->dev, |
591 | "%s Tx and Rx buffer NULL\n", __func__); | 442 | "%s Tx and Rx buffer NULL\n", __func__); |
592 | retval = -EINVAL; | 443 | retval = -EINVAL; |
593 | goto err_return_spinlock; | 444 | goto err_out; |
594 | } | 445 | } |
595 | 446 | ||
596 | if (!(transfer->len)) { | 447 | if (!transfer->len) { |
597 | dev_err(&pspi->dev, "%s Transfer length invalid\n", | 448 | dev_err(&pspi->dev, "%s Transfer length invalid\n", |
598 | __func__); | 449 | __func__); |
599 | retval = -EINVAL; | 450 | retval = -EINVAL; |
600 | goto err_return_spinlock; | 451 | goto err_out; |
601 | } | 452 | } |
602 | 453 | ||
603 | dev_dbg(&pspi->dev, "%s Tx/Rx buffer valid. Transfer length" | 454 | dev_dbg(&pspi->dev, "%s Tx/Rx buffer valid. Transfer length" |
604 | " valid\n", __func__); | 455 | " valid\n", __func__); |
605 | 456 | ||
606 | /* if baud rate hs been specified validate the same */ | 457 | /* if baud rate hs been specified validate the same */ |
607 | if (transfer->speed_hz) { | 458 | if (transfer->speed_hz > PCH_MAX_BAUDRATE) |
608 | if ((transfer->speed_hz) > PCH_MAX_BAUDRATE) | 459 | transfer->speed_hz = PCH_MAX_BAUDRATE; |
609 | transfer->speed_hz = PCH_MAX_BAUDRATE; | ||
610 | } | ||
611 | 460 | ||
612 | /* if bits per word has been specified validate the same */ | 461 | /* if bits per word has been specified validate the same */ |
613 | if (transfer->bits_per_word) { | 462 | if (transfer->bits_per_word) { |
@@ -616,14 +465,15 @@ static int pch_spi_transfer(struct spi_device *pspi, struct spi_message *pmsg) | |||
616 | retval = -EINVAL; | 465 | retval = -EINVAL; |
617 | dev_err(&pspi->dev, | 466 | dev_err(&pspi->dev, |
618 | "%s Invalid bits per word\n", __func__); | 467 | "%s Invalid bits per word\n", __func__); |
619 | goto err_return_spinlock; | 468 | goto err_out; |
620 | } | 469 | } |
621 | } | 470 | } |
622 | } | 471 | } |
623 | 472 | ||
624 | /* We won't process any messages if we have been asked to terminate */ | 473 | spin_lock_irqsave(&data->lock, flags); |
625 | 474 | ||
626 | if (STATUS_EXITING == (data->status)) { | 475 | /* We won't process any messages if we have been asked to terminate */ |
476 | if (data->status == STATUS_EXITING) { | ||
627 | dev_err(&pspi->dev, "%s status = STATUS_EXITING.\n", __func__); | 477 | dev_err(&pspi->dev, "%s status = STATUS_EXITING.\n", __func__); |
628 | retval = -ESHUTDOWN; | 478 | retval = -ESHUTDOWN; |
629 | goto err_return_spinlock; | 479 | goto err_return_spinlock; |
@@ -631,27 +481,23 @@ static int pch_spi_transfer(struct spi_device *pspi, struct spi_message *pmsg) | |||
631 | 481 | ||
632 | /* If suspended ,return -EINVAL */ | 482 | /* If suspended ,return -EINVAL */ |
633 | if (data->board_dat->suspend_sts) { | 483 | if (data->board_dat->suspend_sts) { |
634 | dev_err(&pspi->dev, | 484 | dev_err(&pspi->dev, "%s suspend; returning EINVAL\n", __func__); |
635 | "%s bSuspending= true returning EINVAL\n", __func__); | ||
636 | retval = -EINVAL; | 485 | retval = -EINVAL; |
637 | goto err_return_spinlock; | 486 | goto err_return_spinlock; |
638 | } | 487 | } |
639 | 488 | ||
640 | /* set status of message */ | 489 | /* set status of message */ |
641 | pmsg->actual_length = 0; | 490 | pmsg->actual_length = 0; |
642 | |||
643 | dev_dbg(&pspi->dev, "%s - pmsg->status =%d\n", __func__, pmsg->status); | 491 | dev_dbg(&pspi->dev, "%s - pmsg->status =%d\n", __func__, pmsg->status); |
644 | 492 | ||
645 | pmsg->status = -EINPROGRESS; | 493 | pmsg->status = -EINPROGRESS; |
646 | 494 | ||
647 | /* add message to queue */ | 495 | /* add message to queue */ |
648 | list_add_tail(&pmsg->queue, &data->queue); | 496 | list_add_tail(&pmsg->queue, &data->queue); |
649 | |||
650 | dev_dbg(&pspi->dev, "%s - Invoked list_add_tail\n", __func__); | 497 | dev_dbg(&pspi->dev, "%s - Invoked list_add_tail\n", __func__); |
651 | 498 | ||
652 | /* schedule work queue to run */ | 499 | /* schedule work queue to run */ |
653 | queue_work(data->wk, &data->work); | 500 | queue_work(data->wk, &data->work); |
654 | |||
655 | dev_dbg(&pspi->dev, "%s - Invoked queue work\n", __func__); | 501 | dev_dbg(&pspi->dev, "%s - Invoked queue work\n", __func__); |
656 | 502 | ||
657 | retval = 0; | 503 | retval = 0; |
@@ -666,10 +512,9 @@ err_out: | |||
666 | static inline void pch_spi_select_chip(struct pch_spi_data *data, | 512 | static inline void pch_spi_select_chip(struct pch_spi_data *data, |
667 | struct spi_device *pspi) | 513 | struct spi_device *pspi) |
668 | { | 514 | { |
669 | if ((data->current_chip) != NULL) { | 515 | if (data->current_chip != NULL) { |
670 | if ((pspi->chip_select) != (data->n_curnt_chip)) { | 516 | if (pspi->chip_select != data->n_curnt_chip) { |
671 | dev_dbg(&pspi->dev, | 517 | dev_dbg(&pspi->dev, "%s : different slave\n", __func__); |
672 | "%s : different slave-Invoking\n", __func__); | ||
673 | data->current_chip = NULL; | 518 | data->current_chip = NULL; |
674 | } | 519 | } |
675 | } | 520 | } |
@@ -683,9 +528,8 @@ static inline void pch_spi_select_chip(struct pch_spi_data *data, | |||
683 | } | 528 | } |
684 | 529 | ||
685 | static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, | 530 | static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, |
686 | struct spi_message **ppmsg) | 531 | struct spi_message **ppmsg) |
687 | { | 532 | { |
688 | int b_mem_fail; | ||
689 | int size; | 533 | int size; |
690 | u32 n_writes; | 534 | u32 n_writes; |
691 | int j; | 535 | int j; |
@@ -697,20 +541,16 @@ static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, | |||
697 | 541 | ||
698 | /* set baud rate if needed */ | 542 | /* set baud rate if needed */ |
699 | if (data->cur_trans->speed_hz) { | 543 | if (data->cur_trans->speed_hz) { |
700 | dev_dbg(&data->master->dev, | 544 | dev_dbg(&data->master->dev, "%s:setting baud rate\n", __func__); |
701 | "%s:pctrldatasetting baud rate\n", __func__); | 545 | pch_spi_set_baud_rate(data->master, data->cur_trans->speed_hz); |
702 | pch_spi_set_baud_rate(data->master, | ||
703 | (data->cur_trans->speed_hz)); | ||
704 | } | 546 | } |
705 | 547 | ||
706 | /* set bits per word if needed */ | 548 | /* set bits per word if needed */ |
707 | if ((data->cur_trans->bits_per_word) && | 549 | if (data->cur_trans->bits_per_word && |
708 | ((data->current_msg->spi->bits_per_word) != | 550 | (data->current_msg->spi->bits_per_word != data->cur_trans->bits_per_word)) { |
709 | (data->cur_trans->bits_per_word))) { | 551 | dev_dbg(&data->master->dev, "%s:set bits per word\n", __func__); |
710 | dev_dbg(&data->master->dev, | ||
711 | "%s:setting bits per word\n", __func__); | ||
712 | pch_spi_set_bits_per_word(data->master, | 552 | pch_spi_set_bits_per_word(data->master, |
713 | (data->cur_trans->bits_per_word)); | 553 | data->cur_trans->bits_per_word); |
714 | *bpw = data->cur_trans->bits_per_word; | 554 | *bpw = data->cur_trans->bits_per_word; |
715 | } else { | 555 | } else { |
716 | *bpw = data->current_msg->spi->bits_per_word; | 556 | *bpw = data->current_msg->spi->bits_per_word; |
@@ -721,28 +561,21 @@ static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, | |||
721 | data->rx_index = 0; | 561 | data->rx_index = 0; |
722 | 562 | ||
723 | data->bpw_len = data->cur_trans->len / (*bpw / 8); | 563 | data->bpw_len = data->cur_trans->len / (*bpw / 8); |
724 | b_mem_fail = false; | ||
725 | 564 | ||
726 | /* find alloc size */ | 565 | /* find alloc size */ |
727 | size = (data->cur_trans->len) * (sizeof(*(data->pkt_tx_buff))); | 566 | size = data->cur_trans->len * sizeof(*data->pkt_tx_buff); |
567 | |||
728 | /* allocate memory for pkt_tx_buff & pkt_rx_buffer */ | 568 | /* allocate memory for pkt_tx_buff & pkt_rx_buffer */ |
729 | data->pkt_tx_buff = kzalloc(size, GFP_KERNEL); | 569 | data->pkt_tx_buff = kzalloc(size, GFP_KERNEL); |
730 | |||
731 | if (data->pkt_tx_buff != NULL) { | 570 | if (data->pkt_tx_buff != NULL) { |
732 | data->pkt_rx_buff = kzalloc(size, GFP_KERNEL); | 571 | data->pkt_rx_buff = kzalloc(size, GFP_KERNEL); |
733 | 572 | if (!data->pkt_rx_buff) | |
734 | if (data->pkt_rx_buff == NULL) { | ||
735 | b_mem_fail = true; | ||
736 | kfree(data->pkt_tx_buff); | 573 | kfree(data->pkt_tx_buff); |
737 | } | ||
738 | } else { | ||
739 | b_mem_fail = true; | ||
740 | } | 574 | } |
741 | 575 | ||
742 | if (b_mem_fail) { | 576 | if (!data->pkt_rx_buff) { |
743 | /* flush queue and set status of all transfers to -ENOMEM */ | 577 | /* flush queue and set status of all transfers to -ENOMEM */ |
744 | dev_err(&data->master->dev, | 578 | dev_err(&data->master->dev, "%s :kzalloc failed\n", __func__); |
745 | "Kzalloc fail in %s messages\n", __func__); | ||
746 | list_for_each_entry(pmsg, data->queue.next, queue) { | 579 | list_for_each_entry(pmsg, data->queue.next, queue) { |
747 | pmsg->status = -ENOMEM; | 580 | pmsg->status = -ENOMEM; |
748 | 581 | ||
@@ -752,39 +585,33 @@ static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, | |||
752 | /* delete from queue */ | 585 | /* delete from queue */ |
753 | list_del_init(&pmsg->queue); | 586 | list_del_init(&pmsg->queue); |
754 | } | 587 | } |
755 | |||
756 | return; | 588 | return; |
757 | } | 589 | } |
758 | 590 | ||
759 | /* copy Tx Data */ | 591 | /* copy Tx Data */ |
760 | if ((data->cur_trans->tx_buf) != NULL) { | 592 | if (data->cur_trans->tx_buf != NULL) { |
761 | if (*bpw == 8) { | 593 | if (*bpw == 8) { |
762 | for (j = 0; j < (data->bpw_len); j++) { | 594 | tx_buf = data->cur_trans->tx_buf; |
763 | tx_buf = data->cur_trans->tx_buf; | 595 | for (j = 0; j < data->bpw_len; j++) |
764 | data->pkt_tx_buff[j] = tx_buf[j]; | 596 | data->pkt_tx_buff[j] = *tx_buf++; |
765 | } | ||
766 | } else { | 597 | } else { |
767 | for (j = 0; j < (data->bpw_len); j++) { | 598 | tx_sbuf = data->cur_trans->tx_buf; |
768 | tx_sbuf = data->cur_trans->tx_buf; | 599 | for (j = 0; j < data->bpw_len; j++) |
769 | data->pkt_tx_buff[j] = tx_sbuf[j]; | 600 | data->pkt_tx_buff[j] = *tx_sbuf++; |
770 | } | ||
771 | } | 601 | } |
772 | } | 602 | } |
773 | 603 | ||
774 | /* if len greater than PCH_MAX_FIFO_DEPTH, write 16,else len bytes */ | 604 | /* if len greater than PCH_MAX_FIFO_DEPTH, write 16,else len bytes */ |
775 | if ((data->bpw_len) > PCH_MAX_FIFO_DEPTH) | 605 | n_writes = data->bpw_len; |
606 | if (n_writes > PCH_MAX_FIFO_DEPTH) | ||
776 | n_writes = PCH_MAX_FIFO_DEPTH; | 607 | n_writes = PCH_MAX_FIFO_DEPTH; |
777 | else | ||
778 | n_writes = (data->bpw_len); | ||
779 | 608 | ||
780 | dev_dbg(&data->master->dev, "\n%s:Pulling down SSN low - writing " | 609 | dev_dbg(&data->master->dev, "\n%s:Pulling down SSN low - writing " |
781 | "0x2 to SSNXCR\n", __func__); | 610 | "0x2 to SSNXCR\n", __func__); |
782 | pch_spi_writereg(data->master, PCH_SSNXCR, SSN_LOW); | 611 | pch_spi_writereg(data->master, PCH_SSNXCR, SSN_LOW); |
783 | 612 | ||
784 | for (j = 0; j < n_writes; j++) { | 613 | for (j = 0; j < n_writes; j++) |
785 | pch_spi_writereg(data->master, PCH_SPDWR, | 614 | pch_spi_writereg(data->master, PCH_SPDWR, data->pkt_tx_buff[j]); |
786 | data->pkt_tx_buff[j]); | ||
787 | } | ||
788 | 615 | ||
789 | /* update tx_index */ | 616 | /* update tx_index */ |
790 | data->tx_index = j; | 617 | data->tx_index = j; |
@@ -798,13 +625,12 @@ static void pch_spi_set_tx(struct pch_spi_data *data, int *bpw, | |||
798 | static void pch_spi_nomore_transfer(struct pch_spi_data *data, | 625 | static void pch_spi_nomore_transfer(struct pch_spi_data *data, |
799 | struct spi_message *pmsg) | 626 | struct spi_message *pmsg) |
800 | { | 627 | { |
801 | dev_dbg(&data->master->dev, | 628 | dev_dbg(&data->master->dev, "%s called\n", __func__); |
802 | "%s:no more transfers in this message\n", __func__); | ||
803 | /* Invoke complete callback | 629 | /* Invoke complete callback |
804 | [To the spi core..indicating end of transfer] */ | 630 | * [To the spi core..indicating end of transfer] */ |
805 | data->current_msg->status = 0; | 631 | data->current_msg->status = 0; |
806 | 632 | ||
807 | if ((data->current_msg->complete) != 0) { | 633 | if (data->current_msg->complete != 0) { |
808 | dev_dbg(&data->master->dev, | 634 | dev_dbg(&data->master->dev, |
809 | "%s:Invoking callback of SPI core\n", __func__); | 635 | "%s:Invoking callback of SPI core\n", __func__); |
810 | data->current_msg->complete(data->current_msg->context); | 636 | data->current_msg->complete(data->current_msg->context); |
@@ -819,28 +645,26 @@ static void pch_spi_nomore_transfer(struct pch_spi_data *data, | |||
819 | data->current_msg = NULL; | 645 | data->current_msg = NULL; |
820 | data->cur_trans = NULL; | 646 | data->cur_trans = NULL; |
821 | 647 | ||
822 | /* check if we have items in list and not suspending */ | 648 | /* check if we have items in list and not suspending |
823 | /* return 1 if list empty */ | 649 | * return 1 if list empty */ |
824 | if ((list_empty(&data->queue) == 0) && | 650 | if ((list_empty(&data->queue) == 0) && |
825 | (!(data->board_dat->suspend_sts)) | 651 | (!data->board_dat->suspend_sts) && |
826 | && (data->status != STATUS_EXITING)) { | 652 | (data->status != STATUS_EXITING)) { |
827 | /* We have some more work to do (either there is more tranint | 653 | /* We have some more work to do (either there is more tranint |
828 | bpw;sfer requests in the current message or there are | 654 | * bpw;sfer requests in the current message or there are |
829 | more messages) | 655 | *more messages) |
830 | */ | 656 | */ |
831 | dev_dbg(&data->master->dev, | 657 | dev_dbg(&data->master->dev, "%s:Invoke queue_work\n", __func__); |
832 | "%s:we have pending messages-Invoking queue_work\n", | ||
833 | __func__); | ||
834 | queue_work(data->wk, &data->work); | 658 | queue_work(data->wk, &data->work); |
835 | } else if ((data->board_dat->suspend_sts) || | 659 | } else if (data->board_dat->suspend_sts || |
836 | (data->status == STATUS_EXITING)) { | 660 | data->status == STATUS_EXITING) { |
837 | dev_dbg(&data->master->dev, | 661 | dev_dbg(&data->master->dev, |
838 | "%s suspend/remove initiated, flushing queue\n", | 662 | "%s suspend/remove initiated, flushing queue\n", |
839 | __func__); | 663 | __func__); |
840 | list_for_each_entry(pmsg, data->queue.next, queue) { | 664 | list_for_each_entry(pmsg, data->queue.next, queue) { |
841 | pmsg->status = -EIO; | 665 | pmsg->status = -EIO; |
842 | 666 | ||
843 | if (pmsg->complete != 0) | 667 | if (pmsg->complete) |
844 | pmsg->complete(pmsg->context); | 668 | pmsg->complete(pmsg->context); |
845 | 669 | ||
846 | /* delete from queue */ | 670 | /* delete from queue */ |
@@ -851,30 +675,29 @@ static void pch_spi_nomore_transfer(struct pch_spi_data *data, | |||
851 | 675 | ||
852 | static void pch_spi_set_ir(struct pch_spi_data *data) | 676 | static void pch_spi_set_ir(struct pch_spi_data *data) |
853 | { | 677 | { |
854 | u32 reg_spcr_val; | ||
855 | |||
856 | /* enable interrupts */ | 678 | /* enable interrupts */ |
857 | if ((data->bpw_len) > PCH_MAX_FIFO_DEPTH) { | 679 | if ((data->bpw_len) > PCH_MAX_FIFO_DEPTH) { |
858 | /* set receive threhold to PCH_RX_THOLD */ | 680 | /* set receive threhold to PCH_RX_THOLD */ |
859 | pch_spi_set_threshold(data->current_chip, PCH_RX_THOLD, PCH_RX); | 681 | pch_spi_setclr_reg(data->master, PCH_SPCR, |
682 | PCH_RX_THOLD << SPCR_TFIC_FIELD, | ||
683 | ~MASK_TFIC_SPCR_BITS); | ||
860 | /* enable FI and RFI interrupts */ | 684 | /* enable FI and RFI interrupts */ |
861 | pch_spi_enable_interrupts(data->master, PCH_RFI | PCH_FI); | 685 | pch_spi_setclr_reg(data->master, PCH_SPCR, |
686 | SPCR_RFIE_BIT | SPCR_TFIE_BIT, 0); | ||
862 | } else { | 687 | } else { |
863 | /* set receive threhold to maximum */ | 688 | /* set receive threhold to maximum */ |
864 | pch_spi_set_threshold(data->current_chip, PCH_RX_THOLD_MAX, | 689 | pch_spi_setclr_reg(data->master, PCH_SPCR, |
865 | PCH_RX); | 690 | PCH_RX_THOLD_MAX << SPCR_TFIC_FIELD, |
691 | ~MASK_TFIC_SPCR_BITS); | ||
866 | /* enable FI interrupt */ | 692 | /* enable FI interrupt */ |
867 | pch_spi_enable_interrupts(data->master, PCH_FI); | 693 | pch_spi_setclr_reg(data->master, PCH_SPCR, SPCR_FIE_BIT, 0); |
868 | } | 694 | } |
869 | 695 | ||
870 | dev_dbg(&data->master->dev, | 696 | dev_dbg(&data->master->dev, |
871 | "%s:invoking pch_spi_set_enable to enable SPI\n", __func__); | 697 | "%s:invoking pch_spi_set_enable to enable SPI\n", __func__); |
872 | 698 | ||
873 | /* SPI set enable */ | 699 | /* SPI set enable */ |
874 | reg_spcr_val = pch_spi_readreg(data->current_chip->master, PCH_SPCR); | 700 | pch_spi_setclr_reg(data->current_chip->master, PCH_SPCR, SPCR_SPE_BIT, 0); |
875 | pch_set_bitmsk(®_spcr_val, SPCR_SPE_BIT); | ||
876 | pch_spi_writereg(data->current_chip->master, PCH_SPCR, reg_spcr_val); | ||
877 | |||
878 | 701 | ||
879 | /* Wait until the transfer completes; go to sleep after | 702 | /* Wait until the transfer completes; go to sleep after |
880 | initiating the transfer. */ | 703 | initiating the transfer. */ |
@@ -893,9 +716,9 @@ static void pch_spi_set_ir(struct pch_spi_data *data) | |||
893 | 716 | ||
894 | /* clear all interrupts */ | 717 | /* clear all interrupts */ |
895 | pch_spi_writereg(data->master, PCH_SPSR, | 718 | pch_spi_writereg(data->master, PCH_SPSR, |
896 | (pch_spi_readreg(data->master, PCH_SPSR))); | 719 | pch_spi_readreg(data->master, PCH_SPSR)); |
897 | /* disable interrupts */ | 720 | /* disable interrupts */ |
898 | pch_spi_disable_interrupts(data->master, PCH_ALL); | 721 | pch_spi_setclr_reg(data->master, PCH_SPCR, 0, PCH_ALL); |
899 | } | 722 | } |
900 | 723 | ||
901 | static void pch_spi_copy_rx_data(struct pch_spi_data *data, int bpw) | 724 | static void pch_spi_copy_rx_data(struct pch_spi_data *data, int bpw) |
@@ -905,19 +728,17 @@ static void pch_spi_copy_rx_data(struct pch_spi_data *data, int bpw) | |||
905 | u16 *rx_sbuf; | 728 | u16 *rx_sbuf; |
906 | 729 | ||
907 | /* copy Rx Data */ | 730 | /* copy Rx Data */ |
908 | if (!(data->cur_trans->rx_buf)) | 731 | if (!data->cur_trans->rx_buf) |
909 | return; | 732 | return; |
910 | 733 | ||
911 | if (bpw == 8) { | 734 | if (bpw == 8) { |
912 | for (j = 0; j < (data->bpw_len); j++) { | 735 | rx_buf = data->cur_trans->rx_buf; |
913 | rx_buf = data->cur_trans->rx_buf; | 736 | for (j = 0; j < data->bpw_len; j++) |
914 | rx_buf[j] = (data->pkt_rx_buff[j]) & 0xFF; | 737 | *rx_buf++ = data->pkt_rx_buff[j] & 0xFF; |
915 | } | ||
916 | } else { | 738 | } else { |
917 | for (j = 0; j < (data->bpw_len); j++) { | 739 | rx_sbuf = data->cur_trans->rx_buf; |
918 | rx_sbuf = data->cur_trans->rx_buf; | 740 | for (j = 0; j < data->bpw_len; j++) |
919 | rx_sbuf[j] = data->pkt_rx_buff[j]; | 741 | *rx_sbuf++ = data->pkt_rx_buff[j]; |
920 | } | ||
921 | } | 742 | } |
922 | } | 743 | } |
923 | 744 | ||
@@ -925,20 +746,20 @@ static void pch_spi_copy_rx_data(struct pch_spi_data *data, int bpw) | |||
925 | static void pch_spi_process_messages(struct work_struct *pwork) | 746 | static void pch_spi_process_messages(struct work_struct *pwork) |
926 | { | 747 | { |
927 | struct spi_message *pmsg; | 748 | struct spi_message *pmsg; |
749 | struct pch_spi_data *data; | ||
928 | int bpw; | 750 | int bpw; |
929 | 751 | ||
930 | struct pch_spi_data *data = | ||
931 | container_of(pwork, struct pch_spi_data, work); | ||
932 | dev_dbg(&data->master->dev, "%s data initialized\n", __func__); | 752 | dev_dbg(&data->master->dev, "%s data initialized\n", __func__); |
753 | data = container_of(pwork, struct pch_spi_data, work); | ||
933 | 754 | ||
934 | spin_lock(&data->lock); | 755 | spin_lock(&data->lock); |
935 | 756 | ||
936 | /* check if suspend has been initiated;if yes flush queue */ | 757 | /* check if suspend has been initiated;if yes flush queue */ |
937 | if ((data->board_dat->suspend_sts) || | 758 | if (data->board_dat->suspend_sts || (data->status == STATUS_EXITING)) { |
938 | (data->status == STATUS_EXITING)) { | ||
939 | dev_dbg(&data->master->dev, | 759 | dev_dbg(&data->master->dev, |
940 | "%s suspend/remove initiated,flushing queue\n", | 760 | "%s suspend/remove initiated,flushing queue\n", |
941 | __func__); | 761 | __func__); |
762 | |||
942 | list_for_each_entry(pmsg, data->queue.next, queue) { | 763 | list_for_each_entry(pmsg, data->queue.next, queue) { |
943 | pmsg->status = -EIO; | 764 | pmsg->status = -EIO; |
944 | 765 | ||
@@ -961,8 +782,8 @@ static void pch_spi_process_messages(struct work_struct *pwork) | |||
961 | "%s Set data->bcurrent_msg_processing= true\n", __func__); | 782 | "%s Set data->bcurrent_msg_processing= true\n", __func__); |
962 | 783 | ||
963 | /* Get the message from the queue and delete it from there. */ | 784 | /* Get the message from the queue and delete it from there. */ |
964 | data->current_msg = | 785 | data->current_msg = list_entry(data->queue.next, struct spi_message, |
965 | list_entry(data->queue.next, struct spi_message, queue); | 786 | queue); |
966 | 787 | ||
967 | list_del_init(&data->current_msg->queue); | 788 | list_del_init(&data->current_msg->queue); |
968 | 789 | ||
@@ -1044,7 +865,7 @@ static void pch_spi_process_messages(struct work_struct *pwork) | |||
1044 | 865 | ||
1045 | spin_unlock(&data->lock); | 866 | spin_unlock(&data->lock); |
1046 | 867 | ||
1047 | } while ((data->cur_trans) != NULL); | 868 | } while (data->cur_trans != NULL); |
1048 | } | 869 | } |
1049 | 870 | ||
1050 | static void pch_spi_free_resources(struct pch_spi_board_data *board_dat) | 871 | static void pch_spi_free_resources(struct pch_spi_board_data *board_dat) |
@@ -1063,14 +884,11 @@ static void pch_spi_free_resources(struct pch_spi_board_data *board_dat) | |||
1063 | /* disable interrupts & free IRQ */ | 884 | /* disable interrupts & free IRQ */ |
1064 | if (board_dat->irq_reg_sts) { | 885 | if (board_dat->irq_reg_sts) { |
1065 | /* disable interrupts */ | 886 | /* disable interrupts */ |
1066 | pch_spi_disable_interrupts(board_dat->data-> | 887 | pch_spi_setclr_reg(board_dat->data->master, PCH_SPCR, 0, |
1067 | master, PCH_ALL); | 888 | PCH_ALL); |
1068 | dev_dbg(&board_dat->pdev->dev, | ||
1069 | "%s pch_spi_disable_interrupts invoked " | ||
1070 | "successfully\n", __func__); | ||
1071 | 889 | ||
1072 | /* free IRQ */ | 890 | /* free IRQ */ |
1073 | free_irq(board_dat->pdev->irq, (void *)board_dat); | 891 | free_irq(board_dat->pdev->irq, board_dat); |
1074 | 892 | ||
1075 | dev_dbg(&board_dat->pdev->dev, | 893 | dev_dbg(&board_dat->pdev->dev, |
1076 | "%s free_irq invoked successfully\n", __func__); | 894 | "%s free_irq invoked successfully\n", __func__); |
@@ -1079,7 +897,7 @@ static void pch_spi_free_resources(struct pch_spi_board_data *board_dat) | |||
1079 | } | 897 | } |
1080 | 898 | ||
1081 | /* unmap PCI base address */ | 899 | /* unmap PCI base address */ |
1082 | if ((board_dat->data->io_remap_addr) != 0) { | 900 | if (board_dat->data->io_remap_addr != 0) { |
1083 | pci_iounmap(board_dat->pdev, board_dat->data->io_remap_addr); | 901 | pci_iounmap(board_dat->pdev, board_dat->data->io_remap_addr); |
1084 | 902 | ||
1085 | board_dat->data->io_remap_addr = 0; | 903 | board_dat->data->io_remap_addr = 0; |
@@ -1104,26 +922,9 @@ static int pch_spi_get_resources(struct pch_spi_board_data *board_dat) | |||
1104 | int retval; | 922 | int retval; |
1105 | dev_dbg(&board_dat->pdev->dev, "%s ENTRY\n", __func__); | 923 | dev_dbg(&board_dat->pdev->dev, "%s ENTRY\n", __func__); |
1106 | 924 | ||
1107 | /* iniatize queue of pending messages */ | ||
1108 | INIT_LIST_HEAD(&(board_dat->data->queue)); | ||
1109 | |||
1110 | /* initialize spin locks */ | ||
1111 | spin_lock_init(&(board_dat->data->lock)); | ||
1112 | |||
1113 | /* set channel status */ | ||
1114 | board_dat->data->status = STATUS_RUNNING; | ||
1115 | |||
1116 | /* initialize work structure */ | ||
1117 | INIT_WORK(&(board_dat->data->work), | ||
1118 | pch_spi_process_messages); | ||
1119 | |||
1120 | /* initialize wait queues */ | ||
1121 | init_waitqueue_head(&(board_dat->data->wait)); | ||
1122 | |||
1123 | /* create workqueue */ | 925 | /* create workqueue */ |
1124 | board_dat->data->wk = create_singlethread_workqueue(KBUILD_MODNAME); | 926 | board_dat->data->wk = create_singlethread_workqueue(KBUILD_MODNAME); |
1125 | 927 | if (!board_dat->data->wk) { | |
1126 | if ((board_dat->data->wk) == NULL) { | ||
1127 | dev_err(&board_dat->pdev->dev, | 928 | dev_err(&board_dat->pdev->dev, |
1128 | "%s create_singlet hread_workqueue failed\n", __func__); | 929 | "%s create_singlet hread_workqueue failed\n", __func__); |
1129 | retval = -EBUSY; | 930 | retval = -EBUSY; |
@@ -1143,7 +944,6 @@ static int pch_spi_get_resources(struct pch_spi_board_data *board_dat) | |||
1143 | board_dat->pci_req_sts = true; | 944 | board_dat->pci_req_sts = true; |
1144 | 945 | ||
1145 | io_remap_addr = pci_iomap(board_dat->pdev, 1, 0); | 946 | io_remap_addr = pci_iomap(board_dat->pdev, 1, 0); |
1146 | |||
1147 | if (io_remap_addr == 0) { | 947 | if (io_remap_addr == 0) { |
1148 | dev_err(&board_dat->pdev->dev, | 948 | dev_err(&board_dat->pdev->dev, |
1149 | "%s pci_iomap failed\n", __func__); | 949 | "%s pci_iomap failed\n", __func__); |
@@ -1161,7 +961,7 @@ static int pch_spi_get_resources(struct pch_spi_board_data *board_dat) | |||
1161 | 961 | ||
1162 | /* register IRQ */ | 962 | /* register IRQ */ |
1163 | retval = request_irq(board_dat->pdev->irq, pch_spi_handler, | 963 | retval = request_irq(board_dat->pdev->irq, pch_spi_handler, |
1164 | IRQF_SHARED, KBUILD_MODNAME, (void *)board_dat); | 964 | IRQF_SHARED, KBUILD_MODNAME, board_dat); |
1165 | if (retval != 0) { | 965 | if (retval != 0) { |
1166 | dev_err(&board_dat->pdev->dev, | 966 | dev_err(&board_dat->pdev->dev, |
1167 | "%s request_irq failed\n", __func__); | 967 | "%s request_irq failed\n", __func__); |
@@ -1172,8 +972,7 @@ static int pch_spi_get_resources(struct pch_spi_board_data *board_dat) | |||
1172 | __func__, retval); | 972 | __func__, retval); |
1173 | 973 | ||
1174 | board_dat->irq_reg_sts = true; | 974 | board_dat->irq_reg_sts = true; |
1175 | dev_dbg(&board_dat->pdev->dev, | 975 | dev_dbg(&board_dat->pdev->dev, "%s data->irq_reg_sts=true\n", __func__); |
1176 | "%s data->irq_reg_sts=true\n", __func__); | ||
1177 | 976 | ||
1178 | err_return: | 977 | err_return: |
1179 | if (retval != 0) { | 978 | if (retval != 0) { |
@@ -1187,38 +986,6 @@ err_return: | |||
1187 | return retval; | 986 | return retval; |
1188 | } | 987 | } |
1189 | 988 | ||
1190 | static int pch_spi_check_request_pending(struct pch_spi_board_data *board_dat) | ||
1191 | { | ||
1192 | int sts; | ||
1193 | u16 count; | ||
1194 | |||
1195 | count = 500; | ||
1196 | spin_lock(&(board_dat->data->lock)); | ||
1197 | board_dat->data->status = STATUS_EXITING; | ||
1198 | |||
1199 | while ((list_empty(&(board_dat->data->queue)) == 0) && | ||
1200 | (--count)) { | ||
1201 | dev_dbg(&board_dat->pdev->dev, | ||
1202 | "%s :queue not empty\n", __func__); | ||
1203 | spin_unlock(&(board_dat->data->lock)); | ||
1204 | msleep(PCH_SLEEP_TIME); | ||
1205 | spin_lock(&(board_dat->data->lock)); | ||
1206 | } | ||
1207 | |||
1208 | spin_unlock(&(board_dat->data->lock)); | ||
1209 | |||
1210 | if (count) { | ||
1211 | sts = 0; | ||
1212 | dev_dbg(&board_dat->pdev->dev, "%s :queue empty\n", __func__); | ||
1213 | } else { | ||
1214 | sts = -EBUSY; | ||
1215 | } | ||
1216 | |||
1217 | dev_dbg(&board_dat->pdev->dev, "%s : EXIT=%d\n", __func__, sts); | ||
1218 | |||
1219 | return sts; | ||
1220 | } | ||
1221 | |||
1222 | static int pch_spi_probe(struct pci_dev *pdev, const struct pci_device_id *id) | 989 | static int pch_spi_probe(struct pci_dev *pdev, const struct pci_device_id *id) |
1223 | { | 990 | { |
1224 | 991 | ||
@@ -1279,12 +1046,17 @@ static int pch_spi_probe(struct pci_dev *pdev, const struct pci_device_id *id) | |||
1279 | board_dat->data->master = master; | 1046 | board_dat->data->master = master; |
1280 | board_dat->data->n_curnt_chip = 255; | 1047 | board_dat->data->n_curnt_chip = 255; |
1281 | board_dat->data->board_dat = board_dat; | 1048 | board_dat->data->board_dat = board_dat; |
1049 | board_dat->data->status = STATUS_RUNNING; | ||
1050 | |||
1051 | INIT_LIST_HEAD(&board_dat->data->queue); | ||
1052 | spin_lock_init(&board_dat->data->lock); | ||
1053 | INIT_WORK(&board_dat->data->work, pch_spi_process_messages); | ||
1054 | init_waitqueue_head(&board_dat->data->wait); | ||
1282 | 1055 | ||
1283 | /* allocate resources for PCH SPI */ | 1056 | /* allocate resources for PCH SPI */ |
1284 | retval = pch_spi_get_resources(board_dat); | 1057 | retval = pch_spi_get_resources(board_dat); |
1285 | if (retval != 0) { | 1058 | if (retval) { |
1286 | dev_err(&pdev->dev, "%s fail(retval=%d)\n", | 1059 | dev_err(&pdev->dev, "%s fail(retval=%d)\n", __func__, retval); |
1287 | __func__, retval); | ||
1288 | goto err_spi_get_resources; | 1060 | goto err_spi_get_resources; |
1289 | } | 1061 | } |
1290 | 1062 | ||
@@ -1292,7 +1064,7 @@ static int pch_spi_probe(struct pci_dev *pdev, const struct pci_device_id *id) | |||
1292 | __func__, retval); | 1064 | __func__, retval); |
1293 | 1065 | ||
1294 | /* save private data in dev */ | 1066 | /* save private data in dev */ |
1295 | pci_set_drvdata(pdev, (void *)board_dat); | 1067 | pci_set_drvdata(pdev, board_dat); |
1296 | dev_dbg(&pdev->dev, "%s invoked pci_set_drvdata\n", __func__); | 1068 | dev_dbg(&pdev->dev, "%s invoked pci_set_drvdata\n", __func__); |
1297 | 1069 | ||
1298 | /* set master mode */ | 1070 | /* set master mode */ |
@@ -1329,6 +1101,7 @@ err_kmalloc: | |||
1329 | static void pch_spi_remove(struct pci_dev *pdev) | 1101 | static void pch_spi_remove(struct pci_dev *pdev) |
1330 | { | 1102 | { |
1331 | struct pch_spi_board_data *board_dat = pci_get_drvdata(pdev); | 1103 | struct pch_spi_board_data *board_dat = pci_get_drvdata(pdev); |
1104 | int count; | ||
1332 | 1105 | ||
1333 | dev_dbg(&pdev->dev, "%s ENTRY\n", __func__); | 1106 | dev_dbg(&pdev->dev, "%s ENTRY\n", __func__); |
1334 | 1107 | ||
@@ -1338,19 +1111,23 @@ static void pch_spi_remove(struct pci_dev *pdev) | |||
1338 | return; | 1111 | return; |
1339 | } | 1112 | } |
1340 | 1113 | ||
1341 | /* check for any pending messages */ | 1114 | /* check for any pending messages; no action is taken if the queue |
1342 | if ((-EBUSY) == pch_spi_check_request_pending(board_dat)) { | 1115 | * is still full; but at least we tried. Unload anyway */ |
1343 | dev_dbg(&pdev->dev, | 1116 | count = 500; |
1344 | "%s pch_spi_check_request_pending returned" | 1117 | spin_lock(&board_dat->data->lock); |
1345 | " EBUSY\n", __func__); | 1118 | board_dat->data->status = STATUS_EXITING; |
1346 | /* no need to take any particular action; proceed with remove | 1119 | while ((list_empty(&board_dat->data->queue) == 0) && --count) { |
1347 | even though queue is not empty */ | 1120 | dev_dbg(&board_dat->pdev->dev, "%s :queue not empty\n", |
1121 | __func__); | ||
1122 | spin_unlock(&board_dat->data->lock); | ||
1123 | msleep(PCH_SLEEP_TIME); | ||
1124 | spin_lock(&board_dat->data->lock); | ||
1348 | } | 1125 | } |
1126 | spin_unlock(&board_dat->data->lock); | ||
1349 | 1127 | ||
1350 | /* Free resources allocated for PCH SPI */ | 1128 | /* Free resources allocated for PCH SPI */ |
1351 | pch_spi_free_resources(board_dat); | 1129 | pch_spi_free_resources(board_dat); |
1352 | 1130 | ||
1353 | /* Unregister SPI master */ | ||
1354 | spi_unregister_master(board_dat->data->master); | 1131 | spi_unregister_master(board_dat->data->master); |
1355 | 1132 | ||
1356 | /* free memory for private data */ | 1133 | /* free memory for private data */ |
@@ -1401,13 +1178,11 @@ static int pch_spi_suspend(struct pci_dev *pdev, pm_message_t state) | |||
1401 | /* Free IRQ */ | 1178 | /* Free IRQ */ |
1402 | if (board_dat->irq_reg_sts) { | 1179 | if (board_dat->irq_reg_sts) { |
1403 | /* disable all interrupts */ | 1180 | /* disable all interrupts */ |
1404 | pch_spi_disable_interrupts(board_dat->data->master, PCH_ALL); | 1181 | pch_spi_setclr_reg(board_dat->data->master, PCH_SPCR, 0, |
1182 | PCH_ALL); | ||
1405 | pch_spi_reset(board_dat->data->master); | 1183 | pch_spi_reset(board_dat->data->master); |
1406 | dev_dbg(&pdev->dev, | ||
1407 | "%s pch_spi_disable_interrupts invoked successfully\n", | ||
1408 | __func__); | ||
1409 | 1184 | ||
1410 | free_irq(board_dat->pdev->irq, (void *)board_dat); | 1185 | free_irq(board_dat->pdev->irq, board_dat); |
1411 | 1186 | ||
1412 | board_dat->irq_reg_sts = false; | 1187 | board_dat->irq_reg_sts = false; |
1413 | dev_dbg(&pdev->dev, | 1188 | dev_dbg(&pdev->dev, |
@@ -1471,7 +1246,7 @@ static int pch_spi_resume(struct pci_dev *pdev) | |||
1471 | pci_enable_wake(pdev, PCI_D3hot, 0); | 1246 | pci_enable_wake(pdev, PCI_D3hot, 0); |
1472 | 1247 | ||
1473 | /* register IRQ handler */ | 1248 | /* register IRQ handler */ |
1474 | if (!(board->irq_reg_sts)) { | 1249 | if (!board->irq_reg_sts) { |
1475 | /* register IRQ */ | 1250 | /* register IRQ */ |
1476 | retval = request_irq(board->pdev->irq, pch_spi_handler, | 1251 | retval = request_irq(board->pdev->irq, pch_spi_handler, |
1477 | IRQF_SHARED, KBUILD_MODNAME, | 1252 | IRQF_SHARED, KBUILD_MODNAME, |
@@ -1518,7 +1293,6 @@ static int __init pch_spi_init(void) | |||
1518 | } | 1293 | } |
1519 | module_init(pch_spi_init); | 1294 | module_init(pch_spi_init); |
1520 | 1295 | ||
1521 | |||
1522 | static void __exit pch_spi_exit(void) | 1296 | static void __exit pch_spi_exit(void) |
1523 | { | 1297 | { |
1524 | pci_unregister_driver(&pch_spi_pcidev); | 1298 | pci_unregister_driver(&pch_spi_pcidev); |
@@ -1526,4 +1300,4 @@ static void __exit pch_spi_exit(void) | |||
1526 | module_exit(pch_spi_exit); | 1300 | module_exit(pch_spi_exit); |
1527 | 1301 | ||
1528 | MODULE_LICENSE("GPL"); | 1302 | MODULE_LICENSE("GPL"); |
1529 | MODULE_DESCRIPTION("PCH SPI PCI Driver"); | 1303 | MODULE_DESCRIPTION("Topcliff PCH SPI PCI Driver"); |