rp2040js 0.17.17 → 0.18.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cjs/clock/clock.d.ts +11 -11
- package/dist/cjs/clock/clock.js +2 -2
- package/dist/cjs/clock/mock-clock.d.ts +17 -17
- package/dist/cjs/clock/mock-clock.js +52 -52
- package/dist/cjs/clock/realtime-clock.d.ts +23 -23
- package/dist/cjs/clock/realtime-clock.js +73 -73
- package/dist/cjs/cortex-m0-core.d.ts +87 -87
- package/dist/cjs/cortex-m0-core.js +1251 -1251
- package/dist/cjs/gdb/gdb-connection.d.ts +11 -11
- package/dist/cjs/gdb/gdb-connection.js +57 -57
- package/dist/cjs/gdb/gdb-server.d.ts +23 -23
- package/dist/cjs/gdb/gdb-server.js +232 -232
- package/dist/cjs/gdb/gdb-tcp-server.d.ts +10 -10
- package/dist/cjs/gdb/gdb-tcp-server.js +34 -34
- package/dist/cjs/gdb/gdb-utils.d.ts +9 -9
- package/dist/cjs/gdb/gdb-utils.js +48 -48
- package/dist/cjs/gpio-pin.d.ts +56 -56
- package/dist/cjs/gpio-pin.js +216 -216
- package/dist/cjs/index.d.ts +11 -11
- package/dist/cjs/index.js +36 -36
- package/dist/cjs/interpolator.d.ts +36 -36
- package/dist/cjs/interpolator.js +150 -150
- package/dist/cjs/irq.d.ts +29 -29
- package/dist/cjs/irq.js +33 -33
- package/dist/cjs/peripherals/adc.d.ts +52 -52
- package/dist/cjs/peripherals/adc.js +261 -261
- package/dist/cjs/peripherals/busctrl.d.ts +10 -10
- package/dist/cjs/peripherals/busctrl.js +84 -84
- package/dist/cjs/peripherals/clocks.d.ts +9 -9
- package/dist/cjs/peripherals/clocks.js +42 -42
- package/dist/cjs/peripherals/dma.d.ts +109 -109
- package/dist/cjs/peripherals/dma.js +520 -520
- package/dist/cjs/peripherals/i2c.d.ts +54 -54
- package/dist/cjs/peripherals/i2c.js +458 -458
- package/dist/cjs/peripherals/io.d.ts +11 -11
- package/dist/cjs/peripherals/io.js +100 -100
- package/dist/cjs/peripherals/pads.d.ts +13 -13
- package/dist/cjs/peripherals/pads.js +58 -58
- package/dist/cjs/peripherals/peripheral.d.ts +22 -22
- package/dist/cjs/peripherals/peripheral.js +61 -61
- package/dist/cjs/peripherals/pio.d.ts +120 -120
- package/dist/cjs/peripherals/pio.js +1086 -1086
- package/dist/cjs/peripherals/ppb.d.ts +25 -25
- package/dist/cjs/peripherals/ppb.js +229 -229
- package/dist/cjs/peripherals/pwm.d.ts +65 -65
- package/dist/cjs/peripherals/pwm.js +372 -372
- package/dist/cjs/peripherals/reset.d.ts +8 -8
- package/dist/cjs/peripherals/reset.js +40 -40
- package/dist/cjs/peripherals/rtc.d.ts +10 -10
- package/dist/cjs/peripherals/rtc.js +74 -74
- package/dist/cjs/peripherals/spi.d.ts +38 -38
- package/dist/cjs/peripherals/spi.js +240 -240
- package/dist/cjs/peripherals/ssi.d.ts +6 -6
- package/dist/cjs/peripherals/ssi.js +43 -43
- package/dist/cjs/peripherals/syscfg.d.ts +5 -5
- package/dist/cjs/peripherals/syscfg.js +26 -26
- package/dist/cjs/peripherals/sysinfo.d.ts +4 -4
- package/dist/cjs/peripherals/sysinfo.js +22 -22
- package/dist/cjs/peripherals/tbman.d.ts +4 -4
- package/dist/cjs/peripherals/tbman.js +17 -17
- package/dist/cjs/peripherals/timer.d.ts +18 -18
- package/dist/cjs/peripherals/timer.js +156 -156
- package/dist/cjs/peripherals/uart.d.ts +31 -31
- package/dist/cjs/peripherals/uart.js +132 -132
- package/dist/cjs/peripherals/usb.d.ts +29 -29
- package/dist/cjs/peripherals/usb.js +309 -309
- package/dist/cjs/rp2040.d.ts +71 -71
- package/dist/cjs/rp2040.js +361 -361
- package/dist/cjs/sio.d.ts +21 -21
- package/dist/cjs/sio.js +425 -425
- package/dist/cjs/usb/cdc.d.ts +20 -20
- package/dist/cjs/usb/cdc.js +126 -126
- package/dist/cjs/usb/interfaces.d.ts +47 -47
- package/dist/cjs/usb/interfaces.js +46 -46
- package/dist/cjs/usb/setup.d.ts +5 -5
- package/dist/cjs/usb/setup.js +53 -53
- package/dist/cjs/utils/assembler.d.ts +79 -79
- package/dist/cjs/utils/assembler.js +328 -328
- package/dist/cjs/utils/bit.d.ts +3 -3
- package/dist/cjs/utils/bit.js +15 -15
- package/dist/cjs/utils/fifo.d.ts +15 -15
- package/dist/cjs/utils/fifo.js +56 -56
- package/dist/cjs/utils/logging.d.ts +23 -23
- package/dist/cjs/utils/logging.js +48 -48
- package/dist/cjs/utils/pio-assembler.d.ts +45 -45
- package/dist/cjs/utils/pio-assembler.js +87 -87
- package/dist/cjs/utils/time.d.ts +2 -2
- package/dist/cjs/utils/time.js +32 -32
- package/dist/cjs/utils/timer32.d.ts +57 -57
- package/dist/cjs/utils/timer32.js +208 -208
- package/dist/esm/clock/clock.d.ts +11 -11
- package/dist/esm/clock/clock.js +1 -1
- package/dist/esm/clock/mock-clock.d.ts +17 -17
- package/dist/esm/clock/mock-clock.js +47 -47
- package/dist/esm/clock/realtime-clock.d.ts +23 -23
- package/dist/esm/clock/realtime-clock.js +68 -68
- package/dist/esm/cortex-m0-core.d.ts +87 -87
- package/dist/esm/cortex-m0-core.js +1247 -1247
- package/dist/esm/gdb/gdb-connection.d.ts +11 -11
- package/dist/esm/gdb/gdb-connection.js +53 -53
- package/dist/esm/gdb/gdb-server.d.ts +23 -23
- package/dist/esm/gdb/gdb-server.js +228 -228
- package/dist/esm/gdb/gdb-tcp-server.d.ts +10 -10
- package/dist/esm/gdb/gdb-tcp-server.js +30 -30
- package/dist/esm/gdb/gdb-utils.d.ts +9 -9
- package/dist/esm/gdb/gdb-utils.js +36 -36
- package/dist/esm/gpio-pin.d.ts +56 -56
- package/dist/esm/gpio-pin.js +212 -212
- package/dist/esm/index.d.ts +11 -11
- package/dist/esm/index.js +11 -11
- package/dist/esm/interpolator.d.ts +36 -36
- package/dist/esm/interpolator.js +145 -145
- package/dist/esm/irq.d.ts +29 -29
- package/dist/esm/irq.js +30 -30
- package/dist/esm/peripherals/adc.d.ts +52 -52
- package/dist/esm/peripherals/adc.js +257 -257
- package/dist/esm/peripherals/busctrl.d.ts +10 -10
- package/dist/esm/peripherals/busctrl.js +80 -80
- package/dist/esm/peripherals/clocks.d.ts +9 -9
- package/dist/esm/peripherals/clocks.js +38 -38
- package/dist/esm/peripherals/dma.d.ts +109 -109
- package/dist/esm/peripherals/dma.js +515 -515
- package/dist/esm/peripherals/i2c.d.ts +54 -54
- package/dist/esm/peripherals/i2c.js +454 -454
- package/dist/esm/peripherals/io.d.ts +11 -11
- package/dist/esm/peripherals/io.js +96 -96
- package/dist/esm/peripherals/pads.d.ts +13 -13
- package/dist/esm/peripherals/pads.js +54 -54
- package/dist/esm/peripherals/peripheral.d.ts +22 -22
- package/dist/esm/peripherals/peripheral.js +55 -55
- package/dist/esm/peripherals/pio.d.ts +120 -120
- package/dist/esm/peripherals/pio.js +1081 -1081
- package/dist/esm/peripherals/ppb.d.ts +25 -25
- package/dist/esm/peripherals/ppb.js +225 -225
- package/dist/esm/peripherals/pwm.d.ts +65 -65
- package/dist/esm/peripherals/pwm.js +368 -368
- package/dist/esm/peripherals/reset.d.ts +8 -8
- package/dist/esm/peripherals/reset.js +36 -36
- package/dist/esm/peripherals/rtc.d.ts +10 -10
- package/dist/esm/peripherals/rtc.js +70 -70
- package/dist/esm/peripherals/spi.d.ts +38 -38
- package/dist/esm/peripherals/spi.js +236 -236
- package/dist/esm/peripherals/ssi.d.ts +6 -6
- package/dist/esm/peripherals/ssi.js +39 -39
- package/dist/esm/peripherals/syscfg.d.ts +5 -5
- package/dist/esm/peripherals/syscfg.js +22 -22
- package/dist/esm/peripherals/sysinfo.d.ts +4 -4
- package/dist/esm/peripherals/sysinfo.js +18 -18
- package/dist/esm/peripherals/tbman.d.ts +4 -4
- package/dist/esm/peripherals/tbman.js +13 -13
- package/dist/esm/peripherals/timer.d.ts +18 -18
- package/dist/esm/peripherals/timer.js +152 -152
- package/dist/esm/peripherals/uart.d.ts +31 -31
- package/dist/esm/peripherals/uart.js +128 -128
- package/dist/esm/peripherals/usb.d.ts +29 -29
- package/dist/esm/peripherals/usb.js +305 -305
- package/dist/esm/rp2040.d.ts +71 -71
- package/dist/esm/rp2040.js +357 -357
- package/dist/esm/sio.d.ts +21 -21
- package/dist/esm/sio.js +421 -421
- package/dist/esm/usb/cdc.d.ts +20 -20
- package/dist/esm/usb/cdc.js +121 -121
- package/dist/esm/usb/interfaces.d.ts +47 -47
- package/dist/esm/usb/interfaces.js +43 -43
- package/dist/esm/usb/setup.d.ts +5 -5
- package/dist/esm/usb/setup.js +46 -46
- package/dist/esm/utils/assembler.d.ts +79 -79
- package/dist/esm/utils/assembler.js +245 -245
- package/dist/esm/utils/bit.d.ts +3 -3
- package/dist/esm/utils/bit.js +9 -9
- package/dist/esm/utils/fifo.d.ts +15 -15
- package/dist/esm/utils/fifo.js +52 -52
- package/dist/esm/utils/logging.d.ts +23 -23
- package/dist/esm/utils/logging.js +44 -44
- package/dist/esm/utils/pio-assembler.d.ts +45 -45
- package/dist/esm/utils/pio-assembler.js +75 -75
- package/dist/esm/utils/time.d.ts +2 -2
- package/dist/esm/utils/time.js +27 -27
- package/dist/esm/utils/timer32.d.ts +57 -57
- package/dist/esm/utils/timer32.js +203 -203
- package/package.json +33 -22
- package/dist/esm/package.json +0 -1
package/dist/cjs/rp2040.js
CHANGED
|
@@ -1,361 +1,361 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.RP2040 = exports.SIO_START_ADDRESS = exports.DPRAM_START_ADDRESS = exports.APB_START_ADDRESS = exports.RAM_START_ADDRESS = exports.FLASH_START_ADDRESS = void 0;
|
|
4
|
-
const
|
|
5
|
-
const
|
|
6
|
-
const
|
|
7
|
-
const
|
|
8
|
-
const
|
|
9
|
-
const
|
|
10
|
-
const
|
|
11
|
-
const
|
|
12
|
-
const
|
|
13
|
-
const
|
|
14
|
-
const
|
|
15
|
-
const
|
|
16
|
-
const
|
|
17
|
-
const
|
|
18
|
-
const
|
|
19
|
-
const
|
|
20
|
-
const
|
|
21
|
-
const
|
|
22
|
-
const
|
|
23
|
-
const
|
|
24
|
-
const
|
|
25
|
-
const
|
|
26
|
-
const
|
|
27
|
-
const
|
|
28
|
-
const
|
|
29
|
-
const
|
|
30
|
-
const
|
|
31
|
-
exports.FLASH_START_ADDRESS = 0x10000000;
|
|
32
|
-
exports.RAM_START_ADDRESS = 0x20000000;
|
|
33
|
-
exports.APB_START_ADDRESS = 0x40000000;
|
|
34
|
-
exports.DPRAM_START_ADDRESS = 0x50100000;
|
|
35
|
-
exports.SIO_START_ADDRESS = 0xd0000000;
|
|
36
|
-
const LOG_NAME = 'RP2040';
|
|
37
|
-
const KB = 1024;
|
|
38
|
-
const MB = 1024 * KB;
|
|
39
|
-
const MHz = 1000000;
|
|
40
|
-
class RP2040 {
|
|
41
|
-
constructor(clock = new
|
|
42
|
-
this.clock = clock;
|
|
43
|
-
this.bootrom = new Uint32Array(4 * KB);
|
|
44
|
-
this.sram = new Uint8Array(264 * KB);
|
|
45
|
-
this.sramView = new DataView(this.sram.buffer);
|
|
46
|
-
this.flash = new Uint8Array(16 * MB);
|
|
47
|
-
this.flash16 = new Uint16Array(this.flash.buffer);
|
|
48
|
-
this.flashView = new DataView(this.flash.buffer);
|
|
49
|
-
this.usbDPRAM = new Uint8Array(4 * KB);
|
|
50
|
-
this.usbDPRAMView = new DataView(this.usbDPRAM.buffer);
|
|
51
|
-
this.core = new
|
|
52
|
-
/* Clocks */
|
|
53
|
-
this.clkSys = 125 * MHz;
|
|
54
|
-
this.clkPeri = 125 * MHz;
|
|
55
|
-
this.ppb = new
|
|
56
|
-
this.sio = new
|
|
57
|
-
this.uart = [
|
|
58
|
-
new
|
|
59
|
-
rx:
|
|
60
|
-
tx:
|
|
61
|
-
}),
|
|
62
|
-
new
|
|
63
|
-
rx:
|
|
64
|
-
tx:
|
|
65
|
-
}),
|
|
66
|
-
];
|
|
67
|
-
this.i2c = [new
|
|
68
|
-
this.pwm = new
|
|
69
|
-
this.adc = new
|
|
70
|
-
this.gpio = [
|
|
71
|
-
new
|
|
72
|
-
new
|
|
73
|
-
new
|
|
74
|
-
new
|
|
75
|
-
new
|
|
76
|
-
new
|
|
77
|
-
new
|
|
78
|
-
new
|
|
79
|
-
new
|
|
80
|
-
new
|
|
81
|
-
new
|
|
82
|
-
new
|
|
83
|
-
new
|
|
84
|
-
new
|
|
85
|
-
new
|
|
86
|
-
new
|
|
87
|
-
new
|
|
88
|
-
new
|
|
89
|
-
new
|
|
90
|
-
new
|
|
91
|
-
new
|
|
92
|
-
new
|
|
93
|
-
new
|
|
94
|
-
new
|
|
95
|
-
new
|
|
96
|
-
new
|
|
97
|
-
new
|
|
98
|
-
new
|
|
99
|
-
new
|
|
100
|
-
new
|
|
101
|
-
];
|
|
102
|
-
this.qspi = [
|
|
103
|
-
new
|
|
104
|
-
new
|
|
105
|
-
new
|
|
106
|
-
new
|
|
107
|
-
new
|
|
108
|
-
new
|
|
109
|
-
];
|
|
110
|
-
this.dma = new
|
|
111
|
-
this.pio = [
|
|
112
|
-
new
|
|
113
|
-
new
|
|
114
|
-
];
|
|
115
|
-
this.usbCtrl = new
|
|
116
|
-
this.spi = [
|
|
117
|
-
new
|
|
118
|
-
rx:
|
|
119
|
-
tx:
|
|
120
|
-
}),
|
|
121
|
-
new
|
|
122
|
-
rx:
|
|
123
|
-
tx:
|
|
124
|
-
}),
|
|
125
|
-
];
|
|
126
|
-
this.stopped = true;
|
|
127
|
-
this.logger = new
|
|
128
|
-
this.executeTimer = null;
|
|
129
|
-
this.peripherals = {
|
|
130
|
-
0x18000: new
|
|
131
|
-
0x40000: new
|
|
132
|
-
0x40004: new
|
|
133
|
-
0x40008: new
|
|
134
|
-
0x4000c: new
|
|
135
|
-
0x40010: new
|
|
136
|
-
0x40014: new
|
|
137
|
-
0x40018: new
|
|
138
|
-
0x4001c: new
|
|
139
|
-
0x40020: new
|
|
140
|
-
0x40024: new
|
|
141
|
-
0x40028: new
|
|
142
|
-
0x4002c: new
|
|
143
|
-
0x40030: new
|
|
144
|
-
0x40034: this.uart[0],
|
|
145
|
-
0x40038: this.uart[1],
|
|
146
|
-
0x4003c: this.spi[0],
|
|
147
|
-
0x40040: this.spi[1],
|
|
148
|
-
0x40044: this.i2c[0],
|
|
149
|
-
0x40048: this.i2c[1],
|
|
150
|
-
0x4004c: this.adc,
|
|
151
|
-
0x40050: this.pwm,
|
|
152
|
-
0x40054: new
|
|
153
|
-
0x40058: new
|
|
154
|
-
0x4005c: new
|
|
155
|
-
0x40060: new
|
|
156
|
-
0x40064: new
|
|
157
|
-
0x4006c: new
|
|
158
|
-
0x50000: this.dma,
|
|
159
|
-
0x50110: this.usbCtrl,
|
|
160
|
-
0x50200: this.pio[0],
|
|
161
|
-
0x50300: this.pio[1],
|
|
162
|
-
};
|
|
163
|
-
// Debugging
|
|
164
|
-
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
165
|
-
this.onBreak = (code) => {
|
|
166
|
-
// TODO: raise HardFault exception
|
|
167
|
-
// console.error('Breakpoint!', code);
|
|
168
|
-
this.stopped = true;
|
|
169
|
-
};
|
|
170
|
-
this.reset();
|
|
171
|
-
}
|
|
172
|
-
loadBootrom(bootromData) {
|
|
173
|
-
this.bootrom.set(bootromData);
|
|
174
|
-
this.reset();
|
|
175
|
-
}
|
|
176
|
-
reset() {
|
|
177
|
-
this.core.reset();
|
|
178
|
-
this.pwm.reset();
|
|
179
|
-
this.flash.fill(0xff);
|
|
180
|
-
}
|
|
181
|
-
readUint32(address) {
|
|
182
|
-
address = address >>> 0; // round to 32-bits, unsigned
|
|
183
|
-
if (address & 0x3) {
|
|
184
|
-
this.logger.error(LOG_NAME, `read from address ${address.toString(16)}, which is not 32 bit aligned`);
|
|
185
|
-
}
|
|
186
|
-
const { bootrom } = this;
|
|
187
|
-
if (address < bootrom.length * 4) {
|
|
188
|
-
return bootrom[address / 4];
|
|
189
|
-
}
|
|
190
|
-
else if (address >= exports.FLASH_START_ADDRESS &&
|
|
191
|
-
address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
192
|
-
return this.flashView.getUint32(address - exports.FLASH_START_ADDRESS, true);
|
|
193
|
-
}
|
|
194
|
-
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
195
|
-
return this.sramView.getUint32(address - exports.RAM_START_ADDRESS, true);
|
|
196
|
-
}
|
|
197
|
-
else if (address >= exports.DPRAM_START_ADDRESS &&
|
|
198
|
-
address < exports.DPRAM_START_ADDRESS + this.usbDPRAM.length) {
|
|
199
|
-
return this.usbDPRAMView.getUint32(address - exports.DPRAM_START_ADDRESS, true);
|
|
200
|
-
}
|
|
201
|
-
else if (address >>> 12 === 0xe000e) {
|
|
202
|
-
return this.ppb.readUint32(address & 0xfff);
|
|
203
|
-
}
|
|
204
|
-
else if (address >= exports.SIO_START_ADDRESS && address < exports.SIO_START_ADDRESS + 0x10000000) {
|
|
205
|
-
return this.sio.readUint32(address - exports.SIO_START_ADDRESS);
|
|
206
|
-
}
|
|
207
|
-
const peripheral = this.findPeripheral(address);
|
|
208
|
-
if (peripheral) {
|
|
209
|
-
return peripheral.readUint32(address & 0x3fff);
|
|
210
|
-
}
|
|
211
|
-
this.logger.warn(LOG_NAME, `Read from invalid memory address: ${address.toString(16)}`);
|
|
212
|
-
return 0xffffffff;
|
|
213
|
-
}
|
|
214
|
-
findPeripheral(address) {
|
|
215
|
-
return this.peripherals[(address >>> 14) << 2];
|
|
216
|
-
}
|
|
217
|
-
/** We assume the address is 16-bit aligned */
|
|
218
|
-
readUint16(address) {
|
|
219
|
-
if (address >= exports.FLASH_START_ADDRESS && address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
220
|
-
return this.flashView.getUint16(address - exports.FLASH_START_ADDRESS, true);
|
|
221
|
-
}
|
|
222
|
-
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
223
|
-
return this.sramView.getUint16(address - exports.RAM_START_ADDRESS, true);
|
|
224
|
-
}
|
|
225
|
-
const value = this.readUint32(address & 0xfffffffc);
|
|
226
|
-
return address & 0x2 ? (value & 0xffff0000) >>> 16 : value & 0xffff;
|
|
227
|
-
}
|
|
228
|
-
readUint8(address) {
|
|
229
|
-
if (address >= exports.FLASH_START_ADDRESS && address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
230
|
-
return this.flash[address - exports.FLASH_START_ADDRESS];
|
|
231
|
-
}
|
|
232
|
-
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
233
|
-
return this.sram[address - exports.RAM_START_ADDRESS];
|
|
234
|
-
}
|
|
235
|
-
const value = this.readUint16(address & 0xfffffffe);
|
|
236
|
-
return (address & 0x1 ? (value & 0xff00) >>> 8 : value & 0xff) >>> 0;
|
|
237
|
-
}
|
|
238
|
-
writeUint32(address, value) {
|
|
239
|
-
address = address >>> 0;
|
|
240
|
-
const { bootrom } = this;
|
|
241
|
-
const peripheral = this.findPeripheral(address);
|
|
242
|
-
if (peripheral) {
|
|
243
|
-
const atomicType = (address & 0x3000) >> 12;
|
|
244
|
-
const offset = address & 0xfff;
|
|
245
|
-
peripheral.writeUint32Atomic(offset, value, atomicType);
|
|
246
|
-
}
|
|
247
|
-
else if (address < bootrom.length * 4) {
|
|
248
|
-
bootrom[address / 4] = value;
|
|
249
|
-
}
|
|
250
|
-
else if (address >= exports.FLASH_START_ADDRESS &&
|
|
251
|
-
address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
252
|
-
this.flashView.setUint32(address - exports.FLASH_START_ADDRESS, value, true);
|
|
253
|
-
}
|
|
254
|
-
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
255
|
-
this.sramView.setUint32(address - exports.RAM_START_ADDRESS, value, true);
|
|
256
|
-
}
|
|
257
|
-
else if (address >= exports.DPRAM_START_ADDRESS &&
|
|
258
|
-
address < exports.DPRAM_START_ADDRESS + this.usbDPRAM.length) {
|
|
259
|
-
const offset = address - exports.DPRAM_START_ADDRESS;
|
|
260
|
-
this.usbDPRAMView.setUint32(offset, value, true);
|
|
261
|
-
this.usbCtrl.DPRAMUpdated(offset, value);
|
|
262
|
-
}
|
|
263
|
-
else if (address >= exports.SIO_START_ADDRESS && address < exports.SIO_START_ADDRESS + 0x10000000) {
|
|
264
|
-
this.sio.writeUint32(address - exports.SIO_START_ADDRESS, value);
|
|
265
|
-
}
|
|
266
|
-
else if (address >>> 12 === 0xe000e) {
|
|
267
|
-
this.ppb.writeUint32(address & 0xfff, value);
|
|
268
|
-
}
|
|
269
|
-
else {
|
|
270
|
-
this.logger.warn(LOG_NAME, `Write to undefined address: ${address.toString(16)}`);
|
|
271
|
-
}
|
|
272
|
-
}
|
|
273
|
-
writeUint8(address, value) {
|
|
274
|
-
if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
275
|
-
this.sram[address - exports.RAM_START_ADDRESS] = value;
|
|
276
|
-
return;
|
|
277
|
-
}
|
|
278
|
-
const alignedAddress = (address & 0xfffffffc) >>> 0;
|
|
279
|
-
const offset = address & 0x3;
|
|
280
|
-
const peripheral = this.findPeripheral(address);
|
|
281
|
-
if (peripheral) {
|
|
282
|
-
const atomicType = (alignedAddress & 0x3000) >> 12;
|
|
283
|
-
const offset = alignedAddress & 0xfff;
|
|
284
|
-
peripheral.writeUint32Atomic(offset, (value & 0xff) | ((value & 0xff) << 8) | ((value & 0xff) << 16) | ((value & 0xff) << 24), atomicType);
|
|
285
|
-
return;
|
|
286
|
-
}
|
|
287
|
-
const originalValue = this.readUint32(alignedAddress);
|
|
288
|
-
const newValue = new Uint32Array([originalValue]);
|
|
289
|
-
new DataView(newValue.buffer).setUint8(offset, value);
|
|
290
|
-
this.writeUint32(alignedAddress, newValue[0]);
|
|
291
|
-
}
|
|
292
|
-
writeUint16(address, value) {
|
|
293
|
-
// we assume that addess is 16-bit aligned.
|
|
294
|
-
// Ideally we should generate a fault if not!
|
|
295
|
-
if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
296
|
-
this.sramView.setUint16(address - exports.RAM_START_ADDRESS, value, true);
|
|
297
|
-
return;
|
|
298
|
-
}
|
|
299
|
-
const alignedAddress = (address & 0xfffffffc) >>> 0;
|
|
300
|
-
const offset = address & 0x3;
|
|
301
|
-
const peripheral = this.findPeripheral(address);
|
|
302
|
-
if (peripheral) {
|
|
303
|
-
const atomicType = (alignedAddress & 0x3000) >> 12;
|
|
304
|
-
const offset = alignedAddress & 0xfff;
|
|
305
|
-
peripheral.writeUint32Atomic(offset, (value & 0xffff) | ((value & 0xffff) << 16), atomicType);
|
|
306
|
-
return;
|
|
307
|
-
}
|
|
308
|
-
const originalValue = this.readUint32(alignedAddress);
|
|
309
|
-
const newValue = new Uint32Array([originalValue]);
|
|
310
|
-
new DataView(newValue.buffer).setUint16(offset, value, true);
|
|
311
|
-
this.writeUint32(alignedAddress, newValue[0]);
|
|
312
|
-
}
|
|
313
|
-
get gpioValues() {
|
|
314
|
-
const { gpio } = this;
|
|
315
|
-
let result = 0;
|
|
316
|
-
for (let gpioIndex = 0; gpioIndex < gpio.length; gpioIndex++) {
|
|
317
|
-
if (gpio[gpioIndex].inputValue) {
|
|
318
|
-
result |= 1 << gpioIndex;
|
|
319
|
-
}
|
|
320
|
-
}
|
|
321
|
-
return result;
|
|
322
|
-
}
|
|
323
|
-
setInterrupt(irq, value) {
|
|
324
|
-
this.core.setInterrupt(irq, value);
|
|
325
|
-
}
|
|
326
|
-
updateIOInterrupt() {
|
|
327
|
-
let interruptValue = false;
|
|
328
|
-
for (const pin of this.gpio) {
|
|
329
|
-
if (pin.irqValue) {
|
|
330
|
-
interruptValue = true;
|
|
331
|
-
}
|
|
332
|
-
}
|
|
333
|
-
this.setInterrupt(
|
|
334
|
-
}
|
|
335
|
-
step() {
|
|
336
|
-
this.core.executeInstruction();
|
|
337
|
-
}
|
|
338
|
-
execute() {
|
|
339
|
-
this.clock.resume();
|
|
340
|
-
this.executeTimer = null;
|
|
341
|
-
this.stopped = false;
|
|
342
|
-
for (let i = 0; i < 100000 && !this.stopped && !this.core.waiting; i++) {
|
|
343
|
-
this.core.executeInstruction();
|
|
344
|
-
}
|
|
345
|
-
if (!this.stopped) {
|
|
346
|
-
this.executeTimer = setTimeout(() => this.execute(), 0);
|
|
347
|
-
}
|
|
348
|
-
}
|
|
349
|
-
stop() {
|
|
350
|
-
this.stopped = true;
|
|
351
|
-
if (this.executeTimer != null) {
|
|
352
|
-
clearTimeout(this.executeTimer);
|
|
353
|
-
this.executeTimer = null;
|
|
354
|
-
}
|
|
355
|
-
this.clock.pause();
|
|
356
|
-
}
|
|
357
|
-
get executing() {
|
|
358
|
-
return !this.stopped;
|
|
359
|
-
}
|
|
360
|
-
}
|
|
361
|
-
exports.RP2040 = RP2040;
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.RP2040 = exports.SIO_START_ADDRESS = exports.DPRAM_START_ADDRESS = exports.APB_START_ADDRESS = exports.RAM_START_ADDRESS = exports.FLASH_START_ADDRESS = void 0;
|
|
4
|
+
const realtime_clock_js_1 = require("./clock/realtime-clock.js");
|
|
5
|
+
const cortex_m0_core_js_1 = require("./cortex-m0-core.js");
|
|
6
|
+
const gpio_pin_js_1 = require("./gpio-pin.js");
|
|
7
|
+
const irq_js_1 = require("./irq.js");
|
|
8
|
+
const adc_js_1 = require("./peripherals/adc.js");
|
|
9
|
+
const busctrl_js_1 = require("./peripherals/busctrl.js");
|
|
10
|
+
const clocks_js_1 = require("./peripherals/clocks.js");
|
|
11
|
+
const dma_js_1 = require("./peripherals/dma.js");
|
|
12
|
+
const i2c_js_1 = require("./peripherals/i2c.js");
|
|
13
|
+
const io_js_1 = require("./peripherals/io.js");
|
|
14
|
+
const pads_js_1 = require("./peripherals/pads.js");
|
|
15
|
+
const peripheral_js_1 = require("./peripherals/peripheral.js");
|
|
16
|
+
const pio_js_1 = require("./peripherals/pio.js");
|
|
17
|
+
const ppb_js_1 = require("./peripherals/ppb.js");
|
|
18
|
+
const pwm_js_1 = require("./peripherals/pwm.js");
|
|
19
|
+
const reset_js_1 = require("./peripherals/reset.js");
|
|
20
|
+
const rtc_js_1 = require("./peripherals/rtc.js");
|
|
21
|
+
const spi_js_1 = require("./peripherals/spi.js");
|
|
22
|
+
const ssi_js_1 = require("./peripherals/ssi.js");
|
|
23
|
+
const syscfg_js_1 = require("./peripherals/syscfg.js");
|
|
24
|
+
const sysinfo_js_1 = require("./peripherals/sysinfo.js");
|
|
25
|
+
const tbman_js_1 = require("./peripherals/tbman.js");
|
|
26
|
+
const timer_js_1 = require("./peripherals/timer.js");
|
|
27
|
+
const uart_js_1 = require("./peripherals/uart.js");
|
|
28
|
+
const usb_js_1 = require("./peripherals/usb.js");
|
|
29
|
+
const sio_js_1 = require("./sio.js");
|
|
30
|
+
const logging_js_1 = require("./utils/logging.js");
|
|
31
|
+
exports.FLASH_START_ADDRESS = 0x10000000;
|
|
32
|
+
exports.RAM_START_ADDRESS = 0x20000000;
|
|
33
|
+
exports.APB_START_ADDRESS = 0x40000000;
|
|
34
|
+
exports.DPRAM_START_ADDRESS = 0x50100000;
|
|
35
|
+
exports.SIO_START_ADDRESS = 0xd0000000;
|
|
36
|
+
const LOG_NAME = 'RP2040';
|
|
37
|
+
const KB = 1024;
|
|
38
|
+
const MB = 1024 * KB;
|
|
39
|
+
const MHz = 1000000;
|
|
40
|
+
class RP2040 {
|
|
41
|
+
constructor(clock = new realtime_clock_js_1.RealtimeClock()) {
|
|
42
|
+
this.clock = clock;
|
|
43
|
+
this.bootrom = new Uint32Array(4 * KB);
|
|
44
|
+
this.sram = new Uint8Array(264 * KB);
|
|
45
|
+
this.sramView = new DataView(this.sram.buffer);
|
|
46
|
+
this.flash = new Uint8Array(16 * MB);
|
|
47
|
+
this.flash16 = new Uint16Array(this.flash.buffer);
|
|
48
|
+
this.flashView = new DataView(this.flash.buffer);
|
|
49
|
+
this.usbDPRAM = new Uint8Array(4 * KB);
|
|
50
|
+
this.usbDPRAMView = new DataView(this.usbDPRAM.buffer);
|
|
51
|
+
this.core = new cortex_m0_core_js_1.CortexM0Core(this);
|
|
52
|
+
/* Clocks */
|
|
53
|
+
this.clkSys = 125 * MHz;
|
|
54
|
+
this.clkPeri = 125 * MHz;
|
|
55
|
+
this.ppb = new ppb_js_1.RPPPB(this, 'PPB');
|
|
56
|
+
this.sio = new sio_js_1.RPSIO(this);
|
|
57
|
+
this.uart = [
|
|
58
|
+
new uart_js_1.RPUART(this, 'UART0', irq_js_1.IRQ.UART0, {
|
|
59
|
+
rx: dma_js_1.DREQChannel.DREQ_UART0_RX,
|
|
60
|
+
tx: dma_js_1.DREQChannel.DREQ_UART0_TX,
|
|
61
|
+
}),
|
|
62
|
+
new uart_js_1.RPUART(this, 'UART1', irq_js_1.IRQ.UART1, {
|
|
63
|
+
rx: dma_js_1.DREQChannel.DREQ_UART1_RX,
|
|
64
|
+
tx: dma_js_1.DREQChannel.DREQ_UART1_TX,
|
|
65
|
+
}),
|
|
66
|
+
];
|
|
67
|
+
this.i2c = [new i2c_js_1.RPI2C(this, 'I2C0', irq_js_1.IRQ.I2C0), new i2c_js_1.RPI2C(this, 'I2C1', irq_js_1.IRQ.I2C1)];
|
|
68
|
+
this.pwm = new pwm_js_1.RPPWM(this, 'PWM_BASE');
|
|
69
|
+
this.adc = new adc_js_1.RPADC(this, 'ADC');
|
|
70
|
+
this.gpio = [
|
|
71
|
+
new gpio_pin_js_1.GPIOPin(this, 0),
|
|
72
|
+
new gpio_pin_js_1.GPIOPin(this, 1),
|
|
73
|
+
new gpio_pin_js_1.GPIOPin(this, 2),
|
|
74
|
+
new gpio_pin_js_1.GPIOPin(this, 3),
|
|
75
|
+
new gpio_pin_js_1.GPIOPin(this, 4),
|
|
76
|
+
new gpio_pin_js_1.GPIOPin(this, 5),
|
|
77
|
+
new gpio_pin_js_1.GPIOPin(this, 6),
|
|
78
|
+
new gpio_pin_js_1.GPIOPin(this, 7),
|
|
79
|
+
new gpio_pin_js_1.GPIOPin(this, 8),
|
|
80
|
+
new gpio_pin_js_1.GPIOPin(this, 9),
|
|
81
|
+
new gpio_pin_js_1.GPIOPin(this, 10),
|
|
82
|
+
new gpio_pin_js_1.GPIOPin(this, 11),
|
|
83
|
+
new gpio_pin_js_1.GPIOPin(this, 12),
|
|
84
|
+
new gpio_pin_js_1.GPIOPin(this, 13),
|
|
85
|
+
new gpio_pin_js_1.GPIOPin(this, 14),
|
|
86
|
+
new gpio_pin_js_1.GPIOPin(this, 15),
|
|
87
|
+
new gpio_pin_js_1.GPIOPin(this, 16),
|
|
88
|
+
new gpio_pin_js_1.GPIOPin(this, 17),
|
|
89
|
+
new gpio_pin_js_1.GPIOPin(this, 18),
|
|
90
|
+
new gpio_pin_js_1.GPIOPin(this, 19),
|
|
91
|
+
new gpio_pin_js_1.GPIOPin(this, 20),
|
|
92
|
+
new gpio_pin_js_1.GPIOPin(this, 21),
|
|
93
|
+
new gpio_pin_js_1.GPIOPin(this, 22),
|
|
94
|
+
new gpio_pin_js_1.GPIOPin(this, 23),
|
|
95
|
+
new gpio_pin_js_1.GPIOPin(this, 24),
|
|
96
|
+
new gpio_pin_js_1.GPIOPin(this, 25),
|
|
97
|
+
new gpio_pin_js_1.GPIOPin(this, 26),
|
|
98
|
+
new gpio_pin_js_1.GPIOPin(this, 27),
|
|
99
|
+
new gpio_pin_js_1.GPIOPin(this, 28),
|
|
100
|
+
new gpio_pin_js_1.GPIOPin(this, 29),
|
|
101
|
+
];
|
|
102
|
+
this.qspi = [
|
|
103
|
+
new gpio_pin_js_1.GPIOPin(this, 0, 'SCLK'),
|
|
104
|
+
new gpio_pin_js_1.GPIOPin(this, 1, 'SS'),
|
|
105
|
+
new gpio_pin_js_1.GPIOPin(this, 2, 'SD0'),
|
|
106
|
+
new gpio_pin_js_1.GPIOPin(this, 3, 'SD1'),
|
|
107
|
+
new gpio_pin_js_1.GPIOPin(this, 4, 'SD2'),
|
|
108
|
+
new gpio_pin_js_1.GPIOPin(this, 5, 'SD3'),
|
|
109
|
+
];
|
|
110
|
+
this.dma = new dma_js_1.RPDMA(this, 'DMA');
|
|
111
|
+
this.pio = [
|
|
112
|
+
new pio_js_1.RPPIO(this, 'PIO0', irq_js_1.IRQ.PIO0_IRQ0, 0),
|
|
113
|
+
new pio_js_1.RPPIO(this, 'PIO1', irq_js_1.IRQ.PIO1_IRQ0, 1),
|
|
114
|
+
];
|
|
115
|
+
this.usbCtrl = new usb_js_1.RPUSBController(this, 'USB');
|
|
116
|
+
this.spi = [
|
|
117
|
+
new spi_js_1.RPSPI(this, 'SPI0', irq_js_1.IRQ.SPI0, {
|
|
118
|
+
rx: dma_js_1.DREQChannel.DREQ_SPI0_RX,
|
|
119
|
+
tx: dma_js_1.DREQChannel.DREQ_SPI0_TX,
|
|
120
|
+
}),
|
|
121
|
+
new spi_js_1.RPSPI(this, 'SPI1', irq_js_1.IRQ.SPI1, {
|
|
122
|
+
rx: dma_js_1.DREQChannel.DREQ_SPI1_RX,
|
|
123
|
+
tx: dma_js_1.DREQChannel.DREQ_SPI1_TX,
|
|
124
|
+
}),
|
|
125
|
+
];
|
|
126
|
+
this.stopped = true;
|
|
127
|
+
this.logger = new logging_js_1.ConsoleLogger(logging_js_1.LogLevel.Debug, true);
|
|
128
|
+
this.executeTimer = null;
|
|
129
|
+
this.peripherals = {
|
|
130
|
+
0x18000: new ssi_js_1.RPSSI(this, 'SSI'),
|
|
131
|
+
0x40000: new sysinfo_js_1.RP2040SysInfo(this, 'SYSINFO_BASE'),
|
|
132
|
+
0x40004: new syscfg_js_1.RP2040SysCfg(this, 'SYSCFG'),
|
|
133
|
+
0x40008: new clocks_js_1.RPClocks(this, 'CLOCKS_BASE'),
|
|
134
|
+
0x4000c: new reset_js_1.RPReset(this, 'RESETS_BASE'),
|
|
135
|
+
0x40010: new peripheral_js_1.UnimplementedPeripheral(this, 'PSM_BASE'),
|
|
136
|
+
0x40014: new io_js_1.RPIO(this, 'IO_BANK0_BASE'),
|
|
137
|
+
0x40018: new peripheral_js_1.UnimplementedPeripheral(this, 'IO_QSPI_BASE'),
|
|
138
|
+
0x4001c: new pads_js_1.RPPADS(this, 'PADS_BANK0_BASE', 'bank0'),
|
|
139
|
+
0x40020: new pads_js_1.RPPADS(this, 'PADS_QSPI_BASE', 'qspi'),
|
|
140
|
+
0x40024: new peripheral_js_1.UnimplementedPeripheral(this, 'XOSC_BASE'),
|
|
141
|
+
0x40028: new peripheral_js_1.UnimplementedPeripheral(this, 'PLL_SYS_BASE'),
|
|
142
|
+
0x4002c: new peripheral_js_1.UnimplementedPeripheral(this, 'PLL_USB_BASE'),
|
|
143
|
+
0x40030: new busctrl_js_1.RPBUSCTRL(this, 'BUSCTRL_BASE'),
|
|
144
|
+
0x40034: this.uart[0],
|
|
145
|
+
0x40038: this.uart[1],
|
|
146
|
+
0x4003c: this.spi[0],
|
|
147
|
+
0x40040: this.spi[1],
|
|
148
|
+
0x40044: this.i2c[0],
|
|
149
|
+
0x40048: this.i2c[1],
|
|
150
|
+
0x4004c: this.adc,
|
|
151
|
+
0x40050: this.pwm,
|
|
152
|
+
0x40054: new timer_js_1.RPTimer(this, 'TIMER_BASE'),
|
|
153
|
+
0x40058: new peripheral_js_1.UnimplementedPeripheral(this, 'WATCHDOG_BASE'),
|
|
154
|
+
0x4005c: new rtc_js_1.RP2040RTC(this, 'RTC_BASE'),
|
|
155
|
+
0x40060: new peripheral_js_1.UnimplementedPeripheral(this, 'ROSC_BASE'),
|
|
156
|
+
0x40064: new peripheral_js_1.UnimplementedPeripheral(this, 'VREG_AND_CHIP_RESET_BASE'),
|
|
157
|
+
0x4006c: new tbman_js_1.RPTBMAN(this, 'TBMAN_BASE'),
|
|
158
|
+
0x50000: this.dma,
|
|
159
|
+
0x50110: this.usbCtrl,
|
|
160
|
+
0x50200: this.pio[0],
|
|
161
|
+
0x50300: this.pio[1],
|
|
162
|
+
};
|
|
163
|
+
// Debugging
|
|
164
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
165
|
+
this.onBreak = (code) => {
|
|
166
|
+
// TODO: raise HardFault exception
|
|
167
|
+
// console.error('Breakpoint!', code);
|
|
168
|
+
this.stopped = true;
|
|
169
|
+
};
|
|
170
|
+
this.reset();
|
|
171
|
+
}
|
|
172
|
+
loadBootrom(bootromData) {
|
|
173
|
+
this.bootrom.set(bootromData);
|
|
174
|
+
this.reset();
|
|
175
|
+
}
|
|
176
|
+
reset() {
|
|
177
|
+
this.core.reset();
|
|
178
|
+
this.pwm.reset();
|
|
179
|
+
this.flash.fill(0xff);
|
|
180
|
+
}
|
|
181
|
+
readUint32(address) {
|
|
182
|
+
address = address >>> 0; // round to 32-bits, unsigned
|
|
183
|
+
if (address & 0x3) {
|
|
184
|
+
this.logger.error(LOG_NAME, `read from address ${address.toString(16)}, which is not 32 bit aligned`);
|
|
185
|
+
}
|
|
186
|
+
const { bootrom } = this;
|
|
187
|
+
if (address < bootrom.length * 4) {
|
|
188
|
+
return bootrom[address / 4];
|
|
189
|
+
}
|
|
190
|
+
else if (address >= exports.FLASH_START_ADDRESS &&
|
|
191
|
+
address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
192
|
+
return this.flashView.getUint32(address - exports.FLASH_START_ADDRESS, true);
|
|
193
|
+
}
|
|
194
|
+
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
195
|
+
return this.sramView.getUint32(address - exports.RAM_START_ADDRESS, true);
|
|
196
|
+
}
|
|
197
|
+
else if (address >= exports.DPRAM_START_ADDRESS &&
|
|
198
|
+
address < exports.DPRAM_START_ADDRESS + this.usbDPRAM.length) {
|
|
199
|
+
return this.usbDPRAMView.getUint32(address - exports.DPRAM_START_ADDRESS, true);
|
|
200
|
+
}
|
|
201
|
+
else if (address >>> 12 === 0xe000e) {
|
|
202
|
+
return this.ppb.readUint32(address & 0xfff);
|
|
203
|
+
}
|
|
204
|
+
else if (address >= exports.SIO_START_ADDRESS && address < exports.SIO_START_ADDRESS + 0x10000000) {
|
|
205
|
+
return this.sio.readUint32(address - exports.SIO_START_ADDRESS);
|
|
206
|
+
}
|
|
207
|
+
const peripheral = this.findPeripheral(address);
|
|
208
|
+
if (peripheral) {
|
|
209
|
+
return peripheral.readUint32(address & 0x3fff);
|
|
210
|
+
}
|
|
211
|
+
this.logger.warn(LOG_NAME, `Read from invalid memory address: ${address.toString(16)}`);
|
|
212
|
+
return 0xffffffff;
|
|
213
|
+
}
|
|
214
|
+
findPeripheral(address) {
|
|
215
|
+
return this.peripherals[(address >>> 14) << 2];
|
|
216
|
+
}
|
|
217
|
+
/** We assume the address is 16-bit aligned */
|
|
218
|
+
readUint16(address) {
|
|
219
|
+
if (address >= exports.FLASH_START_ADDRESS && address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
220
|
+
return this.flashView.getUint16(address - exports.FLASH_START_ADDRESS, true);
|
|
221
|
+
}
|
|
222
|
+
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
223
|
+
return this.sramView.getUint16(address - exports.RAM_START_ADDRESS, true);
|
|
224
|
+
}
|
|
225
|
+
const value = this.readUint32(address & 0xfffffffc);
|
|
226
|
+
return address & 0x2 ? (value & 0xffff0000) >>> 16 : value & 0xffff;
|
|
227
|
+
}
|
|
228
|
+
readUint8(address) {
|
|
229
|
+
if (address >= exports.FLASH_START_ADDRESS && address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
230
|
+
return this.flash[address - exports.FLASH_START_ADDRESS];
|
|
231
|
+
}
|
|
232
|
+
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
233
|
+
return this.sram[address - exports.RAM_START_ADDRESS];
|
|
234
|
+
}
|
|
235
|
+
const value = this.readUint16(address & 0xfffffffe);
|
|
236
|
+
return (address & 0x1 ? (value & 0xff00) >>> 8 : value & 0xff) >>> 0;
|
|
237
|
+
}
|
|
238
|
+
writeUint32(address, value) {
|
|
239
|
+
address = address >>> 0;
|
|
240
|
+
const { bootrom } = this;
|
|
241
|
+
const peripheral = this.findPeripheral(address);
|
|
242
|
+
if (peripheral) {
|
|
243
|
+
const atomicType = (address & 0x3000) >> 12;
|
|
244
|
+
const offset = address & 0xfff;
|
|
245
|
+
peripheral.writeUint32Atomic(offset, value, atomicType);
|
|
246
|
+
}
|
|
247
|
+
else if (address < bootrom.length * 4) {
|
|
248
|
+
bootrom[address / 4] = value;
|
|
249
|
+
}
|
|
250
|
+
else if (address >= exports.FLASH_START_ADDRESS &&
|
|
251
|
+
address < exports.FLASH_START_ADDRESS + this.flash.length) {
|
|
252
|
+
this.flashView.setUint32(address - exports.FLASH_START_ADDRESS, value, true);
|
|
253
|
+
}
|
|
254
|
+
else if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
255
|
+
this.sramView.setUint32(address - exports.RAM_START_ADDRESS, value, true);
|
|
256
|
+
}
|
|
257
|
+
else if (address >= exports.DPRAM_START_ADDRESS &&
|
|
258
|
+
address < exports.DPRAM_START_ADDRESS + this.usbDPRAM.length) {
|
|
259
|
+
const offset = address - exports.DPRAM_START_ADDRESS;
|
|
260
|
+
this.usbDPRAMView.setUint32(offset, value, true);
|
|
261
|
+
this.usbCtrl.DPRAMUpdated(offset, value);
|
|
262
|
+
}
|
|
263
|
+
else if (address >= exports.SIO_START_ADDRESS && address < exports.SIO_START_ADDRESS + 0x10000000) {
|
|
264
|
+
this.sio.writeUint32(address - exports.SIO_START_ADDRESS, value);
|
|
265
|
+
}
|
|
266
|
+
else if (address >>> 12 === 0xe000e) {
|
|
267
|
+
this.ppb.writeUint32(address & 0xfff, value);
|
|
268
|
+
}
|
|
269
|
+
else {
|
|
270
|
+
this.logger.warn(LOG_NAME, `Write to undefined address: ${address.toString(16)}`);
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
writeUint8(address, value) {
|
|
274
|
+
if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
275
|
+
this.sram[address - exports.RAM_START_ADDRESS] = value;
|
|
276
|
+
return;
|
|
277
|
+
}
|
|
278
|
+
const alignedAddress = (address & 0xfffffffc) >>> 0;
|
|
279
|
+
const offset = address & 0x3;
|
|
280
|
+
const peripheral = this.findPeripheral(address);
|
|
281
|
+
if (peripheral) {
|
|
282
|
+
const atomicType = (alignedAddress & 0x3000) >> 12;
|
|
283
|
+
const offset = alignedAddress & 0xfff;
|
|
284
|
+
peripheral.writeUint32Atomic(offset, (value & 0xff) | ((value & 0xff) << 8) | ((value & 0xff) << 16) | ((value & 0xff) << 24), atomicType);
|
|
285
|
+
return;
|
|
286
|
+
}
|
|
287
|
+
const originalValue = this.readUint32(alignedAddress);
|
|
288
|
+
const newValue = new Uint32Array([originalValue]);
|
|
289
|
+
new DataView(newValue.buffer).setUint8(offset, value);
|
|
290
|
+
this.writeUint32(alignedAddress, newValue[0]);
|
|
291
|
+
}
|
|
292
|
+
writeUint16(address, value) {
|
|
293
|
+
// we assume that addess is 16-bit aligned.
|
|
294
|
+
// Ideally we should generate a fault if not!
|
|
295
|
+
if (address >= exports.RAM_START_ADDRESS && address < exports.RAM_START_ADDRESS + this.sram.length) {
|
|
296
|
+
this.sramView.setUint16(address - exports.RAM_START_ADDRESS, value, true);
|
|
297
|
+
return;
|
|
298
|
+
}
|
|
299
|
+
const alignedAddress = (address & 0xfffffffc) >>> 0;
|
|
300
|
+
const offset = address & 0x3;
|
|
301
|
+
const peripheral = this.findPeripheral(address);
|
|
302
|
+
if (peripheral) {
|
|
303
|
+
const atomicType = (alignedAddress & 0x3000) >> 12;
|
|
304
|
+
const offset = alignedAddress & 0xfff;
|
|
305
|
+
peripheral.writeUint32Atomic(offset, (value & 0xffff) | ((value & 0xffff) << 16), atomicType);
|
|
306
|
+
return;
|
|
307
|
+
}
|
|
308
|
+
const originalValue = this.readUint32(alignedAddress);
|
|
309
|
+
const newValue = new Uint32Array([originalValue]);
|
|
310
|
+
new DataView(newValue.buffer).setUint16(offset, value, true);
|
|
311
|
+
this.writeUint32(alignedAddress, newValue[0]);
|
|
312
|
+
}
|
|
313
|
+
get gpioValues() {
|
|
314
|
+
const { gpio } = this;
|
|
315
|
+
let result = 0;
|
|
316
|
+
for (let gpioIndex = 0; gpioIndex < gpio.length; gpioIndex++) {
|
|
317
|
+
if (gpio[gpioIndex].inputValue) {
|
|
318
|
+
result |= 1 << gpioIndex;
|
|
319
|
+
}
|
|
320
|
+
}
|
|
321
|
+
return result;
|
|
322
|
+
}
|
|
323
|
+
setInterrupt(irq, value) {
|
|
324
|
+
this.core.setInterrupt(irq, value);
|
|
325
|
+
}
|
|
326
|
+
updateIOInterrupt() {
|
|
327
|
+
let interruptValue = false;
|
|
328
|
+
for (const pin of this.gpio) {
|
|
329
|
+
if (pin.irqValue) {
|
|
330
|
+
interruptValue = true;
|
|
331
|
+
}
|
|
332
|
+
}
|
|
333
|
+
this.setInterrupt(irq_js_1.IRQ.IO_BANK0, interruptValue);
|
|
334
|
+
}
|
|
335
|
+
step() {
|
|
336
|
+
this.core.executeInstruction();
|
|
337
|
+
}
|
|
338
|
+
execute() {
|
|
339
|
+
this.clock.resume();
|
|
340
|
+
this.executeTimer = null;
|
|
341
|
+
this.stopped = false;
|
|
342
|
+
for (let i = 0; i < 100000 && !this.stopped && !this.core.waiting; i++) {
|
|
343
|
+
this.core.executeInstruction();
|
|
344
|
+
}
|
|
345
|
+
if (!this.stopped) {
|
|
346
|
+
this.executeTimer = setTimeout(() => this.execute(), 0);
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
stop() {
|
|
350
|
+
this.stopped = true;
|
|
351
|
+
if (this.executeTimer != null) {
|
|
352
|
+
clearTimeout(this.executeTimer);
|
|
353
|
+
this.executeTimer = null;
|
|
354
|
+
}
|
|
355
|
+
this.clock.pause();
|
|
356
|
+
}
|
|
357
|
+
get executing() {
|
|
358
|
+
return !this.stopped;
|
|
359
|
+
}
|
|
360
|
+
}
|
|
361
|
+
exports.RP2040 = RP2040;
|