Phase 4: Ereignisschleife und klassische Traps

This commit is contained in:
2026-09-04 15:56:47 +02:00
parent 060674b466
commit 5cf5a6582c
40 changed files with 4024 additions and 176 deletions

View File

@@ -103,9 +103,19 @@ nicht um.
## Ereignisse
| Element | Art |
|---|---|
| `DOEVENTS` | Funktion |
| Element | Art | Syntax und Wirkung |
|---|---|---|
| `DOEVENTS` | Funktion | `DOEVENTS` stellt ein anstehendes Ereignis zu und liefert 0. |
| `EVENT` | Anweisung | `EVENT ON\|OFF` schaltet die Erkennung aller Ereignis-Traps ein oder aus. |
| `KEY (Ereignis)` | Anweisung | `KEY(n) ON\|OFF\|STOP` steuert einen Tasten-Trap. |
| `ON KEY` | Anweisung | `ON KEY(n) GOSUB ziel` bindet eine Taste an einen Handler. |
| `ON SIGNAL` | Anweisung | `ON SIGNAL(n) GOSUB ziel` bindet `SIGINT` oder `SIGTERM` an einen Handler. |
| `ON TIMER` | Anweisung | `ON TIMER(n) GOSUB ziel` bindet ein Intervall von 186 400 Sekunden. |
| `ON UEVENT` | Anweisung | `ON UEVENT GOSUB ziel` bindet das benutzerdefinierte Ereignis. |
| `SetUEvent` | Routine | `CALL SetUEvent` löst ein benutzerdefiniertes Ereignis aus. |
| `SIGNAL` | Anweisung | `SIGNAL(n) ON\|OFF\|STOP` steuert einen Signal-Trap. |
| `TIMER` | Anweisung | `TIMER ON\|OFF\|STOP` steuert den Zeit-Trap. |
| `UEVENT` | Anweisung | `UEVENT ON\|OFF\|STOP` steuert den benutzerdefinierten Trap. |
## Fehlerbehandlung

View File

@@ -21,7 +21,7 @@ namentlich abgewiesen. `Non-Feature` = abgelehnt, gelistet unter
**Fundstelle.** Bei `implementiert` das Modul, bei `Non-Feature` der
Abschnitt der Sprachreferenz, bei `offen` ein Strich.
**Abdeckung.** implementiert 217 · offen 15 · Non-Feature 53 · gesamt 285
**Abdeckung.** implementiert 227 · offen 5 · Non-Feature 53 · gesamt 285
| Name | Art | Gruppe | Status | Fundstelle | Quelle |
|---|---|---|---|---|---|
@@ -125,22 +125,22 @@ Abschnitt der Sprachreferenz, bei `offen` ein Strich.
| `TYPE` | Anweisung | Deklaration | implementiert | tb-frontend::sema | bas7advr |
| `UBOUND` | Funktion | Deklaration | implementiert | tb-frontend::sema | bas7advr |
| `DOEVENTS` | Funktion | Ereignisse | implementiert | tb-runtime::builtins | sprachreferenz |
| `EVENT` | Anweisung | Ereignisse | offen | - | bas7advr |
| `KEY (Ereignis)` | Anweisung | Ereignisse | offen | - | bas7advr |
| `ON KEY` | Anweisung | Ereignisse | offen | - | bas7advr |
| `EVENT` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `KEY (Ereignis)` | Anweisung | Ereignisse | implementiert | tb-runtime::traps | bas7advr |
| `ON KEY` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `ON PEN` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `ON PLAY` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `ON SIGNAL` | Anweisung | Ereignisse | offen | - | bas7advr |
| `ON SIGNAL` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `ON STRIG` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `ON TIMER` | Anweisung | Ereignisse | offen | - | bas7advr |
| `ON UEVENT` | Anweisung | Ereignisse | offen | - | bas7advr |
| `ON TIMER` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `ON UEVENT` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `PEN` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `PLAY (Ereignis)` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `SetUEvent` | Routine | Ereignisse | offen | - | bas7advr |
| `SIGNAL` | Anweisung | Ereignisse | offen | - | bas7advr |
| `SetUEvent` | Routine | Ereignisse | implementiert | tb-runtime::builtins | bas7advr |
| `SIGNAL` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `STRIG` | Anweisung | Ereignisse | Non-Feature | sprachreferenz.md#abweichungen | bas7advr |
| `TIMER` | Anweisung | Ereignisse | offen | - | bas7advr |
| `UEVENT` | Anweisung | Ereignisse | offen | - | bas7advr |
| `TIMER` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `UEVENT` | Anweisung | Ereignisse | implementiert | tb-vm::interp | bas7advr |
| `ERL` | Funktion | Fehlerbehandlung | implementiert | tb-vm::interp | bas7advr |
| `ERR` | Anweisung | Fehlerbehandlung | implementiert | tb-vm::interp | bas7advr |
| `ERR` | Funktion | Fehlerbehandlung | implementiert | tb-vm::interp | bas7advr |

View File

@@ -184,11 +184,63 @@ INTEGER 1 (wahr) / 0 (falsch).
## 8. Ereignis-Traps (klassisch, ohne Forms)
Vorhanden im Vorbild: `ON COM/KEY/PEN/PLAY/STRIG/TIMER/UEVENT(…) GOSUB label`
mit Steueranweisungen `… ON/OFF/STOP`, dazu das `EVENT`-Statement (auch für
Forms-Ereignisse) und `SetUEvent`. Timer-Events und Trapping sind ausgesetzt,
solange ein Menü-Control den Fokus hat. Für Terminal Basic relevant:
`TIMER`, `KEY`, `UEVENT`; `COM/PEN/PLAY/STRIG`: Nicht-Ziel (Fehler 73).
Vorhanden im Vorbild: `ON COM/KEY/PEN/PLAY/SIGNAL/STRIG/TIMER/UEVENT(…)
GOSUB label` mit Steueranweisungen `… ON/OFF/STOP`, dazu das
`EVENT`-Statement (auch für Forms-Ereignisse) und `SetUEvent`.
Timer-Events und Trapping sind ausgesetzt, solange ein Menü-Control den
Fokus hat. Für Terminal Basic relevant: `TIMER`, `KEY`, `UEVENT`,
`SIGNAL`; `COM/PEN/PLAY/STRIG`: Nicht-Ziel (Fehler 73).
**Traps und Wertebereiche**
| Anweisung | Wertebereich | Quelle |
|---|---|---|
| `ON TIMER(n&) GOSUB ziel` | `n&` = 186 400 Sekunden | verstrichene Zeit |
| `ON KEY(n%) GOSUB ziel` | `n%` = 0 (alle), 110 (F1F10), 11 ↑, 12 ←, 13 →, 14 ↓, 1525 (benutzerdefiniert), 3031 (F11F12) | Tastendruck |
| `ON UEVENT GOSUB ziel` | — | `SetUEvent` |
| `ON SIGNAL(n%) GOSUB ziel` | `n%` = 1 (`SIGINT`), 2 (`SIGTERM`) | Betriebssystem |
`GOSUB 0` schaltet den jeweiligen Trap ab. Ein Wert außerhalb des
Bereichs wird namentlich abgewiesen — zur Übersetzungszeit, wenn er
konstant ist, sonst mit Fehler 5.
**Maskierung.** Je Quelle `ON` (zustellen), `OFF` (verwerfen — auch ein
unter `STOP` bereits gemerktes Ereignis) und `STOP` (höchstens eines
merken und beim nächsten `ON` zustellen). `EVENT ON`/`EVENT OFF`
klammern einen Abschnitt, in dem keine Ereignisse erkannt werden müssen;
ein `EVENT STOP` gibt es nicht.
**Zustellpunkte.** Anweisungsgrenze, `DOEVENTS`, während `SLEEP` und vor
blockierender Eingabe — sonst nirgends. Ein zugestelltes Ereignis
beendet ein laufendes `SLEEP`.
**Wiedereintritt.** Der Eintritt in einen Handler führt selbsttätig
`STOP` seiner Quelle aus, das `RETURN` selbsttätig `ON` — außer im
Handler stand ein ausdrückliches `OFF`, dann bleibt die Quelle aus.
**Benutzerdefinierte Trap-Tasten.** `KEY n, CHR$(flag) + CHR$(scancode)`
erklärt für `n` = 1525, welche Taste der zugehörige `ON KEY(n)`-Trap
fängt — anders als für 110 und 3031, wo dieselbe Anweisung ein Makro
zuweist. `flag` ist das Tastaturflagbyte (1 rechte Umschalttaste, 2 linke,
4 Strg, 8 Alt), `scancode` der Scancode der Taste. Beispiel: `KEY 15,
CHR$(4) + CHR$(30)` fängt Strg+A.
**Festlegungen ohne Beleg im Vorbild** (2026-09-04; die Original-Hilfe
verweist dazu auf ein nicht vorliegendes Kapitel des Programmer's Guide):
- Eine Taste mit aktivem `ON KEY`-Trap erscheint **nicht** zusätzlich bei
`INKEY$`/`INPUT`; sonst sähe ein Programm dieselbe Taste zweimal.
- Sind mehrere Ereignisse zugleich fällig, gilt die Reihenfolge `KEY`
(aufsteigend nach `n`), `TIMER`, `UEVENT`, `SIGNAL`; zugestellt wird
eines je Zustellpunkt.
- Zugestellt wird an jeder Anweisungsgrenze, auch innerhalb von
`SUB`/`FUNCTION`; das Sprungziel liegt im Modulrumpf — dieselbe Regel
wie beim modulweiten `ON ERROR`.
- Die Bits des Tastaturflagbytes folgen der BIOS-Belegung. Linke und
rechte Umschalttaste sind im Terminal nicht unterscheidbar; beide Bits
gelten gleich. NumLock und CapsLock werden ignoriert.
- Zeichen ohne Eintrag in der Scancode-Tabelle des Vorbilds können keinen
benutzerdefinierten Trap auslösen.
## 9. Konsolen-E/A
@@ -482,3 +534,16 @@ Dialoge:
links erhalten, der Cursor wird in die neuen Grenzen geklemmt, und ein
`VIEW PRINT`-Bereich wird am unteren Rand geklemmt bzw. — wenn er ganz
vom Schirm fällt — auf den vollen Bildschirm zurückgesetzt.
8. **`SIGNAL` liegt auf Betriebssystemsignalen** (2026-09-04): Im Vorbild
trappte `ON SIGNAL(n%)` OS/2-Signale — Prozessflags A/B/C, ausgelöst
über `DOSFLAGPROCESS` aus einem anderen Prozess; einen Wertebereich
für `n%` dokumentierte die Hilfe nicht. Diese Quelle existiert auf
keiner Zielplattform. Abgebildet wird deshalb die minimale Menge, die
auf allen dreien besteht: `SIGNAL(1)` = `SIGINT`, `SIGNAL(2)` =
`SIGTERM`. Die vier übrigen Signale des C-Standards (`SIGABRT`,
`SIGFPE`, `SIGILL`, `SIGSEGV`) entstehen aus dem eigenen
Programmzustand und sind nach einem `RETURN` nicht fortsetzbar; sie
werden nicht abgebildet. Unter Windows ist `SIGTERM` von außen nicht
zustellbar — `SIGNAL(2)` bleibt dort wirkungslos. Trifft `SIGINT` ohne aktiven Trap
ein, bleibt es beim bisherigen Abbruch.