ipc

package
v0.3.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 14, 2026 License: MIT Imports: 3 Imported by: 0

Documentation

Overview

Package ipc — the private socket's codes, range 0.3.91.* (ADR 0148).

The range was allocated to internal/service/proc/ipc, the engine, and is declared here, at the same path in the core, since ADR 0160. The values did not change with the move, and the LL byte still records the service layer that allocated them.

Package ipc — the sentinels internal/service/proc/ipc refuses with. Each var's name equals its errs.Define Reason in SCREAMING_SNAKE form. None quotes a path in its Public half: the path travels in the "path" field, for the log. The Private strings name the service package, where each condition is detected.

Package ipc is the private socket's contract (ADR 0148, ADR 0160): who is at the other end of a connection, the connection that carries that answer, the two ports a private socket is reached through — the Listener that accepts and the Dialer that connects — and the codes every refusal carries.

The engine is internal/service/proc/ipc: a Unix socket in a 0700 directory whose whole path is audited, the kernel's word on the peer where it gives one, a named pipe with its own DACL on Windows. Nothing here opens a socket. The ports exist so a caller that holds a Listener or a Dialer can be handed a double in a test — connections from net.Pipe with the peer the test chooses — instead of a socket on disk.

Index

Constants

View Source
const CodeClosed errs.Code = 0x00_03_5B_08 // 0.3.91.8

CodeClosed identifies an Accept on a listener that was closed.

View Source
const CodeDialFailed errs.Code = 0x00_03_5B_06 // 0.3.91.6

CodeDialFailed identifies a dial that did not reach a listener.

View Source
const CodeDirectoryUnsafe errs.Code = 0x00_03_5B_02 // 0.3.91.2

CodeDirectoryUnsafe identifies a socket directory another account could plant an entry in or read through: not a directory, a link, not owned by this process's user, or writable by its group or by anyone.

View Source
const CodeEndpointForeign errs.Code = 0x00_03_5B_07 // 0.3.91.7

CodeEndpointForeign identifies a socket file owned by another account: a client refuses to talk to what may be an impostor.

View Source
const CodeInUse errs.Code = 0x00_03_5B_03 // 0.3.91.3

CodeInUse identifies a socket path a live process already answers on.

View Source
const CodeListenFailed errs.Code = 0x00_03_5B_04 // 0.3.91.4

CodeListenFailed identifies a listen the kernel refused.

View Source
const CodeMisconfigured errs.Code = 0x00_03_5B_01 // 0.3.91.1

CodeMisconfigured identifies a configuration no endpoint can be built from: an empty or relative path, one longer than the kernel's sun_path, a UID or GID list holding a negative value.

View Source
const CodePathUnsafe errs.Code = 0x00_03_5B_09 // 0.3.91.9

CodePathUnsafe identifies a socket path another account could steer: a component ABOVE the socket's directory, or the directory holding it, lets another account decide where the path leads — a link planted where anybody can write, a directory another account created there, or an entry anybody can replace. The socket directory's own entry stays CodeDirectoryUnsafe's.

It is its own code, as LOCK_PATH_REDIRECTED is lock's (ADR 0083), because the remedy differs: DIRECTORY_UNSAFE asks for a chmod or a chown, this asks a human to look at a component that may be an attack in progress — or to move the socket under the directory the engine's RuntimeDir names.

View Source
const CodePeerRefused errs.Code = 0x00_03_5B_05 // 0.3.91.5

CodePeerRefused identifies a peer whose kernel-reported identity is not this process's user nor in the allow-lists.

Variables

View Source
var (
	// Misconfigured refuses a configuration no endpoint can be built from.
	Misconfigured = errs.Define(CodeMisconfigured, "MISCONFIGURED",
		"The private socket is misconfigured",
		"service/proc/ipc: empty or relative path, path beyond sun_path, or a negative UID/GID; the rule field says which",
		errs.WithExitCode(exitConfig))

	// DirectoryUnsafe refuses a socket directory another account could reach.
	DirectoryUnsafe = errs.Define(CodeDirectoryUnsafe, "DIRECTORY_UNSAFE",
		"The private socket's directory is not private",
		"service/proc/ipc: the directory is a link, not a directory, not ours, or group/world writable; the rule field says which",
		errs.WithExitCode(exitConfig))

	// InUse refuses to listen where a live process already answers.
	InUse = errs.Define(CodeInUse, "IN_USE",
		"Another process already listens on this private socket",
		"service/proc/ipc: a dial to the existing socket succeeded, so it was not removed")

	// ListenFailed reports a listen the kernel refused.
	ListenFailed = errs.Define(CodeListenFailed, "LISTEN_FAILED",
		"The private socket could not be opened",
		"service/proc/ipc: net.Listen or the chmod after it failed; the cause is in the chain")

	// PeerRefused reports a connection from an account the listener does not
	// admit. It is returned to no one but the listener's observer: the
	// connection is closed without a word.
	PeerRefused = errs.Define(CodePeerRefused, "PEER_REFUSED",
		"The peer is not allowed on this private socket",
		"service/proc/ipc: the kernel-reported UID/GID is neither ours nor in the allow-lists; uid and gid fields")

	// DialFailed reports a dial that reached no listener.
	DialFailed = errs.Define(CodeDialFailed, "DIAL_FAILED",
		"The private socket did not answer",
		"service/proc/ipc: the dial failed or timed out; the cause is in the chain")

	// EndpointForeign refuses a socket file another account owns.
	EndpointForeign = errs.Define(CodeEndpointForeign, "ENDPOINT_FOREIGN",
		"The private socket belongs to another account",
		"service/proc/ipc: the socket file's owner is not this process's user nor an allowed one; the uid field names it",
		errs.WithExitCode(exitConfig))

	// Closed reports an Accept on a closed listener.
	Closed = errs.Define(CodeClosed, "CLOSED",
		"The private socket is closed",
		"service/proc/ipc: Accept after Close")

	// PathUnsafe refuses a socket path another account could steer.
	PathUnsafe = errs.Define(CodePathUnsafe, "PATH_UNSAFE",
		"The private socket's path runs through a directory another account controls",
		"service/proc/ipc: a component above the socket's directory is a link planted where anybody can write, a directory another account owns there, or an entry anybody can replace; the path, dir, kind and container fields say which, target and uid where they apply",
		errs.WithExitCode(exitConfig))
)

Functions

This section is empty.

Types

type Conn

type Conn struct {
	net.Conn
	// Peer is who connected (for a listener) or who listens (for a dialer).
	Peer PeerValue
}

Conn is a connection with its peer's identity: what a Listener's Accept returns to a listener and a Dialer's Dial to a client, Peer naming the other end.

type Dialer

type Dialer interface {
	// Dial connects within ctx. Peer names the listener where the kernel
	// does; a listener of an account that is not admitted is refused.
	Dial(ctx context.Context) (*Conn, error)
}

Dialer is the connecting end of a private socket: it reaches the listener its configuration names and refuses — before a byte is sent — an endpoint it cannot trust. It is frozen at one method (ADR 0039).

type Listener

type Listener interface {
	// Accept returns the next connection of an admitted peer. A peer the
	// kernel names and the configuration does not admit is closed at once,
	// counted by Refused, and never returned. After Close it returns the
	// CLOSED sentinel.
	Accept() (*Conn, error)
	// Addr is the endpoint's address.
	Addr() net.Addr
	// Close stops accepting and releases the endpoint.
	Close() error
	// Path is the endpoint's configured path — the socket file, or the path
	// a Windows pipe's name is derived from.
	Path() string
	// Refused is how many connections Accept closed because their peer was
	// not admitted.
	Refused() int64
}

Listener is the accepting end of a private socket: it hands out the connections of admitted peers only, and closes and counts the others.

It is frozen at these five methods (ADR 0039): a method added to a published interface breaks every double a caller wrote, so a capability that comes later is a sibling interface a Listener may also implement.

type PeerValue

type PeerValue struct {
	// UID and GID are the peer's effective user and group; -1 when the
	// kernel does not say (Verified is then false).
	UID, GID int
	// PID is the peer's process, 0 when the kernel does not say.
	PID int
	// SID is the peer's account on Windows, read from its process token;
	// empty elsewhere.
	SID string
	// Verified is true when the kernel named the peer — UID and GID by
	// SO_PEERCRED on Linux, SID from the process token on Windows —, false
	// when only the directory's permissions admitted it.
	Verified bool
}

PeerValue is who is at the other end of a connection, as the kernel says: the peer's user, group and process where the kernel names them, and whether it did (Verified) — false where only the directory's permissions admitted it.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL