| Commit message (Collapse) | Author | Age |
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
carries the session directory, not / and a rename
A pane named in the update that made it (Config's init file, a look
renamed on open) logged `rename N <name>` before `new N`, so a follower met
a serial it had never seen. The boot shell, started with no directory, was
announced as `new 1 /` and renamed once its shell spoke. Now noteLog drops
the rename of a pane not yet announced, since its new carries the name, and
announces a pane first for any other record about it. A terminal whose shell
has not said where it is is named by the session's directory, where it was
started, and the shell saying so is no rename.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
`>` write leaves the tag as it was
A column's or the workspace's tag took any length, so a write past 4096 bytes went in and a later Dump failed on it (bad dump tag), and a truncating open wiped any tag before the write after it could be refused. The column and workspace tags now refuse what a pane tag refuses: the 4096-byte limit (ENOSPC, tag: no space: over 4096 bytes) as well as the control characters they already did. A truncation of any of the three is held until the write after it is known to fit, and done with it; a refused write drops it; a close or read with no write after it does it then (so `: > tag` still clears). A test runs a truncating write too long, a control character and a bare truncation at each kind, and Dumps after. docs/fs.md says so.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
whole body: 60 KB appends go from 35.7 to 2.1 ms each
Round 25 measured bulk body writes at about 8 ms a write. There is no frame wait in it: a profile of open, write, clunk in a loop found the flush of each close walking the whole body five times. dotOf, setDot and showOffset turned the cursor between offsets and rows by counting every newline from the top; setContent found the line index's changed span by comparing old and new byte for byte, and hashed the new text to see whether it was back to the saved one. The rows now come from the file's line index by binary search (checked against the counting at every offset), a splice tells setContent the span it changed, and the text is hashed only when its length is the saved text's. Measured over 9P on a Debug build: 60 KB appends 35.7 to 2.1 ms, 8 KB 5.3 to 0.8 ms, 1 KB 1.3 to 0.9 ms. What is left is two copies of the text an edit (the splice's and the undo snapshot's). The perf gate gains body-appends, 64 appends of 8 KB on the 50k-line file, and its three baselines are recorded again.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
namespace's lowercase name
The last of the deferred renames, now that the tty and theme agents have landed: panes.terminal at its importers, the alias lines in Text.zig and File.zig and panes.zig's own uses following. dump.zig's Terminal struct, a dump record, is not this. The served sources list and docs/design.typ name the new file. test/perf.zig's references change, so the three perf baselines take its new harness id with their numbers as recorded. No behaviour changes.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
maps to ENOSPC as the docs say
The tree answers ENOSPC, but through a mount 9ns maps the words, and tag: over 4096 bytes carried none it knows, so a shell saw EIO. The words now hold no space; docs/fs.md says ENOSPC again.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
first step
A 9P write served before a detached host's first pump holds its batch stamped at time 0, so nextWake said to wake at 20 ms while advance, seeing the clock for the first time, set stepped_ns days later and counted due - stepped_ns back past zero: an integer-overflow panic. It was what the 64 KiB msize trial hit in fs-test (restore detached space, the connection closing at the first write's clunk), a race any msize can lose. A batch's wake is now never before the next frame.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
A write to tag longer than the room left was cut and applied in part. It now changes nothing and fails ENOSPC, tag: over 4096 bytes; the docs give the limit.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
is linear
Each body or data write copied and hashed the whole buffer, so a write the mount cut in 8 KB pieces was quadratic: 10 MB took 50 s and a 1 MB insert into 10 MB 11 s, holding the editor's turn. An open's appends to body, or inserts going on at data's address, are now held and put in as one splice (one copy, one undo step, one line-starts pass) before any other request, the close, or the editor's step once the writes pause 20 ms. fs.py-driven: 2 MB 2.19 -> 0.16 s, 10 MB 50.17 -> 0.78 s, 1 MB data into 10 MB 11.49 -> 0.26 s. A body-2m case (2 MB in 256 KB writes on one open) joins the perf gate: 84023 -> 15785 us; baselines re-recorded.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
it needs more
A last line with no newline was held to the close, so printf bogus > ctl answered 0 and failed only in the log, Edit ,s/zzz/y/ too. A write shorter than its Twrite is the whole of what was written (acme takes each write whole): its tail runs then and a failure is the write's. It is held only when the parser says it needs more -- an open { block, an a/c/i text -- or when the write filled its Twrite and may go on (the listener tells the core the room, msize less its header).
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
is a real refusal or says why it cannot fire
A sweep for round 23's crash: a run's answer (pty/run) was bufPrint'd into 48 bytes with catch unreachable, so a foreground program's long name (macOS gives up to 32 bytes) panicked; it now cuts at the room, keeping its newline, in 96 bytes. The rest were numbers into buffers sized for them, a braille codepoint, pthread calls on the queue's own mutex, and pdf_view's resolved outline entries: each now carries a one-line comment saying why it cannot fire.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
Both ends said a blank at its end.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
open
bash writes printf 'a\nb\n' a line at a time, so each line arrived as a whole name on the held open and renamed the pane twice. An open that has named its pane now refuses a further line, as a two-line write already was.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
A file deleted under an open buffer left dirty 0 and let Del, Exit and the rest throw the only copy of its text away unasked. It now counts as dirty, as acme's does, and the refusals ask about it.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
addr kept the old address under a failed one, and an address written relative to it went from that old one. Such an address now fails with no address: the last one written to addr failed, until one that stands alone is written.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
The body of a PDF pane read as empty. It now reads MuPDF's text extraction of the page shown, the text search and n/N already use, read-only (a write is refused, as round 22's body refusal made it).
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
The join mark a write left was the pane's, so another open's write joined the first open's step. Writing opens of body, data and xdata now get an open record, the mark names the open that set it, and another open's write starts its own step (the pane's one history: each turn the opens take is a step).
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
Each write to name was taken as a whole name, so a name a client wrote in two pieces renamed the pane twice, the first time to half a name. name's writes are now held per open, as exec's and ctl's lines are, until the newline or the close.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
room fails, and so does a write to an image's or PDF's body
Callers or Callees with nothing found, Hover or Lspwhy with no room for its pane, and a question asked of no file's pane said nothing, the 9P write succeeding; a body write to an image or PDF pane went nowhere. A write that asks a language server now waits for its answer (turn.lsp_answers), and what fails there -- nothing found, no answer, a backend's @none why, a placement with no room (ENOSPC) -- fails the write and logs its err. No diagnostics is said, not failed.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
A renamed scratch never saved and a /virtual/ pane were recorded as recent files, and at 200 the oldest entry went even when that file was open. Opens, renames and closes now record a path only when it is a file on this host, and the cap drops the oldest closed entry. A name with a newline is not written to the kept list, where it would read back as two.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
bash line-buffers its stdout, so printf 'x\ny\nz\n' > data arrives as three writes and took three Undos. A write now leaves the join mark a truncation already left, so the next write on the file joins its step until the open is released; a truncation and any other edit start a step of their own.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
closed file reopens it
A file closed by accident, its path forgotten, could not be found again:
the jumplist dropped closed panes. Every file opened (a look, a Save of a
scratch, a Restore, a rename) goes first in a list of 200, kept once, its
dot noted when it closes, kept across sessions in $XDG_STATE_HOME/pardes/
recent. `Recent` (SPC f r) shows it in a reused +Recent, each row
`path:line:col open|closed` a look reopens; /recent reads `open|closed
<path>`. The jumplist keeps a closed file's entries, +Jumps marks them
`(closed)`, and Back to one opens the file at its place. acme has no
such thing; its dump and Load are the nearest.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
| |
says so
A NUL written into a tag went into the dump, which the host then could
not write, and Dump said nothing: a success that wrote nothing. Tag
writes, the workspace's, a column's and a pane's, refuse control
characters but tab and newline, DEL, C1 and bytes not UTF-8, EINVAL; and
Dump reports any failure of its own instead of swallowing it.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
| |
name as \n
/index printed a name as it was, so a directory with a newline in it split
its row in two, and bytes not UTF-8 went through; the log turned the
newline into a space, silently another name. Both now show a name one
way: a newline `\n`, other controls, DEL and C1 a space, bytes not UTF-8
`\xNN`.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
| |
character
An empty name, a word written to log other than follow, a data, sel, dot
or dirty write to a pane with no text, a truncate other than to zero,
and a control character in a look line written through a held open were
refused with no words, logged as `Invalid argument`. Each says its reason
now; and DEL is refused in exec and look lines as in names.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
one line of UTF-8
A name took a second line, DEL, a C1 control or bytes that are not UTF-8,
which then went into /index and /log as they were and split or garbled a
reader's lines. `name` strips one trailing newline and refuses the rest,
saying which (`bad character in file name: not UTF-8`); and the log turns
DEL and C1 into spaces, as it did control characters, and escapes bytes
that are not UTF-8 as `\xNN`.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
| |
Any rename marked the pane dirty (saved revision one back), while the
guards ask only whether its text was ever edited: /index said dirty for a
pane Exit let go without asking. The name is no edit now, so /index, the
guards and Restore agree; Save writes under the new name all the same.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
| |
`name` trimmed blanks off both ends, so `trailing.zig ` named another
file than the one written without a word. acme refuses any blank in a
name, `bad character in file name` (xfid.c:650); pardes takes one inside
(it names files with spaces) and now refuses one at an end, and a
control character, in acme's words.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
| |
active pane's
No pane asked for it, so borrowing the directory of whichever pane last
had the keyboard named it after an accident; acme's new window has acme's
directory.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
argument
Writing a chorded exec's three records back as read ran the argument
and its location as shell commands. The first record (flag 8) now takes
the next record as its argument when it comes in the same write, else
the one kept from the click (or, with none kept, waits for it); its two
follow-up records, however they are written, are consumed as its, never
run. Tested written back together and one per write.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
| |
The workspace had /tagexec and a column its exec, but a pane's own tag
could be clicked only by an event record. pane/<n>/tagexec runs each line
as a click in that pane's tag (never redirected to its event reader, as a
header's is not) and reads back what it touched. The README, fs.md and
the skill list it.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
| |
With event open, a 2-1 chord's exec went out as one record with flag 8
and nothing after it: the argument was freed unsaid. As acme does
(exec.c:150-190), two records follow it, the argument's text and where
it came from (file:#q0,#q1, empty when not known), and the pane keeps the
argument, so the record written back runs with it (acme's own write-back,
xfid.c:842, passes none; the reader was told, so it runs as the click
would have).
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
| |
Edit's p and = put their output in +Errors, and when its column had no
room the placement refusal failed the whole Edit. +Errors now tries every
column with room, the last first, and with none its text is logged as msg
records, a line each; the Edit succeeds.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
| |
With no address after a failed write, a read of addr itself failed (EIO
through a mount), which reads as a broken file rather than as no address.
It now reads empty, as an unset limit does; data and xdata still refuse.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
| |
A shell's > truncates limit, which lifted it, before the write; a write
that then failed left no limit at all. The truncation now keeps the old
limit until that open's write, and a failed write puts it back; a bare
truncation still lifts it once its open is released.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
| |
sam and acme address runes; pardes snapped #n, line:col, dot and data's
reads to grapheme clusters, so a lone combining mark or a CRLF's \r could
not be addressed. #n, line:col, a search's match, dot (both ways) and data
now land on rune boundaries (modal.runeStart and friends), and the tty's
cell drawing is untouched. The README, fs.md and the skill say so.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
| |
/col/<n> named a column by its index, which shifts when a column left of it
closes: exactly what scripts trip on. A column is now /col/<serial>, its
serial kept while it lives and never reused; /layout lines give serial and
index (`<serial> <index> ...`), active names the serial, /index's last
field is the column's serial, and the log says newcol and delcol with
serials. Docs, the skill and the tree's README say so.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
A script could not see where the panes sit or edit the tags a person
clicks in. /layout lists each column, its index, x and width in cells,
current or not, empty or full, and its panes' serials, then the active
column; /tag is the workspace tag and /col/<n>/tag a column's, read and
written as a pane tag is (one line: a newline written in is a space, and a
truncating write drops the one ending it); /index's lines end with the
pane's column; the log says newcol <n> and delcol <n>. acme serves no
column files, and the docs say so.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
| |
takes no name
`echo Del > pane/6/exec` just after pane 6 closed failed EACCES: the shell's
lookup failed, it tried to create the file, and the engine refused every
Tcreate as a permission error. pardes now takes Tcreate itself: refused as
before (acme's fsyscreate refuses it too), ENOENT in a pane that has
closed. Renaming a terminal was refused with only EPERM; it now says a
terminal is named by its shell's directory, worded so a mount still maps
it to EPERM.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
| |
`echo X > tag` stored X and a trailing newline, which drew an empty tag row.
After a truncation the newline ending each write is held back until more
text follows or the open is released, so the one ending the whole of it is
dropped and any other stays; `>>` keeps what it is given.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |\ \ |
|
| | | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
makenewwindow puts them
Newcol makes an empty column; closing a column's last pane leaves it empty with
the keyboard on its tag; Delcol and Joincol alone take a column away; the
session's last pane closing quits. The +New stand-in and replaceStillborn /
stillborn_joiner are gone. Every new pane goes through exec.placeNew, which
follows acme's makenewwindow (active column, empty column whole, blank space,
halving the biggest) or, with Placement pardes, the old rules. ColumnTags is
gone: column tags are always shown. A grip drag shows acme's box cursor.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| | | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
A dogfood agent wrote winsize 100 30 to pty/ctl and pty/status went on
reporting the pane's grid, and the status line had no newline to end it.
The size winsize sets is kept until the pane resizes and gives the pty its
grid again; ctl's winsize read back and status both report it, and status
ends with a newline.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| | | |
| | |
| | |
| | |
| | |
| | | |
A shell's printf x > data truncates the addressed range and then writes, and each pushed its own undo point, so one replace took two Undos. A truncation of data, xdata or body now lets the write that follows it at once join its step, as acme's replace is one.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |/ /
| |
| |
| |
| |
| | |
mark 0 skipped the undo point of each write, and mark 1 then pushed the text as it had become, so the text from before the batch was in no step: with no history before it, no Undo brought it back. Turning mark off now keeps the text as it is, and the writes after it are one step back to it, as acme's nomark joins them.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| | |
| |
| |
| |
| |
| | |
Truncating addr reset it to #0, so a shell's find-and-replace loop matched the first hit for ever, .+#1 read 1 1 each time, and foo x foo y foo became foobarbarbar... acme resets addr on the first open (xfid.c:105-108), for clients that hold the fid; a shell cannot. Here neither an open nor a truncation resets it: the address written is evaluated from the last one, and 0 or , starts over. Documented as a departure from acme.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |/
|
|
|
|
| |
The refusal `takes 1 or 0` matched none of 9ns's words, so a mount turned it into EIO. It now starts `bad flag:`, which 9ns maps to EINVAL, as it did the bare errno before.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
| |
A failure read `Del k|j: InvalidArgument`, `Kill: NoSuchCommand`, `ill-formed control message`, or nothing at all. reportError now spells an error's name as words, and the refusals name their accepted forms: pty/ctl lists its verbs, a flag file takes 1 or 0, a setting word takes on or off, Del takes k, j or nothing, Repl takes - or a language. Kill with nothing to stop says so, /focus says pane, a Look that found nothing says no match, and pty/run on a command pane says it is not a shell. A ctl write's failure has room for the Repl list and is cut between words, the Repl word at a character.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
| |
stat said a terminal's body was 0 bytes while a read gave its screen and
history, and the docs promise real sizes; a client that sizes its read from
stat got nothing. The length is now that of the text a read answers, counted
the way the pane's ctl line already counts it.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
is refused
-/re/ searched forward, since only ?re? set the direction, where acme's
address() takes the direction a minus set (addr.c). And #100,#50 was taken,
leaving data to act on an empty range at 100; sam refuses it as 'addresses out
of order', which acme leaves out, and so does pardes now. The rest of the
dogfood report on addresses already held and is now tested: an expression is
evaluated from the current address, as acme evaluates it from w->addr
(xfid.c:446), so a search starts where the last address or data write left
it and . is that address. Taking . as the selection instead, as the report
asked, would part from acme, which has dot only in its ctl messages; the docs
say which is which.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
failed addr leaves no address
addr's regexps ran mvzr over text[from..hi]: ^ and $ anchored only at the
slice's ends, . matched newlines, the search never wrapped, and every
failure read as bad address syntax. The regexps stay mvzr's, called the
way sam searches (editors/acme/regx.c): one line per haystack, so ^ and $
fall at line boundaries and . never crosses a newline; a pattern naming
\\n runs over the whole text with its . made [^\\n]; /re/ wraps unless
limit is set, and ?re? takes the last match before the range. The ceiling
(mvzr's first alternative, not sam's longest) is documented. A failed
address says why (no match for regexp, address out of range, bad regular
expression), and a failed write to addr leaves no address, so data and
xdata refuse until the next good one instead of writing at the old range.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
|