From eedbdc4f5593b6d0bb242ef053fdccdd6bdad180 Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Thu, 15 Feb 2024 16:09:38 -0700 Subject: [PATCH] track starting positions of readExpArray() calls --- src/kiss/Helpers.hx | 4 ++-- src/kiss/Kiss.hx | 3 ++- src/kiss/Reader.hx | 39 +++++++++++++++++++++++++++++++++++++-- 3 files changed, 41 insertions(+), 5 deletions(-) diff --git a/src/kiss/Helpers.hx b/src/kiss/Helpers.hx index 27fc4aa..62881be 100644 --- a/src/kiss/Helpers.hx +++ b/src/kiss/Helpers.hx @@ -530,8 +530,8 @@ class Helpers { // The macro interpreter gets everything a KissInterp has, // plus macro-specific things. var interp = new KissInterp(); - interp.variables.set("read", Reader.assertRead.bind(_, k)); - interp.variables.set("readExpArray", Reader.readExpArray.bind(_, _, k)); + interp.variables.set("read", Reader._assertRead.bind(_, k)); + interp.variables.set("readExpArray", Reader._readExpArray.bind(_, _, k)); interp.variables.set("ReaderExp", ReaderExpDef); interp.variables.set("nextToken", Reader.nextToken.bind(_, "a token")); interp.variables.set("printExp", printExp); diff --git a/src/kiss/Kiss.hx b/src/kiss/Kiss.hx index 7181138..a730411 100644 --- a/src/kiss/Kiss.hx +++ b/src/kiss/Kiss.hx @@ -498,6 +498,7 @@ class Kiss { Context.registerModuleDependency(module, fullPath); var previousFile = k.file; + var isNested = previousFile != null; k.file = fullPath; if (k.loadedFiles.exists(fullPath)) { @@ -541,7 +542,7 @@ class Kiss { loadedExps.push(nextExp); } } - }); + }, isNested); var exp = if (loadedExps.length > 0) { CallExp(Symbol("begin").withPos(startPosition), loadedExps).withPos(startPosition); diff --git a/src/kiss/Reader.hx b/src/kiss/Reader.hx index 0c27bfc..e16f80b 100644 --- a/src/kiss/Reader.hx +++ b/src/kiss/Reader.hx @@ -23,6 +23,7 @@ class UnmatchedBracketSignal { typedef ReadFunction = (Stream, KissState) -> Null; typedef ReadTable = Map; +@:allow(kiss.Helpers) class Reader { // The built-in readtable public static function builtins() { @@ -292,6 +293,7 @@ class Reader { } public static function read(stream:Stream, k:KissState):Option { + assertNoPriorState(stream); return _read(stream, k); } @@ -323,7 +325,22 @@ class Reader { } } + static var nestedReadExpArrayStartPositions = []; + static var readExpArrayStartPositions = []; + + static function currentReadExpArrayStart() { + return readExpArrayStartPositions[readExpArrayStartPositions.length - 1]; + } + + static function assertNoPriorState(stream) { + if (readExpArrayStartPositions.length != 0) { + trace(readExpArrayStartPositions); + throw new StreamError(stream.position(), "Prior readExpArray() state is remaining in Reader"); + } + } + public static function readExpArray(stream:Stream, end:String, k:KissState, allowEof=false, startingPos=null):Array { + assertNoPriorState(stream); return _readExpArray(stream, end, k, allowEof, startingPos); } @@ -331,6 +348,9 @@ class Reader { var array = []; if (startingPos == null) startingPos = stream.position(); + + readExpArrayStartPositions.push(startingPos); + while (!stream.startsWith(end)) { stream.dropWhitespace(); if (!stream.startsWith(end)) { @@ -339,7 +359,7 @@ class Reader { case Some(exp): array.push(exp); case None: - if (allowEof) { return array; } + if (allowEof) { readExpArrayStartPositions.pop(); return array; } else throw new StreamError(startingPos, 'Ran out of expressions before $end was found.'); } } catch (s:UnmatchedBracketSignal) { @@ -354,6 +374,7 @@ class Reader { } } stream.dropString(end); + readExpArrayStartPositions.pop(); return array; } @@ -361,7 +382,13 @@ class Reader { Read all the expressions in the given stream, processing them one by one while reading. They can't be read all at once because some expressions change the Readtable state **/ - public static function readAndProcess(stream:Stream, k:KissState, process:(ReaderExp) -> Void) { + public static function readAndProcess(stream:Stream, k:KissState, process:(ReaderExp) -> Void, nested = false) { + if (nested) { + nestedReadExpArrayStartPositions.push(readExpArrayStartPositions); + readExpArrayStartPositions = []; + } else { + assertNoPriorState(stream); + } for (key => func in k.startOfFileReadTable) { if (stream.startsWith(key)) { var pos = stream.position(); @@ -398,6 +425,14 @@ class Reader { stream.dropWhitespace(); // If there was a comment, drop whitespace that comes after } } + + if (readExpArrayStartPositions.length != 0) { + throw new StreamError(stream.position(), "readExpArray() state is remaining in Reader after readAndProcess()"); + } + + if (nested) { + readExpArrayStartPositions = nestedReadExpArrayStartPositions.pop(); + } } public static function withPos(def:ReaderExpDef, pos:Position) {