Changeset ae1f70e in mainline


Ignore:
Timestamp:
2011-01-07T08:54:28Z (13 years ago)
Author:
Vojtech Horky <vojtechhorky@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
0f191a2, 8f8a0cd6
Parents:
f03d3786 (diff), 3d5e190 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge mainline changes

Files:
2 deleted
11 edited
2 moved

Legend:

Unmodified
Added
Removed
  • kernel/generic/include/ddi/irq.h

    rf03d3786 rae1f70e  
    5454        /** Read 4 bytes from the I/O space. */
    5555        CMD_PIO_READ_32,
     56       
    5657        /** Write 1 byte to the I/O space. */
    5758        CMD_PIO_WRITE_8,
     
    6263       
    6364        /**
    64          * Perform a bit test on the source argument and store the result into
    65          * the destination argument.
     65         * Write 1 byte from the source argument
     66         * to the I/O space.
     67         */
     68        CMD_PIO_WRITE_A_8,
     69        /**
     70         * Write 2 bytes from the source argument
     71         * to the I/O space.
     72         */
     73        CMD_PIO_WRITE_A_16,
     74        /**
     75         * Write 4 bytes from the source argument
     76         * to the I/O space.
     77         */
     78        CMD_PIO_WRITE_A_32,
     79       
     80        /**
     81         * Perform a bit masking on the source argument
     82         * and store the result into the destination argument.
    6683         */
    6784        CMD_BTEST,
    6885       
    6986        /**
    70          * Predicate the execution of the following N commands by the boolean
    71          * value of the source argument.
     87         * Predicate the execution of the following
     88         * N commands by the boolean value of the source
     89         * argument.
    7290         */
    7391        CMD_PREDICATE,
     
    7593        /** Accept the interrupt. */
    7694        CMD_ACCEPT,
     95       
    7796        /** Decline the interrupt. */
    7897        CMD_DECLINE,
  • kernel/generic/src/ipc/irq.c

    rf03d3786 rae1f70e  
    404404                            (uint32_t) code->cmds[i].value);
    405405                        break;
     406                case CMD_PIO_WRITE_A_8:
     407                        if (srcarg) {
     408                                pio_write_8((ioport8_t *) code->cmds[i].addr,
     409                                    (uint8_t) scratch[srcarg]);
     410                        }
     411                        break;
     412                case CMD_PIO_WRITE_A_16:
     413                        if (srcarg) {
     414                                pio_write_16((ioport16_t *) code->cmds[i].addr,
     415                                    (uint16_t) scratch[srcarg]);
     416                        }
     417                        break;
     418                case CMD_PIO_WRITE_A_32:
     419                        if (srcarg) {
     420                                pio_write_32((ioport32_t *) code->cmds[i].addr,
     421                                    (uint32_t) scratch[srcarg]);
     422                        }
     423                        break;
    406424                case CMD_BTEST:
    407425                        if ((srcarg) && (dstarg)) {
  • uspace/Makefile

    rf03d3786 rae1f70e  
    8383        srv/hw/char/s3c24xx_uart \
    8484        srv/hw/netif/dp8390 \
    85         srv/net/cfg \
    8685        srv/net/netif/lo \
    8786        srv/net/il/arp \
  • uspace/srv/hw/netif/dp8390/dp8390.c

    rf03d3786 rae1f70e  
    11/*
    2  * Copyright (c) 1987,1997, 2006, Vrije Universiteit, Amsterdam, The Netherlands All rights reserved. Redistribution and use of the MINIX 3 operating system in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
    3  *
    4  * * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
    5  * * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
    6  * * Neither the name of the Vrije Universiteit nor the names of the software authors or contributors may be used to endorse or promote products derived from this software without specific prior written permission.
    7  * * Any deviations from these conditions require written permission from the copyright holder in advance
    8  *
    9  *
    10  * Disclaimer
    11  *
    12  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS, AUTHORS, AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
     2 * Copyright (c) 2009 Lukas Mejdrech
     3 * Copyright (c) 2011 Martin Decky
     4 * All rights reserved.
     5 *
     6 * Redistribution and use in source and binary forms, with or without
     7 * modification, are permitted provided that the following conditions
     8 * are met:
     9 *
     10 * - Redistributions of source code must retain the above copyright
     11 *   notice, this list of conditions and the following disclaimer.
     12 * - Redistributions in binary form must reproduce the above copyright
     13 *   notice, this list of conditions and the following disclaimer in the
     14 *   documentation and/or other materials provided with the distribution.
     15 * - The name of the author may not be used to endorse or promote products
     16 *   derived from this software without specific prior written permission.
     17 *
     18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
    1319 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
    1420 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
    15  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR ANY AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
     21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
    1622 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
    1723 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     
    2026 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
    2127 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    22  *
    23  * Changes:
    24  *  2009 ported to HelenOS, Lukas Mejdrech
     28 */
     29
     30/*
     31 * This code is based upon the NE2000 driver for MINIX,
     32 * distributed according to a BSD-style license.
     33 *
     34 * Copyright (c) 1987, 1997, 2006 Vrije Universiteit
     35 * Copyright (c) 1992, 1994 Philip Homburg
     36 * Copyright (c) 1996 G. Falzoni
     37 *
    2538 */
    2639
     
    3649#include <byteorder.h>
    3750#include <errno.h>
    38 
    3951#include <netif_local.h>
    4052#include <net/packet.h>
     53#include <nil_interface.h>
    4154#include <packet_client.h>
    42 
    4355#include "dp8390_drv.h"
    4456#include "dp8390_port.h"
    45 
    46 /*
    47  * dp8390.c
    48  *
    49  * Created:     before Dec 28, 1992 by Philip Homburg <philip@f-mnx.phicoh.com>
    50  *
    51  * Modified Mar 10 1994 by Philip Homburg
    52  *      Become a generic dp8390 driver.
    53  *
    54  * Modified Dec 20 1996 by G. Falzoni <falzoni@marina.scn.de>
    55  *      Added support for 3c503 boards.
    56  */
    57 
    58 #include "local.h"
    5957#include "dp8390.h"
    60 
    61 /** Queues the outgoing packet.
    62  *  @param[in] dep The network interface structure.
    63  *  @param[in] packet The outgoing packet.
    64  *  @return EOK on success.
    65  *  @return EINVAL
    66  */
    67 int queue_packet(dpeth_t * dep, packet_t *packet);
    68 
    69 /** Reads a memory block byte by byte.
     58#include "ne2000.h"
     59
     60/** Read a memory block byte by byte.
     61 *
    7062 *  @param[in] port The source address.
    7163 *  @param[out] buf The destination buffer.
    7264 *  @param[in] size The memory block size in bytes.
     65 *
    7366 */
    7467static void outsb(port_t port, void * buf, size_t size);
    7568
    76 /** Reads a memory block word by word.
     69/** Read a memory block word by word.
     70 *
    7771 *  @param[in] port The source address.
    7872 *  @param[out] buf The destination buffer.
    7973 *  @param[in] size The memory block size in bytes.
     74 *
    8075 */
    8176static void outsw(port_t port, void * buf, size_t size);
    8277
    83 //static u16_t eth_ign_proto;
    84 //static char *progname;
    85 
    86 /* Configuration */
    87 /*typedef struct dp_conf
    88 {
    89         port_t dpc_port;
    90         int dpc_irq;
    91         phys_bytes dpc_mem;
    92         char *dpc_envvar;
    93 } dp_conf_t;
    94 */
    95 //dp_conf_t dp_conf[]=  /* Card addresses */
    96 //{
    97         /* I/O port, IRQ,  Buffer address,  Env. var. */
    98 /*      { 0x280,     3,    0xD0000,        "DPETH0"     },
    99         { 0x300,     5,    0xC8000,        "DPETH1"     },
    100         { 0x380,    10,    0xD8000,        "DPETH2"     },
    101 };
    102 */
    103 /* Test if dp_conf has exactly DE_PORT_NR entries.  If not then you will see
    104  * the error: "array size is negative".
    105  */
    106 //extern int ___dummy[DE_PORT_NR == sizeof(dp_conf)/sizeof(dp_conf[0]) ? 1 : -1];
    107 
    108 /* Card inits configured out? */
    109 #if !ENABLE_WDETH
    110 #define wdeth_probe(dep)        (0)
    111 #endif
    112 #if !ENABLE_NE2000
    113 #define ne_probe(dep)           (0)
    114 #endif
    115 #if !ENABLE_3C503
    116 #define el2_probe(dep)          (0)
    117 #endif
    118 
    119 /* Some clones of the dp8390 and the PC emulator 'Bochs' require the CR_STA
     78/*
     79 * Some clones of the dp8390 and the PC emulator 'Bochs' require the CR_STA
    12080 * on writes to the CR register. Additional CR_STAs do not appear to hurt
    121  * genuine dp8390s
    122  */
    123 #define CR_EXTRA        CR_STA
    124 
    125 //#if ENABLE_PCI
    126 //_PROTOTYPE(static void pci_conf, (void)                               );
    127 //#endif
    128 //_PROTOTYPE(static void do_vwrite, (message *mp, int from_int,
    129 //                                                      int vectored)   );
    130 //_PROTOTYPE(static void do_vwrite_s, (message *mp, int from_int)       );
    131 //_PROTOTYPE(static void do_vread, (message *mp, int vectored)          );
    132 //_PROTOTYPE(static void do_vread_s, (message *mp)                      );
    133 //_PROTOTYPE(static void do_init, (message *mp)                         );
    134 //_PROTOTYPE(static void do_int, (dpeth_t *dep)                         );
    135 //_PROTOTYPE(static void do_getstat, (message *mp)                      );
    136 //_PROTOTYPE(static void do_getstat_s, (message *mp)                    );
    137 //_PROTOTYPE(static void do_getname, (message *mp)                      );
    138 //_PROTOTYPE(static void do_stop, (message *mp)                         );
    139 _PROTOTYPE(static void dp_init, (dpeth_t *dep)                          );
    140 //_PROTOTYPE(static void dp_confaddr, (dpeth_t *dep)                    );
    141 _PROTOTYPE(static void dp_reinit, (dpeth_t *dep)                        );
    142 _PROTOTYPE(static void dp_reset, (dpeth_t *dep)                 );
    143 //_PROTOTYPE(static void dp_check_ints, (dpeth_t *dep)                  );
    144 _PROTOTYPE(static void dp_recv, (dpeth_t *dep)                          );
    145 _PROTOTYPE(static void dp_send, (dpeth_t *dep)                          );
    146 //_PROTOTYPE(static void dp8390_stop, (void)                            );
    147 _PROTOTYPE(static void dp_getblock, (dpeth_t *dep, int page,
    148                                 size_t offset, size_t size, void *dst)  );
    149 _PROTOTYPE(static void dp_pio8_getblock, (dpeth_t *dep, int page,
    150                                 size_t offset, size_t size, void *dst)  );
    151 _PROTOTYPE(static void dp_pio16_getblock, (dpeth_t *dep, int page,
    152                                 size_t offset, size_t size, void *dst)  );
    153 _PROTOTYPE(static int dp_pkt2user, (dpeth_t *dep, int page,
    154                                                         int length) );
    155 //_PROTOTYPE(static int dp_pkt2user_s, (dpeth_t *dep, int page,
    156 //                                                      int length)     );
    157 _PROTOTYPE(static void dp_user2nic, (dpeth_t *dep, iovec_dat_t *iovp,
    158                 vir_bytes offset, int nic_addr, vir_bytes count) );
    159 //_PROTOTYPE(static void dp_user2nic_s, (dpeth_t *dep, iovec_dat_s_t *iovp,
    160 //              vir_bytes offset, int nic_addr, vir_bytes count)        );
    161 _PROTOTYPE(static void dp_pio8_user2nic, (dpeth_t *dep,
    162                                 iovec_dat_t *iovp, vir_bytes offset,
    163                                 int nic_addr, vir_bytes count) );
    164 //_PROTOTYPE(static void dp_pio8_user2nic_s, (dpeth_t *dep,
    165 //                              iovec_dat_s_t *iovp, vir_bytes offset,
    166 //                              int nic_addr, vir_bytes count)          );
    167 _PROTOTYPE(static void dp_pio16_user2nic, (dpeth_t *dep,
    168                                 iovec_dat_t *iovp, vir_bytes offset,
    169                                 int nic_addr, vir_bytes count) );
    170 //_PROTOTYPE(static void dp_pio16_user2nic_s, (dpeth_t *dep,
    171 //                              iovec_dat_s_t *iovp, vir_bytes offset,
    172 //                              int nic_addr, vir_bytes count)          );
    173 _PROTOTYPE(static void dp_nic2user, (dpeth_t *dep, int nic_addr,
    174                 iovec_dat_t *iovp, vir_bytes offset, vir_bytes count)   );
    175 //_PROTOTYPE(static void dp_nic2user_s, (dpeth_t *dep, int nic_addr,
    176 //              iovec_dat_s_t *iovp, vir_bytes offset, vir_bytes count) );
    177 _PROTOTYPE(static void dp_pio8_nic2user, (dpeth_t *dep, int nic_addr,
    178                 iovec_dat_t *iovp, vir_bytes offset, vir_bytes count)   );
    179 //_PROTOTYPE(static void dp_pio8_nic2user_s, (dpeth_t *dep, int nic_addr,
    180 //              iovec_dat_s_t *iovp, vir_bytes offset, vir_bytes count) );
    181 _PROTOTYPE(static void dp_pio16_nic2user, (dpeth_t *dep, int nic_addr,
    182                 iovec_dat_t *iovp, vir_bytes offset, vir_bytes count)   );
    183 //_PROTOTYPE(static void dp_pio16_nic2user_s, (dpeth_t *dep, int nic_addr,
    184 //              iovec_dat_s_t *iovp, vir_bytes offset, vir_bytes count) );
    185 _PROTOTYPE(static void dp_next_iovec, (iovec_dat_t *iovp)               );
    186 //_PROTOTYPE(static void dp_next_iovec_s, (iovec_dat_s_t *iovp)         );
    187 _PROTOTYPE(static void conf_hw, (dpeth_t *dep)                          );
    188 //_PROTOTYPE(static void update_conf, (dpeth_t *dep, dp_conf_t *dcp)    );
    189 _PROTOTYPE(static void map_hw_buffer, (dpeth_t *dep)                    );
    190 //_PROTOTYPE(static int calc_iovec_size, (iovec_dat_t *iovp)            );
    191 //_PROTOTYPE(static int calc_iovec_size_s, (iovec_dat_s_t *iovp)                );
    192 _PROTOTYPE(static void reply, (dpeth_t *dep, int err, int may_block)    );
    193 //_PROTOTYPE(static void mess_reply, (message *req, message *reply)     );
    194 _PROTOTYPE(static void get_userdata, (int user_proc,
    195                 vir_bytes user_addr, vir_bytes count, void *loc_addr)   );
    196 //_PROTOTYPE(static void get_userdata_s, (int user_proc,
    197 //              cp_grant_id_t grant, vir_bytes offset, vir_bytes count,
    198 //              void *loc_addr) );
    199 //_PROTOTYPE(static void put_userdata, (int user_proc,
    200 //              vir_bytes user_addr, vir_bytes count, void *loc_addr)   );
    201 //_PROTOTYPE(static void put_userdata_s, (int user_proc,
    202 //              cp_grant_id_t grant, size_t count, void *loc_addr)      );
    203 _PROTOTYPE(static void insb, (port_t port, void *buf, size_t size)                              );
    204 _PROTOTYPE(static void insw, (port_t port, void *buf, size_t size)                              );
    205 //_PROTOTYPE(static void do_vir_insb, (port_t port, int proc,
    206 //                                      vir_bytes buf, size_t size)     );
    207 //_PROTOTYPE(static void do_vir_insw, (port_t port, int proc,
    208 //                                      vir_bytes buf, size_t size)     );
    209 //_PROTOTYPE(static void do_vir_outsb, (port_t port, int proc,
    210 //                                      vir_bytes buf, size_t size)     );
    211 //_PROTOTYPE(static void do_vir_outsw, (port_t port, int proc,
    212 //                                      vir_bytes buf, size_t size)     );
    213 
    214 int do_probe(dpeth_t * dep){
     81 * genuine dp8390s.
     82 */
     83#define CR_EXTRA  CR_STA
     84
     85static void dp_init(dpeth_t *dep);
     86static void dp_reinit(dpeth_t *dep);
     87static void dp_reset(dpeth_t *dep);
     88static void dp_recv(int nil_phone, device_id_t device_id, dpeth_t *dep);
     89static int dp_pkt2user(int nil_phone, device_id_t device_id, dpeth_t *dep, int page, int length);
     90static void conf_hw(dpeth_t *dep);
     91static void insb(port_t port, void *buf, size_t size);
     92static void insw(port_t port, void *buf, size_t size);
     93
     94int do_probe(dpeth_t *dep)
     95{
    21596        /* This is the default, try to (re)locate the device. */
    21697        conf_hw(dep);
    217         if (dep->de_mode == DEM_DISABLED)
    218         {
     98        if (!dep->up)
    21999                /* Probe failed, or the device is configured off. */
    220                 return EXDEV;//ENXIO;
    221         }
    222         if (dep->de_mode == DEM_ENABLED)
     100                return EXDEV;
     101       
     102        if (dep->up)
    223103                dp_init(dep);
     104       
    224105        return EOK;
    225106}
    226107
    227 /*===========================================================================*
    228  *                              dp8390_dump                                  *
    229  *===========================================================================*/
    230 void dp8390_dump(dpeth_t * dep)
    231 {
    232 //      dpeth_t *dep;
    233         int /*i,*/ isr;
    234 
    235 //      printf("\n");
    236 //      for (i= 0, dep = &de_table[0]; i<DE_PORT_NR; i++, dep++)
    237 //      {
    238 #if XXX
    239                 if (dep->de_mode == DEM_DISABLED)
    240                         printf("dp8390 port %d is disabled\n", i);
    241                 else if (dep->de_mode == DEM_SINK)
    242                         printf("dp8390 port %d is in sink mode\n", i);
    243 #endif
    244 
    245                 if (dep->de_mode != DEM_ENABLED)
    246 //                      continue;
    247                         return;
    248 
    249 //              printf("dp8390 statistics of port %d:\n", i);
    250 
    251                 printf("recvErr    :%8ld\t", dep->de_stat.ets_recvErr);
    252                 printf("sendErr    :%8ld\t", dep->de_stat.ets_sendErr);
    253                 printf("OVW        :%8ld\n", dep->de_stat.ets_OVW);
    254 
    255                 printf("CRCerr     :%8ld\t", dep->de_stat.ets_CRCerr);
    256                 printf("frameAll   :%8ld\t", dep->de_stat.ets_frameAll);
    257                 printf("missedP    :%8ld\n", dep->de_stat.ets_missedP);
    258 
    259                 printf("packetR    :%8ld\t", dep->de_stat.ets_packetR);
    260                 printf("packetT    :%8ld\t", dep->de_stat.ets_packetT);
    261                 printf("transDef   :%8ld\n", dep->de_stat.ets_transDef);
    262 
    263                 printf("collision  :%8ld\t", dep->de_stat.ets_collision);
    264                 printf("transAb    :%8ld\t", dep->de_stat.ets_transAb);
    265                 printf("carrSense  :%8ld\n", dep->de_stat.ets_carrSense);
    266 
    267                 printf("fifoUnder  :%8ld\t", dep->de_stat.ets_fifoUnder);
    268                 printf("fifoOver   :%8ld\t", dep->de_stat.ets_fifoOver);
    269                 printf("CDheartbeat:%8ld\n", dep->de_stat.ets_CDheartbeat);
    270 
    271                 printf("OWC        :%8ld\t", dep->de_stat.ets_OWC);
    272 
    273                 isr= inb_reg0(dep, DP_ISR);
    274                 printf("dp_isr = 0x%x + 0x%x, de_flags = 0x%x\n", isr,
    275                                         inb_reg0(dep, DP_ISR), dep->de_flags);
    276 //      }
    277 }
    278 
    279 /*===========================================================================*
    280  *                              do_init                                      *
    281  *===========================================================================*/
    282 int do_init(dpeth_t * dep, int mode){
    283         if (dep->de_mode == DEM_DISABLED)
    284         {
    285                 // might call do_probe()
     108/** Initialize and/or start the network interface.
     109 *
     110 *  @param[in,out] dep The network interface structure.
     111 *
     112 *  @return EOK on success.
     113 *  @return EXDEV if the network interface is disabled.
     114 *
     115 */
     116int do_init(dpeth_t *dep)
     117{
     118        if (!dep->up)
     119                /* FIXME: Perhaps call do_probe()? */
    286120                return EXDEV;
    287         }
    288 
    289         if (dep->de_mode == DEM_SINK)
    290         {
    291 //              strncpy((char *) dep->de_address.ea_addr, "ZDP", 6);
    292 //              dep->de_address.ea_addr[5] = port;
    293 //              dp_confaddr(dep);
    294 //              reply_mess.m_type = DL_CONF_REPLY;
    295 //              reply_mess.m3_i1 = mp->DL_PORT;
    296 //              reply_mess.m3_i2 = DE_PORT_NR;
    297 //              *(ether_addr_t *) reply_mess.m3_ca1 = dep->de_address;
    298 //              mess_reply(mp, &reply_mess);
    299 //              return;
    300                 return EOK;
    301         }
    302         assert(dep->de_mode == DEM_ENABLED);
    303         assert(dep->de_flags &DEF_ENABLED);
    304 
    305         dep->de_flags &= ~(DEF_PROMISC | DEF_MULTI | DEF_BROAD);
    306 
    307         if (mode &DL_PROMISC_REQ)
    308                 dep->de_flags |= DEF_PROMISC | DEF_MULTI | DEF_BROAD;
    309         if (mode &DL_MULTI_REQ)
    310                 dep->de_flags |= DEF_MULTI;
    311         if (mode &DL_BROAD_REQ)
    312                 dep->de_flags |= DEF_BROAD;
    313 
    314 //      dep->de_client = mp->m_source;
     121       
     122        assert(dep->up);
     123        assert(dep->enabled);
     124       
    315125        dp_reinit(dep);
    316 
    317 //      reply_mess.m_type = DL_CONF_REPLY;
    318 //      reply_mess.m3_i1 = mp->DL_PORT;
    319 //      reply_mess.m3_i2 = DE_PORT_NR;
    320 //      *(ether_addr_t *) reply_mess.m3_ca1 = dep->de_address;
    321 
    322 //      mess_reply(mp, &reply_mess);
    323126        return EOK;
    324127}
    325128
    326 /*===========================================================================*
    327  *                              do_stop                                      *
    328  *===========================================================================*/
    329 void do_stop(dpeth_t * dep){
    330         if((dep->de_mode != DEM_SINK) && (dep->de_mode == DEM_ENABLED) && (dep->de_flags &DEF_ENABLED)){
     129void do_stop(dpeth_t *dep)
     130{
     131        if ((dep->up) && (dep->enabled)) {
    331132                outb_reg0(dep, DP_CR, CR_STP | CR_DM_ABORT);
    332                 (dep->de_stopf)(dep);
    333 
    334                 dep->de_flags = DEF_EMPTY;
    335         }
    336 }
    337 
    338 int queue_packet(dpeth_t * dep, packet_t *packet){
    339         packet_t *tmp;
    340 
    341         if(dep->packet_count >= MAX_PACKETS){
    342                 netif_pq_release(packet_get_id(packet));
    343                 return ELIMIT;
    344         }
    345 
    346         tmp = dep->packet_queue;
    347         while(pq_next(tmp)){
    348                 tmp = pq_next(tmp);
    349         }
    350         if(pq_add(&tmp, packet, 0, 0) != EOK){
    351                 return EINVAL;
    352         }
    353         if(! dep->packet_count){
    354                 dep->packet_queue = packet;
    355         }
    356         ++ dep->packet_count;
    357         return EBUSY;
    358 }
    359 
    360 /*===========================================================================*
    361  *                      based on        do_vwrite                                    *
    362  *===========================================================================*/
    363 int do_pwrite(dpeth_t * dep, packet_t *packet, int from_int)
    364 {
    365 //      int port, count, size;
     133                ne_stop(dep);
     134               
     135                dep->enabled = false;
     136                dep->stopped = false;
     137                dep->sending = false;
     138                dep->send_avail = false;
     139        }
     140}
     141
     142static void dp_user2nic(dpeth_t *dep, void *buf, size_t offset, int nic_addr, size_t size)
     143{
     144        size_t ecount = size & ~1;
     145       
     146        outb_reg0(dep, DP_ISR, ISR_RDC);
     147       
     148        if (dep->de_16bit) {
     149                outb_reg0(dep, DP_RBCR0, ecount & 0xff);
     150                outb_reg0(dep, DP_RBCR1, ecount >> 8);
     151        } else {
     152                outb_reg0(dep, DP_RBCR0, size & 0xff);
     153                outb_reg0(dep, DP_RBCR1, size >> 8);
     154        }
     155       
     156        outb_reg0(dep, DP_RSAR0, nic_addr & 0xff);
     157        outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
     158        outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
     159       
     160        if (dep->de_16bit) {
     161                void *ptr = buf + offset;
     162               
     163                if (ecount != 0) {
     164                        outsw(dep->de_data_port, ptr, ecount);
     165                        size -= ecount;
     166                        offset += ecount;
     167                        ptr += ecount;
     168                }
     169               
     170                if (size) {
     171                        assert(size == 1);
     172                       
     173                        uint16_t two_bytes;
     174                       
     175                        memcpy(&(((uint8_t *) &two_bytes)[0]), ptr, 1);
     176                        outw(dep->de_data_port, two_bytes);
     177                }
     178        } else
     179                outsb(dep->de_data_port, buf + offset, size);
     180       
     181        unsigned int i;
     182        for (i = 0; i < 100; i++) {
     183                if (inb_reg0(dep, DP_ISR) & ISR_RDC)
     184                        break;
     185        }
     186       
     187        if (i == 100)
     188                fprintf(stderr, "Remote DMA failed to complete\n");
     189}
     190
     191int do_pwrite(dpeth_t *dep, packet_t *packet, int from_int)
     192{
    366193        int size;
    367194        int sendq_head;
    368 /*      dpeth_t *dep;
    369 
    370         port = mp->DL_PORT;
    371         count = mp->DL_COUNT;
    372         if (port < 0 || port >= DE_PORT_NR)
    373                 panic("", "dp8390: illegal port", port);
    374         dep= &de_table[port];
    375         dep->de_client= mp->DL_PROC;
    376 */
    377         if (dep->de_mode == DEM_SINK)
    378         {
    379                 assert(!from_int);
    380 //              dep->de_flags |= DEF_PACK_SEND;
    381                 reply(dep, OK, FALSE);
    382 //              return;
    383                 return EOK;
    384         }
    385         assert(dep->de_mode == DEM_ENABLED);
    386         assert(dep->de_flags &DEF_ENABLED);
    387         if(dep->packet_queue && (! from_int)){
    388 //      if (dep->de_flags &DEF_SEND_AVAIL){
    389 //              panic("", "dp8390: send already in progress", NO_NUM);
    390                 return queue_packet(dep, packet);
    391         }
    392 
    393         sendq_head= dep->de_sendq_head;
    394 //      if (dep->de_sendq[sendq_head].sq_filled)
    395 //      {
    396 //              if (from_int)
    397 //                      panic("", "dp8390: should not be sending\n", NO_NUM);
    398 //              dep->de_sendmsg= *mp;
    399 //              dep->de_flags |= DEF_SEND_AVAIL;
    400 //              reply(dep, OK, FALSE);
    401 //              return;
    402 //              return queue_packet(dep, packet);
    403 //      }
    404 //      assert(!(dep->de_flags &DEF_PACK_SEND));
    405 
    406 /*      if (vectored)
    407         {
    408                 get_userdata(mp->DL_PROC, (vir_bytes) mp->DL_ADDR,
    409                         (count > IOVEC_NR ? IOVEC_NR : count) *
    410                         sizeof(iovec_t), dep->de_write_iovec.iod_iovec);
    411                 dep->de_write_iovec.iod_iovec_s = count;
    412                 dep->de_write_iovec.iod_proc_nr = mp->DL_PROC;
    413                 dep->de_write_iovec.iod_iovec_addr = (vir_bytes) mp->DL_ADDR;
    414 
    415                 dep->de_tmp_iovec = dep->de_write_iovec;
    416                 size = calc_iovec_size(&dep->de_tmp_iovec);
    417         }
    418         else
    419         {
    420                 dep->de_write_iovec.iod_iovec[0].iov_addr =
    421                         (vir_bytes) mp->DL_ADDR;
    422                 dep->de_write_iovec.iod_iovec[0].iov_size =
    423                         mp->DL_COUNT;
    424                 dep->de_write_iovec.iod_iovec_s = 1;
    425                 dep->de_write_iovec.iod_proc_nr = mp->DL_PROC;
    426                 dep->de_write_iovec.iod_iovec_addr = 0;
    427                 size= mp->DL_COUNT;
    428         }
    429 */
     195       
     196        assert(dep->up);
     197        assert(dep->enabled);
     198       
     199        if (dep->send_avail) {
     200                fprintf(stderr, "Send already in progress\n");
     201                return EBUSY;
     202        }
     203       
     204        sendq_head = dep->de_sendq_head;
     205        if (dep->de_sendq[sendq_head].sq_filled) {
     206                if (from_int)
     207                        fprintf(stderr, "dp8390: should not be sending\n");
     208                dep->send_avail = true;
     209                dep->sending = false;
     210               
     211                return EBUSY;
     212        }
     213       
     214        assert(!dep->sending);
     215       
     216        void *buf = packet_get_data(packet);
    430217        size = packet_get_data_length(packet);
    431         dep->de_write_iovec.iod_iovec[0].iov_addr = (vir_bytes) packet_get_data(packet);
    432         dep->de_write_iovec.iod_iovec[0].iov_size = size;
    433         dep->de_write_iovec.iod_iovec_s = 1;
    434         dep->de_write_iovec.iod_iovec_addr = (uintptr_t) NULL;
    435 
    436         if (size < ETH_MIN_PACK_SIZE || size > ETH_MAX_PACK_SIZE_TAGGED)
    437         {
    438                 panic("", "dp8390: invalid packet size", size);
     218       
     219        if (size < ETH_MIN_PACK_SIZE || size > ETH_MAX_PACK_SIZE_TAGGED) {
     220                fprintf(stderr, "dp8390: invalid packet size\n");
    439221                return EINVAL;
    440222        }
    441         (dep->de_user2nicf)(dep, &dep->de_write_iovec, 0,
    442                 dep->de_sendq[sendq_head].sq_sendpage * DP_PAGESIZE,
    443                 size);
    444         dep->de_sendq[sendq_head].sq_filled= TRUE;
    445         if (dep->de_sendq_tail == sendq_head)
    446         {
     223       
     224        dp_user2nic(dep, buf, 0, dep->de_sendq[sendq_head].sq_sendpage
     225            * DP_PAGESIZE, size);
     226        dep->de_sendq[sendq_head].sq_filled = true;
     227       
     228        if (dep->de_sendq_tail == sendq_head) {
    447229                outb_reg0(dep, DP_TPSR, dep->de_sendq[sendq_head].sq_sendpage);
    448230                outb_reg0(dep, DP_TBCR1, size >> 8);
    449                 outb_reg0(dep, DP_TBCR0, size &0xff);
    450                 outb_reg0(dep, DP_CR, CR_TXP | CR_EXTRA);/* there it goes.. */
    451         }
    452         else
    453                 dep->de_sendq[sendq_head].sq_size= size;
     231                outb_reg0(dep, DP_TBCR0, size & 0xff);
     232                outb_reg0(dep, DP_CR, CR_TXP | CR_EXTRA);  /* there it goes .. */
     233        } else
     234                dep->de_sendq[sendq_head].sq_size = size;
    454235       
    455236        if (++sendq_head == dep->de_sendq_nr)
    456                 sendq_head= 0;
     237                sendq_head = 0;
     238       
    457239        assert(sendq_head < SENDQ_NR);
    458         dep->de_sendq_head= sendq_head;
    459 
    460 //      dep->de_flags |= DEF_PACK_SEND;
    461 
    462         /* If the interrupt handler called, don't send a reply. The reply
    463          * will be sent after all interrupts are handled.
    464          */
     240        dep->de_sendq_head = sendq_head;
     241        dep->sending = true;
     242       
    465243        if (from_int)
    466244                return EOK;
    467         reply(dep, OK, FALSE);
    468 
    469         assert(dep->de_mode == DEM_ENABLED);
    470         assert(dep->de_flags &DEF_ENABLED);
     245       
     246        dep->sending = false;
     247       
    471248        return EOK;
    472249}
    473250
    474 /*===========================================================================*
    475  *                              dp_init                                      *
    476  *===========================================================================*/
    477 void dp_init(dep)
    478 dpeth_t *dep;
     251void dp_init(dpeth_t *dep)
    479252{
    480253        int dp_rcr_reg;
    481         int i;//, r;
    482 
     254        int i;
     255       
    483256        /* General initialization */
    484         dep->de_flags = DEF_EMPTY;
    485         (*dep->de_initf)(dep);
    486 
    487 //      dp_confaddr(dep);
    488 
    489         if (debug)
    490         {
    491                 printf("%s: Ethernet address ", dep->de_name);
    492                 for (i= 0; i < 6; i++)
    493                         printf("%x%c", dep->de_address.ea_addr[i],
    494                                                         i < 5 ? ':' : '\n');
    495         }
    496 
    497         /* Map buffer */
    498         map_hw_buffer(dep);
    499 
    500         /* Initialization of the dp8390 following the mandatory procedure
     257        dep->enabled = false;
     258        dep->stopped = false;
     259        dep->sending = false;
     260        dep->send_avail = false;
     261        ne_init(dep);
     262       
     263        printf("Ethernet address ");
     264        for (i = 0; i < 6; i++)
     265                printf("%x%c", dep->de_address.ea_addr[i], i < 5 ? ':' : '\n');
     266       
     267        /*
     268         * Initialization of the dp8390 following the mandatory procedure
    501269         * in reference manual ("DP8390D/NS32490D NIC Network Interface
    502270         * Controller", National Semiconductor, July 1995, Page 29).
    503271         */
     272       
    504273        /* Step 1: */
    505274        outb_reg0(dep, DP_CR, CR_PS_P0 | CR_STP | CR_DM_ABORT);
     275       
    506276        /* Step 2: */
    507277        if (dep->de_16bit)
     
    509279        else
    510280                outb_reg0(dep, DP_DCR, DCR_BYTEWIDE | DCR_8BYTES | DCR_BMS);
     281       
    511282        /* Step 3: */
    512283        outb_reg0(dep, DP_RBCR0, 0);
    513284        outb_reg0(dep, DP_RBCR1, 0);
     285       
    514286        /* Step 4: */
    515         dp_rcr_reg = 0;
    516         if (dep->de_flags &DEF_PROMISC)
    517                 dp_rcr_reg |= RCR_AB | RCR_PRO | RCR_AM;
    518         if (dep->de_flags &DEF_BROAD)
    519                 dp_rcr_reg |= RCR_AB;
    520         if (dep->de_flags &DEF_MULTI)
    521                 dp_rcr_reg |= RCR_AM;
     287        dp_rcr_reg = RCR_AB;  /* Enable broadcasts */
     288       
    522289        outb_reg0(dep, DP_RCR, dp_rcr_reg);
     290       
    523291        /* Step 5: */
    524292        outb_reg0(dep, DP_TCR, TCR_INTERNAL);
     293       
    525294        /* Step 6: */
    526295        outb_reg0(dep, DP_BNRY, dep->de_startpage);
    527296        outb_reg0(dep, DP_PSTART, dep->de_startpage);
    528297        outb_reg0(dep, DP_PSTOP, dep->de_stoppage);
     298       
    529299        /* Step 7: */
    530300        outb_reg0(dep, DP_ISR, 0xFF);
     301       
    531302        /* Step 8: */
    532303        outb_reg0(dep, DP_IMR, IMR_PRXE | IMR_PTXE | IMR_RXEE | IMR_TXEE |
    533                 IMR_OVWE | IMR_CNTE);
     304            IMR_OVWE | IMR_CNTE);
     305       
    534306        /* Step 9: */
    535307        outb_reg0(dep, DP_CR, CR_PS_P1 | CR_DM_ABORT | CR_STP);
    536 
     308       
    537309        outb_reg1(dep, DP_PAR0, dep->de_address.ea_addr[0]);
    538310        outb_reg1(dep, DP_PAR1, dep->de_address.ea_addr[1]);
     
    541313        outb_reg1(dep, DP_PAR4, dep->de_address.ea_addr[4]);
    542314        outb_reg1(dep, DP_PAR5, dep->de_address.ea_addr[5]);
    543 
     315       
    544316        outb_reg1(dep, DP_MAR0, 0xff);
    545317        outb_reg1(dep, DP_MAR1, 0xff);
     
    550322        outb_reg1(dep, DP_MAR6, 0xff);
    551323        outb_reg1(dep, DP_MAR7, 0xff);
    552 
     324       
    553325        outb_reg1(dep, DP_CURR, dep->de_startpage + 1);
     326       
    554327        /* Step 10: */
    555328        outb_reg0(dep, DP_CR, CR_DM_ABORT | CR_STA);
     329       
    556330        /* Step 11: */
    557331        outb_reg0(dep, DP_TCR, TCR_NORMAL);
    558 
    559         inb_reg0(dep, DP_CNTR0);                /* reset counters by reading */
     332       
     333        inb_reg0(dep, DP_CNTR0);  /* Reset counters by reading */
    560334        inb_reg0(dep, DP_CNTR1);
    561335        inb_reg0(dep, DP_CNTR2);
    562 
     336       
    563337        /* Finish the initialization. */
    564         dep->de_flags |= DEF_ENABLED;
    565         for (i= 0; i<dep->de_sendq_nr; i++)
     338        dep->enabled = true;
     339        for (i = 0; i < dep->de_sendq_nr; i++)
    566340                dep->de_sendq[i].sq_filled= 0;
    567         dep->de_sendq_head= 0;
    568         dep->de_sendq_tail= 0;
    569         if (!dep->de_prog_IO)
    570         {
    571                 dep->de_user2nicf= dp_user2nic;
    572 //              dep->de_user2nicf_s= dp_user2nic_s;
    573                 dep->de_nic2userf= dp_nic2user;
    574 //              dep->de_nic2userf_s= dp_nic2user_s;
    575                 dep->de_getblockf= dp_getblock;
    576         }
    577         else if (dep->de_16bit)
    578         {
    579                 dep->de_user2nicf= dp_pio16_user2nic;
    580 //              dep->de_user2nicf_s= dp_pio16_user2nic_s;
    581                 dep->de_nic2userf= dp_pio16_nic2user;
    582 //              dep->de_nic2userf_s= dp_pio16_nic2user_s;
    583                 dep->de_getblockf= dp_pio16_getblock;
    584         }
    585         else
    586         {
    587                 dep->de_user2nicf= dp_pio8_user2nic;
    588 //              dep->de_user2nicf_s= dp_pio8_user2nic_s;
    589                 dep->de_nic2userf= dp_pio8_nic2user;
    590 //              dep->de_nic2userf_s= dp_pio8_nic2user_s;
    591                 dep->de_getblockf= dp_pio8_getblock;
    592         }
    593 
    594         /* Set the interrupt handler and policy. Do not automatically
    595          * reenable interrupts. Return the IRQ line number on interrupts.
    596          */
    597 /*      dep->de_hook = dep->de_irq;
    598         r= sys_irqsetpolicy(dep->de_irq, 0, &dep->de_hook);
    599         if (r != OK)
    600                 panic("DP8390", "sys_irqsetpolicy failed", r);
    601 
    602         r= sys_irqenable(&dep->de_hook);
    603         if (r != OK)
    604         {
    605                 panic("DP8390", "unable enable interrupts", r);
    606         }
    607 */
    608 }
    609 
    610 /*===========================================================================*
    611  *                              dp_reinit                                    *
    612  *===========================================================================*/
    613 static void dp_reinit(dep)
    614 dpeth_t *dep;
     341       
     342        dep->de_sendq_head = 0;
     343        dep->de_sendq_tail = 0;
     344}
     345
     346static void dp_reinit(dpeth_t *dep)
    615347{
    616348        int dp_rcr_reg;
    617 
     349       
    618350        outb_reg0(dep, DP_CR, CR_PS_P0 | CR_EXTRA);
    619 
    620         dp_rcr_reg = 0;
    621         if (dep->de_flags &DEF_PROMISC)
    622                 dp_rcr_reg |= RCR_AB | RCR_PRO | RCR_AM;
    623         if (dep->de_flags &DEF_BROAD)
    624                 dp_rcr_reg |= RCR_AB;
    625         if (dep->de_flags &DEF_MULTI)
    626                 dp_rcr_reg |= RCR_AM;
     351       
     352        /* Enable broadcasts */
     353        dp_rcr_reg = RCR_AB;
     354       
    627355        outb_reg0(dep, DP_RCR, dp_rcr_reg);
    628356}
    629357
    630 /*===========================================================================*
    631  *                              dp_reset                                     *
    632  *===========================================================================*/
    633 static void dp_reset(dep)
    634 dpeth_t *dep;
     358static void dp_reset(dpeth_t *dep)
    635359{
    636360        int i;
    637 
     361       
    638362        /* Stop chip */
    639363        outb_reg0(dep, DP_CR, CR_STP | CR_DM_ABORT);
    640364        outb_reg0(dep, DP_RBCR0, 0);
    641365        outb_reg0(dep, DP_RBCR1, 0);
    642         for (i= 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) &ISR_RST) == 0); i++)
     366       
     367        for (i = 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) & ISR_RST) == 0); i++)
    643368                ; /* Do nothing */
    644         outb_reg0(dep, DP_TCR, TCR_1EXTERNAL|TCR_OFST);
    645         outb_reg0(dep, DP_CR, CR_STA|CR_DM_ABORT);
     369       
     370        outb_reg0(dep, DP_TCR, TCR_1EXTERNAL | TCR_OFST);
     371        outb_reg0(dep, DP_CR, CR_STA | CR_DM_ABORT);
    646372        outb_reg0(dep, DP_TCR, TCR_NORMAL);
    647 
    648         /* Acknowledge the ISR_RDC (remote dma) interrupt. */
    649         for (i= 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) &ISR_RDC) == 0); i++)
     373       
     374        /* Acknowledge the ISR_RDC (remote DMA) interrupt. */
     375        for (i = 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) &ISR_RDC) == 0); i++)
    650376                ; /* Do nothing */
    651         outb_reg0(dep, DP_ISR, inb_reg0(dep, DP_ISR) &~ISR_RDC);
    652 
    653         /* Reset the transmit ring. If we were transmitting a packet, we
     377       
     378        outb_reg0(dep, DP_ISR, inb_reg0(dep, DP_ISR) & ~ISR_RDC);
     379       
     380        /*
     381         * Reset the transmit ring. If we were transmitting a packet, we
    654382         * pretend that the packet is processed. Higher layers will
    655383         * retransmit if the packet wasn't actually sent.
    656384         */
    657         dep->de_sendq_head= dep->de_sendq_tail= 0;
    658         for (i= 0; i<dep->de_sendq_nr; i++)
    659                 dep->de_sendq[i].sq_filled= 0;
    660         dp_send(dep);
    661         dep->de_flags &= ~DEF_STOPPED;
    662 }
    663 
    664 /*===========================================================================*
    665  *                              dp_check_ints                                *
    666  *===========================================================================*/
    667 void dp_check_ints(dep, isr)
    668 dpeth_t *dep;
    669 int isr;
    670 {
    671         int /*isr,*/ tsr;
     385        dep->de_sendq_head = 0;
     386        dep->de_sendq_tail = 0;
     387       
     388        for (i = 0; i < dep->de_sendq_nr; i++)
     389                dep->de_sendq[i].sq_filled = 0;
     390       
     391        dep->send_avail = false;
     392        dep->stopped = false;
     393}
     394
     395static uint8_t isr_acknowledge(dpeth_t *dep)
     396{
     397        uint8_t isr = inb_reg0(dep, DP_ISR);
     398        if (isr != 0)
     399                outb_reg0(dep, DP_ISR, isr);
     400       
     401        return isr;
     402}
     403
     404void dp_check_ints(int nil_phone, device_id_t device_id, dpeth_t *dep, uint8_t isr)
     405{
     406        int tsr;
    672407        int size, sendq_tail;
    673 
    674         if (!(dep->de_flags &DEF_ENABLED))
    675                 panic("", "dp8390: got premature interrupt", NO_NUM);
    676 
    677         for(;;)
    678         {
    679 //              isr = inb_reg0(dep, DP_ISR);
    680                 if (!isr)
    681                         break;
    682                 outb_reg0(dep, DP_ISR, isr);
    683                 if (isr &(ISR_PTX|ISR_TXE))
    684                 {
    685                         if (isr &ISR_TXE)
    686                         {
    687 #if DEBUG
    688  {printf("%s: got send Error\n", dep->de_name);}
    689 #endif
     408       
     409        for (; (isr & 0x7f) != 0; isr = isr_acknowledge(dep)) {
     410                if (isr & (ISR_PTX | ISR_TXE)) {
     411                        if (isr & ISR_TXE)
    690412                                dep->de_stat.ets_sendErr++;
     413                        else {
     414                                tsr = inb_reg0(dep, DP_TSR);
     415                               
     416                                if (tsr & TSR_PTX)
     417                                        dep->de_stat.ets_packetT++;
     418                               
     419                                if (tsr & TSR_COL)
     420                                        dep->de_stat.ets_collision++;
     421                               
     422                                if (tsr & TSR_ABT)
     423                                        dep->de_stat.ets_transAb++;
     424                               
     425                                if (tsr & TSR_CRS)
     426                                        dep->de_stat.ets_carrSense++;
     427                               
     428                                if ((tsr & TSR_FU) && (++dep->de_stat.ets_fifoUnder <= 10))
     429                                        printf("FIFO underrun\n");
     430                               
     431                                if ((tsr & TSR_CDH) && (++dep->de_stat.ets_CDheartbeat <= 10))
     432                                        printf("CD heart beat failure\n");
     433                               
     434                                if (tsr & TSR_OWC)
     435                                        dep->de_stat.ets_OWC++;
    691436                        }
    692                         else
    693                         {
    694                                 tsr = inb_reg0(dep, DP_TSR);
    695 
    696                                 if (tsr &TSR_PTX) dep->de_stat.ets_packetT++;
    697 #if 0   /* Reserved in later manuals, should be ignored */
    698                                 if (!(tsr &TSR_DFR))
    699                                 {
    700                                         /* In most (all?) implementations of
    701                                          * the dp8390, this bit is set
    702                                          * when the packet is not deferred
    703                                          */
    704                                         dep->de_stat.ets_transDef++;
    705                                 }
    706 #endif
    707                                 if (tsr &TSR_COL) dep->de_stat.ets_collision++;
    708                                 if (tsr &TSR_ABT) dep->de_stat.ets_transAb++;
    709                                 if (tsr &TSR_CRS) dep->de_stat.ets_carrSense++;
    710                                 if (tsr &TSR_FU
    711                                         && ++dep->de_stat.ets_fifoUnder <= 10)
    712                                 {
    713                                         printf("%s: fifo underrun\n",
    714                                                 dep->de_name);
    715                                 }
    716                                 if (tsr &TSR_CDH
    717                                         && ++dep->de_stat.ets_CDheartbeat <= 10)
    718                                 {
    719                                         printf("%s: CD heart beat failure\n",
    720                                                 dep->de_name);
    721                                 }
    722                                 if (tsr &TSR_OWC) dep->de_stat.ets_OWC++;
    723                         }
    724                         sendq_tail= dep->de_sendq_tail;
    725 
    726                         if (!(dep->de_sendq[sendq_tail].sq_filled))
    727                         {
    728                                 /* Software bug? */
    729                                 assert(!debug);
    730 
    731                                 /* Or hardware bug? */
    732                                 printf(
    733                                 "%s: transmit interrupt, but not sending\n",
    734                                         dep->de_name);
     437                       
     438                        sendq_tail = dep->de_sendq_tail;
     439                       
     440                        if (!(dep->de_sendq[sendq_tail].sq_filled)) {
     441                                printf("PTX interrupt, but no frame to send\n");
    735442                                continue;
    736443                        }
    737                         dep->de_sendq[sendq_tail].sq_filled= 0;
     444                       
     445                        dep->de_sendq[sendq_tail].sq_filled = false;
     446                       
    738447                        if (++sendq_tail == dep->de_sendq_nr)
    739                                 sendq_tail= 0;
    740                         dep->de_sendq_tail= sendq_tail;
    741                         if (dep->de_sendq[sendq_tail].sq_filled)
    742                         {
    743                                 size= dep->de_sendq[sendq_tail].sq_size;
     448                                sendq_tail = 0;
     449                       
     450                        dep->de_sendq_tail = sendq_tail;
     451                       
     452                        if (dep->de_sendq[sendq_tail].sq_filled) {
     453                                size = dep->de_sendq[sendq_tail].sq_size;
    744454                                outb_reg0(dep, DP_TPSR,
    745                                         dep->de_sendq[sendq_tail].sq_sendpage);
     455                                    dep->de_sendq[sendq_tail].sq_sendpage);
    746456                                outb_reg0(dep, DP_TBCR1, size >> 8);
    747                                 outb_reg0(dep, DP_TBCR0, size &0xff);
     457                                outb_reg0(dep, DP_TBCR0, size & 0xff);
    748458                                outb_reg0(dep, DP_CR, CR_TXP | CR_EXTRA);
    749459                        }
    750 //                      if (dep->de_flags &DEF_SEND_AVAIL)
    751                                 dp_send(dep);
    752                 }
    753 
    754                 if (isr &ISR_PRX)
    755                 {
    756                         /* Only call dp_recv if there is a read request */
    757 //                      if (dep->de_flags) &DEF_READING)
    758                                 dp_recv(dep);
    759                 }
    760                
    761                 if (isr &ISR_RXE) dep->de_stat.ets_recvErr++;
    762                 if (isr &ISR_CNT)
    763                 {
     460                       
     461                        dep->send_avail = false;
     462                }
     463               
     464                if (isr & ISR_PRX)
     465                        dp_recv(nil_phone, device_id, dep);
     466               
     467                if (isr & ISR_RXE)
     468                        dep->de_stat.ets_recvErr++;
     469               
     470                if (isr & ISR_CNT) {
    764471                        dep->de_stat.ets_CRCerr += inb_reg0(dep, DP_CNTR0);
    765472                        dep->de_stat.ets_frameAll += inb_reg0(dep, DP_CNTR1);
    766473                        dep->de_stat.ets_missedP += inb_reg0(dep, DP_CNTR2);
    767474                }
    768                 if (isr &ISR_OVW)
    769                 {
     475               
     476                if (isr & ISR_OVW)
    770477                        dep->de_stat.ets_OVW++;
    771 #if 0
    772                         {printW(); printf(
    773                                 "%s: got overwrite warning\n", dep->de_name);}
    774 #endif
    775 /*                      if (dep->de_flags &DEF_READING)
    776                         {
    777                                 printf(
    778 "dp_check_ints: strange: overwrite warning and pending read request\n");
    779                                 dp_recv(dep);
    780                         }
    781 */              }
    782                 if (isr &ISR_RDC)
    783                 {
     478               
     479                if (isr & ISR_RDC) {
    784480                        /* Nothing to do */
    785481                }
    786                 if (isr &ISR_RST)
    787                 {
    788                         /* this means we got an interrupt but the ethernet
    789                          * chip is shutdown. We set the flag DEF_STOPPED,
     482               
     483                if (isr & ISR_RST) {
     484                        /*
     485                         * This means we got an interrupt but the ethernet
     486                         * chip is shutdown. We set the flag 'stopped'
    790487                         * and continue processing arrived packets. When the
    791488                         * receive buffer is empty, we reset the dp8390.
    792489                         */
    793 #if 0
    794                          {printW(); printf(
    795                                 "%s: NIC stopped\n", dep->de_name);}
    796 #endif
    797                         dep->de_flags |= DEF_STOPPED;
     490                        dep->stopped = true;
    798491                        break;
    799492                }
    800                 isr = inb_reg0(dep, DP_ISR);
    801         }
    802 //      if ((dep->de_flags &(DEF_READING|DEF_STOPPED)) ==
    803 //                                              (DEF_READING|DEF_STOPPED))
    804         if ((dep->de_flags &DEF_STOPPED) == DEF_STOPPED)
    805         {
    806                 /* The chip is stopped, and all arrived packets are
    807                  * delivered.
     493        }
     494       
     495        if (dep->stopped) {
     496                /*
     497                 * The chip is stopped, and all arrived
     498                 * frames are delivered.
    808499                 */
    809500                dp_reset(dep);
    810501        }
    811 }
    812 
    813 /*===========================================================================*
    814  *                              dp_recv                                      *
    815  *===========================================================================*/
    816 static void dp_recv(dep)
    817 dpeth_t *dep;
     502       
     503        dep->sending = false;
     504}
     505
     506static void dp_getblock(dpeth_t *dep, int page, size_t offset, size_t size, void *dst)
     507{
     508        offset = page * DP_PAGESIZE + offset;
     509       
     510        outb_reg0(dep, DP_RBCR0, size & 0xff);
     511        outb_reg0(dep, DP_RBCR1, size >> 8);
     512        outb_reg0(dep, DP_RSAR0, offset & 0xff);
     513        outb_reg0(dep, DP_RSAR1, offset >> 8);
     514        outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
     515       
     516        if (dep->de_16bit) {
     517                assert((size % 2) == 0);
     518                insw(dep->de_data_port, dst, size);
     519        } else
     520                insb(dep->de_data_port, dst, size);
     521}
     522
     523static void dp_recv(int nil_phone, device_id_t device_id, dpeth_t *dep)
    818524{
    819525        dp_rcvhdr_t header;
    820         //unsigned pageno, curr, next;
    821526        int pageno, curr, next;
    822         vir_bytes length;
     527        size_t length;
    823528        int packet_processed, r;
    824         u16_t eth_type;
    825 
    826         packet_processed = FALSE;
     529        uint16_t eth_type;
     530       
     531        packet_processed = false;
    827532        pageno = inb_reg0(dep, DP_BNRY) + 1;
    828         if (pageno == dep->de_stoppage) pageno = dep->de_startpage;
    829 
    830         do
    831         {
     533        if (pageno == dep->de_stoppage)
     534                pageno = dep->de_startpage;
     535       
     536        do {
    832537                outb_reg0(dep, DP_CR, CR_PS_P1 | CR_EXTRA);
    833538                curr = inb_reg1(dep, DP_CURR);
    834539                outb_reg0(dep, DP_CR, CR_PS_P0 | CR_EXTRA);
    835 
    836                 if (curr == pageno) break;
    837 
    838                 (dep->de_getblockf)(dep, pageno, (size_t)0, sizeof(header),
    839                         &header);
    840                 (dep->de_getblockf)(dep, pageno, sizeof(header) +
    841                         2*sizeof(ether_addr_t), sizeof(eth_type), &eth_type);
    842 
    843                 length = (header.dr_rbcl | (header.dr_rbch << 8)) -
    844                         sizeof(dp_rcvhdr_t);
     540               
     541                if (curr == pageno)
     542                        break;
     543               
     544                dp_getblock(dep, pageno, (size_t) 0, sizeof(header), &header);
     545                dp_getblock(dep, pageno, sizeof(header) +
     546                    2 * sizeof(ether_addr_t), sizeof(eth_type), &eth_type);
     547               
     548                length = (header.dr_rbcl | (header.dr_rbch << 8)) - sizeof(dp_rcvhdr_t);
    845549                next = header.dr_next;
    846                 if (length < ETH_MIN_PACK_SIZE ||
    847                         length > ETH_MAX_PACK_SIZE_TAGGED)
    848                 {
    849                         printf("%s: packet with strange length arrived: %d\n",
    850                                 dep->de_name, (int) length);
     550                if ((length < ETH_MIN_PACK_SIZE) || (length > ETH_MAX_PACK_SIZE_TAGGED)) {
     551                        printf("Packet with strange length arrived: %zu\n", length);
    851552                        next= curr;
    852                 }
    853                 else if (next < dep->de_startpage || next >= dep->de_stoppage)
    854                 {
    855                         printf("%s: strange next page\n", dep->de_name);
     553                } else if ((next < dep->de_startpage) || (next >= dep->de_stoppage)) {
     554                        printf("Strange next page\n");
    856555                        next= curr;
    857                 }
    858 /*              else if (eth_type == eth_ign_proto)
    859                 {
    860 */                      /* Hack: ignore packets of a given protocol, useful
    861                          * if you share a net with 80 computers sending
    862                          * Amoeba FLIP broadcasts.  (Protocol 0x8146.)
     556                } else if (header.dr_status & RSR_FO) {
     557                        /*
     558                         * This is very serious, so we issue a warning and
     559                         * reset the buffers
    863560                         */
    864 /*                      static int first= 1;
    865                         if (first)
    866                         {
    867                                 first= 0;
    868                                 printf("%s: dropping proto 0x%04x packets\n",
    869                                         dep->de_name,
    870                                         ntohs(eth_ign_proto));
    871                         }
    872                         dep->de_stat.ets_packetR++;
    873                 }
    874 */              else if (header.dr_status &RSR_FO)
    875                 {
    876                         /* This is very serious, so we issue a warning and
    877                          * reset the buffers */
    878                         printf("%s: fifo overrun, resetting receive buffer\n",
    879                                 dep->de_name);
     561                        printf("FIFO overrun, resetting receive buffer\n");
    880562                        dep->de_stat.ets_fifoOver++;
    881563                        next = curr;
    882                 }
    883                 else if ((header.dr_status &RSR_PRX) &&
    884                                            (dep->de_flags &DEF_ENABLED))
    885                 {
    886 //                      if (dep->de_safecopy_read)
    887 //                              r = dp_pkt2user_s(dep, pageno, length);
    888 //                      else
    889                                 r = dp_pkt2user(dep, pageno, length);
    890                         if (r != OK)
     564                } else if ((header.dr_status & RSR_PRX) && (dep->enabled)) {
     565                        r = dp_pkt2user(nil_phone, device_id, dep, pageno, length);
     566                        if (r != EOK)
    891567                                return;
    892 
    893                         packet_processed = TRUE;
     568                       
     569                        packet_processed = true;
    894570                        dep->de_stat.ets_packetR++;
    895571                }
     572               
    896573                if (next == dep->de_startpage)
    897574                        outb_reg0(dep, DP_BNRY, dep->de_stoppage - 1);
    898575                else
    899576                        outb_reg0(dep, DP_BNRY, next - 1);
    900 
     577               
    901578                pageno = next;
    902         }
    903         while (!packet_processed);
    904 }
    905 
    906 /*===========================================================================*
    907  *                              dp_send                                      *
    908  *===========================================================================*/
    909 static void dp_send(dep)
    910 dpeth_t *dep;
    911 {
    912         packet_t *packet;
    913 
    914 //      if (!(dep->de_flags &DEF_SEND_AVAIL))
    915 //              return;
    916 
    917         if(dep->packet_queue){
    918                 packet = dep->packet_queue;
    919                 dep->packet_queue = pq_detach(packet);
    920                 do_pwrite(dep, packet, TRUE);
    921                 netif_pq_release(packet_get_id(packet));
    922                 -- dep->packet_count;
    923         }
    924 //      if(! dep->packet_queue){
    925 //              dep->de_flags &= ~DEF_SEND_AVAIL;
    926 //      }
    927 /*      switch(dep->de_sendmsg.m_type)
    928         {
    929         case DL_WRITE:  do_vwrite(&dep->de_sendmsg, TRUE, FALSE);       break;
    930         case DL_WRITEV: do_vwrite(&dep->de_sendmsg, TRUE, TRUE);        break;
    931         case DL_WRITEV_S: do_vwrite_s(&dep->de_sendmsg, TRUE);  break;
    932         default:
    933                 panic("", "dp8390: wrong type", dep->de_sendmsg.m_type);
    934                 break;
    935         }
    936 */
    937 }
    938 
    939 /*===========================================================================*
    940  *                              dp_getblock                                  *
    941  *===========================================================================*/
    942 static void dp_getblock(dep, page, offset, size, dst)
    943 dpeth_t *dep;
    944 int page;
    945 size_t offset;
    946 size_t size;
    947 void *dst;
    948 {
    949 //      int r;
    950 
    951         offset = page * DP_PAGESIZE + offset;
    952 
    953         memcpy(dst, dep->de_locmem + offset, size);
    954 }
    955 
    956 /*===========================================================================*
    957  *                              dp_pio8_getblock                             *
    958  *===========================================================================*/
    959 static void dp_pio8_getblock(dep, page, offset, size, dst)
    960 dpeth_t *dep;
    961 int page;
    962 size_t offset;
    963 size_t size;
    964 void *dst;
    965 {
    966         offset = page * DP_PAGESIZE + offset;
    967         outb_reg0(dep, DP_RBCR0, size &0xFF);
    968         outb_reg0(dep, DP_RBCR1, size >> 8);
    969         outb_reg0(dep, DP_RSAR0, offset &0xFF);
    970         outb_reg0(dep, DP_RSAR1, offset >> 8);
     579        } while (!packet_processed);
     580}
     581
     582static void dp_nic2user(dpeth_t *dep, int nic_addr, void *buf, size_t offset, size_t size)
     583{
     584        size_t ecount = size & ~1;
     585       
     586        if (dep->de_16bit) {
     587                outb_reg0(dep, DP_RBCR0, ecount & 0xFF);
     588                outb_reg0(dep, DP_RBCR1, ecount >> 8);
     589        } else {
     590                outb_reg0(dep, DP_RBCR0, size & 0xff);
     591                outb_reg0(dep, DP_RBCR1, size >> 8);
     592        }
     593       
     594        outb_reg0(dep, DP_RSAR0, nic_addr & 0xff);
     595        outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
    971596        outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    972 
    973         insb(dep->de_data_port, dst, size);
    974 }
    975 
    976 /*===========================================================================*
    977  *                              dp_pio16_getblock                            *
    978  *===========================================================================*/
    979 static void dp_pio16_getblock(dep, page, offset, size, dst)
    980 dpeth_t *dep;
    981 int page;
    982 size_t offset;
    983 size_t size;
    984 void *dst;
    985 {
    986         offset = page * DP_PAGESIZE + offset;
    987         outb_reg0(dep, DP_RBCR0, size &0xFF);
    988         outb_reg0(dep, DP_RBCR1, size >> 8);
    989         outb_reg0(dep, DP_RSAR0, offset &0xFF);
    990         outb_reg0(dep, DP_RSAR1, offset >> 8);
    991         outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    992 
    993         assert (!(size &1));
    994         insw(dep->de_data_port, dst, size);
    995 }
    996 
    997 /*===========================================================================*
    998  *                              dp_pkt2user                                  *
    999  *===========================================================================*/
    1000 static int dp_pkt2user(dep, page, length)
    1001 dpeth_t *dep;
    1002 int page, length;
     597       
     598        if (dep->de_16bit) {
     599                void *ptr = buf + offset;
     600               
     601                if (ecount != 0) {
     602                        insw(dep->de_data_port, ptr, ecount);
     603                        size -= ecount;
     604                        offset += ecount;
     605                        ptr += ecount;
     606                }
     607               
     608                if (size) {
     609                        assert(size == 1);
     610                       
     611                        uint16_t two_bytes = inw(dep->de_data_port);
     612                        memcpy(ptr, &(((uint8_t *) &two_bytes)[0]), 1);
     613                }
     614        } else
     615                insb(dep->de_data_port, buf + offset, size);
     616}
     617
     618static int dp_pkt2user(int nil_phone, device_id_t device_id, dpeth_t *dep, int page, int length)
    1003619{
    1004620        int last, count;
    1005621        packet_t *packet;
    1006 
    1007 //      if (!(dep->de_flags &DEF_READING))
    1008 //              return EGENERIC;
    1009 
     622       
    1010623        packet = netif_packet_get_1(length);
    1011         if(! packet){
     624        if (!packet)
    1012625                return ENOMEM;
    1013         }
    1014         dep->de_read_iovec.iod_iovec[0].iov_addr = (vir_bytes) packet_suffix(packet, length);
    1015         dep->de_read_iovec.iod_iovec[0].iov_size = length;
    1016         dep->de_read_iovec.iod_iovec_s = 1;
    1017         dep->de_read_iovec.iod_iovec_addr = (uintptr_t) NULL;
    1018 
     626       
     627        void *buf = packet_suffix(packet, length);
     628       
    1019629        last = page + (length - 1) / DP_PAGESIZE;
    1020         if (last >= dep->de_stoppage)
    1021         {
    1022                 count = (dep->de_stoppage - page) * DP_PAGESIZE -
    1023                         sizeof(dp_rcvhdr_t);
    1024 
    1025                 /* Save read_iovec since we need it twice. */
    1026                 dep->de_tmp_iovec = dep->de_read_iovec;
    1027                 (dep->de_nic2userf)(dep, page * DP_PAGESIZE +
    1028                         sizeof(dp_rcvhdr_t), &dep->de_tmp_iovec, 0, count);
    1029                 (dep->de_nic2userf)(dep, dep->de_startpage * DP_PAGESIZE,
    1030                         &dep->de_read_iovec, count, length - count);
    1031         }
    1032         else
    1033         {
    1034                 (dep->de_nic2userf)(dep, page * DP_PAGESIZE +
    1035                         sizeof(dp_rcvhdr_t), &dep->de_read_iovec, 0, length);
    1036         }
    1037 
    1038         dep->de_read_s = length;
    1039         dep->de_flags |= DEF_PACK_RECV;
    1040 //      dep->de_flags &= ~DEF_READING;
    1041 
    1042         if(dep->received_count >= MAX_PACKETS){
    1043                 netif_pq_release(packet_get_id(packet));
    1044                 return ELIMIT;
    1045         }else{
    1046                 if(pq_add(&dep->received_queue, packet, 0, 0) == EOK){
    1047                         ++ dep->received_count;
    1048                 }else{
    1049                         netif_pq_release(packet_get_id(packet));
    1050                 }
    1051         }
    1052         return OK;
    1053 }
    1054 
    1055 /*===========================================================================*
    1056  *                              dp_user2nic                                  *
    1057  *===========================================================================*/
    1058 static void dp_user2nic(dep, iovp, offset, nic_addr, count)
    1059 dpeth_t *dep;
    1060 iovec_dat_t *iovp;
    1061 vir_bytes offset;
    1062 int nic_addr;
    1063 vir_bytes count;
    1064 {
    1065         vir_bytes vir_hw;//, vir_user;
    1066         //int bytes, i, r;
    1067         int i, r;
    1068         vir_bytes bytes;
    1069 
    1070         vir_hw = (vir_bytes)dep->de_locmem + nic_addr;
    1071 
    1072         i= 0;
    1073         while (count > 0)
    1074         {
    1075                 if (i >= IOVEC_NR)
    1076                 {
    1077                         dp_next_iovec(iovp);
    1078                         i= 0;
    1079                         continue;
    1080                 }
    1081                 assert(i < iovp->iod_iovec_s);
    1082                 if (offset >= iovp->iod_iovec[i].iov_size)
    1083                 {
    1084                         offset -= iovp->iod_iovec[i].iov_size;
    1085                         i++;
    1086                         continue;
    1087                 }
    1088                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1089                 if (bytes > count)
    1090                         bytes = count;
    1091 
    1092                 r= sys_vircopy(iovp->iod_proc_nr, D,
    1093                         iovp->iod_iovec[i].iov_addr + offset,
    1094                         SELF, D, vir_hw, bytes);
    1095                 if (r != OK)
    1096                         panic("DP8390", "dp_user2nic: sys_vircopy failed", r);
    1097 
    1098                 count -= bytes;
    1099                 vir_hw += bytes;
    1100                 offset += bytes;
    1101         }
    1102         assert(count == 0);
    1103 }
    1104 
    1105 /*===========================================================================*
    1106  *                              dp_pio8_user2nic                             *
    1107  *===========================================================================*/
    1108 static void dp_pio8_user2nic(dep, iovp, offset, nic_addr, count)
    1109 dpeth_t *dep;
    1110 iovec_dat_t *iovp;
    1111 vir_bytes offset;
    1112 int nic_addr;
    1113 vir_bytes count;
    1114 {
    1115 //      phys_bytes phys_user;
    1116         int i;
    1117         vir_bytes bytes;
    1118 
    1119         outb_reg0(dep, DP_ISR, ISR_RDC);
    1120 
    1121         outb_reg0(dep, DP_RBCR0, count &0xFF);
    1122         outb_reg0(dep, DP_RBCR1, count >> 8);
    1123         outb_reg0(dep, DP_RSAR0, nic_addr &0xFF);
    1124         outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
    1125         outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
    1126 
    1127         i= 0;
    1128         while (count > 0)
    1129         {
    1130                 if (i >= IOVEC_NR)
    1131                 {
    1132                         dp_next_iovec(iovp);
    1133                         i= 0;
    1134                         continue;
    1135                 }
    1136                 assert(i < iovp->iod_iovec_s);
    1137                 if (offset >= iovp->iod_iovec[i].iov_size)
    1138                 {
    1139                         offset -= iovp->iod_iovec[i].iov_size;
    1140                         i++;
    1141                         continue;
    1142                 }
    1143                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1144                 if (bytes > count)
    1145                         bytes = count;
    1146 
    1147                 do_vir_outsb(dep->de_data_port, iovp->iod_proc_nr,
    1148                         iovp->iod_iovec[i].iov_addr + offset, bytes);
    1149                 count -= bytes;
    1150                 offset += bytes;
    1151         }
    1152         assert(count == 0);
    1153 
    1154         for (i= 0; i<100; i++)
    1155         {
    1156                 if (inb_reg0(dep, DP_ISR) &ISR_RDC)
    1157                         break;
    1158         }
    1159         if (i == 100)
    1160         {
    1161                 panic("", "dp8390: remote dma failed to complete", NO_NUM);
    1162         }
    1163 }
    1164 
    1165 /*===========================================================================*
    1166  *                              dp_pio16_user2nic                            *
    1167  *===========================================================================*/
    1168 static void dp_pio16_user2nic(dep, iovp, offset, nic_addr, count)
    1169 dpeth_t *dep;
    1170 iovec_dat_t *iovp;
    1171 vir_bytes offset;
    1172 int nic_addr;
    1173 vir_bytes count;
    1174 {
    1175         vir_bytes vir_user;
    1176         vir_bytes ecount;
    1177         int i, r, user_proc;
    1178         vir_bytes bytes;
    1179         //u8_t two_bytes[2];
    1180         u16_t two_bytes;
    1181         int odd_byte;
    1182 
    1183         ecount= (count+1) &~1;
    1184         odd_byte= 0;
    1185 
    1186         outb_reg0(dep, DP_ISR, ISR_RDC);
    1187         outb_reg0(dep, DP_RBCR0, ecount &0xFF);
    1188         outb_reg0(dep, DP_RBCR1, ecount >> 8);
    1189         outb_reg0(dep, DP_RSAR0, nic_addr &0xFF);
    1190         outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
    1191         outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
    1192 
    1193         i= 0;
    1194         while (count > 0)
    1195         {
    1196                 if (i >= IOVEC_NR)
    1197                 {
    1198                         dp_next_iovec(iovp);
    1199                         i= 0;
    1200                         continue;
    1201                 }
    1202                 assert(i < iovp->iod_iovec_s);
    1203                 if (offset >= iovp->iod_iovec[i].iov_size)
    1204                 {
    1205                         offset -= iovp->iod_iovec[i].iov_size;
    1206                         i++;
    1207                         continue;
    1208                 }
    1209                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1210                 if (bytes > count)
    1211                         bytes = count;
    1212 
    1213                 user_proc= iovp->iod_proc_nr;
    1214                 vir_user= iovp->iod_iovec[i].iov_addr + offset;
    1215                 if (odd_byte)
    1216                 {
    1217                         r= sys_vircopy(user_proc, D, vir_user,
    1218                         //      SELF, D, (vir_bytes)&two_bytes[1], 1);
    1219                                 SELF, D, (vir_bytes)&(((u8_t *)&two_bytes)[1]), 1);
    1220                         if (r != OK)
    1221                         {
    1222                                 panic("DP8390",
    1223                                         "dp_pio16_user2nic: sys_vircopy failed",
    1224                                         r);
    1225                         }
    1226                         //outw(dep->de_data_port, *(u16_t *)two_bytes);
    1227                         outw(dep->de_data_port, two_bytes);
    1228                         count--;
    1229                         offset++;
    1230                         bytes--;
    1231                         vir_user++;
    1232                         odd_byte= 0;
    1233                         if (!bytes)
    1234                                 continue;
    1235                 }
    1236                 ecount= bytes &~1;
    1237                 if (ecount != 0)
    1238                 {
    1239                         do_vir_outsw(dep->de_data_port, user_proc, vir_user,
    1240                                 ecount);
    1241                         count -= ecount;
    1242                         offset += ecount;
    1243                         bytes -= ecount;
    1244                         vir_user += ecount;
    1245                 }
    1246                 if (bytes)
    1247                 {
    1248                         assert(bytes == 1);
    1249                         r= sys_vircopy(user_proc, D, vir_user,
    1250                         //      SELF, D, (vir_bytes)&two_bytes[0], 1);
    1251                                 SELF, D, (vir_bytes)&(((u8_t *)&two_bytes)[0]), 1);
    1252                         if (r != OK)
    1253                         {
    1254                                 panic("DP8390",
    1255                                         "dp_pio16_user2nic: sys_vircopy failed",
    1256                                         r);
    1257                         }
    1258                         count--;
    1259                         offset++;
    1260                         bytes--;
    1261                         vir_user++;
    1262                         odd_byte= 1;
    1263                 }
    1264         }
    1265         assert(count == 0);
    1266 
    1267         if (odd_byte)
    1268                 //outw(dep->de_data_port, *(u16_t *)two_bytes);
    1269                 outw(dep->de_data_port, two_bytes);
    1270 
    1271         for (i= 0; i<100; i++)
    1272         {
    1273                 if (inb_reg0(dep, DP_ISR) &ISR_RDC)
    1274                         break;
    1275         }
    1276         if (i == 100)
    1277         {
    1278                 panic("", "dp8390: remote dma failed to complete", NO_NUM);
    1279         }
    1280 }
    1281 
    1282 /*===========================================================================*
    1283  *                              dp_nic2user                                  *
    1284  *===========================================================================*/
    1285 static void dp_nic2user(dep, nic_addr, iovp, offset, count)
    1286 dpeth_t *dep;
    1287 int nic_addr;
    1288 iovec_dat_t *iovp;
    1289 vir_bytes offset;
    1290 vir_bytes count;
    1291 {
    1292         vir_bytes vir_hw;//, vir_user;
    1293         vir_bytes bytes;
    1294         int i, r;
    1295 
    1296         vir_hw = (vir_bytes)dep->de_locmem + nic_addr;
    1297 
    1298         i= 0;
    1299         while (count > 0)
    1300         {
    1301                 if (i >= IOVEC_NR)
    1302                 {
    1303                         dp_next_iovec(iovp);
    1304                         i= 0;
    1305                         continue;
    1306                 }
    1307                 assert(i < iovp->iod_iovec_s);
    1308                 if (offset >= iovp->iod_iovec[i].iov_size)
    1309                 {
    1310                         offset -= iovp->iod_iovec[i].iov_size;
    1311                         i++;
    1312                         continue;
    1313                 }
    1314                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1315                 if (bytes > count)
    1316                         bytes = count;
    1317 
    1318                 r= sys_vircopy(SELF, D, vir_hw,
    1319                         iovp->iod_proc_nr, D,
    1320                         iovp->iod_iovec[i].iov_addr + offset, bytes);
    1321                 if (r != OK)
    1322                         panic("DP8390", "dp_nic2user: sys_vircopy failed", r);
    1323 
    1324                 count -= bytes;
    1325                 vir_hw += bytes;
    1326                 offset += bytes;
    1327         }
    1328         assert(count == 0);
    1329 }
    1330 
    1331 /*===========================================================================*
    1332  *                              dp_pio8_nic2user                             *
    1333  *===========================================================================*/
    1334 static void dp_pio8_nic2user(dep, nic_addr, iovp, offset, count)
    1335 dpeth_t *dep;
    1336 int nic_addr;
    1337 iovec_dat_t *iovp;
    1338 vir_bytes offset;
    1339 vir_bytes count;
    1340 {
    1341 //      phys_bytes phys_user;
    1342         int i;
    1343         vir_bytes bytes;
    1344 
    1345         outb_reg0(dep, DP_RBCR0, count &0xFF);
    1346         outb_reg0(dep, DP_RBCR1, count >> 8);
    1347         outb_reg0(dep, DP_RSAR0, nic_addr &0xFF);
    1348         outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
    1349         outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    1350 
    1351         i= 0;
    1352         while (count > 0)
    1353         {
    1354                 if (i >= IOVEC_NR)
    1355                 {
    1356                         dp_next_iovec(iovp);
    1357                         i= 0;
    1358                         continue;
    1359                 }
    1360                 assert(i < iovp->iod_iovec_s);
    1361                 if (offset >= iovp->iod_iovec[i].iov_size)
    1362                 {
    1363                         offset -= iovp->iod_iovec[i].iov_size;
    1364                         i++;
    1365                         continue;
    1366                 }
    1367                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1368                 if (bytes > count)
    1369                         bytes = count;
    1370 
    1371                 do_vir_insb(dep->de_data_port, iovp->iod_proc_nr,
    1372                         iovp->iod_iovec[i].iov_addr + offset, bytes);
    1373                 count -= bytes;
    1374                 offset += bytes;
    1375         }
    1376         assert(count == 0);
    1377 }
    1378 
    1379 /*===========================================================================*
    1380  *                              dp_pio16_nic2user                            *
    1381  *===========================================================================*/
    1382 static void dp_pio16_nic2user(dep, nic_addr, iovp, offset, count)
    1383 dpeth_t *dep;
    1384 int nic_addr;
    1385 iovec_dat_t *iovp;
    1386 vir_bytes offset;
    1387 vir_bytes count;
    1388 {
    1389         vir_bytes vir_user;
    1390         vir_bytes ecount;
    1391         int i, r, user_proc;
    1392         vir_bytes bytes;
    1393         //u8_t two_bytes[2];
    1394         u16_t two_bytes;
    1395         int odd_byte;
    1396 
    1397         ecount= (count+1) &~1;
    1398         odd_byte= 0;
    1399 
    1400         outb_reg0(dep, DP_RBCR0, ecount &0xFF);
    1401         outb_reg0(dep, DP_RBCR1, ecount >> 8);
    1402         outb_reg0(dep, DP_RSAR0, nic_addr &0xFF);
    1403         outb_reg0(dep, DP_RSAR1, nic_addr >> 8);
    1404         outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    1405 
    1406         i= 0;
    1407         while (count > 0)
    1408         {
    1409                 if (i >= IOVEC_NR)
    1410                 {
    1411                         dp_next_iovec(iovp);
    1412                         i= 0;
    1413                         continue;
    1414                 }
    1415                 assert(i < iovp->iod_iovec_s);
    1416                 if (offset >= iovp->iod_iovec[i].iov_size)
    1417                 {
    1418                         offset -= iovp->iod_iovec[i].iov_size;
    1419                         i++;
    1420                         continue;
    1421                 }
    1422                 bytes = iovp->iod_iovec[i].iov_size - offset;
    1423                 if (bytes > count)
    1424                         bytes = count;
    1425 
    1426                 user_proc= iovp->iod_proc_nr;
    1427                 vir_user= iovp->iod_iovec[i].iov_addr + offset;
    1428                 if (odd_byte)
    1429                 {
    1430                         //r= sys_vircopy(SELF, D, (vir_bytes)&two_bytes[1],
    1431                         r= sys_vircopy(SELF, D, (vir_bytes)&(((u8_t *)&two_bytes)[1]),
    1432                                 user_proc, D, vir_user,  1);
    1433                         if (r != OK)
    1434                         {
    1435                                 panic("DP8390",
    1436                                         "dp_pio16_nic2user: sys_vircopy failed",
    1437                                         r);
    1438                         }
    1439                         count--;
    1440                         offset++;
    1441                         bytes--;
    1442                         vir_user++;
    1443                         odd_byte= 0;
    1444                         if (!bytes)
    1445                                 continue;
    1446                 }
    1447                 ecount= bytes &~1;
    1448                 if (ecount != 0)
    1449                 {
    1450                         do_vir_insw(dep->de_data_port, user_proc, vir_user,
    1451                                 ecount);
    1452                         count -= ecount;
    1453                         offset += ecount;
    1454                         bytes -= ecount;
    1455                         vir_user += ecount;
    1456                 }
    1457                 if (bytes)
    1458                 {
    1459                         assert(bytes == 1);
    1460                         //*(u16_t *)two_bytes= inw(dep->de_data_port);
    1461                         two_bytes= inw(dep->de_data_port);
    1462                         //r= sys_vircopy(SELF, D, (vir_bytes)&two_bytes[0],
    1463                         r= sys_vircopy(SELF, D, (vir_bytes)&(((u8_t *)&two_bytes)[0]),
    1464                                 user_proc, D, vir_user,  1);
    1465                         if (r != OK)
    1466                         {
    1467                                 panic("DP8390",
    1468                                         "dp_pio16_nic2user: sys_vircopy failed",
    1469                                         r);
    1470                         }
    1471                         count--;
    1472                         offset++;
    1473                         bytes--;
    1474                         vir_user++;
    1475                         odd_byte= 1;
    1476                 }
    1477         }
    1478         assert(count == 0);
    1479 }
    1480 
    1481 /*===========================================================================*
    1482  *                              dp_next_iovec                                *
    1483  *===========================================================================*/
    1484 static void dp_next_iovec(iovp)
    1485 iovec_dat_t *iovp;
    1486 {
    1487         assert(iovp->iod_iovec_s > IOVEC_NR);
    1488 
    1489         iovp->iod_iovec_s -= IOVEC_NR;
    1490 
    1491         iovp->iod_iovec_addr += IOVEC_NR * sizeof(iovec_t);
    1492 
    1493         get_userdata(iovp->iod_proc_nr, iovp->iod_iovec_addr,
    1494                 (iovp->iod_iovec_s > IOVEC_NR ? IOVEC_NR : iovp->iod_iovec_s) *
    1495                 sizeof(iovec_t), iovp->iod_iovec);
    1496 }
    1497 
    1498 /*===========================================================================*
    1499  *                              conf_hw                                      *
    1500  *===========================================================================*/
    1501 static void conf_hw(dep)
    1502 dpeth_t *dep;
    1503 {
    1504 //      static eth_stat_t empty_stat = {0, 0, 0, 0, 0, 0        /* ,... */};
    1505 
    1506 //      int ifnr;
    1507 //      dp_conf_t *dcp;
    1508 
    1509 //      dep->de_mode= DEM_DISABLED;     /* Superfluous */
    1510 //      ifnr= dep-de_table;
    1511 
    1512 //      dcp= &dp_conf[ifnr];
    1513 //      update_conf(dep, dcp);
    1514 //      if (dep->de_mode != DEM_ENABLED)
    1515 //              return;
    1516         if (!wdeth_probe(dep) && !ne_probe(dep) && !el2_probe(dep))
    1517         {
    1518                 printf("%s: No ethernet card found at %#lx\n",
    1519                     dep->de_name, dep->de_base_port);
    1520                 dep->de_mode= DEM_DISABLED;
     630        if (last >= dep->de_stoppage) {
     631                count = (dep->de_stoppage - page) * DP_PAGESIZE - sizeof(dp_rcvhdr_t);
     632               
     633                dp_nic2user(dep, page * DP_PAGESIZE + sizeof(dp_rcvhdr_t),
     634                    buf, 0, count);
     635                dp_nic2user(dep, dep->de_startpage * DP_PAGESIZE,
     636                    buf, count, length - count);
     637        } else {
     638                dp_nic2user(dep, page * DP_PAGESIZE + sizeof(dp_rcvhdr_t),
     639                    buf, 0, length);
     640        }
     641       
     642        nil_received_msg(nil_phone, device_id, packet, SERVICE_NONE);
     643       
     644        return EOK;
     645}
     646
     647static void conf_hw(dpeth_t *dep)
     648{
     649        if (!ne_probe(dep)) {
     650                printf("No ethernet card found at %#lx\n", dep->de_base_port);
     651                dep->up = false;
    1521652                return;
    1522653        }
    1523 
    1524 /* XXX */ if (dep->de_linmem == 0) dep->de_linmem= 0xFFFF0000;
    1525 
    1526         dep->de_mode = DEM_ENABLED;
    1527 
    1528         dep->de_flags = DEF_EMPTY;
    1529 //      dep->de_stat = empty_stat;
    1530 }
    1531 
    1532 /*===========================================================================*
    1533  *                              map_hw_buffer                                *
    1534  *===========================================================================*/
    1535 static void map_hw_buffer(dep)
    1536 dpeth_t *dep;
    1537 {
    1538 //      int r;
    1539 //      size_t o, size;
    1540 //      char *buf, *abuf;
    1541 
    1542         if (dep->de_prog_IO)
    1543         {
    1544 #if 0
    1545                 if(debug){
    1546                         printf(
    1547                         "map_hw_buffer: programmed I/O, no need to map buffer\n");
    1548                 }
    1549 #endif
    1550                 dep->de_locmem = (char *)-dep->de_ramsize; /* trap errors */
    1551                 return;
    1552         }else{
    1553                 printf("map_hw_buffer: no buffer!\n");
    1554         }
    1555 
    1556 //      size = dep->de_ramsize + PAGE_SIZE;     /* Add PAGE_SIZE for
    1557 //                                               * alignment
    1558 //                                               */
    1559 //      buf= malloc(size);
    1560 //      if (buf == NULL)
    1561 //              panic(__FILE__, "map_hw_buffer: cannot malloc size", size);
    1562 //      o= PAGE_SIZE - ((vir_bytes)buf % PAGE_SIZE);
    1563 //      abuf= buf + o;
    1564 //      printf("buf at 0x%x, abuf at 0x%x\n", buf, abuf);
    1565 
    1566 //      r= sys_vm_map(SELF, 1 /* map */, (vir_bytes)abuf,
    1567 //                      dep->de_ramsize, (phys_bytes)dep->de_linmem);
    1568 //      if (r != OK)
    1569 //              panic(__FILE__, "map_hw_buffer: sys_vm_map failed", r);
    1570 //      dep->de_locmem = abuf;
    1571 }
    1572 
    1573 /*===========================================================================*
    1574  *                              reply                                        *
    1575  *===========================================================================*/
    1576 static void reply(dep, err, may_block)
    1577 dpeth_t *dep;
    1578 int err;
    1579 int may_block;
    1580 {
    1581 /*      message reply;
    1582         int status;
    1583         int r;
    1584 
    1585         status = 0;
    1586         if (dep->de_flags &DEF_PACK_SEND)
    1587                 status |= DL_PACK_SEND;
    1588         if (dep->de_flags &DEF_PACK_RECV)
    1589                 status |= DL_PACK_RECV;
    1590 
    1591         reply.m_type = DL_TASK_REPLY;
    1592         reply.DL_PORT = dep - de_table;
    1593         reply.DL_PROC = dep->de_client;
    1594         reply.DL_STAT = status | ((u32_t) err << 16);
    1595         reply.DL_COUNT = dep->de_read_s;
    1596         reply.DL_CLCK = 0;      *//* Don't know */
    1597 /*      r= send(dep->de_client, &reply);
    1598 
    1599         if (r == ELOCKED && may_block)
    1600         {
    1601 #if 0
    1602                 printf("send locked\n");
    1603 #endif
    1604                 return;
    1605         }
    1606 
    1607         if (r < 0)
    1608                 panic("", "dp8390: send failed:", r);
    1609        
    1610 */      dep->de_read_s = 0;
    1611 //      dep->de_flags &= ~(DEF_PACK_SEND | DEF_PACK_RECV);
    1612 }
    1613 
    1614 /*===========================================================================*
    1615  *                              get_userdata                                 *
    1616  *===========================================================================*/
    1617 static void get_userdata(user_proc, user_addr, count, loc_addr)
    1618 int user_proc;
    1619 vir_bytes user_addr;
    1620 vir_bytes count;
    1621 void *loc_addr;
    1622 {
    1623         int r;
    1624 
    1625         r= sys_vircopy(user_proc, D, user_addr,
    1626                 SELF, D, (vir_bytes)loc_addr, count);
    1627         if (r != OK)
    1628                 panic("DP8390", "get_userdata: sys_vircopy failed", r);
     654       
     655        dep->up = true;
     656        dep->enabled = false;
     657        dep->stopped = false;
     658        dep->sending = false;
     659        dep->send_avail = false;
    1629660}
    1630661
     
    1632663{
    1633664        size_t i;
    1634 
    1635         for(i = 0; i < size; ++ i){
     665       
     666        for (i = 0; i < size; i++)
    1636667                *((uint8_t *) buf + i) = inb(port);
    1637         }
    1638668}
    1639669
     
    1641671{
    1642672        size_t i;
    1643 
    1644         for(i = 0; i * 2 < size; ++ i){
     673       
     674        for (i = 0; i * 2 < size; i++)
    1645675                *((uint16_t *) buf + i) = inw(port);
    1646         }
    1647676}
    1648677
     
    1650679{
    1651680        size_t i;
    1652 
    1653         for(i = 0; i < size; ++ i){
     681       
     682        for (i = 0; i < size; i++)
    1654683                outb(port, *((uint8_t *) buf + i));
    1655         }
    1656684}
    1657685
     
    1659687{
    1660688        size_t i;
    1661 
    1662         for(i = 0; i * 2 < size; ++ i){
     689       
     690        for (i = 0; i * 2 < size; i++)
    1663691                outw(port, *((uint16_t *) buf + i));
    1664         }
    1665 }
    1666 
    1667 /*
    1668  * $PchId: dp8390.c,v 1.25 2005/02/10 17:32:07 philip Exp $
    1669  */
     692}
    1670693
    1671694/** @}
  • uspace/srv/hw/netif/dp8390/dp8390.h

    rf03d3786 rae1f70e  
    11/*
    2  * Copyright (c) 1987,1997, 2006, Vrije Universiteit, Amsterdam, The Netherlands All rights reserved. Redistribution and use of the MINIX 3 operating system in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
    3  *
    4  * * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
    5  * * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
    6  * * Neither the name of the Vrije Universiteit nor the names of the software authors or contributors may be used to endorse or promote products derived from this software without specific prior written permission.
    7  * * Any deviations from these conditions require written permission from the copyright holder in advance
    8  *
    9  *
    10  * Disclaimer
    11  *
    12  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS, AUTHORS, AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
     2 * Copyright (c) 2009 Lukas Mejdrech
     3 * Copyright (c) 2011 Martin Decky
     4 * All rights reserved.
     5 *
     6 * Redistribution and use in source and binary forms, with or without
     7 * modification, are permitted provided that the following conditions
     8 * are met:
     9 *
     10 * - Redistributions of source code must retain the above copyright
     11 *   notice, this list of conditions and the following disclaimer.
     12 * - Redistributions in binary form must reproduce the above copyright
     13 *   notice, this list of conditions and the following disclaimer in the
     14 *   documentation and/or other materials provided with the distribution.
     15 * - The name of the author may not be used to endorse or promote products
     16 *   derived from this software without specific prior written permission.
     17 *
     18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
    1319 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
    1420 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
    15  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR ANY AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
     21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
    1622 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
    1723 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     
    2026 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
    2127 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    22  *
    23  * Changes:
    24  *  2009 ported to HelenOS, Lukas Mejdrech
     28 */
     29
     30/*
     31 * This code is based upon the NE2000 driver for MINIX,
     32 * distributed according to a BSD-style license.
     33 *
     34 * Copyright (c) 1987, 1997, 2006 Vrije Universiteit
     35 * Copyright (c) 1992, 1994 Philip Homburg
     36 * Copyright (c) 1996 G. Falzoni
     37 *
    2538 */
    2639
     
    3750
    3851#include <net/packet.h>
    39 
    4052#include "dp8390_port.h"
    41 #include "local.h"
    42 
    43 /** Input/output size.
    44  */
    45 #define DP8390_IO_SIZE  0x020
    46 
    47 /*
    48 dp8390.h
    49 
    50 Created:        before Dec 28, 1992 by Philip Homburg
    51 */
     53
     54/** Input/output size */
     55#define DP8390_IO_SIZE  0x0020
    5256
    5357/* National Semiconductor DP8390 Network Interface Controller. */
    5458
    55                                 /* Page 0, for reading ------------- */
    56 #define DP_CR           0x0     /* Read side of Command Register     */
    57 #define DP_CLDA0        0x1     /* Current Local Dma Address 0       */
    58 #define DP_CLDA1        0x2     /* Current Local Dma Address 1       */
    59 #define DP_BNRY         0x3     /* Boundary Pointer                  */
    60 #define DP_TSR          0x4     /* Transmit Status Register          */
    61 #define DP_NCR          0x5     /* Number of Collisions Register     */
    62 #define DP_FIFO         0x6     /* Fifo ??                           */
    63 #define DP_ISR          0x7     /* Interrupt Status Register         */
    64 #define DP_CRDA0        0x8     /* Current Remote Dma Address 0      */
    65 #define DP_CRDA1        0x9     /* Current Remote Dma Address 1      */
    66 #define DP_DUM1         0xA     /* unused                            */
    67 #define DP_DUM2         0xB     /* unused                            */
    68 #define DP_RSR          0xC     /* Receive Status Register           */
    69 #define DP_CNTR0        0xD     /* Tally Counter 0                   */
    70 #define DP_CNTR1        0xE     /* Tally Counter 1                   */
    71 #define DP_CNTR2        0xF     /* Tally Counter 2                   */
    72 
    73                                 /* Page 0, for writing ------------- */
    74 #define DP_CR           0x0     /* Write side of Command Register    */
    75 #define DP_PSTART       0x1     /* Page Start Register               */
    76 #define DP_PSTOP        0x2     /* Page Stop Register                */
    77 #define DP_BNRY         0x3     /* Boundary Pointer                  */
    78 #define DP_TPSR         0x4     /* Transmit Page Start Register      */
    79 #define DP_TBCR0        0x5     /* Transmit Byte Count Register 0    */
    80 #define DP_TBCR1        0x6     /* Transmit Byte Count Register 1    */
    81 #define DP_ISR          0x7     /* Interrupt Status Register         */
    82 #define DP_RSAR0        0x8     /* Remote Start Address Register 0   */
    83 #define DP_RSAR1        0x9     /* Remote Start Address Register 1   */
    84 #define DP_RBCR0        0xA     /* Remote Byte Count Register 0      */
    85 #define DP_RBCR1        0xB     /* Remote Byte Count Register 1      */
    86 #define DP_RCR          0xC     /* Receive Configuration Register    */
    87 #define DP_TCR          0xD     /* Transmit Configuration Register   */
    88 #define DP_DCR          0xE     /* Data Configuration Register       */
    89 #define DP_IMR          0xF     /* Interrupt Mask Register           */
    90 
    91                                 /* Page 1, read/write -------------- */
    92 #define DP_CR           0x0     /* Command Register                  */
    93 #define DP_PAR0         0x1     /* Physical Address Register 0       */
    94 #define DP_PAR1         0x2     /* Physical Address Register 1       */
    95 #define DP_PAR2         0x3     /* Physical Address Register 2       */
    96 #define DP_PAR3         0x4     /* Physical Address Register 3       */
    97 #define DP_PAR4         0x5     /* Physical Address Register 4       */
    98 #define DP_PAR5         0x6     /* Physical Address Register 5       */
    99 #define DP_CURR         0x7     /* Current Page Register             */
    100 #define DP_MAR0         0x8     /* Multicast Address Register 0      */
    101 #define DP_MAR1         0x9     /* Multicast Address Register 1      */
    102 #define DP_MAR2         0xA     /* Multicast Address Register 2      */
    103 #define DP_MAR3         0xB     /* Multicast Address Register 3      */
    104 #define DP_MAR4         0xC     /* Multicast Address Register 4      */
    105 #define DP_MAR5         0xD     /* Multicast Address Register 5      */
    106 #define DP_MAR6         0xE     /* Multicast Address Register 6      */
    107 #define DP_MAR7         0xF     /* Multicast Address Register 7      */
     59/** Page 0, for reading */
     60#define DP_CR     0x00  /**< Command Register */
     61#define DP_CLDA0  0x01  /**< Current Local DMA Address 0 */
     62#define DP_CLDA1  0x02  /**< Current Local DMA Address 1 */
     63#define DP_BNRY   0x03  /**< Boundary Pointer */
     64#define DP_TSR    0x04  /**< Transmit Status Register */
     65#define DP_NCR    0x05  /**< Number of Collisions Register */
     66#define DP_FIFO   0x06  /**< FIFO */
     67#define DP_ISR    0x07  /**< Interrupt Status Register */
     68#define DP_CRDA0  0x08  /**< Current Remote DMA Address 0 */
     69#define DP_CRDA1  0x09  /**< Current Remote DMA Address 1 */
     70#define DP_RSR    0x0c  /**< Receive Status Register */
     71#define DP_CNTR0  0x0d  /**< Tally Counter 0 */
     72#define DP_CNTR1  0x0e  /**< Tally Counter 1 */
     73#define DP_CNTR2  0x0f  /**< Tally Counter 2 */
     74
     75/** Page 0, for writing */
     76#define DP_PSTART  0x01  /**< Page Start Register*/
     77#define DP_PSTOP   0x02  /**< Page Stop Register */
     78#define DP_TPSR    0x04  /**< Transmit Page Start Register */
     79#define DP_TBCR0   0x05  /**< Transmit Byte Count Register 0 */
     80#define DP_TBCR1   0x06  /**< Transmit Byte Count Register 1 */
     81#define DP_RSAR0   0x08  /**< Remote Start Address Register 0 */
     82#define DP_RSAR1   0x09  /**< Remote Start Address Register 1 */
     83#define DP_RBCR0   0x0a  /**< Remote Byte Count Register 0 */
     84#define DP_RBCR1   0x0b  /**< Remote Byte Count Register 1 */
     85#define DP_RCR     0x0c  /**< Receive Configuration Register */
     86#define DP_TCR     0x0d  /**< Transmit Configuration Register */
     87#define DP_DCR     0x0e  /**< Data Configuration Register */
     88#define DP_IMR     0x0f  /**< Interrupt Mask Register */
     89
     90/** Page 1, read/write */
     91#define DP_PAR0  0x01  /**< Physical Address Register 0 */
     92#define DP_PAR1  0x02  /**< Physical Address Register 1 */
     93#define DP_PAR2  0x03  /**< Physical Address Register 2 */
     94#define DP_PAR3  0x04  /**< Physical Address Register 3 */
     95#define DP_PAR4  0x05  /**< Physical Address Register 4 */
     96#define DP_PAR5  0x06  /**< Physical Address Register 5 */
     97#define DP_CURR  0x07  /**< Current Page Register */
     98#define DP_MAR0  0x08  /**< Multicast Address Register 0 */
     99#define DP_MAR1  0x09  /**< Multicast Address Register 1 */
     100#define DP_MAR2  0x0a  /**< Multicast Address Register 2 */
     101#define DP_MAR3  0x0b  /**< Multicast Address Register 3 */
     102#define DP_MAR4  0x0c  /**< Multicast Address Register 4 */
     103#define DP_MAR5  0x0d  /**< Multicast Address Register 5 */
     104#define DP_MAR6  0x0e  /**< Multicast Address Register 6 */
     105#define DP_MAR7  0x0f  /**< Multicast Address Register 7 */
    108106
    109107/* Bits in dp_cr */
     
    199197#define RSR_DFR         0x80    /* In later manuals: Deferring       */
    200198
    201 /** Type definition of the receive header.
    202  */
    203 typedef struct dp_rcvhdr
    204 {
    205         /** Copy of rsr.
    206          */
    207         u8_t dr_status;
    208         /** Pointer to next packet.
    209          */
    210         u8_t dr_next;
    211         /** Receive Byte Count Low.
    212          */
    213         u8_t dr_rbcl;
    214         /** Receive Byte Count High.
    215          */
    216         u8_t dr_rbch;
     199/** Type definition of the receive header
     200 *
     201 */
     202typedef struct dp_rcvhdr {
     203        /** Copy of rsr */
     204        uint8_t dr_status;
     205       
     206        /** Pointer to next packet */
     207        uint8_t dr_next;
     208       
     209        /** Receive Byte Count Low */
     210        uint8_t dr_rbcl;
     211       
     212        /** Receive Byte Count High */
     213        uint8_t dr_rbch;
    217214} dp_rcvhdr_t;
    218215
    219 /** Page size.
    220  */
    221 #define DP_PAGESIZE     256
    222 
    223 /* Some macros to simplify accessing the dp8390 */
    224 /** Reads 1 byte from the zero page register.
     216/** Page size */
     217#define DP_PAGESIZE  256
     218
     219/** Read 1 byte from the zero page register.
    225220 *  @param[in] dep The network interface structure.
    226221 *  @param[in] reg The register offset.
    227222 *  @returns The read value.
    228223 */
    229 #define inb_reg0(dep, reg)              (inb(dep->de_dp8390_port+reg))
    230 
    231 /** Writes 1 byte zero page register.
     224#define inb_reg0(dep, reg)  (inb(dep->de_dp8390_port + reg))
     225
     226/** Write 1 byte zero page register.
    232227 *  @param[in] dep The network interface structure.
    233228 *  @param[in] reg The register offset.
    234229 *  @param[in] data The value to be written.
    235230 */
    236 #define outb_reg0(dep, reg, data)       (outb(dep->de_dp8390_port+reg, data))
    237 
    238 /** Reads 1 byte from the first page register.
     231#define outb_reg0(dep, reg, data)  (outb(dep->de_dp8390_port + reg, data))
     232
     233/** Read 1 byte from the first page register.
    239234 *  @param[in] dep The network interface structure.
    240235 *  @param[in] reg The register offset.
    241236 *  @returns The read value.
    242237 */
    243 #define inb_reg1(dep, reg)              (inb(dep->de_dp8390_port+reg))
    244 
    245 /** Writes 1 byte first page register.
     238#define inb_reg1(dep, reg)  (inb(dep->de_dp8390_port + reg))
     239
     240/** Write 1 byte first page register.
    246241 *  @param[in] dep The network interface structure.
    247242 *  @param[in] reg The register offset.
    248243 *  @param[in] data The value to be written.
    249244 */
    250 #define outb_reg1(dep, reg, data)       (outb(dep->de_dp8390_port+reg, data))
    251 
    252 /* Software interface to the dp8390 driver */
    253 
    254 struct dpeth;
    255 struct iovec_dat;
    256 //struct iovec_dat_s;
    257 _PROTOTYPE(typedef void (*dp_initf_t), (struct dpeth *dep)              );
    258 _PROTOTYPE(typedef void (*dp_stopf_t), (struct dpeth *dep)              );
    259 _PROTOTYPE(typedef void (*dp_user2nicf_t), (struct dpeth *dep,
    260                         struct iovec_dat *iovp, vir_bytes offset,
    261                         int nic_addr, vir_bytes count) );
    262 //_PROTOTYPE(typedef void (*dp_user2nicf_s_t), (struct dpeth *dep,
    263 //                      struct iovec_dat_s *iovp, vir_bytes offset,
    264 //                      int nic_addr, vir_bytes count)                  );
    265 _PROTOTYPE(typedef void (*dp_nic2userf_t), (struct dpeth *dep,
    266                         int nic_addr, struct iovec_dat *iovp,
    267                         vir_bytes offset, vir_bytes count) );
    268 //_PROTOTYPE(typedef void (*dp_nic2userf_s_t), (struct dpeth *dep,
    269 //                      int nic_addr, struct iovec_dat_s *iovp,
    270 //                      vir_bytes offset, vir_bytes count)              );
    271 //#if 0
    272 //_PROTOTYPE(typedef void (*dp_getheaderf_t), (struct dpeth *dep,
    273 //                      int page, struct dp_rcvhdr *h, u16_t *eth_type) );
    274 //#endif
    275 _PROTOTYPE(typedef void (*dp_getblock_t), (struct dpeth *dep,
    276                 int page, size_t offset, size_t size, void *dst)        );
    277 
    278 /* iovectors are handled IOVEC_NR entries at a time. */
    279 //#define IOVEC_NR      16
    280 // no vectors allowed
    281 #define IOVEC_NR        1
    282 
    283 /*
    284 typedef int irq_hook_t;
    285 */
    286 typedef struct iovec_dat
    287 {
    288   iovec_t iod_iovec[IOVEC_NR];
    289   int iod_iovec_s;
    290   // no direct process access
    291   int iod_proc_nr;
    292   vir_bytes iod_iovec_addr;
    293 } iovec_dat_t;
    294 /*
    295 typedef struct iovec_dat_s
    296 {
    297   iovec_s_t iod_iovec[IOVEC_NR];
    298   int iod_iovec_s;
    299   int iod_proc_nr;
    300   cp_grant_id_t iod_grant;
    301   vir_bytes iod_iovec_offset;
    302 } iovec_dat_s_t;
    303 */
    304 #define SENDQ_NR        1       /* Maximum size of the send queue */
    305 #define SENDQ_PAGES     6       /* 6 * DP_PAGESIZE >= 1514 bytes */
    306 
    307 /** Maximum number of waiting packets to be sent or received.
    308  */
    309 #define MAX_PACKETS     4
    310 
    311 typedef struct dpeth
    312 {
    313         /** Outgoing packets queue.
    314          */
    315         packet_t *packet_queue;
    316         /** Outgoing packets count.
    317          */
    318         int packet_count;
    319 
    320         /** Received packets queue.
    321          */
    322         packet_t *received_queue;
    323         /** Received packets count.
    324          */
    325         int received_count;
    326 
    327         /* The de_base_port field is the starting point of the probe.
    328          * The conf routine also fills de_linmem and de_irq. If the probe
     245#define outb_reg1(dep, reg, data)  (outb(dep->de_dp8390_port + reg, data))
     246
     247#define SENDQ_NR     2  /* Maximum size of the send queue */
     248#define SENDQ_PAGES  6  /* 6 * DP_PAGESIZE >= 1514 bytes */
     249
     250typedef struct dpeth {
     251        /*
     252         * The de_base_port field is the starting point of the probe.
     253         * The conf routine also fills de_irq. If the probe
    329254         * routine knows the irq and/or memory address because they are
    330255         * hardwired in the board, the probe should modify these fields.
    331          * Futhermore, the probe routine should also fill in de_initf and
    332          * de_stopf fields with the appropriate function pointers and set
    333          * de_prog_IO iff programmed I/O is to be used.
    334256         */
    335257        port_t de_base_port;
    336         phys_bytes de_linmem;
    337         char *de_locmem;
    338258        int de_irq;
    339         int de_int_pending;
    340 //      irq_hook_t de_hook;
    341         dp_initf_t de_initf;
    342         dp_stopf_t de_stopf;
    343         int de_prog_IO;
    344         char de_name[sizeof("dp8390#n")];
    345 
    346         /* The initf function fills the following fields. Only cards that do
    347          * programmed I/O fill in the de_pata_port field.
    348          * In addition, the init routine has to fill in the sendq data
    349          * structures.
    350          */
     259       
    351260        ether_addr_t de_address;
    352261        port_t de_dp8390_port;
     
    357266        int de_startpage;
    358267        int de_stoppage;
    359 
    360         /* should be here - read even for ne2k isa init... */
    361         char de_pci;                    /* TRUE iff PCI device */
    362 
    363 #if ENABLE_PCI
    364         /* PCI config */
    365 //      char de_pci;                    /* TRUE iff PCI device */
    366 //      u8_t de_pcibus;
    367 //      u8_t de_pcidev;
    368 //      u8_t de_pcifunc;       
     268       
     269        /* Do it yourself send queue */
     270        struct sendq {
     271                int sq_filled;    /* this buffer contains a packet */
     272                int sq_size;      /* with this size */
     273                int sq_sendpage;  /* starting page of the buffer */
     274        } de_sendq[SENDQ_NR];
     275       
     276        int de_sendq_nr;
     277        int de_sendq_head;  /* Enqueue at the head */
     278        int de_sendq_tail;  /* Dequeue at the tail */
     279       
     280        /* Fields for internal use by the dp8390 driver. */
     281        eth_stat_t de_stat;
     282       
     283        /* Driver flags */
     284        bool up;
     285        bool enabled;
     286        bool stopped;
     287        bool sending;
     288        bool send_avail;
     289} dpeth_t;
     290
    369291#endif
    370292
    371         /* Do it yourself send queue */
    372         struct sendq
    373         {
    374                 int sq_filled;          /* this buffer contains a packet */
    375                 int sq_size;            /* with this size */
    376                 int sq_sendpage;        /* starting page of the buffer */
    377         } de_sendq[SENDQ_NR];
    378         int de_sendq_nr;
    379         int de_sendq_head;              /* Enqueue at the head */
    380         int de_sendq_tail;              /* Dequeue at the tail */
    381 
    382         /* Fields for internal use by the dp8390 driver. */
    383         int de_flags;
    384         int de_mode;
    385         eth_stat_t de_stat;
    386         iovec_dat_t de_read_iovec;
    387 //      iovec_dat_s_t de_read_iovec_s;
    388 //      int de_safecopy_read;
    389         iovec_dat_t de_write_iovec;
    390 //      iovec_dat_s_t de_write_iovec_s;
    391         iovec_dat_t de_tmp_iovec;
    392 //      iovec_dat_s_t de_tmp_iovec_s;
    393         vir_bytes de_read_s;
    394 //      int de_client;
    395 //      message de_sendmsg;
    396         dp_user2nicf_t de_user2nicf;
    397 //      dp_user2nicf_s_t de_user2nicf_s;
    398         dp_nic2userf_t de_nic2userf;
    399 //      dp_nic2userf_s_t de_nic2userf_s;
    400         dp_getblock_t de_getblockf;
    401 } dpeth_t;
    402 
    403 #define DEI_DEFAULT     0x8000
    404 
    405 #define DEF_EMPTY       0x000
    406 #define DEF_PACK_SEND   0x001
    407 #define DEF_PACK_RECV   0x002
    408 #define DEF_SEND_AVAIL  0x004
    409 #define DEF_READING     0x010
    410 #define DEF_PROMISC     0x040
    411 #define DEF_MULTI       0x080
    412 #define DEF_BROAD       0x100
    413 #define DEF_ENABLED     0x200
    414 #define DEF_STOPPED     0x400
    415 
    416 #define DEM_DISABLED    0x0
    417 #define DEM_SINK        0x1
    418 #define DEM_ENABLED     0x2
    419 
    420 //#if !__minix_vmd
    421 #define debug           1       /* Standard Minix lacks debug variable */
    422 //#endif
    423 
    424 /*
    425  * $PchId: dp8390.h,v 1.10 2005/02/10 17:26:06 philip Exp $
    426  */
    427 
    428 #endif
    429 
    430293/** @}
    431294 */
  • uspace/srv/hw/netif/dp8390/dp8390_drv.h

    rf03d3786 rae1f70e  
    4040#include "dp8390.h"
    4141
    42 /** Initializes and/or starts the network interface.
    43  *  @param[in,out] dep The network interface structure.
    44  *  @param[in] mode The state mode.
    45  *  @returns EOK on success.
    46  *  @returns EXDEV if the network interface is disabled.
    47  */
    48 int do_init(dpeth_t *dep, int mode);
     42int do_init(dpeth_t *dep);
    4943
    5044/** Stops the network interface.
     
    5549/** Processes the interrupt.
    5650 *  @param[in,out] dep The network interface structure.
    57  *  @param[in] isr The interrupt status register.
    5851 */
    59 void dp_check_ints(dpeth_t *dep, int isr);
     52void dp_check_ints(int nil_phone, device_id_t device_id, dpeth_t *dep, uint8_t isr);
    6053
    6154/** Probes and initializes the network interface.
     
    7063 *  @param[in] packet The packet t be sent.
    7164 *  @param[in] from_int The value indicating whether the sending is initialized from the interrupt handler.
    72  *  @returns 
     65 *  @returns
    7366 */
    7467int do_pwrite(dpeth_t * dep, packet_t *packet, int from_int);
    75 
    76 /** Prints out network interface information.
    77  *  @param[in] dep The network interface structure.
    78  */
    79 void dp8390_dump(dpeth_t * dep);
    8068
    8169#endif
  • uspace/srv/hw/netif/dp8390/dp8390_module.c

    rf03d3786 rae1f70e  
    4343#include <ipc/ipc.h>
    4444#include <ipc/services.h>
    45 
    4645#include <net/modules.h>
    4746#include <packet_client.h>
     
    5150#include <netif_interface.h>
    5251#include <netif_local.h>
    53 
    5452#include "dp8390.h"
    5553#include "dp8390_drv.h"
     
    6058#define NAME  "dp8390"
    6159
    62 /** Returns the device from the interrupt call.
     60/** Return the device from the interrupt call.
     61 *
    6362 *  @param[in] call The interrupt call.
    64  */
    65 #define IRQ_GET_DEVICE(call)                    (device_id_t) IPC_GET_IMETHOD(*call)
    66 
    67 /** Returns the interrupt status register from the interrupt call.
     63 *
     64 */
     65#define IRQ_GET_DEVICE(call)  ((device_id_t) IPC_GET_IMETHOD(call))
     66
     67/** Return the ISR from the interrupt call.
     68 *
    6869 *  @param[in] call The interrupt call.
    69  */
    70 #define IPC_GET_ISR(call)                               (int) IPC_GET_ARG2(*call)
     70 *
     71 */
     72#define IRQ_GET_ISR(call)  ((int) IPC_GET_ARG2(call))
    7173
    7274/** DP8390 kernel interrupt command sequence.
    7375 */
    74 static irq_cmd_t        dp8390_cmds[] = {
    75         {       .cmd = CMD_PIO_READ_8,
     76static irq_cmd_t dp8390_cmds[] = {
     77        {
     78                .cmd = CMD_PIO_READ_8,
    7679                .addr = NULL,
    7780                .dstarg = 2
    7881        },
    7982        {
     83                .cmd = CMD_BTEST,
     84                .value = 0x7f,
     85                .srcarg = 2,
     86                .dstarg = 3,
     87        },
     88        {
    8089                .cmd = CMD_PREDICATE,
    81                 .value = 1,
    82                 .srcarg = 2
     90                .value = 2,
     91                .srcarg = 3
    8392        },
    8493        {
     94                .cmd = CMD_PIO_WRITE_A_8,
     95                .addr = NULL,
     96                .srcarg = 3
     97        },
     98        {
    8599                .cmd = CMD_ACCEPT
    86100        }
     
    89103/** DP8390 kernel interrupt code.
    90104 */
    91 static irq_code_t       dp8390_code = {
     105static irq_code_t dp8390_code = {
    92106        sizeof(dp8390_cmds) / sizeof(irq_cmd_t),
    93107        dp8390_cmds
     
    99113 *  @param[in] call The interrupt message.
    100114 */
    101 static void irq_handler(ipc_callid_t iid, ipc_call_t * call)
    102 {
    103         netif_device_t * device;
    104         dpeth_t * dep;
    105         packet_t *received;
    106         device_id_t device_id;
    107         int phone;
    108 
    109         device_id = IRQ_GET_DEVICE(call);
     115static void irq_handler(ipc_callid_t iid, ipc_call_t *call)
     116{
     117        device_id_t device_id = IRQ_GET_DEVICE(*call);
     118        netif_device_t *device;
     119        int nil_phone;
     120        dpeth_t *dep;
     121       
    110122        fibril_rwlock_write_lock(&netif_globals.lock);
    111         if(find_device(device_id, &device) != EOK){
    112                 fibril_rwlock_write_unlock(&netif_globals.lock);
    113                 return;
    114         }
    115         dep = (dpeth_t *) device->specific;
    116         if (dep->de_mode != DEM_ENABLED){
    117                 fibril_rwlock_write_unlock(&netif_globals.lock);
    118                 return;
    119         }
    120         assert(dep->de_flags &DEF_ENABLED);
    121         dep->de_int_pending = 0;
    122         dp_check_ints(dep, IPC_GET_ISR(call));
    123         if(dep->received_queue){
    124                 received = dep->received_queue;
    125                 phone = device->nil_phone;
    126                 dep->received_queue = NULL;
    127                 dep->received_count = 0;
    128                 fibril_rwlock_write_unlock(&netif_globals.lock);
    129                 nil_received_msg(phone, device_id, received, SERVICE_NONE);
    130         }else{
    131                 fibril_rwlock_write_unlock(&netif_globals.lock);
    132         }
    133         ipc_answer_0(iid, EOK);
     123       
     124        if (find_device(device_id, &device) == EOK) {
     125                nil_phone = device->nil_phone;
     126                dep = (dpeth_t *) device->specific;
     127        } else
     128                dep = NULL;
     129       
     130        fibril_rwlock_write_unlock(&netif_globals.lock);
     131       
     132        if ((dep != NULL) && (dep->up)) {
     133                assert(dep->enabled);
     134                dp_check_ints(nil_phone, device_id, dep, IRQ_GET_ISR(*call));
     135        }
    134136}
    135137
     
    139141 *  @returns The new state.
    140142 */
    141 static int change_state(netif_device_t * device, device_state_t state)
     143static int change_state(netif_device_t *device, device_state_t state)
    142144{
    143145        if (device->state != state) {
     
    153155}
    154156
    155 int netif_specific_message(ipc_callid_t callid, ipc_call_t * call, ipc_call_t * answer, int * answer_count){
     157int netif_specific_message(ipc_callid_t callid, ipc_call_t *call,
     158    ipc_call_t *answer, int *answer_count)
     159{
    156160        return ENOTSUP;
    157161}
     
    162166        eth_stat_t * de_stat;
    163167        int rc;
    164 
    165         if(! stats){
     168       
     169        if (!stats)
    166170                return EBADMEM;
    167         }
     171       
    168172        rc = find_device(device_id, &device);
    169173        if (rc != EOK)
    170174                return rc;
     175       
    171176        de_stat = &((dpeth_t *) device->specific)->de_stat;
     177       
    172178        null_device_stats(stats);
    173179        stats->receive_errors = de_stat->ets_recvErr;
     
    183189        stats->send_heartbeat_errors = de_stat->ets_CDheartbeat;
    184190        stats->send_window_errors = de_stat->ets_OWC;
    185         return EOK;
    186 }
    187 
    188 int netif_get_addr_message(device_id_t device_id, measured_string_t *address){
    189         netif_device_t * device;
    190         int rc;
    191 
    192         if(! address){
     191       
     192        return EOK;
     193}
     194
     195int netif_get_addr_message(device_id_t device_id, measured_string_t *address)
     196{
     197        netif_device_t *device;
     198        int rc;
     199       
     200        if (!address)
    193201                return EBADMEM;
    194         }
     202       
    195203        rc = find_device(device_id, &device);
    196204        if (rc != EOK)
    197205                return rc;
     206       
    198207        address->value = (char *) (&((dpeth_t *) device->specific)->de_address);
    199208        address->length = sizeof(ether_addr_t);
     
    201210}
    202211
    203 
    204 
    205 int netif_probe_message(device_id_t device_id, int irq, uintptr_t io){
    206         netif_device_t * device;
    207         dpeth_t * dep;
    208         int rc;
    209 
     212int netif_probe_message(device_id_t device_id, int irq, uintptr_t io)
     213{
     214        netif_device_t *device;
     215        dpeth_t *dep;
     216        int rc;
     217       
    210218        device = (netif_device_t *) malloc(sizeof(netif_device_t));
    211         if(! device){
     219        if (!device)
    212220                return ENOMEM;
    213         }
     221       
    214222        dep = (dpeth_t *) malloc(sizeof(dpeth_t));
    215         if(! dep){
     223        if (!dep) {
    216224                free(device);
    217225                return ENOMEM;
    218226        }
     227       
    219228        bzero(device, sizeof(netif_device_t));
    220229        bzero(dep, sizeof(dpeth_t));
     
    224233        device->state = NETIF_STOPPED;
    225234        dep->de_irq = irq;
    226         dep->de_mode = DEM_DISABLED;
     235        dep->up = false;
     236       
    227237        //TODO address?
    228238        rc = pio_enable((void *) io, DP8390_IO_SIZE, (void **) &dep->de_base_port);
     
    231241                free(device);
    232242                return rc;
    233         }       
     243        }
     244       
    234245        rc = do_probe(dep);
    235246        if (rc != EOK) {
     
    238249                return rc;
    239250        }
     251       
    240252        rc = netif_device_map_add(&netif_globals.device_map, device->device_id, device);
    241         if (rc != EOK){
     253        if (rc != EOK) {
    242254                free(dep);
    243255                free(device);
    244256                return rc;
    245257        }
    246         return EOK;
    247 }
    248 
    249 int netif_send_message(device_id_t device_id, packet_t *packet, services_t sender){
    250         netif_device_t * device;
    251         dpeth_t * dep;
     258       
     259        return EOK;
     260}
     261
     262int netif_send_message(device_id_t device_id, packet_t *packet,
     263    services_t sender)
     264{
     265        netif_device_t *device;
     266        dpeth_t *dep;
    252267        packet_t *next;
    253268        int rc;
    254 
     269       
    255270        rc = find_device(device_id, &device);
    256271        if (rc != EOK)
    257272                return rc;
    258         if(device->state != NETIF_ACTIVE){
     273       
     274        if (device->state != NETIF_ACTIVE){
    259275                netif_pq_release(packet_get_id(packet));
    260276                return EFORWARD;
    261277        }
     278       
    262279        dep = (dpeth_t *) device->specific;
    263         // process packet queue
    264         do{
     280       
     281        /* Process packet queue */
     282        do {
    265283                next = pq_detach(packet);
    266                 if(do_pwrite(dep, packet, FALSE) != EBUSY){
     284               
     285                if (do_pwrite(dep, packet, false) != EBUSY)
    267286                        netif_pq_release(packet_get_id(packet));
    268                 }
     287               
    269288                packet = next;
    270         }while(packet);
    271         return EOK;
    272 }
    273 
    274 int netif_start_message(netif_device_t * device){
    275         dpeth_t * dep;
    276         int rc;
    277 
    278         if(device->state != NETIF_ACTIVE){
     289        } while (packet);
     290       
     291        return EOK;
     292}
     293
     294int netif_start_message(netif_device_t * device)
     295{
     296        dpeth_t *dep;
     297        int rc;
     298       
     299        if (device->state != NETIF_ACTIVE) {
    279300                dep = (dpeth_t *) device->specific;
    280301                dp8390_cmds[0].addr = (void *) (uintptr_t) (dep->de_dp8390_port + DP_ISR);
    281                 dp8390_cmds[2].addr = dp8390_cmds[0].addr;
     302                dp8390_cmds[3].addr = dp8390_cmds[0].addr;
     303               
    282304                rc = ipc_register_irq(dep->de_irq, device->device_id, device->device_id, &dp8390_code);
    283305                if (rc != EOK)
    284306                        return rc;
    285                 rc = do_init(dep, DL_BROAD_REQ);
     307               
     308                rc = do_init(dep);
    286309                if (rc != EOK) {
    287310                        ipc_unregister_irq(dep->de_irq, device->device_id);
    288311                        return rc;
    289312                }
     313               
    290314                return change_state(device, NETIF_ACTIVE);
    291315        }
    292         return EOK;
    293 }
    294 
    295 int netif_stop_message(netif_device_t * device){
    296         dpeth_t * dep;
    297 
    298         if(device->state != NETIF_STOPPED){
     316       
     317        return EOK;
     318}
     319
     320int netif_stop_message(netif_device_t * device)
     321{
     322        dpeth_t *dep;
     323       
     324        if (device->state != NETIF_STOPPED) {
    299325                dep = (dpeth_t *) device->specific;
    300326                do_stop(dep);
     
    302328                return change_state(device, NETIF_STOPPED);
    303329        }
    304         return EOK;
    305 }
    306 
    307 int netif_initialize(void){
     330       
     331        return EOK;
     332}
     333
     334int netif_initialize(void)
     335{
    308336        sysarg_t phonehash;
    309 
    310337        async_set_interrupt_received(irq_handler);
    311 
    312338        return ipc_connect_to_me(PHONE_NS, SERVICE_DP8390, 0, 0, &phonehash);
    313339}
     
    319345 *
    320346 */
    321 static void netif_client_connection(ipc_callid_t iid, ipc_call_t * icall)
     347static void netif_client_connection(ipc_callid_t iid, ipc_call_t *icall)
    322348{
    323349        /*
     
    327353        ipc_answer_0(iid, EOK);
    328354       
    329         while(true) {
     355        while (true) {
    330356                ipc_call_t answer;
    331357                int answer_count;
     
    351377}
    352378
    353 /** Starts the module.
     379/** Start the module.
    354380 *
    355381 *  @param argc The count of the command line arguments. Ignored parameter.
     
    362388int main(int argc, char *argv[])
    363389{
    364         int rc;
    365        
    366390        /* Start the module */
    367         rc = netif_module_start(netif_client_connection);
    368         return rc;
     391        return netif_module_start(netif_client_connection);
    369392}
    370393
  • uspace/srv/hw/netif/dp8390/dp8390_port.h

    rf03d3786 rae1f70e  
    4444#include <sys/types.h>
    4545
    46 /** Macro for difining functions.
    47  *  @param[in] function The function type and name definition.
    48  *  @param[in] params The function parameters definition.
    49  */
    50 #define _PROTOTYPE(function, params) function params
    51 
    52 /** Success error code.
    53  */
    54 #define OK      EOK
    55 
    56 /** Type definition of the unsigned byte.
    57  */
    58 typedef uint8_t u8_t;
    59 
    60 /** Type definition of the unsigned short.
    61  */
    62 typedef uint16_t u16_t;
    63 
    6446/** Compares two memory blocks.
    6547 *  @param[in] first The first memory block.
     
    7052 *  @returns 1 if the second is greater than the first.
    7153 */
    72 #define memcmp(first, second, size)     bcmp((char *) (first), (char *) (second), (size))
     54#define memcmp(first, second, size)  bcmp((char *) (first), (char *) (second), (size))
    7355
    7456/** Reads 1 byte.
     
    7658 *  @returns The read value.
    7759 */
    78 #define inb(port)       pio_read_8((ioport8_t *) (port))
     60#define inb(port)  pio_read_8((ioport8_t *) (port))
    7961
    8062/** Reads 1 word (2 bytes).
     
    8264 *  @returns The read value.
    8365 */
    84 #define inw(port)       pio_read_16((ioport16_t *) (port))
     66#define inw(port)  pio_read_16((ioport16_t *) (port))
    8567
    8668/** Writes 1 byte.
     
    8870 *  @param[in] value The value to be written.
    8971 */
    90 #define outb(port, value)       pio_write_8((ioport8_t *) (port), (value))
     72#define outb(port, value)  pio_write_8((ioport8_t *) (port), (value))
    9173
    9274/** Writes 1 word (2 bytes).
     
    9476 *  @param[in] value The value to be written.
    9577 */
    96 #define outw(port, value)       pio_write_16((ioport16_t *) (port), (value))
     78#define outw(port, value)  pio_write_16((ioport16_t *) (port), (value))
    9779
    98 /** Prints out the driver critical error.
    99  *  Does not call the system panic().
    100  */
    101 #define panic(...)      printf("%s%s%d", __VA_ARGS__)
    102 
    103 /** Copies a memory block.
    104  *  @param proc The source process. Ignored parameter.
    105  *  @param src_s Ignored parameter.
    106  *  @param[in] src The source address.
    107  *  @param me The current proces. Ignored parameter.
    108  *  @param dst_s Ignored parameter.
    109  *  @param[in] dst The destination address.
    110  *  @param[in] bytes The block size in bytes.
    111  *  @returns EOK.
    112  */
    113 #define sys_vircopy(proc, src_s, src, me, dst_s, dst, bytes)    ({memcpy((void *)(dst), (void *)(src), (bytes)); EOK;})
    114 
    115 /** Reads a memory block byte by byte.
    116  *  @param[in] port The address to be written.
    117  *  @param proc The source process. Ignored parameter.
    118  *  @param[in] dst The destination address.
    119  *  @param[in] bytes The block size in bytes.
    120  */
    121 #define do_vir_insb(port, proc, dst, bytes)     insb((port), (void *)(dst), (bytes))
    122 
    123 /** Reads a memory block word by word (2 bytes).
    124  *  @param[in] port The address to be written.
    125  *  @param proc The source process. Ignored parameter.
    126  *  @param[in] dst The destination address.
    127  *  @param[in] bytes The block size in bytes.
    128  */
    129 #define do_vir_insw(port, proc, dst, bytes)     insw((port), (void *)(dst), (bytes))
    130 
    131 /** Writes a memory block byte by byte.
    132  *  @param[in] port The address to be written.
    133  *  @param proc The source process. Ignored parameter.
    134  *  @param[in] src The source address.
    135  *  @param[in] bytes The block size in bytes.
    136  */
    137 #define do_vir_outsb(port, proc, src, bytes)    outsb((port), (void *)(src), (bytes))
    138 
    139 /** Writes a memory block word by word (2 bytes).
    140  *  @param[in] port The address to be written.
    141  *  @param proc The source process. Ignored parameter.
    142  *  @param[in] src The source address.
    143  *  @param[in] bytes The block size in bytes.
    144  */
    145 #define do_vir_outsw(port, proc, src, bytes)    outsw((port), (void *)(src), (bytes))
    146 
    147 /* com.h */
    148 /* Bits in 'DL_MODE' field of DL requests. */
    149 #  define DL_NOMODE             0x0
    150 #  define DL_PROMISC_REQ        0x2
    151 #  define DL_MULTI_REQ          0x4
    152 #  define DL_BROAD_REQ          0x8
    153 
    154 /* const.h */
    155 /** True value.
    156  */
    157 #define TRUE               1    /* used for turning integers into Booleans */
    158 
    159 /** False value.
    160  */
    161 #define FALSE              0    /* used for turning integers into Booleans */
    162 
    163 /** No number value.
    164  */
    165 #define NO_NUM        0x8000    /* used as numerical argument to panic() */
    166 
    167 /* devio.h */
    168 //typedef u16_t port_t;
    16980/** Type definition of a port.
    17081 */
    17182typedef long port_t;
    17283
    173 /* dl_eth.h */
    17484/** Ethernet statistics.
    17585 */
    176 typedef struct eth_stat
    177 {
     86typedef struct eth_stat {
    17887        /** Number of receive errors.
    17988         */
     
    226135} eth_stat_t;
    227136
    228 /* errno.h */
    229 /** Generic error.
    230  */
    231 #define EGENERIC     EINVAL
    232 
    233 /* ether.h */
    234137/** Minimum Ethernet packet size in bytes.
    235138 */
    236 #define ETH_MIN_PACK_SIZE                 60
     139#define ETH_MIN_PACK_SIZE  60
    237140
    238141/** Maximum Ethernet packet size in bytes.
    239142 */
    240 #define ETH_MAX_PACK_SIZE_TAGGED        1518
     143#define ETH_MAX_PACK_SIZE_TAGGED  1518
    241144
    242145/** Ethernet address type definition.
    243146 */
    244 typedef struct ether_addr
    245 {
     147typedef struct ether_addr {
    246148        /** Address data.
    247149         */
    248         u8_t ea_addr[6];
     150        uint8_t ea_addr[6];
    249151} ether_addr_t;
    250 
    251 /* type.h */
    252 /** Type definition of the physical addresses and lengths in bytes.
    253  */
    254 typedef unsigned long phys_bytes;
    255 
    256 /** Type definition of the virtual addresses and lengths in bytes.
    257  */
    258 typedef unsigned long vir_bytes;
    259 
    260 /** Type definition of the input/output vector.
    261  */
    262 typedef struct {
    263         /** Address of an I/O buffer.
    264          */
    265         vir_bytes iov_addr;
    266         /** Sizeof an I/O buffer.
    267          */
    268         vir_bytes iov_size;
    269 } iovec_t;
    270152
    271153#endif
  • uspace/srv/hw/netif/dp8390/ne2000.c

    rf03d3786 rae1f70e  
    11/*
    2  * Copyright (c) 1987,1997, 2006, Vrije Universiteit, Amsterdam, The Netherlands All rights reserved. Redistribution and use of the MINIX 3 operating system in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
    3  *
    4  * * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
    5  * * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
    6  * * Neither the name of the Vrije Universiteit nor the names of the software authors or contributors may be used to endorse or promote products derived from this software without specific prior written permission.
    7  * * Any deviations from these conditions require written permission from the copyright holder in advance
    8  *
    9  *
    10  * Disclaimer
    11  *
    12  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS, AUTHORS, AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
     2 * Copyright (c) 2009 Lukas Mejdrech
     3 * Copyright (c) 2011 Martin Decky
     4 * All rights reserved.
     5 *
     6 * Redistribution and use in source and binary forms, with or without
     7 * modification, are permitted provided that the following conditions
     8 * are met:
     9 *
     10 * - Redistributions of source code must retain the above copyright
     11 *   notice, this list of conditions and the following disclaimer.
     12 * - Redistributions in binary form must reproduce the above copyright
     13 *   notice, this list of conditions and the following disclaimer in the
     14 *   documentation and/or other materials provided with the distribution.
     15 * - The name of the author may not be used to endorse or promote products
     16 *   derived from this software without specific prior written permission.
     17 *
     18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
    1319 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
    1420 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
    15  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR ANY AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
     21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
    1622 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
    1723 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     
    2026 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
    2127 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    22  *
    23  * Changes:
    24  *  2009 ported to HelenOS, Lukas Mejdrech
     28 */
     29
     30/*
     31 * This code is based upon the NE2000 driver for MINIX,
     32 * distributed according to a BSD-style license.
     33 *
     34 * Copyright (c) 1987, 1997, 2006 Vrije Universiteit
     35 * Copyright (c) 1992, 1994 Philip Homburg
     36 * Copyright (c) 1996 G. Falzoni
     37 *
    2538 */
    2639
     
    3548#include <stdio.h>
    3649#include <unistd.h>
    37 
    3850#include "dp8390_port.h"
    39 
    40 /*
    41 ne2000.c
    42 
    43 Driver for the ne2000 ethernet cards. This file contains only the ne2000
    44 specific code, the rest is in dp8390.c
    45 
    46 Created:        March 15, 1994 by Philip Homburg <philip@f-mnx.phicoh.com>
    47 */
    48 
    49 //#include "../drivers.h"
    50 
    51 //#include <net/gen/ether.h>
    52 //#include <net/gen/eth_io.h>
    53 //#if __minix_vmd
    54 //#include "config.h"
    55 //#endif
    56 
    57 #include "local.h"
    5851#include "dp8390.h"
    5952#include "ne2000.h"
    6053
    61 #if ENABLE_NE2000
    62 
    63 /** Number of bytes to transfer.
    64  */
    65 #define N 100
    66 
    67 //#define MILLIS_TO_TICKS(m)  (((m)*HZ/1000)+1)
    68 
    69 /** Sleeps for the defined millicesonds.
    70  *  @param[in] millis The number of milliseconds to sleep.
    71  */
    72 #define milli_delay(millis)     usleep((millis) * 1000)
    73 
    74 /** Type definition of the testing function.
    75  */
    76 _PROTOTYPE(typedef int (*testf_t), (dpeth_t *dep, int pos, u8_t *pat)   );
    77 
    78 /** First data pattern.
    79  */
    80 u8_t    pat0[]= {0x00, 0x00, 0x00, 0x00};
    81 
    82 /** Second data pattern.
    83  */
    84 u8_t    pat1[]= {0xFF, 0xFF, 0xFF, 0xFF};
    85 
    86 /** Third data pattern.
    87  */
    88 u8_t    pat2[]= {0xA5, 0x5A, 0x69, 0x96};
    89 
    90 /** Fourth data pattern.
    91  */
    92 u8_t    pat3[]= {0x96, 0x69, 0x5A, 0xA5};
     54/** Number of bytes to transfer */
     55#define N  100
     56
     57typedef int (*testf_t)(dpeth_t *dep, int pos, uint8_t *pat);
     58
     59/** Data patterns */
     60uint8_t pat0[] = {0x00, 0x00, 0x00, 0x00};
     61uint8_t pat1[] = {0xFF, 0xFF, 0xFF, 0xFF};
     62uint8_t pat2[] = {0xA5, 0x5A, 0x69, 0x96};
     63uint8_t pat3[] = {0x96, 0x69, 0x5A, 0xA5};
    9364
    9465/** Tests 8 bit NE2000 network interface.
     
    9768 *  @param[in] pat The data pattern to be written.
    9869 *  @returns True on success.
    99  *  @returns FALSE otherwise.
    100  */
    101 static int test_8(dpeth_t *dep, int pos, u8_t *pat);
     70 *  @returns false otherwise.
     71 */
     72static int test_8(dpeth_t *dep, int pos, uint8_t *pat);
    10273
    10374/** Tests 16 bit NE2000 network interface.
     
    10677 *  @param[in] pat The data pattern to be written.
    10778 *  @returns True on success.
    108  *  @returns FALSE otherwise.
    109  */
    110 static int test_16(dpeth_t *dep, int pos, u8_t *pat);
    111 
    112 /** Stops the NE2000 network interface.
    113  *  @param[in,out] dep The network interface structure.
    114  */
    115 static void ne_stop(dpeth_t *dep);
    116 //_PROTOTYPE(static void milli_delay, (unsigned long millis)            );
    117 
    118 /** Initializes the NE2000 network interface.
    119  *  @param[in,out] dep The network interface structure.
    120  */
    121 void ne_init(struct dpeth *dep);
    122 
    123 /*===========================================================================*
    124  *                              ne_probe                                     *
    125  *===========================================================================*/
    126 int ne_probe(dep)
    127 dpeth_t *dep;
     79 *  @returns false otherwise.
     80 */
     81static int test_16(dpeth_t *dep, int pos, uint8_t *pat);
     82
     83int ne_probe(dpeth_t *dep)
    12884{
    12985        int byte;
     
    13187        int loc1, loc2;
    13288        testf_t f;
    133 
    134         dep->de_dp8390_port= dep->de_base_port + NE_DP8390;
    135 
    136         /* We probe for an ne1000 or an ne2000 by testing whether the
     89       
     90        dep->de_dp8390_port = dep->de_base_port + NE_DP8390;
     91       
     92        /*
     93         * We probe for an ne1000 or an ne2000 by testing whether the
    13794         * on board is reachable through the dp8390. Note that the
    13895         * ne1000 is an 8bit card and has a memory region distict from
    13996         * the 16bit ne2000
    14097         */
    141 
    142         for (dep->de_16bit= 0; dep->de_16bit < 2; dep->de_16bit++)
    143         {
     98       
     99        for (dep->de_16bit = 0; dep->de_16bit < 2; dep->de_16bit++) {
    144100                /* Reset the ethernet card */
    145101                byte= inb_ne(dep, NE_RESET);
    146                 milli_delay(2);
     102                usleep(2000);
    147103                outb_ne(dep, NE_RESET, byte);
    148                 milli_delay(2);
    149 
     104                usleep(2000);
     105               
    150106                /* Reset the dp8390 */
    151107                outb_reg0(dep, DP_CR, CR_STP | CR_DM_ABORT);
    152                 for (i= 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) &ISR_RST) == 0); i++)
     108                for (i = 0; i < 0x1000 && ((inb_reg0(dep, DP_ISR) & ISR_RST) == 0); i++)
    153109                        ; /* Do nothing */
    154 
     110               
    155111                /* Check if the dp8390 is really there */
    156                 if ((inb_reg0(dep, DP_CR) &(CR_STP|CR_DM_ABORT)) !=
    157                         (CR_STP|CR_DM_ABORT))
    158                 {
     112                if ((inb_reg0(dep, DP_CR) & (CR_STP | CR_DM_ABORT)) !=
     113                    (CR_STP | CR_DM_ABORT))
    159114                        return 0;
    160                 }
    161 
     115               
    162116                /* Disable the receiver and init TCR and DCR. */
    163117                outb_reg0(dep, DP_RCR, RCR_MON);
    164118                outb_reg0(dep, DP_TCR, TCR_NORMAL);
    165                 if (dep->de_16bit)
    166                 {
     119                if (dep->de_16bit) {
    167120                        outb_reg0(dep, DP_DCR, DCR_WORDWIDE | DCR_8BYTES |
    168                                 DCR_BMS);
     121                            DCR_BMS);
     122                } else {
     123                        outb_reg0(dep, DP_DCR, DCR_BYTEWIDE | DCR_8BYTES |
     124                            DCR_BMS);
    169125                }
    170                 else
    171                 {
    172                         outb_reg0(dep, DP_DCR, DCR_BYTEWIDE | DCR_8BYTES |
    173                                 DCR_BMS);
     126               
     127                if (dep->de_16bit) {
     128                        loc1 = NE2000_START;
     129                        loc2 = NE2000_START + NE2000_SIZE - 4;
     130                        f = test_16;
     131                } else {
     132                        loc1 = NE1000_START;
     133                        loc2 = NE1000_START + NE1000_SIZE - 4;
     134                        f = test_8;
    174135                }
    175 
    176                 if (dep->de_16bit)
    177                 {
    178                         loc1= NE2000_START;
    179                         loc2= NE2000_START + NE2000_SIZE - 4;
    180                         f= test_16;
    181                 }
    182                 else
    183                 {
    184                         loc1= NE1000_START;
    185                         loc2= NE1000_START + NE1000_SIZE - 4;
    186                         f= test_8;
    187                 }
    188                 if (f(dep, loc1, pat0) && f(dep, loc1, pat1) &&
    189                         f(dep, loc1, pat2) && f(dep, loc1, pat3) &&
    190                         f(dep, loc2, pat0) && f(dep, loc2, pat1) &&
    191                         f(dep, loc2, pat2) && f(dep, loc2, pat3))
    192                 {
    193                         /* We don't need a memory segment */
    194                         dep->de_linmem= 0;
    195                         if (!dep->de_pci)
    196                                 dep->de_initf= ne_init;
    197                         dep->de_stopf= ne_stop;
    198                         dep->de_prog_IO= 1;
     136               
     137                if (f(dep, loc1, pat0) && f(dep, loc1, pat1) &&
     138                    f(dep, loc1, pat2) && f(dep, loc1, pat3) &&
     139                    f(dep, loc2, pat0) && f(dep, loc2, pat1) &&
     140                    f(dep, loc2, pat2) && f(dep, loc2, pat3)) {
    199141                        return 1;
    200142                }
    201143        }
     144       
    202145        return 0;
    203146}
    204147
    205 /*===========================================================================*
    206  *                              ne_init                                      *
    207  *===========================================================================*/
    208 void ne_init(dep)
    209 dpeth_t *dep;
     148/** Initializes the NE2000 network interface.
     149 *
     150 *  @param[in,out] dep The network interface structure.
     151 *
     152 */
     153void ne_init(dpeth_t *dep)
    210154{
    211155        int i;
    212156        int word, sendq_nr;
    213 
     157       
    214158        /* Setup a transfer to get the ethernet address. */
    215159        if (dep->de_16bit)
     
    217161        else
    218162                outb_reg0(dep, DP_RBCR0, 6);
     163       
    219164        outb_reg0(dep, DP_RBCR1, 0);
    220165        outb_reg0(dep, DP_RSAR0, 0);
    221166        outb_reg0(dep, DP_RSAR1, 0);
    222167        outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    223 
    224         for (i= 0; i<6; i++)
    225         {
    226                 if (dep->de_16bit)
    227                 {
    228                         word= inw_ne(dep, NE_DATA);
    229                         dep->de_address.ea_addr[i]= word;
    230                 }
    231                 else
    232                 {
     168       
     169        for (i = 0; i < 6; i++) {
     170                if (dep->de_16bit) {
     171                        word = inw_ne(dep, NE_DATA);
     172                        dep->de_address.ea_addr[i] = word;
     173                } else
    233174                        dep->de_address.ea_addr[i] = inb_ne(dep, NE_DATA);
    234                 }
    235         }
     175        }
     176       
    236177        dep->de_data_port= dep->de_base_port + NE_DATA;
    237         if (dep->de_16bit)
    238         {
    239                 dep->de_ramsize= NE2000_SIZE;
    240                 dep->de_offset_page= NE2000_START / DP_PAGESIZE;
    241         }
    242         else
    243         {
    244                 dep->de_ramsize= NE1000_SIZE;
    245                 dep->de_offset_page= NE1000_START / DP_PAGESIZE;
    246         }
    247 
     178        if (dep->de_16bit) {
     179                dep->de_ramsize = NE2000_SIZE;
     180                dep->de_offset_page = NE2000_START / DP_PAGESIZE;
     181        } else {
     182                dep->de_ramsize = NE1000_SIZE;
     183                dep->de_offset_page = NE1000_START / DP_PAGESIZE;
     184        }
     185       
    248186        /* Allocate one send buffer (1.5KB) per 8KB of on board memory. */
    249         sendq_nr= dep->de_ramsize / 0x2000;
     187        sendq_nr = dep->de_ramsize / 0x2000;
     188       
    250189        if (sendq_nr < 1)
    251                 sendq_nr= 1;
     190                sendq_nr = 1;
    252191        else if (sendq_nr > SENDQ_NR)
    253                 sendq_nr= SENDQ_NR;
    254         dep->de_sendq_nr= sendq_nr;
    255         for (i= 0; i<sendq_nr; i++)
    256         {
    257                 dep->de_sendq[i].sq_sendpage= dep->de_offset_page +
    258                         i*SENDQ_PAGES; 
    259         }
    260 
    261         dep->de_startpage= dep->de_offset_page + i*SENDQ_PAGES;
    262         dep->de_stoppage= dep->de_offset_page + dep->de_ramsize / DP_PAGESIZE;
    263 
    264         /* Can't override the default IRQ. */
    265         dep->de_irq &= ~DEI_DEFAULT;
    266 
    267         if (!debug)
    268         {
    269                 printf("%s: NE%d000 at %#lx:%d\n",
    270                     dep->de_name, dep->de_16bit ? 2 : 1,
    271                     dep->de_base_port, dep->de_irq);
    272         }
    273         else
    274         {
    275                 printf("%s: Novell NE%d000 ethernet card at I/O address "
    276                     "%#lx, memory size %#lx, irq %d\n",
    277                     dep->de_name, dep->de_16bit ? 2 : 1,
    278                     dep->de_base_port, dep->de_ramsize, dep->de_irq);
    279         }
    280 }
    281 
    282 /*===========================================================================*
    283  *                              test_8                                       *
    284  *===========================================================================*/
    285 static int test_8(dep, pos, pat)
    286 dpeth_t *dep;
    287 int pos;
    288 u8_t *pat;
    289 {
    290         u8_t buf[4];
    291         int i;
    292         int r;
    293 
    294         outb_reg0(dep, DP_ISR, 0xFF);
    295 
     192                sendq_nr = SENDQ_NR;
     193       
     194        dep->de_sendq_nr = sendq_nr;
     195        for (i = 0; i < sendq_nr; i++)
     196                dep->de_sendq[i].sq_sendpage = dep->de_offset_page + i * SENDQ_PAGES;
     197       
     198        dep->de_startpage = dep->de_offset_page + i * SENDQ_PAGES;
     199        dep->de_stoppage = dep->de_offset_page + dep->de_ramsize / DP_PAGESIZE;
     200       
     201        printf("Novell NE%d000 ethernet card at I/O address "
     202            "%#lx, memory size %#lx, irq %d\n",
     203            dep->de_16bit ? 2 : 1, dep->de_base_port, dep->de_ramsize,
     204            dep->de_irq);
     205}
     206
     207static int test_8(dpeth_t *dep, int pos, uint8_t *pat)
     208{
     209        uint8_t buf[4];
     210        int i;
     211       
     212        outb_reg0(dep, DP_ISR, 0xff);
     213       
    296214        /* Setup a transfer to put the pattern. */
    297215        outb_reg0(dep, DP_RBCR0, 4);
    298216        outb_reg0(dep, DP_RBCR1, 0);
    299         outb_reg0(dep, DP_RSAR0, pos &0xFF);
     217        outb_reg0(dep, DP_RSAR0, pos & 0xff);
    300218        outb_reg0(dep, DP_RSAR1, pos >> 8);
    301219        outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
    302 
    303         for (i= 0; i<4; i++)
     220       
     221        for (i = 0; i < 4; i++)
    304222                outb_ne(dep, NE_DATA, pat[i]);
    305 
    306         for (i= 0; i<N; i++)
    307         {
     223       
     224        for (i = 0; i < N; i++) {
     225                if (inb_reg0(dep, DP_ISR) & ISR_RDC)
     226                        break;
     227        }
     228       
     229        if (i == N) {
     230                printf("NE1000 remote DMA test failed\n");
     231                return 0;
     232        }
     233       
     234        outb_reg0(dep, DP_RBCR0, 4);
     235        outb_reg0(dep, DP_RBCR1, 0);
     236        outb_reg0(dep, DP_RSAR0, pos & 0xff);
     237        outb_reg0(dep, DP_RSAR1, pos >> 8);
     238        outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
     239       
     240        for (i = 0; i < 4; i++)
     241                buf[i] = inb_ne(dep, NE_DATA);
     242       
     243        return (memcmp(buf, pat, 4) == 0);
     244}
     245
     246static int test_16(dpeth_t *dep, int pos, uint8_t *pat)
     247{
     248        uint8_t buf[4];
     249        int i;
     250       
     251        outb_reg0(dep, DP_ISR, 0xff);
     252       
     253        /* Setup a transfer to put the pattern. */
     254        outb_reg0(dep, DP_RBCR0, 4);
     255        outb_reg0(dep, DP_RBCR1, 0);
     256        outb_reg0(dep, DP_RSAR0, pos & 0xff);
     257        outb_reg0(dep, DP_RSAR1, pos >> 8);
     258        outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
     259       
     260        for (i = 0; i < 4; i += 2)
     261                outw_ne(dep, NE_DATA, *(uint16_t *)(pat + i));
     262       
     263        for (i = 0; i < N; i++) {
    308264                if (inb_reg0(dep, DP_ISR) &ISR_RDC)
    309265                        break;
    310266        }
    311         if (i == N)
    312         {
    313                 if (debug)
    314                 {
    315                         printf("%s: NE1000 remote DMA test failed\n",
    316                                 dep->de_name);
    317                 }
     267       
     268        if (i == N) {
     269                printf("NE2000 remote DMA test failed\n");
    318270                return 0;
    319271        }
    320 
    321         outb_reg0(dep, DP_RBCR0, 4);
    322         outb_reg0(dep, DP_RBCR1, 0);
    323         outb_reg0(dep, DP_RSAR0, pos &0xFF);
     272       
     273        outb_reg0(dep, DP_RBCR0, 4);
     274        outb_reg0(dep, DP_RBCR1, 0);
     275        outb_reg0(dep, DP_RSAR0, pos & 0xff);
    324276        outb_reg0(dep, DP_RSAR1, pos >> 8);
    325277        outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    326 
    327         for (i= 0; i<4; i++)
    328                 buf[i]= inb_ne(dep, NE_DATA);
    329 
    330         r= (memcmp(buf, pat, 4) == 0);
    331         return r;
    332 }
    333 
    334 /*===========================================================================*
    335  *                              test_16                                      *
    336  *===========================================================================*/
    337 static int test_16(dep, pos, pat)
    338 dpeth_t *dep;
    339 int pos;
    340 u8_t *pat;
    341 {
    342         u8_t buf[4];
    343         int i;
    344         int r;
    345 
    346         outb_reg0(dep, DP_ISR, 0xFF);
    347 
    348         /* Setup a transfer to put the pattern. */
    349         outb_reg0(dep, DP_RBCR0, 4);
    350         outb_reg0(dep, DP_RBCR1, 0);
    351         outb_reg0(dep, DP_RSAR0, pos &0xFF);
    352         outb_reg0(dep, DP_RSAR1, pos >> 8);
    353         outb_reg0(dep, DP_CR, CR_DM_RW | CR_PS_P0 | CR_STA);
    354 
    355         for (i= 0; i<4; i += 2)
    356         {
    357                 outw_ne(dep, NE_DATA, *(u16_t *)(pat+i));
    358         }
    359 
    360         for (i= 0; i<N; i++)
    361         {
    362                 if (inb_reg0(dep, DP_ISR) &ISR_RDC)
    363                         break;
    364         }
    365         if (i == N)
    366         {
    367                 if (debug)
    368                 {
    369                         printf("%s: NE2000 remote DMA test failed\n",
    370                                 dep->de_name);
    371                 }
    372                 return 0;
    373         }
    374 
    375         outb_reg0(dep, DP_RBCR0, 4);
    376         outb_reg0(dep, DP_RBCR1, 0);
    377         outb_reg0(dep, DP_RSAR0, pos &0xFF);
    378         outb_reg0(dep, DP_RSAR1, pos >> 8);
    379         outb_reg0(dep, DP_CR, CR_DM_RR | CR_PS_P0 | CR_STA);
    380 
    381         for (i= 0; i<4; i += 2)
    382         {
    383                 *(u16_t *)(buf+i)= inw_ne(dep, NE_DATA);
    384         }
    385 
    386         r= (memcmp(buf, pat, 4) == 0);
    387         return r;
    388 }
    389 
    390 /*===========================================================================*
    391  *                              ne_stop                                      *
    392  *===========================================================================*/
    393 static void ne_stop(dep)
    394 dpeth_t *dep;
    395 {
    396         int byte;
    397 
     278       
     279        for (i = 0; i < 4; i += 2)
     280                *(uint16_t *)(buf + i) = inw_ne(dep, NE_DATA);
     281       
     282        return (memcmp(buf, pat, 4) == 0);
     283}
     284
     285/** Stop the NE2000 network interface.
     286 *
     287 *  @param[in,out] dep The network interface structure.
     288 *
     289 */
     290void ne_stop(dpeth_t *dep)
     291{
    398292        /* Reset the ethernet card */
    399         byte= inb_ne(dep, NE_RESET);
    400         milli_delay(2);
     293        int byte = inb_ne(dep, NE_RESET);
     294        usleep(2000);
    401295        outb_ne(dep, NE_RESET, byte);
    402296}
    403 /*
    404 static void milli_delay(unsigned long millis)
    405 {
    406         tickdelay(MILLIS_TO_TICKS(millis));
    407 }
    408 */
    409 #endif /* ENABLE_NE2000 */
    410 
    411 /*
    412  * $PchId: ne2000.c,v 1.10 2004/08/03 12:03:00 philip Exp $
    413  */
    414297
    415298/** @}
  • uspace/srv/hw/netif/dp8390/ne2000.h

    rf03d3786 rae1f70e  
    11/*
    2  * Copyright (c) 1987,1997, 2006, Vrije Universiteit, Amsterdam, The Netherlands All rights reserved. Redistribution and use of the MINIX 3 operating system in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
     2 * Copyright (c) 2009 Lukas Mejdrech
     3 * Copyright (c) 2011 Martin Decky
     4 * All rights reserved.
    35 *
    4  * * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
    5  * * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
    6  * * Neither the name of the Vrije Universiteit nor the names of the software authors or contributors may be used to endorse or promote products derived from this software without specific prior written permission.
    7  * * Any deviations from these conditions require written permission from the copyright holder in advance
     6 * Redistribution and use in source and binary forms, with or without
     7 * modification, are permitted provided that the following conditions
     8 * are met:
    89 *
     10 * - Redistributions of source code must retain the above copyright
     11 *   notice, this list of conditions and the following disclaimer.
     12 * - Redistributions in binary form must reproduce the above copyright
     13 *   notice, this list of conditions and the following disclaimer in the
     14 *   documentation and/or other materials provided with the distribution.
     15 * - The name of the author may not be used to endorse or promote products
     16 *   derived from this software without specific prior written permission.
    917 *
    10  * Disclaimer
    11  *
    12  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS, AUTHORS, AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
     18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
    1319 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
    1420 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
    15  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR ANY AUTHORS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
     21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
    1622 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
    1723 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     
    2026 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
    2127 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
    22  *
    23  * Changes:
    24  *  2009 ported to HelenOS, Lukas Mejdrech
    2528 */
    2629
    2730/*
    28 ne2000.h
    29 
    30 Created:        March 15, 1994 by Philip Homburg <philip@f-mnx.phicoh.com>
    31 */
     31 * This code is based upon the NE2000 driver for MINIX,
     32 * distributed according to a BSD-style license.
     33 *
     34 * Copyright (c) 1987, 1997, 2006 Vrije Universiteit
     35 * Copyright (c) 1992, 1994 Philip Homburg
     36 * Copyright (c) 1996 G. Falzoni
     37 *
     38 */
    3239
    3340/** @addtogroup ne2k
     
    4350
    4451#include <libarch/ddi.h>
    45 
    4652#include "dp8390_port.h"
    4753
    4854/** DP8390 register offset.
    4955 */
    50 #define NE_DP8390       0x00
     56#define NE_DP8390  0x00
    5157
    5258/** Data register.
    5359 */
    54 #define NE_DATA         0x10
     60#define NE_DATA  0x10
    5561
    5662/** Reset register.
    5763 */
    58 #define NE_RESET        0x1F
     64#define NE_RESET  0x1f
    5965
    6066/** NE1000 data start.
    6167 */
    62 #define NE1000_START    0x2000
     68#define NE1000_START  0x2000
    6369
    6470/** NE1000 data size.
    6571 */
    66 #define NE1000_SIZE     0x2000
     72#define NE1000_SIZE  0x2000
    6773
    6874/** NE2000 data start.
    6975 */
    70 #define NE2000_START    0x4000
     76#define NE2000_START  0x4000
    7177
    7278/** NE2000 data size.
    7379 */
    74 #define NE2000_SIZE     0x4000
     80#define NE2000_SIZE  0x4000
    7581
    7682/** Reads 1 byte register.
     
    7985 *  @returns The read value.
    8086 */
    81 #define inb_ne(dep, reg)        (inb(dep->de_base_port+reg))
     87#define inb_ne(dep, reg)  (inb(dep->de_base_port + reg))
    8288
    8389/** Writes 1 byte register.
     
    8692 *  @param[in] data The value to be written.
    8793 */
    88 #define outb_ne(dep, reg, data) (outb(dep->de_base_port+reg, data))
     94#define outb_ne(dep, reg, data)  (outb(dep->de_base_port + reg, data))
    8995
    9096/** Reads 1 word (2 bytes) register.
     
    9399 *  @returns The read value.
    94100 */
    95 #define inw_ne(dep, reg)        (inw(dep->de_base_port+reg))
     101#define inw_ne(dep, reg)  (inw(dep->de_base_port + reg))
    96102
    97103/** Writes 1 word (2 bytes) register.
     
    100106 *  @param[in] data The value to be written.
    101107 */
    102 #define outw_ne(dep, reg, data) (outw(dep->de_base_port+reg, data))
     108#define outw_ne(dep, reg, data)  (outw(dep->de_base_port + reg, data))
    103109
    104 #endif /* __NET_NETIF_NE2000_H__ */
     110struct dpeth;
    105111
    106 /*
    107  * $PchId: ne2000.h,v 1.4 2004/08/03 12:03:20 philip Exp $
    108  */
     112extern int ne_probe(struct dpeth *);
     113extern void ne_init(struct dpeth *);
     114extern void ne_stop(struct dpeth *);
     115
     116#endif
    109117
    110118/** @}
  • uspace/srv/net/tl/icmp/icmp.c

    rf03d3786 rae1f70e  
    529529        icmp_code_t code;
    530530        int rc;
    531 
     531       
    532532        switch (error) {
    533533        case SERVICE_NONE:
Note: See TracChangeset for help on using the changeset viewer.