⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ppc_prep.c

📁 qemu虚拟机代码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* * QEMU PPC PREP hardware System Emulator *  * Copyright (c) 2003-2004 Jocelyn Mayer *  * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */#include "vl.h"//#define HARD_DEBUG_PPC_IO//#define DEBUG_PPC_IO#define BIOS_FILENAME "ppc_rom.bin"#define KERNEL_LOAD_ADDR 0x01000000#define INITRD_LOAD_ADDR 0x01800000extern int loglevel;extern FILE *logfile;#if defined (HARD_DEBUG_PPC_IO) && !defined (DEBUG_PPC_IO)#define DEBUG_PPC_IO#endif#if defined (HARD_DEBUG_PPC_IO)#define PPC_IO_DPRINTF(fmt, args...)                     \do {                                                     \    if (loglevel & CPU_LOG_IOPORT) {                     \        fprintf(logfile, "%s: " fmt, __func__ , ##args); \    } else {                                             \        printf("%s : " fmt, __func__ , ##args);          \    }                                                    \} while (0)#elif defined (DEBUG_PPC_IO)#define PPC_IO_DPRINTF(fmt, args...)                     \do {                                                     \    if (loglevel & CPU_LOG_IOPORT) {                     \        fprintf(logfile, "%s: " fmt, __func__ , ##args); \    }                                                    \} while (0)#else#define PPC_IO_DPRINTF(fmt, args...) do { } while (0)#endif/* Constants for devices init */static const int ide_iobase[2] = { 0x1f0, 0x170 };static const int ide_iobase2[2] = { 0x3f6, 0x376 };static const int ide_irq[2] = { 13, 13 };#define NE2000_NB_MAX 6static uint32_t ne2000_io[NE2000_NB_MAX] = { 0x300, 0x320, 0x340, 0x360, 0x280, 0x380 };static int ne2000_irq[NE2000_NB_MAX] = { 9, 10, 11, 3, 4, 5 };//static PITState *pit;/* ISA IO ports bridge */#define PPC_IO_BASE 0x80000000/* Speaker port 0x61 */int speaker_data_on;int dummy_refresh_clock;static void speaker_ioport_write(void *opaque, uint32_t addr, uint32_t val){#if 0    speaker_data_on = (val >> 1) & 1;    pit_set_gate(pit, 2, val & 1);#endif}static uint32_t speaker_ioport_read(void *opaque, uint32_t addr){#if 0    int out;    out = pit_get_out(pit, 2, qemu_get_clock(vm_clock));    dummy_refresh_clock ^= 1;    return (speaker_data_on << 1) | pit_get_gate(pit, 2) | (out << 5) |      (dummy_refresh_clock << 4);#endif    return 0;}static void pic_irq_request(void *opaque, int level){    if (level)        cpu_interrupt(first_cpu, CPU_INTERRUPT_HARD);    else        cpu_reset_interrupt(first_cpu, CPU_INTERRUPT_HARD);}/* PCI intack register *//* Read-only register (?) */static void _PPC_intack_write (void *opaque, target_phys_addr_t addr, uint32_t value){    //    printf("%s: 0x%08x => 0x%08x\n", __func__, addr, value);}static inline uint32_t _PPC_intack_read (target_phys_addr_t addr){    uint32_t retval = 0;    if (addr == 0xBFFFFFF0)        retval = pic_intack_read(isa_pic);       //   printf("%s: 0x%08x <= %d\n", __func__, addr, retval);    return retval;}static uint32_t PPC_intack_readb (void *opaque, target_phys_addr_t addr){    return _PPC_intack_read(addr);}static uint32_t PPC_intack_readw (void *opaque, target_phys_addr_t addr){#ifdef TARGET_WORDS_BIGENDIAN    return bswap16(_PPC_intack_read(addr));#else    return _PPC_intack_read(addr);#endif}static uint32_t PPC_intack_readl (void *opaque, target_phys_addr_t addr){#ifdef TARGET_WORDS_BIGENDIAN    return bswap32(_PPC_intack_read(addr));#else    return _PPC_intack_read(addr);#endif}static CPUWriteMemoryFunc *PPC_intack_write[] = {    &_PPC_intack_write,    &_PPC_intack_write,    &_PPC_intack_write,};static CPUReadMemoryFunc *PPC_intack_read[] = {    &PPC_intack_readb,    &PPC_intack_readw,    &PPC_intack_readl,};/* PowerPC control and status registers */#if 0 // Not usedstatic struct {    /* IDs */    uint32_t veni_devi;    uint32_t revi;    /* Control and status */    uint32_t gcsr;    uint32_t xcfr;    uint32_t ct32;    uint32_t mcsr;    /* General purpose registers */    uint32_t gprg[6];    /* Exceptions */    uint32_t feen;    uint32_t fest;    uint32_t fema;    uint32_t fecl;    uint32_t eeen;    uint32_t eest;    uint32_t eecl;    uint32_t eeint;    uint32_t eemck0;    uint32_t eemck1;    /* Error diagnostic */} XCSR;static void PPC_XCSR_writeb (void *opaque, target_phys_addr_t addr, uint32_t value){    printf("%s: 0x%08lx => 0x%08x\n", __func__, (long)addr, value);}static void PPC_XCSR_writew (void *opaque, target_phys_addr_t addr, uint32_t value){#ifdef TARGET_WORDS_BIGENDIAN    value = bswap16(value);#endif    printf("%s: 0x%08lx => 0x%08x\n", __func__, (long)addr, value);}static void PPC_XCSR_writel (void *opaque, target_phys_addr_t addr, uint32_t value){#ifdef TARGET_WORDS_BIGENDIAN    value = bswap32(value);#endif    printf("%s: 0x%08lx => 0x%08x\n", __func__, (long)addr, value);}static uint32_t PPC_XCSR_readb (void *opaque, target_phys_addr_t addr){    uint32_t retval = 0;    printf("%s: 0x%08lx <= %d\n", __func__, (long)addr, retval);    return retval;}static uint32_t PPC_XCSR_readw (void *opaque, target_phys_addr_t addr){    uint32_t retval = 0;    printf("%s: 0x%08lx <= %d\n", __func__, (long)addr, retval);#ifdef TARGET_WORDS_BIGENDIAN    retval = bswap16(retval);#endif    return retval;}static uint32_t PPC_XCSR_readl (void *opaque, target_phys_addr_t addr){    uint32_t retval = 0;    printf("%s: 0x%08lx <= %d\n", __func__, (long)addr, retval);#ifdef TARGET_WORDS_BIGENDIAN    retval = bswap32(retval);#endif    return retval;}static CPUWriteMemoryFunc *PPC_XCSR_write[] = {    &PPC_XCSR_writeb,    &PPC_XCSR_writew,    &PPC_XCSR_writel,};static CPUReadMemoryFunc *PPC_XCSR_read[] = {    &PPC_XCSR_readb,    &PPC_XCSR_readw,    &PPC_XCSR_readl,};#endif/* Fake super-io ports for PREP platform (Intel 82378ZB) */typedef struct sysctrl_t {    m48t59_t *nvram;    uint8_t state;    uint8_t syscontrol;    uint8_t fake_io[2];    int contiguous_map;    int endian;} sysctrl_t;enum {    STATE_HARDFILE = 0x01,};static sysctrl_t *sysctrl;static void PREP_io_write (void *opaque, uint32_t addr, uint32_t val){    sysctrl_t *sysctrl = opaque;    PPC_IO_DPRINTF("0x%08lx => 0x%08x\n", (long)addr - PPC_IO_BASE, val);    sysctrl->fake_io[addr - 0x0398] = val;}static uint32_t PREP_io_read (void *opaque, uint32_t addr){    sysctrl_t *sysctrl = opaque;    PPC_IO_DPRINTF("0x%08lx <= 0x%08x\n", (long)addr - PPC_IO_BASE,                   sysctrl->fake_io[addr - 0x0398]);    return sysctrl->fake_io[addr - 0x0398];}static void PREP_io_800_writeb (void *opaque, uint32_t addr, uint32_t val){    sysctrl_t *sysctrl = opaque;    PPC_IO_DPRINTF("0x%08lx => 0x%08x\n", (long)addr - PPC_IO_BASE, val);    switch (addr) {    case 0x0092:        /* Special port 92 */        /* Check soft reset asked */        if (val & 0x01) {            //            cpu_interrupt(first_cpu, CPU_INTERRUPT_RESET);        }        /* Check LE mode */        if (val & 0x02) {            sysctrl->endian = 1;        } else {            sysctrl->endian = 0;        }        break;    case 0x0800:        /* Motorola CPU configuration register : read-only */        break;    case 0x0802:        /* Motorola base module feature register : read-only */        break;    case 0x0803:        /* Motorola base module status register : read-only */        break;    case 0x0808:        /* Hardfile light register */        if (val & 1)            sysctrl->state |= STATE_HARDFILE;        else            sysctrl->state &= ~STATE_HARDFILE;        break;    case 0x0810:        /* Password protect 1 register */        if (sysctrl->nvram != NULL)            m48t59_toggle_lock(sysctrl->nvram, 1);        break;    case 0x0812:        /* Password protect 2 register */        if (sysctrl->nvram != NULL)            m48t59_toggle_lock(sysctrl->nvram, 2);        break;    case 0x0814:        /* L2 invalidate register */        //        tlb_flush(first_cpu, 1);        break;    case 0x081C:        /* system control register */        sysctrl->syscontrol = val & 0x0F;        break;    case 0x0850:        /* I/O map type register */        sysctrl->contiguous_map = val & 0x01;        break;    default:        printf("ERROR: unaffected IO port write: %04lx => %02x\n",               (long)addr, val);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -