2
* Luminary Micro Stellaris peripherals
4
* Copyright (c) 2006 CodeSourcery.
5
* Written by Paul Brook
7
* This code is licenced under the GPL.
12
#include "primecell.h"
14
#include "qemu-timer.h"
29
#define BP_OLED_I2C 0x01
30
#define BP_OLED_SSI 0x02
31
#define BP_GAMEPAD 0x04
33
typedef const struct {
43
} stellaris_board_info;
45
/* General purpose timer module. */
47
typedef struct gptm_state {
56
uint32_t match_prescale[2];
59
struct gptm_state *opaque[2];
62
/* The timers have an alternate output used to trigger the ADC. */
67
static void gptm_update_irq(gptm_state *s)
70
level = (s->state & s->mask) != 0;
71
qemu_set_irq(s->irq, level);
74
static void gptm_stop(gptm_state *s, int n)
76
qemu_del_timer(s->timer[n]);
79
static void gptm_reload(gptm_state *s, int n, int reset)
83
tick = qemu_get_clock(vm_clock);
88
/* 32-bit CountDown. */
90
count = s->load[0] | (s->load[1] << 16);
91
tick += (int64_t)count * system_clock_scale;
92
} else if (s->config == 1) {
93
/* 32-bit RTC. 1Hz tick. */
94
tick += ticks_per_sec;
95
} else if (s->mode[n] == 0xa) {
96
/* PWM mode. Not implemented. */
98
cpu_abort(cpu_single_env, "TODO: 16-bit timer mode 0x%x\n",
102
qemu_mod_timer(s->timer[n], tick);
105
static void gptm_tick(void *opaque)
107
gptm_state **p = (gptm_state **)opaque;
113
if (s->config == 0) {
115
if ((s->control & 0x20)) {
116
/* Output trigger. */
117
qemu_irq_raise(s->trigger);
118
qemu_irq_lower(s->trigger);
120
if (s->mode[0] & 1) {
125
gptm_reload(s, 0, 0);
127
} else if (s->config == 1) {
131
match = s->match[0] | (s->match[1] << 16);
137
gptm_reload(s, 0, 0);
138
} else if (s->mode[n] == 0xa) {
139
/* PWM mode. Not implemented. */
141
cpu_abort(cpu_single_env, "TODO: 16-bit timer mode 0x%x\n",
147
static uint32_t gptm_read(void *opaque, target_phys_addr_t offset)
149
gptm_state *s = (gptm_state *)opaque;
155
case 0x04: /* TAMR */
157
case 0x08: /* TBMR */
166
return s->state & s->mask;
169
case 0x28: /* TAILR */
170
return s->load[0] | ((s->config < 4) ? (s->load[1] << 16) : 0);
171
case 0x2c: /* TBILR */
173
case 0x30: /* TAMARCHR */
174
return s->match[0] | ((s->config < 4) ? (s->match[1] << 16) : 0);
175
case 0x34: /* TBMATCHR */
177
case 0x38: /* TAPR */
178
return s->prescale[0];
179
case 0x3c: /* TBPR */
180
return s->prescale[1];
181
case 0x40: /* TAPMR */
182
return s->match_prescale[0];
183
case 0x44: /* TBPMR */
184
return s->match_prescale[1];
189
cpu_abort(cpu_single_env, "TODO: Timer value read\n");
191
cpu_abort(cpu_single_env, "gptm_read: Bad offset 0x%x\n", (int)offset);
196
static void gptm_write(void *opaque, target_phys_addr_t offset, uint32_t value)
198
gptm_state *s = (gptm_state *)opaque;
202
/* The timers should be disabled before changing the configuration.
203
We take advantage of this and defer everything until the timer
209
case 0x04: /* TAMR */
212
case 0x08: /* TBMR */
218
/* TODO: Implement pause. */
219
if ((oldval ^ value) & 1) {
221
gptm_reload(s, 0, 1);
226
if (((oldval ^ value) & 0x100) && s->config >= 4) {
228
gptm_reload(s, 1, 1);
235
s->mask = value & 0x77;
241
case 0x28: /* TAILR */
242
s->load[0] = value & 0xffff;
244
s->load[1] = value >> 16;
247
case 0x2c: /* TBILR */
248
s->load[1] = value & 0xffff;
250
case 0x30: /* TAMARCHR */
251
s->match[0] = value & 0xffff;
253
s->match[1] = value >> 16;
256
case 0x34: /* TBMATCHR */
257
s->match[1] = value >> 16;
259
case 0x38: /* TAPR */
260
s->prescale[0] = value;
262
case 0x3c: /* TBPR */
263
s->prescale[1] = value;
265
case 0x40: /* TAPMR */
266
s->match_prescale[0] = value;
268
case 0x44: /* TBPMR */
269
s->match_prescale[0] = value;
272
cpu_abort(cpu_single_env, "gptm_write: Bad offset 0x%x\n", (int)offset);
277
static CPUReadMemoryFunc *gptm_readfn[] = {
283
static CPUWriteMemoryFunc *gptm_writefn[] = {
289
static void gptm_save(QEMUFile *f, void *opaque)
291
gptm_state *s = (gptm_state *)opaque;
293
qemu_put_be32(f, s->config);
294
qemu_put_be32(f, s->mode[0]);
295
qemu_put_be32(f, s->mode[1]);
296
qemu_put_be32(f, s->control);
297
qemu_put_be32(f, s->state);
298
qemu_put_be32(f, s->mask);
299
qemu_put_be32(f, s->mode[0]);
300
qemu_put_be32(f, s->mode[0]);
301
qemu_put_be32(f, s->load[0]);
302
qemu_put_be32(f, s->load[1]);
303
qemu_put_be32(f, s->match[0]);
304
qemu_put_be32(f, s->match[1]);
305
qemu_put_be32(f, s->prescale[0]);
306
qemu_put_be32(f, s->prescale[1]);
307
qemu_put_be32(f, s->match_prescale[0]);
308
qemu_put_be32(f, s->match_prescale[1]);
309
qemu_put_be32(f, s->rtc);
310
qemu_put_be64(f, s->tick[0]);
311
qemu_put_be64(f, s->tick[1]);
312
qemu_put_timer(f, s->timer[0]);
313
qemu_put_timer(f, s->timer[1]);
316
static int gptm_load(QEMUFile *f, void *opaque, int version_id)
318
gptm_state *s = (gptm_state *)opaque;
323
s->config = qemu_get_be32(f);
324
s->mode[0] = qemu_get_be32(f);
325
s->mode[1] = qemu_get_be32(f);
326
s->control = qemu_get_be32(f);
327
s->state = qemu_get_be32(f);
328
s->mask = qemu_get_be32(f);
329
s->mode[0] = qemu_get_be32(f);
330
s->mode[0] = qemu_get_be32(f);
331
s->load[0] = qemu_get_be32(f);
332
s->load[1] = qemu_get_be32(f);
333
s->match[0] = qemu_get_be32(f);
334
s->match[1] = qemu_get_be32(f);
335
s->prescale[0] = qemu_get_be32(f);
336
s->prescale[1] = qemu_get_be32(f);
337
s->match_prescale[0] = qemu_get_be32(f);
338
s->match_prescale[1] = qemu_get_be32(f);
339
s->rtc = qemu_get_be32(f);
340
s->tick[0] = qemu_get_be64(f);
341
s->tick[1] = qemu_get_be64(f);
342
qemu_get_timer(f, s->timer[0]);
343
qemu_get_timer(f, s->timer[1]);
348
static void stellaris_gptm_init(uint32_t base, qemu_irq irq, qemu_irq trigger)
353
s = (gptm_state *)qemu_mallocz(sizeof(gptm_state));
356
s->trigger = trigger;
357
s->opaque[0] = s->opaque[1] = s;
359
iomemtype = cpu_register_io_memory(0, gptm_readfn,
361
cpu_register_physical_memory(base, 0x00001000, iomemtype);
362
s->timer[0] = qemu_new_timer(vm_clock, gptm_tick, &s->opaque[0]);
363
s->timer[1] = qemu_new_timer(vm_clock, gptm_tick, &s->opaque[1]);
364
register_savevm("stellaris_gptm", -1, 1, gptm_save, gptm_load, s);
368
/* System controller. */
386
stellaris_board_info *board;
389
static void ssys_update(ssys_state *s)
391
qemu_set_irq(s->irq, (s->int_status & s->int_mask) != 0);
394
static uint32_t pllcfg_sandstorm[16] = {
396
0x1ae0, /* 1.8432 Mhz */
398
0xd573, /* 2.4576 Mhz */
399
0x37a6, /* 3.57954 Mhz */
400
0x1ae2, /* 3.6864 Mhz */
402
0x98bc, /* 4.906 Mhz */
403
0x935b, /* 4.9152 Mhz */
405
0x4dee, /* 5.12 Mhz */
407
0x75db, /* 6.144 Mhz */
408
0x1ae6, /* 7.3728 Mhz */
410
0x585b /* 8.192 Mhz */
413
static uint32_t pllcfg_fury[16] = {
415
0x1b20, /* 1.8432 Mhz */
417
0xf42b, /* 2.4576 Mhz */
418
0x37e3, /* 3.57954 Mhz */
419
0x1b21, /* 3.6864 Mhz */
421
0x98ee, /* 4.906 Mhz */
422
0xd5b4, /* 4.9152 Mhz */
424
0x4e27, /* 5.12 Mhz */
426
0xec1c, /* 6.144 Mhz */
427
0x1b23, /* 7.3728 Mhz */
429
0xb11c /* 8.192 Mhz */
432
static uint32_t ssys_read(void *opaque, target_phys_addr_t offset)
434
ssys_state *s = (ssys_state *)opaque;
438
case 0x000: /* DID0 */
439
return s->board->did0;
440
case 0x004: /* DID1 */
441
return s->board->did1;
442
case 0x008: /* DC0 */
443
return s->board->dc0;
444
case 0x010: /* DC1 */
445
return s->board->dc1;
446
case 0x014: /* DC2 */
447
return s->board->dc2;
448
case 0x018: /* DC3 */
449
return s->board->dc3;
450
case 0x01c: /* DC4 */
451
return s->board->dc4;
452
case 0x030: /* PBORCTL */
454
case 0x034: /* LDOPCTL */
456
case 0x040: /* SRCR0 */
458
case 0x044: /* SRCR1 */
460
case 0x048: /* SRCR2 */
462
case 0x050: /* RIS */
463
return s->int_status;
464
case 0x054: /* IMC */
466
case 0x058: /* MISC */
467
return s->int_status & s->int_mask;
468
case 0x05c: /* RESC */
470
case 0x060: /* RCC */
472
case 0x064: /* PLLCFG */
475
xtal = (s->rcc >> 6) & 0xf;
476
if (s->board->did0 & (1 << 16)) {
477
return pllcfg_fury[xtal];
479
return pllcfg_sandstorm[xtal];
482
case 0x100: /* RCGC0 */
484
case 0x104: /* RCGC1 */
486
case 0x108: /* RCGC2 */
488
case 0x110: /* SCGC0 */
490
case 0x114: /* SCGC1 */
492
case 0x118: /* SCGC2 */
494
case 0x120: /* DCGC0 */
496
case 0x124: /* DCGC1 */
498
case 0x128: /* DCGC2 */
500
case 0x150: /* CLKVCLR */
502
case 0x160: /* LDOARST */
504
case 0x1e0: /* USER0 */
506
case 0x1e4: /* USER1 */
509
cpu_abort(cpu_single_env, "ssys_read: Bad offset 0x%x\n", (int)offset);
514
static void ssys_calculate_system_clock(ssys_state *s)
516
system_clock_scale = 5 * (((s->rcc >> 23) & 0xf) + 1);
519
static void ssys_write(void *opaque, target_phys_addr_t offset, uint32_t value)
521
ssys_state *s = (ssys_state *)opaque;
525
case 0x030: /* PBORCTL */
526
s->pborctl = value & 0xffff;
528
case 0x034: /* LDOPCTL */
529
s->ldopctl = value & 0x1f;
531
case 0x040: /* SRCR0 */
532
case 0x044: /* SRCR1 */
533
case 0x048: /* SRCR2 */
534
fprintf(stderr, "Peripheral reset not implemented\n");
536
case 0x054: /* IMC */
537
s->int_mask = value & 0x7f;
539
case 0x058: /* MISC */
540
s->int_status &= ~value;
542
case 0x05c: /* RESC */
543
s->resc = value & 0x3f;
545
case 0x060: /* RCC */
546
if ((s->rcc & (1 << 13)) != 0 && (value & (1 << 13)) == 0) {
548
s->int_status |= (1 << 6);
551
ssys_calculate_system_clock(s);
553
case 0x100: /* RCGC0 */
556
case 0x104: /* RCGC1 */
559
case 0x108: /* RCGC2 */
562
case 0x110: /* SCGC0 */
565
case 0x114: /* SCGC1 */
568
case 0x118: /* SCGC2 */
571
case 0x120: /* DCGC0 */
574
case 0x124: /* DCGC1 */
577
case 0x128: /* DCGC2 */
580
case 0x150: /* CLKVCLR */
583
case 0x160: /* LDOARST */
587
cpu_abort(cpu_single_env, "ssys_write: Bad offset 0x%x\n", (int)offset);
592
static CPUReadMemoryFunc *ssys_readfn[] = {
598
static CPUWriteMemoryFunc *ssys_writefn[] = {
604
static void ssys_reset(void *opaque)
606
ssys_state *s = (ssys_state *)opaque;
615
static void ssys_save(QEMUFile *f, void *opaque)
617
ssys_state *s = (ssys_state *)opaque;
619
qemu_put_be32(f, s->pborctl);
620
qemu_put_be32(f, s->ldopctl);
621
qemu_put_be32(f, s->int_mask);
622
qemu_put_be32(f, s->int_status);
623
qemu_put_be32(f, s->resc);
624
qemu_put_be32(f, s->rcc);
625
qemu_put_be32(f, s->rcgc[0]);
626
qemu_put_be32(f, s->rcgc[1]);
627
qemu_put_be32(f, s->rcgc[2]);
628
qemu_put_be32(f, s->scgc[0]);
629
qemu_put_be32(f, s->scgc[1]);
630
qemu_put_be32(f, s->scgc[2]);
631
qemu_put_be32(f, s->dcgc[0]);
632
qemu_put_be32(f, s->dcgc[1]);
633
qemu_put_be32(f, s->dcgc[2]);
634
qemu_put_be32(f, s->clkvclr);
635
qemu_put_be32(f, s->ldoarst);
638
static int ssys_load(QEMUFile *f, void *opaque, int version_id)
640
ssys_state *s = (ssys_state *)opaque;
645
s->pborctl = qemu_get_be32(f);
646
s->ldopctl = qemu_get_be32(f);
647
s->int_mask = qemu_get_be32(f);
648
s->int_status = qemu_get_be32(f);
649
s->resc = qemu_get_be32(f);
650
s->rcc = qemu_get_be32(f);
651
s->rcgc[0] = qemu_get_be32(f);
652
s->rcgc[1] = qemu_get_be32(f);
653
s->rcgc[2] = qemu_get_be32(f);
654
s->scgc[0] = qemu_get_be32(f);
655
s->scgc[1] = qemu_get_be32(f);
656
s->scgc[2] = qemu_get_be32(f);
657
s->dcgc[0] = qemu_get_be32(f);
658
s->dcgc[1] = qemu_get_be32(f);
659
s->dcgc[2] = qemu_get_be32(f);
660
s->clkvclr = qemu_get_be32(f);
661
s->ldoarst = qemu_get_be32(f);
662
ssys_calculate_system_clock(s);
667
static void stellaris_sys_init(uint32_t base, qemu_irq irq,
668
stellaris_board_info * board,
674
s = (ssys_state *)qemu_mallocz(sizeof(ssys_state));
678
/* Most devices come preprogrammed with a MAC address in the user data. */
679
s->user0 = macaddr[0] | (macaddr[1] << 8) | (macaddr[2] << 16);
680
s->user1 = macaddr[3] | (macaddr[4] << 8) | (macaddr[5] << 16);
682
iomemtype = cpu_register_io_memory(0, ssys_readfn,
684
cpu_register_physical_memory(base, 0x00001000, iomemtype);
686
register_savevm("stellaris_sys", -1, 1, ssys_save, ssys_load, s);
690
/* I2C controller. */
703
} stellaris_i2c_state;
705
#define STELLARIS_I2C_MCS_BUSY 0x01
706
#define STELLARIS_I2C_MCS_ERROR 0x02
707
#define STELLARIS_I2C_MCS_ADRACK 0x04
708
#define STELLARIS_I2C_MCS_DATACK 0x08
709
#define STELLARIS_I2C_MCS_ARBLST 0x10
710
#define STELLARIS_I2C_MCS_IDLE 0x20
711
#define STELLARIS_I2C_MCS_BUSBSY 0x40
713
static uint32_t stellaris_i2c_read(void *opaque, target_phys_addr_t offset)
715
stellaris_i2c_state *s = (stellaris_i2c_state *)opaque;
722
/* We don't emulate timing, so the controller is never busy. */
723
return s->mcs | STELLARIS_I2C_MCS_IDLE;
726
case 0x0c: /* MTPR */
728
case 0x10: /* MIMR */
730
case 0x14: /* MRIS */
732
case 0x18: /* MMIS */
733
return s->mris & s->mimr;
737
cpu_abort(cpu_single_env, "strllaris_i2c_read: Bad offset 0x%x\n",
743
static void stellaris_i2c_update(stellaris_i2c_state *s)
747
level = (s->mris & s->mimr) != 0;
748
qemu_set_irq(s->irq, level);
751
static void stellaris_i2c_write(void *opaque, target_phys_addr_t offset,
754
stellaris_i2c_state *s = (stellaris_i2c_state *)opaque;
759
s->msa = value & 0xff;
762
if ((s->mcr & 0x10) == 0) {
763
/* Disabled. Do nothing. */
766
/* Grab the bus if this is starting a transfer. */
767
if ((value & 2) && (s->mcs & STELLARIS_I2C_MCS_BUSBSY) == 0) {
768
if (i2c_start_transfer(s->bus, s->msa >> 1, s->msa & 1)) {
769
s->mcs |= STELLARIS_I2C_MCS_ARBLST;
771
s->mcs &= ~STELLARIS_I2C_MCS_ARBLST;
772
s->mcs |= STELLARIS_I2C_MCS_BUSBSY;
775
/* If we don't have the bus then indicate an error. */
776
if (!i2c_bus_busy(s->bus)
777
|| (s->mcs & STELLARIS_I2C_MCS_BUSBSY) == 0) {
778
s->mcs |= STELLARIS_I2C_MCS_ERROR;
781
s->mcs &= ~STELLARIS_I2C_MCS_ERROR;
783
/* Transfer a byte. */
784
/* TODO: Handle errors. */
787
s->mdr = i2c_recv(s->bus) & 0xff;
790
i2c_send(s->bus, s->mdr);
792
/* Raise an interrupt. */
796
/* Finish transfer. */
797
i2c_end_transfer(s->bus);
798
s->mcs &= ~STELLARIS_I2C_MCS_BUSBSY;
802
s->mdr = value & 0xff;
804
case 0x0c: /* MTPR */
805
s->mtpr = value & 0xff;
807
case 0x10: /* MIMR */
810
case 0x1c: /* MICR */
815
cpu_abort(cpu_single_env,
816
"stellaris_i2c_write: Loopback not implemented\n");
818
cpu_abort(cpu_single_env,
819
"stellaris_i2c_write: Slave mode not implemented\n");
820
s->mcr = value & 0x31;
823
cpu_abort(cpu_single_env, "stellaris_i2c_write: Bad offset 0x%x\n",
826
stellaris_i2c_update(s);
829
static void stellaris_i2c_reset(stellaris_i2c_state *s)
831
if (s->mcs & STELLARIS_I2C_MCS_BUSBSY)
832
i2c_end_transfer(s->bus);
841
stellaris_i2c_update(s);
844
static CPUReadMemoryFunc *stellaris_i2c_readfn[] = {
850
static CPUWriteMemoryFunc *stellaris_i2c_writefn[] = {
856
static void stellaris_i2c_save(QEMUFile *f, void *opaque)
858
stellaris_i2c_state *s = (stellaris_i2c_state *)opaque;
860
qemu_put_be32(f, s->msa);
861
qemu_put_be32(f, s->mcs);
862
qemu_put_be32(f, s->mdr);
863
qemu_put_be32(f, s->mtpr);
864
qemu_put_be32(f, s->mimr);
865
qemu_put_be32(f, s->mris);
866
qemu_put_be32(f, s->mcr);
869
static int stellaris_i2c_load(QEMUFile *f, void *opaque, int version_id)
871
stellaris_i2c_state *s = (stellaris_i2c_state *)opaque;
876
s->msa = qemu_get_be32(f);
877
s->mcs = qemu_get_be32(f);
878
s->mdr = qemu_get_be32(f);
879
s->mtpr = qemu_get_be32(f);
880
s->mimr = qemu_get_be32(f);
881
s->mris = qemu_get_be32(f);
882
s->mcr = qemu_get_be32(f);
887
static void stellaris_i2c_init(uint32_t base, qemu_irq irq, i2c_bus *bus)
889
stellaris_i2c_state *s;
892
s = (stellaris_i2c_state *)qemu_mallocz(sizeof(stellaris_i2c_state));
897
iomemtype = cpu_register_io_memory(0, stellaris_i2c_readfn,
898
stellaris_i2c_writefn, s);
899
cpu_register_physical_memory(base, 0x00001000, iomemtype);
900
/* ??? For now we only implement the master interface. */
901
stellaris_i2c_reset(s);
902
register_savevm("stellaris_i2c", -1, 1,
903
stellaris_i2c_save, stellaris_i2c_load, s);
906
/* Analogue to Digital Converter. This is only partially implemented,
907
enough for applications that use a combined ADC and timer tick. */
909
#define STELLARIS_ADC_EM_CONTROLLER 0
910
#define STELLARIS_ADC_EM_COMP 1
911
#define STELLARIS_ADC_EM_EXTERNAL 4
912
#define STELLARIS_ADC_EM_TIMER 5
913
#define STELLARIS_ADC_EM_PWM0 6
914
#define STELLARIS_ADC_EM_PWM1 7
915
#define STELLARIS_ADC_EM_PWM2 8
917
#define STELLARIS_ADC_FIFO_EMPTY 0x0100
918
#define STELLARIS_ADC_FIFO_FULL 0x1000
939
} stellaris_adc_state;
941
static uint32_t stellaris_adc_fifo_read(stellaris_adc_state *s, int n)
945
tail = s->fifo[n].state & 0xf;
946
if (s->fifo[n].state & STELLARIS_ADC_FIFO_EMPTY) {
949
s->fifo[n].state = (s->fifo[n].state & ~0xf) | ((tail + 1) & 0xf);
950
s->fifo[n].state &= ~STELLARIS_ADC_FIFO_FULL;
951
if (tail + 1 == ((s->fifo[n].state >> 4) & 0xf))
952
s->fifo[n].state |= STELLARIS_ADC_FIFO_EMPTY;
954
return s->fifo[n].data[tail];
957
static void stellaris_adc_fifo_write(stellaris_adc_state *s, int n,
962
head = (s->fifo[n].state >> 4) & 0xf;
963
if (s->fifo[n].state & STELLARIS_ADC_FIFO_FULL) {
967
s->fifo[n].data[head] = value;
968
head = (head + 1) & 0xf;
969
s->fifo[n].state &= ~STELLARIS_ADC_FIFO_EMPTY;
970
s->fifo[n].state = (s->fifo[n].state & ~0xf0) | (head << 4);
971
if ((s->fifo[n].state & 0xf) == head)
972
s->fifo[n].state |= STELLARIS_ADC_FIFO_FULL;
975
static void stellaris_adc_update(stellaris_adc_state *s)
979
level = (s->ris & s->im) != 0;
980
qemu_set_irq(s->irq, level);
983
static void stellaris_adc_trigger(void *opaque, int irq, int level)
985
stellaris_adc_state *s = (stellaris_adc_state *)opaque;
987
if ((s->actss & 1) == 0) {
991
/* Some applications use the ADC as a random number source, so introduce
992
some variation into the signal. */
993
s->noise = s->noise * 314159 + 1;
994
/* ??? actual inputs not implemented. Return an arbitrary value. */
995
stellaris_adc_fifo_write(s, 0, 0x200 + ((s->noise >> 16) & 7));
997
stellaris_adc_update(s);
1000
static void stellaris_adc_reset(stellaris_adc_state *s)
1004
for (n = 0; n < 4; n++) {
1007
s->fifo[n].state = STELLARIS_ADC_FIFO_EMPTY;
1011
static uint32_t stellaris_adc_read(void *opaque, target_phys_addr_t offset)
1013
stellaris_adc_state *s = (stellaris_adc_state *)opaque;
1015
/* TODO: Implement this. */
1017
if (offset >= 0x40 && offset < 0xc0) {
1019
n = (offset - 0x40) >> 5;
1020
switch (offset & 0x1f) {
1021
case 0x00: /* SSMUX */
1023
case 0x04: /* SSCTL */
1025
case 0x08: /* SSFIFO */
1026
return stellaris_adc_fifo_read(s, n);
1027
case 0x0c: /* SSFSTAT */
1028
return s->fifo[n].state;
1034
case 0x00: /* ACTSS */
1036
case 0x04: /* RIS */
1040
case 0x0c: /* ISC */
1041
return s->ris & s->im;
1042
case 0x10: /* OSTAT */
1044
case 0x14: /* EMUX */
1046
case 0x18: /* USTAT */
1048
case 0x20: /* SSPRI */
1050
case 0x30: /* SAC */
1053
cpu_abort(cpu_single_env, "strllaris_adc_read: Bad offset 0x%x\n",
1059
static void stellaris_adc_write(void *opaque, target_phys_addr_t offset,
1062
stellaris_adc_state *s = (stellaris_adc_state *)opaque;
1064
/* TODO: Implement this. */
1066
if (offset >= 0x40 && offset < 0xc0) {
1068
n = (offset - 0x40) >> 5;
1069
switch (offset & 0x1f) {
1070
case 0x00: /* SSMUX */
1071
s->ssmux[n] = value & 0x33333333;
1073
case 0x04: /* SSCTL */
1075
cpu_abort(cpu_single_env, "ADC: Unimplemented sequence %x\n",
1078
s->ssctl[n] = value;
1085
case 0x00: /* ACTSS */
1086
s->actss = value & 0xf;
1088
cpu_abort(cpu_single_env,
1089
"Not implemented: ADC sequencers 1-3\n");
1095
case 0x0c: /* ISC */
1098
case 0x10: /* OSTAT */
1101
case 0x14: /* EMUX */
1104
case 0x18: /* USTAT */
1107
case 0x20: /* SSPRI */
1110
case 0x28: /* PSSI */
1111
cpu_abort(cpu_single_env, "Not implemented: ADC sample initiate\n");
1113
case 0x30: /* SAC */
1117
cpu_abort(cpu_single_env, "stellaris_adc_write: Bad offset 0x%x\n",
1120
stellaris_adc_update(s);
1123
static CPUReadMemoryFunc *stellaris_adc_readfn[] = {
1129
static CPUWriteMemoryFunc *stellaris_adc_writefn[] = {
1130
stellaris_adc_write,
1131
stellaris_adc_write,
1135
static void stellaris_adc_save(QEMUFile *f, void *opaque)
1137
stellaris_adc_state *s = (stellaris_adc_state *)opaque;
1141
qemu_put_be32(f, s->actss);
1142
qemu_put_be32(f, s->ris);
1143
qemu_put_be32(f, s->im);
1144
qemu_put_be32(f, s->emux);
1145
qemu_put_be32(f, s->ostat);
1146
qemu_put_be32(f, s->ustat);
1147
qemu_put_be32(f, s->sspri);
1148
qemu_put_be32(f, s->sac);
1149
for (i = 0; i < 4; i++) {
1150
qemu_put_be32(f, s->fifo[i].state);
1151
for (j = 0; j < 16; j++) {
1152
qemu_put_be32(f, s->fifo[i].data[j]);
1154
qemu_put_be32(f, s->ssmux[i]);
1155
qemu_put_be32(f, s->ssctl[i]);
1157
qemu_put_be32(f, s->noise);
1160
static int stellaris_adc_load(QEMUFile *f, void *opaque, int version_id)
1162
stellaris_adc_state *s = (stellaris_adc_state *)opaque;
1166
if (version_id != 1)
1169
s->actss = qemu_get_be32(f);
1170
s->ris = qemu_get_be32(f);
1171
s->im = qemu_get_be32(f);
1172
s->emux = qemu_get_be32(f);
1173
s->ostat = qemu_get_be32(f);
1174
s->ustat = qemu_get_be32(f);
1175
s->sspri = qemu_get_be32(f);
1176
s->sac = qemu_get_be32(f);
1177
for (i = 0; i < 4; i++) {
1178
s->fifo[i].state = qemu_get_be32(f);
1179
for (j = 0; j < 16; j++) {
1180
s->fifo[i].data[j] = qemu_get_be32(f);
1182
s->ssmux[i] = qemu_get_be32(f);
1183
s->ssctl[i] = qemu_get_be32(f);
1185
s->noise = qemu_get_be32(f);
1190
static qemu_irq stellaris_adc_init(uint32_t base, qemu_irq irq)
1192
stellaris_adc_state *s;
1196
s = (stellaris_adc_state *)qemu_mallocz(sizeof(stellaris_adc_state));
1200
iomemtype = cpu_register_io_memory(0, stellaris_adc_readfn,
1201
stellaris_adc_writefn, s);
1202
cpu_register_physical_memory(base, 0x00001000, iomemtype);
1203
stellaris_adc_reset(s);
1204
qi = qemu_allocate_irqs(stellaris_adc_trigger, s, 1);
1205
register_savevm("stellaris_adc", -1, 1,
1206
stellaris_adc_save, stellaris_adc_load, s);
1210
/* Some boards have both an OLED controller and SD card connected to
1211
the same SSI port, with the SD card chip select connected to a
1212
GPIO pin. Technically the OLED chip select is connected to the SSI
1213
Fss pin. We do not bother emulating that as both devices should
1214
never be selected simultaneously, and our OLED controller ignores stray
1215
0xff commands that occur when deselecting the SD card. */
1218
ssi_xfer_cb xfer_cb[2];
1222
} stellaris_ssi_bus_state;
1224
static void stellaris_ssi_bus_select(void *opaque, int irq, int level)
1226
stellaris_ssi_bus_state *s = (stellaris_ssi_bus_state *)opaque;
1228
s->current_dev = level;
1231
static int stellaris_ssi_bus_xfer(void *opaque, int val)
1233
stellaris_ssi_bus_state *s = (stellaris_ssi_bus_state *)opaque;
1235
return s->xfer_cb[s->current_dev](s->opaque[s->current_dev], val);
1238
static void stellaris_ssi_bus_save(QEMUFile *f, void *opaque)
1240
stellaris_ssi_bus_state *s = (stellaris_ssi_bus_state *)opaque;
1242
qemu_put_be32(f, s->current_dev);
1245
static int stellaris_ssi_bus_load(QEMUFile *f, void *opaque, int version_id)
1247
stellaris_ssi_bus_state *s = (stellaris_ssi_bus_state *)opaque;
1249
if (version_id != 1)
1252
s->current_dev = qemu_get_be32(f);
1257
static void *stellaris_ssi_bus_init(qemu_irq *irqp,
1258
ssi_xfer_cb cb0, void *opaque0,
1259
ssi_xfer_cb cb1, void *opaque1)
1262
stellaris_ssi_bus_state *s;
1264
s = (stellaris_ssi_bus_state *)qemu_mallocz(sizeof(stellaris_ssi_bus_state));
1265
s->xfer_cb[0] = cb0;
1266
s->opaque[0] = opaque0;
1267
s->xfer_cb[1] = cb1;
1268
s->opaque[1] = opaque1;
1269
qi = qemu_allocate_irqs(stellaris_ssi_bus_select, s, 1);
1271
register_savevm("stellaris_ssi_bus", -1, 1,
1272
stellaris_ssi_bus_save, stellaris_ssi_bus_load, s);
1277
static stellaris_board_info stellaris_boards[] = {
1281
0x001f001f, /* dc0 */
1291
0x00ff007f, /* dc0 */
1296
BP_OLED_SSI | BP_GAMEPAD
1300
static void stellaris_init(const char *kernel_filename, const char *cpu_model,
1301
DisplayState *ds, stellaris_board_info *board)
1303
static const int uart_irq[] = {5, 6, 33, 34};
1304
static const int timer_irq[] = {19, 21, 23, 35};
1305
static const uint32_t gpio_addr[7] =
1306
{ 0x40004000, 0x40005000, 0x40006000, 0x40007000,
1307
0x40024000, 0x40025000, 0x40026000};
1308
static const int gpio_irq[7] = {0, 1, 2, 3, 4, 30, 31};
1311
qemu_irq *gpio_in[7];
1312
qemu_irq *gpio_out[7];
1319
flash_size = ((board->dc0 & 0xffff) + 1) << 1;
1320
sram_size = (board->dc0 >> 18) + 1;
1321
pic = armv7m_init(flash_size, sram_size, kernel_filename, cpu_model);
1323
if (board->dc1 & (1 << 16)) {
1324
adc = stellaris_adc_init(0x40038000, pic[14]);
1328
for (i = 0; i < 4; i++) {
1329
if (board->dc2 & (0x10000 << i)) {
1330
stellaris_gptm_init(0x40030000 + i * 0x1000,
1331
pic[timer_irq[i]], adc);
1335
stellaris_sys_init(0x400fe000, pic[28], board, nd_table[0].macaddr);
1337
for (i = 0; i < 7; i++) {
1338
if (board->dc4 & (1 << i)) {
1339
gpio_in[i] = pl061_init(gpio_addr[i], pic[gpio_irq[i]],
1344
if (board->dc2 & (1 << 12)) {
1345
i2c = i2c_init_bus();
1346
stellaris_i2c_init(0x40020000, pic[8], i2c);
1347
if (board->peripherals & BP_OLED_I2C) {
1348
ssd0303_init(ds, i2c, 0x3d);
1352
for (i = 0; i < 4; i++) {
1353
if (board->dc2 & (1 << i)) {
1354
pl011_init(0x4000c000 + i * 0x1000, pic[uart_irq[i]],
1355
serial_hds[i], PL011_LUMINARY);
1358
if (board->dc2 & (1 << 4)) {
1359
if (board->peripherals & BP_OLED_SSI) {
1365
oled = ssd0323_init(ds, &gpio_out[GPIO_C][7]);
1366
index = drive_get_index(IF_SD, 0, 0);
1367
sd = ssi_sd_init(drives_table[index].bdrv);
1369
ssi_bus = stellaris_ssi_bus_init(&gpio_out[GPIO_D][0],
1371
ssd0323_xfer_ssi, oled);
1373
pl022_init(0x40008000, pic[7], stellaris_ssi_bus_xfer, ssi_bus);
1374
/* Make sure the select pin is high. */
1375
qemu_irq_raise(gpio_out[GPIO_D][0]);
1377
pl022_init(0x40008000, pic[7], NULL, NULL);
1380
if (board->dc4 & (1 << 28)) {
1381
/* FIXME: Obey network model. */
1382
stellaris_enet_init(&nd_table[0], 0x40048000, pic[42]);
1384
if (board->peripherals & BP_GAMEPAD) {
1385
qemu_irq gpad_irq[5];
1386
static const int gpad_keycode[5] = { 0xc8, 0xd0, 0xcb, 0xcd, 0x1d };
1388
gpad_irq[0] = qemu_irq_invert(gpio_in[GPIO_E][0]); /* up */
1389
gpad_irq[1] = qemu_irq_invert(gpio_in[GPIO_E][1]); /* down */
1390
gpad_irq[2] = qemu_irq_invert(gpio_in[GPIO_E][2]); /* left */
1391
gpad_irq[3] = qemu_irq_invert(gpio_in[GPIO_E][3]); /* right */
1392
gpad_irq[4] = qemu_irq_invert(gpio_in[GPIO_F][1]); /* select */
1394
stellaris_gamepad_init(5, gpad_irq, gpad_keycode);
1398
/* FIXME: Figure out how to generate these from stellaris_boards. */
1399
static void lm3s811evb_init(ram_addr_t ram_size, int vga_ram_size,
1400
const char *boot_device, DisplayState *ds,
1401
const char *kernel_filename, const char *kernel_cmdline,
1402
const char *initrd_filename, const char *cpu_model)
1404
stellaris_init(kernel_filename, cpu_model, ds, &stellaris_boards[0]);
1407
static void lm3s6965evb_init(ram_addr_t ram_size, int vga_ram_size,
1408
const char *boot_device, DisplayState *ds,
1409
const char *kernel_filename, const char *kernel_cmdline,
1410
const char *initrd_filename, const char *cpu_model)
1412
stellaris_init(kernel_filename, cpu_model, ds, &stellaris_boards[1]);
1415
QEMUMachine lm3s811evb_machine = {
1416
.name = "lm3s811evb",
1417
.desc = "Stellaris LM3S811EVB",
1418
.init = lm3s811evb_init,
1419
.ram_require = (64 * 1024 + 8 * 1024) | RAMSIZE_FIXED,
1422
QEMUMachine lm3s6965evb_machine = {
1423
.name = "lm3s6965evb",
1424
.desc = "Stellaris LM3S6965EVB",
1425
.init = lm3s6965evb_init,
1426
.ram_require = (256 * 1024 + 64 * 1024) | RAMSIZE_FIXED,