Revision 8a8696a3 hw/pci.c

b/hw/pci.c
100 100
{
101 101
    PCIIORegion *r;
102 102

  
103
    if ((unsigned int)region_num >= 6)
103
    if ((unsigned int)region_num >= PCI_NUM_REGIONS)
104 104
        return;
105 105
    r = &pci_dev->io_regions[region_num];
106 106
    r->addr = -1;
......
125 125
{
126 126
    PCIIORegion *r;
127 127
    int cmd, i;
128
    uint32_t last_addr, new_addr;
128
    uint32_t last_addr, new_addr, config_ofs;
129 129
    
130 130
    cmd = le16_to_cpu(*(uint16_t *)(d->config + PCI_COMMAND));
131
    for(i = 0; i < 6; i++) {
131
    for(i = 0; i < PCI_NUM_REGIONS; i++) {
132 132
        r = &d->io_regions[i];
133
        if (i == PCI_ROM_SLOT) {
134
            config_ofs = 0x30;
135
        } else {
136
            config_ofs = 0x10 + i * 4;
137
        }
133 138
        if (r->size != 0) {
134 139
            if (r->type & PCI_ADDRESS_SPACE_IO) {
135 140
                if (cmd & PCI_COMMAND_IO) {
136 141
                    new_addr = le32_to_cpu(*(uint32_t *)(d->config + 
137
                                                         0x10 + i * 4));
142
                                                         config_ofs));
138 143
                    new_addr = new_addr & ~(r->size - 1);
139 144
                    last_addr = new_addr + r->size - 1;
140 145
                    /* NOTE: we have only 64K ioports on PC */
......
148 153
            } else {
149 154
                if (cmd & PCI_COMMAND_MEMORY) {
150 155
                    new_addr = le32_to_cpu(*(uint32_t *)(d->config + 
151
                                                         0x10 + i * 4));
156
                                                         config_ofs));
157
                    /* the ROM slot has a specific enable bit */
158
                    if (i == PCI_ROM_SLOT && !(new_addr & 1))
159
                        goto no_mem_map;
152 160
                    new_addr = new_addr & ~(r->size - 1);
153 161
                    last_addr = new_addr + r->size - 1;
154 162
                    /* NOTE: we do not support wrapping */
......
160 168
                        new_addr = -1;
161 169
                    }
162 170
                } else {
171
                no_mem_map:
163 172
                    new_addr = -1;
164 173
                }
165 174
            }
......
216 225
    int can_write, i;
217 226
    uint32_t end, addr;
218 227

  
219
    if (len == 4 && (address >= 0x10 && address < 0x10 + 4 * 6)) {
228
    if (len == 4 && ((address >= 0x10 && address < 0x10 + 4 * 6) || 
229
                     (address >= 0x30 && address < 0x34))) {
220 230
        PCIIORegion *r;
221 231
        int reg;
222 232

  
223
        reg = (address - 0x10) >> 2;
233
        if ( address >= 0x30 ) {
234
            reg = PCI_ROM_SLOT;
235
        }else{
236
            reg = (address - 0x10) >> 2;
237
        }
224 238
        r = &d->io_regions[reg];
225 239
        if (r->size == 0)
226 240
            goto default_config;
227 241
        /* compute the stored value */
228
        val &= ~(r->size - 1);
229
        val |= r->type;
230
        *(uint32_t *)(d->config + 0x10 + reg * 4) = cpu_to_le32(val);
242
        if (reg == PCI_ROM_SLOT) {
243
            /* keep ROM enable bit */
244
            val &= (~(r->size - 1)) | 1;
245
        } else {
246
            val &= ~(r->size - 1);
247
            val |= r->type;
248
        }
249
        *(uint32_t *)(d->config + address) = cpu_to_le32(val);
231 250
        pci_update_mappings(d);
232 251
        return;
233 252
    }
......
484 503
    s->config_reg = 0x80000000 | (addr & 0xfc) | (devfn << 8);
485 504
}
486 505

  
487
static void PPC_PCIIO_writeb (target_phys_addr_t addr, uint32_t val)
506
static void PPC_PCIIO_writeb (void *opaque, target_phys_addr_t addr, uint32_t val)
488 507
{
489
    PCIBridge *s = &pci_bridge;
508
    PCIBridge *s = opaque;
490 509
    set_config(s, addr);
491 510
    pci_data_write(s, addr, val, 1);
492 511
}
493 512

  
494
static void PPC_PCIIO_writew (target_phys_addr_t addr, uint32_t val)
513
static void PPC_PCIIO_writew (void *opaque, target_phys_addr_t addr, uint32_t val)
495 514
{
496
    PCIBridge *s = &pci_bridge;
515
    PCIBridge *s = opaque;
497 516
    set_config(s, addr);
498 517
#ifdef TARGET_WORDS_BIGENDIAN
499 518
    val = bswap16(val);
......
501 520
    pci_data_write(s, addr, val, 2);
502 521
}
503 522

  
504
static void PPC_PCIIO_writel (target_phys_addr_t addr, uint32_t val)
523
static void PPC_PCIIO_writel (void *opaque, target_phys_addr_t addr, uint32_t val)
505 524
{
506
    PCIBridge *s = &pci_bridge;
525
    PCIBridge *s = opaque;
507 526
    set_config(s, addr);
508 527
#ifdef TARGET_WORDS_BIGENDIAN
509 528
    val = bswap32(val);
......
511 530
    pci_data_write(s, addr, val, 4);
512 531
}
513 532

  
514
static uint32_t PPC_PCIIO_readb (target_phys_addr_t addr)
533
static uint32_t PPC_PCIIO_readb (void *opaque, target_phys_addr_t addr)
515 534
{
516
    PCIBridge *s = &pci_bridge;
535
    PCIBridge *s = opaque;
517 536
    uint32_t val;
518 537
    set_config(s, addr);
519 538
    val = pci_data_read(s, addr, 1);
520 539
    return val;
521 540
}
522 541

  
523
static uint32_t PPC_PCIIO_readw (target_phys_addr_t addr)
542
static uint32_t PPC_PCIIO_readw (void *opaque, target_phys_addr_t addr)
524 543
{
525
    PCIBridge *s = &pci_bridge;
544
    PCIBridge *s = opaque;
526 545
    uint32_t val;
527 546
    set_config(s, addr);
528 547
    val = pci_data_read(s, addr, 2);
......
532 551
    return val;
533 552
}
534 553

  
535
static uint32_t PPC_PCIIO_readl (target_phys_addr_t addr)
554
static uint32_t PPC_PCIIO_readl (void *opaque, target_phys_addr_t addr)
536 555
{
537
    PCIBridge *s = &pci_bridge;
556
    PCIBridge *s = opaque;
538 557
    uint32_t val;
539 558
    set_config(s, addr);
540 559
    val = pci_data_read(s, addr, 4);
......
558 577

  
559 578
void pci_prep_init(void)
560 579
{
580
    PCIBridge *s = &pci_bridge;
561 581
    PCIDevice *d;
562 582
    int PPC_io_memory;
563 583

  
564
    PPC_io_memory = cpu_register_io_memory(0, PPC_PCIIO_read, PPC_PCIIO_write);
584
    PPC_io_memory = cpu_register_io_memory(0, PPC_PCIIO_read, 
585
                                           PPC_PCIIO_write, s);
565 586
    cpu_register_physical_memory(0x80800000, 0x00400000, PPC_io_memory);
566 587

  
567 588
    d = pci_register_device("PREP PCI Bridge", sizeof(PCIDevice), 0, 0, 
......
581 602

  
582 603
/* pmac pci init */
583 604

  
584
static void pci_pmac_config_writel (target_phys_addr_t addr, uint32_t val)
605
static void pci_pmac_config_writel (void *opaque, target_phys_addr_t addr, uint32_t val)
585 606
{
586
    PCIBridge *s = &pci_bridge;
607
    PCIBridge *s = opaque;
587 608
#ifdef TARGET_WORDS_BIGENDIAN
588 609
    val = bswap32(val);
589 610
#endif
590 611
    s->config_reg = val;
591 612
}
592 613

  
593
static uint32_t pci_pmac_config_readl (target_phys_addr_t addr)
614
static uint32_t pci_pmac_config_readl (void *opaque, target_phys_addr_t addr)
594 615
{
595
    PCIBridge *s = &pci_bridge;
616
    PCIBridge *s = opaque;
596 617
    uint32_t val;
597 618

  
598 619
    val = s->config_reg;
......
614 635
    &pci_pmac_config_readl,
615 636
};
616 637

  
617
static void pci_pmac_writeb (target_phys_addr_t addr, uint32_t val)
638
static void pci_pmac_writeb (void *opaque, target_phys_addr_t addr, uint32_t val)
618 639
{
619
    PCIBridge *s = &pci_bridge;
640
    PCIBridge *s = opaque;
620 641
    pci_data_write(s, addr, val, 1);
621 642
}
622 643

  
623
static void pci_pmac_writew (target_phys_addr_t addr, uint32_t val)
644
static void pci_pmac_writew (void *opaque, target_phys_addr_t addr, uint32_t val)
624 645
{
625
    PCIBridge *s = &pci_bridge;
646
    PCIBridge *s = opaque;
626 647
#ifdef TARGET_WORDS_BIGENDIAN
627 648
    val = bswap16(val);
628 649
#endif
629 650
    pci_data_write(s, addr, val, 2);
630 651
}
631 652

  
632
static void pci_pmac_writel (target_phys_addr_t addr, uint32_t val)
653
static void pci_pmac_writel (void *opaque, target_phys_addr_t addr, uint32_t val)
633 654
{
634
    PCIBridge *s = &pci_bridge;
655
    PCIBridge *s = opaque;
635 656
#ifdef TARGET_WORDS_BIGENDIAN
636 657
    val = bswap32(val);
637 658
#endif
638 659
    pci_data_write(s, addr, val, 4);
639 660
}
640 661

  
641
static uint32_t pci_pmac_readb (target_phys_addr_t addr)
662
static uint32_t pci_pmac_readb (void *opaque, target_phys_addr_t addr)
642 663
{
643
    PCIBridge *s = &pci_bridge;
664
    PCIBridge *s = opaque;
644 665
    uint32_t val;
645 666
    val = pci_data_read(s, addr, 1);
646 667
    return val;
647 668
}
648 669

  
649
static uint32_t pci_pmac_readw (target_phys_addr_t addr)
670
static uint32_t pci_pmac_readw (void *opaque, target_phys_addr_t addr)
650 671
{
651
    PCIBridge *s = &pci_bridge;
672
    PCIBridge *s = opaque;
652 673
    uint32_t val;
653 674
    val = pci_data_read(s, addr, 2);
654 675
#ifdef TARGET_WORDS_BIGENDIAN
......
657 678
    return val;
658 679
}
659 680

  
660
static uint32_t pci_pmac_readl (target_phys_addr_t addr)
681
static uint32_t pci_pmac_readl (void *opaque, target_phys_addr_t addr)
661 682
{
662
    PCIBridge *s = &pci_bridge;
683
    PCIBridge *s = opaque;
663 684
    uint32_t val;
664 685

  
665 686
    val = pci_data_read(s, addr, 4);
......
683 704

  
684 705
void pci_pmac_init(void)
685 706
{
707
    PCIBridge *s = &pci_bridge;
686 708
    PCIDevice *d;
687 709
    int pci_mem_config, pci_mem_data;
688 710

  
689 711
    pci_mem_config = cpu_register_io_memory(0, pci_pmac_config_read, 
690
                                            pci_pmac_config_write);
691
    pci_mem_data = cpu_register_io_memory(0, pci_pmac_read, pci_pmac_write);
712
                                            pci_pmac_config_write, s);
713
    pci_mem_data = cpu_register_io_memory(0, pci_pmac_read, pci_pmac_write, s);
692 714

  
693 715
    cpu_register_physical_memory(0xfec00000, 0x1000, pci_mem_config);
694 716
    cpu_register_physical_memory(0xfee00000, 0x1000, pci_mem_data);
......
812 834
    if (d->config[PCI_INTERRUPT_PIN] != 0) {
813 835
        printf("      IRQ %d.\n", d->config[PCI_INTERRUPT_LINE]);
814 836
    }
815
    for(i = 0;i < 6; i++) {
837
    for(i = 0;i < PCI_NUM_REGIONS; i++) {
816 838
        r = &d->io_regions[i];
817 839
        if (r->size != 0) {
818 840
            printf("      BAR%d: ", i);
......
934 956
{
935 957
    PCIIORegion *r;
936 958
    uint16_t cmd;
959
    uint32_t ofs;
960

  
961
    if ( region_num == PCI_ROM_SLOT ) {
962
        ofs = 0x30;
963
    }else{
964
        ofs = 0x10 + region_num * 4;
965
    }
937 966

  
938
    pci_config_writel(d, 0x10 + region_num * 4, addr);
967
    pci_config_writel(d, ofs, addr);
939 968
    r = &d->io_regions[region_num];
940 969

  
941 970
    /* enable memory mappings */
942 971
    cmd = pci_config_readw(d, PCI_COMMAND);
943
    if (r->type & PCI_ADDRESS_SPACE_IO)
972
    if ( region_num == PCI_ROM_SLOT )
973
        cmd |= 2;
974
    else if (r->type & PCI_ADDRESS_SPACE_IO)
944 975
        cmd |= 1;
945 976
    else
946 977
        cmd |= 2;
......
977 1008
        break;
978 1009
    default:
979 1010
        /* default memory mappings */
980
        for(i = 0; i < 6; i++) {
1011
        for(i = 0; i < PCI_NUM_REGIONS; i++) {
981 1012
            r = &d->io_regions[i];
982 1013
            if (r->size) {
983 1014
                if (r->type & PCI_ADDRESS_SPACE_IO)

Also available in: Unified diff