New OSC parser (#9950)

This replaces the OSC parser with one that only uses a state machine to
determine which OSC is being handled, rather than parsing the whole OSC.
Once the OSC command is determined the remainder of the data is stored
in a buffer until the terminator is found. The data is then parsed to
determine the final OSC command.

```
→ poop './zig-out/bin/ghostty-bench-old +osc-parser --data=osc.txt' './zig-out/bin/ghostty-bench +osc-parser --data=osc.txt'
Benchmark 1 (3 runs): ./zig-out/bin/ghostty-bench-old +osc-parser --data=osc.txt
  measurement          mean ± σ            min … max           outliers         delta
  wall_time          4.19s  ± 69.1ms    4.12s  … 4.25s           0 ( 0%)        0%
  peak_rss           5.86MB ± 37.8KB    5.84MB … 5.91MB          0 ( 0%)        0%
  cpu_cycles         15.3G  ±  330M     14.9G  … 15.5G           0 ( 0%)        0%
  instructions       41.1G  ± 7.81      41.1G  … 41.1G           0 ( 0%)        0%
  cache_references    130M  ± 2.40M      128M  …  132M           0 ( 0%)        0%
  cache_misses        658K  ± 88.5K      603K  …  760K           0 ( 0%)        0%
  branch_misses      31.5M  ±  112K     31.4M  … 31.6M           0 ( 0%)        0%
Benchmark 2 (4 runs): ./zig-out/bin/ghostty-bench +osc-parser --data=osc.txt
  measurement          mean ± σ            min … max           outliers         delta
  wall_time          1.54s  ± 7.08ms    1.53s  … 1.55s           0 ( 0%)        - 63.3% ±  2.1%
  peak_rss           5.84MB ±  270KB    5.45MB … 6.02MB          1 (25%)          -  0.4% ±  7.1%
  cpu_cycles         6.07G  ± 7.82M     6.06G  … 6.08G           0 ( 0%)        - 60.3% ±  2.7%
  instructions       17.3G  ± 39.5      17.3G  … 17.3G           1 (25%)        - 57.8% ±  0.0%
  cache_references   64.7M  ±  655K     63.8M  … 65.3M           0 ( 0%)        - 50.4% ±  2.4%
  cache_misses        733K  ±  116K      611K  …  890K           0 ( 0%)          + 11.4% ± 31.7%
  branch_misses      21.7M  ±  167K     21.5M  … 21.9M           0 ( 0%)        - 31.3% ±  0.9%
```
This commit is contained in:
Jeffrey C. Ollie
2026-01-08 14:35:00 -06:00
committed by GitHub
4 changed files with 966 additions and 1299 deletions

View File

@@ -100,8 +100,8 @@ fn step(ptr: *anyopaque) Benchmark.Error!void {
error.ReadFailed => return error.BenchmarkFailed,
};
for (osc_buf[0..len]) |c| self.parser.next(c);
_ = self.parser.end(std.ascii.control_code.bel);
for (osc_buf[0..len]) |c| @call(.always_inline, Parser.next, .{ &self.parser, c });
std.mem.doNotOptimizeAway(self.parser.end(std.ascii.control_code.bel));
self.parser.reset();
}
}

View File

@@ -359,7 +359,7 @@ inline fn doAction(self: *Parser, action: TransitionAction, c: u8) ?Action {
break :param null;
},
.osc_put => osc_put: {
self.osc_parser.next(c);
@call(.always_inline, osc.Parser.next, .{ &self.osc_parser, c });
break :osc_put null;
},
.csi_dispatch => csi_dispatch: {

View File

@@ -17,6 +17,10 @@ pub const OSC = struct {
/// request.
terminator: Terminator = .st,
pub fn deinit(self: *OSC, alloc: std.mem.Allocator) void {
self.list.deinit(alloc);
}
/// We don't currently support encoding this to C in any way.
pub const C = void;

File diff suppressed because it is too large Load Diff