Revision ee9dbb29

b/hw/ne2000.c
103 103
#define ENTSR_CDH 0x40	/* The collision detect "heartbeat" signal was lost. */
104 104
#define ENTSR_OWC 0x80  /* There was an out-of-window collision. */
105 105

  
106
#define NE2000_MEM_SIZE 32768
106
#define NE2000_PMEM_SIZE    (32*1024)
107
#define NE2000_PMEM_START   (16*1024)
108
#define NE2000_PMEM_END     (NE2000_PMEM_SIZE+NE2000_PMEM_START)
109
#define NE2000_MEM_SIZE     NE2000_PMEM_END
107 110

  
108 111
typedef struct NE2000State {
109 112
    uint8_t cmd;
......
244 247
        /* control register */
245 248
        s->cmd = val;
246 249
        if (val & E8390_START) {
250
            s->isr &= ~ENISR_RESET;
247 251
            /* test specific case: zero length transfert */
248 252
            if ((val & (E8390_RREAD | E8390_RWRITE)) &&
249 253
                s->rcnt == 0) {
......
251 255
                ne2000_update_irq(s);
252 256
            }
253 257
            if (val & E8390_TRANS) {
254
                net_send_packet(s->nd, s->mem + (s->tpsr << 8), s->tcnt);
258
                qemu_send_packet(s->nd, s->mem + (s->tpsr << 8), s->tcnt);
255 259
                /* signal end of transfert */
256 260
                s->tsr = ENTSR_PTX;
257 261
                s->isr |= ENISR_TX;
......
300 304
            s->dcfg = val;
301 305
            break;
302 306
        case EN0_ISR:
303
            s->isr &= ~val;
307
            s->isr &= ~(val & 0x7f);
304 308
            ne2000_update_irq(s);
305 309
            break;
306 310
        case EN1_PHYS ... EN1_PHYS + 5:
......
337 341
        case EN0_ISR:
338 342
            ret = s->isr;
339 343
            break;
344
	case EN0_RSARLO:
345
	    ret = s->rsar & 0x00ff;
346
	    break;
347
	case EN0_RSARHI:
348
	    ret = s->rsar >> 8;
349
	    break;
340 350
        case EN1_PHYS ... EN1_PHYS + 5:
341 351
            ret = s->phys[offset - EN1_PHYS];
342 352
            break;
......
357 367
    return ret;
358 368
}
359 369

  
370
static inline void ne2000_mem_writeb(NE2000State *s, uint32_t addr, 
371
                                    uint32_t val)
372
{
373
    if (addr < 32 || 
374
        (addr >= NE2000_PMEM_START && addr < NE2000_MEM_SIZE)) {
375
        s->mem[addr] = val;
376
    }
377
}
378

  
379
static inline void ne2000_mem_writew(NE2000State *s, uint32_t addr, 
380
                                     uint32_t val)
381
{
382
    addr &= ~1; /* XXX: check exact behaviour if not even */
383
    if (addr < 32 || 
384
        (addr >= NE2000_PMEM_START && addr < NE2000_MEM_SIZE)) {
385
        s->mem[addr] = val;
386
        s->mem[addr + 1] = val >> 8;
387
    }
388
}
389

  
390
static inline uint32_t ne2000_mem_readb(NE2000State *s, uint32_t addr)
391
{
392
    if (addr < 32 || 
393
        (addr >= NE2000_PMEM_START && addr < NE2000_MEM_SIZE)) {
394
        return s->mem[addr];
395
    } else {
396
        return 0xff;
397
    }
398
}
399

  
400
static inline uint32_t ne2000_mem_readw(NE2000State *s, uint32_t addr)
401
{
402
    addr &= ~1; /* XXX: check exact behaviour if not even */
403
    if (addr < 32 || 
404
        (addr >= NE2000_PMEM_START && addr < NE2000_MEM_SIZE)) {
405
        return s->mem[addr] | (s->mem[addr + 1] << 8);
406
    } else {
407
        return 0xffff;
408
    }
409
}
410

  
360 411
static void ne2000_asic_ioport_write(void *opaque, uint32_t addr, uint32_t val)
361 412
{
362 413
    NE2000State *s = opaque;
363
    uint8_t *p;
364 414

  
365 415
#ifdef DEBUG_NE2000
366 416
    printf("NE2000: asic write val=0x%04x\n", val);
367 417
#endif
368
    p = s->mem + s->rsar;
418
    if (s->rcnt == 0)
419
	    return;
369 420
    if (s->dcfg & 0x01) {
370 421
        /* 16 bit access */
371
        p[0] = val;
372
        p[1] = val >> 8;
422
        ne2000_mem_writew(s, s->rsar, val);
373 423
        s->rsar += 2;
374 424
        s->rcnt -= 2;
375 425
    } else {
376 426
        /* 8 bit access */
377
        p[0] = val;
427
        ne2000_mem_writeb(s, s->rsar, val);
378 428
        s->rsar++;
379 429
        s->rcnt--;
380 430
    }
......
391 441
static uint32_t ne2000_asic_ioport_read(void *opaque, uint32_t addr)
392 442
{
393 443
    NE2000State *s = opaque;
394
    uint8_t *p;
395 444
    int ret;
396 445

  
397
    p = s->mem + s->rsar;
398 446
    if (s->dcfg & 0x01) {
399 447
        /* 16 bit access */
400
        ret = p[0] | (p[1] << 8);
448
        ret = ne2000_mem_readw(s, s->rsar);
401 449
        s->rsar += 2;
402 450
        s->rcnt -= 2;
403 451
    } else {
404 452
        /* 8 bit access */
405
        ret = p[0];
453
        ret = ne2000_mem_readb(s, s->rsar);
406 454
        s->rsar++;
407 455
        s->rcnt--;
408 456
    }
......
455 503

  
456 504
    ne2000_reset(s);
457 505

  
458
    qemu_add_fd_read_handler(nd->fd, ne2000_can_receive, ne2000_receive, s);
506
    qemu_add_read_packet(nd, ne2000_can_receive, ne2000_receive, s);
459 507
}

Also available in: Unified diff