core: Add CPU, I/O, and network resource limits to run-service#3767
Open
joaoantoniocardoso wants to merge 1 commit intobluerobotics:masterfrom
Open
core: Add CPU, I/O, and network resource limits to run-service#3767joaoantoniocardoso wants to merge 1 commit intobluerobotics:masterfrom
joaoantoniocardoso wants to merge 1 commit intobluerobotics:masterfrom
Conversation
This comment was marked as outdated.
This comment was marked as outdated.
2e61b3c to
b0d917d
Compare
There was a problem hiding this comment.
Hey - I've found 1 issue, and left some high level feedback:
- The description mentions BLUEOS_DISABLE_* environment variables to selectively disable limits, but the script changes don’t appear to read or honor these variables yet; consider wiring them into has_any_limit and the individual limit sections so behavior matches the documented interface.
- The I/O limiting logic relies on a hardcoded list of block devices (/dev/mmcblk0, /dev/sda, /dev/nvme0n1); consider deriving the underlying block device dynamically (e.g., via findmnt/lsblk/stat on the root filesystem) so this works correctly on a wider range of platforms and configurations.
Prompt for AI Agents
Please address the comments from this code review:
## Overall Comments
- The description mentions BLUEOS_DISABLE_* environment variables to selectively disable limits, but the script changes don’t appear to read or honor these variables yet; consider wiring them into has_any_limit and the individual limit sections so behavior matches the documented interface.
- The I/O limiting logic relies on a hardcoded list of block devices (/dev/mmcblk0, /dev/sda, /dev/nvme0n1); consider deriving the underlying block device dynamically (e.g., via findmnt/lsblk/stat on the root filesystem) so this works correctly on a wider range of platforms and configurations.
## Individual Comments
### Comment 1
<location> `core/run-service.sh:39-54` </location>
<code_context>
+ ROOT_MINOR=""
+
+ # Try whole block devices (not partitions) - order matters for Raspberry Pi
+ for DEV in /dev/mmcblk0 /dev/sda /dev/nvme0n1; do
+ if [ -b "$DEV" ]; then
+ ROOT_MAJOR=$(stat -c '%t' "$DEV" 2>/dev/null)
+ ROOT_MINOR=$(stat -c '%T' "$DEV" 2>/dev/null)
+ if [ -n "$ROOT_MAJOR" ] && [ -n "$ROOT_MINOR" ]; then
+ # Convert from hex to decimal
+ ROOT_MAJOR=$((16#$ROOT_MAJOR))
+ ROOT_MINOR=$((16#$ROOT_MINOR))
+ break
+ fi
+ fi
+ done
+
+ # Skip I/O limiting if no valid block device found
</code_context>
<issue_to_address>
**suggestion:** I/O limiting only considers a very small fixed set of block device names, which may miss valid root devices on other platforms or configurations.
The logic only checks `/dev/mmcblk0`, `/dev/sda`, and `/dev/nvme0n1`, so I/O limiting silently won’t apply on systems with other root devices (e.g. `/dev/mmcblk1`, `/dev/vda`, other NVMe indices, custom mappings). It would be more robust to (1) derive the backing block device for `/` programmatically (e.g. via `stat -c %d /` and mapping to `/dev`), or (2) at least expand the candidate set (e.g. wildcard matches, filtered to whole devices only) so this works across more environments.
```suggestion
ROOT_MAJOR=""
ROOT_MINOR=""
ROOT_DEV=""
# Try to derive the backing block device for "/" programmatically.
# Prefer findmnt, fall back to /proc/self/mounts.
if command -v findmnt >/dev/null 2>&1; then
ROOT_SOURCE=$(findmnt -n -o SOURCE / 2>/dev/null || true)
else
ROOT_SOURCE=$(awk '$2=="/"{print $1; exit}' /proc/self/mounts 2>/dev/null || true)
fi
# Map mount source to a /dev/... node when possible
if [ -n "$ROOT_SOURCE" ]; then
case "$ROOT_SOURCE" in
/dev/*)
ROOT_DEV="$ROOT_SOURCE"
;;
UUID=*|LABEL=*)
if command -v blkid >/dev/null 2>&1; then
ROOT_DEV=$(blkid -o device -t "$ROOT_SOURCE" 2>/dev/null | head -n1 || true)
fi
;;
esac
fi
# Normalise to a whole-disk device (not a partition) if possible
if [ -n "$ROOT_DEV" ] && [ -b "$ROOT_DEV" ]; then
BASENAME=$(basename "$ROOT_DEV")
case "$BASENAME" in
nvme*n*p[0-9]*|mmcblk*p[0-9]*)
WHOLE_DEV="/dev/${BASENAME%p*[0-9]}"
;;
*[0-9])
WHOLE_DEV="/dev/${BASENAME%[0-9]*}"
;;
*)
WHOLE_DEV="$ROOT_DEV"
;;
esac
if [ -b "$WHOLE_DEV" ]; then
ROOT_DEV="$WHOLE_DEV"
fi
fi
# If we successfully resolved a device, get its major/minor
if [ -n "$ROOT_DEV" ] && [ -b "$ROOT_DEV" ]; then
ROOT_MAJOR=$(stat -c '%t' "$ROOT_DEV" 2>/dev/null)
ROOT_MINOR=$(stat -c '%T' "$ROOT_DEV" 2>/dev/null)
fi
# Fallback: scan a broader set of common whole block devices across platforms
if [ -z "$ROOT_MAJOR" ] || [ -z "$ROOT_MINOR" ]; then
for DEV in /dev/mmcblk* /dev/sd? /dev/vd? /dev/nvme*n1; do
[ -b "$DEV" ] || continue
ROOT_MAJOR=$(stat -c '%t' "$DEV" 2>/dev/null)
ROOT_MINOR=$(stat -c '%T' "$DEV" 2>/dev/null)
if [ -n "$ROOT_MAJOR" ] && [ -n "$ROOT_MINOR" ]; then
break
fi
done
fi
# Convert from hex to decimal if we obtained values
if [ -n "$ROOT_MAJOR" ] && [ -n "$ROOT_MINOR" ]; then
ROOT_MAJOR=$((16#$ROOT_MAJOR))
ROOT_MINOR=$((16#$ROOT_MINOR))
fi
```
</issue_to_address>Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
Extend the service resource limitation system beyond memory to include: - CPU limits via cgroups v2 cpu.max (percentage of cores) - I/O bandwidth limits via cgroups v2 io.max (read/write MB/s) Service tuple format updated to: NAME,MEMORY_MB,CPU_PERCENT,IO_READ_MBPS,IO_WRITE_MBPS,COMMAND Environment variables to disable limits: - BLUEOS_DISABLE_RESOURCE_LIMITS: disables all limits - BLUEOS_DISABLE_MEMORY_LIMIT: disables memory limit - BLUEOS_DISABLE_CPU_LIMIT: disables CPU limit - BLUEOS_DISABLE_IO_LIMIT: disables I/O limits
b0d917d to
44c0ce8
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Helps #3356
Extend the service resource limitation system beyond memory to include:
Service tuple format updated to:
NAME,MEMORY_MB,CPU_PERCENT,IO_READ_MBPS,IO_WRITE_MBPS,COMMAND
Environment variables to disable limits:
Testing
Setup
Test 1: Memory Limit
Test 2: CPU Limit
Test 3: I/O Write Limit
Test 4: Combined Limits
Test 5: Verify Existing Services
Expected Results
Verifying Real Services
To verify limits work for actual services (with
DOCKER_CGROUPproperly set):Cleanup
Summary by Sourcery
Extend run-service resource management to support optional CPU and disk I/O limits alongside memory, and improve how processes are attached to cgroups.
New Features:
Enhancements: