Palacios Public Git Repository

To checkout Palacios execute

  git clone http://v3vee.org/palacios/palacios.web/palacios.git
This will give you the master branch. You probably want the devel branch or one of the release branches. To switch to the devel branch, simply execute
  cd palacios
  git checkout --track -b devel origin/devel
The other branches are similar.


484355d8a7ebc6609fe45d6575b7b1db73d66ea5
[palacios-OLD.git] / palacios / src / devices / ne2k.c
1 /*
2  * This file is part of the Palacios Virtual Machine Monitor developed
3  * by the V3VEE Project with funding from the United States National 
4  * Science Foundation and the Department of Energy.  
5  *
6  * The V3VEE Project is a joint project between Northwestern University
7  * and the University of New Mexico.  You can find out more at 
8  * http://www.v3vee.org
9  *
10  * Copyright (c) 2009, Lei Xia <lxia@northwestern.edu> 
11  * Copyright (c) 2009, The V3VEE Project <http://www.v3vee.org> 
12  * All rights reserved.
13  *
14  * Author: Lei Xia <lxia@northwestern.edu>
15  *
16  * This is free software.  You are permitted to use,
17  * redistribute, and modify it as specified in the file "V3VEE_LICENSE".
18  */
19  
20 #include <devices/pci.h>
21 #include <palacios/vmm.h>
22 #include <palacios/vmm_io.h>
23 #include <palacios/vmm_debug.h>
24 #include <palacios/vmm_string.h>
25 #include <palacios/vmm_dev_mgr.h>
26 #include <palacios/vmm_intr.h>
27 #include <palacios/vmm_ethernet.h>
28 #include <palacios/vm_guest.h>
29 #include <palacios/vmm_sprintf.h>
30
31 #ifndef V3_CONFIG_DEBUG_NE2K
32 #undef PrintDebug
33 #define PrintDebug(fmts, args...)
34 #endif
35
36
37 #define NE2K_DEFAULT_IRQ        11
38
39 // What the hell is this crap?
40 #define NE2K_PMEM_SIZE          (32 * 1024)
41 #define NE2K_PMEM_START         (16 * 1024)
42 #define NE2K_PMEM_END           (NE2K_PMEM_SIZE + NE2K_PMEM_START)
43 #define NE2K_MEM_SIZE           NE2K_PMEM_END
44
45 #define NIC_REG_BASE_PORT       0xc100          /* Command register (for all pages) */
46
47 #define NE2K_CMD_OFFSET 0x00
48 #define NE2K_DATA_OFFSET        0x10
49 #define NE2K_RESET_OFFSET       0x1f
50
51 /* Page 0 registers */
52 #define EN0_CLDALO              0x01    /* Low byte of current local dma addr  RD */
53 #define EN0_STARTPG             0x01    /* Starting page of ring bfr WR  */
54 #define EN0_CLDAHI              0x02    /* High byte of current local dma addr  RD  */
55 #define EN0_STOPPG              0x02    /* Ending page +1 of ring bfr WR */
56 #define EN0_BOUNDARY            0x03    /* Boundary page of ring bfr RD WR */
57 #define EN0_TSR                 0x04    /* Transmit status reg RD */
58 #define EN0_TPSR                0x04    /* Transmit starting page WR */
59 #define EN0_NCR                 0x05    /* Number of collision reg RD */
60 #define EN0_TCNTLO              0x05    /* Low  byte of tx byte count WR */
61 #define EN0_FIFO                0x06    /* FIFO RD */
62 #define EN0_TCNTHI              0x06    /* High byte of tx byte count WR */
63 #define EN0_ISR                 0x07    /* Interrupt status reg RD WR */
64 #define EN0_CRDALO              0x08    /* low byte of current remote dma address RD */
65 #define EN0_RSARLO              0x08    /* Remote start address reg 0 */
66 #define EN0_CRDAHI              0x09    /* high byte, current remote dma address RD */
67 #define EN0_RSARHI              0x09    /* Remote start address reg 1 */
68 #define EN0_RCNTLO              0x0a    /* Remote byte count reg WR */
69 #define EN0_RTL8029ID0          0x0a    /* Realtek ID byte #1 RD */
70 #define EN0_RCNTHI              0x0b    /* Remote byte count reg WR */
71 #define EN0_RTL8029ID1          0x0b    /* Realtek ID byte #2 RD */
72 #define EN0_RSR                 0x0c    /* rx status reg RD */
73 #define EN0_RXCR                0x0c    /* RX configuration reg WR */
74 #define EN0_TXCR                0x0d    /* TX configuration reg WR */
75 #define EN0_COUNTER0            0x0d    /* Rcv alignment error counter RD */
76 #define EN0_DCFG                0x0e    /* Data configuration reg WR */
77 #define EN0_COUNTER1            0x0e    /* Rcv CRC error counter RD */
78 #define EN0_IMR                 0x0f    /* Interrupt mask reg WR */
79 #define EN0_COUNTER2            0x0f    /* Rcv missed frame error counter RD */
80
81 /* Page 1 registers */
82 #define EN1_PHYS                0x01
83 #define EN1_CURPAG              0x07
84 #define EN1_MULT                0x08
85
86 /* Page 2 registers */
87 #define EN2_STARTPG             0x01    /* Starting page of ring bfr RD */
88 #define EN2_STOPPG              0x02    /* Ending page +1 of ring bfr RD */
89 #define EN2_LDMA0               0x01    /* Current Local DMA Address 0 WR */
90 #define EN2_LDMA1               0x02    /* Current Local DMA Address 1 WR */
91 #define EN2_RNPR                0x03    /* Remote Next Packet Pointer RD WR */
92 #define EN2_TPSR                0x04            /* Transmit Page Start Address RD */
93 #define EN2_LNRP                0x05    /* Local Next Packet Pointer RD WR */
94 #define EN2_ACNT0               0x06    /* Address Counter Upper WR */
95 #define EN2_ACNT1               0x07    /* Address Counter Lower WR */
96 #define EN2_RCR                 0x0c    /* Receive Configuration Register RD */
97 #define EN2_TCR                 0x0d    /* Transmit Configuration Register RD */
98 #define EN2_DCR                 0x0e    /* Data Configuration Register RD */
99 #define EN2_IMR                 0x0f    /* Interrupt Mask Register RD */
100
101 /* Page 3 registers */
102 #define EN3_CONFIG0             0x03
103 #define EN3_CONFIG1             0x04
104 #define EN3_CONFIG2             0x05
105 #define EN3_CONFIG3             0x06
106
107
108 struct cmd_reg {
109     union {
110         uint8_t val;
111         struct {
112             uint8_t stop        : 1;
113             uint8_t start       : 1;
114             uint8_t tx_pkt      : 1;
115             uint8_t rem_dma_cmd : 3;    /* 0=Not allowed, 1=Read, 2=Write, 3=Send Pkt, 4=Abort/Complete DMA */
116             uint8_t pg_sel      : 2;
117         } __attribute__((packed));
118     } __attribute__((packed));
119 } __attribute__((packed));
120
121
122 struct intr_status_reg {
123     union {
124         uint8_t val;
125         struct {
126             uint8_t pkt_rx          : 1;
127             uint8_t pkt_tx          : 1;
128             uint8_t rx_err          : 1;
129             uint8_t tx_err          : 1;
130             uint8_t overwrite_warn  : 1;
131             uint8_t cnt_overflow    : 1;
132             uint8_t rem_dma_done    : 1;
133             uint8_t reset_status    : 1;
134         } __attribute__((packed));
135     } __attribute__((packed));
136 } __attribute__((packed));
137
138
139 struct intr_mask_reg {
140     union {
141         uint8_t val;
142         struct {
143             uint8_t pkt_rx          : 1;
144             uint8_t pkt_tx          : 1;
145             uint8_t rx_err          : 1;
146             uint8_t tx_err          : 1;
147             uint8_t overwrite_warn  : 1;
148             uint8_t cnt_overflow    : 1;
149             uint8_t rem_dma_done    : 1;
150             uint8_t rsvd            : 1;
151         } __attribute__((packed));
152     } __attribute__((packed));
153 } __attribute__((packed));
154
155
156 struct data_cfg_reg {
157     union {
158         uint8_t val;
159         struct {
160             uint8_t word_trans_sel   : 1;
161             uint8_t byte_order_sel   : 1;
162             uint8_t long_addr_sel    : 1;
163             uint8_t loopback_sel     : 1;
164             uint8_t auto_init_rem    : 1;
165             uint8_t fifo_thresh_sel  : 2;
166             uint8_t rsvd             : 1;
167         } __attribute__((packed));
168     } __attribute__((packed));
169 } __attribute__((packed));
170
171
172 struct tx_cfg_reg { 
173     union {
174         uint8_t val;
175         struct {
176             uint8_t inhibit_crc     : 1;
177             uint8_t enc_loop_ctrl   : 2;
178             uint8_t auto_tx_disable : 1;
179             uint8_t coll_offset_en  : 1;
180             uint8_t rsvd            : 3;
181         } __attribute__((packed));
182     } __attribute__((packed));
183 } __attribute__((packed));
184
185 struct tx_status_reg { 
186     union {
187         uint8_t val;
188         struct {
189             uint8_t pkt_tx_ok       : 1;
190             uint8_t rsvd            : 1;
191             uint8_t tx_collision    : 1;
192             uint8_t tx_aborted      : 1;
193             uint8_t carrier_lost    : 1;
194             uint8_t fifo_underrun   : 1;
195             uint8_t cd_heartbeat    : 1;
196             uint8_t oow_collision   : 1;
197         } __attribute__((packed));
198     } __attribute__((packed));
199 } __attribute__((packed));
200
201 struct rx_cfg_reg { 
202     union {
203         uint8_t val;
204         struct {
205             uint8_t save_pkt_errs    : 1;
206             uint8_t runt_pkt_ok      : 1;
207             uint8_t bcast_ok         : 1;
208             uint8_t mcast_ok         : 1;
209             uint8_t prom_phys_enable : 1;
210             uint8_t mon_mode         : 1;
211             uint8_t rsvd             : 2;
212         } __attribute__((packed));
213     } __attribute__((packed));
214 } __attribute__((packed));
215
216
217 struct rx_status_reg { 
218     union {
219         uint8_t val;
220         struct {
221             uint8_t pkt_rx_ok        : 1;
222             uint8_t crc_err          : 1;
223             uint8_t frame_align_err  : 1;
224             uint8_t fifo_overrun     : 1;
225             uint8_t missed_pkt       : 1;
226             uint8_t phy_match        : 1;   /* 0=Physical Addr Match, 1=MCAST/BCAST Addr Match */
227             uint8_t rx_disabled      : 1;
228             uint8_t deferring        : 1;
229         } __attribute__((packed));
230     } __attribute__((packed));
231 } __attribute__((packed));
232
233
234 struct ne2k_registers {
235     struct cmd_reg cmd;
236     struct intr_status_reg isr;
237     struct intr_mask_reg imr;
238     struct data_cfg_reg dcr;
239     struct tx_cfg_reg tcr;
240     struct tx_status_reg tsr;
241     struct rx_cfg_reg rcr;
242     struct rx_status_reg rsr;  
243
244     uint8_t      pgstart;      /* page start reg */
245     uint8_t      pgstop;       /* page stop reg */
246     uint8_t      boundary;     /* boundary ptr */
247     uint8_t      tpsr;         /* tx page start addr */
248     uint8_t      ncr;          /* number of collisions */
249     uint8_t      fifo;         /* FIFO... */
250
251     uint8_t      curpag;       /* current page */
252     uint8_t      rnpp;         /* rem next pkt ptr */
253     uint8_t      lnpp;         /* local next pkt ptr */
254
255     uint8_t      cntr0;        /* counter 0 (frame alignment errors) */
256     uint8_t      cntr1;        /* counter 1 (CRC Errors) */
257     uint8_t      cntr2;        /* counter 2 (missed pkt errors) */
258
259     union {                    /* current local DMA Addr */
260         uint16_t     clda;
261         struct {
262             uint8_t clda0;
263             uint8_t clda1;
264         } __attribute__((packed));
265     } __attribute__((packed));
266
267
268     union {                    /* current remote DMA addr */
269         uint16_t     crda;
270         struct {
271             uint8_t crda0;
272             uint8_t crda1;
273         } __attribute__((packed));
274     } __attribute__((packed));
275
276
277     union {                    /* Remote Start Addr Reg */
278         uint16_t     rsar;
279         struct {
280             uint8_t rsar0;
281             uint8_t rsar1;
282         } __attribute__((packed));
283     } __attribute__((packed));
284
285
286     union {                    /* TX Byte count Reg */
287         uint16_t     tbcr;
288         struct {
289             uint8_t tbcr0;
290             uint8_t tbcr1;
291         } __attribute__((packed));
292     } __attribute__((packed));
293
294     union {                    /* Remote Byte count Reg */
295         uint16_t     rbcr;
296         struct {
297             uint8_t rbcr0;
298             uint8_t rbcr1;
299         } __attribute__((packed));
300     } __attribute__((packed));
301
302     union {                    /* Address counter? */
303         uint16_t     addcnt;
304         struct {
305             uint8_t addcnt0;
306             uint8_t addcnt1;
307         } __attribute__((packed));
308     } __attribute__((packed));
309 };
310
311
312 struct ne2k_state {
313     struct v3_vm_info * vm;
314     struct pci_device * pci_dev;
315     struct vm_device * pci_bus;
316     struct vm_device * dev;
317
318     struct ne2k_registers context;
319     uint8_t mem[NE2K_MEM_SIZE];
320
321     uint8_t mcast_addr[8];
322     uint8_t mac[ETH_ALEN];
323
324     struct nic_statistics statistics;
325
326     struct v3_dev_net_ops * net_ops;
327     void * backend_data;
328 };
329
330 static int ne2k_update_irq(struct ne2k_state * nic_state) {
331     struct pci_device * pci_dev = nic_state->pci_dev;
332
333     if ((nic_state->context.isr.val & nic_state->context.imr.val) & 0x7f) {
334        if (pci_dev == NULL){
335             v3_raise_virq(&(nic_state->vm->cores[0]), NE2K_DEFAULT_IRQ);
336        } else {     
337             v3_pci_raise_irq(nic_state->pci_bus, 0, nic_state->pci_dev);
338        }
339
340        PrintDebug("NE2000: Raise IRQ\n");
341     }
342
343     return 0;
344 }
345
346 static int tx_one_pkt(struct ne2k_state * nic_state, uchar_t *pkt, uint32_t length) {
347         
348 #ifdef V3_CONFIG_DEBUG_NE2K
349     PrintDebug("NE2000: Send Packet:\n");
350     v3_hexdump(pkt, length, NULL, 0);
351 #endif    
352
353     if(nic_state->net_ops->send(pkt, length, nic_state->backend_data) >= 0){
354         nic_state->statistics.tx_pkts ++;
355         nic_state->statistics.tx_bytes += length;
356
357         return 0;
358     }
359         
360     nic_state->statistics.tx_dropped ++;
361
362     return -1;
363 }
364
365 static int ne2k_rxbuf_full(struct ne2k_registers * regs) {
366     int empty;
367     int index;
368     int boundary;
369
370     index = regs->curpag << 8;
371     boundary = regs->boundary << 8;
372
373     if (index < boundary) {
374         empty = boundary - index;
375     } else {
376         empty = ((regs->pgstop - regs->pgstart) << 8) - (index - boundary);
377     }
378
379     if (empty < (ETHERNET_PACKET_LEN + 4)) {
380         return 1;
381     }
382
383     return 0;
384 }
385
386 #define MIN_BUF_SIZE 60
387
388
389 // This needs to be completely redone...
390 static int rx_one_pkt(struct ne2k_state * nic_state, const uchar_t * pkt,  uint32_t length) {
391     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
392     uchar_t * p;
393     uint32_t total_len;
394     uint32_t next;
395     uint32_t len;
396     uint32_t index;
397     uint32_t empty;
398     uint32_t start;
399     uint32_t stop;
400
401     start = regs->pgstart << 8;
402     stop = regs->pgstop << 8;
403    
404     if (regs->cmd.stop) {
405         return -1;
406     }
407
408     if (ne2k_rxbuf_full(regs)) {
409         PrintError("Ne2k: received buffer overflow\n");
410         return -1;
411     }
412
413     //packet too small, expand it
414     if (length < MIN_BUF_SIZE) {
415         uchar_t buf[MIN_BUF_SIZE];
416
417         memcpy(buf, pkt, length);
418         memset(buf + length, 0, MIN_BUF_SIZE - length);
419         pkt = buf;
420         length = MIN_BUF_SIZE;
421     }
422
423     index = regs->curpag << 8;
424
425     //header, 4 bytes
426     total_len = length + 4;
427
428     //address for next packet (4 bytes for CRC)
429     next = index + ((total_len + 4 + 255) & ~0xff);
430
431     if (next >= stop) {
432         next -= (stop - start);
433     }
434
435     p = nic_state->mem + index;
436     regs->rsr.val = 0;
437     regs->rsr.pkt_rx_ok = 1;
438
439     if (pkt[0] & 0x01) {
440         regs->rsr.phy_match = 1; /* TODO: Check this back */
441     }
442
443     p[0] = regs->rsr.val;
444     p[1] = next >> 8;
445     p[2] = total_len;
446     p[3] = total_len >> 8;
447     index += 4;
448
449     while (length > 0) {
450         if (index <= stop) {
451             empty = stop - index;
452         } else {
453             empty = 0;
454         }
455
456         len = length;
457
458         if (len > empty) {
459             len = empty;
460         }
461
462         memcpy(nic_state->mem + index, pkt, len);
463         pkt += len;
464         index += len;
465
466         if (index == stop) {
467             index = start;
468         }
469
470         length -= len;
471     }
472
473     regs->curpag = next >> 8;
474
475     regs->isr.pkt_rx = 1;
476     ne2k_update_irq(nic_state);
477
478     return 0;
479 }
480
481
482 static int ne2k_rx(uint8_t * buf, uint32_t size, void * private_data){
483     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
484   
485 #ifdef V3_CONFIG_DEBUG_NE2K
486     PrintDebug("\nNe2k: Packet Received:\n");
487     v3_hexdump(buf, size, NULL, 0);
488 #endif    
489
490     if(!rx_one_pkt(nic_state, buf, size)){
491         nic_state->statistics.rx_pkts ++;
492         nic_state->statistics.rx_bytes += size;
493         
494         return 0;
495     }
496
497     nic_state->statistics.rx_dropped ++;
498         
499     return -1;
500 }
501
502
503 static inline void mem_writeb(struct ne2k_state * nic_state, 
504                         uint32_t addr, 
505                         uint32_t val) {
506     uchar_t tmp = (uchar_t) (val & 0x000000ff);
507
508     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
509         nic_state->mem[addr] = tmp;
510     }
511 }
512
513 static inline void mem_writew(struct ne2k_state * nic_state, 
514                             uint32_t addr,
515                             uint32_t val) {
516     addr &= ~1;
517
518     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
519         *(uint16_t *)(nic_state->mem + addr) = val;
520     }
521 }
522
523 static inline void mem_writel(struct ne2k_state * nic_state,
524                             uint32_t addr,
525                             uint32_t val) {
526     addr &= ~1;
527
528     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
529         *(uint32_t *)(nic_state->mem + addr) = val;
530     }
531 }
532
533 static inline uint8_t  mem_readb(struct ne2k_state * nic_state, uint32_t addr) {
534         
535     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
536         return nic_state->mem[addr];
537     } else {
538         return 0xff;
539     }
540 }
541
542 static inline uint16_t mem_readw(struct ne2k_state * nic_state, uint32_t addr) {
543     addr &= ~1;
544
545     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
546         return *(uint16_t *)(nic_state->mem + addr);
547     } else {
548         return 0xffff;
549     }
550 }
551
552 static uint32_t mem_readl(struct ne2k_state * nic_state, uint32_t addr) {
553     addr &= ~1;
554
555     if ((addr < 32) || (addr >= NE2K_PMEM_START && addr < NE2K_MEM_SIZE)) {
556         return *(uint32_t *)(nic_state->mem + addr);
557     } else {
558         return 0xffffffff;
559     }
560 }
561
562
563 static void dma_update( struct ne2k_state * nic_state, int len) {                       
564     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
565
566     regs->rsar += len;
567
568     // wrap
569     if (regs->rsar == regs->pgstop) {
570         regs->rsar = regs->pgstart;
571     }
572
573     if (regs->rbcr <= len) {
574         regs->rbcr = 0;
575         regs->isr.rem_dma_done = 1;
576         ne2k_update_irq(nic_state);
577     } else {
578         regs->rbcr -= len;
579     }
580 }
581
582 static int ne2k_data_read(struct guest_info * core, 
583                           uint16_t port, 
584                           void * dst, 
585                           uint_t length, 
586                           void * private_data) {
587     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
588     uint32_t val;
589     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
590
591     // current dma address
592     uint32_t addr = regs->rsar;
593
594     switch (length){
595         case 1:
596             val = mem_readb(nic_state, addr);
597             break;
598         case 2:
599             val = mem_readw(nic_state, addr);
600             break;
601         case 4:
602             val = mem_readl(nic_state, addr);
603             break;
604         default:
605             PrintError("ne2k_data_read error: invalid length %d\n", length);
606             val = 0x0;
607     }
608     
609     dma_update(nic_state, length);
610     memcpy(dst, &val, length);
611
612     PrintDebug("NE2000 read: port:0x%x (%u bytes): 0x%x", port & 0x1f, length, val);
613
614     return length;
615 }
616
617 static int ne2k_data_write(struct guest_info * core, 
618                            uint16_t port, 
619                            void * src, 
620                            uint_t length, 
621                            void * private_data) {
622     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
623     uint32_t val;
624     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
625         
626     uint32_t addr = regs->rsar;
627         
628     if (regs->rbcr == 0) {
629         return length;
630     }
631
632     memcpy(&val, src, length);
633
634     switch (length) {
635         case 1:
636             mem_writeb(nic_state, addr, val);
637             break;
638         case 2:
639             mem_writew(nic_state, addr, val);
640             break;
641         case 4:
642             mem_writel(nic_state, addr, val);
643             break;
644         default:
645             PrintError("NE2000 port write error: invalid length %d\n", length);
646     }
647     
648     dma_update(nic_state, length);
649
650     PrintDebug("NE2000: Write port:0x%x (%u bytes): 0x%x\n", port & 0x1f, length, val);
651     
652     return length;
653 }
654
655
656 static void ne2k_init_state(struct ne2k_state * nic_state) {
657
658
659     /* Not sure what this is about....  */
660     memset(nic_state->mem, 0xff, 32); 
661         
662     memcpy(nic_state->mem, nic_state->mac, ETH_ALEN);
663     memset(nic_state->mcast_addr, 0xff, sizeof(nic_state->mcast_addr));
664     nic_state->mem[14] = 0x57;
665     nic_state->mem[15] = 0x57;
666
667     /* initiate registers */
668     nic_state->context.isr.reset_status = 1;
669     nic_state->context.imr.val = 0x00;
670     nic_state->context.cmd.val = 0x22;
671 }
672
673 static int reset_device(struct ne2k_state * nic_state) {  
674     ne2k_init_state(nic_state);
675
676     PrintDebug("NE2000: Reset device\n");
677
678     return 0;
679 }
680
681 //for 0xc11f port
682 static int ne2k_reset_port_read(struct guest_info * core, 
683                                 uint16_t port, 
684                                 void * dst, 
685                                 uint_t length, 
686                                 void * private_data) {
687     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
688
689     memset(dst, 0, length);
690     reset_device(nic_state);
691
692     return length;
693 }
694
695 static int ne2k_reset_port_write(struct guest_info * core, 
696                                  uint16_t port, 
697                                  void * src, 
698                                  uint_t length, 
699                                  void * private_data) {
700
701     return length;
702 }
703
704
705
706 static int ne2k_cmd_write(struct guest_info * core, 
707                           uint16_t port, 
708                           void * src, 
709                           uint_t length, 
710                           void * private_data) {
711     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
712     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
713
714     if (length != 1) {
715         PrintError("Invalid write length to NE2000 Command register\n");
716         return -1;
717     }
718
719     regs->cmd.val = *(uint8_t *)src;
720
721     if (!(regs->cmd.stop)) {
722         regs->isr.reset_status = 0;
723         
724         // if ((send pkt) && (dma byte count == 0)) 
725         if ((regs->cmd.rem_dma_cmd & 0x3) && (regs->rbcr == 0)) {
726             regs->isr.rem_dma_done = 1;
727             ne2k_update_irq(nic_state);
728         }
729         
730         if (regs->cmd.tx_pkt) {
731             int offset = (regs->tpsr << 8);
732             
733             if (offset >= NE2K_PMEM_END) {
734                 offset -= NE2K_PMEM_SIZE;
735             }
736
737             if (offset + regs->tbcr <= NE2K_PMEM_END) {
738                 tx_one_pkt(nic_state, nic_state->mem + offset, regs->tbcr);
739             }
740
741             regs->tsr.val = 0;        /* clear the tx status reg */
742             regs->tsr.pkt_tx_ok = 1;  /* indicate successful tx */
743
744             regs->isr.pkt_tx = 1;     /* irq due to pkt tx */
745             regs->cmd.tx_pkt = 0;     /* reset cmd bit  */
746             
747             ne2k_update_irq(nic_state);
748         }
749     } else {
750         /* stop the controller */
751     }
752
753     return length;
754 }
755
756 static int ne2k_cmd_read(struct guest_info * core, 
757                          uint16_t port, 
758                          void * dst, 
759                          uint_t length, 
760                          void * private_data) {
761     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
762
763     if (length != 1) {
764         PrintError("Invalid read length to NE2000 Command register\n");
765         return -1;
766     }
767
768     *(uint8_t *)dst = nic_state->context.cmd.val;
769
770     PrintDebug("ne2k_read: port:0x%x  val: 0x%x\n", port, *(uint8_t *)dst);
771     return length;
772 }
773
774 static int ne2k_std_write(struct guest_info * core, 
775                           uint16_t port, 
776                           void * src, 
777                           uint_t length, 
778                           void * private_data) {
779     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
780     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
781     int idx = port & 0x1f;
782     uint8_t page = regs->cmd.pg_sel;
783
784     if (length != 1){
785         PrintError("NE2000 port write error: length %d port 0x%xnot equal to 1\n", length, port);  
786         return -1;
787     }
788
789     uint8_t val = *(uint8_t *)src;
790         
791     PrintDebug("NE2000: write port:0x%x val: 0x%x\n", port, (uint8_t)val);
792     
793     if (page == 0) {
794         switch (idx) {
795             case EN0_STARTPG:
796                 regs->pgstart = val;
797                 break;
798             case EN0_STOPPG:
799                 regs->pgstop = val;
800                 break;
801             case EN0_BOUNDARY:
802                 regs->boundary = val;
803                 break;
804             case EN0_TPSR:
805                 regs->tpsr = val;
806                 break;
807             case EN0_TCNTLO:
808                 regs->tbcr0 = val;
809                 break;
810             case EN0_TCNTHI:
811                 regs->tbcr1 = val;
812                 break;
813             case EN0_ISR:
814                 regs->isr.val &= ~(val & 0x7f);
815                 ne2k_update_irq(nic_state);
816                 break;
817             case EN0_RSARLO:
818                 regs->rsar0 = val;
819                 break;
820             case EN0_RSARHI:
821                 regs->rsar1 = val;
822                 break;
823             case EN0_RCNTLO:
824                 regs->rbcr0 = val;
825                 break;
826             case EN0_RCNTHI:
827                 regs->rbcr1 = val;
828                 break;
829             case EN0_RXCR:
830                 regs->rcr.val = val;
831                 break;
832             case EN0_TXCR:
833                 regs->tcr.val = val;
834                 break;
835             case EN0_DCFG:
836                 regs->dcr.val = val;
837                 break;  
838             case EN0_IMR:
839                 regs->imr.val = val;
840                 ne2k_update_irq(nic_state);
841                 break;
842
843             default:
844                 PrintError("NE2000 port write error: invalid port:0x%x\n", port);
845                 return -1;
846         }
847     } else if (page == 1) {
848         switch (idx) {
849             case EN1_PHYS ... EN1_PHYS + ETH_ALEN -1:
850                 nic_state->mac[port - EN1_PHYS] = val;
851                 break;
852             case EN1_CURPAG:
853                 regs->curpag = val;
854                 break;
855             case EN1_MULT ... EN1_MULT + 7:
856                 nic_state->mcast_addr[port - EN1_MULT] = val;
857                 break;
858                 
859             default:
860                 PrintError("NE2000 write port error: invalid port:0x%x\n", port);
861                 return -1;
862         }
863     } else if (page == 2) {
864         switch (idx) {
865             case EN2_LDMA0:
866                 regs->clda0 = val;
867                 break;
868             case EN2_LDMA1:
869                 regs->clda1 = val;
870                 break;
871             case EN2_RNPR:
872                 regs->rnpp = val;
873                 break;
874             case EN2_LNRP:
875                 regs->lnpp = val;
876                 break;
877             case EN2_ACNT0:
878                 regs->addcnt0 = val;
879                 break;
880             case EN2_ACNT1: 
881                 regs->addcnt1 = val;
882                 break;
883                 
884             default:
885                 PrintError("NE2000 write port error: invalid port:0x%x\n", port);
886                 return -1;
887         }
888     } else {
889         PrintError("NE2000: Invalid Register Page Value\n");
890         return -1;
891     }
892
893
894     return length;
895         
896 }
897
898 static int ne2k_std_read(struct guest_info * core, 
899                          uint16_t port, 
900                          void * dst, 
901                          uint_t length, 
902                          void * private_data) {
903     struct ne2k_state * nic_state = (struct ne2k_state *)private_data;
904     struct ne2k_registers * regs = (struct ne2k_registers *)&(nic_state->context);
905     uint16_t index = port & 0x1f;
906     uint8_t page = regs->cmd.pg_sel;
907
908     if (length > 1) {
909         PrintError("ne2k_read error: length %d\n", length);
910         return length;
911     }
912
913     if (page == 0) {
914         switch (index) {                
915             case EN0_CLDALO:
916                 *(uint8_t *)dst = regs->clda0;
917                 break;
918             case EN0_CLDAHI:
919                 *(uint8_t *)dst = regs->clda1;
920                 break;
921             case EN0_BOUNDARY:
922                 *(uint8_t *)dst = regs->boundary;
923                 break;
924             case EN0_TSR:
925                 *(uint8_t *)dst = regs->tsr.val;
926                 break;
927             case EN0_NCR:
928                 *(uint8_t *)dst = regs->ncr;
929                 break;
930             case EN0_FIFO:
931                 *(uint8_t *)dst = regs->fifo;
932                 break;
933             case EN0_ISR:
934                 *(uint8_t *)dst = regs->isr.val;
935                 ne2k_update_irq(nic_state);
936                 break;
937             case EN0_CRDALO:
938                 *(uint8_t *)dst = regs->crda0;
939                 break;
940             case EN0_CRDAHI:
941                 *(uint8_t *)dst = regs->crda1;
942                 break;
943             case EN0_RSR:
944                 *(uint8_t *)dst = regs->rsr.val;
945                 break;
946             case EN0_COUNTER0:
947                 *(uint8_t *)dst = regs->cntr0;
948                 break;
949             case EN0_COUNTER1:
950                 *(uint8_t *)dst = regs->cntr1;
951                 break;  
952             case EN0_COUNTER2:
953                 *(uint8_t *)dst = regs->cntr2;
954                 break;
955                 
956             default:
957                 PrintError("NE2000 port read error: invalid port:0x%x\n", port);
958                 return -1;
959         }
960     } else if (page == 1) {
961         switch (index) {
962             case EN1_PHYS ... EN1_PHYS + ETH_ALEN -1:
963                 *(uint8_t *)dst = nic_state->mac[index - EN1_PHYS];
964                 break;
965             case EN1_CURPAG:
966                 *(uint8_t *)dst = regs->curpag;
967                 break;
968             case EN1_MULT ... EN1_MULT + 7:
969                 *(uint8_t *)dst = nic_state->mcast_addr[index - EN1_MULT];
970                 break;
971                 
972             default:
973                 PrintError("ne2k_read error: invalid port:0x%x\n", port);
974                 return -1;
975         }
976     } else if (page == 2) {
977         switch (index) {
978             case EN2_STARTPG:
979                 *(uint8_t *)dst = regs->pgstart;
980                 break;
981             case EN2_STOPPG:
982                 *(uint8_t *)dst = regs->pgstop;
983                 break;
984             case EN2_RNPR:
985                 *(uint8_t *)dst = regs->rnpp;
986                 break;
987             case EN2_LNRP:
988                 *(uint8_t *)dst = regs->lnpp;
989                 break;
990             case EN2_TPSR:
991                 *(uint8_t *)dst = regs->tpsr;
992                 break;
993             case EN2_ACNT0:
994                 *(uint8_t *)dst = regs->addcnt0;
995                 break;
996             case EN2_ACNT1: 
997                 *(uint8_t *)dst = regs->addcnt1;
998                 break;
999             case EN2_RCR:
1000                 *(uint8_t *)dst = regs->rcr.val;
1001                 break;
1002             case EN2_TCR:
1003                 *(uint8_t *)dst = regs->tcr.val;
1004                 break;
1005             case EN2_DCR:
1006                 *(uint8_t *)dst = regs->dcr.val;
1007                 break;
1008             case EN2_IMR:
1009                 *(uint8_t *)dst = regs->imr.val;
1010                 break;
1011             default:
1012                 PrintError("NE2000 port read error: invalid port:0x%x\n", port);
1013                 return -1;
1014         }
1015     } else {
1016         PrintError("NE2000 port read: Invalid Register Page Value\n");
1017         return -1;
1018     }
1019
1020     PrintDebug("NE2000 port read: port:0x%x  val: 0x%x\n", port, *(uint8_t *)dst);
1021
1022     return length;
1023 }
1024
1025
1026
1027 static int ne2k_pci_write(struct guest_info * core, 
1028                           uint16_t port, 
1029                           void * src, 
1030                           uint_t length, 
1031                           void * private_data) {
1032     uint16_t idx = port & 0x1f;
1033     int ret;
1034
1035     switch (idx) {
1036         case NE2K_CMD_OFFSET:
1037             ret =  ne2k_cmd_write(core, port, src, length, private_data);
1038             break;
1039         case NE2K_CMD_OFFSET+1 ... NE2K_CMD_OFFSET+15:
1040             ret = ne2k_std_write(core, port, src, length, private_data);
1041             break;
1042         case NE2K_DATA_OFFSET:
1043             ret = ne2k_data_write(core, port, src, length, private_data);
1044             break;
1045         case NE2K_RESET_OFFSET:
1046             ret = ne2k_reset_port_write(core, port, src, length, private_data);
1047             break;
1048
1049         default:
1050             PrintError("NE2000 port write error: invalid port:0x%x\n", port);
1051             return -1;
1052     }
1053
1054     return ret;
1055 }
1056
1057 static int ne2k_pci_read(struct guest_info * core, 
1058                          uint16_t port, 
1059                          void * dst, 
1060                          uint_t length, 
1061                          void * private_data) {
1062     uint16_t idx = port & 0x1f;
1063     int ret;
1064
1065     switch (idx) {
1066         case NE2K_CMD_OFFSET:
1067             ret =  ne2k_cmd_read(core, port, dst, length, private_data);
1068             break;
1069         case NE2K_CMD_OFFSET+1 ... NE2K_CMD_OFFSET+15:
1070             ret = ne2k_std_read(core, port, dst, length, private_data);
1071             break;
1072         case NE2K_DATA_OFFSET:
1073             ret = ne2k_data_read(core, port, dst, length, private_data);
1074             break;
1075         case NE2K_RESET_OFFSET:
1076             ret = ne2k_reset_port_read(core, port, dst, length, private_data);
1077             break;
1078
1079         default:
1080             PrintError("NE2000 port read error: invalid port:0x%x\n", port);
1081             return -1;
1082     }
1083
1084     return ret;
1085
1086
1087 }
1088
1089 static int pci_config_update(uint_t reg_num, 
1090                              void * src, 
1091                              uint_t length,
1092                              void * private_data) {
1093     PrintDebug("PCI Config Update\n");
1094
1095
1096     return 0;
1097 }
1098
1099
1100 static int register_dev(struct ne2k_state * nic_state) 
1101 {
1102     int i;
1103
1104     if (nic_state->pci_bus != NULL) {
1105         struct v3_pci_bar bars[6];
1106         struct pci_device * pci_dev = NULL;
1107
1108         PrintDebug("NE2000: PCI Enabled\n");
1109
1110         for (i = 0; i < 6; i++) {
1111             bars[i].type = PCI_BAR_NONE;
1112         }
1113
1114         bars[0].type = PCI_BAR_IO;
1115         bars[0].default_base_port = NIC_REG_BASE_PORT;
1116         bars[0].num_ports = 256;
1117
1118         bars[0].io_read = ne2k_pci_read;
1119         bars[0].io_write = ne2k_pci_write;
1120        bars[0].private_data = nic_state;
1121
1122         pci_dev = v3_pci_register_device(nic_state->pci_bus, PCI_STD_DEVICE, 0, -1, 0, 
1123                                          "NE2000", bars,
1124                                          pci_config_update, NULL, NULL, nic_state);
1125
1126
1127         if (pci_dev == NULL) {
1128             PrintError("NE2000: Could not register PCI Device\n");
1129             return -1;
1130         }
1131         
1132         pci_dev->config_header.vendor_id = 0x10ec;
1133         pci_dev->config_header.device_id = 0x8029;
1134         pci_dev->config_header.revision = 0x00;
1135
1136         pci_dev->config_header.subclass = 0x00;
1137         pci_dev->config_header.class = 0x02;
1138         pci_dev->config_header.header_type = 0x00;
1139
1140         pci_dev->config_header.intr_line = 11;
1141         pci_dev->config_header.intr_pin = 1;
1142
1143         nic_state->pci_dev = pci_dev;
1144     }else {
1145         PrintDebug("NE2000: Not attached to PCI\n");
1146
1147         v3_dev_hook_io(nic_state->dev, NIC_REG_BASE_PORT , &ne2k_cmd_read, &ne2k_cmd_write);
1148
1149         for (i = 1; i < 16; i++){       
1150             v3_dev_hook_io(nic_state->dev, NIC_REG_BASE_PORT + i, &ne2k_std_read, &ne2k_std_write);
1151         }
1152
1153         v3_dev_hook_io(nic_state->dev, NIC_REG_BASE_PORT + NE2K_DATA_OFFSET, &ne2k_data_read, &ne2k_data_write);
1154         v3_dev_hook_io(nic_state->dev, NIC_REG_BASE_PORT + NE2K_RESET_OFFSET, &ne2k_reset_port_read, &ne2k_reset_port_write);
1155     }
1156
1157
1158     return 0;
1159 }
1160
1161 static int connect_fn(struct v3_vm_info * info, 
1162                       void * frontend_data, 
1163                       struct v3_dev_net_ops * ops, 
1164                       v3_cfg_tree_t * cfg, 
1165                       void * private_data) {
1166     struct ne2k_state * nic_state = (struct ne2k_state *)frontend_data;
1167
1168     ne2k_init_state(nic_state);
1169     register_dev(nic_state);
1170
1171     nic_state->net_ops = ops;
1172     nic_state->backend_data = private_data;     
1173
1174     ops->recv = ne2k_rx;
1175     ops->poll = NULL;
1176     ops->config.frontend_data = nic_state;
1177     ops->config.fnt_mac = nic_state->mac;
1178
1179     return 0;
1180 }
1181
1182
1183 static int ne2k_free(struct ne2k_state * nic_state) {
1184     int i;
1185
1186     /* dettached from backend */
1187
1188     if(nic_state->pci_bus == NULL){
1189         for (i = 0; i < 16; i++){               
1190             v3_dev_unhook_io(nic_state->dev, NIC_REG_BASE_PORT + i);
1191         }
1192     
1193        v3_dev_unhook_io(nic_state->dev, NIC_REG_BASE_PORT + NE2K_DATA_OFFSET);
1194        v3_dev_unhook_io(nic_state->dev, NIC_REG_BASE_PORT + NE2K_RESET_OFFSET);
1195     }else {
1196        /* unregistered from PCI? */
1197     }
1198
1199     V3_Free(nic_state);
1200         
1201     return 0;
1202 }
1203
1204
1205 static struct v3_device_ops dev_ops = {
1206     .free = (int (*)(void *))ne2k_free,
1207 };
1208
1209
1210 static int ne2k_init(struct v3_vm_info * vm, v3_cfg_tree_t * cfg) {
1211     struct vm_device * pci_bus = v3_find_dev(vm, v3_cfg_val(cfg, "bus"));
1212     struct ne2k_state * nic_state = NULL;
1213     char * dev_id = v3_cfg_val(cfg, "ID");
1214     char * macstr = v3_cfg_val(cfg, "mac");
1215
1216     nic_state  = (struct ne2k_state *)V3_Malloc(sizeof(struct ne2k_state));
1217     memset(nic_state, 0, sizeof(struct ne2k_state));
1218
1219     nic_state->pci_bus = pci_bus;
1220     nic_state->vm = vm;
1221
1222     if (macstr != NULL && !str2mac(macstr, nic_state->mac)) {
1223         PrintDebug("NE2000: Mac specified %s\n", macstr);
1224     }else {
1225         PrintDebug("NE2000: MAC not specified\n");
1226         random_ethaddr(nic_state->mac);
1227     }
1228
1229     struct vm_device * dev = v3_add_device(vm, dev_id, &dev_ops, nic_state);
1230
1231     if (dev == NULL) {
1232         PrintError("NE2000: Could not attach device %s\n", dev_id);
1233         V3_Free(nic_state);
1234         return -1;
1235     }
1236
1237     nic_state->dev = dev;
1238
1239     if (v3_dev_add_net_frontend(vm, dev_id, connect_fn, (void *)nic_state) == -1) {
1240         PrintError("NE2000: Could not register %s as net frontend\n", dev_id);
1241         v3_remove_device(dev);
1242         V3_Free(nic_state);
1243         return -1;
1244     }
1245             
1246     return 0;
1247 }
1248
1249 device_register("NE2000", ne2k_init)