{"record":{"id":"64c5c6e3677a66dc","repo":"shadow1ng/fscan","slug":"ms17010-pipe-response-incomplete","errorCode":null,"errorMessage":"ms17010_pipe_response_incomplete","messagePattern":"ms17010_pipe_response_incomplete","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"plugins/services/ms17010.go","lineNumber":385,"sourceCode":"\n\t// 命名管道请求\n\ttreeID := reply[28:30]\n\ttransNamedPipe := append([]byte(nil), transNamedPipeRequest...)\n\ttransNamedPipe[28] = treeID[0]\n\ttransNamedPipe[29] = treeID[1]\n\ttransNamedPipe[32] = userID[0]\n\ttransNamedPipe[33] = userID[1]\n\n\tif _, err = conn.Write(transNamedPipe); err != nil {\n\t\treturn false, osVersion, false, fmt.Errorf(\"%s: %w\", i18n.GetText(\"ms17010_send_pipe_error\"), err)\n\t}\n\n\tn, readErr = conn.Read(reply)\n\tif readErr != nil || n < 36 {\n\t\tif readErr != nil {\n\t\t\treturn false, osVersion, false, fmt.Errorf(\"%s: %w\", i18n.GetText(\"ms17010_read_pipe_error\"), readErr)\n\t\t}\n\t\treturn false, osVersion, false, fmt.Errorf(\"%s\", i18n.GetText(\"ms17010_pipe_response_incomplete\"))\n\t}\n\n\t// 漏洞检测 - 关键检查点\n\tif reply[9] == 0x05 && reply[10] == 0x02 && reply[11] == 0x00 && reply[12] == 0xc0 {\n\t\ttrans2SessionSetup := append([]byte(nil), trans2SessionSetupRequest...)\n\t\ttrans2SessionSetup[28] = treeID[0]\n\t\ttrans2SessionSetup[29] = treeID[1]\n\t\ttrans2SessionSetup[32] = userID[0]\n\t\ttrans2SessionSetup[33] = userID[1]\n\n\t\tif _, err = conn.Write(trans2SessionSetup); err != nil {\n\t\t\treturn true, osVersion, false, nil\n\t\t}\n\t\tn, readErr = conn.Read(reply)\n\t\tif readErr != nil || n < 36 {\n\t\t\treturn true, osVersion, false, nil\n\t\t}\n","sourceCodeStart":367,"sourceCodeEnd":403,"githubUrl":"https://github.com/shadow1ng/fscan/blob/95cc12e753bf43de7004e5aef42a9ffba3934303/plugins/services/ms17010.go#L367-L403","documentation":"This error is returned by checkMS17010VulnerabilityAt when the SMB named-pipe probe response is shorter than the 36 bytes needed to parse the SMB header (including the fields checked at reply[9..12]). The code only throws it when conn.Read returned no error but delivered fewer than 36 bytes, meaning the target closed or truncated the response mid-conversation. It signals the target did not reply with a well-formed Trans/NamedPipe response, so the MS17-010 (EternalBlue) check cannot proceed.","triggerScenarios":"Calling checkMS17010Vulnerability (which invokes checkMS17010VulnerabilityAt) against a host whose TCP 445 connection accepts the transNamedPipeRequest but returns a partial (<36 byte) reply — e.g. a non-Windows Samba variant, a hardened/patched host dropping the payload, an IDS/resetting middlebox truncating the response, or a slow host whose partial read races with the single conn.Read call.","commonSituations":"Scanning hardened or patched Windows hosts that RST or close early; probing Linux/Samba servers that respond with malformed or minimal SMB data; scanning through firewalls/NAT devices that mangle SMB traffic; overloaded hosts delivering fragmented responses that the single unlooped conn.Read does not reassemble.","solutions":["Retry the check; TCP fragmentation can make a single conn.Read return <36 bytes even from a vulnerable host — add a read loop until 36 bytes accumulate or a timeout expires.","Verify the target actually exposes SMB on port 445 and is a Windows host worth probing (nmap -sV -p445).","Confirm no middlebox/IPS is stripping SMB responses between scanner and target.","If it persists, treat the host as not MS17-010 confirmable and fall back to other detection methods (patch level, os fingerprint)."],"exampleFix":"// before\nn, readErr = conn.Read(reply)\nif readErr != nil || n < 36 {\n    ...\n    return false, osVersion, false, fmt.Errorf(\"%s\", i18n.GetText(\"ms17010_pipe_response_incomplete\"))\n}\n// after\nfor n < 36 {\n    m, rerr := conn.Read(reply[n:])\n    if rerr != nil {\n        return false, osVersion, false, fmt.Errorf(\"%s: %w\", i18n.GetText(\"ms17010_read_pipe_error\"), rerr)\n    }\n    if m == 0 {\n        return false, osVersion, false, fmt.Errorf(\"%s\", i18n.GetText(\"ms17010_pipe_response_incomplete\"))\n    }\n    n += m\n}","handlingStrategy":"retry","validationCode":"// before probing\nfunc probeSMB(host string) bool {\n    conn, err := net.DialTimeout(\"tcp\", host+\":445\", 3*time.Second)\n    if err != nil { return false }\n    defer conn.Close()\n    _ = conn.SetDeadline(time.Now().Add(3 * time.Second))\n    return true\n}","typeGuard":"func isCompleteSMBReply(n int, err error) bool {\n    return err == nil && n >= 36\n}","tryCatchPattern":"if err := checkMS17010Vulnerability(host); err != nil {\n    if strings.Contains(err.Error(), \"ms17010_pipe_response_incomplete\") {\n        // transient truncation: retry once with longer deadline, then mark inconclusive\n        time.Sleep(500 * time.Millisecond)\n        err = checkMS17010Vulnerability(host)\n    }\n    if err != nil { log.Printf(\"MS17-010 check inconclusive for %s: %v\", host, err) }\n}","preventionTips":["Only run the check against confirmed Windows/SMB hosts on port 445.","Use a read loop until a full SMB header (36 bytes) is received rather than a single conn.Read.","Set generous connection deadlines for slow or WAN targets.","Treat inconclusive results as 'unknown', not 'not vulnerable', and re-verify with a second method."],"tags":["network","smb","scan","incomplete-response"],"backgroundTag":"unexpected-response-shape","analyzedSha":"95cc12e753bf43de7004e5aef42a9ffba3934303","analyzedAt":"2026-09-06T17:07:30.094Z","contentChangedAt":"2026-09-06T17:07:30.094Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}