Container visibility
A RouterOS container shares the router’s kernel, but not all of the kernel’s view: some files inside it describe the router, others only the container. The kernel’s namespaces draw that line, and no container setting mikroscope could choose moves it. Which files fall on which side is a property of the kernel and of how RouterOS builds its containers (other boards and versions not checked).
Host-wide files
Section titled “Host-wide files”The CPU, interrupt, memory and block-device files are global: inside the container they are the router’s own, and they are read on every tick (a block device’s row is stored only when it did something):
/proc/stat, per core/proc/interruptsand/proc/softirqs/proc/net/softnet_stat: drops and time squeezes in the kernel’s receive path. It lives under/proc/netbut counts per CPU, not per namespace./proc/meminfo,/proc/vmstatand/proc/loadavg/proc/diskstats
An ordinary, unprivileged container also reads these as the router’s: the thermal zones under
/sys/class/thermal, scaling_cur_freq per core, the NAND wear counters in /proc/yaffs, and
the page allocator’s free lists in /proc/buddyinfo. The device tree’s model string is not
namespaced either, and it is how the agent identifies the board without the RouterOS API.
Namespaced network files
Section titled “Namespaced network files”/proc/net/dev, /proc/net/snmp, /proc/net/netstat and nf_conntrack_count are per
network namespace. Inside the container they describe the container’s own veth: a few packets
while the router forwards millions. The agent does not read them as router data, and
/capabilities lists them under namespaced so a consumer can see they were left out on
purpose rather than missed.
privileged=yes does not change this. It drops the container’s user namespace, not
its network namespace (verified).
So per-interface bytes and packets come from the RouterOS API instead, and the collector merges them with the kernel tier on the agent’s clock. They are not interpolated from anything the container can see. How that tier is polled is on RouterOS API tier.
The same boundary shows up in other places:
| What | What the container sees |
|---|---|
/sys/class/net |
only lo and the veth; no device for any front-panel port, privileged or not |
/sys/class/mdio_bus, /sys/class/phy |
mdio_bus holds only fixed-0; phy is empty |
netdev_budget, netdev_max_backlog and the other global net.core entries |
absent; per-namespace entries such as somaxconn are present |
/proc/net/* files created by modules |
the container’s own: fib_trie shows only the veth’s /30, snmp6 counts its packets |
nf_conntrack_max |
the router’s real ceiling, the same value RouterOS reports as max-entries |
| conntrack timeouts | Linux defaults (tcp_timeout_established 432 000 s against RouterOS’s 1d) |
Scroll sideways to see every column
The last two rows sit in the same directory and split in opposite directions.
nf_conntrack_max is read once at start and shipped as the connection table’s ceiling. The
timeouts are never presented as the router’s configuration, because they are not.
The absent netdev_budget is also why the squeeze panels have no budget denominator: that
is the namespace’s doing, not the agent’s.
Conntrack count
Section titled “Conntrack count”The connection count is the exception. Under privileged=yes the agent reads
/proc/slabinfo, and the slab allocator is global: the nf_conntrack cache’s active-object
count is the router’s real conntrack population, while the container’s own namespace reports 0.
Conntrack without the API has the readings, and how to
cross-check the count once against the API.
That replaces an API table scan with a file read, and it is why the collector never polls
the conntrack count unless --conntrack-every is set (off by default in every
--api-mode). With the ceiling above, “how full is
the connection table” is answerable from the container alone.
What it cannot tell you is what the connections are. /proc/slabinfo counts objects in a
cache and nothing else: no protocol, no address, no state. A conntrack flood and a
legitimate burst of many connections (a torrent, say) look the same in it. Without privileged=yes the file is unreadable and
the count is gone; see Privileged mode.
Host mounts
Section titled “Host mounts”Bind-mounting the router’s own paths into a privileged container does not get past the namespaces (tested):
- Host
/procmounts but reads zero PIDs. RouterOS renders a fresh procfs at the mount point, so the PID namespace holds and per-process CPU for RouterOS’s own processes stays out of reach. - Host
/sysmounts but has noclass/net. Sysfs networking is per network namespace and the mount does not carry the host’s, so per-interface counters stay API-only. - Host
/works, and exposes the RouterOS flash filesystem: configuration and files, not live telemetry. A privileged container with/mounted reads the whole configuration, secrets included. mikroscope’s installer mounts nothing into the container and must never do this.
Namespaces are kernel boundaries, and a filesystem mount does not cross them.