diff --git a/src/parser/lang-6502.grammar b/src/parser/lang-6502.grammar index 5dbee73e..ad459dc3 100644 --- a/src/parser/lang-6502.grammar +++ b/src/parser/lang-6502.grammar @@ -9,6 +9,7 @@ Line { Statement { Instruction | Directive | + HexDirective | MacroDef | MacEnd | ControlOp | @@ -22,7 +23,7 @@ Instruction { } Register { - @specialize + @specialize } Directive { @@ -31,15 +32,27 @@ Directive { PseudoOp { @specialize } +HexOp { @specialize } + +HexDirective { + HexOp HexByte* +} + +@external tokens hexTokenizer from "../../src/parser/tokens-6502" { HexByte } + Mac { @specialize } MacEnd { @specialize } @@ -56,20 +69,20 @@ CurrentAddress { Opcode { @specialize } diff --git a/src/parser/lang-6502.ts b/src/parser/lang-6502.ts index 17c8146b..97d65068 100644 --- a/src/parser/lang-6502.ts +++ b/src/parser/lang-6502.ts @@ -35,6 +35,8 @@ export const Lezer6502: LRLanguage = LRLanguage.define({ BinaryGt: t.compareOperator, UnaryLt: t.arithmeticOperator, UnaryGt: t.arithmeticOperator, + HexOp: t.definition(t.variableName), + HexByte: t.number, Mac: t.definitionKeyword, MacEnd: t.definitionKeyword, "MacroDef/Identifier": t.macroName, diff --git a/src/parser/lang-z80.grammar b/src/parser/lang-z80.grammar index a4c5f063..b727186b 100644 --- a/src/parser/lang-z80.grammar +++ b/src/parser/lang-z80.grammar @@ -22,7 +22,12 @@ Directive { } PseudoOp { - @specialize + @specialize } Condition { diff --git a/src/parser/tokens-6502.ts b/src/parser/tokens-6502.ts new file mode 100644 index 00000000..c5b51aeb --- /dev/null +++ b/src/parser/tokens-6502.ts @@ -0,0 +1,15 @@ +import { ExternalTokenizer } from "@lezer/lr" +import { HexByte } from "../../gen/parser/lang-6502.grammar.terms" + +function isHexDigit(ch: number) { + return (ch >= 48 && ch <= 57) || // 0-9 + (ch >= 65 && ch <= 70) || // A-F + (ch >= 97 && ch <= 102) // a-f +} + +export const hexTokenizer = new ExternalTokenizer((input) => { + if (!isHexDigit(input.peek(0)) || !isHexDigit(input.peek(1))) return + let len = 2 + while (isHexDigit(input.peek(len))) len++ + if (len % 2 === 0) input.acceptToken(HexByte, len) +})