memlimit

package
v0.11.0 Latest Latest
Warning

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

Go to latest
Published: Aug 13, 2026 License: MIT Imports: 6 Imported by: 0

Documentation

Overview

Package memlimit resolves the memory this process may actually use, so the module's engine-wide ceilings can be derived from the smallest bound that is observable rather than from a constant chosen without knowledge of the host.

Why a library must not simply set GOMEMLIMIT

GOMEMLIMIT is process-global state and belongs to the embedder: a library that sets it silently changes the GC behaviour of an application that may have many other components. So this package only ever READS a limit, and the module uses what it reads to lower its OWN ceilings. Setting GOMEMLIMIT remains the right move for a program — the ggserver binary — and the wrong move here.

Why the constants were not enough (rmp #2421)

The engine-wide ceilings landed by the 2026-08-10 certification are finite, and that closed a real denial-of-service hole. But they are FIXED: 4 GiB of results and 1 GiB of inbound decode, applied whenever the process has no Go soft memory limit to derive from — which is the default state of every Go process. Inside a container capped below those numbers the ceiling is larger than the whole container, so it cannot bind before the kernel's OOM killer does, and the failure mode is a killed process rather than a typed error. That is the opposite of the graceful degradation the module promises.

It is not a theoretical concern: a 4M-relationship Cypher load was OOM-killed in an 8 GB container on 2026-08-11 ("Killed process (ggserver) anon-rss:8370788kB"), and re-running the identical fixture with GOMEMLIMIT=6GiB completed at 4520 MB. The cap was the missing input, not the workload.

Memgraph solves the same problem by reading the host: its global memory limit defaults to 100% of physical memory with swap and 90% without, via utils::sysinfo::InstalledMemory (src/flags/memory_limit.cpp:20-38, v3.9.0). The shape adopted here is the same — derive from what is observable — while the magnitudes stay this module's own.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Available

func Available() (int64, bool)

Available returns the smallest observable bound, in bytes, on the memory this process may use, and whether one was found at all.

The sources are consulted in order of authority:

  1. the Go soft memory limit, when the embedder has set one (GOMEMLIMIT or runtime/debug.SetMemoryLimit) — an explicit statement of intent;
  2. the cgroup v2 memory.max of the process's own cgroup;
  3. the cgroup v1 memory.limit_in_bytes.

It deliberately does NOT fall back to installed RAM. A bound this package cannot vouch for is worse than no bound: the caller's own finite constant is the documented last resort, and reporting false here selects it.

The answer is computed ONCE and cached: it is consulted while constructing an engine or a server, never on a query path, and the underlying limit cannot change for a running process in the cases that matter.

Safe for concurrent use.

func ResolveCount

func ResolveCount() int64

ResolveCount reports how many times the underlying lookup has run. It exists for the test that pins the once-per-process contract.

Types

This section is empty.

Jump to

Keyboard shortcuts

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