What’s new in Speech Layer
Every notable change to Speech Layer, grouped by day, newest first. Built straight from the project git history.
September 9, 2026
1 commit- Docs
Commit messages must never name panes, callsigns, or clients - subjects and bodies are public via the speechlayer.com changelog, so use <pane> and generic wording instead
- Mailbox
Document boss-pane task handoff routing in the mailbox AGENTS.md
September 4, 2026
11 commits- Fix
Bounce-worker hardening for set -e + pipefail - grep with no match inside command-substitution assignments (Exec line parse, workspace count) would abort the detached worker before verification and the orch/boss report
- CLI
New 'speechlayer kill' takes the whole herdr fleet down in order - helper daemons (orch-watcher, callsign-sync, pane-healer, fanfare, keys-guard, compaction-guard), stray pi procs (own ancestor chain excluded), speechlayer window, then 'herdr server stop' last since it kills every pane PTY - voice stack (whisper-voice-daemon, say/TTS, OpenRC services) deliberately untouched - verified no cron/OpenRC/watchdog respawns the fleet, so it stays down until the Desktop shortcut / speechlayer-session-open reopens it
- CLI
New 'speechlayer bounce' is a full simulated reboot - snapshots pre-state, then a setsid+nohup fully-detached bounce-worker (stdio to /dev/null) kills the fleet, re-runs the exact XDG autostart Exec lines (herdr-server, callsign-sync, fanfare, keys-guard, pane-healer, compaction-guard, session-open; %-codes expanded, Hidden/disabled skipped) so restart and reboot can never drift apart, then verifies herdr status green + helpers + window and logs to /tmp/speechlayer-bounce.log, and reports the result to the orch + boss agents with retry
- Docs
README + AGENTS warn never to pkill speechlayer processes (half-kills the voice stack, leaves the fleet running) - use 'speechlayer kill' / 'speechlayer bounce' instead
- TTS
Say-pocket-impl aplay gets a deep ring buffer (--buffer-time, PK_APLAY_BUFFER_US default 500 ms) so CPU storms cannot starve playback into jitter between scheduler slices
- Install
Cpulimit added to PKGS_CORE (hard duty-cycle cap behind training/selfthrottle.py) and INSTALL.md documents the self-throttle stack
- Shell
Llm() gguf picker now uses find -printf + sort instead of ls -t (mtime order across both dirs)
- Add voice-stats.sh
Per-channel message origin breakdown from pi session logs
- TTS
Voice-barge playback-start grace (~1.1s) so a wake word spoken as say begins cannot kill it
- Email-pi-bridge
Fix cross-project reply leak (turn binding + resolution gate + mailbox handoff)
- TTS
Training/generation self-throttle now enforces a hard CPU duty-cycle cap - selfthrottle.py spawns a sibling 'cpulimit -l <TRAIN_CPU_CAP|30> -p <self>' before nice/pin, because nice 15 + core pinning alone still let 3 pinned gen_samples.py hold load >20 and jitter say (live retest 2026-09-04); SIGSTOP/SIGCONT throttling composes with nice/affinity since it is orthogonal to scheduler priority
- Fix
Self-spawned cpulimit must never get -i (include-children) - cpulimit is a child of its own target and -i makes it SIGSTOP itself, parking the target in state T forever; verified and documented in selfthrottle.py and speechlayer.md
- Audio
Nice-guard now also spawns a NICE_GUARD_CPU_CAP% (default 30, 0 disables) cpulimit on discovered training-class pythons that did not self-cap - belt and suspenders; procs already carrying a cpulimit are detected by cmdline probe and skipped so two cyclers never compound on one pid
- Verified
Burner at cap 30 holds ~29-31% and TRAIN_CPU_CAP=50 holds ~47-52% with nice 15 + pinning + thread caps all applied, duplicate-tag flock still refuses (exit 1), per-shard locks still coexist, TRAIN_ALLOW_MULTI=1 still bypasses, real gen_samples.py launches show 'cap=30% (cpulimit pid N)' in the banner
- Docs
Speech Layer TTS CPU Protection and tts/README CPU priority sections describe the cap layer, TRAIN_CPU_CAP/NICE_GUARD_CPU_CAP knobs, and the -i self-stop gotcha
- Docs
Broken-pane session recovery procedure (boss touch-loop incident 2026-09-04)
- Voice
Addressed 'tell <pane> stop talking / be quiet / shut up' now toggles /say off on that pane immediately - addressing the pane by name is the consent, so no yes/no question is asked
- Voice
Addressed 'tell <pane> start talking / speak up' toggles /say on immediately
- Voice
Both acknowledgements state how to reverse it ('<pane> muted, say tell <pane> start talking to unmute' / '<pane> unmuted, say tell <pane> stop talking to mute')
- Voice
STT-mangled toggle phrases ('stop talk', 'stop talk start talking again') now match the toggle intent instead of being delivered to the pane as chat text
- Voice
The yes/no confirmation pattern stays available for other flows - it is no longer wired into this toggle
- TTS
Permanent fix for say CPU starvation - training/generation scripts self-throttle at launch via training/selfthrottle.py (nice 15, pin to cores 0..nproc-3 leaving two audio cores, OMP/BLAS thread caps, per-shard single-instance flock) wired into gen_samples.py, train-hey-speechlayer.py and train-kapish.py before any heavy import
- Audio
Nice-guard moved into the repo as core/nice-guard.sh (~/.local/bin/nice-guard is now a symlink, autostart unchanged) and extended to renice + pin tts312/wakeword-train venv pythons and speechlayer/training scripts
- TTS
Say-pocket-daemon self-applies nice -10 at startup via the new root helper system/linux/speechlayer-audio-rt + sudoers rule (sudo system/linux/install-audio-rt.sh once), graceful logged fallback to nice 0 without it; fix_pocket_tts re-applies on speechlayer restart
- Audio
Nice-guard watchdog renices top unprotected CPU hogs to +15 (training class also pinned) whenever load exceeds nproc-1 while the say queue is active
- Docs
Speech Layer TTS CPU Protection section, tts/README CPU priority section
- Voice
Addressed 'tell <pane> stop talking / be quiet / shut up' offer now re-opens the mic for the answer instead of leaving the daemon deaf until the offer TTL expired
- Voice
Every yes/no confirmation times out after eight seconds of silence only and defaults to no, and any real speech resets the window
- Voice
A spoken yes or no is consumed by the pending confirmation gate, never typed into the pane as a chat message
- Fix
Whisper hallucinating 'yes' or 'music playing' from a quiet room no longer confirms the mute - noise probes never early-cut, a whole-probe gate plus a silence-anchor buffer trim keep the fiction out of the transcript, and a low-confidence sidecar lets the gate refuse it
- Docs
Internals documents the reusable yes/no spoken confirmation pattern so other flows (spawn-offer, pane-close) can adopt it
- Voice
Per-pane 'stop talking' now confirms before muting - the discriminant is whether the pane was addressed by name
- Voice
Bare shut up / stop talking / be quiet keeps the existing global soft cut, no question, no state change
- Voice
Addressed 'tell <pane> stop talking / be quiet / shut up' barges the current say with the short offer 'Tell <pane> not to respond verbally from now on?' and waits for yes or no
- Voice
Yes runs /say off on the addressed pane (persistent mute); no or TTL expiry changes nothing
- Voice
Tell <pane> start talking / speak up runs /say on directly with no confirm
- STT
Say-off consent reuses the spawn-offer pending state (kind=say_off on the shared file, pane_id pinned) with yes/no resolved against the offer, never parsed as a fresh tell; arm timestamp persisted so the spoken answer lands in a separate daemon process; legacy spawn-offer schema unchanged for the phone bridge
September 3, 2026
1 commit- STT
Add a callsign respell to the user respell dictionary
September 1, 2026
8 commits- Fix
Privacy index never seeds English function words as names (From: The client-site no longer masks every 'the' thread-wide)
- Fix
Stopword-class tokens are never replaced at masking time, whatever a legacy store entry says
- Privacy
Load-time migration purges seeded names whose token is a stopword or NEVER word and evicts their orphaned fakes (live store: 1 entry cleaned, name:the)
- Privacy
Migrate CLI command rewrites the store and reports the purge count
- Tests
The client-site seeds surname only, a sentence of pure function words masks nothing, legacy store with name:the migrates clean
- Fix
Herdr early-cut no longer fires on a structured tell - a comma or other separator from a mid-sentence breath pause keeps listening instead of stopping the recording (the 'read me out' cut)
- STT
Adaptive silence/speech threshold learned per mic source from whisper probe verdicts (WVD_ADAPTIVE_THRESH, default on) so quiet laptop-mic speech is no longer invisible to every energy guard
- STT
Learned threshold is clamped between a small floor and the old fixed 150, persists per mic source, and feeds the silence wall, its recheck, both trailing-pause guards, and the transcript-silence energy guard
- Docs
Internals env table documents the adaptive threshold knobs
- STT
Respell Shoplight to shoplite (project name) in the proper-nouns dictionary
- STT
Respell pain to pane unconditionally (Whisper mishear in herdr context; real-word tradeoff accepted)
- Refactor
Extract terminator probe into named configurable strategy (WVD_TERM_MATCH_MODE, default trailing - no behavior change)
- Docs
Silence auto-stop docs now match the 8 s WVD_SILENCE_S code default (was documented as 30 s in wake-words, internals, README, speechlayer)
- Fix
SpeechLayer mic-route keeps pinned Shokz USB through standby instead of falling back to the laptop internal mic
- Fix
Sticky USB pin written on ensure, wiped only on true USB disconnect (card gone), re-picked on USB reappear
- SpeechLayer
Speech Layer-mix.sh mic_source now prefers the sticky USB source while its card is still listed
- Icon
Render correct favicon.svg (blue bubble + waveform) at 180x180, transparent
- Icon
Flood-fill only outside bubble, keep white shirt glyph intact
August 31, 2026
12 commits- Install
Also install speechlayer.png to hicolor when writing desktop shortcut
- Desktop
Install icon to hicolor + reference by name (survives DE icon-cache reloads)
- Install
Add speechlayer-session-open to symlink set (repairs bin targets after renames)
- Install
No-op idempotent re-link for pre-existing targets
- Desktop icon
Transparent PNG background (only bubble opaque)
- Install
Mark ~/Desktop shortcut as trusted (no more Unrusted application launcher prompt)
- Install
Write ~/Desktop/Speech Layer.desktop with favicon icon (no more broken pi-surf-session-open)
Favicon assets vendored under assets/favicon/ for desktop + web parity
Wake word renamed to hey_speechlayer.onnx (was hey_marvin_v0.1)
- Wake UI
Friendly labels in notifications (no raw model names or scores)
- Bashrc
Personal speechlayer=speechlayer alias
- Docs
Os-adapters leftover identifier
- Docs
Rename leftover speechlayer identifiers in live docs
Rebrand speechlayer -> speechlayer: tree move, identifiers, paths
Rename pi-surf family to speechlayer/surfagent; drop surfagent force-loading
August 28, 2026
1 commit- STT
Wharton now respells to speechlayer in all STT entry points (wharton → speechlayer)
August 26, 2026
2 commits- Convention
The service-pane registry, spawn wrapper, and scaffold are live - code owns routing and never-do gates, prose owns domain behavior - and mailbox is migrated as the first citizen
- Fix
Voice say-that-again now falls back to the pane text store when the audio ring is empty, and the say queue daemon no longer lets a leaked SAY_TAG from its launching shell suppress all replay capture
August 25, 2026
1 commit- Router
Voice routing now asks nemotron instead of ling, and a leftover kimi pin in the environment was brought in line with it
August 24, 2026
9 commits- Rename
The hey-speechlayer voice window now opens as speechlayer instead of pi-surf, and everything that looks for the window by name was updated to match
- Fix
A pasted clipboard image path can no longer end up in the window title
Revert "- [x] Rename: The hey-speechlayer voice window now opens as speechlayer instead of pi-surf, and everything that looks for the window by name was updated to match"
- Rename
The hey-speechlayer voice window now opens as speechlayer instead of pi-surf, and everything that looks for the window by name was updated to match
- Fix
A pasted clipboard image path can no longer end up in the window title
- Terminology
The voice status and restart readouts now say speech layer instead of voice infrastructure
- Fix
Voice barge-in no longer loops a replayed sentence, the replay plays through unless you stop it
- Fix
Replay now sets a marker while a re-spoken clip is on the speaker so the barge-in detector leaves it alone
- Fix
Voice commands like say that again and say off no longer get typed into a pane as chat text, they run the speech control and answer aloud
- Fix
Replayed speech no longer interrupts itself in a loop when you talk over it
Fix spoken repeat command not firing when a source tag is attached. Saying "say that again" with the trailing origin tag (the "[voice]" the inject path adds, or the phone "[xmpp]"/"[email]" tags) left a stray trailing word after the brackets were stripped, and that broke the whole-utterance match so the repeat never happened and the words were typed as prose instead. The same fragility hit every whole-utterance voice command (new/delete/compact session, shift-tab, thinking level, clear). The transform now strips a trailing voice/email/xmpp tag word before matching commands, while leaving real command words alone (so "close pane", "cycle thinking", "new voice" still work). Verified: "say that again [voice]" now triggers the repeat, and "please say that again for me [voice]" still passes through as prose.
Barge-in during a spoken agent summary now stops the whole readout, not just the sentence. The energy/wake barge-in was wired to say --skip (cut only the playing sentence, leave the rest of the summary queued). Switched it to say --skip-group, which also drops the still-queued sentences that share the playing summary's group. Other panes' queued speech is untouched, and an ungrouped utterance still just skips the current sentence. Hard shut-up (say --stop) is unchanged.
August 23, 2026
3 commitsRewrite leg follows the pane router to inclusionai/ling-3.0-flash so both cloud paths share one model. Extend the reasoning-off gate in _post_chat to cover ling (it was nemotron-only); with effort none ling matches nemotron on rewrite, without it ling returns NONE. Keep reasoning effort none. Revert: SL_REWRITE_MODEL=nvidia/nemotron-3-nano-30b-a3b
- Router cloud leg
Swap nemotron for inclusionai/ling-3.0-flash (reasoning effort none + max_tokens 8 mandatory; thinking on returns empty). Needle POST shape already correct (query/panes), no fix needed. Update the rewrite-model comment in wvd-herdr-control to note the router diverged. Revert: SL_ROUTER_MODEL=nvidia/nemotron-3-nano-30b-a3b
Remove stale .bak copies next to live dictate/herdr scripts, and make the whisper-server model overridable via WHISPER_MODEL (default ggml-base.en.bin) instead of a hardcoded path; fix the WHDISPER_MODEL typo in speechlayer.md
August 20, 2026
1 commitKeep HTML email links so the LLM sees the actual URLs.
August 19, 2026
3 commits- Voice routing
Local first, one cloud model, no more wrong-pane injections.
Reminders no longer talk over Speech Layer: one speech queue, and the ding waits its turn.
Stop cutting mid-sentence on "tell my browser" and trailing please.
August 18, 2026
4 commitsWhisper-voice-daemon: recheck recent audio before silence wall-timeout cuts (fix mid-sentence cut-outs under CPU load); load canonical cancel phrases from speechlayer_cancel_phrases.py
- Voice
When the phone and the headset both hear the same sentence, only one message reaches a chat pane - near-duplicate repeats within 90 seconds are dropped, and short replies like yes or Resume always still go through
- Voice
Needle 2, a tiny on-device command model, tidies misheard voice commands (like 'even those out' becoming 'balance panes') with no internet call
- Voice
The wake-word mic now follows whichever microphone is selected in sound settings, including headset plug and unplug, instead of staying stuck on the old one
August 13, 2026
4 commits- Say
If you start talking while a reply is playing, it pauses and finishes after you stop
- Say
Replies never start over an open mic, and stop or skip still cut through right away
- Docs
The public changelog page now refreshes itself on every push, so it can no longer fall behind the real history
- Say
Every queued play re-checks the current speaker so headset and laptop no longer swap mid-burst
- Say
The play log now notes which speaker was used, so a future mix-up is one search away
- Phone
Raise wake-record hard cap from 40s to 60s (SL_RECORD_S)
August 12, 2026
3 commitsPi compaction-freeze guard: watchdog daemon + install wiring
- Voice barge-in
Say 'barge in' before a message to interrupt a busy pi pane (Esc) and submit fresh instead of queueing as a steer; works after a callsign ('tell features barge in …') and after a workspace route, and never triggers on mid-sentence 'barged in'
Say again now speaks on panes whose replies were never read out loud
August 6, 2026
2 commitsAdd 'speechlayer calibrate stop' - cancel an in-flight barge battery (SIGINT, SIGTERM after 3s); watcher untouched
- Restart
Fix 'running but no state file' race + set -e mid-restart abort
August 5, 2026
1 commit- TTS
Stop mid-sentence cutoffs (root-cause + hardening)
July 30, 2026
7 commits- Say
Spoken replies are kept as short audio clips, so say --replay and /say again play back exactly what you heard instead of generating it again
- Say
Keeping those clips is off by default and only starts once you turn it on, it never keeps more than five, and each pane only replays its own messages
- Say
Asking for a replay cuts whatever is playing and clears your own backlog, while other panes keep their queued messages and play right after
- Say
The talking queue, the always-ready pocket voice, and the skip-what-is-playing hotkey script now ship with the repo so a fresh install gets the whole setup
- Pi
/say again replays your pane's last answers, and each workspace can have its own voice or stay muted
- Fix
Wifi watchdog only nudges saved networks, never when wifi is already up, so phantom password popups stop
- Fix
Voice commands now catch plural mis-hearings like cue bolts and fix them to client-site
- Docs
Personal API keys (BYOK) now covered in README, INSTALL, speechlayer and AGENTS
- Docs
Listen mode explains always-listen at boot and how talking over the agent becomes the next turn
- Docs
Portability table lists the personal-keys file alongside the other per-machine settings
- Docs
Add the Needle page that AGENTS.md already pointed to
- Barge
Sensitive mode now pulls talk-over loopback knobs from one list
- Barge
Residual floor can go up to 80k so big calibrations are not clamped away
- Say pocket
Workspace voice map plus per-voice gain file after pane resolve
- Say pocket
File export bakes gain so soft voices stay leveled off-play
- Say server
Pocket engine through the warm daemon for phone TTS
- Phone bridge
Xmpp inject uses herdr agent prompt (atomic submit) with pane send-text plus Enter as fallback
- Phone bridge
Multi-step marker sequences paste via pane send-text since agent send is gone
- Email bridge
Sticky default heals from legacy mac to herdr and auto-spins the my workspace home lane when it is missing
- Email bridge
Ensure_agent_lane creates workspace, splits pane, and starts the pi agent for a callsign
- Email bridge
Wait_idle requires a busy sighting or sustained idle so a mid-retry spinner never becomes the emailed reply
- Email bridge
Screen scrape drops spinner glyphs, retry countdowns, error toasts, and the pi status bar
- Email bridge
Reply comes from the session log and keeps waiting while the agent is still busy
- Outbox
Xmpp-outbox-drain pulls per-site commit outboxes over ssh and fans out to xmpp, ntfy, or webpush recipients
- Outbox
Drain restores curly quotes mangled into U+XXXX placeholders, raw JSON escapes, and common HTML entities
- Bridge
Xmpp-pi-bridge-ensure idempotent supervisor refreshes the D-Bus address and heals the pidfile
- Bridge
Xmpp-send-file sends attachments encrypted with XEP-0454 so the phone shows them inline
- BYOK
Per-directory project keys in keys.json with longest-prefix path match
- BYOK
Project key beats user default, then env, then bashrc per request
- BYOK
Speech Layer keys projects, emit, import-pi-sh, and --path/--cwd flags
- UI
Settings page lists project overrides and can save or remove them
- Integrations
Herder and listen treat project keys as personal on 401
- Integrations
Openrouter resolve reports project source via resolve_key_info
- Fix
Brand import path in listen-intent so product name lookup does not crash
- Fix
Peel doubled tell verb after respell so callsign still parses
- Docs
README, AGENTS, INSTALL, speechlayer plus keys.json.example cover project keys
- Herdr
Pane rename comment matches agent prompt (send is gone)
- Herdr
Sticky only re-pins on a real focus edge so background tell keeps its target
- Herdr
Prefer unique agent name over duplicate pane label for sticky inject
- Skills
Herdr docs use agent prompt, pane-first start, and barge-in stop order
- Rules
Steering keeps open work; surfagent claim leases; agent prompt for phone inject
July 29, 2026
2 commits- Brand
Install renders desktop Names and paths from product name and CLI name
- Brand
Dual CLI symlink when the public name differs, keep speechlayer forever
- Brand
Launchd Label prefix is data, templates stay com.speechlayer on disk
- Brand
Mix sink name is MIX_SINK with speechlayer_mix default across audio helpers
- Brand
Web templates plus render-brand write Speech Layer by default, speechlayer overlay ready
- Brand
One runtime brand layer so Speech Layer and public speechlayer share one tree
- Brand
Defaults stay Speech Layer (wake, config dir, URLs, spoken prompts) with fail-safe fallback
- Brand
High-traffic surfaces read product name, wake phrase, and app name from the brand file/env
- Brand
Speech Layer brand dumps the resolved values; inventory lists what still needs a wake-model choice
July 27, 2026
2 commits- BYOK
Per-user LLM provider keys in ~/.config/speechlayer/keys.json (600), user key beats server env key per request
- BYOK
Core/speechlayer_keys.py shared store + masked display + cheap key validation + auth-failure surfacing (marker + notify, never silent server billing)
- UI
Speech Layer keys status|set|clear|test|ui plus localhost :7782 settings web page (provider selector, password input, save/test/clear)
- Integrations
Wvd-herdr-control and wvd-listen-intent resolve OpenRouter keys via the BYOK store with strangler-safe env fallback
- Docs
README BYOK section; install.sh warns with the speechlayer keys alternative
- Tell
Resolve panes on non-active tabs of a workspace
July 24, 2026
2 commits- Fix
Herdr 0.7.5 dropped agent send; inject path now uses agent prompt
- Docs
AGENTS.md and wake-words herder-route notes match the new CLI
- Privacy
Stop treating bare 10/11-digit runs as phones
- Privacy
Drop postal code masking entirely
July 23, 2026
1 commit- Fix
Speech Layer restart now revives a dead email-pi-bridge via email-pi-bridge-ensure (best-effort, cron remains primary supervisor)
July 22, 2026
1 commit- Privacy
Footer and logs count distinct identities, not hits
- Privacy
Shield and unshield phone XMPP sticky injects and replies
- Privacy
Shared store with email bridge and kill-switch XMPP_PRIVACY
July 20, 2026
3 commits- Privacy
Count shield replacements per message and log them
- Privacy
Tell agents that fake tokens are stand-ins to quote as-is
- Privacy
Footer replies with what Speech Layer shielded during LLM calls
- Fix
Herd residual body verbs ask which pane, never spawn to or two
Fix client-site-two bug: body_starter includes to/too/two; herd-default routing for workspace-matched tells; block function-word callsigns.
July 19, 2026
6 commits- Say
Wake poke, CLI fast path, dead-air slimming, hold presynth
- Tts
Install committed say/say-queue-daemon (wake.fifo 8ms claim, same-group ordering, recording-hold presynth, 40ms enqueue)
- Barge
Hands-free auto-calibration battery + daemon self-barge detector
- Tts
Spoken-prep leading-zero trim (PI-000018 -> PI-18); README: wake.fifo/same-group/presynth queue docs
- Proper-nouns
Glue 'tilda/tilde slash foo' to ~/foo before flat pairs
- Privacy
Mask bare and keyword-anchored phone numbers with NANP validation
- Privacy
Mask payment cards, tax ids, and Canadian postal codes with stable fakes
July 18, 2026
3 commits- Privacy
Mask emails and phones to stable short fakes before prompts reach the LLM and restore them on replies
- Privacy
Seed names from mail headers and body anchors with separate first and last fakes
- Email bridge
Shield injected prompts and unshield replies with a shared locked-down lookup file
- Voice
Ask which pane when duplicate labels span workspaces
- Voice
Silent deciders sticky then focused herd then unique agent name
- Phone
Share the which-pane question and answer across voice and text
- Voice
Mute or unmute the default sink with switch volume and goodnight phrases
- Voice
Set Pocket voice across a whole workspace or a named pane
- TTS
Queue by default, pane-scoped replay ring, and soft barge gating
- TTS
Reconcile Pocket daemon pile-ups and durable HF cache on restart
- Phone
Keep XMPP channel sticky separate from voice sticky and focus
- Callsigns
Allow duplicate pane labels and keep agent names unique
- Counters
Stop bare thinking words cutting mid-sentence dictation
July 17, 2026
12 commits- Transform
Drop dead svn commit historical map note
- TTS
Speak xmpp as x m p p
- TTS
Currency, paths, URLs, emails, dates, emoji in speak-prep
- STT
Log respell diffs for training when raw ≠ fixed
- TTS
Absorb trailing dots on a.m./p.m. clock forms
- TTS
Fix a.m./p.m. trailing period after clock expand
- TTS
Speak clock times without colon (14:30, 3pm)
- TTS
Space month abbr expansions so Oct.17 reads clean
- TTS
Month abbreviations speak as full names
- STT
Client-site-class fusions respelled as tell client-site
- TTS speak seeds
Degrees, ops, %, #N, units, e.g., cwd
- TTS
Speak-prep dict (~ → roughly; digit.digit → point)
- Fix
Successful tell no longer dual-dispatches into the focused pane
- Herdr control
Mark tell committed before TTS; fire-and-forget say
- Dictate
Wall after commit counts handled; refuse tell-shaped fallthrough with voice retry
Free-form pi-surf prefers sticky pin over focused eyes
Evolve proper-nouns into a respell dictionary (pie/pi, user JSON)
July 16, 2026
1 commit- Fix
Delete pi session runs /delete and confirms Yes
Agent inject keeps multi-Enter sleep order for confirms
July 15, 2026
32 commitsEyes/focus on also raises the herdr pi-surf window
- Fix
Focus client-site cleaner lands on the cleaner pane
Tell body re-runs bare control grammar on target pane
Tell body runs cwd/nav control on target pane not chat paste
STT togel focus for tell-move-focus toggle
Home sticky channel is herdr not the home pane
Voice toggle for tells moving eyes focus
Fix show me bare eyes-on grammar
Voice eyes on/off for bare workspace and pane focus
Fold client-site's / client-site STT into client-site for tell routing
Sticky hold checked every tick so focus cannot keep the channel
Sticky hold reasserts herdr against focus steal
Handoff wait-scrape herdr reply to phone; re-pin sticky + hold
Focus sync skips sticky during hold so channel stays herdr
- Spawn handoff
SMS herdr reply after wait; re-pin sticky
Fix bridge crash mangle on scrap path regex
STICKY machine line; instruct create to re-stick new pane
- Spawn handoff
Short ensure herdr pane when missing
Confirm keyword yes/no never agent-sends the herdr pane
- Spawn free-form
Default handoff to herdr pane via agent send
Keep rules/LLM rewrite path intact behind spawn-offer-clarify flip
- Spawn clarify
Quoted my workspace and label-before-noun patterns
Live herd name in free text re-routes offer with held body
- Phone scrape
Never TUI dump mid-working; reject chrome junk
- Tell
Keep live herd det words like my for inventory peel
- Spawn offer
Non-yes/no → rules then Needle/LLM rewrite route only
Consent stays keywords; wrong rewrite vectors never invent yes
- Phone bridge
Live-offer free-form asks speechlayer clarify path
- Tell MSG lead
Stop he eating hello
- Phone
Forward speechlayer spawn-offer text to XMPP not echo inbound
- Tell peel
Stop to/that hard split; long-comma English stays peel
- Xmpp-send
Heal session D-Bus so Gajim remote can ack
- Herdr
Silent focus cutover repins sticky without phone spam
- Docs
Sticky is channel not eyes address wins then manual focus
- Docs
Herdr skill notes label equals agent callsign dual-write
- Herdr
Pane rename always dual-writes agent callsign (shim plus control)
- Herdr
Background callsign sync heals TUI renames upgrade-proof
- Voice
Tell shell pane to launch pi types pi plus enter not prose
- Voice
Move working directory force-relocates pi session and resumes
- Voice
Keep change working directory as exit-pi shell-cd path
- Docs
Folder nav resolves chat basenames and change-cwd phrases
- Voice
Match change working directory / cwd / folder to name
- Voice
Resolve short basenames under chat before zoxide
- Voice
Never agent-send spawn yes/no residual or I don't know garbage
- Voice
Wait for TTS and skip free-wake preroll on spawn oneshot
- Voice
Peel hey speechlayer wake so spawn yes/no is not tell-to-speechlayer
- Voice
Arm one-shot free-wake after spawn offer, cut on yes/no
- XMPP
Accept no thanks and wake-style yes/no on spawn offers
- XMPP
Typed Note-to-Self runs the same Speech Layer pipeline as voice notes
- Control
Peel my/the and trailing pane nouns on tell routes
- Say
Caption side-channel for current, last, queue, status.json
- Say
Queue daemon updates captions on play, skip, done, and cancel
- Control
Tell client-site pane launch pi route works despite STT mangling
- Control
Tall/tel aliases of tell and cube-old folds into client-site
- Control
Stop hyphen split and cwd-basename false pane on tell peel
- Control
Hey and yo aliases for tell with dual-use hey (filler vs route)
- Control
Sticky fallthrough on soft free-form, shared with phone target file
- Control
Unknown tell target offers spoken yes/no spawn (shared XMPP offer state)
- Control
Tell workspace pane message routes via live inventory longest match
- Control
Herdr agent inject (XMPP-style) for tell, herder route, and --inject CLI
- Control
Everyday make/create/new pane wording maps to ensure pane
- Dictate
Wvd_agent_inject helper; pi-surf-term prefers agent send over xdotool
July 13, 2026
7 commits- Control
Soft "speechlayer …" free-form gate with salvage before network and hard walls so blue never hangs
- Control
Ensure workspace and ensure pane create-if-missing then focus, including natural hybrid phrasing
- Control
Bash wvd_herdr_control wall plus {{SHIFTTAB}} marker wins in dictate scripts
- CLI/docs
Needle and herder-route ops, tts barge conf, phone mic and listen-path polish
- TTS
Hold say playback while Speech Layer is recording so panes don't talk over the mic
- TTS
Soft interrupt skips only the current utterance and keeps the rest of the queue
- TTS
Wake and energy barge use skip; shut up still drains the whole queue
Track host say queue tools and say-summary extension with Speech Layer
- Bench
Void guest shutdown check with default-device arecord proof; image retained
- Portability
Void thin-guest L2 claim and burn-in scorecard (runit, on-target whisper, PA mix)
- Install
Rewrite DAEMON_HOME pyenv templates and ship alsa-plugins-pulseaudio on void
- Runit
Dual-ship service trees with WVD default Pulse device fallback for Void asound
- Install
Force-distro/init/DE overrides and optional scrcpy on void and suse
- Install
Harden runit enable and systemd unit write for thin containers
- Bench
Family dry-run matrix, container smokes, Level-3 residual scrub
- Docs
Linux-family-matrix plus void and opensuse package smoke reports
- Portability
Cross-host macos svc_status port heuristics and soft LAN path
- Portability
Add macos-first-hour checklist with Darwin-safe probes
- Portability
Gate first-hour and forced-macos status in adapter selfcheck
- Docs
Point macOS install and resumption at first-hour playbook
- Install
Multi-family (debian/Mint) path, models seed step, on-target whisper wrappers
- Install
KDE/Cinnamon/dconf-cli hotkeys and never transplant cross-distro whisper bins
- Assets
Ship wakeword-models seed including hey_speechlayer verifier
- Docs/Bench
Mint walkthrough, portability claim calibrated, debian-family QEMU burn-in
July 12, 2026
2 commits- Portability
Add install-macos first-boot helper and optional indicator launchd unit
- Portability
Ship skhd and Hammerspoon hotkey examples under system/macos
- Portability
Prefer TMPDIR for SL_RUNTIME_DIR on Darwin in env.sh
- Portability
Make fetch-deps cmake jobs work without Linux nproc
- Docs
Point README and portability at the macOS install path
- Portability
Route dictate RECORD_DEVICE through audio_fallback_device for CoreAudio default
- Portability
Ship rumps menu-bar indicator skeleton and wire Darwin CLI check or fix
- Portability
Add dictate and indicator gates to adapter selfcheck
- Docs
Update macOS install resumption and progress for residual scrub
July 11, 2026
4 commits- Portability
A5 pipewire PASS on Fedora QEMU with stream-measure ratio 0.998
- Install
Pull alsa-plugins-pulseaudio so Fedora arecord pulse devices work
- Fix
Skip indicator check and restart when tray helper is not installed
- Fix
Session-heal polls for speechlayer mix and re-bounces daemon if arecord missing
- Fix
Keep speechlayer mix ensure after pulse recover when headless has no real mic
- Docs
Guest-validate PULSE_SERVER unset recover on Ubuntu QEMU restart
- Docs
Record Ubuntu QEMU systemd burn-in scorecard and partial gates
- Portability
Unset PULSE_SERVER before pulseaudio start after kill so restart can recover
July 10, 2026
15 commits- Fix
Lower TTS energy cancel so hot speaker mon no longer zeros talk-over residual
- Fix
Fire residual barge on soft speaker monitor under high mic instead of hard skip
- Fix
Trial barge knobs need two chunks residual 2500 and ratio thr 3.5
- Dictate
Require switch model to alias so bare model names stay prose
- Dictate
Preflight complete herdr commands in listen mode before the LLM
- Herdr
Fuzzy workspace match and richer voice targets for STT near-misses
- STT
Accept cubald-style client-site mishears in proper-noun rewrite
- Training
Add standalone kapish terminator model trainer
- Docs
Freeze Artix Level-3 campaign work at host-gated stop-line
- Docs
List single-host burn-in tickets and regression bar for adapters
- Portability
Make status fix and session-heal accept pipewire-pulse without a pulseaudio process
- Portability
Refuse ha commands on Darwin and route speechlayer test capture through adapters
- Portability
Document A4 user units and expand Fedora dnf package list
- Portability
Extend adapter-selfcheck for CLI residual gates
- Portability
Add Linux adapter selfcheck covering macos force and launchd templates
- Docs
Point resumption install and progress at the selfcheck regression bar
- Portability
Add launchd installer so macOS templates are a real writer not just docs sed
- Portability
Scaffold Windows inject HTTP shim and WSL2 platform overrides after W0
- Docs
Point macos install and progress at launchd installer and Option C door
- Portability
Add stream measure script with ratio and cadence gates for A5 and W0
- Docs
Record Artix Pulse golden numbers for pipewire and WSLg comparison
- Docs
Spell out WSLg W0 operator procedure without claiming a pass yet
- Portability
Route macos beep pid check and speaker mon through adapters
- Portability
Teach speechlayer CLI Darwin-safe status restart and session-heal paths
- Portability
Skip the indicator cleanly when rumps is not installed
- Docs
Add macOS resumption door for real macOS hardware burn-in next
- Docs
Mark Option A A2 and A3 complete and fill INSTALL systemd install pointers
- Docs
Document OpenRC versus systemd sudoers as mutually exclusive
- Docs
Expand systemd Level 2 slices A1 to A6 and link them from INSTALL
- Portability
Route speechlayer managed service control through SL_SVC without OpenRC-only copy
- Portability
Write svc-backend on systemd install and sketch Fedora packages
- Portability
Draft user unit and systemctl sudoers examples off by default
- Docs
Spell out systemd Level 2 burn-in path unit gaps and first boot checklist
- Portability
Scaffold macOS adapters for capture inject notify svc and paths
- Portability
Add raw PCM capture helper that keeps the recording loop shape
- Portability
Ship untested launchd templates and macOS install TCC notes
- Portability
Opt-in systemd verbs via SL_SVC without auto-detecting init
- Docs
Record Option B decision readiness table and half-contract review
- Docs
Campaign brief for OS backends orchestrator after Phase 4 product close
- Voice
Stop soft mon from free-firing ratio barge mid long readouts without killing real talk-over
- Voice
Fix tts-barge set clamps that capped spk_k below real bleed and ratio thr at three
- Status
Count only real python daemon processes so supervise and grep noise stop false multi-daemon warnings
- Voice
Free-wake idle gap so amber can show between turns without killing barge or wake
- Voice
Seed free-wake recordings from the always-on PCM pre-roll so first words are not clipped
- Docs
Mark Phase 4 executed, platform readiness table, listen free-wake idle and pre-roll notes
July 9, 2026
15 commits- Voice
Stop free-wake from rearming while TTS still plays without killing barge or wake
- Voice
Blank free-wake WAV during spoken acks so switching is not reheard as a new command
- Voice
Drop command-shaped listen acks and herdr switch TTS plus short-window herdr dedupe
- Voice
Ship always-on listen mode with CLI, rearm, intent LLM and plan executor
- Voice
Show an amber listening state on the corner indicator while mode is armed
- STT
Fold known client-site mishears on every dictate herdr and phone path before routing
- Docs
Document listen-mode harness files enter exit phrases and half-contract rules
- Docs
Mark the OS-adapter split finished end-to-end so the plan matches the tree
- Portability
Put every desktop notification under the single app name speechlayer so nothing collides with random voice daemons
- Voice
Lock TTS energy-barge knobs so loud talk-over and hey speechlayer can interrupt without clipping clean playback
- Voice
Age barge grace from first audio, not process start, so synthesize lag cannot burn the window
- Voice
Keep a softer wake threshold even when energy barge is off so drowned speech still reaches hey speechlayer
- Voice
Drop bare cancel as a cancel phrase so random prose no longer kills a recording
- Voice
Prefer okay-go and kapish spelling variants for the mid-recording instant cut
- Portability
Build the wake-word mic capture command through the OS adapter so the recording loop stays the same on every platform
- Portability
Record and play audio through the OS adapter so capture tools can change without rewriting the scripts
- Portability
Restart managed services through the OS adapter so Linux is not hard-wired into the CLI
- Voice
Reclaim dead recording locks so a crashed capture cannot block the next wake forever
- Voice
Let loud speech interrupt TTS playback, with knobs you can change without restarting
- Voice
Treat Whisper's clipped 'her D' as 'herd d' so herd switching still works
- Voice
Harden the keystroke-marker walker so unknown markers are dropped, not typed forever
- Voice
Map full 'new session' phrases to /new after slash commands settle
- Portability
Route every keystroke and window-focus call through the OS adapter so typing works the same on every platform
- Portability
Preserve per-site xdotool flags including flag-less Escape and --delay 8 type
- Voice
Revert bare 'go to <name>'; folder-noun required again (cd stays short form)
- Voice
Accept bare 'go to <name>' (≤3 tokens) when not a herd/pane command
- Voice
Harden folder resolve for whisper typos (client-site ≈ client-site) and TLD-ish tokens
- Voice
Drop legacy project-as-herd entirely - project is filesystem-only now
- Docs
Herds-and-folders.md voice cheat sheet (switch herd / folder nav / move session / resume pi)
July 8, 2026
12 commits- Voice
Rebrand herdr workspaces as 'herd' (heard/workspace aliases), freeing 'project' for folder nav
- Voice
Plain folder nav inside pi now exits pi then cds; only 'move session to X' uses pi /cd relocate
- Voice
Add 'resume pi' -> pi -c
- Voice
Add folder-navigation intent (go to folder / cd / go up|home|back) to wvd-herdr-control, zoxide-resolved, shell cd vs pi /cd
- Portability
Send desktop notifications through the OS adapter so non-Linux backends can plug in
- Docs
Note that notification app-names should be unified after the port, since the current ones are generic enough to clash with other apps
- Docs
Record how the Linux dispatch layer was actually built, so the design matches the code
- Portability
Add the per-OS dispatch layer with Linux implementations built in, ready for scripts to adopt
- Voice
Add new-pane and pause keystroke macros so spoken herdr commands can open panes and let slash commands settle before submitting
- Portability
Route all runtime state files through a single configurable directory instead of hardcoding /tmp
- Docs
Inventory every OS-specific call site in the voice stack, grouped by adapter
- Docs
Design the OS-adapter split (audio, keystrokes, notifications, services) with a step-by-step migration plan
- Docs
Link the new portability design into the existing plan so the next phase is ready to start
- Docs
Note that MATE hotkeys run the dconf action field not command, so a stale action still errors even when command looks right
- Docs
Add scroll-in chat examples and modernize speechlayer landing page capabilities and privacy messaging
- Docs
Add charming non-technical speechlayer landing page
July 7, 2026
11 commits- Docs
Restructure speechlayer landing page; feature herdr voice control and TTS reply playback
- Docs
Add plain-text ASCII-art landing page explaining speechlayer
- Fix
Systemd StartLimitIntervalSec/Burst moved to [Unit] section (were silently ignored in [Service])
- Fix
Debian/Ubuntu pkgs list drops bogus libnotify (aborted apt txn), adds python3-venv/pip + build-essential/cmake/git for whisper.cpp build
- Fix
Venv installs use --no-deps so pip-freeze closures don't pull 3GB of nvidia CUDA wheels via misaki
- Fix
Recreate broken venv lacking pip (failed earlier run left python3 but no pip)
- Fix
Wake-word models missing is a warning not a verify failure (user-trained artifacts, not in repo)
- Install
Validated full install.sh systemd burn-in on Ubuntu 24.04 VM (all 4 units active, whisper.cpp built, transcription working)
- Phase 3c
Level-2/3 scrub - de-hardcode default install user, dual-ship systemd units
- Portability.md
Phase 3b fully live - init.d copied, compat shims removed, full smoke matrix green
- Phase 3b
Root rename ~/scripts+~/.speechlayer -> ~/speechlayer with core/pi/net/training/media/lib subdirs
- Herdr grammar
Accept 'panel' as spoken alias for pane
Phase 3a portability: SL_HOME parameterization
Phase 2 portability: install.sh + fetch-deps.sh
Phase 1 portability: system snapshots, requirements, models, INSTALL.md
Initial messy commit: ~/scripts + ~/.speechlayer as-is, pre-restructure