diff options
| author | Uri Shaked | 2021-10-22 04:44:33 +0300 |
|---|---|---|
| committer | Uri Shaked | 2021-10-22 04:44:33 +0300 |
| commit | 8c15d5d1a3bdeb1f4c95248fc35b9ebe0a6aa235 (patch) | |
| tree | d72fc8560ea653141b2fafcceb270fb3d4ac08dd | |
| parent | chore: add node 16 to CI test matrix (diff) | |
| download | avr8js-8c15d5d1a3bdeb1f4c95248fc35b9ebe0a6aa235.tar.gz avr8js-8c15d5d1a3bdeb1f4c95248fc35b9ebe0a6aa235.tar.bz2 avr8js-8c15d5d1a3bdeb1f4c95248fc35b9ebe0a6aa235.zip | |
fix(spi): setting SPIE doesn't fire pending interrupt
Diffstat (limited to '')
| -rw-r--r-- | src/peripherals/spi.spec.ts | 22 | ||||
| -rw-r--r-- | src/peripherals/spi.ts | 3 |
2 files changed, 25 insertions, 0 deletions
diff --git a/src/peripherals/spi.spec.ts b/src/peripherals/spi.spec.ts index f323b88..9e6dac5 100644 --- a/src/peripherals/spi.spec.ts +++ b/src/peripherals/spi.spec.ts @@ -203,6 +203,28 @@ describe('SPI', () => { expect(cpu.pc).toEqual(0x22); // SPI Ready interrupt }); + it('should fire a pending SPI interrupt when SPIE flag is set', () => { + const cpu = new CPU(new Uint16Array(1024)); + new AVRSPI(cpu, spiConfig, FREQ_16MHZ); + + cpu.writeData(SPCR, SPE | MSTR); + cpu.writeData(SPDR, 0x50); + cpu.data[SREG] = 0x80; // SREG: I------- + + // Wait for transfer to complete (8 bits * 8 cycles per bit = 64). + cpu.cycles += 64; + cpu.tick(); + + expect(cpu.data[SPSR] & SPIF).toEqual(SPIF); + expect(cpu.pc).toEqual(0); // Interrupt not taken (yet) + + // Enable the interrupt (SPIE) + cpu.writeData(SPCR, SPE | MSTR | SPIE); + cpu.tick(); + expect(cpu.pc).toEqual(0x22); // SPI Ready interrupt + expect(cpu.data[SPSR] & SPIF).toEqual(0); + }); + it('should should only update SPDR when tranfer finishes (double buffering)', () => { const cpu = new CPU(new Uint16Array(1024)); const spi = new AVRSPI(cpu, spiConfig, FREQ_16MHZ); diff --git a/src/peripherals/spi.ts b/src/peripherals/spi.ts index 9707307..7b753ab 100644 --- a/src/peripherals/spi.ts +++ b/src/peripherals/spi.ts @@ -78,6 +78,9 @@ export class AVRSPI { }, cyclesToComplete); return true; }; + cpu.writeHooks[SPCR] = (value: u8) => { + this.cpu.updateInterruptEnable(this.SPI, value); + }; cpu.writeHooks[SPSR] = (value: u8) => { this.cpu.data[SPSR] = value; this.cpu.clearInterruptByFlag(this.SPI, value); |
