Merge from kseries.
authorbatt <batt@38d2e660-2303-0410-9eaa-f027e97ec537>
Tue, 19 Feb 2008 14:50:05 +0000 (14:50 +0000)
committerbatt <batt@38d2e660-2303-0410-9eaa-f027e97ec537>
Tue, 19 Feb 2008 14:50:05 +0000 (14:50 +0000)
git-svn-id: https://src.develer.com/svnoss/bertos/trunk@1140 38d2e660-2303-0410-9eaa-f027e97ec537

drv/ser.c
drv/ser.h

index dbbf9382fbb8eb9c2c42cb92dce0e510c7bb6b6e..d920d9dec59f1cbe4327daf4671b351be9eb737f 100644 (file)
--- a/drv/ser.c
+++ b/drv/ser.c
@@ -184,21 +184,19 @@ static int ser_getchar(struct Serial *port)
        return (int)(unsigned char)fifo_pop_locked(&port->rxfifo);
 }
 
-#if 0
 /**
  * Preleva un carattere dal buffer di ricezione.
  * Se il buffer e' vuoto, ser_getchar_nowait() ritorna
  * immediatamente EOF.
  */
-int ser_getchar_nowait(struct Serial *port)
+int ser_getchar_nowait(struct KFileSerial *fd)
 {
-       if (fifo_isempty_locked(&port->rxfifo))
+       if (fifo_isempty_locked(&fd->ser->rxfifo))
                return EOF;
 
        /* NOTE: the double cast prevents unwanted sign extension */
-       return (int)(unsigned char)fifo_pop_locked(&port->rxfifo);
+       return (int)(unsigned char)fifo_pop_locked(&fd->ser->rxfifo);
 }
-#endif
 
 
 /**
@@ -467,17 +465,32 @@ void ser_init(struct KFileSerial *fds, unsigned int unit)
  * Since we are master, we have to trigger slave by sending
  * fake chars on the bus.
  */
-static size_t spimaster_read(struct KFile *fd, void *buf, size_t size)
+static size_t spimaster_read(struct KFile *fd, void *_buf, size_t size)
 {
        KFileSerial *fd_spi = KFILESERIAL(fd);
 
        ser_flush(&fd_spi->fd);
        ser_purgeRx(fd_spi);
 
-       for (size_t i = 0; i < size; i++)
+       size_t total_rd = 0;
+       uint8_t *buf = (uint8_t *)_buf;
+       int c;
+
+       while (size--)
+       {
+               /*
+                * Send and receive chars 1 by 1, otherwise the rxfifo
+                * will overrun.
+                */
                ser_putchar(0, fd_spi->ser);
 
-       return ser_read(&fd_spi->fd, buf, size);
+               if ((c = ser_getchar(fd_spi->ser)) == EOF)
+                       break;
+
+               *buf++ = c;
+               total_rd++;
+       }
+       return total_rd;
 }
 
 /**
@@ -510,3 +523,5 @@ void spimaster_init(KFileSerial *fds, unsigned int unit)
        fds->fd.read = spimaster_read;
        fds->fd.write = spimaster_write;
 }
+
+
index 0790758d28abd30f2a72470198b65d55ab4d9310..f4edc6841487cd99dace0b03d260423092e487eb 100644 (file)
--- a/drv/ser.h
+++ b/drv/ser.h
@@ -171,6 +171,7 @@ void ser_setbaudrate(struct KFileSerial *fd, unsigned long rate);
 void ser_setparity(struct KFileSerial *fd, int parity);
 void ser_settimeouts(struct KFileSerial *fd, mtime_t rxtimeout, mtime_t txtimeout);
 void ser_resync(struct KFileSerial *fd, mtime_t delay);
+int ser_getchar_nowait(struct KFileSerial *fd);
 
 void ser_purgeRx(struct KFileSerial *fd);
 void ser_purgeTx(struct KFileSerial *fd);