velxio/docs/wiki/circuit-emulation-appendix.md

329 lines
10 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Appendix — Netlists, Opcodes, Model Parameters, Glossary
## A. Reference netlists (one per analysis type)
### A.1 `.op` — DC operating point
```spice
Voltage divider DC op-point
V1 vcc 0 DC 9
R1 vcc out 1k
R2 out 0 2k
.op
.end
```
### A.2 `.tran` — transient analysis
```spice
RC charging
V1 vcc 0 PULSE(0 5 0 1n 1n 10 20)
R1 vcc out 10k
C1 out 0 100u IC=0
.ic v(out)=0
.tran 10m 3
.end
```
### A.3 `.ac` — AC small-signal sweep
```spice
RC low-pass AC sweep
V1 in 0 AC 1
R1 in out 1k
C1 out 0 159.155n
.ac dec 20 10 1Meg
.end
```
### A.4 `.dc` — DC sweep
```spice
Diode I-V curve
V1 a 0 DC 0
D1 a 0 DMOD
.model DMOD D(Is=1e-14 N=1)
.dc V1 0 1 0.01
.end
```
### A.5 Behavioral logic gates (B-source)
```spice
NAND gate
Va a 0 DC 5
Vb b 0 DC 5
Bnand y 0 V = 5 * (1 - u(V(a)-2.5) * u(V(b)-2.5))
Rload y 0 1k
.op
.end
```
### A.6 Schmitt-switch relaxation oscillator (simplified 555)
```spice
Relaxation oscillator
Vcc vcc 0 DC 5
R1 vcc cap 10k
Ccap cap 0 10n IC=0
Sdis cap 0 cap 0 SMOD
.model SMOD SW(Vt=2.5 Vh=0.833 Ron=100 Roff=1G)
Sbuf out vcc cap 0 SOUT
.model SOUT SW(Vt=2.5 Vh=0.833 Ron=10 Roff=1G)
Rpd out 0 100k
.tran 0.5u 2m
.end
```
### A.7 Bridge rectifier with sine source
```spice
Full-wave bridge rectifier
V1 a b SIN(0 6 50)
D1 a p DMOD
D2 b p DMOD
D3 n a DMOD
D4 n b DMOD
R1 p n 1k
.model DMOD D(Is=1e-14 N=1)
.tran 0.1m 40m
.end
```
### A.8 Common-emitter BJT amplifier
```spice
Common-emitter with 2N2222
Vcc vcc 0 DC 12
Vin in 0 SIN(0 0.01 1k)
Cin in b 1u
RB1 vcc b 47k
RB2 b 0 10k
RC vcc c 4.7k
RE e 0 1k
CE e 0 100u
Q1 c b e Q2N2222
Cout c out 1u
Rout out 0 100k
.model Q2N2222 NPN(Is=1e-14 Bf=200 Vaf=75)
.tran 10u 6m
.end
```
### A.9 Ideal op-amp (VCVS) as inverting amplifier
```spice
Op-amp inverting amplifier, gain -10
Vin in 0 DC 0.2
Rin in n 1k
Rf n out 10k
Eopa out 0 0 n 1e6
.op
.end
```
### A.10 N-MOSFET switch
```spice
N-MOS switch
Vcc vcc 0 DC 5
Vgate gate 0 DC 5
RL vcc drain 1k
M1 drain gate 0 0 NMOS_L1 L=1u W=100u
.model NMOS_L1 NMOS(Level=1 Vto=1.0 Kp=50u Lambda=0.01)
.op
.end
```
## B. AVR opcode encodings (the ones we use)
| Instruction | Encoding (bits 15..0) | Bytes | Notes |
|---|---|---|---|
| `LDI Rd, K` | `1110 KKKK dddd KKKK` | 2 | `d = Rd 16`, `Rd ∈ [16..31]` |
| `OUT A, Rr` | `1011 1AAr rrrr AAAA` | 2 | `A ∈ [0..63]` (I/O space) |
| `IN Rd, A` | `1011 0AAd dddd AAAA` | 2 | |
| `STS k, Rr` | `1001 001r rrrr 0000` + `kkkkkkkk kkkkkkkk` | 4 | 32-bit instruction, `k` is 16-bit address |
| `LDS Rd, k` | `1001 000d dddd 0000` + `kkkkkkkk kkkkkkkk` | 4 | 32-bit |
| `RJMP k` | `1100 kkkk kkkk kkkk` | 2 | signed 12-bit word offset from PC+1 |
| `SBRC Rr, b` | `1111 110r rrrr 0bbb` | 2 | skip if bit clear |
| `SBRS Rr, b` | `1111 111r rrrr 0bbb` | 2 | skip if bit set |
| `NOP` | `0000 0000 0000 0000` | 2 | |
| `CALL k` | `1001 010k kkkk 111k` + `kkkkkkkk kkkkkkkk` | 4 | not used here |
| `RET` | `1001 0101 0000 1000` | 2 | not used here |
## C. ATmega328P register addresses (used in our programs)
| Register | I/O addr | SRAM addr | Purpose |
|---|---|---|---|
| DDRB | 0x04 | 0x24 | Port B data direction |
| PORTB | 0x05 | 0x25 | Port B output |
| PINB | 0x03 | 0x23 | Port B input |
| DDRC | 0x07 | 0x27 | Port C data direction |
| PORTC | 0x08 | 0x28 | Port C output |
| DDRD | 0x0A | 0x2A | Port D data direction |
| PORTD | 0x0B | 0x2B | Port D output |
| TCCR0A | 0x24 | 0x44 | Timer0 control A |
| TCCR0B | 0x25 | 0x45 | Timer0 control B |
| TCNT0 | 0x26 | 0x46 | Timer0 counter |
| OCR0A | 0x27 | 0x47 | Timer0 compare A (PWM D6) |
| OCR0B | 0x28 | 0x48 | Timer0 compare B (PWM D5) |
| OCR2A | — | 0xB3 | Timer2 compare A (PWM D11) |
| OCR2B | — | 0xB4 | Timer2 compare B (PWM D3) |
| TCCR1A | — | 0x80 | Timer1 control A |
| TCCR1B | — | 0x81 | Timer1 control B |
| OCR1AL | — | 0x88 | Timer1A compare low (PWM D9) |
| OCR1AH | — | 0x89 | Timer1A compare high |
| OCR1BL | — | 0x8A | Timer1B compare low (PWM D10) |
| ADCL | — | 0x78 | ADC result low byte |
| ADCH | — | 0x79 | ADC result high byte |
| ADCSRA | — | 0x7A | ADC control and status A |
| ADMUX | — | 0x7C | ADC multiplexer |
Registers above 0x5F can only be accessed via `STS` / `LDS` (32-bit instructions), not `OUT` / `IN`.
## D. ADMUX / ADCSRA bit fields
### ADMUX (0x7C)
| Bit | Name | Purpose |
|---|---|---|
| 7 | REFS1 | Voltage reference selection bit 1 |
| 6 | REFS0 | Voltage reference selection bit 0 — `01` = AVCC with cap at AREF |
| 5 | ADLAR | ADC Left Adjust Result — `0` = right, `1` = left |
| 4 | — | reserved |
| 3..0 | MUX3..0 | Channel select — `0000` = ADC0 (A0), `0001` = A1, … |
Common values:
- `0x40` = AVCC ref, right-adjusted, A0
- `0x60` = AVCC ref, **left-adjusted**, A0 (we use this!)
- `0xC0` = Internal 1.1V ref, right-adjusted, A0
### ADCSRA (0x7A)
| Bit | Name | Purpose |
|---|---|---|
| 7 | ADEN | ADC Enable |
| 6 | ADSC | ADC Start Conversion — write 1 to start; auto-clears when done |
| 5 | ADATE | Auto Trigger Enable |
| 4 | ADIF | ADC Interrupt Flag |
| 3 | ADIE | ADC Interrupt Enable |
| 2..0 | ADPS2..0 | Prescaler Select — `111` = /128 (= 125 kHz ADC clock at 16 MHz) |
Common values:
- `0x87` = ADEN + prescaler /128 (initial setup)
- `0xC7` = ADEN + **ADSC** + /128 (start conversion)
### Conversion timing
- First conversion: 25 ADC clock cycles
- Subsequent: 13 ADC clock cycles
- At 125 kHz ADC clock: first ≈ 200 µs, subsequent ≈ 104 µs
## E. TCCR0A / TCCR0B bit fields
### TCCR0A (0x24, I/O)
| Bit | Purpose |
|---|---|
| 7 | COM0A1 — 1 for non-inverting PWM on OC0A |
| 6 | COM0A0 |
| 5 | COM0B1 |
| 4 | COM0B0 |
| 3..2 | — |
| 1 | WGM01 — Waveform Generation Mode bit 1 |
| 0 | WGM00 — bit 0 |
### TCCR0B (0x25, I/O)
| Bit | Purpose |
|---|---|
| 7 | FOC0A / FOC0B — force compare |
| 5..4 | — |
| 3 | WGM02 |
| 2..0 | CS02..0 — clock source |
**Mode 3: Fast PWM 8-bit**`WGM02:0 = 011`. Counter counts 0..255, TOP = 0xFF.
Settings we use (for the `potToPwmProgram`):
- `TCCR0A = 0x83` = COM0A1=1 + WGM01=1 + WGM00=1 → non-inverting Fast PWM on D6
- `TCCR0B = 0x01` = CS00=1 → no prescaler (16 MHz counter → 62.5 kHz PWM frequency)
## F. LED model parameters (tuned for typical datasheet Vf @ 10 mA)
```javascript
const LED_PARAMS = {
red: { Is: 1e-20, n: 1.7, ratedCurrent: 0.020 }, // V_f ≈ 2.0 V
green: { Is: 1e-22, n: 1.9, ratedCurrent: 0.020 }, // V_f ≈ 2.2 V
yellow: { Is: 1e-21, n: 1.8, ratedCurrent: 0.020 }, // V_f ≈ 2.1 V
blue: { Is: 1e-28, n: 2.0, ratedCurrent: 0.020 }, // V_f ≈ 3.1 V
white: { Is: 1e-28, n: 2.0, ratedCurrent: 0.020 },
};
```
Shockley: `I = Is · (exp(V / (n · Vt)) 1)`, with `Vt = 0.02585 V` at 300 K.
To tune another color: pick a datasheet point `(V_f, I)` and solve for `Is`:
```
Is = I · exp(V / (n · Vt))
```
## G. NTC β-model
```javascript
R(T) = R0 · exp(β · (1/T 1/T0)) // T in Kelvin
```
Common 10 kΩ NTC (β=3950, T₀=25 °C = 298.15 K):
| T (°C) | T (K) | R (kΩ) | V_A0 @ 10k pullup to 5V |
|---|---|---|---|
| 20 | 253.15 | 95.4 | 4.52 V |
| 0 | 273.15 | 33.6 | 3.85 V |
| 25 | 298.15 | 10.0 | 2.50 V |
| 50 | 323.15 | 3.59 | 1.32 V |
| 100 | 373.15 | 0.68 | 0.32 V |
Inverse (recovering T from measured R):
```
T = 1 / (1/T0 + (1/β) · ln(R / R0))
```
This is what `e2e_thermistor.test.js` does to convert ADC readings back to Celsius.
## H. Glossary
- **MNA (Modified Nodal Analysis)** — SPICE's core algorithm. Unknowns are node voltages plus branch currents of voltage sources.
- **Companion model** — linearization of a reactive element (C, L) into an equivalent resistor + source at each timestep.
- **Backward Euler** — simple first-order implicit integration, unconditionally stable but damps high-frequency content.
- **Trapezoidal integration** — second-order, SPICE's default; more accurate but can ring.
- **Newton-Raphson** — iterative method for non-linear equations. Converges quadratically near a solution.
- **`pnjlim`** — SPICE's internal voltage limiter for PN junctions; prevents `exp()` overflow on early iterations.
- **GMIN** — minimum conductance added to every node; prevents singular matrices.
- **Shockley equation** — `I = Is · (exp(V/(nVt)) 1)`. Governs ideal pn junctions.
- **Ebers-Moll** — simplified BJT model; predecessor to the more accurate Gummel-Poon.
- **Schmitt trigger** — a comparator with hysteresis; outputs digital clean levels from noisy analog inputs.
- **XSPICE** — ngspice extension that adds digital primitives (AND, OR, FF, etc.) as first-class elements. Not compiled into the current `eecircuit-engine` WASM.
- **B-source** — ngspice behavioral voltage/current source: `B1 n+ n- V = expression`.
- **S-element** — ngspice voltage-controlled switch with optional hysteresis.
- **VCVS/VCCS/CCVS/CCCS** — voltage-controlled-voltage / voltage-controlled-current / current-controlled-voltage / current-controlled-current sources; implement ideal op-amps, gain blocks, etc.
- **PWL** — piecewise-linear source, `PWL(t0 v0 t1 v1 …)`. Useful for arbitrary-shape stimuli.
- **Intel HEX** — ASCII file format for program memory, used by Arduino, avr-objcopy, etc.
- **PORTB / PORTC / PORTD** — 8-bit I/O registers on ATmega328P. Drive the Arduino pin sets.
- **ADLAR** — ADC Left Adjust Result. When set, the 10-bit ADC result is aligned so that ADCH has the top 8 bits.
- **OCR** — Output Compare Register. Compared against a timer counter to drive PWM.
- **Quasi-static co-simulation** — digital and analog engines advance independently on a coarse time grid, not cycle-locked.
## I. Useful external references
- ngspice manual — <https://ngspice.sourceforge.io/docs.html>
- `eecircuit-engine` on GitHub — <https://github.com/eelab-dev/EEcircuit-engine>
- EEcircuit online — <https://eecircuit.com/>
- AVR instruction set manual — <https://www.microchip.com/content/dam/mchp/documents/OTH/ProductDocuments/DataSheets/AVR-Instruction-Set-Manual.pdf>
- ATmega328P datasheet — <https://www.microchip.com/en-us/product/atmega328p>
- `avr8js` on GitHub — <https://github.com/wokwi/avr8js>
- Wokwi elements — <https://github.com/wokwi/wokwi-elements>
- SPICE model library (Linear Technology) — <https://www.analog.com/en/design-center/design-tools-and-calculators/ltspice-simulator.html>
- Gummel-Poon BJT model explanation — standard SPICE references