Commit c1713132e07955819477a87a0ce830358e77a147

Authored by balrog
1 parent 201a51fc

Core features of ARM XScale processors. Main PXA270 and PXA255 peripherals.


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@2749 c046a42c-6fe2-441c-8c8c-71466251a162
hw/pxa.h 0 → 100644
  1 +/*
  2 + * Intel XScale PXA255/270 processor support.
  3 + *
  4 + * Copyright (c) 2006 Openedhand Ltd.
  5 + * Written by Andrzej Zaborowski <balrog@zabor.org>
  6 + *
  7 + * This code is licenced under the GPL.
  8 + */
  9 +#ifndef PXA_H
  10 +# define PXA_H "pxa.h"
  11 +
  12 +/* Interrupt numbers */
  13 +# define PXA2XX_PIC_SSP3 0
  14 +# define PXA2XX_PIC_USBH2 2
  15 +# define PXA2XX_PIC_USBH1 3
  16 +# define PXA2XX_PIC_PWRI2C 6
  17 +# define PXA25X_PIC_HWUART 7
  18 +# define PXA27X_PIC_OST_4_11 7
  19 +# define PXA2XX_PIC_GPIO_0 8
  20 +# define PXA2XX_PIC_GPIO_1 9
  21 +# define PXA2XX_PIC_GPIO_X 10
  22 +# define PXA2XX_PIC_I2S 13
  23 +# define PXA26X_PIC_ASSP 15
  24 +# define PXA25X_PIC_NSSP 16
  25 +# define PXA27X_PIC_SSP2 16
  26 +# define PXA2XX_PIC_LCD 17
  27 +# define PXA2XX_PIC_I2C 18
  28 +# define PXA2XX_PIC_ICP 19
  29 +# define PXA2XX_PIC_STUART 20
  30 +# define PXA2XX_PIC_BTUART 21
  31 +# define PXA2XX_PIC_FFUART 22
  32 +# define PXA2XX_PIC_MMC 23
  33 +# define PXA2XX_PIC_SSP 24
  34 +# define PXA2XX_PIC_DMA 25
  35 +# define PXA2XX_PIC_OST_0 26
  36 +# define PXA2XX_PIC_RTC1HZ 30
  37 +# define PXA2XX_PIC_RTCALARM 31
  38 +
  39 +/* DMA requests */
  40 +# define PXA2XX_RX_RQ_I2S 2
  41 +# define PXA2XX_TX_RQ_I2S 3
  42 +# define PXA2XX_RX_RQ_BTUART 4
  43 +# define PXA2XX_TX_RQ_BTUART 5
  44 +# define PXA2XX_RX_RQ_FFUART 6
  45 +# define PXA2XX_TX_RQ_FFUART 7
  46 +# define PXA2XX_RX_RQ_SSP1 13
  47 +# define PXA2XX_TX_RQ_SSP1 14
  48 +# define PXA2XX_RX_RQ_SSP2 15
  49 +# define PXA2XX_TX_RQ_SSP2 16
  50 +# define PXA2XX_RX_RQ_ICP 17
  51 +# define PXA2XX_TX_RQ_ICP 18
  52 +# define PXA2XX_RX_RQ_STUART 19
  53 +# define PXA2XX_TX_RQ_STUART 20
  54 +# define PXA2XX_RX_RQ_MMCI 21
  55 +# define PXA2XX_TX_RQ_MMCI 22
  56 +# define PXA2XX_USB_RQ(x) ((x) + 24)
  57 +# define PXA2XX_RX_RQ_SSP3 66
  58 +# define PXA2XX_TX_RQ_SSP3 67
  59 +
  60 +# define PXA2XX_RAM_BASE 0xa0000000
  61 +
  62 +/* pxa2xx_pic.c */
  63 +struct pxa2xx_pic_state_s;
  64 +qemu_irq *pxa2xx_pic_init(target_phys_addr_t base, CPUState *env);
  65 +
  66 +/* pxa2xx_gpio.c */
  67 +struct pxa2xx_gpio_info_s;
  68 +struct pxa2xx_gpio_info_s *pxa2xx_gpio_init(target_phys_addr_t base,
  69 + CPUState *env, qemu_irq *pic, int lines);
  70 +void pxa2xx_gpio_set(struct pxa2xx_gpio_info_s *s, int line, int level);
  71 +void pxa2xx_gpio_handler_set(struct pxa2xx_gpio_info_s *s, int line,
  72 + gpio_handler_t handler, void *opaque);
  73 +void pxa2xx_gpio_read_notifier(struct pxa2xx_gpio_info_s *s,
  74 + void (*handler)(void *opaque), void *opaque);
  75 +
  76 +/* pxa2xx_dma.c */
  77 +struct pxa2xx_dma_state_s;
  78 +struct pxa2xx_dma_state_s *pxa255_dma_init(target_phys_addr_t base,
  79 + qemu_irq irq);
  80 +struct pxa2xx_dma_state_s *pxa27x_dma_init(target_phys_addr_t base,
  81 + qemu_irq irq);
  82 +void pxa2xx_dma_request(struct pxa2xx_dma_state_s *s, int req_num, int on);
  83 +
  84 +/* pxa2xx.c */
  85 +struct pxa2xx_ssp_s;
  86 +void pxa2xx_ssp_attach(struct pxa2xx_ssp_s *port,
  87 + uint32_t (*readfn)(void *opaque),
  88 + void (*writefn)(void *opaque, uint32_t value), void *opaque);
  89 +
  90 +struct pxa2xx_i2s_s;
  91 +struct pxa2xx_fir_s;
  92 +
  93 +struct pxa2xx_state_s {
  94 + CPUState *env;
  95 + qemu_irq *pic;
  96 + struct pxa2xx_dma_state_s *dma;
  97 + struct pxa2xx_gpio_info_s *gpio;
  98 + struct pxa2xx_ssp_s **ssp;
  99 + struct pxa2xx_i2s_s *i2s;
  100 + struct pxa2xx_fir_s *fir;
  101 +
  102 + /* Power management */
  103 + target_phys_addr_t pm_base;
  104 + uint32_t pm_regs[0x40];
  105 +
  106 + /* Clock management */
  107 + target_phys_addr_t cm_base;
  108 + uint32_t cm_regs[4];
  109 + uint32_t clkcfg;
  110 +
  111 + /* Memory management */
  112 + target_phys_addr_t mm_base;
  113 + uint32_t mm_regs[0x1a];
  114 +
  115 + /* Performance monitoring */
  116 + uint32_t pmnc;
  117 +
  118 + /* Real-Time clock */
  119 + target_phys_addr_t rtc_base;
  120 + uint32_t rttr;
  121 + uint32_t rtsr;
  122 + uint32_t rtar;
  123 + uint32_t rdar1;
  124 + uint32_t rdar2;
  125 + uint32_t ryar1;
  126 + uint32_t ryar2;
  127 + uint32_t swar1;
  128 + uint32_t swar2;
  129 + uint32_t piar;
  130 + uint32_t last_rcnr;
  131 + uint32_t last_rdcr;
  132 + uint32_t last_rycr;
  133 + uint32_t last_swcr;
  134 + uint32_t last_rtcpicr;
  135 + int64_t last_hz;
  136 + int64_t last_sw;
  137 + int64_t last_pi;
  138 + QEMUTimer *rtc_hz;
  139 + QEMUTimer *rtc_rdal1;
  140 + QEMUTimer *rtc_rdal2;
  141 + QEMUTimer *rtc_swal1;
  142 + QEMUTimer *rtc_swal2;
  143 + QEMUTimer *rtc_pi;
  144 +};
  145 +
  146 +struct pxa2xx_i2s_s {
  147 + target_phys_addr_t base;
  148 + qemu_irq irq;
  149 + struct pxa2xx_dma_state_s *dma;
  150 + void (*data_req)(void *, int, int);
  151 +
  152 + uint32_t control[2];
  153 + uint32_t status;
  154 + uint32_t mask;
  155 + uint32_t clk;
  156 +
  157 + int enable;
  158 + int rx_len;
  159 + int tx_len;
  160 + void (*codec_out)(void *, uint32_t);
  161 + uint32_t (*codec_in)(void *);
  162 + void *opaque;
  163 +
  164 + int fifo_len;
  165 + uint32_t fifo[16];
  166 +};
  167 +
  168 +# define PA_FMT "0x%08lx"
  169 +# define REG_FMT "0x%lx"
  170 +
  171 +struct pxa2xx_state_s *pxa270_init(DisplayState *ds, const char *revision);
  172 +struct pxa2xx_state_s *pxa255_init(DisplayState *ds);
  173 +
  174 +void pxa2xx_reset(int line, int level, void *opaque);
  175 +
  176 +#endif /* PXA_H */
... ...
hw/pxa2xx.c 0 → 100644
  1 +/*
  2 + * Intel XScale PXA255/270 processor support.
  3 + *
  4 + * Copyright (c) 2006 Openedhand Ltd.
  5 + * Written by Andrzej Zaborowski <balrog@zabor.org>
  6 + *
  7 + * This code is licenced under the GPL.
  8 + */
  9 +
  10 +# include "vl.h"
  11 +
  12 +static struct {
  13 + target_phys_addr_t io_base;
  14 + int irqn;
  15 +} pxa255_serial[] = {
  16 + { 0x40100000, PXA2XX_PIC_FFUART },
  17 + { 0x40200000, PXA2XX_PIC_BTUART },
  18 + { 0x40700000, PXA2XX_PIC_STUART },
  19 + { 0x41600000, PXA25X_PIC_HWUART },
  20 + { 0, 0 }
  21 +}, pxa270_serial[] = {
  22 + { 0x40100000, PXA2XX_PIC_FFUART },
  23 + { 0x40200000, PXA2XX_PIC_BTUART },
  24 + { 0x40700000, PXA2XX_PIC_STUART },
  25 + { 0, 0 }
  26 +};
  27 +
  28 +static struct {
  29 + target_phys_addr_t io_base;
  30 + int irqn;
  31 +} pxa250_ssp[] = {
  32 + { 0x41000000, PXA2XX_PIC_SSP },
  33 + { 0, 0 }
  34 +}, pxa255_ssp[] = {
  35 + { 0x41000000, PXA2XX_PIC_SSP },
  36 + { 0x41400000, PXA25X_PIC_NSSP },
  37 + { 0, 0 }
  38 +}, pxa26x_ssp[] = {
  39 + { 0x41000000, PXA2XX_PIC_SSP },
  40 + { 0x41400000, PXA25X_PIC_NSSP },
  41 + { 0x41500000, PXA26X_PIC_ASSP },
  42 + { 0, 0 }
  43 +}, pxa27x_ssp[] = {
  44 + { 0x41000000, PXA2XX_PIC_SSP },
  45 + { 0x41700000, PXA27X_PIC_SSP2 },
  46 + { 0x41900000, PXA2XX_PIC_SSP3 },
  47 + { 0, 0 }
  48 +};
  49 +
  50 +#define PMCR 0x00 /* Power Manager Control register */
  51 +#define PSSR 0x04 /* Power Manager Sleep Status register */
  52 +#define PSPR 0x08 /* Power Manager Scratch-Pad register */
  53 +#define PWER 0x0c /* Power Manager Wake-Up Enable register */
  54 +#define PRER 0x10 /* Power Manager Rising-Edge Detect Enable register */
  55 +#define PFER 0x14 /* Power Manager Falling-Edge Detect Enable register */
  56 +#define PEDR 0x18 /* Power Manager Edge-Detect Status register */
  57 +#define PCFR 0x1c /* Power Manager General Configuration register */
  58 +#define PGSR0 0x20 /* Power Manager GPIO Sleep-State register 0 */
  59 +#define PGSR1 0x24 /* Power Manager GPIO Sleep-State register 1 */
  60 +#define PGSR2 0x28 /* Power Manager GPIO Sleep-State register 2 */
  61 +#define PGSR3 0x2c /* Power Manager GPIO Sleep-State register 3 */
  62 +#define RCSR 0x30 /* Reset Controller Status register */
  63 +#define PSLR 0x34 /* Power Manager Sleep Configuration register */
  64 +#define PTSR 0x38 /* Power Manager Standby Configuration register */
  65 +#define PVCR 0x40 /* Power Manager Voltage Change Control register */
  66 +#define PUCR 0x4c /* Power Manager USIM Card Control/Status register */
  67 +#define PKWR 0x50 /* Power Manager Keyboard Wake-Up Enable register */
  68 +#define PKSR 0x54 /* Power Manager Keyboard Level-Detect Status */
  69 +#define PCMD0 0x80 /* Power Manager I2C Command register File 0 */
  70 +#define PCMD31 0xfc /* Power Manager I2C Command register File 31 */
  71 +
  72 +static uint32_t pxa2xx_pm_read(void *opaque, target_phys_addr_t addr)
  73 +{
  74 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  75 + addr -= s->pm_base;
  76 +
  77 + switch (addr) {
  78 + case PMCR ... PCMD31:
  79 + if (addr & 3)
  80 + goto fail;
  81 +
  82 + return s->pm_regs[addr >> 2];
  83 + default:
  84 + fail:
  85 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  86 + break;
  87 + }
  88 + return 0;
  89 +}
  90 +
  91 +static void pxa2xx_pm_write(void *opaque, target_phys_addr_t addr,
  92 + uint32_t value)
  93 +{
  94 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  95 + addr -= s->pm_base;
  96 +
  97 + switch (addr) {
  98 + case PMCR:
  99 + s->pm_regs[addr >> 2] &= 0x15 & ~(value & 0x2a);
  100 + s->pm_regs[addr >> 2] |= value & 0x15;
  101 + break;
  102 +
  103 + case PSSR: /* Read-clean registers */
  104 + case RCSR:
  105 + case PKSR:
  106 + s->pm_regs[addr >> 2] &= ~value;
  107 + break;
  108 +
  109 + default: /* Read-write registers */
  110 + if (addr >= PMCR && addr <= PCMD31 && !(addr & 3)) {
  111 + s->pm_regs[addr >> 2] = value;
  112 + break;
  113 + }
  114 +
  115 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  116 + break;
  117 + }
  118 +}
  119 +
  120 +static CPUReadMemoryFunc *pxa2xx_pm_readfn[] = {
  121 + pxa2xx_pm_read,
  122 + pxa2xx_pm_read,
  123 + pxa2xx_pm_read,
  124 +};
  125 +
  126 +static CPUWriteMemoryFunc *pxa2xx_pm_writefn[] = {
  127 + pxa2xx_pm_write,
  128 + pxa2xx_pm_write,
  129 + pxa2xx_pm_write,
  130 +};
  131 +
  132 +#define CCCR 0x00 /* Core Clock Configuration register */
  133 +#define CKEN 0x04 /* Clock Enable register */
  134 +#define OSCC 0x08 /* Oscillator Configuration register */
  135 +#define CCSR 0x0c /* Core Clock Status register */
  136 +
  137 +static uint32_t pxa2xx_cm_read(void *opaque, target_phys_addr_t addr)
  138 +{
  139 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  140 + addr -= s->cm_base;
  141 +
  142 + switch (addr) {
  143 + case CCCR:
  144 + case CKEN:
  145 + case OSCC:
  146 + return s->cm_regs[addr >> 2];
  147 +
  148 + case CCSR:
  149 + return s->cm_regs[CCCR >> 2] | (3 << 28);
  150 +
  151 + default:
  152 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  153 + break;
  154 + }
  155 + return 0;
  156 +}
  157 +
  158 +static void pxa2xx_cm_write(void *opaque, target_phys_addr_t addr,
  159 + uint32_t value)
  160 +{
  161 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  162 + addr -= s->cm_base;
  163 +
  164 + switch (addr) {
  165 + case CCCR:
  166 + case CKEN:
  167 + s->cm_regs[addr >> 2] = value;
  168 + break;
  169 +
  170 + case OSCC:
  171 + s->cm_regs[addr >> 2] &= ~0x6e;
  172 + s->cm_regs[addr >> 2] |= value & 0x6e;
  173 + break;
  174 +
  175 + default:
  176 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  177 + break;
  178 + }
  179 +}
  180 +
  181 +static CPUReadMemoryFunc *pxa2xx_cm_readfn[] = {
  182 + pxa2xx_cm_read,
  183 + pxa2xx_cm_read,
  184 + pxa2xx_cm_read,
  185 +};
  186 +
  187 +static CPUWriteMemoryFunc *pxa2xx_cm_writefn[] = {
  188 + pxa2xx_cm_write,
  189 + pxa2xx_cm_write,
  190 + pxa2xx_cm_write,
  191 +};
  192 +
  193 +static uint32_t pxa2xx_clkpwr_read(void *opaque, int op2, int reg, int crm)
  194 +{
  195 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  196 +
  197 + switch (reg) {
  198 + case 6: /* Clock Configuration register */
  199 + return s->clkcfg;
  200 +
  201 + case 7: /* Power Mode register */
  202 + return 0;
  203 +
  204 + default:
  205 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  206 + break;
  207 + }
  208 + return 0;
  209 +}
  210 +
  211 +static void pxa2xx_clkpwr_write(void *opaque, int op2, int reg, int crm,
  212 + uint32_t value)
  213 +{
  214 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  215 + static const char *pwrmode[8] = {
  216 + "Normal", "Idle", "Deep-idle", "Standby",
  217 + "Sleep", "reserved (!)", "reserved (!)", "Deep-sleep",
  218 + };
  219 +
  220 + switch (reg) {
  221 + case 6: /* Clock Configuration register */
  222 + s->clkcfg = value & 0xf;
  223 + if (value & 2)
  224 + printf("%s: CPU frequency change attempt\n", __FUNCTION__);
  225 + break;
  226 +
  227 + case 7: /* Power Mode register */
  228 + if (value & 8)
  229 + printf("%s: CPU voltage change attempt\n", __FUNCTION__);
  230 + switch (value & 7) {
  231 + case 0:
  232 + /* Do nothing */
  233 + break;
  234 +
  235 + case 1:
  236 + /* Idle */
  237 + if (!(s->cm_regs[CCCR] & (1 << 31))) { /* CPDIS */
  238 + cpu_interrupt(s->env, CPU_INTERRUPT_HALT);
  239 + break;
  240 + }
  241 + /* Fall through. */
  242 +
  243 + case 2:
  244 + /* Deep-Idle */
  245 + cpu_interrupt(s->env, CPU_INTERRUPT_HALT);
  246 + s->pm_regs[RCSR >> 2] |= 0x8; /* Set GPR */
  247 + goto message;
  248 +
  249 + case 3:
  250 + cpu_reset(s->env);
  251 + s->env->cp15.c1_sys = 0;
  252 + s->env->cp15.c1_coproc = 0;
  253 + s->env->cp15.c2 = 0;
  254 + s->env->cp15.c3 = 0;
  255 + s->pm_regs[PSSR >> 2] |= 0x8; /* Set STS */
  256 + s->pm_regs[RCSR >> 2] |= 0x8; /* Set GPR */
  257 +
  258 + /*
  259 + * The scratch-pad register is almost universally used
  260 + * for storing the return address on suspend. For the
  261 + * lack of a resuming bootloader, perform a jump
  262 + * directly to that address.
  263 + */
  264 + memset(s->env->regs, 0, 4 * 15);
  265 + s->env->regs[15] = s->pm_regs[PSPR >> 2];
  266 +
  267 +#if 0
  268 + buffer = 0xe59ff000; /* ldr pc, [pc, #0] */
  269 + cpu_physical_memory_write(0, &buffer, 4);
  270 + buffer = s->pm_regs[PSPR >> 2];
  271 + cpu_physical_memory_write(8, &buffer, 4);
  272 +#endif
  273 +
  274 + /* Suspend */
  275 + cpu_interrupt(cpu_single_env, CPU_INTERRUPT_HALT);
  276 +
  277 + goto message;
  278 +
  279 + default:
  280 + message:
  281 + printf("%s: machine entered %s mode\n", __FUNCTION__,
  282 + pwrmode[value & 7]);
  283 + }
  284 + break;
  285 +
  286 + default:
  287 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  288 + break;
  289 + }
  290 +}
  291 +
  292 +/* Performace Monitoring Registers */
  293 +#define CPPMNC 0 /* Performance Monitor Control register */
  294 +#define CPCCNT 1 /* Clock Counter register */
  295 +#define CPINTEN 4 /* Interrupt Enable register */
  296 +#define CPFLAG 5 /* Overflow Flag register */
  297 +#define CPEVTSEL 8 /* Event Selection register */
  298 +
  299 +#define CPPMN0 0 /* Performance Count register 0 */
  300 +#define CPPMN1 1 /* Performance Count register 1 */
  301 +#define CPPMN2 2 /* Performance Count register 2 */
  302 +#define CPPMN3 3 /* Performance Count register 3 */
  303 +
  304 +static uint32_t pxa2xx_perf_read(void *opaque, int op2, int reg, int crm)
  305 +{
  306 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  307 +
  308 + switch (reg) {
  309 + case CPPMNC:
  310 + return s->pmnc;
  311 + case CPCCNT:
  312 + if (s->pmnc & 1)
  313 + return qemu_get_clock(vm_clock);
  314 + else
  315 + return 0;
  316 + case CPINTEN:
  317 + case CPFLAG:
  318 + case CPEVTSEL:
  319 + return 0;
  320 +
  321 + default:
  322 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  323 + break;
  324 + }
  325 + return 0;
  326 +}
  327 +
  328 +static void pxa2xx_perf_write(void *opaque, int op2, int reg, int crm,
  329 + uint32_t value)
  330 +{
  331 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  332 +
  333 + switch (reg) {
  334 + case CPPMNC:
  335 + s->pmnc = value;
  336 + break;
  337 +
  338 + case CPCCNT:
  339 + case CPINTEN:
  340 + case CPFLAG:
  341 + case CPEVTSEL:
  342 + break;
  343 +
  344 + default:
  345 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  346 + break;
  347 + }
  348 +}
  349 +
  350 +static uint32_t pxa2xx_cp14_read(void *opaque, int op2, int reg, int crm)
  351 +{
  352 + switch (crm) {
  353 + case 0:
  354 + return pxa2xx_clkpwr_read(opaque, op2, reg, crm);
  355 + case 1:
  356 + return pxa2xx_perf_read(opaque, op2, reg, crm);
  357 + case 2:
  358 + switch (reg) {
  359 + case CPPMN0:
  360 + case CPPMN1:
  361 + case CPPMN2:
  362 + case CPPMN3:
  363 + return 0;
  364 + }
  365 + /* Fall through */
  366 + default:
  367 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  368 + break;
  369 + }
  370 + return 0;
  371 +}
  372 +
  373 +static void pxa2xx_cp14_write(void *opaque, int op2, int reg, int crm,
  374 + uint32_t value)
  375 +{
  376 + switch (crm) {
  377 + case 0:
  378 + pxa2xx_clkpwr_write(opaque, op2, reg, crm, value);
  379 + break;
  380 + case 1:
  381 + pxa2xx_perf_write(opaque, op2, reg, crm, value);
  382 + break;
  383 + case 2:
  384 + switch (reg) {
  385 + case CPPMN0:
  386 + case CPPMN1:
  387 + case CPPMN2:
  388 + case CPPMN3:
  389 + return;
  390 + }
  391 + /* Fall through */
  392 + default:
  393 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  394 + break;
  395 + }
  396 +}
  397 +
  398 +#define MDCNFG 0x00 /* SDRAM Configuration register */
  399 +#define MDREFR 0x04 /* SDRAM Refresh Control register */
  400 +#define MSC0 0x08 /* Static Memory Control register 0 */
  401 +#define MSC1 0x0c /* Static Memory Control register 1 */
  402 +#define MSC2 0x10 /* Static Memory Control register 2 */
  403 +#define MECR 0x14 /* Expansion Memory Bus Config register */
  404 +#define SXCNFG 0x1c /* Synchronous Static Memory Config register */
  405 +#define MCMEM0 0x28 /* PC Card Memory Socket 0 Timing register */
  406 +#define MCMEM1 0x2c /* PC Card Memory Socket 1 Timing register */
  407 +#define MCATT0 0x30 /* PC Card Attribute Socket 0 register */
  408 +#define MCATT1 0x34 /* PC Card Attribute Socket 1 register */
  409 +#define MCIO0 0x38 /* PC Card I/O Socket 0 Timing register */
  410 +#define MCIO1 0x3c /* PC Card I/O Socket 1 Timing register */
  411 +#define MDMRS 0x40 /* SDRAM Mode Register Set Config register */
  412 +#define BOOT_DEF 0x44 /* Boot-time Default Configuration register */
  413 +#define ARB_CNTL 0x48 /* Arbiter Control register */
  414 +#define BSCNTR0 0x4c /* Memory Buffer Strength Control register 0 */
  415 +#define BSCNTR1 0x50 /* Memory Buffer Strength Control register 1 */
  416 +#define LCDBSCNTR 0x54 /* LCD Buffer Strength Control register */
  417 +#define MDMRSLP 0x58 /* Low Power SDRAM Mode Set Config register */
  418 +#define BSCNTR2 0x5c /* Memory Buffer Strength Control register 2 */
  419 +#define BSCNTR3 0x60 /* Memory Buffer Strength Control register 3 */
  420 +#define SA1110 0x64 /* SA-1110 Memory Compatibility register */
  421 +
  422 +static uint32_t pxa2xx_mm_read(void *opaque, target_phys_addr_t addr)
  423 +{
  424 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  425 + addr -= s->mm_base;
  426 +
  427 + switch (addr) {
  428 + case MDCNFG ... SA1110:
  429 + if ((addr & 3) == 0)
  430 + return s->mm_regs[addr >> 2];
  431 +
  432 + default:
  433 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  434 + break;
  435 + }
  436 + return 0;
  437 +}
  438 +
  439 +static void pxa2xx_mm_write(void *opaque, target_phys_addr_t addr,
  440 + uint32_t value)
  441 +{
  442 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  443 + addr -= s->mm_base;
  444 +
  445 + switch (addr) {
  446 + case MDCNFG ... SA1110:
  447 + if ((addr & 3) == 0) {
  448 + s->mm_regs[addr >> 2] = value;
  449 + break;
  450 + }
  451 +
  452 + default:
  453 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  454 + break;
  455 + }
  456 +}
  457 +
  458 +static CPUReadMemoryFunc *pxa2xx_mm_readfn[] = {
  459 + pxa2xx_mm_read,
  460 + pxa2xx_mm_read,
  461 + pxa2xx_mm_read,
  462 +};
  463 +
  464 +static CPUWriteMemoryFunc *pxa2xx_mm_writefn[] = {
  465 + pxa2xx_mm_write,
  466 + pxa2xx_mm_write,
  467 + pxa2xx_mm_write,
  468 +};
  469 +
  470 +/* Synchronous Serial Ports */
  471 +struct pxa2xx_ssp_s {
  472 + target_phys_addr_t base;
  473 + qemu_irq irq;
  474 + int enable;
  475 +
  476 + uint32_t sscr[2];
  477 + uint32_t sspsp;
  478 + uint32_t ssto;
  479 + uint32_t ssitr;
  480 + uint32_t sssr;
  481 + uint8_t sstsa;
  482 + uint8_t ssrsa;
  483 + uint8_t ssacd;
  484 +
  485 + uint32_t rx_fifo[16];
  486 + int rx_level;
  487 + int rx_start;
  488 +
  489 + uint32_t (*readfn)(void *opaque);
  490 + void (*writefn)(void *opaque, uint32_t value);
  491 + void *opaque;
  492 +};
  493 +
  494 +#define SSCR0 0x00 /* SSP Control register 0 */
  495 +#define SSCR1 0x04 /* SSP Control register 1 */
  496 +#define SSSR 0x08 /* SSP Status register */
  497 +#define SSITR 0x0c /* SSP Interrupt Test register */
  498 +#define SSDR 0x10 /* SSP Data register */
  499 +#define SSTO 0x28 /* SSP Time-Out register */
  500 +#define SSPSP 0x2c /* SSP Programmable Serial Protocol register */
  501 +#define SSTSA 0x30 /* SSP TX Time Slot Active register */
  502 +#define SSRSA 0x34 /* SSP RX Time Slot Active register */
  503 +#define SSTSS 0x38 /* SSP Time Slot Status register */
  504 +#define SSACD 0x3c /* SSP Audio Clock Divider register */
  505 +
  506 +/* Bitfields for above registers */
  507 +#define SSCR0_SPI(x) (((x) & 0x30) == 0x00)
  508 +#define SSCR0_SSP(x) (((x) & 0x30) == 0x10)
  509 +#define SSCR0_UWIRE(x) (((x) & 0x30) == 0x20)
  510 +#define SSCR0_PSP(x) (((x) & 0x30) == 0x30)
  511 +#define SSCR0_SSE (1 << 7)
  512 +#define SSCR0_RIM (1 << 22)
  513 +#define SSCR0_TIM (1 << 23)
  514 +#define SSCR0_MOD (1 << 31)
  515 +#define SSCR0_DSS(x) (((((x) >> 16) & 0x10) | ((x) & 0xf)) + 1)
  516 +#define SSCR1_RIE (1 << 0)
  517 +#define SSCR1_TIE (1 << 1)
  518 +#define SSCR1_LBM (1 << 2)
  519 +#define SSCR1_MWDS (1 << 5)
  520 +#define SSCR1_TFT(x) ((((x) >> 6) & 0xf) + 1)
  521 +#define SSCR1_RFT(x) ((((x) >> 10) & 0xf) + 1)
  522 +#define SSCR1_EFWR (1 << 14)
  523 +#define SSCR1_PINTE (1 << 18)
  524 +#define SSCR1_TINTE (1 << 19)
  525 +#define SSCR1_RSRE (1 << 20)
  526 +#define SSCR1_TSRE (1 << 21)
  527 +#define SSCR1_EBCEI (1 << 29)
  528 +#define SSITR_INT (7 << 5)
  529 +#define SSSR_TNF (1 << 2)
  530 +#define SSSR_RNE (1 << 3)
  531 +#define SSSR_TFS (1 << 5)
  532 +#define SSSR_RFS (1 << 6)
  533 +#define SSSR_ROR (1 << 7)
  534 +#define SSSR_PINT (1 << 18)
  535 +#define SSSR_TINT (1 << 19)
  536 +#define SSSR_EOC (1 << 20)
  537 +#define SSSR_TUR (1 << 21)
  538 +#define SSSR_BCE (1 << 23)
  539 +#define SSSR_RW 0x00bc0080
  540 +
  541 +static void pxa2xx_ssp_int_update(struct pxa2xx_ssp_s *s)
  542 +{
  543 + int level = 0;
  544 +
  545 + level |= s->ssitr & SSITR_INT;
  546 + level |= (s->sssr & SSSR_BCE) && (s->sscr[1] & SSCR1_EBCEI);
  547 + level |= (s->sssr & SSSR_TUR) && !(s->sscr[0] & SSCR0_TIM);
  548 + level |= (s->sssr & SSSR_EOC) && (s->sssr & (SSSR_TINT | SSSR_PINT));
  549 + level |= (s->sssr & SSSR_TINT) && (s->sscr[1] & SSCR1_TINTE);
  550 + level |= (s->sssr & SSSR_PINT) && (s->sscr[1] & SSCR1_PINTE);
  551 + level |= (s->sssr & SSSR_ROR) && !(s->sscr[0] & SSCR0_RIM);
  552 + level |= (s->sssr & SSSR_RFS) && (s->sscr[1] & SSCR1_RIE);
  553 + level |= (s->sssr & SSSR_TFS) && (s->sscr[1] & SSCR1_TIE);
  554 + qemu_set_irq(s->irq, !!level);
  555 +}
  556 +
  557 +static void pxa2xx_ssp_fifo_update(struct pxa2xx_ssp_s *s)
  558 +{
  559 + s->sssr &= ~(0xf << 12); /* Clear RFL */
  560 + s->sssr &= ~(0xf << 8); /* Clear TFL */
  561 + s->sssr &= ~SSSR_TNF;
  562 + if (s->enable) {
  563 + s->sssr |= ((s->rx_level - 1) & 0xf) << 12;
  564 + if (s->rx_level >= SSCR1_RFT(s->sscr[1]))
  565 + s->sssr |= SSSR_RFS;
  566 + else
  567 + s->sssr &= ~SSSR_RFS;
  568 + if (0 <= SSCR1_TFT(s->sscr[1]))
  569 + s->sssr |= SSSR_TFS;
  570 + else
  571 + s->sssr &= ~SSSR_TFS;
  572 + if (s->rx_level)
  573 + s->sssr |= SSSR_RNE;
  574 + else
  575 + s->sssr &= ~SSSR_RNE;
  576 + s->sssr |= SSSR_TNF;
  577 + }
  578 +
  579 + pxa2xx_ssp_int_update(s);
  580 +}
  581 +
  582 +static uint32_t pxa2xx_ssp_read(void *opaque, target_phys_addr_t addr)
  583 +{
  584 + struct pxa2xx_ssp_s *s = (struct pxa2xx_ssp_s *) opaque;
  585 + uint32_t retval;
  586 + addr -= s->base;
  587 +
  588 + switch (addr) {
  589 + case SSCR0:
  590 + return s->sscr[0];
  591 + case SSCR1:
  592 + return s->sscr[1];
  593 + case SSPSP:
  594 + return s->sspsp;
  595 + case SSTO:
  596 + return s->ssto;
  597 + case SSITR:
  598 + return s->ssitr;
  599 + case SSSR:
  600 + return s->sssr | s->ssitr;
  601 + case SSDR:
  602 + if (!s->enable)
  603 + return 0xffffffff;
  604 + if (s->rx_level < 1) {
  605 + printf("%s: SSP Rx Underrun\n", __FUNCTION__);
  606 + return 0xffffffff;
  607 + }
  608 + s->rx_level --;
  609 + retval = s->rx_fifo[s->rx_start ++];
  610 + s->rx_start &= 0xf;
  611 + pxa2xx_ssp_fifo_update(s);
  612 + return retval;
  613 + case SSTSA:
  614 + return s->sstsa;
  615 + case SSRSA:
  616 + return s->ssrsa;
  617 + case SSTSS:
  618 + return 0;
  619 + case SSACD:
  620 + return s->ssacd;
  621 + default:
  622 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  623 + break;
  624 + }
  625 + return 0;
  626 +}
  627 +
  628 +static void pxa2xx_ssp_write(void *opaque, target_phys_addr_t addr,
  629 + uint32_t value)
  630 +{
  631 + struct pxa2xx_ssp_s *s = (struct pxa2xx_ssp_s *) opaque;
  632 + addr -= s->base;
  633 +
  634 + switch (addr) {
  635 + case SSCR0:
  636 + s->sscr[0] = value & 0xc7ffffff;
  637 + s->enable = value & SSCR0_SSE;
  638 + if (value & SSCR0_MOD)
  639 + printf("%s: Attempt to use network mode\n", __FUNCTION__);
  640 + if (s->enable && SSCR0_DSS(value) < 4)
  641 + printf("%s: Wrong data size: %i bits\n", __FUNCTION__,
  642 + SSCR0_DSS(value));
  643 + if (!(value & SSCR0_SSE)) {
  644 + s->sssr = 0;
  645 + s->ssitr = 0;
  646 + s->rx_level = 0;
  647 + }
  648 + pxa2xx_ssp_fifo_update(s);
  649 + break;
  650 +
  651 + case SSCR1:
  652 + s->sscr[1] = value;
  653 + if (value & (SSCR1_LBM | SSCR1_EFWR))
  654 + printf("%s: Attempt to use SSP test mode\n", __FUNCTION__);
  655 + pxa2xx_ssp_fifo_update(s);
  656 + break;
  657 +
  658 + case SSPSP:
  659 + s->sspsp = value;
  660 + break;
  661 +
  662 + case SSTO:
  663 + s->ssto = value;
  664 + break;
  665 +
  666 + case SSITR:
  667 + s->ssitr = value & SSITR_INT;
  668 + pxa2xx_ssp_int_update(s);
  669 + break;
  670 +
  671 + case SSSR:
  672 + s->sssr &= ~(value & SSSR_RW);
  673 + pxa2xx_ssp_int_update(s);
  674 + break;
  675 +
  676 + case SSDR:
  677 + if (SSCR0_UWIRE(s->sscr[0])) {
  678 + if (s->sscr[1] & SSCR1_MWDS)
  679 + value &= 0xffff;
  680 + else
  681 + value &= 0xff;
  682 + } else
  683 + /* Note how 32bits overflow does no harm here */
  684 + value &= (1 << SSCR0_DSS(s->sscr[0])) - 1;
  685 +
  686 + /* Data goes from here to the Tx FIFO and is shifted out from
  687 + * there directly to the slave, no need to buffer it.
  688 + */
  689 + if (s->enable) {
  690 + if (s->writefn)
  691 + s->writefn(s->opaque, value);
  692 +
  693 + if (s->rx_level < 0x10) {
  694 + if (s->readfn)
  695 + s->rx_fifo[(s->rx_start + s->rx_level ++) & 0xf] =
  696 + s->readfn(s->opaque);
  697 + else
  698 + s->rx_fifo[(s->rx_start + s->rx_level ++) & 0xf] = 0x0;
  699 + } else
  700 + s->sssr |= SSSR_ROR;
  701 + }
  702 + pxa2xx_ssp_fifo_update(s);
  703 + break;
  704 +
  705 + case SSTSA:
  706 + s->sstsa = value;
  707 + break;
  708 +
  709 + case SSRSA:
  710 + s->ssrsa = value;
  711 + break;
  712 +
  713 + case SSACD:
  714 + s->ssacd = value;
  715 + break;
  716 +
  717 + default:
  718 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  719 + break;
  720 + }
  721 +}
  722 +
  723 +void pxa2xx_ssp_attach(struct pxa2xx_ssp_s *port,
  724 + uint32_t (*readfn)(void *opaque),
  725 + void (*writefn)(void *opaque, uint32_t value), void *opaque)
  726 +{
  727 + if (!port) {
  728 + printf("%s: no such SSP\n", __FUNCTION__);
  729 + exit(-1);
  730 + }
  731 +
  732 + port->opaque = opaque;
  733 + port->readfn = readfn;
  734 + port->writefn = writefn;
  735 +}
  736 +
  737 +static CPUReadMemoryFunc *pxa2xx_ssp_readfn[] = {
  738 + pxa2xx_ssp_read,
  739 + pxa2xx_ssp_read,
  740 + pxa2xx_ssp_read,
  741 +};
  742 +
  743 +static CPUWriteMemoryFunc *pxa2xx_ssp_writefn[] = {
  744 + pxa2xx_ssp_write,
  745 + pxa2xx_ssp_write,
  746 + pxa2xx_ssp_write,
  747 +};
  748 +
  749 +/* Real-Time Clock */
  750 +#define RCNR 0x00 /* RTC Counter register */
  751 +#define RTAR 0x04 /* RTC Alarm register */
  752 +#define RTSR 0x08 /* RTC Status register */
  753 +#define RTTR 0x0c /* RTC Timer Trim register */
  754 +#define RDCR 0x10 /* RTC Day Counter register */
  755 +#define RYCR 0x14 /* RTC Year Counter register */
  756 +#define RDAR1 0x18 /* RTC Wristwatch Day Alarm register 1 */
  757 +#define RYAR1 0x1c /* RTC Wristwatch Year Alarm register 1 */
  758 +#define RDAR2 0x20 /* RTC Wristwatch Day Alarm register 2 */
  759 +#define RYAR2 0x24 /* RTC Wristwatch Year Alarm register 2 */
  760 +#define SWCR 0x28 /* RTC Stopwatch Counter register */
  761 +#define SWAR1 0x2c /* RTC Stopwatch Alarm register 1 */
  762 +#define SWAR2 0x30 /* RTC Stopwatch Alarm register 2 */
  763 +#define RTCPICR 0x34 /* RTC Periodic Interrupt Counter register */
  764 +#define PIAR 0x38 /* RTC Periodic Interrupt Alarm register */
  765 +
  766 +static inline void pxa2xx_rtc_int_update(struct pxa2xx_state_s *s)
  767 +{
  768 + qemu_set_irq(s->pic[PXA2XX_PIC_RTCALARM], !!(s->rtsr & 0x2553));
  769 +}
  770 +
  771 +static void pxa2xx_rtc_hzupdate(struct pxa2xx_state_s *s)
  772 +{
  773 + int64_t rt = qemu_get_clock(rt_clock);
  774 + s->last_rcnr += ((rt - s->last_hz) << 15) /
  775 + (1000 * ((s->rttr & 0xffff) + 1));
  776 + s->last_rdcr += ((rt - s->last_hz) << 15) /
  777 + (1000 * ((s->rttr & 0xffff) + 1));
  778 + s->last_hz = rt;
  779 +}
  780 +
  781 +static void pxa2xx_rtc_swupdate(struct pxa2xx_state_s *s)
  782 +{
  783 + int64_t rt = qemu_get_clock(rt_clock);
  784 + if (s->rtsr & (1 << 12))
  785 + s->last_swcr += (rt - s->last_sw) / 10;
  786 + s->last_sw = rt;
  787 +}
  788 +
  789 +static void pxa2xx_rtc_piupdate(struct pxa2xx_state_s *s)
  790 +{
  791 + int64_t rt = qemu_get_clock(rt_clock);
  792 + if (s->rtsr & (1 << 15))
  793 + s->last_swcr += rt - s->last_pi;
  794 + s->last_pi = rt;
  795 +}
  796 +
  797 +static inline void pxa2xx_rtc_alarm_update(struct pxa2xx_state_s *s,
  798 + uint32_t rtsr)
  799 +{
  800 + if ((rtsr & (1 << 2)) && !(rtsr & (1 << 0)))
  801 + qemu_mod_timer(s->rtc_hz, s->last_hz +
  802 + (((s->rtar - s->last_rcnr) * 1000 *
  803 + ((s->rttr & 0xffff) + 1)) >> 15));
  804 + else
  805 + qemu_del_timer(s->rtc_hz);
  806 +
  807 + if ((rtsr & (1 << 5)) && !(rtsr & (1 << 4)))
  808 + qemu_mod_timer(s->rtc_rdal1, s->last_hz +
  809 + (((s->rdar1 - s->last_rdcr) * 1000 *
  810 + ((s->rttr & 0xffff) + 1)) >> 15)); /* TODO: fixup */
  811 + else
  812 + qemu_del_timer(s->rtc_rdal1);
  813 +
  814 + if ((rtsr & (1 << 7)) && !(rtsr & (1 << 6)))
  815 + qemu_mod_timer(s->rtc_rdal2, s->last_hz +
  816 + (((s->rdar2 - s->last_rdcr) * 1000 *
  817 + ((s->rttr & 0xffff) + 1)) >> 15)); /* TODO: fixup */
  818 + else
  819 + qemu_del_timer(s->rtc_rdal2);
  820 +
  821 + if ((rtsr & 0x1200) == 0x1200 && !(rtsr & (1 << 8)))
  822 + qemu_mod_timer(s->rtc_swal1, s->last_sw +
  823 + (s->swar1 - s->last_swcr) * 10); /* TODO: fixup */
  824 + else
  825 + qemu_del_timer(s->rtc_swal1);
  826 +
  827 + if ((rtsr & 0x1800) == 0x1800 && !(rtsr & (1 << 10)))
  828 + qemu_mod_timer(s->rtc_swal2, s->last_sw +
  829 + (s->swar2 - s->last_swcr) * 10); /* TODO: fixup */
  830 + else
  831 + qemu_del_timer(s->rtc_swal2);
  832 +
  833 + if ((rtsr & 0xc000) == 0xc000 && !(rtsr & (1 << 13)))
  834 + qemu_mod_timer(s->rtc_pi, s->last_pi +
  835 + (s->piar & 0xffff) - s->last_rtcpicr);
  836 + else
  837 + qemu_del_timer(s->rtc_pi);
  838 +}
  839 +
  840 +static inline void pxa2xx_rtc_hz_tick(void *opaque)
  841 +{
  842 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  843 + s->rtsr |= (1 << 0);
  844 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  845 + pxa2xx_rtc_int_update(s);
  846 +}
  847 +
  848 +static inline void pxa2xx_rtc_rdal1_tick(void *opaque)
  849 +{
  850 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  851 + s->rtsr |= (1 << 4);
  852 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  853 + pxa2xx_rtc_int_update(s);
  854 +}
  855 +
  856 +static inline void pxa2xx_rtc_rdal2_tick(void *opaque)
  857 +{
  858 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  859 + s->rtsr |= (1 << 6);
  860 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  861 + pxa2xx_rtc_int_update(s);
  862 +}
  863 +
  864 +static inline void pxa2xx_rtc_swal1_tick(void *opaque)
  865 +{
  866 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  867 + s->rtsr |= (1 << 8);
  868 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  869 + pxa2xx_rtc_int_update(s);
  870 +}
  871 +
  872 +static inline void pxa2xx_rtc_swal2_tick(void *opaque)
  873 +{
  874 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  875 + s->rtsr |= (1 << 10);
  876 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  877 + pxa2xx_rtc_int_update(s);
  878 +}
  879 +
  880 +static inline void pxa2xx_rtc_pi_tick(void *opaque)
  881 +{
  882 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  883 + s->rtsr |= (1 << 13);
  884 + pxa2xx_rtc_piupdate(s);
  885 + s->last_rtcpicr = 0;
  886 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  887 + pxa2xx_rtc_int_update(s);
  888 +}
  889 +
  890 +static uint32_t pxa2xx_rtc_read(void *opaque, target_phys_addr_t addr)
  891 +{
  892 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  893 + addr -= s->rtc_base;
  894 +
  895 + switch (addr) {
  896 + case RTTR:
  897 + return s->rttr;
  898 + case RTSR:
  899 + return s->rtsr;
  900 + case RTAR:
  901 + return s->rtar;
  902 + case RDAR1:
  903 + return s->rdar1;
  904 + case RDAR2:
  905 + return s->rdar2;
  906 + case RYAR1:
  907 + return s->ryar1;
  908 + case RYAR2:
  909 + return s->ryar2;
  910 + case SWAR1:
  911 + return s->swar1;
  912 + case SWAR2:
  913 + return s->swar2;
  914 + case PIAR:
  915 + return s->piar;
  916 + case RCNR:
  917 + return s->last_rcnr + ((qemu_get_clock(rt_clock) - s->last_hz) << 15) /
  918 + (1000 * ((s->rttr & 0xffff) + 1));
  919 + case RDCR:
  920 + return s->last_rdcr + ((qemu_get_clock(rt_clock) - s->last_hz) << 15) /
  921 + (1000 * ((s->rttr & 0xffff) + 1));
  922 + case RYCR:
  923 + return s->last_rycr;
  924 + case SWCR:
  925 + if (s->rtsr & (1 << 12))
  926 + return s->last_swcr + (qemu_get_clock(rt_clock) - s->last_sw) / 10;
  927 + else
  928 + return s->last_swcr;
  929 + default:
  930 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  931 + break;
  932 + }
  933 + return 0;
  934 +}
  935 +
  936 +static void pxa2xx_rtc_write(void *opaque, target_phys_addr_t addr,
  937 + uint32_t value)
  938 +{
  939 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  940 + addr -= s->rtc_base;
  941 +
  942 + switch (addr) {
  943 + case RTTR:
  944 + if (!(s->rttr & (1 << 31))) {
  945 + pxa2xx_rtc_hzupdate(s);
  946 + s->rttr = value;
  947 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  948 + }
  949 + break;
  950 +
  951 + case RTSR:
  952 + if ((s->rtsr ^ value) & (1 << 15))
  953 + pxa2xx_rtc_piupdate(s);
  954 +
  955 + if ((s->rtsr ^ value) & (1 << 12))
  956 + pxa2xx_rtc_swupdate(s);
  957 +
  958 + if (((s->rtsr ^ value) & 0x4aac) | (value & ~0xdaac))
  959 + pxa2xx_rtc_alarm_update(s, value);
  960 +
  961 + s->rtsr = (value & 0xdaac) | (s->rtsr & ~(value & ~0xdaac));
  962 + pxa2xx_rtc_int_update(s);
  963 + break;
  964 +
  965 + case RTAR:
  966 + s->rtar = value;
  967 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  968 + break;
  969 +
  970 + case RDAR1:
  971 + s->rdar1 = value;
  972 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  973 + break;
  974 +
  975 + case RDAR2:
  976 + s->rdar2 = value;
  977 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  978 + break;
  979 +
  980 + case RYAR1:
  981 + s->ryar1 = value;
  982 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  983 + break;
  984 +
  985 + case RYAR2:
  986 + s->ryar2 = value;
  987 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  988 + break;
  989 +
  990 + case SWAR1:
  991 + pxa2xx_rtc_swupdate(s);
  992 + s->swar1 = value;
  993 + s->last_swcr = 0;
  994 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  995 + break;
  996 +
  997 + case SWAR2:
  998 + s->swar2 = value;
  999 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1000 + break;
  1001 +
  1002 + case PIAR:
  1003 + s->piar = value;
  1004 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1005 + break;
  1006 +
  1007 + case RCNR:
  1008 + pxa2xx_rtc_hzupdate(s);
  1009 + s->last_rcnr = value;
  1010 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1011 + break;
  1012 +
  1013 + case RDCR:
  1014 + pxa2xx_rtc_hzupdate(s);
  1015 + s->last_rdcr = value;
  1016 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1017 + break;
  1018 +
  1019 + case RYCR:
  1020 + s->last_rycr = value;
  1021 + break;
  1022 +
  1023 + case SWCR:
  1024 + pxa2xx_rtc_swupdate(s);
  1025 + s->last_swcr = value;
  1026 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1027 + break;
  1028 +
  1029 + case RTCPICR:
  1030 + pxa2xx_rtc_piupdate(s);
  1031 + s->last_rtcpicr = value & 0xffff;
  1032 + pxa2xx_rtc_alarm_update(s, s->rtsr);
  1033 + break;
  1034 +
  1035 + default:
  1036 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  1037 + }
  1038 +}
  1039 +
  1040 +static void pxa2xx_rtc_reset(struct pxa2xx_state_s *s)
  1041 +{
  1042 + struct tm *tm;
  1043 + time_t ti;
  1044 + int wom;
  1045 +
  1046 + s->rttr = 0x7fff;
  1047 + s->rtsr = 0;
  1048 +
  1049 + time(&ti);
  1050 + if (rtc_utc)
  1051 + tm = gmtime(&ti);
  1052 + else
  1053 + tm = localtime(&ti);
  1054 + wom = ((tm->tm_mday - 1) / 7) + 1;
  1055 +
  1056 + s->last_rcnr = (uint32_t) ti;
  1057 + s->last_rdcr = (wom << 20) | ((tm->tm_wday + 1) << 17) |
  1058 + (tm->tm_hour << 12) | (tm->tm_min << 6) | tm->tm_sec;
  1059 + s->last_rycr = ((tm->tm_year + 1900) << 9) |
  1060 + ((tm->tm_mon + 1) << 5) | tm->tm_mday;
  1061 + s->last_swcr = (tm->tm_hour << 19) |
  1062 + (tm->tm_min << 13) | (tm->tm_sec << 7);
  1063 + s->last_rtcpicr = 0;
  1064 + s->last_hz = s->last_sw = s->last_pi = qemu_get_clock(rt_clock);
  1065 +
  1066 + s->rtc_hz = qemu_new_timer(rt_clock, pxa2xx_rtc_hz_tick, s);
  1067 + s->rtc_rdal1 = qemu_new_timer(rt_clock, pxa2xx_rtc_rdal1_tick, s);
  1068 + s->rtc_rdal2 = qemu_new_timer(rt_clock, pxa2xx_rtc_rdal2_tick, s);
  1069 + s->rtc_swal1 = qemu_new_timer(rt_clock, pxa2xx_rtc_swal1_tick, s);
  1070 + s->rtc_swal2 = qemu_new_timer(rt_clock, pxa2xx_rtc_swal2_tick, s);
  1071 + s->rtc_pi = qemu_new_timer(rt_clock, pxa2xx_rtc_pi_tick, s);
  1072 +}
  1073 +
  1074 +static CPUReadMemoryFunc *pxa2xx_rtc_readfn[] = {
  1075 + pxa2xx_rtc_read,
  1076 + pxa2xx_rtc_read,
  1077 + pxa2xx_rtc_read,
  1078 +};
  1079 +
  1080 +static CPUWriteMemoryFunc *pxa2xx_rtc_writefn[] = {
  1081 + pxa2xx_rtc_write,
  1082 + pxa2xx_rtc_write,
  1083 + pxa2xx_rtc_write,
  1084 +};
  1085 +
  1086 +/* PXA Inter-IC Sound Controller */
  1087 +static void pxa2xx_i2s_reset(struct pxa2xx_i2s_s *i2s)
  1088 +{
  1089 + i2s->rx_len = 0;
  1090 + i2s->tx_len = 0;
  1091 + i2s->fifo_len = 0;
  1092 + i2s->clk = 0x1a;
  1093 + i2s->control[0] = 0x00;
  1094 + i2s->control[1] = 0x00;
  1095 + i2s->status = 0x00;
  1096 + i2s->mask = 0x00;
  1097 +}
  1098 +
  1099 +#define SACR_TFTH(val) ((val >> 8) & 0xf)
  1100 +#define SACR_RFTH(val) ((val >> 12) & 0xf)
  1101 +#define SACR_DREC(val) (val & (1 << 3))
  1102 +#define SACR_DPRL(val) (val & (1 << 4))
  1103 +
  1104 +static inline void pxa2xx_i2s_update(struct pxa2xx_i2s_s *i2s)
  1105 +{
  1106 + int rfs, tfs;
  1107 + rfs = SACR_RFTH(i2s->control[0]) < i2s->rx_len &&
  1108 + !SACR_DREC(i2s->control[1]);
  1109 + tfs = (i2s->tx_len || i2s->fifo_len < SACR_TFTH(i2s->control[0])) &&
  1110 + i2s->enable && !SACR_DPRL(i2s->control[1]);
  1111 +
  1112 + pxa2xx_dma_request(i2s->dma, PXA2XX_RX_RQ_I2S, rfs);
  1113 + pxa2xx_dma_request(i2s->dma, PXA2XX_TX_RQ_I2S, tfs);
  1114 +
  1115 + i2s->status &= 0xe0;
  1116 + if (i2s->rx_len)
  1117 + i2s->status |= 1 << 1; /* RNE */
  1118 + if (i2s->enable)
  1119 + i2s->status |= 1 << 2; /* BSY */
  1120 + if (tfs)
  1121 + i2s->status |= 1 << 3; /* TFS */
  1122 + if (rfs)
  1123 + i2s->status |= 1 << 4; /* RFS */
  1124 + if (!(i2s->tx_len && i2s->enable))
  1125 + i2s->status |= i2s->fifo_len << 8; /* TFL */
  1126 + i2s->status |= MAX(i2s->rx_len, 0xf) << 12; /* RFL */
  1127 +
  1128 + qemu_set_irq(i2s->irq, i2s->status & i2s->mask);
  1129 +}
  1130 +
  1131 +#define SACR0 0x00 /* Serial Audio Global Control register */
  1132 +#define SACR1 0x04 /* Serial Audio I2S/MSB-Justified Control register */
  1133 +#define SASR0 0x0c /* Serial Audio Interface and FIFO Status register */
  1134 +#define SAIMR 0x14 /* Serial Audio Interrupt Mask register */
  1135 +#define SAICR 0x18 /* Serial Audio Interrupt Clear register */
  1136 +#define SADIV 0x60 /* Serial Audio Clock Divider register */
  1137 +#define SADR 0x80 /* Serial Audio Data register */
  1138 +
  1139 +static uint32_t pxa2xx_i2s_read(void *opaque, target_phys_addr_t addr)
  1140 +{
  1141 + struct pxa2xx_i2s_s *s = (struct pxa2xx_i2s_s *) opaque;
  1142 + addr -= s->base;
  1143 +
  1144 + switch (addr) {
  1145 + case SACR0:
  1146 + return s->control[0];
  1147 + case SACR1:
  1148 + return s->control[1];
  1149 + case SASR0:
  1150 + return s->status;
  1151 + case SAIMR:
  1152 + return s->mask;
  1153 + case SAICR:
  1154 + return 0;
  1155 + case SADIV:
  1156 + return s->clk;
  1157 + case SADR:
  1158 + if (s->rx_len > 0) {
  1159 + s->rx_len --;
  1160 + pxa2xx_i2s_update(s);
  1161 + return s->codec_in(s->opaque);
  1162 + }
  1163 + return 0;
  1164 + default:
  1165 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  1166 + break;
  1167 + }
  1168 + return 0;
  1169 +}
  1170 +
  1171 +static void pxa2xx_i2s_write(void *opaque, target_phys_addr_t addr,
  1172 + uint32_t value)
  1173 +{
  1174 + struct pxa2xx_i2s_s *s = (struct pxa2xx_i2s_s *) opaque;
  1175 + uint32_t *sample;
  1176 + addr -= s->base;
  1177 +
  1178 + switch (addr) {
  1179 + case SACR0:
  1180 + if (value & (1 << 3)) /* RST */
  1181 + pxa2xx_i2s_reset(s);
  1182 + s->control[0] = value & 0xff3d;
  1183 + if (!s->enable && (value & 1) && s->tx_len) { /* ENB */
  1184 + for (sample = s->fifo; s->fifo_len > 0; s->fifo_len --, sample ++)
  1185 + s->codec_out(s->opaque, *sample);
  1186 + s->status &= ~(1 << 7); /* I2SOFF */
  1187 + }
  1188 + if (value & (1 << 4)) /* EFWR */
  1189 + printf("%s: Attempt to use special function\n", __FUNCTION__);
  1190 + s->enable = ((value ^ 4) & 5) == 5; /* ENB && !RST*/
  1191 + pxa2xx_i2s_update(s);
  1192 + break;
  1193 + case SACR1:
  1194 + s->control[1] = value & 0x0039;
  1195 + if (value & (1 << 5)) /* ENLBF */
  1196 + printf("%s: Attempt to use loopback function\n", __FUNCTION__);
  1197 + if (value & (1 << 4)) /* DPRL */
  1198 + s->fifo_len = 0;
  1199 + pxa2xx_i2s_update(s);
  1200 + break;
  1201 + case SAIMR:
  1202 + s->mask = value & 0x0078;
  1203 + pxa2xx_i2s_update(s);
  1204 + break;
  1205 + case SAICR:
  1206 + s->status &= ~(value & (3 << 5));
  1207 + pxa2xx_i2s_update(s);
  1208 + break;
  1209 + case SADIV:
  1210 + s->clk = value & 0x007f;
  1211 + break;
  1212 + case SADR:
  1213 + if (s->tx_len && s->enable) {
  1214 + s->tx_len --;
  1215 + pxa2xx_i2s_update(s);
  1216 + s->codec_out(s->opaque, value);
  1217 + } else if (s->fifo_len < 16) {
  1218 + s->fifo[s->fifo_len ++] = value;
  1219 + pxa2xx_i2s_update(s);
  1220 + }
  1221 + break;
  1222 + default:
  1223 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  1224 + }
  1225 +}
  1226 +
  1227 +static CPUReadMemoryFunc *pxa2xx_i2s_readfn[] = {
  1228 + pxa2xx_i2s_read,
  1229 + pxa2xx_i2s_read,
  1230 + pxa2xx_i2s_read,
  1231 +};
  1232 +
  1233 +static CPUWriteMemoryFunc *pxa2xx_i2s_writefn[] = {
  1234 + pxa2xx_i2s_write,
  1235 + pxa2xx_i2s_write,
  1236 + pxa2xx_i2s_write,
  1237 +};
  1238 +
  1239 +static void pxa2xx_i2s_data_req(void *opaque, int tx, int rx)
  1240 +{
  1241 + struct pxa2xx_i2s_s *s = (struct pxa2xx_i2s_s *) opaque;
  1242 + uint32_t *sample;
  1243 +
  1244 + /* Signal FIFO errors */
  1245 + if (s->enable && s->tx_len)
  1246 + s->status |= 1 << 5; /* TUR */
  1247 + if (s->enable && s->rx_len)
  1248 + s->status |= 1 << 6; /* ROR */
  1249 +
  1250 + /* Should be tx - MIN(tx, s->fifo_len) but we don't really need to
  1251 + * handle the cases where it makes a difference. */
  1252 + s->tx_len = tx - s->fifo_len;
  1253 + s->rx_len = rx;
  1254 + /* Note that is s->codec_out wasn't set, we wouldn't get called. */
  1255 + if (s->enable)
  1256 + for (sample = s->fifo; s->fifo_len; s->fifo_len --, sample ++)
  1257 + s->codec_out(s->opaque, *sample);
  1258 + pxa2xx_i2s_update(s);
  1259 +}
  1260 +
  1261 +static struct pxa2xx_i2s_s *pxa2xx_i2s_init(target_phys_addr_t base,
  1262 + qemu_irq irq, struct pxa2xx_dma_state_s *dma)
  1263 +{
  1264 + int iomemtype;
  1265 + struct pxa2xx_i2s_s *s = (struct pxa2xx_i2s_s *)
  1266 + qemu_mallocz(sizeof(struct pxa2xx_i2s_s));
  1267 +
  1268 + s->base = base;
  1269 + s->irq = irq;
  1270 + s->dma = dma;
  1271 + s->data_req = pxa2xx_i2s_data_req;
  1272 +
  1273 + pxa2xx_i2s_reset(s);
  1274 +
  1275 + iomemtype = cpu_register_io_memory(0, pxa2xx_i2s_readfn,
  1276 + pxa2xx_i2s_writefn, s);
  1277 + cpu_register_physical_memory(s->base & 0xfff00000, 0xfffff, iomemtype);
  1278 +
  1279 + return s;
  1280 +}
  1281 +
  1282 +/* PXA Fast Infra-red Communications Port */
  1283 +struct pxa2xx_fir_s {
  1284 + target_phys_addr_t base;
  1285 + qemu_irq irq;
  1286 + struct pxa2xx_dma_state_s *dma;
  1287 + int enable;
  1288 + CharDriverState *chr;
  1289 +
  1290 + uint8_t control[3];
  1291 + uint8_t status[2];
  1292 +
  1293 + int rx_len;
  1294 + int rx_start;
  1295 + uint8_t rx_fifo[64];
  1296 +};
  1297 +
  1298 +static void pxa2xx_fir_reset(struct pxa2xx_fir_s *s)
  1299 +{
  1300 + s->control[0] = 0x00;
  1301 + s->control[1] = 0x00;
  1302 + s->control[2] = 0x00;
  1303 + s->status[0] = 0x00;
  1304 + s->status[1] = 0x00;
  1305 + s->enable = 0;
  1306 +}
  1307 +
  1308 +static inline void pxa2xx_fir_update(struct pxa2xx_fir_s *s)
  1309 +{
  1310 + static const int tresh[4] = { 8, 16, 32, 0 };
  1311 + int intr = 0;
  1312 + if ((s->control[0] & (1 << 4)) && /* RXE */
  1313 + s->rx_len >= tresh[s->control[2] & 3]) /* TRIG */
  1314 + s->status[0] |= 1 << 4; /* RFS */
  1315 + else
  1316 + s->status[0] &= ~(1 << 4); /* RFS */
  1317 + if (s->control[0] & (1 << 3)) /* TXE */
  1318 + s->status[0] |= 1 << 3; /* TFS */
  1319 + else
  1320 + s->status[0] &= ~(1 << 3); /* TFS */
  1321 + if (s->rx_len)
  1322 + s->status[1] |= 1 << 2; /* RNE */
  1323 + else
  1324 + s->status[1] &= ~(1 << 2); /* RNE */
  1325 + if (s->control[0] & (1 << 4)) /* RXE */
  1326 + s->status[1] |= 1 << 0; /* RSY */
  1327 + else
  1328 + s->status[1] &= ~(1 << 0); /* RSY */
  1329 +
  1330 + intr |= (s->control[0] & (1 << 5)) && /* RIE */
  1331 + (s->status[0] & (1 << 4)); /* RFS */
  1332 + intr |= (s->control[0] & (1 << 6)) && /* TIE */
  1333 + (s->status[0] & (1 << 3)); /* TFS */
  1334 + intr |= (s->control[2] & (1 << 4)) && /* TRAIL */
  1335 + (s->status[0] & (1 << 6)); /* EOC */
  1336 + intr |= (s->control[0] & (1 << 2)) && /* TUS */
  1337 + (s->status[0] & (1 << 1)); /* TUR */
  1338 + intr |= s->status[0] & 0x25; /* FRE, RAB, EIF */
  1339 +
  1340 + pxa2xx_dma_request(s->dma, PXA2XX_RX_RQ_ICP, (s->status[0] >> 4) & 1);
  1341 + pxa2xx_dma_request(s->dma, PXA2XX_TX_RQ_ICP, (s->status[0] >> 3) & 1);
  1342 +
  1343 + qemu_set_irq(s->irq, intr && s->enable);
  1344 +}
  1345 +
  1346 +#define ICCR0 0x00 /* FICP Control register 0 */
  1347 +#define ICCR1 0x04 /* FICP Control register 1 */
  1348 +#define ICCR2 0x08 /* FICP Control register 2 */
  1349 +#define ICDR 0x0c /* FICP Data register */
  1350 +#define ICSR0 0x14 /* FICP Status register 0 */
  1351 +#define ICSR1 0x18 /* FICP Status register 1 */
  1352 +#define ICFOR 0x1c /* FICP FIFO Occupancy Status register */
  1353 +
  1354 +static uint32_t pxa2xx_fir_read(void *opaque, target_phys_addr_t addr)
  1355 +{
  1356 + struct pxa2xx_fir_s *s = (struct pxa2xx_fir_s *) opaque;
  1357 + uint8_t ret;
  1358 + addr -= s->base;
  1359 +
  1360 + switch (addr) {
  1361 + case ICCR0:
  1362 + return s->control[0];
  1363 + case ICCR1:
  1364 + return s->control[1];
  1365 + case ICCR2:
  1366 + return s->control[2];
  1367 + case ICDR:
  1368 + s->status[0] &= ~0x01;
  1369 + s->status[1] &= ~0x72;
  1370 + if (s->rx_len) {
  1371 + s->rx_len --;
  1372 + ret = s->rx_fifo[s->rx_start ++];
  1373 + s->rx_start &= 63;
  1374 + pxa2xx_fir_update(s);
  1375 + return ret;
  1376 + }
  1377 + printf("%s: Rx FIFO underrun.\n", __FUNCTION__);
  1378 + break;
  1379 + case ICSR0:
  1380 + return s->status[0];
  1381 + case ICSR1:
  1382 + return s->status[1] | (1 << 3); /* TNF */
  1383 + case ICFOR:
  1384 + return s->rx_len;
  1385 + default:
  1386 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  1387 + break;
  1388 + }
  1389 + return 0;
  1390 +}
  1391 +
  1392 +static void pxa2xx_fir_write(void *opaque, target_phys_addr_t addr,
  1393 + uint32_t value)
  1394 +{
  1395 + struct pxa2xx_fir_s *s = (struct pxa2xx_fir_s *) opaque;
  1396 + uint8_t ch;
  1397 + addr -= s->base;
  1398 +
  1399 + switch (addr) {
  1400 + case ICCR0:
  1401 + s->control[0] = value;
  1402 + if (!(value & (1 << 4))) /* RXE */
  1403 + s->rx_len = s->rx_start = 0;
  1404 + if (!(value & (1 << 3))) /* TXE */
  1405 + /* Nop */;
  1406 + s->enable = value & 1; /* ITR */
  1407 + if (!s->enable)
  1408 + s->status[0] = 0;
  1409 + pxa2xx_fir_update(s);
  1410 + break;
  1411 + case ICCR1:
  1412 + s->control[1] = value;
  1413 + break;
  1414 + case ICCR2:
  1415 + s->control[2] = value & 0x3f;
  1416 + pxa2xx_fir_update(s);
  1417 + break;
  1418 + case ICDR:
  1419 + if (s->control[2] & (1 << 2)) /* TXP */
  1420 + ch = value;
  1421 + else
  1422 + ch = ~value;
  1423 + if (s->chr && s->enable && (s->control[0] & (1 << 3))) /* TXE */
  1424 + qemu_chr_write(s->chr, &ch, 1);
  1425 + break;
  1426 + case ICSR0:
  1427 + s->status[0] &= ~(value & 0x66);
  1428 + pxa2xx_fir_update(s);
  1429 + break;
  1430 + case ICFOR:
  1431 + break;
  1432 + default:
  1433 + printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);
  1434 + }
  1435 +}
  1436 +
  1437 +static CPUReadMemoryFunc *pxa2xx_fir_readfn[] = {
  1438 + pxa2xx_fir_read,
  1439 + pxa2xx_fir_read,
  1440 + pxa2xx_fir_read,
  1441 +};
  1442 +
  1443 +static CPUWriteMemoryFunc *pxa2xx_fir_writefn[] = {
  1444 + pxa2xx_fir_write,
  1445 + pxa2xx_fir_write,
  1446 + pxa2xx_fir_write,
  1447 +};
  1448 +
  1449 +static int pxa2xx_fir_is_empty(void *opaque)
  1450 +{
  1451 + struct pxa2xx_fir_s *s = (struct pxa2xx_fir_s *) opaque;
  1452 + return (s->rx_len < 64);
  1453 +}
  1454 +
  1455 +static void pxa2xx_fir_rx(void *opaque, const uint8_t *buf, int size)
  1456 +{
  1457 + struct pxa2xx_fir_s *s = (struct pxa2xx_fir_s *) opaque;
  1458 + if (!(s->control[0] & (1 << 4))) /* RXE */
  1459 + return;
  1460 +
  1461 + while (size --) {
  1462 + s->status[1] |= 1 << 4; /* EOF */
  1463 + if (s->rx_len >= 64) {
  1464 + s->status[1] |= 1 << 6; /* ROR */
  1465 + break;
  1466 + }
  1467 +
  1468 + if (s->control[2] & (1 << 3)) /* RXP */
  1469 + s->rx_fifo[(s->rx_start + s->rx_len ++) & 63] = *(buf ++);
  1470 + else
  1471 + s->rx_fifo[(s->rx_start + s->rx_len ++) & 63] = ~*(buf ++);
  1472 + }
  1473 +
  1474 + pxa2xx_fir_update(s);
  1475 +}
  1476 +
  1477 +static void pxa2xx_fir_event(void *opaque, int event)
  1478 +{
  1479 +}
  1480 +
  1481 +static struct pxa2xx_fir_s *pxa2xx_fir_init(target_phys_addr_t base,
  1482 + qemu_irq irq, struct pxa2xx_dma_state_s *dma,
  1483 + CharDriverState *chr)
  1484 +{
  1485 + int iomemtype;
  1486 + struct pxa2xx_fir_s *s = (struct pxa2xx_fir_s *)
  1487 + qemu_mallocz(sizeof(struct pxa2xx_fir_s));
  1488 +
  1489 + s->base = base;
  1490 + s->irq = irq;
  1491 + s->dma = dma;
  1492 + s->chr = chr;
  1493 +
  1494 + pxa2xx_fir_reset(s);
  1495 +
  1496 + iomemtype = cpu_register_io_memory(0, pxa2xx_fir_readfn,
  1497 + pxa2xx_fir_writefn, s);
  1498 + cpu_register_physical_memory(s->base, 0xfff, iomemtype);
  1499 +
  1500 + if (chr)
  1501 + qemu_chr_add_handlers(chr, pxa2xx_fir_is_empty,
  1502 + pxa2xx_fir_rx, pxa2xx_fir_event, s);
  1503 +
  1504 + return s;
  1505 +}
  1506 +
  1507 +void pxa2xx_reset(int line, int level, void *opaque)
  1508 +{
  1509 + struct pxa2xx_state_s *s = (struct pxa2xx_state_s *) opaque;
  1510 + if (level && (s->pm_regs[PCFR >> 2] & 0x10)) { /* GPR_EN */
  1511 + cpu_reset(s->env);
  1512 + /* TODO: reset peripherals */
  1513 + }
  1514 +}
  1515 +
  1516 +/* Initialise a PXA270 integrated chip (ARM based core). */
  1517 +struct pxa2xx_state_s *pxa270_init(DisplayState *ds, const char *revision)
  1518 +{
  1519 + struct pxa2xx_state_s *s;
  1520 + struct pxa2xx_ssp_s *ssp;
  1521 + char *cpu_model;
  1522 + int iomemtype, i;
  1523 + s = (struct pxa2xx_state_s *) qemu_mallocz(sizeof(struct pxa2xx_state_s));
  1524 +
  1525 + s->env = cpu_init();
  1526 + asprintf(&cpu_model, "pxa270-%s", revision);
  1527 + cpu_arm_set_model(s->env, cpu_model);
  1528 + free(cpu_model);
  1529 +
  1530 + s->pic = pxa2xx_pic_init(0x40d00000, s->env);
  1531 +
  1532 + s->dma = pxa27x_dma_init(0x40000000, s->pic[PXA2XX_PIC_DMA]);
  1533 +
  1534 + s->gpio = pxa2xx_gpio_init(0x40e00000, s->env, s->pic, 121);
  1535 +
  1536 + for (i = 0; pxa270_serial[i].io_base; i ++)
  1537 + if (serial_hds[i])
  1538 + serial_mm_init(pxa270_serial[i].io_base, 2,
  1539 + s->pic[pxa270_serial[i].irqn], serial_hds[i], 1);
  1540 + else
  1541 + break;
  1542 + if (serial_hds[i])
  1543 + s->fir = pxa2xx_fir_init(0x40800000, s->pic[PXA2XX_PIC_ICP],
  1544 + s->dma, serial_hds[i]);
  1545 +
  1546 + s->cm_base = 0x41300000;
  1547 + s->cm_regs[CCCR >> 4] = 0x02000210; /* 416.0 MHz */
  1548 + s->clkcfg = 0x00000009; /* Turbo mode active */
  1549 + iomemtype = cpu_register_io_memory(0, pxa2xx_cm_readfn,
  1550 + pxa2xx_cm_writefn, s);
  1551 + cpu_register_physical_memory(s->cm_base, 0xfff, iomemtype);
  1552 +
  1553 + cpu_arm_set_cp_io(s->env, 14, pxa2xx_cp14_read, pxa2xx_cp14_write, s);
  1554 +
  1555 + s->mm_base = 0x48000000;
  1556 + s->mm_regs[MDMRS >> 2] = 0x00020002;
  1557 + s->mm_regs[MDREFR >> 2] = 0x03ca4000;
  1558 + s->mm_regs[MECR >> 2] = 0x00000001; /* Two PC Card sockets */
  1559 + iomemtype = cpu_register_io_memory(0, pxa2xx_mm_readfn,
  1560 + pxa2xx_mm_writefn, s);
  1561 + cpu_register_physical_memory(s->mm_base, 0xfff, iomemtype);
  1562 +
  1563 + for (i = 0; pxa27x_ssp[i].io_base; i ++);
  1564 + s->ssp = (struct pxa2xx_ssp_s **)
  1565 + qemu_mallocz(sizeof(struct pxa2xx_ssp_s *) * i);
  1566 + ssp = (struct pxa2xx_ssp_s *)
  1567 + qemu_mallocz(sizeof(struct pxa2xx_ssp_s) * i);
  1568 + for (i = 0; pxa27x_ssp[i].io_base; i ++) {
  1569 + s->ssp[i] = &ssp[i];
  1570 + ssp[i].base = pxa27x_ssp[i].io_base;
  1571 + ssp[i].irq = s->pic[pxa27x_ssp[i].irqn];
  1572 +
  1573 + iomemtype = cpu_register_io_memory(0, pxa2xx_ssp_readfn,
  1574 + pxa2xx_ssp_writefn, &ssp[i]);
  1575 + cpu_register_physical_memory(ssp[i].base, 0xfff, iomemtype);
  1576 + }
  1577 +
  1578 + s->rtc_base = 0x40900000;
  1579 + iomemtype = cpu_register_io_memory(0, pxa2xx_rtc_readfn,
  1580 + pxa2xx_rtc_writefn, s);
  1581 + cpu_register_physical_memory(s->rtc_base, 0xfff, iomemtype);
  1582 + pxa2xx_rtc_reset(s);
  1583 +
  1584 + s->pm_base = 0x40f00000;
  1585 + iomemtype = cpu_register_io_memory(0, pxa2xx_pm_readfn,
  1586 + pxa2xx_pm_writefn, s);
  1587 + cpu_register_physical_memory(s->pm_base, 0xfff, iomemtype);
  1588 +
  1589 + s->i2s = pxa2xx_i2s_init(0x40400000, s->pic[PXA2XX_PIC_I2S], s->dma);
  1590 +
  1591 + /* GPIO1 resets the processor */
  1592 + /* The handler can be overriden by board-specific code */
  1593 + pxa2xx_gpio_handler_set(s->gpio, 1, pxa2xx_reset, s);
  1594 + return s;
  1595 +}
  1596 +
  1597 +/* Initialise a PXA255 integrated chip (ARM based core). */
  1598 +struct pxa2xx_state_s *pxa255_init(DisplayState *ds)
  1599 +{
  1600 + struct pxa2xx_state_s *s;
  1601 + struct pxa2xx_ssp_s *ssp;
  1602 + int iomemtype, i;
  1603 + s = (struct pxa2xx_state_s *) qemu_mallocz(sizeof(struct pxa2xx_state_s));
  1604 +
  1605 + s->env = cpu_init();
  1606 + cpu_arm_set_model(s->env, "pxa255");
  1607 +
  1608 + s->pic = pxa2xx_pic_init(0x40d00000, s->env);
  1609 +
  1610 + s->dma = pxa255_dma_init(0x40000000, s->pic[PXA2XX_PIC_DMA]);
  1611 +
  1612 + s->gpio = pxa2xx_gpio_init(0x40e00000, s->env, s->pic, 121);
  1613 +
  1614 + for (i = 0; pxa255_serial[i].io_base; i ++)
  1615 + if (serial_hds[i])
  1616 + serial_mm_init(pxa255_serial[i].io_base, 2,
  1617 + s->pic[pxa255_serial[i].irqn], serial_hds[i], 1);
  1618 + else
  1619 + break;
  1620 + if (serial_hds[i])
  1621 + s->fir = pxa2xx_fir_init(0x40800000, s->pic[PXA2XX_PIC_ICP],
  1622 + s->dma, serial_hds[i]);
  1623 +
  1624 + s->cm_base = 0x41300000;
  1625 + s->cm_regs[CCCR >> 4] = 0x02000210; /* 416.0 MHz */
  1626 + s->clkcfg = 0x00000009; /* Turbo mode active */
  1627 + iomemtype = cpu_register_io_memory(0, pxa2xx_cm_readfn,
  1628 + pxa2xx_cm_writefn, s);
  1629 + cpu_register_physical_memory(s->cm_base, 0xfff, iomemtype);
  1630 +
  1631 + cpu_arm_set_cp_io(s->env, 14, pxa2xx_cp14_read, pxa2xx_cp14_write, s);
  1632 +
  1633 + s->mm_base = 0x48000000;
  1634 + s->mm_regs[MDMRS >> 2] = 0x00020002;
  1635 + s->mm_regs[MDREFR >> 2] = 0x03ca4000;
  1636 + s->mm_regs[MECR >> 2] = 0x00000001; /* Two PC Card sockets */
  1637 + iomemtype = cpu_register_io_memory(0, pxa2xx_mm_readfn,
  1638 + pxa2xx_mm_writefn, s);
  1639 + cpu_register_physical_memory(s->mm_base, 0xfff, iomemtype);
  1640 +
  1641 + for (i = 0; pxa255_ssp[i].io_base; i ++);
  1642 + s->ssp = (struct pxa2xx_ssp_s **)
  1643 + qemu_mallocz(sizeof(struct pxa2xx_ssp_s *) * i);
  1644 + ssp = (struct pxa2xx_ssp_s *)
  1645 + qemu_mallocz(sizeof(struct pxa2xx_ssp_s) * i);
  1646 + for (i = 0; pxa255_ssp[i].io_base; i ++) {
  1647 + s->ssp[i] = &ssp[i];
  1648 + ssp[i].base = pxa255_ssp[i].io_base;
  1649 + ssp[i].irq = s->pic[pxa255_ssp[i].irqn];
  1650 +
  1651 + iomemtype = cpu_register_io_memory(0, pxa2xx_ssp_readfn,
  1652 + pxa2xx_ssp_writefn, &ssp[i]);
  1653 + cpu_register_physical_memory(ssp[i].base, 0xfff, iomemtype);
  1654 + }
  1655 +
  1656 + s->rtc_base = 0x40900000;
  1657 + iomemtype = cpu_register_io_memory(0, pxa2xx_rtc_readfn,
  1658 + pxa2xx_rtc_writefn, s);
  1659 + cpu_register_physical_memory(s->rtc_base, 0xfff, iomemtype);
  1660 + pxa2xx_rtc_reset(s);
  1661 +
  1662 + s->pm_base = 0x40f00000;
  1663 + iomemtype = cpu_register_io_memory(0, pxa2xx_pm_readfn,
  1664 + pxa2xx_pm_writefn, s);
  1665 + cpu_register_physical_memory(s->pm_base, 0xfff, iomemtype);
  1666 +
  1667 + s->i2s = pxa2xx_i2s_init(0x40400000, s->pic[PXA2XX_PIC_I2S], s->dma);
  1668 +
  1669 + /* GPIO1 resets the processor */
  1670 + /* The handler can be overriden by board-specific code */
  1671 + pxa2xx_gpio_handler_set(s->gpio, 1, pxa2xx_reset, s);
  1672 + return s;
  1673 +}
... ...
hw/pxa2xx_dma.c 0 → 100644
  1 +/*
  2 + * Intel XScale PXA255/270 DMA controller.
  3 + *
  4 + * Copyright (c) 2006 Openedhand Ltd.
  5 + * Copyright (c) 2006 Thorsten Zitterell
  6 + * Written by Andrzej Zaborowski <balrog@zabor.org>
  7 + *
  8 + * This code is licenced under the GPL.
  9 + */
  10 +
  11 +#include "vl.h"
  12 +
  13 +struct pxa2xx_dma_channel_s {
  14 + target_phys_addr_t descr;
  15 + target_phys_addr_t src;
  16 + target_phys_addr_t dest;
  17 + uint32_t cmd;
  18 + uint32_t state;
  19 + int request;
  20 +};
  21 +
  22 +/* Allow the DMA to be used as a PIC. */
  23 +typedef void (*pxa2xx_dma_handler_t)(void *opaque, int irq, int level);
  24 +
  25 +struct pxa2xx_dma_state_s {
  26 + pxa2xx_dma_handler_t handler;
  27 + target_phys_addr_t base;
  28 + qemu_irq irq;
  29 +
  30 + uint32_t stopintr;
  31 + uint32_t eorintr;
  32 + uint32_t rasintr;
  33 + uint32_t startintr;
  34 + uint32_t endintr;
  35 +
  36 + uint32_t align;
  37 + uint32_t pio;
  38 +
  39 + int channels;
  40 + struct pxa2xx_dma_channel_s *chan;
  41 +
  42 + uint8_t *req;
  43 +
  44 + /* Flag to avoid recursive DMA invocations. */
  45 + int running;
  46 +};
  47 +
  48 +#define PXA255_DMA_NUM_CHANNELS 16
  49 +#define PXA27X_DMA_NUM_CHANNELS 32
  50 +
  51 +#define PXA2XX_DMA_NUM_REQUESTS 75
  52 +
  53 +#define DCSR0 0x0000 /* DMA Control / Status register for Channel 0 */
  54 +#define DCSR31 0x007c /* DMA Control / Status register for Channel 31 */
  55 +#define DALGN 0x00a0 /* DMA Alignment register */
  56 +#define DPCSR 0x00a4 /* DMA Programmed I/O Control Status register */
  57 +#define DRQSR0 0x00e0 /* DMA DREQ<0> Status register */
  58 +#define DRQSR1 0x00e4 /* DMA DREQ<1> Status register */
  59 +#define DRQSR2 0x00e8 /* DMA DREQ<2> Status register */
  60 +#define DINT 0x00f0 /* DMA Interrupt register */
  61 +#define DRCMR0 0x0100 /* Request to Channel Map register 0 */
  62 +#define DRCMR63 0x01fc /* Request to Channel Map register 63 */
  63 +#define D_CH0 0x0200 /* Channel 0 Descriptor start */
  64 +#define DRCMR64 0x1100 /* Request to Channel Map register 64 */
  65 +#define DRCMR74 0x1128 /* Request to Channel Map register 74 */
  66 +
  67 +/* Per-channel register */
  68 +#define DDADR 0x00
  69 +#define DSADR 0x01
  70 +#define DTADR 0x02
  71 +#define DCMD 0x03
  72 +
  73 +/* Bit-field masks */
  74 +#define DRCMR_CHLNUM 0x1f
  75 +#define DRCMR_MAPVLD (1 << 7)
  76 +#define DDADR_STOP (1 << 0)
  77 +#define DDADR_BREN (1 << 1)
  78 +#define DCMD_LEN 0x1fff
  79 +#define DCMD_WIDTH(x) (1 << ((((x) >> 14) & 3) - 1))
  80 +#define DCMD_SIZE(x) (4 << (((x) >> 16) & 3))
  81 +#define DCMD_FLYBYT (1 << 19)
  82 +#define DCMD_FLYBYS (1 << 20)
  83 +#define DCMD_ENDIRQEN (1 << 21)
  84 +#define DCMD_STARTIRQEN (1 << 22)
  85 +#define DCMD_CMPEN (1 << 25)
  86 +#define DCMD_FLOWTRG (1 << 28)
  87 +#define DCMD_FLOWSRC (1 << 29)
  88 +#define DCMD_INCTRGADDR (1 << 30)
  89 +#define DCMD_INCSRCADDR (1 << 31)
  90 +#define DCSR_BUSERRINTR (1 << 0)
  91 +#define DCSR_STARTINTR (1 << 1)
  92 +#define DCSR_ENDINTR (1 << 2)
  93 +#define DCSR_STOPINTR (1 << 3)
  94 +#define DCSR_RASINTR (1 << 4)
  95 +#define DCSR_REQPEND (1 << 8)
  96 +#define DCSR_EORINT (1 << 9)
  97 +#define DCSR_CMPST (1 << 10)
  98 +#define DCSR_MASKRUN (1 << 22)
  99 +#define DCSR_RASIRQEN (1 << 23)
  100 +#define DCSR_CLRCMPST (1 << 24)
  101 +#define DCSR_SETCMPST (1 << 25)
  102 +#define DCSR_EORSTOPEN (1 << 26)
  103 +#define DCSR_EORJMPEN (1 << 27)
  104 +#define DCSR_EORIRQEN (1 << 28)
  105 +#define DCSR_STOPIRQEN (1 << 29)
  106 +#define DCSR_NODESCFETCH (1 << 30)
  107 +#define DCSR_RUN (1 << 31)
  108 +
  109 +static inline void pxa2xx_dma_update(struct pxa2xx_dma_state_s *s, int ch)
  110 +{
  111 + if (ch >= 0) {
  112 + if ((s->chan[ch].state & DCSR_STOPIRQEN) &&
  113 + (s->chan[ch].state & DCSR_STOPINTR))
  114 + s->stopintr |= 1 << ch;
  115 + else
  116 + s->stopintr &= ~(1 << ch);
  117 +
  118 + if ((s->chan[ch].state & DCSR_EORIRQEN) &&
  119 + (s->chan[ch].state & DCSR_EORINT))
  120 + s->eorintr |= 1 << ch;
  121 + else
  122 + s->eorintr &= ~(1 << ch);
  123 +
  124 + if ((s->chan[ch].state & DCSR_RASIRQEN) &&
  125 + (s->chan[ch].state & DCSR_RASINTR))
  126 + s->rasintr |= 1 << ch;
  127 + else
  128 + s->rasintr &= ~(1 << ch);
  129 +
  130 + if (s->chan[ch].state & DCSR_STARTINTR)
  131 + s->startintr |= 1 << ch;
  132 + else
  133 + s->startintr &= ~(1 << ch);
  134 +
  135 + if (s->chan[ch].state & DCSR_ENDINTR)
  136 + s->endintr |= 1 << ch;
  137 + else
  138 + s->endintr &= ~(1 << ch);
  139 + }
  140 +
  141 + if (s->stopintr | s->eorintr | s->rasintr | s->startintr | s->endintr)
  142 + qemu_irq_raise(s->irq);
  143 + else
  144 + qemu_irq_lower(s->irq);
  145 +}
  146 +
  147 +static inline void pxa2xx_dma_descriptor_fetch(
  148 + struct pxa2xx_dma_state_s *s, int ch)
  149 +{
  150 + uint32_t desc[4];
  151 + target_phys_addr_t daddr = s->chan[ch].descr & ~0xf;
  152 + if ((s->chan[ch].descr & DDADR_BREN) && (s->chan[ch].state & DCSR_CMPST))
  153 + daddr += 32;
  154 +
  155 + cpu_physical_memory_read(daddr, (uint8_t *) desc, 16);
  156 + s->chan[ch].descr = desc[DDADR];
  157 + s->chan[ch].src = desc[DSADR];
  158 + s->chan[ch].dest = desc[DTADR];
  159 + s->chan[ch].cmd = desc[DCMD];
  160 +
  161 + if (s->chan[ch].cmd & DCMD_FLOWSRC)
  162 + s->chan[ch].src &= ~3;
  163 + if (s->chan[ch].cmd & DCMD_FLOWTRG)
  164 + s->chan[ch].dest &= ~3;
  165 +
  166 + if (s->chan[ch].cmd & (DCMD_CMPEN | DCMD_FLYBYS | DCMD_FLYBYT))
  167 + printf("%s: unsupported mode in channel %i\n", __FUNCTION__, ch);
  168 +
  169 + if (s->chan[ch].cmd & DCMD_STARTIRQEN)
  170 + s->chan[ch].state |= DCSR_STARTINTR;
  171 +}
  172 +
  173 +static void pxa2xx_dma_run(struct pxa2xx_dma_state_s *s)
  174 +{
  175 + int c, srcinc, destinc;
  176 + uint32_t n, size;
  177 + uint32_t width;
  178 + uint32_t length;
  179 + char buffer[32];
  180 + struct pxa2xx_dma_channel_s *ch;
  181 +
  182 + if (s->running ++)
  183 + return;
  184 +
  185 + while (s->running) {
  186 + s->running = 1;
  187 + for (c = 0; c < s->channels; c ++) {
  188 + ch = &s->chan[c];
  189 +
  190 + while ((ch->state & DCSR_RUN) && !(ch->state & DCSR_STOPINTR)) {
  191 + /* Test for pending requests */
  192 + if ((ch->cmd & (DCMD_FLOWSRC | DCMD_FLOWTRG)) && !ch->request)
  193 + break;
  194 +
  195 + length = ch->cmd & DCMD_LEN;
  196 + size = DCMD_SIZE(ch->cmd);
  197 + width = DCMD_WIDTH(ch->cmd);
  198 +
  199 + srcinc = (ch->cmd & DCMD_INCSRCADDR) ? width : 0;
  200 + destinc = (ch->cmd & DCMD_INCTRGADDR) ? width : 0;
  201 +
  202 + while (length) {
  203 + size = MIN(length, size);
  204 +
  205 + for (n = 0; n < size; n += width) {
  206 + cpu_physical_memory_read(ch->src, buffer + n, width);
  207 + ch->src += srcinc;
  208 + }
  209 +
  210 + for (n = 0; n < size; n += width) {
  211 + cpu_physical_memory_write(ch->dest, buffer + n, width);
  212 + ch->dest += destinc;
  213 + }
  214 +
  215 + length -= size;
  216 +
  217 + if ((ch->cmd & (DCMD_FLOWSRC | DCMD_FLOWTRG)) &&
  218 + !ch->request) {
  219 + ch->state |= DCSR_EORINT;
  220 + if (ch->state & DCSR_EORSTOPEN)
  221 + ch->state |= DCSR_STOPINTR;
  222 + if ((ch->state & DCSR_EORJMPEN) &&
  223 + !(ch->state & DCSR_NODESCFETCH))
  224 + pxa2xx_dma_descriptor_fetch(s, c);
  225 + break;
  226 + }
  227 + }
  228 +
  229 + ch->cmd = (ch->cmd & ~DCMD_LEN) | length;
  230 +
  231 + /* Is the transfer complete now? */
  232 + if (!length) {
  233 + if (ch->cmd & DCMD_ENDIRQEN)
  234 + ch->state |= DCSR_ENDINTR;
  235 +
  236 + if ((ch->state & DCSR_NODESCFETCH) ||
  237 + (ch->descr & DDADR_STOP) ||
  238 + (ch->state & DCSR_EORSTOPEN)) {
  239 + ch->state |= DCSR_STOPINTR;
  240 + ch->state &= ~DCSR_RUN;
  241 +
  242 + break;
  243 + }
  244 +
  245 + ch->state |= DCSR_STOPINTR;
  246 + break;
  247 + }
  248 + }
  249 + }
  250 +
  251 + s->running --;
  252 + }
  253 +}
  254 +
  255 +static uint32_t pxa2xx_dma_read(void *opaque, target_phys_addr_t offset)
  256 +{
  257 + struct pxa2xx_dma_state_s *s = (struct pxa2xx_dma_state_s *) opaque;
  258 + unsigned int channel;
  259 + offset -= s->base;
  260 +
  261 + switch (offset) {
  262 + case DRCMR64 ... DRCMR74:
  263 + offset -= DRCMR64 - DRCMR0 - (64 << 2);
  264 + /* Fall through */
  265 + case DRCMR0 ... DRCMR63:
  266 + channel = (offset - DRCMR0) >> 2;
  267 + return s->req[channel];
  268 +
  269 + case DRQSR0:
  270 + case DRQSR1:
  271 + case DRQSR2:
  272 + return 0;
  273 +
  274 + case DCSR0 ... DCSR31:
  275 + channel = offset >> 2;
  276 + if (s->chan[channel].request)
  277 + return s->chan[channel].state | DCSR_REQPEND;
  278 + return s->chan[channel].state;
  279 +
  280 + case DINT:
  281 + return s->stopintr | s->eorintr | s->rasintr |
  282 + s->startintr | s->endintr;
  283 +
  284 + case DALGN:
  285 + return s->align;
  286 +
  287 + case DPCSR:
  288 + return s->pio;
  289 + }
  290 +
  291 + if (offset >= D_CH0 && offset < D_CH0 + (s->channels << 4)) {
  292 + channel = (offset - D_CH0) >> 4;
  293 + switch ((offset & 0x0f) >> 2) {
  294 + case DDADR:
  295 + return s->chan[channel].descr;
  296 + case DSADR:
  297 + return s->chan[channel].src;
  298 + case DTADR:
  299 + return s->chan[channel].dest;
  300 + case DCMD:
  301 + return s->chan[channel].cmd;
  302 + }
  303 + }
  304 +
  305 + cpu_abort(cpu_single_env,
  306 + "%s: Bad offset 0x%04lx\n", __FUNCTION__, offset);
  307 + return 7;
  308 +}
  309 +
  310 +static void pxa2xx_dma_write(void *opaque,
  311 + target_phys_addr_t offset, uint32_t value)
  312 +{
  313 + struct pxa2xx_dma_state_s *s = (struct pxa2xx_dma_state_s *) opaque;
  314 + unsigned int channel;
  315 + offset -= s->base;
  316 +
  317 + switch (offset) {
  318 + case DRCMR64 ... DRCMR74:
  319 + offset -= DRCMR64 - DRCMR0 - (64 << 2);
  320 + /* Fall through */
  321 + case DRCMR0 ... DRCMR63:
  322 + channel = (offset - DRCMR0) >> 2;
  323 +
  324 + if (value & DRCMR_MAPVLD)
  325 + if ((value & DRCMR_CHLNUM) > s->channels)
  326 + cpu_abort(cpu_single_env, "%s: Bad DMA channel %i\n",
  327 + __FUNCTION__, value & DRCMR_CHLNUM);
  328 +
  329 + s->req[channel] = value;
  330 + break;
  331 +
  332 + case DRQSR0:
  333 + case DRQSR1:
  334 + case DRQSR2:
  335 + /* Nothing to do */
  336 + break;
  337 +
  338 + case DCSR0 ... DCSR31:
  339 + channel = offset >> 2;
  340 + s->chan[channel].state &= 0x0000071f & ~(value &
  341 + (DCSR_EORINT | DCSR_ENDINTR |
  342 + DCSR_STARTINTR | DCSR_BUSERRINTR));
  343 + s->chan[channel].state |= value & 0xfc800000;
  344 +
  345 + if (s->chan[channel].state & DCSR_STOPIRQEN)
  346 + s->chan[channel].state &= ~DCSR_STOPINTR;
  347 +
  348 + if (value & DCSR_NODESCFETCH) {
  349 + /* No-descriptor-fetch mode */
  350 + if (value & DCSR_RUN)
  351 + pxa2xx_dma_run(s);
  352 + } else {
  353 + /* Descriptor-fetch mode */
  354 + if (value & DCSR_RUN) {
  355 + s->chan[channel].state &= ~DCSR_STOPINTR;
  356 + pxa2xx_dma_descriptor_fetch(s, channel);
  357 + pxa2xx_dma_run(s);
  358 + }
  359 + }
  360 +
  361 + /* Shouldn't matter as our DMA is synchronous. */
  362 + if (!(value & (DCSR_RUN | DCSR_MASKRUN)))
  363 + s->chan[channel].state |= DCSR_STOPINTR;
  364 +
  365 + if (value & DCSR_CLRCMPST)
  366 + s->chan[channel].state &= ~DCSR_CMPST;
  367 + if (value & DCSR_SETCMPST)
  368 + s->chan[channel].state |= DCSR_CMPST;
  369 +
  370 + pxa2xx_dma_update(s, channel);
  371 + break;
  372 +
  373 + case DALGN:
  374 + s->align = value;
  375 + break;
  376 +
  377 + case DPCSR:
  378 + s->pio = value & 0x80000001;
  379 + break;
  380 +
  381 + default:
  382 + if (offset >= D_CH0 && offset < D_CH0 + (s->channels << 4)) {
  383 + channel = (offset - D_CH0) >> 4;
  384 + switch ((offset & 0x0f) >> 2) {
  385 + case DDADR:
  386 + s->chan[channel].descr = value;
  387 + break;
  388 + case DSADR:
  389 + s->chan[channel].src = value;
  390 + break;
  391 + case DTADR:
  392 + s->chan[channel].dest = value;
  393 + break;
  394 + case DCMD:
  395 + s->chan[channel].cmd = value;
  396 + break;
  397 + default:
  398 + goto fail;
  399 + }
  400 +
  401 + break;
  402 + }
  403 + fail:
  404 + cpu_abort(cpu_single_env, "%s: Bad offset 0x%04lx\n",
  405 + __FUNCTION__, offset);
  406 + }
  407 +}
  408 +
  409 +static uint32_t pxa2xx_dma_readbad(void *opaque, target_phys_addr_t offset)
  410 +{
  411 + cpu_abort(cpu_single_env, "%s: Bad access width\n", __FUNCTION__);
  412 + return 5;
  413 +}
  414 +
  415 +static void pxa2xx_dma_writebad(void *opaque,
  416 + target_phys_addr_t offset, uint32_t value)
  417 +{
  418 + cpu_abort(cpu_single_env, "%s: Bad access width\n", __FUNCTION__);
  419 +}
  420 +
  421 +static CPUReadMemoryFunc *pxa2xx_dma_readfn[] = {
  422 + pxa2xx_dma_readbad,
  423 + pxa2xx_dma_readbad,
  424 + pxa2xx_dma_read
  425 +};
  426 +
  427 +static CPUWriteMemoryFunc *pxa2xx_dma_writefn[] = {
  428 + pxa2xx_dma_writebad,
  429 + pxa2xx_dma_writebad,
  430 + pxa2xx_dma_write
  431 +};
  432 +
  433 +static struct pxa2xx_dma_state_s *pxa2xx_dma_init(target_phys_addr_t base,
  434 + qemu_irq irq, int channels)
  435 +{
  436 + int i, iomemtype;
  437 + struct pxa2xx_dma_state_s *s;
  438 + s = (struct pxa2xx_dma_state_s *)
  439 + qemu_mallocz(sizeof(struct pxa2xx_dma_state_s));
  440 +
  441 + s->channels = channels;
  442 + s->chan = qemu_mallocz(sizeof(struct pxa2xx_dma_channel_s) * s->channels);
  443 + s->base = base;
  444 + s->irq = irq;
  445 + s->handler = (pxa2xx_dma_handler_t) pxa2xx_dma_request;
  446 + s->req = qemu_mallocz(sizeof(int) * PXA2XX_DMA_NUM_REQUESTS);
  447 +
  448 + memset(s->chan, 0, sizeof(struct pxa2xx_dma_channel_s) * s->channels);
  449 + for (i = 0; i < s->channels; i ++)
  450 + s->chan[i].state = DCSR_STOPINTR;
  451 +
  452 + memset(s->req, 0, sizeof(int) * PXA2XX_DMA_NUM_REQUESTS);
  453 +
  454 + iomemtype = cpu_register_io_memory(0, pxa2xx_dma_readfn,
  455 + pxa2xx_dma_writefn, s);
  456 + cpu_register_physical_memory(base, 0x0000ffff, iomemtype);
  457 +
  458 + return s;
  459 +}
  460 +
  461 +struct pxa2xx_dma_state_s *pxa27x_dma_init(target_phys_addr_t base,
  462 + qemu_irq irq)
  463 +{
  464 + return pxa2xx_dma_init(base, irq, PXA27X_DMA_NUM_CHANNELS);
  465 +}
  466 +
  467 +struct pxa2xx_dma_state_s *pxa255_dma_init(target_phys_addr_t base,
  468 + qemu_irq irq)
  469 +{
  470 + return pxa2xx_dma_init(base, irq, PXA255_DMA_NUM_CHANNELS);
  471 +}
  472 +
  473 +void pxa2xx_dma_request(struct pxa2xx_dma_state_s *s, int req_num, int on)
  474 +{
  475 + int ch;
  476 + if (req_num < 0 || req_num >= PXA2XX_DMA_NUM_REQUESTS)
  477 + cpu_abort(cpu_single_env,
  478 + "%s: Bad DMA request %i\n", __FUNCTION__, req_num);
  479 +
  480 + if (!(s->req[req_num] & DRCMR_MAPVLD))
  481 + return;
  482 + ch = s->req[req_num] & DRCMR_CHLNUM;
  483 +
  484 + if (!s->chan[ch].request && on)
  485 + s->chan[ch].state |= DCSR_RASINTR;
  486 + else
  487 + s->chan[ch].state &= ~DCSR_RASINTR;
  488 + if (s->chan[ch].request && !on)
  489 + s->chan[ch].state |= DCSR_EORINT;
  490 +
  491 + s->chan[ch].request = on;
  492 + if (on) {
  493 + pxa2xx_dma_run(s);
  494 + pxa2xx_dma_update(s, ch);
  495 + }
  496 +}
... ...
hw/pxa2xx_gpio.c 0 → 100644
  1 +/*
  2 + * Intel XScale PXA255/270 GPIO controller emulation.
  3 + *
  4 + * Copyright (c) 2006 Openedhand Ltd.
  5 + * Written by Andrzej Zaborowski <balrog@zabor.org>
  6 + *
  7 + * This code is licensed under the GPL.
  8 + */
  9 +
  10 +#include "vl.h"
  11 +
  12 +#define PXA2XX_GPIO_BANKS 4
  13 +
  14 +struct pxa2xx_gpio_info_s {
  15 + target_phys_addr_t base;
  16 + qemu_irq *pic;
  17 + int lines;
  18 + CPUState *cpu_env;
  19 +
  20 + /* XXX: GNU C vectors are more suitable */
  21 + uint32_t ilevel[PXA2XX_GPIO_BANKS];
  22 + uint32_t olevel[PXA2XX_GPIO_BANKS];
  23 + uint32_t dir[PXA2XX_GPIO_BANKS];
  24 + uint32_t rising[PXA2XX_GPIO_BANKS];
  25 + uint32_t falling[PXA2XX_GPIO_BANKS];
  26 + uint32_t status[PXA2XX_GPIO_BANKS];
  27 + uint32_t gafr[PXA2XX_GPIO_BANKS * 2];
  28 +
  29 + uint32_t prev_level[PXA2XX_GPIO_BANKS];
  30 + struct {
  31 + gpio_handler_t fn;
  32 + void *opaque;
  33 + } handler[PXA2XX_GPIO_BANKS * 32];
  34 +
  35 + void (*read_notify)(void *opaque);
  36 + void *opaque;
  37 +};
  38 +
  39 +static struct {
  40 + enum {
  41 + GPIO_NONE,
  42 + GPLR,
  43 + GPSR,
  44 + GPCR,
  45 + GPDR,
  46 + GRER,
  47 + GFER,
  48 + GEDR,
  49 + GAFR_L,
  50 + GAFR_U,
  51 + } reg;
  52 + int bank;
  53 +} pxa2xx_gpio_regs[0x200] = {
  54 + [0 ... 0x1ff] = { GPIO_NONE, 0 },
  55 +#define PXA2XX_REG(reg, a0, a1, a2, a3) \
  56 + [a0] = { reg, 0 }, [a1] = { reg, 1 }, [a2] = { reg, 2 }, [a3] = { reg, 3 },
  57 +
  58 + PXA2XX_REG(GPLR, 0x000, 0x004, 0x008, 0x100)
  59 + PXA2XX_REG(GPSR, 0x018, 0x01c, 0x020, 0x118)
  60 + PXA2XX_REG(GPCR, 0x024, 0x028, 0x02c, 0x124)
  61 + PXA2XX_REG(GPDR, 0x00c, 0x010, 0x014, 0x10c)
  62 + PXA2XX_REG(GRER, 0x030, 0x034, 0x038, 0x130)
  63 + PXA2XX_REG(GFER, 0x03c, 0x040, 0x044, 0x13c)
  64 + PXA2XX_REG(GEDR, 0x048, 0x04c, 0x050, 0x148)
  65 + PXA2XX_REG(GAFR_L, 0x054, 0x05c, 0x064, 0x06c)
  66 + PXA2XX_REG(GAFR_U, 0x058, 0x060, 0x068, 0x070)
  67 +};
  68 +
  69 +static void pxa2xx_gpio_irq_update(struct pxa2xx_gpio_info_s *s)
  70 +{
  71 + if (s->status[0] & (1 << 0))
  72 + qemu_irq_raise(s->pic[PXA2XX_PIC_GPIO_0]);
  73 + else
  74 + qemu_irq_lower(s->pic[PXA2XX_PIC_GPIO_0]);
  75 +
  76 + if (s->status[0] & (1 << 1))
  77 + qemu_irq_raise(s->pic[PXA2XX_PIC_GPIO_1]);
  78 + else
  79 + qemu_irq_lower(s->pic[PXA2XX_PIC_GPIO_1]);
  80 +
  81 + if ((s->status[0] & ~3) | s->status[1] | s->status[2] | s->status[3])
  82 + qemu_irq_raise(s->pic[PXA2XX_PIC_GPIO_X]);
  83 + else
  84 + qemu_irq_lower(s->pic[PXA2XX_PIC_GPIO_X]);
  85 +}
  86 +
  87 +/* Bitmap of pins used as standby and sleep wake-up sources. */
  88 +const int pxa2xx_gpio_wake[PXA2XX_GPIO_BANKS] = {
  89 + 0x8003fe1b, 0x002001fc, 0xec080000, 0x0012007f,
  90 +};
  91 +
  92 +void pxa2xx_gpio_set(struct pxa2xx_gpio_info_s *s, int line, int level)
  93 +{
  94 + int bank;
  95 + uint32_t mask;
  96 +
  97 + if (line >= s->lines) {
  98 + printf("%s: No GPIO pin %i\n", __FUNCTION__, line);
  99 + return;
  100 + }
  101 +
  102 + bank = line >> 5;
  103 + mask = 1 << (line & 31);
  104 +
  105 + if (level) {
  106 + s->status[bank] |= s->rising[bank] & mask &
  107 + ~s->ilevel[bank] & ~s->dir[bank];
  108 + s->ilevel[bank] |= mask;
  109 + } else {
  110 + s->status[bank] |= s->falling[bank] & mask &
  111 + s->ilevel[bank] & ~s->dir[bank];
  112 + s->ilevel[bank] &= ~mask;
  113 + }
  114 +
  115 + if (s->status[bank] & mask)
  116 + pxa2xx_gpio_irq_update(s);
  117 +
  118 + /* Wake-up GPIOs */
  119 + if (s->cpu_env->halted && (mask & ~s->dir[bank] & pxa2xx_gpio_wake[bank]))
  120 + cpu_interrupt(s->cpu_env, CPU_INTERRUPT_EXITTB);
  121 +}
  122 +
  123 +static void pxa2xx_gpio_handler_update(struct pxa2xx_gpio_info_s *s) {
  124 + uint32_t level, diff;
  125 + int i, bit, line;
  126 + for (i = 0; i < PXA2XX_GPIO_BANKS; i ++) {
  127 + level = s->olevel[i] & s->dir[i];
  128 +
  129 + for (diff = s->prev_level[i] ^ level; diff; diff ^= 1 << bit) {
  130 + bit = ffs(diff) - 1;
  131 + line = bit + 32 * i;
  132 + if (s->handler[line].fn)
  133 + s->handler[line].fn(line, (level >> bit) & 1,
  134 + s->handler[line].opaque);
  135 + }
  136 +
  137 + s->prev_level[i] = level;
  138 + }
  139 +}
  140 +
  141 +static uint32_t pxa2xx_gpio_read(void *opaque, target_phys_addr_t offset)
  142 +{
  143 + struct pxa2xx_gpio_info_s *s = (struct pxa2xx_gpio_info_s *) opaque;
  144 + uint32_t ret;
  145 + int bank;
  146 + offset -= s->base;
  147 + if (offset >= 0x200)
  148 + return 0;
  149 +
  150 + bank = pxa2xx_gpio_regs[offset].bank;
  151 + switch (pxa2xx_gpio_regs[offset].reg) {
  152 + case GPDR: /* GPIO Pin-Direction registers */
  153 + return s->dir[bank];
  154 +
  155 + case GRER: /* GPIO Rising-Edge Detect Enable registers */
  156 + return s->rising[bank];
  157 +
  158 + case GFER: /* GPIO Falling-Edge Detect Enable registers */
  159 + return s->falling[bank];
  160 +
  161 + case GAFR_L: /* GPIO Alternate Function registers */
  162 + return s->gafr[bank * 2];
  163 +
  164 + case GAFR_U: /* GPIO Alternate Function registers */
  165 + return s->gafr[bank * 2 + 1];
  166 +
  167 + case GPLR: /* GPIO Pin-Level registers */
  168 + ret = (s->olevel[bank] & s->dir[bank]) |
  169 + (s->ilevel[bank] & ~s->dir[bank]);
  170 + if (s->read_notify)
  171 + s->read_notify(s->opaque);
  172 + return ret;
  173 +
  174 + case GEDR: /* GPIO Edge Detect Status registers */
  175 + return s->status[bank];
  176 +
  177 + default:
  178 + cpu_abort(cpu_single_env,
  179 + "%s: Bad offset " REG_FMT "\n", __FUNCTION__, offset);
  180 + }
  181 +
  182 + return 0;
  183 +}
  184 +
  185 +static void pxa2xx_gpio_write(void *opaque,
  186 + target_phys_addr_t offset, uint32_t value)
  187 +{
  188 + struct pxa2xx_gpio_info_s *s = (struct pxa2xx_gpio_info_s *) opaque;
  189 + int bank;
  190 + offset -= s->base;
  191 + if (offset >= 0x200)
  192 + return;
  193 +
  194 + bank = pxa2xx_gpio_regs[offset].bank;
  195 + switch (pxa2xx_gpio_regs[offset].reg) {
  196 + case GPDR: /* GPIO Pin-Direction registers */
  197 + s->dir[bank] = value;
  198 + pxa2xx_gpio_handler_update(s);
  199 + break;
  200 +
  201 + case GPSR: /* GPIO Pin-Output Set registers */
  202 + s->olevel[bank] |= value;
  203 + pxa2xx_gpio_handler_update(s);
  204 + break;
  205 +
  206 + case GPCR: /* GPIO Pin-Output Clear registers */
  207 + s->olevel[bank] &= ~value;
  208 + pxa2xx_gpio_handler_update(s);
  209 + break;
  210 +
  211 + case GRER: /* GPIO Rising-Edge Detect Enable registers */
  212 + s->rising[bank] = value;
  213 + break;
  214 +
  215 + case GFER: /* GPIO Falling-Edge Detect Enable registers */
  216 + s->falling[bank] = value;
  217 + break;
  218 +
  219 + case GAFR_L: /* GPIO Alternate Function registers */
  220 + s->gafr[bank * 2] = value;
  221 + break;
  222 +
  223 + case GAFR_U: /* GPIO Alternate Function registers */
  224 + s->gafr[bank * 2 + 1] = value;
  225 + break;
  226 +
  227 + case GEDR: /* GPIO Edge Detect Status registers */
  228 + s->status[bank] &= ~value;
  229 + pxa2xx_gpio_irq_update(s);
  230 + break;
  231 +
  232 + default:
  233 + cpu_abort(cpu_single_env,
  234 + "%s: Bad offset " REG_FMT "\n", __FUNCTION__, offset);
  235 + }
  236 +}
  237 +
  238 +static CPUReadMemoryFunc *pxa2xx_gpio_readfn[] = {
  239 + pxa2xx_gpio_read,
  240 + pxa2xx_gpio_read,
  241 + pxa2xx_gpio_read
  242 +};
  243 +
  244 +static CPUWriteMemoryFunc *pxa2xx_gpio_writefn[] = {
  245 + pxa2xx_gpio_write,
  246 + pxa2xx_gpio_write,
  247 + pxa2xx_gpio_write
  248 +};
  249 +
  250 +struct pxa2xx_gpio_info_s *pxa2xx_gpio_init(target_phys_addr_t base,
  251 + CPUState *env, qemu_irq *pic, int lines)
  252 +{
  253 + int iomemtype;
  254 + struct pxa2xx_gpio_info_s *s;
  255 +
  256 + s = (struct pxa2xx_gpio_info_s *)
  257 + qemu_mallocz(sizeof(struct pxa2xx_gpio_info_s));
  258 + memset(s, 0, sizeof(struct pxa2xx_gpio_info_s));
  259 + s->base = base;
  260 + s->pic = pic;
  261 + s->lines = lines;
  262 + s->cpu_env = env;
  263 +
  264 + iomemtype = cpu_register_io_memory(0, pxa2xx_gpio_readfn,
  265 + pxa2xx_gpio_writefn, s);
  266 + cpu_register_physical_memory(base, 0x00000fff, iomemtype);
  267 +
  268 + return s;
  269 +}
  270 +
  271 +void pxa2xx_gpio_handler_set(struct pxa2xx_gpio_info_s *s, int line,
  272 + gpio_handler_t handler, void *opaque) {
  273 + if (line >= s->lines) {
  274 + printf("%s: No GPIO pin %i\n", __FUNCTION__, line);
  275 + return;
  276 + }
  277 +
  278 + s->handler[line].fn = handler;
  279 + s->handler[line].opaque = opaque;
  280 +}
  281 +
  282 +/*
  283 + * Registers a callback to notify on GPLR reads. This normally
  284 + * shouldn't be needed but it is used for the hack on Spitz machines.
  285 + */
  286 +void pxa2xx_gpio_read_notifier(struct pxa2xx_gpio_info_s *s,
  287 + void (*handler)(void *opaque), void *opaque) {
  288 + s->read_notify = handler;
  289 + s->opaque = opaque;
  290 +}
... ...
hw/pxa2xx_pic.c 0 → 100644
  1 +/*
  2 + * Intel XScale PXA Programmable Interrupt Controller.
  3 + *
  4 + * Copyright (c) 2006 Openedhand Ltd.
  5 + * Copyright (c) 2006 Thorsten Zitterell
  6 + * Written by Andrzej Zaborowski <balrog@zabor.org>
  7 + *
  8 + * This code is licenced under the GPL.
  9 + */
  10 +
  11 +#include "vl.h"
  12 +
  13 +#define ICIP 0x00 /* Interrupt Controller IRQ Pending register */
  14 +#define ICMR 0x04 /* Interrupt Controller Mask register */
  15 +#define ICLR 0x08 /* Interrupt Controller Level register */
  16 +#define ICFP 0x0c /* Interrupt Controller FIQ Pending register */
  17 +#define ICPR 0x10 /* Interrupt Controller Pending register */
  18 +#define ICCR 0x14 /* Interrupt Controller Control register */
  19 +#define ICHP 0x18 /* Interrupt Controller Highest Priority register */
  20 +#define IPR0 0x1c /* Interrupt Controller Priority register 0 */
  21 +#define IPR31 0x98 /* Interrupt Controller Priority register 31 */
  22 +#define ICIP2 0x9c /* Interrupt Controller IRQ Pending register 2 */
  23 +#define ICMR2 0xa0 /* Interrupt Controller Mask register 2 */
  24 +#define ICLR2 0xa4 /* Interrupt Controller Level register 2 */
  25 +#define ICFP2 0xa8 /* Interrupt Controller FIQ Pending register 2 */
  26 +#define ICPR2 0xac /* Interrupt Controller Pending register 2 */
  27 +#define IPR32 0xb0 /* Interrupt Controller Priority register 32 */
  28 +#define IPR39 0xcc /* Interrupt Controller Priority register 39 */
  29 +
  30 +#define PXA2XX_PIC_SRCS 40
  31 +
  32 +struct pxa2xx_pic_state_s {
  33 + target_phys_addr_t base;
  34 + CPUState *cpu_env;
  35 + uint32_t int_enabled[2];
  36 + uint32_t int_pending[2];
  37 + uint32_t is_fiq[2];
  38 + uint32_t int_idle;
  39 + uint32_t priority[PXA2XX_PIC_SRCS];
  40 +};
  41 +
  42 +static void pxa2xx_pic_update(void *opaque)
  43 +{
  44 + uint32_t mask[2];
  45 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  46 +
  47 + if (s->cpu_env->halted) {
  48 + mask[0] = s->int_pending[0] & (s->int_enabled[0] | s->int_idle);
  49 + mask[1] = s->int_pending[1] & (s->int_enabled[1] | s->int_idle);
  50 + if (mask[0] || mask[1])
  51 + cpu_interrupt(s->cpu_env, CPU_INTERRUPT_EXITTB);
  52 + }
  53 +
  54 + mask[0] = s->int_pending[0] & s->int_enabled[0];
  55 + mask[1] = s->int_pending[1] & s->int_enabled[1];
  56 +
  57 + if ((mask[0] & s->is_fiq[0]) || (mask[1] & s->is_fiq[1]))
  58 + cpu_interrupt(s->cpu_env, CPU_INTERRUPT_FIQ);
  59 + else
  60 + cpu_reset_interrupt(s->cpu_env, CPU_INTERRUPT_FIQ);
  61 +
  62 + if ((mask[0] & ~s->is_fiq[0]) || (mask[1] & ~s->is_fiq[1]))
  63 + cpu_interrupt(s->cpu_env, CPU_INTERRUPT_HARD);
  64 + else
  65 + cpu_reset_interrupt(s->cpu_env, CPU_INTERRUPT_HARD);
  66 +}
  67 +
  68 +/* Note: Here level means state of the signal on a pin, not
  69 + * IRQ/FIQ distinction as in PXA Developer Manual. */
  70 +static void pxa2xx_pic_set_irq(void *opaque, int irq, int level)
  71 +{
  72 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  73 + int int_set = (irq >= 32);
  74 + irq &= 31;
  75 +
  76 + if (level)
  77 + s->int_pending[int_set] |= 1 << irq;
  78 + else
  79 + s->int_pending[int_set] &= ~(1 << irq);
  80 +
  81 + pxa2xx_pic_update(opaque);
  82 +}
  83 +
  84 +static inline uint32_t pxa2xx_pic_highest(struct pxa2xx_pic_state_s *s) {
  85 + int i, int_set, irq;
  86 + uint32_t bit, mask[2];
  87 + uint32_t ichp = 0x003f003f; /* Both IDs invalid */
  88 +
  89 + mask[0] = s->int_pending[0] & s->int_enabled[0];
  90 + mask[1] = s->int_pending[1] & s->int_enabled[1];
  91 +
  92 + for (i = PXA2XX_PIC_SRCS - 1; i >= 0; i --) {
  93 + irq = s->priority[i] & 0x3f;
  94 + if ((s->priority[i] & (1 << 31)) && irq < PXA2XX_PIC_SRCS) {
  95 + /* Source peripheral ID is valid. */
  96 + bit = 1 << (irq & 31);
  97 + int_set = (irq >= 32);
  98 +
  99 + if (mask[int_set] & bit & s->is_fiq[int_set]) {
  100 + /* FIQ asserted */
  101 + ichp &= 0xffff0000;
  102 + ichp |= (1 << 15) | irq;
  103 + }
  104 +
  105 + if (mask[int_set] & bit & ~s->is_fiq[int_set]) {
  106 + /* IRQ asserted */
  107 + ichp &= 0x0000ffff;
  108 + ichp |= (1 << 31) | (irq << 16);
  109 + }
  110 + }
  111 + }
  112 +
  113 + return ichp;
  114 +}
  115 +
  116 +static uint32_t pxa2xx_pic_mem_read(void *opaque, target_phys_addr_t offset)
  117 +{
  118 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  119 + offset -= s->base;
  120 +
  121 + switch (offset) {
  122 + case ICIP: /* IRQ Pending register */
  123 + return s->int_pending[0] & ~s->is_fiq[0] & s->int_enabled[0];
  124 + case ICIP2: /* IRQ Pending register 2 */
  125 + return s->int_pending[1] & ~s->is_fiq[1] & s->int_enabled[1];
  126 + case ICMR: /* Mask register */
  127 + return s->int_enabled[0];
  128 + case ICMR2: /* Mask register 2 */
  129 + return s->int_enabled[1];
  130 + case ICLR: /* Level register */
  131 + return s->is_fiq[0];
  132 + case ICLR2: /* Level register 2 */
  133 + return s->is_fiq[1];
  134 + case ICCR: /* Idle mask */
  135 + return (s->int_idle == 0);
  136 + case ICFP: /* FIQ Pending register */
  137 + return s->int_pending[0] & s->is_fiq[0] & s->int_enabled[0];
  138 + case ICFP2: /* FIQ Pending register 2 */
  139 + return s->int_pending[1] & s->is_fiq[1] & s->int_enabled[1];
  140 + case ICPR: /* Pending register */
  141 + return s->int_pending[0];
  142 + case ICPR2: /* Pending register 2 */
  143 + return s->int_pending[1];
  144 + case IPR0 ... IPR31:
  145 + return s->priority[0 + ((offset - IPR0 ) >> 2)];
  146 + case IPR32 ... IPR39:
  147 + return s->priority[32 + ((offset - IPR32) >> 2)];
  148 + case ICHP: /* Highest Priority register */
  149 + return pxa2xx_pic_highest(s);
  150 + default:
  151 + printf("%s: Bad register offset " REG_FMT "\n", __FUNCTION__, offset);
  152 + return 0;
  153 + }
  154 +}
  155 +
  156 +static void pxa2xx_pic_mem_write(void *opaque, target_phys_addr_t offset,
  157 + uint32_t value)
  158 +{
  159 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  160 + offset -= s->base;
  161 +
  162 + switch (offset) {
  163 + case ICMR: /* Mask register */
  164 + s->int_enabled[0] = value;
  165 + break;
  166 + case ICMR2: /* Mask register 2 */
  167 + s->int_enabled[1] = value;
  168 + break;
  169 + case ICLR: /* Level register */
  170 + s->is_fiq[0] = value;
  171 + break;
  172 + case ICLR2: /* Level register 2 */
  173 + s->is_fiq[1] = value;
  174 + break;
  175 + case ICCR: /* Idle mask */
  176 + s->int_idle = (value & 1) ? 0 : ~0;
  177 + break;
  178 + case IPR0 ... IPR31:
  179 + s->priority[0 + ((offset - IPR0 ) >> 2)] = value & 0x8000003f;
  180 + break;
  181 + case IPR32 ... IPR39:
  182 + s->priority[32 + ((offset - IPR32) >> 2)] = value & 0x8000003f;
  183 + break;
  184 + default:
  185 + printf("%s: Bad register offset " REG_FMT "\n", __FUNCTION__, offset);
  186 + return;
  187 + }
  188 + pxa2xx_pic_update(opaque);
  189 +}
  190 +
  191 +/* Interrupt Controller Coprocessor Space Register Mapping */
  192 +static const int pxa2xx_cp_reg_map[0x10] = {
  193 + [0x0 ... 0xf] = -1,
  194 + [0x0] = ICIP,
  195 + [0x1] = ICMR,
  196 + [0x2] = ICLR,
  197 + [0x3] = ICFP,
  198 + [0x4] = ICPR,
  199 + [0x5] = ICHP,
  200 + [0x6] = ICIP2,
  201 + [0x7] = ICMR2,
  202 + [0x8] = ICLR2,
  203 + [0x9] = ICFP2,
  204 + [0xa] = ICPR2,
  205 +};
  206 +
  207 +static uint32_t pxa2xx_pic_cp_read(void *opaque, int op2, int reg, int crm)
  208 +{
  209 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  210 + target_phys_addr_t offset;
  211 +
  212 + if (pxa2xx_cp_reg_map[reg] == -1) {
  213 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  214 + return 0;
  215 + }
  216 +
  217 + offset = s->base + pxa2xx_cp_reg_map[reg];
  218 + return pxa2xx_pic_mem_read(opaque, offset);
  219 +}
  220 +
  221 +static void pxa2xx_pic_cp_write(void *opaque, int op2, int reg, int crm,
  222 + uint32_t value)
  223 +{
  224 + struct pxa2xx_pic_state_s *s = (struct pxa2xx_pic_state_s *) opaque;
  225 + target_phys_addr_t offset;
  226 +
  227 + if (pxa2xx_cp_reg_map[reg] == -1) {
  228 + printf("%s: Bad register 0x%x\n", __FUNCTION__, reg);
  229 + return;
  230 + }
  231 +
  232 + offset = s->base + pxa2xx_cp_reg_map[reg];
  233 + pxa2xx_pic_mem_write(opaque, offset, value);
  234 +}
  235 +
  236 +static CPUReadMemoryFunc *pxa2xx_pic_readfn[] = {
  237 + pxa2xx_pic_mem_read,
  238 + pxa2xx_pic_mem_read,
  239 + pxa2xx_pic_mem_read,
  240 +};
  241 +
  242 +static CPUWriteMemoryFunc *pxa2xx_pic_writefn[] = {
  243 + pxa2xx_pic_mem_write,
  244 + pxa2xx_pic_mem_write,
  245 + pxa2xx_pic_mem_write,
  246 +};
  247 +
  248 +qemu_irq *pxa2xx_pic_init(target_phys_addr_t base, CPUState *env)
  249 +{
  250 + struct pxa2xx_pic_state_s *s;
  251 + int iomemtype;
  252 + qemu_irq *qi;
  253 +
  254 + s = (struct pxa2xx_pic_state_s *)
  255 + qemu_mallocz(sizeof(struct pxa2xx_pic_state_s));
  256 + if (!s)
  257 + return NULL;
  258 +
  259 + s->cpu_env = env;
  260 + s->base = base;
  261 +
  262 + s->int_pending[0] = 0;
  263 + s->int_pending[1] = 0;
  264 + s->int_enabled[0] = 0;
  265 + s->int_enabled[1] = 0;
  266 + s->is_fiq[0] = 0;
  267 + s->is_fiq[1] = 0;
  268 +
  269 + qi = qemu_allocate_irqs(pxa2xx_pic_set_irq, s, PXA2XX_PIC_SRCS);
  270 +
  271 + /* Enable IC memory-mapped registers access. */
  272 + iomemtype = cpu_register_io_memory(0, pxa2xx_pic_readfn,
  273 + pxa2xx_pic_writefn, s);
  274 + cpu_register_physical_memory(base, 0x000fffff, iomemtype);
  275 +
  276 + /* Enable IC coprocessor access. */
  277 + cpu_arm_set_cp_io(env, 6, pxa2xx_pic_cp_read, pxa2xx_pic_cp_write, s);
  278 +
  279 + return qi;
  280 +}
... ...
target-arm/cpu.h
... ... @@ -38,6 +38,11 @@
38 38 #define EXCP_FIQ 6
39 39 #define EXCP_BKPT 7
40 40  
  41 +typedef void ARMWriteCPFunc(void *opaque, int cp_info,
  42 + int srcreg, int operand, uint32_t value);
  43 +typedef uint32_t ARMReadCPFunc(void *opaque, int cp_info,
  44 + int dstreg, int operand);
  45 +
41 46 /* We currently assume float and double are IEEE single and double
42 47 precision respectively.
43 48 Doing runtime conversions is tricky because VFP registers may contain
... ... @@ -75,6 +80,7 @@ typedef struct CPUARMState {
75 80 /* System control coprocessor (cp15) */
76 81 struct {
77 82 uint32_t c0_cpuid;
  83 + uint32_t c0_cachetype;
78 84 uint32_t c1_sys; /* System control register. */
79 85 uint32_t c1_coproc; /* Coprocessor access register. */
80 86 uint32_t c2; /* MMU translation table base. */
... ... @@ -87,8 +93,16 @@ typedef struct CPUARMState {
87 93 uint32_t c9_data;
88 94 uint32_t c13_fcse; /* FCSE PID. */
89 95 uint32_t c13_context; /* Context ID. */
  96 + uint32_t c15_cpar; /* XScale Coprocessor Access Register */
90 97 } cp15;
91 98  
  99 + /* Coprocessor IO used by peripherals */
  100 + struct {
  101 + ARMReadCPFunc *cp_read;
  102 + ARMWriteCPFunc *cp_write;
  103 + void *opaque;
  104 + } cp[15];
  105 +
92 106 /* Internal CPU feature flags. */
93 107 uint32_t features;
94 108  
... ... @@ -204,10 +218,10 @@ enum arm_cpu_mode {
204 218 #define ARM_VFP_FPINST 9
205 219 #define ARM_VFP_FPINST2 10
206 220  
207   -
208 221 enum arm_features {
209 222 ARM_FEATURE_VFP,
210   - ARM_FEATURE_AUXCR /* ARM1026 Auxiliary control register. */
  223 + ARM_FEATURE_AUXCR, /* ARM1026 Auxiliary control register. */
  224 + ARM_FEATURE_XSCALE, /* Intel XScale extensions. */
211 225 };
212 226  
213 227 static inline int arm_feature(CPUARMState *env, int feature)
... ... @@ -218,8 +232,24 @@ static inline int arm_feature(CPUARMState *env, int feature)
218 232 void arm_cpu_list(void);
219 233 void cpu_arm_set_model(CPUARMState *env, const char *name);
220 234  
221   -#define ARM_CPUID_ARM1026 0x4106a262
222   -#define ARM_CPUID_ARM926 0x41069265
  235 +void cpu_arm_set_cp_io(CPUARMState *env, int cpnum,
  236 + ARMReadCPFunc *cp_read, ARMWriteCPFunc *cp_write,
  237 + void *opaque);
  238 +
  239 +#define ARM_CPUID_ARM1026 0x4106a262
  240 +#define ARM_CPUID_ARM926 0x41069265
  241 +#define ARM_CPUID_PXA250 0x69052100
  242 +#define ARM_CPUID_PXA255 0x69052d00
  243 +#define ARM_CPUID_PXA260 0x69052903
  244 +#define ARM_CPUID_PXA261 0x69052d05
  245 +#define ARM_CPUID_PXA262 0x69052d06
  246 +#define ARM_CPUID_PXA270 0x69054110
  247 +#define ARM_CPUID_PXA270_A0 0x69054110
  248 +#define ARM_CPUID_PXA270_A1 0x69054111
  249 +#define ARM_CPUID_PXA270_B0 0x69054112
  250 +#define ARM_CPUID_PXA270_B1 0x69054113
  251 +#define ARM_CPUID_PXA270_C0 0x69054114
  252 +#define ARM_CPUID_PXA270_C5 0x69054117
223 253  
224 254 #if defined(CONFIG_USER_ONLY)
225 255 #define TARGET_PAGE_BITS 12
... ...
target-arm/exec.h
... ... @@ -54,6 +54,8 @@ int cpu_arm_handle_mmu_fault (CPUState *env, target_ulong address, int rw,
54 54  
55 55 void cpu_lock(void);
56 56 void cpu_unlock(void);
  57 +void helper_set_cp(CPUState *, uint32_t, uint32_t);
  58 +uint32_t helper_get_cp(CPUState *, uint32_t);
57 59 void helper_set_cp15(CPUState *, uint32_t, uint32_t);
58 60 uint32_t helper_get_cp15(CPUState *, uint32_t);
59 61  
... ...
target-arm/helper.c
... ... @@ -17,11 +17,32 @@ static void cpu_reset_model_id(CPUARMState *env, uint32_t id)
17 17 case ARM_CPUID_ARM926:
18 18 set_feature(env, ARM_FEATURE_VFP);
19 19 env->vfp.xregs[ARM_VFP_FPSID] = 0x41011090;
  20 + env->cp15.c0_cachetype = 0x1dd20d2;
20 21 break;
21 22 case ARM_CPUID_ARM1026:
22 23 set_feature(env, ARM_FEATURE_VFP);
23 24 set_feature(env, ARM_FEATURE_AUXCR);
24 25 env->vfp.xregs[ARM_VFP_FPSID] = 0x410110a0;
  26 + env->cp15.c0_cachetype = 0x1dd20d2;
  27 + break;
  28 + case ARM_CPUID_PXA250:
  29 + case ARM_CPUID_PXA255:
  30 + case ARM_CPUID_PXA260:
  31 + case ARM_CPUID_PXA261:
  32 + case ARM_CPUID_PXA262:
  33 + set_feature(env, ARM_FEATURE_XSCALE);
  34 + /* JTAG_ID is ((id << 28) | 0x09265013) */
  35 + env->cp15.c0_cachetype = 0xd172172;
  36 + break;
  37 + case ARM_CPUID_PXA270_A0:
  38 + case ARM_CPUID_PXA270_A1:
  39 + case ARM_CPUID_PXA270_B0:
  40 + case ARM_CPUID_PXA270_B1:
  41 + case ARM_CPUID_PXA270_C0:
  42 + case ARM_CPUID_PXA270_C5:
  43 + set_feature(env, ARM_FEATURE_XSCALE);
  44 + /* JTAG_ID is ((id << 28) | 0x09265013) */
  45 + env->cp15.c0_cachetype = 0xd172172;
25 46 break;
26 47 default:
27 48 cpu_abort(env, "Bad CPU ID: %x\n", id);
... ... @@ -68,6 +89,18 @@ struct arm_cpu_t {
68 89 static const struct arm_cpu_t arm_cpu_names[] = {
69 90 { ARM_CPUID_ARM926, "arm926"},
70 91 { ARM_CPUID_ARM1026, "arm1026"},
  92 + { ARM_CPUID_PXA250, "pxa250" },
  93 + { ARM_CPUID_PXA255, "pxa255" },
  94 + { ARM_CPUID_PXA260, "pxa260" },
  95 + { ARM_CPUID_PXA261, "pxa261" },
  96 + { ARM_CPUID_PXA262, "pxa262" },
  97 + { ARM_CPUID_PXA270, "pxa270" },
  98 + { ARM_CPUID_PXA270_A0, "pxa270-a0" },
  99 + { ARM_CPUID_PXA270_A1, "pxa270-a1" },
  100 + { ARM_CPUID_PXA270_B0, "pxa270-b0" },
  101 + { ARM_CPUID_PXA270_B1, "pxa270-b1" },
  102 + { ARM_CPUID_PXA270_C0, "pxa270-c0" },
  103 + { ARM_CPUID_PXA270_C5, "pxa270-c5" },
71 104 { 0, NULL}
72 105 };
73 106  
... ... @@ -132,6 +165,20 @@ target_phys_addr_t cpu_get_phys_page_debug(CPUState *env, target_ulong addr)
132 165 }
133 166  
134 167 /* These should probably raise undefined insn exceptions. */
  168 +void helper_set_cp(CPUState *env, uint32_t insn, uint32_t val)
  169 +{
  170 + int op1 = (insn >> 8) & 0xf;
  171 + cpu_abort(env, "cp%i insn %08x\n", op1, insn);
  172 + return;
  173 +}
  174 +
  175 +uint32_t helper_get_cp(CPUState *env, uint32_t insn)
  176 +{
  177 + int op1 = (insn >> 8) & 0xf;
  178 + cpu_abort(env, "cp%i insn %08x\n", op1, insn);
  179 + return 0;
  180 +}
  181 +
135 182 void helper_set_cp15(CPUState *env, uint32_t insn, uint32_t val)
136 183 {
137 184 cpu_abort(env, "cp15 insn %08x\n", insn);
... ... @@ -393,12 +440,16 @@ static int get_phys_addr(CPUState *env, uint32_t address, int access_type,
393 440 ap = (desc >> (4 + ((address >> 13) & 6))) & 3;
394 441 break;
395 442 case 3: /* 1k page. */
396   - if (type == 1) {
397   - /* Page translation fault. */
398   - code = 7;
399   - goto do_fault;
  443 + if (arm_feature(env, ARM_FEATURE_XSCALE))
  444 + phys_addr = (desc & 0xfffff000) | (address & 0xfff);
  445 + else {
  446 + if (type == 1) {
  447 + /* Page translation fault. */
  448 + code = 7;
  449 + goto do_fault;
  450 + }
  451 + phys_addr = (desc & 0xfffffc00) | (address & 0x3ff);
400 452 }
401   - phys_addr = (desc & 0xfffffc00) | (address & 0x3ff);
402 453 ap = (desc >> 4) & 3;
403 454 break;
404 455 default:
... ... @@ -461,6 +512,31 @@ target_phys_addr_t cpu_get_phys_page_debug(CPUState *env, target_ulong addr)
461 512 return phys_addr;
462 513 }
463 514  
  515 +void helper_set_cp(CPUState *env, uint32_t insn, uint32_t val)
  516 +{
  517 + int cp_num = (insn >> 8) & 0xf;
  518 + int cp_info = (insn >> 5) & 7;
  519 + int src = (insn >> 16) & 0xf;
  520 + int operand = insn & 0xf;
  521 +
  522 + if (env->cp[cp_num].cp_write)
  523 + env->cp[cp_num].cp_write(env->cp[cp_num].opaque,
  524 + cp_info, src, operand, val);
  525 +}
  526 +
  527 +uint32_t helper_get_cp(CPUState *env, uint32_t insn)
  528 +{
  529 + int cp_num = (insn >> 8) & 0xf;
  530 + int cp_info = (insn >> 5) & 7;
  531 + int dest = (insn >> 16) & 0xf;
  532 + int operand = insn & 0xf;
  533 +
  534 + if (env->cp[cp_num].cp_read)
  535 + return env->cp[cp_num].cp_read(env->cp[cp_num].opaque,
  536 + cp_info, dest, operand);
  537 + return 0;
  538 +}
  539 +
464 540 void helper_set_cp15(CPUState *env, uint32_t insn, uint32_t val)
465 541 {
466 542 uint32_t op2;
... ... @@ -472,15 +548,23 @@ void helper_set_cp15(CPUState *env, uint32_t insn, uint32_t val)
472 548 case 1: /* System configuration. */
473 549 switch (op2) {
474 550 case 0:
475   - env->cp15.c1_sys = val;
  551 + if (!arm_feature(env, ARM_FEATURE_XSCALE) || (insn & 0xf) == 0)
  552 + env->cp15.c1_sys = val;
476 553 /* ??? Lots of these bits are not implemented. */
477 554 /* This may enable/disable the MMU, so do a TLB flush. */
478 555 tlb_flush(env, 1);
479 556 break;
  557 + case 1:
  558 + /* XScale doesn't implement AUX CR (P-Bit) but allows
  559 + * writing with zero and reading. */
  560 + if (arm_feature(env, ARM_FEATURE_XSCALE))
  561 + break;
  562 + goto bad_reg;
480 563 case 2:
481 564 env->cp15.c1_coproc = val;
482 565 /* ??? Is this safe when called from within a TB? */
483 566 tb_flush(env);
  567 + break;
484 568 default:
485 569 goto bad_reg;
486 570 }
... ... @@ -584,13 +668,21 @@ void helper_set_cp15(CPUState *env, uint32_t insn, uint32_t val)
584 668 case 14: /* Reserved. */
585 669 goto bad_reg;
586 670 case 15: /* Implementation specific. */
587   - /* ??? Internal registers not implemented. */
  671 + if (arm_feature(env, ARM_FEATURE_XSCALE)) {
  672 + if (op2 == 0 && (insn & 0xf) == 1) {
  673 + /* Changes cp0 to cp13 behavior, so needs a TB flush. */
  674 + tb_flush(env);
  675 + env->cp15.c15_cpar = (val & 0x3fff) | 2;
  676 + break;
  677 + }
  678 + goto bad_reg;
  679 + }
588 680 break;
589 681 }
590 682 return;
591 683 bad_reg:
592 684 /* ??? For debugging only. Should raise illegal instruction exception. */
593   - cpu_abort(env, "Unimplemented cp15 register read\n");
  685 + cpu_abort(env, "Unimplemented cp15 register write\n");
594 686 }
595 687  
596 688 uint32_t helper_get_cp15(CPUState *env, uint32_t insn)
... ... @@ -604,7 +696,7 @@ uint32_t helper_get_cp15(CPUState *env, uint32_t insn)
604 696 default: /* Device ID. */
605 697 return env->cp15.c0_cpuid;
606 698 case 1: /* Cache Type. */
607   - return 0x1dd20d2;
  699 + return env->cp15.c0_cachetype;
608 700 case 2: /* TCM status. */
609 701 return 0;
610 702 }
... ... @@ -615,6 +707,8 @@ uint32_t helper_get_cp15(CPUState *env, uint32_t insn)
615 707 case 1: /* Auxiliary control register. */
616 708 if (arm_feature(env, ARM_FEATURE_AUXCR))
617 709 return 1;
  710 + if (arm_feature(env, ARM_FEATURE_XSCALE))
  711 + return 0;
618 712 goto bad_reg;
619 713 case 2: /* Coprocessor access register. */
620 714 return env->cp15.c1_coproc;
... ... @@ -649,7 +743,7 @@ uint32_t helper_get_cp15(CPUState *env, uint32_t insn)
649 743 }
650 744 case 7: /* Cache control. */
651 745 /* ??? This is for test, clean and invaidate operations that set the
652   - Z flag. We can't represent N = Z = 1, so it also clears clears
  746 + Z flag. We can't represent N = Z = 1, so it also clears
653 747 the N flag. Oh well. */
654 748 env->NZF = 0;
655 749 return 0;
... ... @@ -682,7 +776,12 @@ uint32_t helper_get_cp15(CPUState *env, uint32_t insn)
682 776 case 14: /* Reserved. */
683 777 goto bad_reg;
684 778 case 15: /* Implementation specific. */
685   - /* ??? Internal registers not implemented. */
  779 + if (arm_feature(env, ARM_FEATURE_XSCALE)) {
  780 + if (op2 == 0 && (insn & 0xf) == 1)
  781 + return env->cp15.c15_cpar;
  782 +
  783 + goto bad_reg;
  784 + }
686 785 return 0;
687 786 }
688 787 bad_reg:
... ... @@ -691,4 +790,18 @@ bad_reg:
691 790 return 0;
692 791 }
693 792  
  793 +void cpu_arm_set_cp_io(CPUARMState *env, int cpnum,
  794 + ARMReadCPFunc *cp_read, ARMWriteCPFunc *cp_write,
  795 + void *opaque)
  796 +{
  797 + if (cpnum < 0 || cpnum > 14) {
  798 + cpu_abort(env, "Bad coprocessor number: %i\n", cpnum);
  799 + return;
  800 + }
  801 +
  802 + env->cp[cpnum].cp_read = cp_read;
  803 + env->cp[cpnum].cp_write = cp_write;
  804 + env->cp[cpnum].opaque = opaque;
  805 +}
  806 +
694 807 #endif
... ...
target-arm/op.c
... ... @@ -1142,12 +1142,24 @@ void OPPROTO op_vfp_mdrr(void)
1142 1142 FT0d = u.d;
1143 1143 }
1144 1144  
1145   -/* Copy the most significant bit to T0 to all bits of T1. */
  1145 +/* Copy the most significant bit of T0 to all bits of T1. */
1146 1146 void OPPROTO op_signbit_T1_T0(void)
1147 1147 {
1148 1148 T1 = (int32_t)T0 >> 31;
1149 1149 }
1150 1150  
  1151 +void OPPROTO op_movl_cp_T0(void)
  1152 +{
  1153 + helper_set_cp(env, PARAM1, T0);
  1154 + FORCE_RET();
  1155 +}
  1156 +
  1157 +void OPPROTO op_movl_T0_cp(void)
  1158 +{
  1159 + T0 = helper_get_cp(env, PARAM1);
  1160 + FORCE_RET();
  1161 +}
  1162 +
1151 1163 void OPPROTO op_movl_cp15_T0(void)
1152 1164 {
1153 1165 helper_set_cp15(env, PARAM1, T0);
... ...
target-arm/translate.c
... ... @@ -492,6 +492,34 @@ static inline void gen_mov_vreg_F0(int dp, int reg)
492 492 gen_op_vfp_setreg_F0s(vfp_reg_offset(dp, reg));
493 493 }
494 494  
  495 +/* Disassemble system coprocessor instruction. Return nonzero if
  496 + instruction is not defined. */
  497 +static int disas_cp_insn(CPUState *env, DisasContext *s, uint32_t insn)
  498 +{
  499 + uint32_t rd = (insn >> 12) & 0xf;
  500 + uint32_t cp = (insn >> 8) & 0xf;
  501 + if (IS_USER(s)) {
  502 + return 1;
  503 + }
  504 +
  505 + if (insn & (1 << 20)) {
  506 + if (!env->cp[cp].cp_read)
  507 + return 1;
  508 + gen_op_movl_T0_im((uint32_t) s->pc);
  509 + gen_op_movl_reg_TN[0][15]();
  510 + gen_op_movl_T0_cp(insn);
  511 + gen_movl_reg_T0(s, rd);
  512 + } else {
  513 + if (!env->cp[cp].cp_write)
  514 + return 1;
  515 + gen_op_movl_T0_im((uint32_t) s->pc);
  516 + gen_op_movl_reg_TN[0][15]();
  517 + gen_movl_T0_reg(s, rd);
  518 + gen_op_movl_cp_T0(insn);
  519 + }
  520 + return 0;
  521 +}
  522 +
495 523 /* Disassemble system coprocessor (cp15) instruction. Return nonzero if
496 524 instruction is not defined. */
497 525 static int disas_cp15_insn(DisasContext *s, uint32_t insn)
... ... @@ -1812,7 +1840,16 @@ static void disas_arm_insn(CPUState * env, DisasContext *s)
1812 1840 case 0xe:
1813 1841 /* Coprocessor. */
1814 1842 op1 = (insn >> 8) & 0xf;
  1843 + if (arm_feature(env, ARM_FEATURE_XSCALE) &&
  1844 + ((env->cp15.c15_cpar ^ 0x3fff) & (1 << op1)))
  1845 + goto illegal_op;
1815 1846 switch (op1) {
  1847 + case 0 ... 1:
  1848 + case 2 ... 9:
  1849 + case 12 ... 14:
  1850 + if (disas_cp_insn (env, s, insn))
  1851 + goto illegal_op;
  1852 + break;
1816 1853 case 10:
1817 1854 case 11:
1818 1855 if (disas_vfp_insn (env, s, insn))
... ...
... ... @@ -1525,6 +1525,8 @@ struct pcmcia_card_s {
1525 1525 /* dscm1xxxx.c */
1526 1526 struct pcmcia_card_s *dscm1xxxx_init(BlockDriverState *bdrv);
1527 1527  
  1528 +#include "hw/pxa.h"
  1529 +
1528 1530 #include "gdbstub.h"
1529 1531  
1530 1532 #endif /* defined(QEMU_TOOL) */
... ...