Phase 4: Steuerelemente implementieren

This commit is contained in:
2026-09-05 12:49:46 +02:00
parent 1cb6ae8fd9
commit 19804e0e2d
36 changed files with 6472 additions and 689 deletions

View File

@@ -1317,7 +1317,7 @@ fn token_def(code: u16) -> Option<TokenDef> {
}),
0x138 => Some(TokenDef {
len: 0,
rules: &["expr::=MKS$({0})"],
rules: &["expr::=MKS$({expr:0})", "{0}"],
}),
0x139 => Some(TokenDef {
len: 0,
@@ -1682,7 +1682,7 @@ fn token_def(code: u16) -> Option<TokenDef> {
}),
0x1b2 => Some(TokenDef {
len: 0,
rules: &["expr::=MSGBOX({2}, {1}, {0})"],
rules: &["expr::=STR$({expr:0})"],
}),
0x1b3 => Some(TokenDef {
len: 0,
@@ -2421,6 +2421,23 @@ impl<'a> Decoder<'a> {
.ok_or_else(|| self.fail(self.at, "P-Code", "Tokendaten abgeschnitten"))?
.to_owned();
self.at += (len + 1) & !1;
if matches!(self.pcode, 0x065 | 0x066) {
let operands = usize::from(self.pcode == 0x066);
let split = self.stack.len().saturating_sub(operands);
if split > 0
&& self.stack[split - 1].kind != "newline"
&& !self.stack[split - 1].text.ends_with(" THEN ")
&& !self.stack[split - 1].text.ends_with(" ELSE ")
{
self.stack.insert(
split,
Item {
kind: "newline".into(),
text: "\r\u{1}".into(),
},
);
}
}
if matches!(self.pcode, 0x1c5 | 0x1c6) {
let first = self
.stack
@@ -2634,6 +2651,26 @@ mod tests {
assert_eq!(decoder.array(&array, false).unwrap(), "Oldcontents()");
}
#[test]
fn next_trennt_eine_vorangehende_anweisung_auch_ohne_newline_token() {
let (sym, ids) = symbols(&["i"]);
let mut code = Vec::new();
code.extend_from_slice(&0u16.to_le_bytes());
code.extend_from_slice(&0x00au16.to_le_bytes());
code.extend_from_slice(&9u16.to_le_bytes());
code.extend_from_slice(&[0, 0]);
code.extend_from_slice(b"PRINT 1");
code.push(0);
code.extend_from_slice(&(0x0400u16 | 0x00b).to_le_bytes());
code.extend_from_slice(&ids[0].to_le_bytes());
code.extend_from_slice(&0x066u16.to_le_bytes());
code.extend_from_slice(&[0xff, 0xff, 1, 0]);
code.extend_from_slice(&0u16.to_le_bytes());
code.extend_from_slice(&8u16.to_le_bytes());
let (decoded, _) = Decoder::new("test.frm", &sym, &code, 0).run().unwrap();
assert!(decoded.contains("PRINT 1\nNEXT i%\n"), "{decoded:?}");
}
#[test]
fn decodes_defint_and_vbdos_isam_tokens() {
let mut decoder = Decoder::new("test.frm", &[], &[], 0);