Advertisement
buletz

Untitled

Mar 22nd, 2013
242
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 20.56 KB | None | 0 0
  1. #include <linux/kernel.h> /* Для printk() и т.д. */
  2. #include <linux/module.h> /* Эта частичка древней магии, которая оживляет модули */
  3. #include <linux/init.h> /* Определения макросов */
  4. #include <linux/fs.h>
  5. #include <asm/uaccess.h> /* put_user */
  6. #include <asm/io.h>
  7. //#include <asm/system.h>
  8. #include <linux/ioport.h>
  9. #include <linux/interrupt.h>
  10. #include <linux/dma-mapping.h>
  11. #include <asm/dma.h>
  12. #include <mach/dma.h>
  13. #include <linux/slab.h>
  14.  
  15. #include "mx53.h"
  16. #include "spislave.h"
  17.  
  18. // Ниже мы задаём информацию о модуле, которую можно будет увидеть с помощью Modinfo
  19. MODULE_LICENSE( "GPL" );
  20. MODULE_AUTHOR( "A l e x1 e 2e v __ V &a ?l e r i y" );
  21. MODULE_DESCRIPTION( "Spi slave driver for imx53" );
  22. MODULE_SUPPORTED_DEVICE( "spi" ); /* /dev/testdevice */
  23.  
  24. #define IRQ_NAME "spislave_irq"
  25. #define IRQ_NUMB  37 // ECSPI-2 irq number  
  26. #define DMA_USE  // использовать DMA
  27.  
  28.  
  29. #define SUCCESS 0
  30. #define DEVICE_NAME "spislave" /* Имя нашего устройства */
  31.  
  32. #define INPUT_BUFFER_SIZE  (1*1024*1024)
  33. #define BYTES_IN_FIFO_IRQ_OCCURS    24 // кол-во байт в фифо когда генерится прерывание (макс 32)
  34.  
  35. //#define DEBUG_OUTPUT_ENABLED
  36.  
  37. struct {
  38.     char data [INPUT_BUFFER_SIZE];
  39.     int start;
  40.     int end;
  41.     } inputBuffer;
  42.  
  43. static int maxRxFifoLoad;
  44. static int maxBufferLoad;
  45. static int rxoverflowedCount;
  46. static char locked;  
  47.  
  48. #if defined(DMA_USE)
  49. static  spi_mxc_port umxcport = {
  50.            .dma_rxbuf_size = SPI_DMA_RXBUFSIZE,
  51.            .dma_rx_id = MXC_DMA_CSPI2_RX, //   from /plat-mxc/include/mach/dma.h
  52.             //  MXC_DMA_CSPI2_TX  
  53.         };
  54. static dma_info dma_list;//This holds the DMA channel information
  55. #endif
  56.  
  57. // Поддерживаемые нашим устройством операции
  58. static int device_open( struct inode *, struct file * );
  59. static int device_release( struct inode *, struct file * );
  60. static ssize_t device_read( struct file *, char *, size_t, loff_t * );
  61. static ssize_t device_write( struct file *, const char *, size_t, loff_t * );
  62. static int region_size = 256;
  63.  
  64. // Глобальные переменные, объявлены как static, воизбежание конфликтов имен.
  65. static int major_number; /* Старший номер устройства нашего драйвера */
  66. static int is_device_open = 0; /* Используется ли девайс ? */
  67. static void *spi_base;
  68. static void *gpio2_base;
  69.  
  70. //-------------------------------------------------------------------------------------
  71. // Прописываем обработчики операций на устройством
  72. static struct file_operations fops =
  73.  {
  74.   .read = device_read,
  75.   .write = device_write,
  76.   .open = device_open,
  77.   .release = device_release
  78.  };
  79.  
  80. #if defined(DMA_USE)
  81. //-------------------------------------------------------------------------------------
  82. //--------------------------------DMA STUFF -------------------------------------------
  83. //-------------------------------------------------------------------------------------
  84. //-------------------------------------------------------------------------------------
  85.  
  86.  
  87.  
  88.  
  89. /*!
  90.  * Stops DMA and frees the DMA resources
  91.  *
  92.  * @param   d_info the structure that holds all the DMA information for a
  93.  *                 particular MXC SPI
  94.  * @param   umxc   the MXC SPI port structure, this includes the \b spi_port
  95.  *                 structure and other members that are specific to MXC SPI
  96.  */
  97. static void mxcspi_freedma(dma_info *d_info, spi_mxc_port *umxc)
  98. {
  99.     int i, rxbufs;
  100.     mxc_spi_rxdmamap *rx_buf_elem;
  101.  
  102.     rxbufs = umxc->dma_rxbuf_size / RXDMA_BUFF_SIZE;
  103.  
  104.     for (i = 0; i < rxbufs; i++) {
  105.         rx_buf_elem = (mxc_spi_rxdmamap *) (umxc->rx_dmamap + i);
  106.         dma_free_coherent(NULL, RXDMA_BUFF_SIZE,  rx_buf_elem->rx_buf, rx_buf_elem->rx_handle);
  107.     }
  108.     kfree(umxc->rx_dmamap);
  109.     //kfree(umxc->tx_buf);
  110.     mxc_dma_free(d_info->rd_channel);
  111.     //mxc_dma_free(d_info->wr_channel);
  112. }
  113.  
  114.  
  115. /*!
  116.  * The read DMA callback, this method is called when the DMA buffer has received its
  117.  * data. This functions copies the data to the tty buffer and updates the tty buffer
  118.  * pointers. It also queues the DMA buffer back to the DMA system.
  119.  *
  120.  * @param   arg   driver private data
  121.  * @param   error any DMA error
  122.  * @param   cnt   amount of data that was transferred
  123.  */
  124. static void mxcspi_dmaread_callback(void *arg, int error, unsigned int cnt)
  125. {
  126. printk(KERN_ERR "\nSPI: DMA READ CALLBACK\n");
  127.  
  128.     spi_mxc_port *umxc = arg;
  129.     //struct tty_struct *tty = umxc->port.state->port.tty;
  130.     int buff_id, num_bufs, rd_cnt;
  131.     mxc_dma_requestbuf_t readchnl_request;
  132.     mxc_spi_rxdmamap *rx_buf_elem = NULL;
  133.     unsigned int sr1, sr2;
  134.     char flag;
  135.  
  136.     //rx_buf_elem = NULL;  // << DELETE(???!!!)
  137.     //char flag;
  138.  
  139.     num_bufs = umxc->dma_rxbuf_size / RXDMA_BUFF_SIZE;
  140.     // Clear the aging timer bit
  141.     //writel(MXC_U A RTUSR1_AGTIM, umxc->port.membase + MXC_ U ARTUSR1);
  142.  
  143.     buff_id = umxc->dma_rxbuf_id;
  144.     //flag = TTY_NORMAL;
  145.  
  146.     umxc->dma_rxbuf_id += 1;
  147.     if (umxc->dma_rxbuf_id >= num_bufs)
  148.         {
  149.         umxc->dma_rxbuf_id = 0;
  150.         }
  151.    
  152.  
  153.     rx_buf_elem = (mxc_spi_rxdmamap *) (umxc->rx_dmamap + buff_id);
  154.  
  155.     if (error == MXC_DMA_TRANSFER_ERROR)
  156.         {
  157.         printk(KERN_ERR "SPI: DMA_ERROR: sr1:%x sr2:%x\n", sr1, sr2);
  158.         // By default clearing all error bits in status reg
  159.          // removed
  160.         }
  161.  
  162.     //rd_cnt = tty_insert_flip_string(tty, rx_buf_elem->rx_buf, cnt);
  163.     //umxc->port.icount.rx += rd_cnt;
  164.  
  165. /*
  166.     if (flag != TTY_NORMAL)
  167.         tty_insert_flip_char(tty, 0, flag);
  168.  
  169.     tty_flip_buffer_push(tty);
  170.     umxc->port.state->port.tty->real_raw = 1;
  171.         */
  172.        
  173. char s[256];
  174. char t[256];
  175. int i;
  176. printk (KERN_ERR "\ndata read count=%d:\n ", cnt);
  177. //printk (KERN_ERR "rxbuf pointer=%08X\n", &rx_buf_elem->rx_buf[0]);
  178.  
  179. char *p = rx_buf_elem->rx_buf;
  180. for (i=0; i<64; i++)
  181.     {
  182.     sprintf (t, "%02X ",rx_buf_elem->rx_buf[i]);
  183.     strcat (s,t);
  184.     }
  185. printk (KERN_ERR "%s", s);
  186.  
  187.       drop_data:
  188.     readchnl_request.src_addr = (ECSPI2_BASE+ECSPI2_RXDATA); //umxc->port.mapbase;
  189.     //readchnl_request.src_addr = umxc->mapbase+ ECSPI2_RXDATA;
  190.     readchnl_request.dst_addr = rx_buf_elem->rx_handle;
  191.     readchnl_request.num_of_bytes = RXDMA_BUFF_SIZE;
  192.     mxc_dma_config(dma_list.rd_channel, &readchnl_request, 1, MXC_DMA_MODE_READ);
  193.     mxc_dma_enable(dma_list.rd_channel);
  194.  
  195. /*
  196. */
  197. }
  198.  
  199. /*!
  200.  * Allocates DMA read and write channels, creates DMA read and write buffers and
  201.  * sets the channel specific parameters.
  202.  *
  203.  * @param   d_info the structure that holds all the DMA information for a
  204.  *                 particular MXC SPI
  205.  * @param   umxc   the MXC SPI port structure, this includes the
  206.  *
  207.  * @return  The function returns 0 on success and a non-zero value on failure.
  208.  */
  209. static int mxcspi_initdma(dma_info *d_info)
  210. {
  211.  
  212.     int rxbufs, i, j;
  213.     spi_mxc_port  * umxc = &umxcport;
  214.    
  215.     umxc->mapbase = spi_base; // ioremap(ECSPI2_BASE, 0x80);
  216.  
  217.     mxc_dma_requestbuf_t *readchnl_reqelem;
  218. //* mxc_dma_requestbuf_t -       an array of physical addresses to the user defined
  219. //*                     buffers. The caller must guarantee the dma_buf is
  220. //*                     available until the transfer is completed.
  221.    
  222.     mxc_spi_rxdmamap *rx_buf_elem;
  223.  
  224.  
  225.     int ret = 0;
  226.     // Request for the read channels
  227.     printk(KERN_ERR "\nMXC SPI: Start init dma, dma_rx_id=%d\n", umxc->dma_rx_id);
  228.     d_info->rd_channel = mxc_dma_request(umxc->dma_rx_id, "MXC SPI2 Read");
  229.     if (d_info->rd_channel < 0)
  230.         {
  231.         printk(KERN_ERR "\nMXC SPI: Cannot allocate DMA read channel\n");
  232.         return -1;
  233.         }
  234.     printk(KERN_ERR "\nMXC SPI: dma_rxbuf_size = %d\n", umxc->dma_rxbuf_size); 
  235.     rxbufs = umxc->dma_rxbuf_size / RXDMA_BUFF_SIZE;
  236.    
  237.     /* Allocate the DMA Virtual Receive Buffer */
  238.     umxc->rx_dmamap = kmalloc(rxbufs * sizeof(mxc_spi_rxdmamap), GFP_KERNEL);
  239.     if (umxc->rx_dmamap == NULL)
  240.         {
  241.         ret = -1;
  242.         goto err_dma_rx_buff; //err_dma_rx_buff;
  243.         }
  244.  
  245.     printk(KERN_ERR "\nMXC SPI: DMA virtual receive buffer allocated");
  246.    
  247.     /* Allocate the DMA Receive Request structures */
  248.     readchnl_reqelem = kmalloc(rxbufs * sizeof(mxc_dma_requestbuf_t),  GFP_KERNEL);
  249.     if (readchnl_reqelem == NULL)
  250.         {
  251.         ret = -1;
  252.         goto err_request;
  253.         }
  254.     printk(KERN_ERR "\nMXC SPI: DMA receive request structures allocated, rxbufs=%d\n", rxbufs);
  255.  
  256.     for (i = 0; i < rxbufs; i++)
  257.         {
  258.         rx_buf_elem = (mxc_spi_rxdmamap *) (umxc->rx_dmamap + i);
  259.         rx_buf_elem->rx_buf = dma_alloc_coherent(NULL, RXDMA_BUFF_SIZE, &rx_buf_elem->rx_handle, GFP_DMA);
  260.         if (rx_buf_elem->rx_buf == NULL)
  261.             {
  262.             for (j = 0; j < i; j++)
  263.                 {
  264.                 rx_buf_elem =  (mxc_spi_rxdmamap *) (umxc->rx_dmamap + j);
  265.                 dma_free_coherent(NULL, RXDMA_BUFF_SIZE, rx_buf_elem->rx_buf, rx_buf_elem->rx_handle);
  266.                 }
  267.             ret = -1;
  268.             goto cleanup;
  269.             }
  270.         }
  271.  
  272.     umxc->dma_rxbuf_id = 0;
  273.  
  274.     /* Setup the DMA read request structures */
  275.     for (i = 0; i < rxbufs; i++)
  276.     {
  277.         rx_buf_elem = (mxc_spi_rxdmamap *) (umxc->rx_dmamap + i);
  278.         (readchnl_reqelem + i)->src_addr = umxc->mapbase+ECSPI2_RXDATA;
  279.         (readchnl_reqelem + i)->dst_addr = rx_buf_elem->rx_handle;
  280.         (readchnl_reqelem + i)->num_of_bytes = RXDMA_BUFF_SIZE;
  281.        
  282.         printk(KERN_ERR "\nMXC SPI: buffer:%d  read request structures: src_addr=%08X, dst_addr=%08X, num_of_bytes=%d\n",  
  283.             i, (readchnl_reqelem + i)->src_addr, (readchnl_reqelem + i)->dst_addr, (readchnl_reqelem + i)->num_of_bytes );
  284.        
  285.     }
  286.     mxc_dma_config(d_info->rd_channel, readchnl_reqelem, rxbufs, MXC_DMA_MODE_READ);           
  287.     mxc_dma_callback_set(d_info->rd_channel, mxcspi_dmaread_callback, umxc);
  288.  
  289.     /* Start the read channel */
  290.     mxc_dma_enable(d_info->rd_channel);
  291.     kfree(readchnl_reqelem);
  292.     //d_info->dma_txchnl_inuse = 0;
  293.     return ret;
  294.    
  295.     cleanup:
  296.     printk(KERN_ERR "\nMXC SPI: Cleanup");
  297.     kfree(readchnl_reqelem);
  298.    
  299.     err_request:
  300.     printk(KERN_ERR "\nMXC SPI: Err request");
  301.     kfree(umxc->rx_dmamap);
  302.    
  303.     err_dma_rx_buff:
  304.     printk(KERN_ERR "\nMXC SPI: Error DMA");
  305.    
  306.     mxc_dma_free(d_info->rd_channel);
  307.  
  308.     return ret;
  309. }
  310. #endif
  311.  
  312. //-------------------------------------------------------------------------------------
  313. //---------------------------- SPI STUFF    -------------------------------------------
  314. //-------------------------------------------------------------------------------------
  315. //-------------------------------------------------------------------------------------
  316.  
  317.  
  318. static void ResetInputBuffer(void)
  319. {
  320. inputBuffer.start=0;
  321. inputBuffer.end=0;
  322. }
  323.  
  324.  
  325. //-------------------------------------------------------------------------------------
  326. static void ConfigureSpi(void)
  327. {
  328.     // ------- CONREG -----------
  329.     // CONREG: 19-18 : 00=channel 0 select (SS0),
  330.     //         7-4 : CHANNEL MODE 0-slave/1-master, [3]-channel 3... [0]-channel 0
  331.     //         3: SMC - immediately starts SPI burst when data is written to TXFIFO
  332.     *(int*)(spi_base+ECSPI2_CONREG) = 0x00 ; // enable bit OFF, to reset block
  333.     *(int*)(spi_base+ECSPI2_CONREG) = (1<<3) | (0x07<<20); // | (0x08<<20); // channel 0 slave , SMC enabled, 8 bits SPI burst
  334.  
  335.     // ------- CONFIGREG -----------
  336.     *(int*)(spi_base+ECSPI2_CONFIGREG) = 0x00;   // согласно картинке Меньшова нам нужен режим POL=0 PHA=0
  337.     // ------- INTREG -----------  // isr control
  338. #if defined(DMA_USE)
  339.     *(int*)(spi_base+ECSPI2_INTREG) = 0;//
  340. #else
  341.     *(int*)(spi_base+ECSPI2_INTREG) = (1<<4) ; // 4: rx fifo data request enable (rxfifo > rx threshold)
  342. #endif
  343.  
  344.     // ------- DMAREG -----------
  345.     // DMAREG:
  346.     //   21-16: rx threshold
  347.     //   23-RXDEN-RXFIFO DMA request enable
  348.     // 29-24 DMA burst length, 31 - RX FIFO tail DMA enable
  349. #if !defined(DMA_USE)
  350.     *(int*)(spi_base+ECSPI2_DMAREG) = (BYTES_IN_FIFO_IRQ_OCCURS<<16); //
  351. #else // DMA enabled
  352.     *(int*)(spi_base+ECSPI2_DMAREG) = (BYTES_IN_FIFO_IRQ_OCCURS<<16) | (1<<23) ;    
  353.         //  | (BYTES_IN_FIFO_IRQ_OCCURS<<24) | (1<<31);  
  354. #endif
  355.      
  356.    
  357.     // ------- PERIODREG -----------
  358. // PERIODREG only for master:
  359. // << PERIODREG SKIPPED >>
  360. //    15 - CSRC : 0-Spi clock, 1- Low freq ref clk 32.768Khz   
  361.  
  362.     // ------- TESTREG -----------
  363.     // TESTREG:
  364.     //   31- LBC: 1- loopback enabled - receiver is connected to transmitter
  365.     *(int*)(spi_base+ECSPI2_TESTREG) = 0;
  366.  
  367.     *(int*)(spi_base+ECSPI2_CONREG) |= 0x01; // enable bit ON
  368.  
  369.  
  370. //----------- end of SPI configure ------------------
  371. }
  372.  
  373. //-------------------------------------------------------------------------------------
  374. // Функция загрузки модуля. Входная точка. Можем считать что это наш main()
  375. static int __init spislave_init( void )
  376. {
  377. struct resource *res;
  378.  
  379. printk( KERN_ALERT "spi driver: configuring ECSPI-2...\n" );
  380.  
  381. res= request_mem_region(ECSPI2_BASE, region_size, "spi");
  382. spi_base = ioremap_nocache(ECSPI2_BASE, region_size);
  383.  
  384. res= request_mem_region(GPIO2_BASE, region_size, "gpio2");
  385. gpio2_base= ioremap_nocache(GPIO2_BASE, region_size);
  386.  
  387. *(int*)(gpio2_base+GPIO_GDIR) |= (1<<24);   // 1 means output
  388.  
  389. ConfigureSpi();
  390.    
  391. printk( KERN_ALERT "spi driver: spislave driver loaded!\n" );
  392.  
  393.  
  394.  // Регистрируем устройсво и получаем старший номер устройства
  395. major_number = register_chrdev( 0, DEVICE_NAME, &fops );
  396.  
  397. if ( major_number < 0 )
  398.     {
  399.     printk( "spi driver: Registering the character device failed with %d\n", major_number );
  400.     return major_number;
  401.     }
  402.  
  403.  // Сообщаем присвоенный нам старший номер устройства
  404. printk( "spi driver: spislave module is loaded!\n" );
  405.  
  406. printk( "spi driver: Please, create a dev file with 'mknod /dev/spislave c %d 0'.\n", major_number );
  407.  
  408. return SUCCESS;
  409. }
  410.  
  411. //-------------------------------------------------------------------------------------
  412. // Функция выгрузки модуля
  413. static void __exit spislave_exit( void )
  414. {
  415.  // Освобождаем устройство
  416.  iounmap(spi_base);
  417.  release_mem_region(ECSPI2_BASE, region_size);
  418.  
  419.  unregister_chrdev( major_number, DEVICE_NAME );
  420.  
  421.  printk( KERN_ALERT "spi driver: spislave module is unloaded!\n" );
  422. }
  423. //-------------------------------------------------------------------------------------
  424. // Указываем наши функции загрузки и выгрузки
  425. module_init( spislave_init );
  426. module_exit( spislave_exit );
  427.  
  428. static void CheckMaxRxFifoLoad(int load)
  429. {
  430. if (load> maxRxFifoLoad)
  431.     {
  432.     maxRxFifoLoad=load;
  433.     printk (KERN_ALERT "max rx fifo load=%d\n", maxRxFifoLoad);
  434.     if (maxRxFifoLoad==64)
  435.         {
  436.         printk (KERN_ALERT "rx fifo MAXIMUM REACHED. cleared.\n");
  437.         maxRxFifoLoad=0;
  438.         }
  439.     }
  440. }
  441.    
  442.  
  443.  
  444.  
  445. //-------------------------------------------------------------------------------------
  446. static irqreturn_t irq_handler(int irq, void *dummy, struct pt_regs * regs)
  447. { // interrupt service routine (ISR)
  448. int testReg;
  449. int rxFifoCounter;
  450. int rxData;
  451. int counter;
  452. *(int*)(gpio2_base+GPIO_DR) |= (1<<24); // дергаем ножкой, для отладки
  453.  
  454. // экспериментально выяснил, что i r q_handler может возникать во время операции read, т.е.
  455. // read не являются блокирующим для прерывания (по идее так и должно быть, однако были в свое время подозрения).
  456.  
  457. //printk(KERN_ALERT "spi IRQ: Interrupt handler executed!\n");
  458.  
  459. counter = 256; // число байт которые можем схавать за раз в одном прерывании. это по сути защита от зависонов.
  460.         //теоретически может быть
  461.             //   больше чем весь FIFO, т.к. пока сидим и хаваем данные тут могут прийти еще данные в FIFO
  462.        
  463. //printk(KERN_ALERT "spi IRQ: %d bytes in buffer\n", rxFifoCounter);
  464.  
  465. testReg = *(int*)(spi_base+ECSPI2_TESTREG);
  466. rxFifoCounter = ((testReg>>8) & 0x7F);// only 7 bits used
  467. #if defined(DEBUG_OUTPUT_ENABLED)
  468. CheckMaxRxFifoLoad(rxFifoCounter);
  469. #endif
  470.  
  471.  
  472. while (rxFifoCounter>0)
  473.     {
  474.     rxData = *(int*)(spi_base+ECSPI2_RXDATA);
  475. locked=1; // lock inputBuffer  
  476.     inputBuffer.data[inputBuffer.end] = rxData & 0xFF;
  477.     inputBuffer.end = (inputBuffer.end+1) % INPUT_BUFFER_SIZE;
  478.    
  479. locked=0; // unlock inputBuffer
  480.     testReg = *(int*)(spi_base+ECSPI2_TESTREG);
  481.     rxFifoCounter = ((testReg>>8)  & 0x7F);// only 7 bits used  
  482. #if defined(DEBUG_OUTPUT_ENABLED)
  483.     CheckMaxRxFifoLoad(rxFifoCounter);
  484. #endif
  485.     if (!(counter--))  // защита от зависонов
  486.         break;
  487.     }
  488.  
  489. *(int*)(gpio2_base+GPIO_DR) &= ~(1<<24);
  490. return IRQ_HANDLED;
  491. }
  492. //-------------------------------------------------------------------------------------
  493. void ResetMaxRxFifoLoad(void)
  494. {
  495. maxRxFifoLoad=0;
  496. maxBufferLoad=0 ;
  497. rxoverflowedCount=0;
  498. #if defined(DEBUG_OUTPUT_ENABLED)
  499. printk (KERN_ALERT "max rx fifo reset\n");
  500. #endif
  501. }
  502. //-------------------------------------------------------------------------------------
  503.  
  504.  
  505. static int device_open( struct inode *inode, struct file *file )
  506. {
  507. int status = 0;
  508. int retval;
  509.  
  510. locked=0;
  511. if ( is_device_open )
  512.   return -EBUSY;
  513.  
  514. ResetInputBuffer();
  515.  
  516. #if defined(DMA_USE)
  517.  
  518. printk("\nspi driver: DMA ENABLED\n");  // isr handling
  519. printk("\nInterrupts for SPI disabled\n");  // isr handling
  520.  
  521. #else
  522.  
  523. printk("\nspi driver: DMA DISABLED\n");  // isr handling
  524. printk("\nspi driver: Requesting interrupt\n");  // isr handling
  525. status = request_irq(IRQ_NUMB, irq_handler,0,IRQ_NAME, NULL);
  526. if (status == 0)
  527.     {
  528.     printk("\nspi driver: spi IRQ request successful!\n");
  529.     }
  530. else
  531.     {
  532.     printk("\nspi driver: spi IRQ request failed!\n");
  533.     return status;
  534.     }
  535. #endif
  536.  
  537.  
  538. ResetMaxRxFifoLoad();
  539.  
  540. //------ Initialize the DMA if we need SDMA data transfer ----------
  541. #if defined(DMA_USE)
  542. retval = mxcspi_initdma(&dma_list);
  543. if (retval != 0)
  544.     {
  545.     printk (KERN_ERR "MXC SPI: Failed to initialize DMA for SPI\n" );
  546.     // TO DO: add here free interrupts
  547.     return retval;
  548.     }
  549.  
  550. // Configure the GPR register to receive SDMA events
  551. //config_spidma_event(0);  // what is it for??
  552. #endif
  553.  
  554. is_device_open++;
  555.  
  556. return SUCCESS;
  557. }
  558. //-------------------------------------------------------------------------------------
  559. static int device_release( struct inode *inode, struct file *file )
  560. {
  561. /*
  562. #if defined(DMA_USE)
  563. mxcspi_freedma(&dma_list, &umxcport);
  564. #endif
  565. */
  566.  
  567.  
  568. is_device_open--;
  569. #if !defined(DMA_USE)
  570. free_irq(IRQ_NUMB, NULL);
  571. printk ("spi driver: spi irq freed\n");
  572. #endif
  573. ResetMaxRxFifoLoad();
  574.  
  575. return SUCCESS;
  576. }
  577. //-------------------------------------------------------------------------------------
  578. static ssize_t
  579.  
  580. device_write( struct file *filp, const char *buff, size_t len, loff_t * off )
  581. {
  582.  printk( "spi driver: Sorry, this operation isn't supported.\n" );
  583.  return -EINVAL;
  584. }
  585.  
  586. //-------------------------------------------------------------------------------------
  587. static int rxCountPreviousDebug;
  588.  
  589.  
  590. static ssize_t device_read( struct file *filp, /* include/linux/fs.h */
  591.        char *buffer, /* buffer */
  592.        size_t length, /* buffer length */
  593.        loff_t * offset )
  594. {
  595. #define MAX_FAILED_OPS   128
  596. int byte_read = 0;
  597. char rx;
  598. int curBufferLoad = (inputBuffer.end>=inputBuffer.start)? (inputBuffer.end-inputBuffer.start) : (INPUT_BUFFER_SIZE-inputBuffer.start + inputBuffer.start);
  599. int failedOps=0;
  600.  
  601. #if defined(DEBUG_OUTPUT_ENABLED)
  602. int rxoverflowed = *(int*)(spi_base+ECSPI2_STATREG) & (1<<6);
  603. if (rxoverflowed)
  604.     {
  605.     *(int*)(spi_base+ECSPI2_STATREG) |= (1<<6) ; // writing to 1 to this bit to clear overflow flag
  606.     rxoverflowedCount++;
  607.     //if (rxoverflowedCount % 5 ==0)
  608.         printk (KERN_ERR "overflow count = %d\n", rxoverflowedCount);
  609.     }
  610. #endif
  611.  
  612. while ( length )
  613.     {
  614.     // need to avoid processing during active interrupt handler process
  615.     // check if inputBuffer is unlocked
  616.     if (locked)
  617.         {
  618.         failedOps++;
  619.         if (failedOps>MAX_FAILED_OPS)
  620.             break;
  621.         else
  622.             continue;
  623.         }
  624.        
  625.        
  626. #if defined(DMA_USE)  // debug var
  627. int rxFifoCounter = (((*(int*)(spi_base+ECSPI2_TESTREG)) >> 8) & 0x7F);// only 7 bits used
  628. if (rxCountPreviousDebug!=rxFifoCounter)
  629.     {
  630.     put_user( (char) (rxFifoCounter & 0xFF), buffer);
  631.     rxCountPreviousDebug=rxFifoCounter;
  632.     return 1;
  633.     }
  634. else
  635.     return 0;
  636. #endif
  637.  
  638.     if (inputBuffer.start==inputBuffer.end)
  639.         break;
  640.  
  641.     rx = inputBuffer.data[inputBuffer.start];
  642.     inputBuffer.start = (inputBuffer.start+1) % INPUT_BUFFER_SIZE;
  643.  
  644.     //put_user( rxFifoCounter, buffer++ );
  645.     put_user( rx, buffer++ );
  646.  
  647.     length--;
  648.     byte_read++;
  649.     }
  650.  
  651. #if defined(DEBUG_OUTPUT_ENABLED)
  652. if (curBufferLoad>maxBufferLoad)
  653.     {
  654.     maxBufferLoad= curBufferLoad;
  655.     printk ("max buffer load = %d\n", maxBufferLoad);
  656.     }
  657. #endif
  658.  
  659. return byte_read;
  660. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement