<feed xmlns='http://www.w3.org/2005/Atom'>
<title>mojibake/docs/reviews, branch main</title>
<subtitle>text editor built to DO-178C-style rigor</subtitle>
<link rel='alternate' type='text/html' href='https://git.mojibake.wiki/mojibake/'/>
<entry>
<title>Normalise every byte offset at entry, and close MJB-DR-002</title>
<updated>2026-08-20T05:16:54+00:00</updated>
<author>
<name>rottedfm</name>
<email>rottedfm@proton.me</email>
</author>
<published>2026-08-20T05:16:54+00:00</published>
<link rel='alternate' type='text/html' href='https://git.mojibake.wiki/mojibake/commit/?id=07cef79834d91ac8db11857b0517697b0e994662'/>
<id>07cef79834d91ac8db11857b0517697b0e994662</id>
<content type='text'>
MJB-DR-002 records the failure mode byte indexing admits and char
indexing cannot express: an offset landing inside a character, which
makes ropey panic. It named two guards and asked the reviewer one
question — error or abort?

Answers the question with a rule. If saturating the input still yields a
sensible answer, saturate; if saturating would silently alter the user's
text, return an error. Aborting is rejected under MJB-HLR-018, and
because a bad offset can come from configuration, not only from internal
code. That splits the subsystem into total functions (offsets, line
indices, ranges — normalised at entry) and validating ones (change sets).

Checking the entry against the code found the defence incomplete beyond
the panic already fixed in the previous commit. `Range::cursor` returned
a raw head for a backward or empty range; `Range::line_range` clamped one
bound but not the other; `grapheme_str`, `line_end_byte`, `char_at` and
`char_before` validated nothing. All feed rope calls that panic — and not
only `insert`/`remove`: `slice`, `char_indices_at`, `byte_to_line_idx`
and `line` panic just as readily, which is what the earlier audit missed.

Two requirement problems surfaced with them. MJB-LLR-011 claimed
constructing a `Range` clamps its offsets to the nearest char boundary;
neither half was true, since `clamped` is opt-in and snaps downward. It
is restated, and the invariant it was reaching for is written down where
it actually holds — MJB-LLR-012 for what the document stores, MJB-LLR-013
for every public entry point. Backward traceability found this: the code
was right and the requirement was wrong.

`tests/boundaries.rs` drives every public entry point from outside the
crate with offsets that are out of bounds, mid-character or both, over
text including a four-byte scalar and a ZWJ cluster — of which the suite
previously contained none. It was checked against the defects it exists
to catch: reverting any one of the three guards makes it fail.

MJB-DR-002 moves to resolved, with a residual: the invariant is enforced
by convention plus that test, not structurally by a type that cannot hold
an invalid offset. Whether that is sufficient assurance at DAL-C is the
reviewer's judgement, and it is recorded as such.

Class:        Requirement change
Requirements: MJB-LLR-011 (restated), MJB-LLR-012, MJB-LLR-013 (new)
Derived:      MJB-DR-002 (resolved; five of seven now open)
Verified:     cargo build; clippy --all-targets -D warnings clean;
              cargo test 302 passing; ./scripts/check-trace.sh 101/101/101;
              cargo llvm-cov 96.50% of src/buffer/**

Co-Authored-By: Claude Opus 5 (1M context) &lt;noreply@anthropic.com&gt;
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
MJB-DR-002 records the failure mode byte indexing admits and char
indexing cannot express: an offset landing inside a character, which
makes ropey panic. It named two guards and asked the reviewer one
question — error or abort?

Answers the question with a rule. If saturating the input still yields a
sensible answer, saturate; if saturating would silently alter the user's
text, return an error. Aborting is rejected under MJB-HLR-018, and
because a bad offset can come from configuration, not only from internal
code. That splits the subsystem into total functions (offsets, line
indices, ranges — normalised at entry) and validating ones (change sets).

Checking the entry against the code found the defence incomplete beyond
the panic already fixed in the previous commit. `Range::cursor` returned
a raw head for a backward or empty range; `Range::line_range` clamped one
bound but not the other; `grapheme_str`, `line_end_byte`, `char_at` and
`char_before` validated nothing. All feed rope calls that panic — and not
only `insert`/`remove`: `slice`, `char_indices_at`, `byte_to_line_idx`
and `line` panic just as readily, which is what the earlier audit missed.

Two requirement problems surfaced with them. MJB-LLR-011 claimed
constructing a `Range` clamps its offsets to the nearest char boundary;
neither half was true, since `clamped` is opt-in and snaps downward. It
is restated, and the invariant it was reaching for is written down where
it actually holds — MJB-LLR-012 for what the document stores, MJB-LLR-013
for every public entry point. Backward traceability found this: the code
was right and the requirement was wrong.

`tests/boundaries.rs` drives every public entry point from outside the
crate with offsets that are out of bounds, mid-character or both, over
text including a four-byte scalar and a ZWJ cluster — of which the suite
previously contained none. It was checked against the defects it exists
to catch: reverting any one of the three guards makes it fail.

MJB-DR-002 moves to resolved, with a residual: the invariant is enforced
by convention plus that test, not structurally by a type that cannot hold
an invalid offset. Whether that is sufficient assurance at DAL-C is the
reviewer's judgement, and it is recorded as such.

Class:        Requirement change
Requirements: MJB-LLR-011 (restated), MJB-LLR-012, MJB-LLR-013 (new)
Derived:      MJB-DR-002 (resolved; five of seven now open)
Verified:     cargo build; clippy --all-targets -D warnings clean;
              cargo test 302 passing; ./scripts/check-trace.sh 101/101/101;
              cargo llvm-cov 96.50% of src/buffer/**

Co-Authored-By: Claude Opus 5 (1M context) &lt;noreply@anthropic.com&gt;
</pre>
</div>
</content>
</entry>
<entry>
<title>feat: implement Helix-style modal buffer under DO-178C DAL-C</title>
<updated>2026-08-19T15:21:47+00:00</updated>
<author>
<name>rottedfm</name>
<email>rottedfm@proton.me</email>
</author>
<published>2026-08-19T15:21:47+00:00</published>
<link rel='alternate' type='text/html' href='https://git.mojibake.wiki/mojibake/commit/?id=ea0bd36167b684c0accdb5ce2b2e21b8d84aeb25'/>
<id>ea0bd36167b684c0accdb5ce2b2e21b8d84aeb25</id>
<content type='text'>
The repository was an unmodified ratatui component template: no editor
code, JSON5 config, and placeholder widgets. This establishes the first
working baseline — `moji &lt;file&gt;` opens a file into a ropey rope and edits
it with Helix selection-first semantics.

Requirements, implementation and tests land together because they must:
the traceability check rejects requirements with no implementation and
tests naming requirements that do not exist, so neither half is a valid
commit on its own.

Package renamed to mojibake-editor (mojibake was taken on crates.io);
binary is moji, library target stays mojibake.

Class:        New behaviour
Requirements: MJB-HLR-001..019, MJB-LLR-001..205
Derived:      MJB-DR-001..007 (DR-001 resolved, six open for review)
Verified:     cargo build; clippy --all-targets -D warnings clean;
              cargo test 294 passing; ./scripts/check-trace.sh 98/98/98;
              cargo package clean

Co-Authored-By: Claude Opus 5 (1M context) &lt;noreply@anthropic.com&gt;
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
The repository was an unmodified ratatui component template: no editor
code, JSON5 config, and placeholder widgets. This establishes the first
working baseline — `moji &lt;file&gt;` opens a file into a ropey rope and edits
it with Helix selection-first semantics.

Requirements, implementation and tests land together because they must:
the traceability check rejects requirements with no implementation and
tests naming requirements that do not exist, so neither half is a valid
commit on its own.

Package renamed to mojibake-editor (mojibake was taken on crates.io);
binary is moji, library target stays mojibake.

Class:        New behaviour
Requirements: MJB-HLR-001..019, MJB-LLR-001..205
Derived:      MJB-DR-001..007 (DR-001 resolved, six open for review)
Verified:     cargo build; clippy --all-targets -D warnings clean;
              cargo test 294 passing; ./scripts/check-trace.sh 98/98/98;
              cargo package clean

Co-Authored-By: Claude Opus 5 (1M context) &lt;noreply@anthropic.com&gt;
</pre>
</div>
</content>
</entry>
</feed>
