~ubuntu-branches/ubuntu/trusty/qemu/trusty

« back to all changes in this revision

Viewing changes to debian/patches/linaro-patches/0055-hw-nseries.c-Add-n900-machine.patch

  • Committer: Package Import Robot
  • Author(s): Serge Hallyn
  • Date: 2013-10-22 22:47:07 UTC
  • mfrom: (1.8.3) (10.1.42 sid)
  • Revision ID: package-import@ubuntu.com-20131022224707-1lya34fw3k3f24tv
Tags: 1.6.0+dfsg-2ubuntu1
* Merge 1.6.0~rc0+dfsg-2exp from debian experimental.  Remaining changes:
  - debian/control
    * update maintainer
    * remove libiscsi, usb-redir, vde, vnc-jpeg, and libssh2-1-dev
      from build-deps
    * enable rbd
    * add qemu-system and qemu-common B/R to qemu-keymaps
    * add D:udev, R:qemu, R:qemu-common and B:qemu-common to
      qemu-system-common
    * qemu-system-arm, qemu-system-ppc, qemu-system-sparc:
      - add qemu-kvm to Provides
      - add qemu-common, qemu-kvm, kvm to B/R
      - remove openbios-sparc from qemu-system-sparc D
      - drop openbios-ppc and openhackware Depends to Suggests (for now)
    * qemu-system-x86:
      - add qemu-common to Breaks/Replaces.
      - add cpu-checker to Recommends.
    * qemu-user: add B/R:qemu-kvm
    * qemu-kvm:
      - add armhf armel powerpc sparc to Architecture
      - C/R/P: qemu-kvm-spice
    * add qemu-common package
    * drop qemu-slof which is not packaged in ubuntu
  - add qemu-system-common.links for tap ifup/down scripts and OVMF link.
  - qemu-system-x86.links:
    * remove pxe rom links which are in kvm-ipxe
    * add symlink for kvm.1 manpage
  - debian/rules
    * add kvm-spice symlink to qemu-kvm
    * call dh_installmodules for qemu-system-x86
    * update dh_installinit to install upstart script
    * run dh_installman (Closes: #709241) (cherrypicked from 1.5.0+dfsg-2)
  - Add qemu-utils.links for kvm-* symlinks.
  - Add qemu-system-x86.qemu-kvm.upstart and .default
  - Add qemu-system-x86.modprobe to set nesting=1
  - Add qemu-system-common.preinst to add kvm group
  - qemu-system-common.postinst: remove bad group acl if there, then have
    udev relabel /dev/kvm.
  - New linaro patches from qemu-linaro rebasing branch
  - Dropped patches:
    * xen-simplify-xen_enabled.patch
    * sparc-linux-user-fix-missing-symbols-in-.rel-.rela.plt-sections.patch
    * main_loop-do-not-set-nonblocking-if-xen_enabled.patch
    * xen_machine_pv-do-not-create-a-dummy-CPU-in-machine-.patch
    * virtio-rng-fix-crash
  - Kept patches:
    * expose_vms_qemu64cpu.patch - updated
    * linaro arm patches from qemu-linaro rebasing branch
  - New patches:
    * fix-pci-add: change CONFIG variable in ifdef to make sure that
      pci_add is defined.
* Add linaro patches
* Add experimental mach-virt patches for arm virtualization.
* qemu-system-common.install: add debian/tmp/usr/lib to install the
  qemu-bridge-helper

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
From ec9fae206ca45f1dba17777532856ea827e17f85 Mon Sep 17 00:00:00 2001
 
2
From: Peter Maydell <peter.maydell@linaro.org>
 
3
Date: Mon, 18 Feb 2013 16:58:32 +0000
 
4
Subject: [PATCH 55/71] hw/nseries.c: Add n900 machine
 
5
 
 
6
add n900 to nseries.c
 
7
---
 
8
 hw/arm/nseries.c | 1048 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
 
9
 1 file changed, 1048 insertions(+)
 
10
 
 
11
diff --git a/hw/arm/nseries.c b/hw/arm/nseries.c
 
12
index 88fab81..887c140 100644
 
13
--- a/hw/arm/nseries.c
 
14
+++ b/hw/arm/nseries.c
 
15
@@ -32,6 +32,7 @@
 
16
 #include "hw/hw.h"
 
17
 #include "hw/bt.h"
 
18
 #include "hw/loader.h"
 
19
+#include "net/net.h"
 
20
 #include "sysemu/blockdev.h"
 
21
 #include "hw/sysbus.h"
 
22
 #include "exec/address-spaces.h"
 
23
@@ -1556,8 +1557,1054 @@ static QEMUMachine n810_machine = {
 
24
     DEFAULT_MACHINE_OPTIONS,
 
25
 };
 
26
 
 
27
+#define N900_SDRAM_SIZE (256 * 1024 * 1024)
 
28
+#define N900_ONENAND_CS 0
 
29
+#define N900_ONENAND_BUFSIZE (0xc000 << 1)
 
30
+#define N900_SMC_CS 1
 
31
+
 
32
+#define N900_ONENAND_GPIO       65
 
33
+#define N900_CAMFOCUS_GPIO      68
 
34
+#define N900_CAMLAUNCH_GPIO     69
 
35
+#define N900_SLIDE_GPIO         71
 
36
+#define N900_PROXIMITY_GPIO     89
 
37
+#define N900_HEADPHONE_EN_GPIO  98
 
38
+#define N900_TSC2005_IRQ_GPIO   100
 
39
+#define N900_TSC2005_RESET_GPIO 104
 
40
+#define N900_CAMCOVER_GPIO      110
 
41
+#define N900_KBLOCK_GPIO        113
 
42
+#define N900_HEADPHONE_GPIO     177
 
43
+#define N900_LIS302DL_INT2_GPIO 180
 
44
+#define N900_LIS302DL_INT1_GPIO 181
 
45
+
 
46
+//#define DEBUG_BQ2415X
 
47
+//#define DEBUG_TPA6130
 
48
+//#define DEBUG_LIS302DL
 
49
+
 
50
+#define N900_TRACE(fmt, ...) \
 
51
+    fprintf(stderr, "%s@%d: " fmt "\n", __FUNCTION__, __LINE__, ##__VA_ARGS__)
 
52
+
 
53
+#ifdef DEBUG_BQ2415X
 
54
+#define TRACE_BQ2415X(fmt, ...) N900_TRACE(fmt, ##__VA_ARGS__)
 
55
+#else
 
56
+#define TRACE_BQ2415X(...)
 
57
+#endif
 
58
+#ifdef DEBUG_TPA6130
 
59
+#define TRACE_TPA6130(fmt, ...) N900_TRACE(fmt, ##__VA_ARGS__)
 
60
+#else
 
61
+#define TRACE_TPA6130(...)
 
62
+#endif
 
63
+#ifdef DEBUG_LIS302DL
 
64
+#define TRACE_LIS302DL(fmt, ...) N900_TRACE(fmt, ##__VA_ARGS__)
 
65
+#else
 
66
+#define TRACE_LIS302DL(...)
 
67
+#endif
 
68
+
 
69
+static uint64_t ssi_read(void *opaque, hwaddr addr, unsigned size)
 
70
+{
 
71
+    switch (addr) {
 
72
+        case 0x00: /* REVISION */
 
73
+            return 0x10;
 
74
+        case 0x14: /* SYSSTATUS */
 
75
+            return 1; /* RESETDONE */
 
76
+        default:
 
77
+            break;
 
78
+    }
 
79
+    //printf("%s: addr= " OMAP_FMT_plx "\n", __FUNCTION__, addr);
 
80
+    return 0;
 
81
+}
 
82
+
 
83
+static void ssi_write(void *opaque, hwaddr addr, uint64_t value,
 
84
+                      unsigned size)
 
85
+{
 
86
+    //printf("%s: addr=" OMAP_FMT_plx ", value=0x%08x\n", __FUNCTION__, addr, value);
 
87
+}
 
88
+
 
89
+static const MemoryRegionOps ssi_ops = {
 
90
+    .read = ssi_read,
 
91
+    .write = ssi_write,
 
92
+    .endianness = DEVICE_NATIVE_ENDIAN,
 
93
+};
 
94
+
 
95
+typedef struct LIS302DLState_s {
 
96
+    I2CSlave i2c;
 
97
+    int firstbyte;
 
98
+    uint8_t reg;
 
99
+
 
100
+    qemu_irq irq[2];
 
101
+    int8_t axis_max, axis_step;
 
102
+    int noise, dr_test_ack;
 
103
+
 
104
+    uint8_t ctrl1, ctrl2, ctrl3;
 
105
+    uint8_t status;
 
106
+    struct {
 
107
+        uint8_t cfg, src, ths, dur;
 
108
+    } ff_wu[2];
 
109
+    struct {
 
110
+        uint8_t cfg, src, thsy_x, thsz;
 
111
+        uint8_t timelimit, latency, window;
 
112
+    } click;
 
113
+    
 
114
+    int32_t x, y, z;
 
115
+} LIS302DLState;
 
116
+
 
117
+static void lis302dl_interrupt_update(LIS302DLState *s)
 
118
+{
 
119
+#ifdef DEBUG_LIS302DL
 
120
+    static const char *rules[8] = {
 
121
+        "GND", "FF_WU_1", "FF_WU_2", "FF_WU_1|2", "DR",
 
122
+        "???", "???", "CLICK"
 
123
+    };
 
124
+#endif
 
125
+    int active = (s->ctrl3 & 0x80) ? 0 : 1;
 
126
+    int cond, latch;
 
127
+    int i;
 
128
+    for (i = 0; i < 2; i++) {
 
129
+        switch ((s->ctrl3 >> (i * 3)) & 0x07) {
 
130
+            case 0:
 
131
+                cond = 0;
 
132
+                break;
 
133
+            case 1:
 
134
+                cond = s->ff_wu[0].src & 0x40;
 
135
+                latch = s->ff_wu[0].cfg & 0x40;
 
136
+                break;
 
137
+            case 2:
 
138
+                cond = s->ff_wu[1].src & 0x40;
 
139
+                latch = s->ff_wu[1].cfg & 0x40;
 
140
+                break;
 
141
+            case 3:
 
142
+                cond = ((s->ff_wu[0].src | s->ff_wu[1].src) & 0x40);
 
143
+                latch = ((s->ff_wu[0].cfg | s->ff_wu[1].cfg) & 0x40);
 
144
+                break;
 
145
+            case 4:
 
146
+                cond = (((s->ff_wu[0].src | s->ff_wu[1].src) & 0x3f) &
 
147
+                        (((s->ctrl1 & 0x01) ? 0x03 : 0x00) |
 
148
+                         ((s->ctrl1 & 0x02) ? 0x0c : 0x00) |
 
149
+                         ((s->ctrl1 & 0x04) ? 0x30 : 0x00)));
 
150
+                latch = 0;
 
151
+                break;
 
152
+            case 7:
 
153
+                cond = s->click.src & 0x40;
 
154
+                latch = s->click.cfg & 0x40;
 
155
+                break;
 
156
+            default:
 
157
+                TRACE_LIS302DL("unsupported irq config (%d)",
 
158
+                               (s->ctrl3 >> (i * 3)) & 0x07);
 
159
+                cond = 0;
 
160
+                latch = 0;
 
161
+                break;
 
162
+        }
 
163
+        TRACE_LIS302DL("%s: %s irq%d", rules[(s->ctrl3 >> (i * 3)) & 0x07],
 
164
+                       cond ? (latch ? "activate" : "pulse") : "deactivate",
 
165
+                       i);
 
166
+        qemu_set_irq(s->irq[i], cond ? active : !active);
 
167
+        if (cond && !latch) {
 
168
+            qemu_set_irq(s->irq[i], !active);
 
169
+        }
 
170
+    }
 
171
+}
 
172
+
 
173
+static void lis302dl_trigger(LIS302DLState *s, int axis, int value)
 
174
+{
 
175
+    if (value > s->axis_max) value = s->axis_max;
 
176
+    if (value < -s->axis_max) value = -s->axis_max;
 
177
+    switch (axis) {
 
178
+        case 0: s->x = value; break;
 
179
+        case 1: s->y = value; break;
 
180
+        case 2: s->z = value; break;
 
181
+        default: break;
 
182
+    }
 
183
+    if (s->status & (0x01 << axis)) {
 
184
+        s->status |= 0x10 << axis;
 
185
+    } else {
 
186
+        s->status |= 0x01 << axis;
 
187
+    }
 
188
+    if ((s->status & 0x07) == 0x07) {
 
189
+        s->status |= 0x08;
 
190
+    }
 
191
+    if ((s->status & 0x70) == 0x70) {
 
192
+        s->status |= 0x80;
 
193
+    }
 
194
+    uint8_t bit = 0x02 << (axis << 1); /* over threshold */
 
195
+    s->ff_wu[0].src |= bit;
 
196
+    s->ff_wu[1].src |= bit;
 
197
+    
 
198
+    int i = 0;
 
199
+    for (; i < 2; i++) {
 
200
+        if (s->ff_wu[i].src & 0x3f) {
 
201
+            if (s->ff_wu[i].cfg & 0x80) {
 
202
+                if ((s->ff_wu[i].cfg & 0x3f) == (s->ff_wu[i].src & 0x3f)) {
 
203
+                    s->ff_wu[i].src |= 0x40;
 
204
+                }
 
205
+            } else {
 
206
+                if (s->ff_wu[i].src & s->ff_wu[i].cfg & 0x3f) {
 
207
+                    s->ff_wu[i].src |= 0x40;
 
208
+                }
 
209
+            }
 
210
+        }
 
211
+        TRACE_LIS302DL("FF_WU_%d: CFG=0x%02x, SRC=0x%02x",
 
212
+                       i, s->ff_wu[i].cfg, s->ff_wu[i].src);
 
213
+    }
 
214
+    
 
215
+    lis302dl_interrupt_update(s);
 
216
+}
 
217
+
 
218
+static void lis302dl_step(void *opaque, int axis, int high, int activate)
 
219
+{
 
220
+    TRACE_LIS302DL("axis=%d, high=%d, activate=%d", axis, high, activate);
 
221
+    LIS302DLState *s = opaque;
 
222
+    if (activate) {
 
223
+        int v = 0;
 
224
+        switch (axis) {
 
225
+            case 0: v = s->x + (high ? s->axis_step : -s->axis_step); break;
 
226
+            case 1: v = s->y + (high ? s->axis_step : -s->axis_step); break;
 
227
+            case 2: v = s->z + (high ? s->axis_step : -s->axis_step); break;
 
228
+            default: break;
 
229
+        }
 
230
+        if (v > s->axis_max) v = -(s->axis_max - s->axis_step);
 
231
+        if (v < -s->axis_max) v = s->axis_max - s->axis_step;
 
232
+        lis302dl_trigger(s, axis, v);
 
233
+    }
 
234
+}
 
235
+
 
236
+static void lis302dl_reset(DeviceState *ds)
 
237
+{
 
238
+    LIS302DLState *s = FROM_I2C_SLAVE(LIS302DLState, I2C_SLAVE(ds));
 
239
+    
 
240
+    s->firstbyte = 0;
 
241
+    s->reg = 0;
 
242
+
 
243
+    s->noise = 4;
 
244
+    s->dr_test_ack = 0;
 
245
+
 
246
+    s->ctrl1 = 0x03;
 
247
+    s->ctrl2 = 0x00;
 
248
+    s->ctrl3 = 0x00;
 
249
+    s->status = 0x00;
 
250
+
 
251
+    memset(s->ff_wu, 0x00, sizeof(s->ff_wu));
 
252
+    memset(&s->click, 0x00, sizeof(s->click));
 
253
+    
 
254
+    s->x = 0;
 
255
+    s->y = -s->axis_max;
 
256
+    s->z = 0;
 
257
+
 
258
+    lis302dl_interrupt_update(s);
 
259
+}
 
260
+
 
261
+static void lis302dl_event(I2CSlave *i2c, enum i2c_event event)
 
262
+{
 
263
+    LIS302DLState *s = FROM_I2C_SLAVE(LIS302DLState, i2c);
 
264
+    if (event == I2C_START_SEND)
 
265
+        s->firstbyte = 1;
 
266
+}
 
267
+
 
268
+static uint8_t lis302dl_readcoord(LIS302DLState *s, int coord)
 
269
+{
 
270
+    int v;
 
271
+
 
272
+    switch (coord) {
 
273
+        case 0:
 
274
+            v = s->x;
 
275
+            break;
 
276
+        case 1:
 
277
+            v = s->y;
 
278
+            break;
 
279
+        case 2:
 
280
+            v = s->z;
 
281
+            break;
 
282
+        default:
 
283
+            hw_error("%s: unknown axis %d", __FUNCTION__, coord);
 
284
+            break;
 
285
+    }
 
286
+    s->status &= ~(0x88 | (0x11 << coord));
 
287
+    if (s->ctrl1 & 0x10) {
 
288
+        switch (coord) {
 
289
+            case 0:
 
290
+                v -= s->noise;
 
291
+                break;
 
292
+            case 1:
 
293
+            case 2:
 
294
+                v += s->noise;
 
295
+                break;
 
296
+            default:
 
297
+                break;
 
298
+        }
 
299
+        if (++s->noise == 32) {
 
300
+            s->noise = 4;
 
301
+        }
 
302
+        int dr1 = ((s->ctrl3 & 0x07) == 4);
 
303
+        int dr2 = (((s->ctrl3 >> 3) & 0x07) == 4);
 
304
+        if (!s->dr_test_ack++) {
 
305
+            if (dr1) {
 
306
+                qemu_irq_pulse(s->irq[0]);
 
307
+            }
 
308
+            if (dr2) {
 
309
+                qemu_irq_pulse(s->irq[1]);
 
310
+            }
 
311
+        } else if (s->dr_test_ack == 1 + (dr1 + dr2) * 3) {
 
312
+            s->dr_test_ack = 0;
 
313
+        }
 
314
+    }
 
315
+    return (uint8_t)v;
 
316
+}
 
317
+
 
318
+static int lis302dl_rx(I2CSlave *i2c)
 
319
+{
 
320
+    LIS302DLState *s = FROM_I2C_SLAVE(LIS302DLState, i2c);
 
321
+    int value = -1;
 
322
+    int n = 0;
 
323
+    switch (s->reg & 0x7f) {
 
324
+        case 0x00 ... 0x0e:
 
325
+        case 0x10 ... 0x1f:
 
326
+        case 0x23 ... 0x26:
 
327
+        case 0x28:
 
328
+        case 0x2a:
 
329
+        case 0x2c:
 
330
+        case 0x2e ... 0x2f:
 
331
+        case 0x3a:
 
332
+            value = 0;
 
333
+            TRACE_LIS302DL("reg 0x%02x = 0x%02x (unused/reserved reg)",
 
334
+                           s->reg & 0x7f, value);
 
335
+            break;
 
336
+        case 0x0f:
 
337
+            value = 0x3b;
 
338
+            TRACE_LIS302DL("WHOAMI = 0x%02x", value);
 
339
+            break;
 
340
+        case 0x20:
 
341
+            value = s->ctrl1;
 
342
+            TRACE_LIS302DL("CTRL1 = 0x%02x", value);
 
343
+            break;
 
344
+        case 0x21:
 
345
+            value = s->ctrl2;
 
346
+            TRACE_LIS302DL("CTRL2 = 0x%02x", value);
 
347
+            break;
 
348
+        case 0x22:
 
349
+            value = s->ctrl3;
 
350
+            TRACE_LIS302DL("CTRL3 = 0x%02x", value);
 
351
+            break;
 
352
+        case 0x27:
 
353
+            value = s->status;
 
354
+            TRACE_LIS302DL("STATUS = 0x%02x", value);
 
355
+            break;
 
356
+        case 0x29:
 
357
+            value = lis302dl_readcoord(s, 0);
 
358
+            TRACE_LIS302DL("X = 0x%02x", value);
 
359
+            break;
 
360
+        case 0x2b:
 
361
+            value = lis302dl_readcoord(s, 1);
 
362
+            TRACE_LIS302DL("Y = 0x%02x", value);
 
363
+            break;
 
364
+        case 0x2d:
 
365
+            value = lis302dl_readcoord(s, 2);
 
366
+            TRACE_LIS302DL("Z = 0x%02x", value);
 
367
+            break;
 
368
+        case 0x34: n++;
 
369
+        case 0x30:
 
370
+            value = s->ff_wu[n].cfg;
 
371
+            TRACE_LIS302DL("FF_WU%d.CFG = 0x%02x", n + 1, value);
 
372
+            break;
 
373
+        case 0x35: n++;
 
374
+        case 0x31:
 
375
+            value = s->ff_wu[n].src;
 
376
+            TRACE_LIS302DL("FF_WU%d.SRC = 0x%02x", n + 1, value);
 
377
+            s->ff_wu[n].src = 0; //&= ~0x40;
 
378
+            lis302dl_interrupt_update(s);
 
379
+            break;
 
380
+        case 0x36: n++;
 
381
+        case 0x32:
 
382
+            value = s->ff_wu[n].ths;
 
383
+            TRACE_LIS302DL("FF_WU%d.THS = 0x%02x", n + 1, value);
 
384
+            break;
 
385
+        case 0x37: n++;
 
386
+        case 0x33:
 
387
+            value = s->ff_wu[n].dur;
 
388
+            TRACE_LIS302DL("FF_WU%d.DUR = 0x%02x", n + 1, value);
 
389
+            break;
 
390
+        case 0x38:
 
391
+            value = s->click.cfg;
 
392
+            TRACE_LIS302DL("CLICK_CFG = 0x%02x", value);
 
393
+            break;
 
394
+        case 0x39:
 
395
+            value = s->click.src;
 
396
+            TRACE_LIS302DL("CLICK_SRC = 0x%02x", value);
 
397
+            s->click.src &= ~0x40;
 
398
+            lis302dl_interrupt_update(s);
 
399
+            break;
 
400
+        case 0x3b:
 
401
+            value = s->click.thsy_x;
 
402
+            TRACE_LIS302DL("CLICK_THSY_X = 0x%02x", value);
 
403
+            break;
 
404
+        case 0x3c:
 
405
+            value = s->click.thsz;
 
406
+            TRACE_LIS302DL("CLICK_THSZ = 0x%02x", value);
 
407
+            break;
 
408
+        case 0x3d:
 
409
+            value = s->click.timelimit;
 
410
+            TRACE_LIS302DL("CLICK_TIMELIMIT = 0x%02x", value);
 
411
+            break;
 
412
+        case 0x3e:
 
413
+            value = s->click.latency;
 
414
+            TRACE_LIS302DL("CLICK_LATENCY = 0x%02x", value);
 
415
+            break;
 
416
+        case 0x3f:
 
417
+            value = s->click.window;
 
418
+            TRACE_LIS302DL("CLICK_WINDOW = 0x%02x", value);
 
419
+            break;
 
420
+        default:
 
421
+            hw_error("%s: unknown register 0x%02x", __FUNCTION__,
 
422
+                     s->reg & 0x7f);
 
423
+            value = 0;
 
424
+            break;
 
425
+    }
 
426
+    if (s->reg & 0x80) { /* auto-increment? */
 
427
+        s->reg = (s->reg + 1) | 0x80;
 
428
+    }
 
429
+    return value;
 
430
+}
 
431
+
 
432
+static int lis302dl_tx(I2CSlave *i2c, uint8_t data)
 
433
+{
 
434
+    LIS302DLState *s = FROM_I2C_SLAVE(LIS302DLState, i2c);
 
435
+    if (s->firstbyte) {
 
436
+        s->reg = data;
 
437
+        s->firstbyte = 0;
 
438
+    } else {
 
439
+        int n = 0;
 
440
+        switch (s->reg & 0x7f) {
 
441
+            case 0x20:
 
442
+                TRACE_LIS302DL("CTRL1 = 0x%02x", data);
 
443
+                s->ctrl1 = data;
 
444
+                break;
 
445
+            case 0x21:
 
446
+                TRACE_LIS302DL("CTRL2 = 0x%02x", data);
 
447
+                s->ctrl2 = data;
 
448
+                break;
 
449
+            case 0x22:
 
450
+                TRACE_LIS302DL("CTRL3 = 0x%02x", data);
 
451
+                s->ctrl3 = data;
 
452
+                lis302dl_interrupt_update(s);
 
453
+                break;
 
454
+            case 0x34: n++;
 
455
+            case 0x30:
 
456
+                TRACE_LIS302DL("FF_WU%d.CFG = 0x%02x", n + 1, data);
 
457
+                s->ff_wu[n].cfg = data;
 
458
+                break;
 
459
+            case 0x36: n++;
 
460
+            case 0x32:
 
461
+                TRACE_LIS302DL("FF_WU%d.THS = 0x%02x", n + 1, data);
 
462
+                s->ff_wu[n].ths = data;
 
463
+                break;
 
464
+            case 0x37: n++;
 
465
+            case 0x33:
 
466
+                TRACE_LIS302DL("FF_WU%d.DUR = 0x%02x", n + 1, data);
 
467
+                s->ff_wu[n].dur = data;
 
468
+                break;
 
469
+            case 0x38:
 
470
+                TRACE_LIS302DL("CLICK_CFG = 0x%02x", data);
 
471
+                s->click.cfg = data;
 
472
+                break;
 
473
+            case 0x39:
 
474
+                TRACE_LIS302DL("CLICK_SRC = 0x%02x", data);
 
475
+                s->click.src = data;
 
476
+                break;
 
477
+            case 0x3b:
 
478
+                TRACE_LIS302DL("CLICK_THSY_X = 0x%02x", data);
 
479
+                s->click.thsy_x = data;
 
480
+                break;
 
481
+            case 0x3c:
 
482
+                TRACE_LIS302DL("CLICK_THSZ = 0x%02x", data);
 
483
+                s->click.thsz = data;
 
484
+                break;
 
485
+            case 0x3d:
 
486
+                TRACE_LIS302DL("CLICK_TIMELIMIT = 0x%02x", data);
 
487
+                s->click.timelimit = data;
 
488
+                break;
 
489
+            case 0x3e:
 
490
+                TRACE_LIS302DL("CLICK_LATENCY = 0x%02x", data);
 
491
+                s->click.latency = data;
 
492
+                break;
 
493
+            case 0x3f:
 
494
+                TRACE_LIS302DL("CLICK_WINDOW = 0x%02x", data);
 
495
+                s->click.window = data;
 
496
+                break;
 
497
+            default:
 
498
+                hw_error("%s: unknown register 0x%02x (value 0x%02x)",
 
499
+                         __FUNCTION__, s->reg & 0x7f, data);
 
500
+                break;
 
501
+        }
 
502
+        if (s->reg & 0x80) { /* auto-increment? */
 
503
+            s->reg = (s->reg + 1) | 0x80;
 
504
+        }
 
505
+    }
 
506
+    return 1;
 
507
+}
 
508
+
 
509
+static int lis302dl_init(I2CSlave *i2c)
 
510
+{
 
511
+    LIS302DLState *s = FROM_I2C_SLAVE(LIS302DLState, i2c);
 
512
+    s->axis_max = 58;
 
513
+    s->axis_step = s->axis_max;// / 2;
 
514
+    qdev_init_gpio_out(&i2c->qdev, s->irq, 2);
 
515
+    return 0;
 
516
+}
 
517
+
 
518
+/* TODO: ideally x, y, z should be runtime modifiable properties,
 
519
+ * which can be set by calling
 
520
+ *     lis302dl_trigger(s, axis, value);
 
521
+ * where axis is 0,1,2 for x,y,z
 
522
+ */
 
523
+static Property lis302dl_properties[] = {
 
524
+    DEFINE_PROP_INT32("x", LIS302DLState, x, 0),
 
525
+    DEFINE_PROP_INT32("y", LIS302DLState, y, 0),
 
526
+    DEFINE_PROP_INT32("z", LIS302DLState, z, 0),
 
527
+    DEFINE_PROP_END_OF_LIST(),
 
528
+};
 
529
+
 
530
+static void lis302dl_class_init(ObjectClass *klass, void *data)
 
531
+{
 
532
+    DeviceClass *dc = DEVICE_CLASS(klass);
 
533
+    I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
 
534
+    k->init = lis302dl_init;
 
535
+    k->event = lis302dl_event;
 
536
+    k->recv = lis302dl_rx;
 
537
+    k->send = lis302dl_tx;
 
538
+    dc->props = lis302dl_properties;
 
539
+    dc->reset = lis302dl_reset;
 
540
+}
 
541
+
 
542
+static TypeInfo lis302dl_info = {
 
543
+    .name = "lis302dl",
 
544
+    .parent = TYPE_I2C_SLAVE,
 
545
+    .instance_size = sizeof(LIS302DLState),
 
546
+    .class_init = lis302dl_class_init,
 
547
+};
 
548
+
 
549
+typedef struct BQ2415XState_s {
 
550
+    I2CSlave i2c;
 
551
+    int firstbyte;
 
552
+    uint8 reg;
 
553
+    
 
554
+    uint8_t id;
 
555
+    uint8_t st_ctrl;
 
556
+    uint8_t ctrl;
 
557
+    uint8_t bat_v;
 
558
+    uint8_t tcc;
 
559
+} BQ2415XState;
 
560
+
 
561
+static void bq2415x_reset(DeviceState *ds)
 
562
+{
 
563
+    BQ2415XState *s = FROM_I2C_SLAVE(BQ2415XState, I2C_SLAVE(ds));
 
564
+    
 
565
+    s->firstbyte = 0;
 
566
+    s->reg = 0;
 
567
+
 
568
+    s->st_ctrl = 0x50 | 0x80; // 40
 
569
+    s->ctrl = 0x30;
 
570
+    s->bat_v = 0x0a;
 
571
+    s->tcc = 0xa1; // 89
 
572
+}
 
573
+
 
574
+static void bq2415x_event(I2CSlave *i2c, enum i2c_event event)
 
575
+{
 
576
+    BQ2415XState *s = FROM_I2C_SLAVE(BQ2415XState, i2c);
 
577
+    if (event == I2C_START_SEND)
 
578
+        s->firstbyte = 1;
 
579
+}
 
580
+
 
581
+static int bq2415x_rx(I2CSlave *i2c)
 
582
+{
 
583
+    BQ2415XState *s = FROM_I2C_SLAVE(BQ2415XState, i2c);
 
584
+    int value = -1;
 
585
+    switch (s->reg) {
 
586
+        case 0x00:
 
587
+            value = s->st_ctrl;
 
588
+            TRACE_BQ2415X("st_ctrl = 0x%02x", value);
 
589
+            break;
 
590
+        case 0x01:
 
591
+            value = s->ctrl;
 
592
+            TRACE_BQ2415X("ctrl = 0x%02x", value);
 
593
+            break;
 
594
+        case 0x02:
 
595
+            value = s->bat_v;
 
596
+            TRACE_BQ2415X("bat_v = 0x%02x", value);
 
597
+            break;
 
598
+        case 0x03:
 
599
+        case 0x3b:
 
600
+            value = s->id;
 
601
+            TRACE_BQ2415X("id = 0x%02x", value);
 
602
+            break;
 
603
+        case 0x04:
 
604
+            value = s->tcc;
 
605
+            TRACE_BQ2415X("tcc = 0x%02x", value);
 
606
+            break;
 
607
+        default:
 
608
+            TRACE_BQ2415X("unknown register 0x%02x", s->reg);
 
609
+            value = 0;
 
610
+            break;
 
611
+    }
 
612
+    s->reg++;
 
613
+    return value;
 
614
+}
 
615
+
 
616
+static int bq2415x_tx(I2CSlave *i2c, uint8_t data)
 
617
+{
 
618
+    BQ2415XState *s = FROM_I2C_SLAVE(BQ2415XState, i2c);
 
619
+    if (s->firstbyte) {
 
620
+        s->reg = data;
 
621
+        s->firstbyte = 0;
 
622
+    } else {
 
623
+        switch (s->reg) {
 
624
+            case 0x00:
 
625
+                TRACE_BQ2415X("st_ctrl = 0x%02x", data);
 
626
+                s->st_ctrl = (s->st_ctrl & 0x3f) | (data & 0x40) | 0x80;
 
627
+                break;
 
628
+            case 0x01:
 
629
+                TRACE_BQ2415X("ctrl = 0x%02x", data);
 
630
+                s->ctrl = data;
 
631
+                break;
 
632
+            case 0x02:
 
633
+                TRACE_BQ2415X("bat_v = 0x%02x", data);
 
634
+                s->bat_v = data;
 
635
+                break;
 
636
+            case 0x04:
 
637
+                TRACE_BQ2415X("tcc = 0x%02x", data);
 
638
+                s->tcc = data | 0x80;
 
639
+                break;
 
640
+            default:
 
641
+                TRACE_BQ2415X("unknown register 0x%02x (value 0x%02x)",
 
642
+                              s->reg, data);
 
643
+                break;
 
644
+        }
 
645
+        s->reg++;
 
646
+    }
 
647
+    return 1;
 
648
+}
 
649
+
 
650
+static int bq2415x_init(I2CSlave *i2c)
 
651
+{
 
652
+    return 0;
 
653
+}
 
654
+
 
655
+static Property bq2415x_properties[] = {
 
656
+    DEFINE_PROP_UINT8("id", BQ2415XState, id, 0x49),
 
657
+    DEFINE_PROP_END_OF_LIST(),
 
658
+};
 
659
+
 
660
+static void bq2415x_class_init(ObjectClass *klass, void *data)
 
661
+{
 
662
+    DeviceClass *dc = DEVICE_CLASS(klass);
 
663
+    I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
 
664
+    k->init = bq2415x_init;
 
665
+    k->event = bq2415x_event;
 
666
+    k->recv = bq2415x_rx;
 
667
+    k->send = bq2415x_tx;
 
668
+    dc->props = bq2415x_properties;
 
669
+    dc->reset = bq2415x_reset;
 
670
+}
 
671
+
 
672
+static TypeInfo bq2415x_info = {
 
673
+    .name = "bq2415x",
 
674
+    .parent = TYPE_I2C_SLAVE,
 
675
+    .instance_size = sizeof(BQ2415XState),
 
676
+    .class_init = bq2415x_class_init,
 
677
+};
 
678
+
 
679
+typedef struct tpa6130_s {
 
680
+    I2CSlave i2c;
 
681
+    int firstbyte;
 
682
+    int reg;
 
683
+    uint8_t data[3];
 
684
+} TPA6130State;
 
685
+
 
686
+static void tpa6130_reset(DeviceState *ds)
 
687
+{
 
688
+    TPA6130State *s = FROM_I2C_SLAVE(TPA6130State, I2C_SLAVE(ds));
 
689
+    s->firstbyte = 0;
 
690
+    s->reg = 0;
 
691
+    memset(s->data, 0, sizeof(s->data));
 
692
+}
 
693
+
 
694
+static void tpa6130_event(I2CSlave *i2c, enum i2c_event event)
 
695
+{
 
696
+    TPA6130State *s = FROM_I2C_SLAVE(TPA6130State, i2c);
 
697
+    if (event == I2C_START_SEND)
 
698
+        s->firstbyte = 1;
 
699
+}
 
700
+
 
701
+static int tpa6130_rx(I2CSlave *i2c)
 
702
+{
 
703
+    TPA6130State *s = FROM_I2C_SLAVE(TPA6130State, i2c);
 
704
+    int value = 0;
 
705
+    switch (s->reg) {
 
706
+        case 1 ... 3:
 
707
+            value = s->data[s->reg - 1];
 
708
+            TRACE_TPA6130("reg %d = 0x%02x", s->reg, value);
 
709
+            break;
 
710
+        case 4: /* VERSION */
 
711
+            value = 0x01;
 
712
+            TRACE_TPA6130("version = 0x%02x", value);
 
713
+            break;
 
714
+        default:
 
715
+            TRACE_TPA6130("unknown register 0x%02x", s->reg);
 
716
+            break;
 
717
+    }
 
718
+    s->reg++;
 
719
+    return value;
 
720
+}
 
721
+
 
722
+static int tpa6130_tx(I2CSlave *i2c, uint8_t data)
 
723
+{
 
724
+    TPA6130State *s = FROM_I2C_SLAVE(TPA6130State, i2c);
 
725
+    if (s->firstbyte) {
 
726
+        s->reg = data;
 
727
+        s->firstbyte = 0;
 
728
+    } else {
 
729
+        switch (s->reg) {
 
730
+            case 1 ... 3:
 
731
+                TRACE_TPA6130("reg %d = 0x%02x", s->reg, data);
 
732
+                s->data[s->reg - 1] = data;
 
733
+                break;
 
734
+            default:
 
735
+                TRACE_TPA6130("unknown register 0x%02x", s->reg);
 
736
+                break;
 
737
+        }
 
738
+        s->reg++;
 
739
+    }
 
740
+    return 1;
 
741
+}
 
742
+
 
743
+static void tpa6130_irq(void *opaque, int n, int level)
 
744
+{
 
745
+    if (n) {
 
746
+        hw_error("%s: unknown interrupt source %d\n", __FUNCTION__, n);
 
747
+    } else {
 
748
+        /* headphone enable */
 
749
+        TRACE_TPA6130("enable = %d", level);
 
750
+    }
 
751
+}
 
752
+
 
753
+static int tpa6130_init(I2CSlave *i2c)
 
754
+{
 
755
+    qdev_init_gpio_in(&i2c->qdev, tpa6130_irq, 1);
 
756
+    return 0;
 
757
+}
 
758
+
 
759
+static void tpa6130_class_init(ObjectClass *klass, void *data)
 
760
+{
 
761
+    DeviceClass *dc = DEVICE_CLASS(klass);
 
762
+    I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
 
763
+    k->init = tpa6130_init;
 
764
+    k->event = tpa6130_event;
 
765
+    k->recv = tpa6130_rx;
 
766
+    k->send = tpa6130_tx;
 
767
+    dc->reset = tpa6130_reset;
 
768
+}
 
769
+
 
770
+static TypeInfo tpa6130_info = {
 
771
+    .name = "tpa6130",
 
772
+    .parent = TYPE_I2C_SLAVE,
 
773
+    .instance_size = sizeof(TPA6130State),
 
774
+    .class_init = tpa6130_class_init,
 
775
+};
 
776
+
 
777
+struct n900_s {
 
778
+    struct omap_mpu_state_s *cpu;
 
779
+    void *twl4030;
 
780
+    DeviceState *nand;
 
781
+    DeviceState *mipid;
 
782
+    DeviceState *tsc2005;
 
783
+    DeviceState *bq2415x;
 
784
+    DeviceState *tpa6130;
 
785
+    DeviceState *lis302dl;
 
786
+    DeviceState *smc;
 
787
+#ifdef CONFIG_GLES2
 
788
+    void *gles2;
 
789
+#endif
 
790
+    int extended_key;
 
791
+    int slide_open;
 
792
+    int camera_cover_open;
 
793
+    int headphone_connected;
 
794
+};
 
795
+
 
796
+/* this takes care of the keys which are not located on the
 
797
+ * n900 keypad (note that volume up/down keys are handled by
 
798
+ * the keypad eventhough the keys are not located on the keypad)
 
799
+ * as well as triggering some other hardware button/switch-like
 
800
+ * events that are mapped to the host keyboard:
 
801
+ *
 
802
+ * escape ... power
 
803
+ * f1 ....... keypad slider open/close
 
804
+ * f2 ....... keypad lock
 
805
+ * f3 ....... camera lens cover open/close
 
806
+ * f4 ....... camera focus
 
807
+ * f5 ....... camera take picture
 
808
+ * f6 ....... stereo headphone connect/disconnect
 
809
+ * kp1 ...... decrease accelerometer x axis value
 
810
+ * kp2 ...... increase accelerometer x axis value
 
811
+ * kp4 ...... decrease accelerometer y axis value
 
812
+ * kp5 ...... increase accelerometer y axis value
 
813
+ * kp7 ...... decrease accelerometer z axis value
 
814
+ * kp8 ...... increase accelerometer z axis value
 
815
+ */
 
816
+static void n900_key_handler(void *opaque, int keycode)
 
817
+{
 
818
+    struct n900_s *s = opaque;
 
819
+    if (!s->extended_key && keycode == 0xe0) {
 
820
+        s->extended_key = 0x80;
 
821
+    } else {
 
822
+        int release = keycode & 0x80;
 
823
+        keycode = (keycode & 0x7f) | s->extended_key;
 
824
+        s->extended_key = 0;
 
825
+        switch (keycode) {
 
826
+            case 0x01: /* escape */
 
827
+                twl4030_set_powerbutton_state(s->twl4030, !release);
 
828
+                break;
 
829
+            case 0x3b: /* f1 */
 
830
+                if (release) {
 
831
+                    s->slide_open = !s->slide_open;
 
832
+                    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio,
 
833
+                                                  N900_SLIDE_GPIO),
 
834
+                                 !s->slide_open);
 
835
+                }
 
836
+                break;
 
837
+            case 0x3c: /* f2 */
 
838
+                qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio, N900_KBLOCK_GPIO),
 
839
+                             !!release);
 
840
+                break;
 
841
+            case 0x3d: /* f3 */
 
842
+                if (release) {
 
843
+                    s->camera_cover_open = !s->camera_cover_open;
 
844
+                    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio,
 
845
+                                                  N900_CAMCOVER_GPIO),
 
846
+                                 s->camera_cover_open);
 
847
+                }
 
848
+                break;
 
849
+            case 0x3e: /* f4 */
 
850
+                qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio,
 
851
+                                              N900_CAMFOCUS_GPIO),
 
852
+                             !!release);
 
853
+                break;
 
854
+            case 0x3f: /* f5 */
 
855
+                qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio,
 
856
+                                              N900_CAMLAUNCH_GPIO),
 
857
+                             !!release);
 
858
+                break;
 
859
+            case 0x40: /* f6 */
 
860
+                if (release) {
 
861
+                    s->headphone_connected = !s->headphone_connected;
 
862
+                    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio,
 
863
+                                                  N900_HEADPHONE_GPIO),
 
864
+                                 !s->headphone_connected);
 
865
+                }
 
866
+                break;
 
867
+            case 0x4f ... 0x50: /* kp1,2 */
 
868
+                lis302dl_step(s->lis302dl, 0, keycode - 0x4f, !release);
 
869
+                break;
 
870
+            case 0x4b ... 0x4c: /* kp4,5 */
 
871
+                lis302dl_step(s->lis302dl, 1, keycode - 0x4b, !release);
 
872
+                break;
 
873
+            case 0x47 ... 0x48: /* kp7,8 */
 
874
+                lis302dl_step(s->lis302dl, 2, keycode - 0x47, !release);
 
875
+                break;
 
876
+            default:
 
877
+                break;
 
878
+        }
 
879
+    }
 
880
+}
 
881
+
 
882
+static void n900_reset(void *opaque)
 
883
+{
 
884
+    struct n900_s *s = opaque;
 
885
+    s->slide_open = 1;
 
886
+    s->camera_cover_open = 0;
 
887
+    s->headphone_connected = 0;
 
888
+    qemu_irq_raise(qdev_get_gpio_in(s->cpu->gpio, N900_KBLOCK_GPIO));
 
889
+    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio, N900_HEADPHONE_GPIO), 
 
890
+                 !s->headphone_connected);
 
891
+    qemu_irq_raise(qdev_get_gpio_in(s->cpu->gpio, N900_CAMLAUNCH_GPIO));
 
892
+    qemu_irq_raise(qdev_get_gpio_in(s->cpu->gpio, N900_CAMFOCUS_GPIO));
 
893
+    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio, N900_CAMCOVER_GPIO),
 
894
+                 s->camera_cover_open);
 
895
+    qemu_set_irq(qdev_get_gpio_in(s->cpu->gpio, N900_SLIDE_GPIO),
 
896
+                 !s->slide_open);
 
897
+    omap3_boot_rom_emu(s->cpu);
 
898
+}
 
899
+
 
900
+
 
901
+static uint16_t n900_twl4030_madc_callback(twl4030_adc_type type, int ch)
 
902
+{
 
903
+    return 0x3ff;
 
904
+}
 
905
+
 
906
+static const TWL4030KeyMap n900_twl4030_keymap[] = {
 
907
+    {0x10, 0, 0}, /* Q */
 
908
+    {0x11, 0, 1}, /* W */
 
909
+    {0x12, 0, 2}, /* E */
 
910
+    {0x13, 0, 3}, /* R */
 
911
+    {0x14, 0, 4}, /* T */
 
912
+    {0x15, 0, 5}, /* Y */
 
913
+    {0x16, 0, 6}, /* U */
 
914
+    {0x17, 0, 7}, /* I */
 
915
+    {0x18, 1, 0}, /* O */
 
916
+    {0x20, 1, 1}, /* D */
 
917
+    {0x34, 1, 2}, /* . */
 
918
+    {0x2f, 1, 3}, /* V */
 
919
+    {0xd0, 1, 4}, /* DOWN */
 
920
+    {0x41, 1, 7}, /* F7 -- volume/zoom down */
 
921
+    {0x19, 2, 0}, /* P */
 
922
+    {0x21, 2, 1}, /* F */
 
923
+    {0xc8, 2, 2}, /* UP */
 
924
+    {0x30, 2, 3}, /* B */
 
925
+    {0xcd, 2, 4}, /* RIGHT */
 
926
+    {0x42, 2, 7}, /* F8 -- volume/zoom up */
 
927
+    {0x33, 3, 0}, /* , */
 
928
+    {0x22, 3, 1}, /* G */
 
929
+    {0x1c, 3, 2}, /* ENTER */
 
930
+    {0x31, 3, 3}, /* N */
 
931
+    {0x0e, 4, 0}, /* BACKSPACE */
 
932
+    {0x23, 4, 1}, /* H */
 
933
+    {0x32, 4, 3}, /* M */
 
934
+    {0x1d, 4, 4}, /* LEFTCTRL */
 
935
+    {0x9d, 4, 4}, /* RIGHTCTRL */
 
936
+    {0x24, 5, 1}, /* J */
 
937
+    {0x2c, 5, 2}, /* Z */
 
938
+    {0x39, 5, 3}, /* SPACE */
 
939
+    {0x38, 5, 4}, /* LEFTALT -- "fn" */
 
940
+    {0xb8, 5, 4}, /* RIGHTALT -- "fn" */
 
941
+    {0x1e, 6, 0}, /* A */
 
942
+    {0x25, 6, 1}, /* K */
 
943
+    {0x2d, 6, 2}, /* X */
 
944
+    {0x39, 6, 3}, /* SPACE */
 
945
+    {0x2a, 6, 4}, /* LEFTSHIFT */
 
946
+    {0x36, 6, 4}, /* RIGHTSHIFT */
 
947
+    {0x1f, 7, 0}, /* S */
 
948
+    {0x26, 7, 1}, /* L */
 
949
+    {0x2e, 7, 2}, /* C */
 
950
+    {0xcb, 7, 3}, /* LEFT */
 
951
+    //    {0x10, 0xff, 2}, /* F9 */
 
952
+    //    {0x10, 0xff, 4}, /* F10 */
 
953
+    //    {0x10, 0xff, 5}, /* F11 */
 
954
+    {-1, -1, -1}
 
955
+};
 
956
+
 
957
+static MouseTransformInfo n900_pointercal = {
 
958
+    .x = 800,
 
959
+    .y = 480,
 
960
+    .a = {14114,  18, -2825064,  34,  -8765, 32972906, 65536},
 
961
+};
 
962
+
 
963
+static void n900_init(QEMUMachineInitArgs *args)
 
964
+{
 
965
+    MemoryRegion *sysmem = get_system_memory();
 
966
+    MemoryRegion *ssi_iomem = g_new(MemoryRegion, 1);
 
967
+    struct n900_s *s = g_malloc0(sizeof(*s));
 
968
+    DriveInfo *dmtd = drive_get(IF_MTD, 0, 0);
 
969
+    DriveInfo *dsd  = drive_get(IF_SD, 0, 0);
 
970
+
 
971
+    if (!dmtd && !dsd) {
 
972
+        hw_error("%s: SD or NAND image required", __FUNCTION__);
 
973
+    }
 
974
+#if MAX_SERIAL_PORTS < 3
 
975
+#error MAX_SERIAL_PORTS must be at least 3!
 
976
+#endif
 
977
+    s->cpu = omap3_mpu_init(sysmem, omap3430, N900_SDRAM_SIZE,
 
978
+                            serial_hds[1], serial_hds[2],
 
979
+                            serial_hds[0], NULL);
 
980
+    omap_lcd_panel_attach(s->cpu->dss);
 
981
+
 
982
+    s->tsc2005 = spi_create_device(omap_mcspi_bus(s->cpu->mcspi, 0),
 
983
+                                   "tsc2005", 0);
 
984
+    qdev_connect_gpio_out(s->tsc2005, 0,
 
985
+                          qdev_get_gpio_in(s->cpu->gpio,
 
986
+                                           N900_TSC2005_IRQ_GPIO));
 
987
+    tsc2005_set_transform(s->tsc2005, &n900_pointercal, 600, 1500);
 
988
+    cursor_hide = 0; // who wants to use touchscreen without a pointer?
 
989
+
 
990
+    s->mipid = spi_create_device_noinit(omap_mcspi_bus(s->cpu->mcspi, 0),
 
991
+                                        "lcd_mipid", 2);
 
992
+    qdev_prop_set_uint32(s->mipid, "id", 0x101234);
 
993
+    qdev_prop_set_uint8(s->mipid, "n900", 1);
 
994
+    qdev_init_nofail(s->mipid);
 
995
+
 
996
+
 
997
+    s->nand = qdev_create(NULL, "onenand");
 
998
+    qdev_prop_set_uint16(s->nand, "manufacturer_id", NAND_MFR_SAMSUNG);
 
999
+    qdev_prop_set_uint16(s->nand, "device_id", 0x40);
 
1000
+    qdev_prop_set_uint16(s->nand, "version_id", 0x121);
 
1001
+    qdev_prop_set_int32(s->nand, "shift", 1);
 
1002
+    if (dmtd && dmtd->bdrv) {
 
1003
+        qdev_prop_set_drive_nofail(s->nand, "drive", dmtd->bdrv);
 
1004
+    }
 
1005
+    qdev_init_nofail(s->nand);
 
1006
+    sysbus_connect_irq(SYS_BUS_DEVICE(s->nand), 0,
 
1007
+                       qdev_get_gpio_in(s->cpu->gpio, N900_ONENAND_GPIO));
 
1008
+    omap_gpmc_attach(s->cpu->gpmc, 0,
 
1009
+                     sysbus_mmio_get_region(SYS_BUS_DEVICE(s->nand), 0));
 
1010
+
 
1011
+    if (dsd) {
 
1012
+        omap3_mmc_attach(s->cpu->omap3_mmc[1], dsd->bdrv, 0, 1);
 
1013
+    }
 
1014
+    if ((dsd = drive_get(IF_SD, 0, 1)) != NULL) {
 
1015
+        omap3_mmc_attach(s->cpu->omap3_mmc[0], dsd->bdrv, 0, 0);
 
1016
+        //qemu_irq_raise(omap2_gpio_in_get(s->cpu->gpif, N900_SDCOVER_GPIO));
 
1017
+    }
 
1018
+
 
1019
+    memory_region_init_io(ssi_iomem, NULL, &ssi_ops, 0, "n900_ssi", 0x3c00);
 
1020
+    memory_region_add_subregion(sysmem, 0x48058000, ssi_iomem);
 
1021
+
 
1022
+    s->twl4030 = twl4030_init(omap_i2c_bus(s->cpu->i2c[0]),
 
1023
+                              qdev_get_gpio_in(s->cpu->ih[0],
 
1024
+                                               OMAP_INT_3XXX_SYS_NIRQ),
 
1025
+                              NULL, n900_twl4030_keymap);
 
1026
+    twl4030_madc_attach(s->twl4030, n900_twl4030_madc_callback);
 
1027
+    i2c_bus *i2c2 = omap_i2c_bus(s->cpu->i2c[1]);
 
1028
+    s->bq2415x = i2c_create_slave(i2c2, "bq2415x", 0x6b);
 
1029
+    s->tpa6130 = i2c_create_slave(i2c2, "tpa6130", 0x60);
 
1030
+    qdev_connect_gpio_out(s->cpu->gpio, N900_HEADPHONE_EN_GPIO,
 
1031
+                          qdev_get_gpio_in(s->tpa6130, 0));
 
1032
+    i2c_bus *i2c3 = omap_i2c_bus(s->cpu->i2c[2]);
 
1033
+    s->lis302dl = i2c_create_slave(i2c3, "lis302dl", 0x1d);
 
1034
+    qdev_connect_gpio_out(s->lis302dl, 0,
 
1035
+                          qdev_get_gpio_in(s->cpu->gpio,
 
1036
+                                           N900_LIS302DL_INT1_GPIO));
 
1037
+    qdev_connect_gpio_out(s->lis302dl, 1,
 
1038
+                          qdev_get_gpio_in(s->cpu->gpio,
 
1039
+                                           N900_LIS302DL_INT2_GPIO));
 
1040
+
 
1041
+    int i;
 
1042
+    for (i = 0; i < nb_nics; i++) {
 
1043
+        if (!nd_table[i].model || !strcmp(nd_table[i].model, "smc91c111")) {
 
1044
+            break;
 
1045
+        }
 
1046
+    }
 
1047
+    if (i < nb_nics) {
 
1048
+        s->smc = qdev_create(NULL, "smc91c111");
 
1049
+        qdev_set_nic_properties(s->smc, &nd_table[i]);
 
1050
+        qdev_init_nofail(s->smc);
 
1051
+        sysbus_connect_irq(SYS_BUS_DEVICE(s->smc), 0,
 
1052
+                           qdev_get_gpio_in(s->cpu->gpio, 54));
 
1053
+        omap_gpmc_attach(s->cpu->gpmc, 1,
 
1054
+                         sysbus_mmio_get_region(SYS_BUS_DEVICE(s->smc), 0));
 
1055
+    } else {
 
1056
+        hw_error("%s: no NIC for smc91c111\n", __FUNCTION__);
 
1057
+    }
 
1058
+
 
1059
+    qemu_add_kbd_event_handler(n900_key_handler, s);
 
1060
+
 
1061
+    qemu_register_reset(n900_reset, s);
 
1062
+}
 
1063
+
 
1064
+static QEMUMachine n900_machine = {
 
1065
+    .name = "n900",
 
1066
+    .desc = "Nokia N900 (OMAP3)",
 
1067
+    .init = n900_init,
 
1068
+};
 
1069
+
 
1070
 static void nseries_register_types(void)
 
1071
 {
 
1072
+    type_register_static(&bq2415x_info);
 
1073
+    type_register_static(&tpa6130_info);
 
1074
+    type_register_static(&lis302dl_info);
 
1075
     type_register_static(&mipid_info);
 
1076
 }
 
1077
 
 
1078
@@ -1565,6 +2612,7 @@ static void nseries_machine_init(void)
 
1079
 {
 
1080
     qemu_register_machine(&n800_machine);
 
1081
     qemu_register_machine(&n810_machine);
 
1082
+    qemu_register_machine(&n900_machine);
 
1083
 }
 
1084
 
 
1085
 type_init(nseries_register_types);
 
1086
-- 
 
1087
1.8.3.2
 
1088