detached 76bfb3a

fix(dgram): contain readiness parsing

commit
76bfb3ab0c41ea61a2da7ca331af6c89e4931bbe
author
brice · · 2026-07-23 20:43 UTC
parent
2bd81b9
signature
GPG VerifiedCD88F9E564E0102646FB6077A1A07C7C7C3E349D · arch-gpg Verified for the committer email
1 file · +22 -16
M internal/adapters/dgram/ssh_dialer.go +22 -16
@@ -258,21 +258,26 @@ type udpReady struct {
258258 }
259259
260260 func readUDPReady(r io.Reader) (udpReady, error) {
261- line, err := bufio.NewReader(r).ReadString('\n')
262- if err != nil && line == "" {
263- return udpReady{}, err
264- }
265-
266- ready := udpReady{key: make([]byte, pdgram.KeySize)}
267- var parseErr error
261+ out := make([]byte, pdgram.KeySize)
262+ var (
263+ port int
264+ keyLen int
265+ parseErr error
266+ )
268267 pdgram.SecretDo(func() {
268+ line, err := bufio.NewReader(r).ReadString('\n')
269+ if err != nil && line == "" {
270+ parseErr = err
271+ return
272+ }
273+
269274 fields := strings.Fields(line)
270275 if len(fields) != 3 || fields[0] != "VEV-UDP" {
271276 parseErr = fmt.Errorf("malformed UDP readiness line")
272277 return
273278 }
274- ready.port, parseErr = strconv.Atoi(fields[1])
275- if parseErr != nil || ready.port < 1 || ready.port > 65535 {
279+ port, parseErr = strconv.Atoi(fields[1])
280+ if parseErr != nil || port < 1 || port > 65535 {
276281 parseErr = fmt.Errorf("invalid UDP port %q", fields[1])
277282 return
278283 }
@@ -282,17 +287,18 @@ func readUDPReady(r io.Reader) (udpReady, error) {
282287 parseErr = fmt.Errorf("invalid bootstrap key: %w", decodeErr)
283288 return
284289 }
285- if len(key) != pdgram.KeySize {
286- parseErr = fmt.Errorf("invalid bootstrap key length %d", len(key))
287- return
288- }
289- copy(ready.key, key)
290+ keyLen = len(key)
291+ copy(out, key)
290292 })
291293 if parseErr != nil {
292- pdgram.Erase(ready.key)
294+ pdgram.Erase(out)
293295 return udpReady{}, parseErr
294296 }
295- return ready, nil
297+ if keyLen != pdgram.KeySize {
298+ pdgram.Erase(out)
299+ return udpReady{}, fmt.Errorf("invalid bootstrap key length %d", keyLen)
300+ }
301+ return udpReady{port: port, key: out}, nil
296302 }
297303
298304 func udpUnavailable(action string, err error, stderr fmt.Stringer) error {
@@ -258,21 +258,26 @@ type udpReady struct {
258 }258 }
259 259
260 func readUDPReady(r io.Reader) (udpReady, error) {260 func readUDPReady(r io.Reader) (udpReady, error) {
261- line, err := bufio.NewReader(r).ReadString('\n')261+ out := make([]byte, pdgram.KeySize)
262- if err != nil && line == "" {262+ var (
263- return udpReady{}, err263+ port int
264- }264+ keyLen int
265-265+ parseErr error
266- ready := udpReady{key: make([]byte, pdgram.KeySize)}266+ )
267- var parseErr error
268 pdgram.SecretDo(func() {267 pdgram.SecretDo(func() {
268+ line, err := bufio.NewReader(r).ReadString('\n')
269+ if err != nil && line == "" {
270+ parseErr = err
271+ return
272+ }
273+
269 fields := strings.Fields(line)274 fields := strings.Fields(line)
270 if len(fields) != 3 || fields[0] != "VEV-UDP" {275 if len(fields) != 3 || fields[0] != "VEV-UDP" {
271 parseErr = fmt.Errorf("malformed UDP readiness line")276 parseErr = fmt.Errorf("malformed UDP readiness line")
272 return277 return
273 }278 }
274- ready.port, parseErr = strconv.Atoi(fields[1])279+ port, parseErr = strconv.Atoi(fields[1])
275- if parseErr != nil || ready.port < 1 || ready.port > 65535 {280+ if parseErr != nil || port < 1 || port > 65535 {
276 parseErr = fmt.Errorf("invalid UDP port %q", fields[1])281 parseErr = fmt.Errorf("invalid UDP port %q", fields[1])
277 return282 return
278 }283 }
@@ -282,17 +287,18 @@ func readUDPReady(r io.Reader) (udpReady, error) {
282 parseErr = fmt.Errorf("invalid bootstrap key: %w", decodeErr)287 parseErr = fmt.Errorf("invalid bootstrap key: %w", decodeErr)
283 return288 return
284 }289 }
285- if len(key) != pdgram.KeySize {290+ keyLen = len(key)
286- parseErr = fmt.Errorf("invalid bootstrap key length %d", len(key))291+ copy(out, key)
287- return
288- }
289- copy(ready.key, key)
290 })292 })
291 if parseErr != nil {293 if parseErr != nil {
292- pdgram.Erase(ready.key)294+ pdgram.Erase(out)
293 return udpReady{}, parseErr295 return udpReady{}, parseErr
294 }296 }
295- return ready, nil297+ if keyLen != pdgram.KeySize {
298+ pdgram.Erase(out)
299+ return udpReady{}, fmt.Errorf("invalid bootstrap key length %d", keyLen)
300+ }
301+ return udpReady{port: port, key: out}, nil
296 }302 }
297 303
298 func udpUnavailable(action string, err error, stderr fmt.Stringer) error {304 func udpUnavailable(action string, err error, stderr fmt.Stringer) error {

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 12

Tags 11

↑↓ moveenter openesc close