]> git.llucax.com Git - z.facultad/66.09/etherled.git/commitdiff
Ahora el módulo de red se encarga sólo de darse cuenta cuando hay que hacer
authorLeandro Lucarella <llucax@gmail.com>
Thu, 8 Dec 2005 21:34:29 +0000 (21:34 +0000)
committerLeandro Lucarella <llucax@gmail.com>
Thu, 8 Dec 2005 21:34:29 +0000 (21:34 +0000)
DMA de más (para el padding).

src/dp8390.c
src/main.c
src/netdev.h

index 30b3fb53468977e1ac9713b84bdb3d47a3809c57..2943554aa0a3339b0827d31ef3048dbf525e3153 100644 (file)
@@ -4,6 +4,9 @@
 #include "eth.h"
 #include "dp8390.h"
 
+/** Tamaño del frame */
+byte netdev_len;
+
 /// Datos persistentes del módulo
 static union // Unión porque nunca se usan ambos juntos
 {
@@ -12,6 +15,15 @@ static union // Unión porque nunca se usan ambos juntos
 }
 persistent;
 
+/// Estructura de la cabecera del buffer de la placa de red.
+struct buf_hdr_t
+{
+    byte status;    ///> Estado del frame recibido
+    byte next;      ///> Offset del próximo frame
+    uint16 len;     ///> Tamaño del frame
+};
+
+
 /// Cambia de página sin modificar los demás bits del CR
 #define SELECT_REG_PAGE(page)                         \
     do                                                \
@@ -305,24 +317,24 @@ void netdev_send_end()
 }
 
 /** Comienza la lectura de un nuevo frame
- * @return Cantidad de bytes del frame leído
+ * @precond netdev_recv_start() debe haber sido ejecutada
  */
-byte netdev_recv_start()
+void netdev_recv_start()
 {
+    // Limpio tamaño del frame
+    netdev_len = 0;
+
     // Check if the rx buffer has overflowed.
     if (read_reg(ISR) & OVW)
     {
         byte current;
 
-        // Select RTL8019AS register page 1.
         SELECT_REG_PAGE(1);
-
-        // Retrieve current receive buffer page
         current = read_reg(CURR);
-
-        // Select RTL8019AS register page 1.
         SELECT_REG_PAGE(0);
 
+        // Hack: a veces reporta mal el flag de OVW, así que verificamos que
+        // relamente haya habido overflow.
         if (read_reg(BNRY) == current)
         {
             printb(read_reg(ISR), 0x01);
@@ -330,18 +342,12 @@ byte netdev_recv_start()
             printb(current, 0x04);
             reset();
         }
-        return 0u;
+        return;
     }
     // Check if there is a packet in the rx buffer.
     else if (read_reg(ISR) & PRX)
     {
-        struct buf_hdr_t
-        {
-            byte status;    // Estado del frame recibido
-            byte next;      // Offset del próximo frame
-            uint16 len;     // Tamaño del frame
-        }
-        buf_hdr;
+        struct buf_hdr_t buf_hdr;
         byte current;
         byte bnry;
 
@@ -368,7 +374,7 @@ byte netdev_recv_start()
         {
             // Clear packet received interrupt flag.
             write_reg(ISR, PRX | RXE);
-            return 0u;
+            return;
         }
 
         // Set remote DMA byte count registers to packet header length.
@@ -399,15 +405,18 @@ byte netdev_recv_start()
                 || ((buf_hdr.status & 0x0F) != RXSOK)
                 || read_reg(RDMA)) // Parte alta del tamaño
         {
-            // Abort/ complete DMA operation.
+            // Terminamos DMA y pasamos al próximo frame
             ABORT_DMA(START);
-
-            // Advance boundary pointer to next packet start.
             write_reg(BNRY, persistent.next_pkt);
-
-            return 0;
+            return;
         }
 
+        // Abort/ complete DMA operation.
+        ABORT_DMA(START);
+
+        // Todo OK, empezamos a recibir así que ponemos bien el tamaño del frame
+        netdev_len = buf_hdr.len;
+
         // Set remote DMA start address registers to packet data.
         write_reg(RSAR0, sizeof(struct buf_hdr_t));
         write_reg(RSAR1, bnry);
@@ -418,10 +427,7 @@ byte netdev_recv_start()
 
         // Initiate DMA transfer of packet data.
         write_reg(CR, READ);
-    
-        return buf_hdr.len;
     }
-    return 0;
 }
 
 /** Lee un byte del buffer de la placa de red
@@ -446,10 +452,20 @@ uint16 netdev_recv_word()
  */
 void netdev_recv_end()
 {
-    // Abort/ complete DMA operation.
+    // Termina de leer bytes de padding (si hay)
+    netdev_len += sizeof(struct buf_hdr_t);
+    if (read_reg(CRDA0) < netdev_len)
+    {
+        netdev_len -= read_reg(CRDA0) - 1; // El puntero está adelantado en 1
+        while (netdev_len--)
+        {
+            //printb(read_reg(CRDA0), netdev_len);
+            netdev_recv_byte();
+        }
+    }
+    // Completa DMA
     ABORT_DMA(START);
-
-    // Advance boundary pointer to next packet start.
+    // Pasa el próximo frame
     write_reg(BNRY, persistent.next_pkt);
 }
 
index 419ad419adc697d59decf92c10c12573575da747..787f025e56be6ee3e65267724c624763ed04fefa 100644 (file)
@@ -31,9 +31,9 @@ void main(void)
     while (1) // Forever
     {
         byte i;
-        byte len = netdev_recv_start();
-        printb(len, 0x1);
-        if (!len) // no recibimos nada (válido)
+        netdev_recv_start();
+        printb(netdev_len, 0x1);
+        if (!netdev_len) // no recibimos nada (válido)
             continue; // Probamos de nuevo
 
         // Tenemos algo!
@@ -70,15 +70,11 @@ void main(void)
                             goto drop; // Tiramos el paquete
 
                         printb(udp_dgram_len, 0x40);
-                        // TODO
                         // Nuestro protocolo, por ahora un simple echo!
                         for (i = 8; i < udp_dgram_len; ++i) // 8 por la cabecera UDP
                         {
                             printb(netdev_recv_byte(), 0x00);
                         }
-                        //i = (udp_dgram_len % 2) ? (udp_dgram_len - 1) : udp_dgram_len;
-                        for (i += 34; i < len; ++i) // 8 por las cabeceras eth+IP
-                            netdev_recv_byte();
 drop:
                         netdev_recv_end();
                 }
index 635432b7099ad19c2f9935ecb439687f74dc6a3d..e8246661b5a02021b7b824cb79e3aa76c9d06d26 100644 (file)
@@ -5,6 +5,9 @@
 
 #include "types.h"
 
+/** Tamaño del frame */
+extern byte netdev_len;
+
 /** Inicializa dispositivo de red
  * @return true si se inicializó correctamente, false si no
  */
@@ -33,9 +36,9 @@ void netdev_send_word(uint16 w);
 void netdev_send_end();
 
 /** Comienza la lectura de un nuevo frame
- * @return Cantidad de bytes del frame leído
+ * @postcond Deja en netdev_len el tamaño del frame recibido
  */
-byte netdev_recv_start();
+void netdev_recv_start();
 
 /** Lee un byte del buffer de la placa de red
  * @precond netdev_recv_start() debe haber sido ejecutada