From 39066900773e7857faf2d02e7ed51b71d219d97d Mon Sep 17 00:00:00 2001 From: godosa Date: Tue, 6 Oct 2026 23:39:36 +0200 Subject: godosa-engine: initial public history --- src/Godosa.Core/Runs/Scripts/ScriptProgram.cs | 57 +++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) create mode 100644 src/Godosa.Core/Runs/Scripts/ScriptProgram.cs (limited to 'src/Godosa.Core/Runs/Scripts/ScriptProgram.cs') diff --git a/src/Godosa.Core/Runs/Scripts/ScriptProgram.cs b/src/Godosa.Core/Runs/Scripts/ScriptProgram.cs new file mode 100644 index 0000000..502e24c --- /dev/null +++ b/src/Godosa.Core/Runs/Scripts/ScriptProgram.cs @@ -0,0 +1,57 @@ +// Provenance: own design — shared run scripts +namespace Godosa.Core.Runs.Scripts; + +public enum Op { Verb, Wait, Expect, Set, Checkpoint, LabelBegin, LabelEnd, ScopeBegin, ScopeEnd, TryBegin, TryEnd, SetupBegin, SetupEnd } + +/// One flattened instruction. = include / call sites, outermost first. +public sealed record Instr(Op Op, SourceRef At, string Text, IReadOnlyList Chain, int Format) +{ + public string A { get; init; } = ""; + public string B { get; init; } = ""; + public int Timeout { get; init; } + public IReadOnlyList> Bindings { get; init; } = []; + public bool LocalVars { get; init; } + public int Jump { get; init; } = -1; +} + +public sealed record ScriptProgram(string Entry, RunMode Mode, ulong? Seed, IReadOnlyDictionary Vars, + IReadOnlySet Locked, IReadOnlyList Code, IReadOnlyList Errors); + +public interface IScriptSource +{ + string? Read(string path); +} + +public sealed class MemoryScriptSource(IReadOnlyDictionary files) : IScriptSource +{ + public string? Read(string path) => files.GetValueOrDefault(path); +} + +/// Files under ; paths are '/'-separated and relative to it. +public sealed class FileScriptSource(string root) : IScriptSource +{ + public string? Read(string path) + { + var full = Path.GetFullPath(Path.Combine(root, path)); + return File.Exists(full) ? File.ReadAllText(full) : null; + } +} + +public static class ScriptPaths +{ + public static string Resolve(string fromFile, string relative) + { + var dir = fromFile.Contains('/') ? fromFile[..fromFile.LastIndexOf('/')] : ""; + var parts = new List(dir.Length == 0 ? [] : dir.Split('/')); + foreach (var part in relative.Replace('\\', '/').Split('/')) + { + if (part is "" or ".") + continue; + if (part == ".." && parts.Count > 0) + parts.RemoveAt(parts.Count - 1); + else if (part != "..") + parts.Add(part); + } + return string.Join('/', parts); + } +} -- cgit