boot: stop emitting splash=verbose to the kernel cmdline#9653
boot: stop emitting splash=verbose to the kernel cmdline#9653igorpecovnik wants to merge 6 commits intomainfrom
Conversation
….ignore-serial-consoles
extensions/grub.sh and extensions/grub-riscv64.sh both had this
conditional in configure_grub():
[[ "$BOOT_LOGO" == "yes" || "$BOOT_LOGO" == "desktop" && "$BUILD_DESKTOP" == "yes" ]] &&
GRUB_CMDLINE_LINUX_DEFAULT+=" quiet splash plymouth.ignore-serial-consoles ..." ||
GRUB_CMDLINE_LINUX_DEFAULT+=" splash=verbose ..."
Two problems with the false branch:
1. 'splash=verbose' is not a valid kernel argument. The kernel
logs it explicitly:
Unknown kernel command line parameters "splash=verbose",
will be passed to user space.
It is also not a documented Plymouth flag (Plymouth uses bare
'splash' as a boolean), and Plymouth interprets the literal
value 'verbose' as a request to render the verbose/text
theme. So a CLI image gets baked with this useless string.
2. The condition only fires the graphical branch when the image
is being built as a desktop image AT IMAGE BUILD TIME. Users
routinely build a CLI image, then add a desktop later via
armbian-config. /etc/default/grub.d/98-armbian.cfg was
already baked with the bad cmdline at image-build time, so
no amount of desktop-install postinst work could ever make
Plymouth render its graphical theme — the user always saw
either text/blank because the cmdline still said
'splash=verbose'.
Drop the conditional. Always emit
quiet splash plymouth.ignore-serial-consoles
on UEFI x86 and riscv64. Plymouth handles "no theme installed"
and "no DRM" gracefully — these flags are harmless on a CLI
install — and they are correct for any subsequent desktop
install whether done at image-build time or later.
Also drop 'i915.force_probe=*' from the riscv64 cmdline. i915
is the x86 Intel graphics driver and the knob is meaningless
on riscv64 hardware.
Reproducer:
build any uefi-x86 image with BUILD_DESKTOP=no, install gnome
via armbian-config later, reboot. /proc/cmdline shows
'splash=verbose', dmesg complains about the unknown arg, and
Plymouth renders its text/details theme instead of the
Armbian splash on every subsequent boot.
Companion to the previous commit ('grub: stop emitting
splash=verbose'), which fixed the same bug in extensions/grub.sh
and extensions/grub-riscv64.sh for UEFI x86/riscv64 images. The
exact same broken pattern lived in 24 U-Boot boot script
templates and one .tvb board file:
if test "${bootlogo}" = "true"; then
setenv consoleargs "splash plymouth.ignore-serial-consoles ${consoleargs}"
else
setenv consoleargs "splash=verbose ${consoleargs}" # <-- broken
fi
The else branch fires whenever /boot/armbianEnv.txt does not set
bootlogo=true, which is the default on every supported SBC. The
resulting kernel cmdline contains 'splash=verbose', which the
kernel rejects with
Unknown kernel command line parameters "splash=verbose"
and Plymouth interprets as "render the verbose/text theme", so
even after a user installs a desktop, Plymouth never shows the
graphical Armbian splash on these boards.
Strip 'splash=verbose' from the else branch in every boot
script. The else branch becomes a no-op self-assignment of
${consoleargs} (or empty plymouthargs in the boot-meson-s4t7
variant), which is what bootlogo=false should mean: no splash
flag in the cmdline at all. Plymouth then runs in text mode
when bootlogo=false and switches to the configured graphical
theme when the user flips bootlogo=true in armbianEnv.txt.
Affected files (24 boot scripts + 1 board file):
config/bootscripts/boot-{cubox,generic.cmd.template,genio,
meson-gx,meson-s4t7,meson64,mvebu,nuvoton-ma35d1,
odroid-xu4,onecloud,qemu,qrb2210,rk322x,rk3506,rk3576,
rk35xx,rockchip,rockchip64,rockchip64-ttyS0,sun50i-next,
sun50iw9,sunxi,udoo,xpressreal-t3}.{cmd,template,ini}
config/boards/aml-t95z-plus.tvb (SRC_CMDLINE)
Two files containing 'splash=verbose' are intentionally left
alone:
- aml-c400-plus/_packages/bsp-cli/boot/{s905,emmc}_autoscript:
these are *binary* compiled U-Boot scripts; the source .cmd
is fixed above and the binaries will be regenerated on the
next image build.
- patch/kernel/archive/rockchip64-6.6/dt/rk3566-core3566.dts:
a vendor-image device tree dump, not active boot config.
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
📝 WalkthroughWalkthroughThis PR removes Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Poem
🚥 Pre-merge checks | ✅ 2 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (1)
config/bootscripts/boot-odroid-xu4.ini (1)
27-31: LGTM! Correct removal of invalidsplash=verboseparameter.The change correctly removes the invalid
splash=verbosekernel parameter from the else branch. Now whenbootlogo != "true", no splash argument is added to the kernel command line, which is the intended behavior.The else branch now performs a no-op assignment (
setenv consoleargs "${consoleargs}"), which could technically be removed entirely to simplify the code. However, this pattern is consistent across all other boot scripts (boot-sunxi.cmd, boot-rockchip64.cmd, boot-mvebu.cmd), suggesting it's an intentional standardized approach for clarity.Optional: Simplify by removing the no-op else branch
While the current pattern is consistent with other boot scripts, the else branch could be removed since it does nothing:
if test "${bootlogo}" = "true"; then setenv consoleargs "splash plymouth.ignore-serial-consoles ${consoleargs}" -else - setenv consoleargs "${consoleargs}" fiNote: Only consider this if you decide to update the pattern across all boot scripts for consistency.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@config/bootscripts/boot-odroid-xu4.ini` around lines 27 - 31, The else branch is a no-op (setenv consoleargs "${consoleargs}") after testing bootlogo and can be removed to simplify the script; edit the block that checks bootlogo (the if test "${bootlogo}" = "true"; then ... fi) to drop the else clause so only the true branch sets consoleargs with splash plymouth.ignore-serial-consoles, and if you want consistency update the equivalent patterns in other scripts that use the same bootlogo check (look for occurrences of setenv consoleargs "${consoleargs}" in their bootlogo conditionals).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@extensions/grub.sh`:
- Around line 268-284: The GRUB_CMDLINE_LINUX_DEFAULT line unconditionally
appends the Intel-specific i915.force_probe=* flag; scope that flag to amd64
only by appending "i915.force_probe=*" conditionally based on the target
architecture (check the same arch variable used elsewhere in this extension,
e.g. TARGET_ARCH or ARCH), while always keeping the Plymouth flags (quiet splash
plymouth.ignore-serial-consoles loglevel=3). Update the extension so
GRUB_CMDLINE_LINUX_DEFAULT gets the Plymouth bits unconditionally and only adds
"i915.force_probe=*" when the detected architecture is amd64 (mirror the
approach used in grub-riscv64.sh where Intel-specific flags are omitted).
---
Nitpick comments:
In `@config/bootscripts/boot-odroid-xu4.ini`:
- Around line 27-31: The else branch is a no-op (setenv consoleargs
"${consoleargs}") after testing bootlogo and can be removed to simplify the
script; edit the block that checks bootlogo (the if test "${bootlogo}" = "true";
then ... fi) to drop the else clause so only the true branch sets consoleargs
with splash plymouth.ignore-serial-consoles, and if you want consistency update
the equivalent patterns in other scripts that use the same bootlogo check (look
for occurrences of setenv consoleargs "${consoleargs}" in their bootlogo
conditionals).
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 02da5638-9895-47ff-9c3b-c6d43edc5875
📒 Files selected for processing (27)
config/boards/aml-t95z-plus.tvbconfig/bootscripts/boot-cubox.cmdconfig/bootscripts/boot-generic.cmd.templateconfig/bootscripts/boot-genio.cmdconfig/bootscripts/boot-meson-gx.cmdconfig/bootscripts/boot-meson-s4t7.cmdconfig/bootscripts/boot-meson64.cmdconfig/bootscripts/boot-mvebu.cmdconfig/bootscripts/boot-nuvoton-ma35d1.cmdconfig/bootscripts/boot-odroid-xu4.iniconfig/bootscripts/boot-onecloud.cmdconfig/bootscripts/boot-qemu.cmdconfig/bootscripts/boot-qrb2210.cmdconfig/bootscripts/boot-rk322x.cmdconfig/bootscripts/boot-rk3506.cmdconfig/bootscripts/boot-rk3576.cmdconfig/bootscripts/boot-rk35xx.cmdconfig/bootscripts/boot-rockchip.cmdconfig/bootscripts/boot-rockchip64-ttyS0.cmdconfig/bootscripts/boot-rockchip64.cmdconfig/bootscripts/boot-sun50i-next.cmdconfig/bootscripts/boot-sun50iw9.cmdconfig/bootscripts/boot-sunxi.cmdconfig/bootscripts/boot-udoo.cmdconfig/bootscripts/boot-xpressreal-t3.cmdextensions/grub-riscv64.shextensions/grub.sh
Follow-up to the previous two commits in this PR. They left the graphical Plymouth flags in place but also kept 'quiet' and 'loglevel=3', which suppress kernel boot messages entirely. The result is a clean boot splash but a user complaint: "I don't see anything during boot anymore." Drop both. Plymouth still renders the splash on top of the kernel boot messages — the messages just remain visible underneath so you can see what the system is doing. The user can still press Esc during boot to drop the splash and read the messages directly, which is the upstream-standard interaction. Applies to extensions/grub.sh (UEFI x86) and extensions/grub-riscv64.sh (UEFI riscv64). U-Boot SBC scripts are unaffected — they already have no 'quiet' or 'loglevel=3' in the bootlogo=true branch and the bootlogo=false branch (the default) is now empty after the previous commit, so SBC users already see kernel messages.
Ubuntu ships a /etc/grub.d/10_linux snippet that, whenever
'splash' appears in GRUB_CMDLINE_LINUX_DEFAULT, automatically
appends 'vt.handoff=7' to the generated kernel cmdline:
if [ x$GRUB_DISABLE_VT_HANDOFF != xtrue ]; then
case "$GRUB_CMDLINE_LINUX $GRUB_CMDLINE_LINUX_DEFAULT" in
*splash*) vt_handoff=vt.handoff=7 ;;
esac
fi
vt.handoff=7 tells the kernel to hand the framebuffer console
over to whatever userspace eventually claims VT7 — i.e. the X
server started by the display manager. On a stock Ubuntu desktop
install that's fine: gdm starts, claims VT7, the screen is
graphical from boot to login.
On Armbian:
- CLI installs have no display manager, nothing ever claims
VT7, and after Plymouth quits the kernel never restores the
framebuffer to fbcon. Result: a blank local console even
though getty@tty1 is alive and accepting writes — direct
'echo TEST > /dev/tty1' silently succeeds but renders no
pixels.
- Desktop installs that the user later removes via
armbian-config end up in the same state: gdm/lightdm gets
purged, VT7 becomes orphaned, and even after we
'systemctl set-default multi-user.target' and isolate, the
framebuffer stays blank. (This is what motivated finding
this bug — the symptom on a virtio-gpu QEMU test box was
"screen never lights up after desktop remove".)
The fix is GRUB_DISABLE_VT_HANDOFF=true, which is the
upstream-supported escape hatch that the same 10_linux snippet
honours: it skips the vt_handoff injection entirely. The
framebuffer console then stays bound to fbcon across the entire
boot, regardless of whether a DM is installed, and tty1 remains
visible and writable for the entire userspace lifetime.
Apply to both extensions/grub.sh (UEFI x86) and
extensions/grub-riscv64.sh.
Together with the previous commits in this PR, the UEFI cmdline
on a freshly built Armbian image is now:
splash plymouth.ignore-serial-consoles i915.force_probe=*
(no quiet, no loglevel=3, no vt.handoff=7) — Plymouth shows the
Armbian theme on top of visible kernel boot messages, and the
local console keeps working through every install/remove cycle.
The previous commit set GRUB_DISABLE_VT_HANDOFF=true expecting
Ubuntu's grub2 to honour it. It does not — that variable is
upstream grub2 only. Ubuntu carries a build-time patch
(debian/patches/vt-handoff.patch) that hardwires the behaviour
behind ./configure --enable-vt-handoff and gives no
/etc/default/grub knob to disable it. Verified against
ubuntu/noble grub2 2.12-1ubuntu7 source.
The runtime gate that DOES exist is in the gfxmode function
emitted into /boot/grub/grub.cfg:
if [ "${1}" = "keep" ]; then
set vt_handoff=vt.handoff=7
else
set vt_handoff=
fi
So vt.handoff=7 only expands when the gfxpayload arg is exactly
'keep'. Setting GRUB_GFXPAYLOAD_LINUX=text makes the runtime
check fail and the framebuffer console stays bound to fbcon for
the entire userspace lifetime.
While I was here I also discovered the previous line
'GRUB_GFXPAYLOAD=keep' was silently ignored — the correct
variable name is GRUB_GFXPAYLOAD_LINUX, not GRUB_GFXPAYLOAD.
That bug has been in extensions/grub.sh and grub-riscv64.sh
since the file was written. The previous typo did no harm
because grub2's default for the missing variable happens to be
'keep' — but it does mean we never had the gfxpayload knob
under our control, which is part of why this bug took so long
to track down.
Drop the dead GRUB_DISABLE_VT_HANDOFF=true line that the
previous commit added, and replace the old GRUB_GFXPAYLOAD=keep
typo with GRUB_GFXPAYLOAD_LINUX=text. After this, /proc/cmdline
on a freshly built UEFI image will be:
splash plymouth.ignore-serial-consoles i915.force_probe=*
with no vt.handoff=7, regardless of whether a desktop is
installed. The framebuffer console remains visible across
install/remove cycles, Plymouth still draws its splash on top.
References:
https://launchpad.net/ubuntu/+archive/primary/+sourcefiles/grub2/2.12-1ubuntu7/grub2_2.12-1ubuntu7.debian.tar.xz
debian/patches/vt-handoff.patch in that source tree
The getty@tty1.service drop-in at
packages/bsp/common/lib/systemd/system/getty@tty1.service.d/10-noclear.conf
only contained 'TTYVTDisallocate=no'. It did NOT actually drop
the upstream '--noclear' from agetty's ExecStart, so the
inherited template ran:
/sbin/agetty -o '-p -- \\u' --noclear - $TERM
Result on every Armbian boot: kernel boot messages and
initramfs output remain stacked above the login prompt on
tty1, even though Plymouth ran and we expected a clean screen.
Override ExecStart in the same drop-in to drop --noclear, so
agetty wipes the screen with \\033[H\\033[2J before painting
its issue/login banner. After this, tty1 shows just:
Armbian X.Y.Z release tty1
hostname login:
The empty 'ExecStart=' line is required by systemd to clear the
inherited template value before we set the new one — that's the
documented pattern for ExecStart overrides in service drop-ins.
The drop-in filename ("10-noclear.conf") is now a slight
misnomer since the file does the opposite of "no clear", but
renaming the file would break package upgrades (the old file
would stick around alongside the new one). The original name
was always referring to TTYVTDisallocate, not agetty's
--noclear, so the filename was never accurate to begin with.
Add a comment in the file explaining what it actually does.
|
For CLI image, it's quite strange to show a bootlogo before shell ? Changing some bootflag after installed desktop maybe a good way. |
Reasoning behind this is switchover from desktop to CLI, after everything desktop, including plymoth is removed. This works as expected on (x86) UEFI targets while not sure what happens elsewhere, so your comment is legit. Perhaps better to change this only on UEFI and leave others as is. |
Summary
`splash=verbose` was being baked into the kernel cmdline on every Armbian image — both UEFI x86/riscv64 (via `extensions/grub.sh`) and every U-Boot SBC (via 24 `config/bootscripts/boot-*.cmd` files plus one `.tvb` board config). It is not a valid kernel argument and not a documented Plymouth flag. The kernel logs:
```
Unknown kernel command line parameters "splash=verbose", will be passed to user space.
```
Plymouth then receives the literal string `verbose` and renders its text/details theme instead of the configured graphical theme. So even after a user installs a desktop and the Armbian Plymouth theme is set as the default, the boot splash never appears.
Reproducer
The same symptom is reproducible on any SBC where `bootlogo` defaults to `false` in `/boot/armbianEnv.txt` (which is most of them).
Changes
Commit 1 — `extensions/grub.sh` and `extensions/grub-riscv64.sh`
The conditional was:
```bash
[[ "$BOOT_LOGO" == "yes" || "$BOOT_LOGO" == "desktop" && "$BUILD_DESKTOP" == "yes" ]] &&
GRUB_CMDLINE_LINUX_DEFAULT+=" quiet splash plymouth.ignore-serial-consoles ..." ||
GRUB_CMDLINE_LINUX_DEFAULT+=" splash=verbose ..."
```
Two problems with the false branch:
Drop the conditional. Always emit `quiet splash plymouth.ignore-serial-consoles` on UEFI x86 and riscv64. Plymouth handles "no theme installed" and "no DRM" gracefully — these flags are harmless on a CLI install — and they are correct for any subsequent desktop install whether done at image-build time or later.
Also drop `i915.force_probe=*` from the riscv64 cmdline. That knob is meaningless on riscv64 (it's the x86 Intel graphics driver).
Commit 2 — 24 U-Boot bootscripts + 1 board file
The exact same broken pattern lives in every `boot-*.cmd`:
```
if test "${bootlogo}" = "true"; then
setenv consoleargs "splash plymouth.ignore-serial-consoles ${consoleargs}"
else
setenv consoleargs "splash=verbose ${consoleargs}" # <-- broken
fi
```
The else branch fires whenever `/boot/armbianEnv.txt` does not set `bootlogo=true`, which is the default on every supported SBC.
Strip `splash=verbose` from the else branch in every boot script. The else branch becomes a no-op self-assignment of `${consoleargs}` (or `setenv plymouthargs ""` in the boot-meson-s4t7 variant), which is what `bootlogo=false` should mean: no splash flag in the cmdline at all. Plymouth runs in text mode silently when `bootlogo=false` and switches to the configured graphical theme when the user flips `bootlogo=true` in armbianEnv.txt.
What is intentionally NOT changed
Test plan
Recovery for existing installs
UEFI x86/riscv64:
```
sudo sed -i -E 's/\bsplash=verbose\b/splash plymouth.ignore-serial-consoles/' /etc/default/grub.d/98-armbian.cfg
sudo update-grub
sudo reboot
```
SBC with U-Boot:
```
echo 'bootlogo=true' | sudo tee -a /boot/armbianEnv.txt
sudo reboot
```
(No image rebuild required for either; the boot scripts read `armbianEnv.txt` at boot time.)
Summary by CodeRabbit
Bug Fixes
Chores