XTLS/Xray-core · warning

no process found for inode

Error message

no process found for inode 

What it means

The socket inode was found in /proc/net/tcp{,6} but the scan of all processes' FD tables completed without any /proc/<pid>/fd/<n> linking to that inode. Either the owner is hidden from this user, or the socket is owned by the kernel (not any process), which happens for listener sockets in some states.

Source

Thrown at common/net/find_process_linux.go:66

	targetHexAddr, err := formatLittleEndianString(net.ParseIP(srcIP), Port(srcPort))
	if err != nil {
		return 0, "", "", errors.New("failed to format address: ", err)
	}

	inode, err := findInodeInFile(procFile, targetHexAddr)
	if err != nil {
		return 0, "", "", errors.New("could not search in ", procFile).Base(err)
	}
	if inode == "" {
		return 0, "", "", errors.New("connection for ", srcIP, ":", srcPort, " not found in ", procFile)
	}

	pidStr, err := findPidByInode(inode)
	if err != nil {
		return 0, "", "", errors.New("could not find PID for inode ", inode, ": ", err)
	}
	if pidStr == "" {
		return 0, "", "", errors.New("no process found for inode ", inode)
	}

	absPath, err := getAbsPath(pidStr)
	if err != nil {
		return 0, "", "", errors.New("could not get process name for PID ", pidStr, ":", err)
	}

	nameSplit := strings.Split(absPath, "/")
	procName := nameSplit[len(nameSplit)-1]

	pid, err := strconv.Atoi(pidStr)
	if err != nil {
		return 0, "", "", errors.New("failed to parse PID: ", err)
	}

	return pid, procName, absPath, nil
}

View on GitHub (pinned to 7d214f8b09)

Solutions

  1. Run with privileges sufficient to see all processes' FD tables (root, or relax hidepid)
  2. Retry once for races where the process list and socket table can be re-read consistently
  3. Accept that kernel-owned sockets have no PID and route them by other criteria
  4. Verify manually: ls -l /proc/*/fd 2>/dev/null | grep inode:<n>
Defensive patterns

Strategy: fallback

Type guard

func isNoProcessForInode(err error) bool {
    return err != nil && strings.Contains(err.Error(), "no process found for inode")
}

Try / catch

if err != nil && isNoProcessForInode(err) {
    // hidden owner or kernel-owned socket; route by other criteria
}

Prevention

When it happens

Trigger: hidepid mounted on /proc so other users' processes are invisible; the owning process exited after the socket table was read but before the FD scan; inode belongs to a kernel worker (e.g. some UDP tunnels, conntrack-owned sockets).

Common situations: Unprivileged process-based routing on multi-user systems; looking up sockets of setuid services; racing with process teardown.

Related errors


AI-assisted analysis of XTLS/Xray-core@7d214f8b09 (2026-08-15). Data as JSON: /api/errors/ed5dec36f82ebcbd. Report an issue: GitHub.