{"record":{"id":"5e18e1ed4076f156","repo":"fatedier/frp","slug":"get-addr-and-extra-payload-timeout","errorCode":null,"errorMessage":"get addr and extra payload timeout","messagePattern":"get addr and extra payload timeout","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/ssh/server.go","lineNumber":251,"sourceCode":"\t\t\tgo s.handleNewChannel(newChannel, extraPayloadCh)\n\t\t}\n\t}()\n\n\tvar (\n\t\taddr         *tcpipForward\n\t\textraPayload string\n\t)\n\n\ttimer := time.NewTimer(timeout)\n\tdefer timer.Stop()\n\tfor {\n\t\tselect {\n\t\tcase v := <-addrCh:\n\t\t\taddr = v\n\t\tcase extra := <-extraPayloadCh:\n\t\t\textraPayload = extra\n\t\tcase <-timer.C:\n\t\t\treturn nil, \"\", fmt.Errorf(\"get addr and extra payload timeout\")\n\t\t}\n\t\tif addr != nil && extraPayload != \"\" {\n\t\t\tbreak\n\t\t}\n\t}\n\treturn addr, extraPayload, nil\n}\n\nfunc (s *TunnelServer) parseClientAndProxyConfigurer(_ *tcpipForward, extraPayload string) (*v1.ClientCommonConfig, v1.ProxyConfigurer, string, error) {\n\thelpMessage := \"\"\n\tcmd := &cobra.Command{\n\t\tUse:   \"ssh v0@{address} [command]\",\n\t\tShort: \"ssh v0@{address} [command]\",\n\t\tRun:   func(*cobra.Command, []string) {},\n\t}\n\tcmd.SetGlobalNormalizationFunc(config.WordSepNormalizeFunc)\n\n\targs := strings.Split(extraPayload, \" \")","sourceCodeStart":233,"sourceCodeEnd":269,"githubUrl":"https://github.com/fatedier/frp/blob/6c8a8d0a97d03b44e9528d30b30c70cb9d61b405/pkg/ssh/server.go#L233-L269","documentation":"waitForwardAddrAndExtraPayload waits on channels fed by the tcpip-forward SSH request and the first opened channel's payload, guarded by a 3-second timer. If either the forward address request or the extra payload string has not arrived within 3 seconds, this error aborts the connection. It exists because a well-behaved frp SSH client sends both immediately after connecting.","triggerScenarios":"Client connects to the frp SSH gateway but sends no command payload (plain `ssh -p port v0@host` with no command, then idles), a non-frp SSH client that only opens a session channel, network stalls that delay the first packets past 3s, or automation that opens the TCP connection and waits.","commonSituations":"Interactive shell into the gateway out of curiosity (the gateway is not a shell); port scanners or health checks that complete the TCP+SSH handshake but send nothing; scripts that establish the connection before composing the command; very slow or lossy links exceeding the fixed 3s budget.","solutions":["Always pass the proxy command as the ssh command argument: ssh -p port v0@host \"tcp 127.0.0.1:22 --remotePort 6000\".","If automating, open the connection and write the payload in one step (paramiko: exec_command; go ssh: start the channel immediately).","Avoid using this port with a plain interactive shell — it is a tunnel endpoint, not a login shell.","For flaky networks, send the payload as early as possible; the 3s window is fixed and not configurable."],"exampleFix":"# before (opens connection, sends nothing)\nssh -p 7000 v0@frps-host\n\n# after (command sent immediately)\nssh -p 7000 v0@frps-host \"tcp 127.0.0.1:22 --remotePort 6000\"","handlingStrategy":"validation","validationCode":"# always send the command in the same step as connecting\n# paramiko example\ncli = paramiko.SSHClient()\ncli.connect(host, port=7000, username=\"v0\", key_filename=\"~/.ssh/frp_gateway\")\nstdin, stdout, stderr = cli.exec_command(\"tcp 127.0.0.1:22 --remotePort 6000\", timeout=5)  # payload sent immediately","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never open a bare interactive shell to the gateway port.","In automation, compose the command string before connecting.","Health checks should TCP-probe, not complete SSH handshakes then idle."],"tags":["ssh","timeout","protocol","user-input"],"backgroundTag":null,"analyzedSha":"6c8a8d0a97d03b44e9528d30b30c70cb9d61b405","analyzedAt":"2026-08-15T06:53:27.215Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}