On Debian desktop images the Armbian GRUB wallpaper was replaced by
Debian's theme image (Trixie: ceratopsian). Armbian only appended its
WALLPAPER to /usr/share/desktop-base/grub_background.sh, which desktop-base
ships and owns as a conffile — on Debian desktop images desktop-base is
installed and its version of that file wins, pointing GRUB at
/usr/share/images/desktop-base/desktop-grub.png. Ubuntu doesn't overwrite
it, so the Armbian image survived there.
Set GRUB_BACKGROUND in Armbian's own 98-armbian.cfg. 05_debian_theme
(grub-common) gives GRUB_BACKGROUND precedence over the sourced WALLPAPER,
so the Armbian image is used on both Debian and Ubuntu regardless of
desktop-base.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
- the way dtc code ends up in pypi is very strange / non-obvious
- there is an upstream fix at git.kernel.org/pub/scm/utils/dtc/dtc.git/commit?id=5008d1d6a356b8d0a78060da2e1021507d529cff
- but that is not yet in Rob Herring's pypi adaptation at devicetree-org/pylibfdt
- I've a fork with the upstream sync at https://github.com/rpardini/devicetree-pylibfdt/tree/sync-with-upstream-26.08
* uefi-x86: resync 7.1 and 7.2 Apple-T2 patches from t2linux
Drop the locally-copied Apple-T2 patch sets for uefi-x86-7.1 and
uefi-x86-7.2 and replace them with the current series from their
upstream home, t2linux/linux-t2-patches (branches 7.1 and 7.2), where
they are actively maintained. Only *.patch files are kept, matching the
family config's own auto-download cleanup.
This realigns both trees with upstream: the 7.1 SMC stack moves to the
macsmc series and both gain the APFS driver; 7.2 additionally picks up
the t2bce driver stack rename and the amdgpu/ACPI T2 fixes.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* uefi-x86-7.1: rebase t2linux magicmouse onto 7.1.12; drop broken macsmc-power
The upstream t2linux 7.1 Apple-T2 series does not apply/build against
Armbian's 7.1.12 kernel, which has since absorbed much of the magicmouse
work upstream. Carry three Armbian deltas on top of the resync:
- 4001: drop the "Add .reset_resume for SPI trackpads" sub-patch --
mainline 7.1.12 already defines magicmouse_reset_resume() and wires
.reset_resume, so the out-of-tree copy is a duplicate (build failure +
a hard-failing hunk on the driver struct).
- 4000 / 4006: bracket the transport-ops stack to reconcile it with
mainline's backported recursion guard (db8d634128d2). 4000 reverts the
__magicmouse_raw_event(nested) split so the stack applies against the
flat function it expects; 4006 restores the guard on the resulting
per-transport USB handler. Fixes "'nested' undeclared".
- Drop 3011 (power-supply-macsmc "add support for intel macs"): this
experimental feature's battery-props rewrite collides with three
mainline refactors in macsmc-power.c (fw_ge_27 detection, the
macsmc_battery_read_bcf0 helper, reordered identity reads) and cannot
be reconciled without a compile+hardware test. It is irrelevant to the
qemu-uboot-x86 build target. The is_acpi field it consumes is defined
by 3001/3002, so nothing else depends on it.
Verified: the full magicmouse chain (4000, 4001, 4004, 4005, 4006)
applies to v7.1.12 with no corrupting fuzz and is structurally
consistent. Compile is left to CI. The durable fix belongs upstream at
t2linux (rebase their 7.1 branch onto current 7.1.y).
Signed-off-by: Igor Pecovnik <igor@armbian.com>
---------
Signed-off-by: Igor Pecovnik <igor@armbian.com>
The nightly "Build All Artifacts" run fails on every x86 kernel target
(edge/current/cloud/legacy) while applying 4001-asahi-trackpad.patch:
Failed to apply patch .../4001-asahi-trackpad.patch
Hunk #2 FAILED at 1391 {hid-magicmouse.c}
The Asahi/T2 magicmouse work has been upstreamed. Mainline and the stable
trees the build now tracks - 6.12.107, 6.18.48, 7.1.12, all rolled out
around 2026-08-27 - carry `magicmouse_reset_resume()` and the
`.reset_resume` field of `struct hid_driver magicmouse_driver` in
drivers/hid/hid-magicmouse.c. The committed T2 patch still adds both, so
it collides and Armbian aborts the whole kernel build. Builds were green
through 2026-08-26; the point releases carrying the backport landed on the
27th, which is exactly when the nightly started failing.
The offending change is the self-contained sub-patch
"HID: magicmouse: Add .reset_resume for SPI trackpads" (adds the function
AND the struct field - both now upstream, so the whole sub-patch, not just
the failing hunk, is redundant). Drop it from all four x86 T2 patch dirs
(6.12/6.18/7.1/7.2 - 7.2/bleedingedge is not in the failing nightly but
carries the identical collision).
Unrelated `hid_driver_reset_resume()` calls in the SPI transport sub-patch
are left untouched. The remaining sub-patches still apply today; note the
rest of the Asahi magicmouse series is also landing upstream, so a full
t2linux re-sync against the new point releases will be the durable fix.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
The clusters still come out of reset on the 24 MHz oscillator in
v2026.07, so boards moved to that tag (turing-rk1, nanopct6,
mekotronics-r58x-pro) crawl through early boot again. The v2026.04
patch applies with a two line offset, so copy it over unchanged.
Signed-off-by: SuperKali <hello@superkali.me>
TI's vendor btti_uart driver oopses while probing the onboard CC33xx Bluetooth UART. The resulting oops prevents the SSD16xx DRM framebuffer from unblanking, leaving the e-paper display stuck on the U-Boot image.\n\nUse Armbian's MODULES_BLACKLIST setting so the driver is disabled in both the root filesystem and generated initramfs until the vendor driver is fixed.
Signed-off-by: Andrei Aldea <andrei1998@gmail.com>
Address review feedback on the shipped 50-default.conf so it is a faithful
drop-in for the linux-sysctl-defaults package it now Provides:
- kernel.sysrq: 16 -> 438 (0x01b6), the value linux-sysctl-defaults ships on
both Debian trixie and Ubuntu. 16 (sync-only) would have disabled REISUB,
process kill and stack traces over serial -- the main recovery path on
headless SBCs.
- fs.protected_regular: 1 -> 2, matching the distro default (on trixie, where
the real package is Conflicts-removed, 1 was weaker than the distro value).
- add vm.max_map_count = 1048576, which the distro file also ships.
- rp_filter: drop the net.ipv4.conf.all.rp_filter line. Effective rp_filter is
max(all, per-interface), so forcing .all overrode per-interface choices;
the distro package only sets .default.
- prefix ping_group_range and net.core.default_qdisc with "-" (failure
tolerant) so old vendor kernels lacking ping_group_range / sch_fq_codel do
not log a sysctl error on every boot. Correct the header comment that
conflated this prefix with the newer glob-exclude syntax.
Also switch the BSP postinst from `sysctl -p` to `sysctl --system` so the
drop-in under /usr/lib/sysctl.d is applied on package upgrade instead of only
on the next boot (`-p` reads only /etc/sysctl.conf).
Signed-off-by: Igor Pecovnik <igor@armbian.com>
Rather than pulling the distro's linux-sysctl-defaults into every image
(armbian/build#9698), ship its content in the board-support package and have the
BSP Provide/Conflict/Replace it - per @tabrisnet's suggestion on that PR.
- Add /usr/lib/sysctl.d/50-default.conf to packages/bsp/common: armbian's copy
of systemd's 50-default.conf (the primary win is net.ipv4.ping_group_range so
ping works without setuid/CAP_NET_RAW; plus fs.protected_* and the usual net
hardening). Kept in pre-glob syntax (explicit .all/.default, no `-key` unset
lines) so it parses on every systemd version Armbian ships. kernel.sysrq stays
at systemd's conservative 16.
- armbian-bsp-cli-deb: Provides + Conflicts + Replaces linux-sysctl-defaults, so
the dependency is satisfied without the external package and the file is taken
over cleanly if it was ever installed.
Supersedes #9698.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
This ensures the swapfile is created with the No_COW attribute.
Otherwise, swapon fails with "Invalid argument" and the kernel logs a
warning:
BTRFS warning (device mmcblk1p1): swapfile must not be copy-on-write
Signed-off-by: Darsey Litzenberger <dlitz@dlitz.net>
Advertise the four PLL1 derived rates the GPU clock mux can reach, so the
driver settles on the rated 819 MHz instead of the vendor default. The mux
also feeds pll2_d3 at 1 GHz, past what the K1 is rated for, so the table
stops at 819.2 MHz.
Signed-off-by: SuperKali <hello@superkali.me>
The DDK pins the core at a hardcoded 614 MHz while the K1 rates the
BXE-2-32 at 819 MHz. Read the highest OPP the device tree advertises so the
frequency comes from the hardware description, and keep the vendor constant
as the fallback for boards that ship no table.
Signed-off-by: SuperKali <hello@superkali.me>
Its udev worker never completes, so udevadm settle in the initramfs waits
out the full timeout on every boot and adds about two minutes before the
root filesystem is even checked. Nothing in the image drives the JPU.
Signed-off-by: SuperKali <hello@superkali.me>
lt8911exb registers a drm_panel but never calls drm_panel_of_backlight(),
so drm_panel_enable() had no backlight to unblank. Bind it at enable time
rather than at probe, because pwm_bl registers after this bridge and
failing the probe on -EPROBE_DEFER stalls the DSI bind.
Signed-off-by: SuperKali <hello@superkali.me>
dtc -@ gives pwm_bl a phandle even though nothing referenced it, and
pwm_bl.c reads that as "another driver will enable this", so the panel came
up blanked. Point the lcd node at pwm_bl so the lt8911exb panel owns it.
Signed-off-by: SuperKali <hello@superkali.me>
The K1 PWM block is compatible "spacemit,k1x-pwm", which pwm-pxa drives, but the
legacy defconfig carried no PWM controller driver at all, so pwm14 never probed
and pwm-backlight on the MUSE Book sat in probe deferral with no backlight class
device. The vendor k1_defconfig builds it in, current already has it as a module.
Signed-off-by: SuperKali <hello@superkali.me>
The K1 opp table carries a turbo-mode entry at 1.8 GHz that the boost flag
unlocks, and the cpufreq driver already allows it since the max freq
limitation patch. Opt the family in, verified on musebook at 57 C under
full load against a 75 C trip point.
Signed-off-by: SuperKali <hello@superkali.me>
OPPs marked turbo-mode stay hidden until the cpufreq boost flag is set, so
writing a turbo frequency to scaling_max_freq is clamped without an error.
Raise the flag from a new BOOST key before the governor and the limits are
applied. It defaults to false, so no board changes behaviour unless it opts in.
Signed-off-by: SuperKali <hello@superkali.me>
* labels: only clear review labels when the approval actually counts
The "Remove review-related labels" step ran on a bare success(), which is not
the same question as "was this PR approved".
The chain fires on any approving review, but the action is configured with
require_committers_approval: true, so it counts only approvals from people with
write access. On a public repo anyone with read access can approve. When a
non-committer does, the action exits 0 and reports isApproved=false: it
correctly declines to add "Ready to merge", and then the next step went ahead
and stripped "Needs review", "Work in progress", "Backlog", "Can be closed?",
"Help needed" and "Needs Documentation" anyway.
So any passer-by could clear a PR's review-tracking state without the PR being
approved by anyone who counts.
Gate the cleanup on the action's isApproved output, which it already exports.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* labels: don't persist the checkout token in the label workflows
actions/checkout writes the workflow token into the local git config by
default. None of these three checkouts run an authenticated git command:
the labeler steps read .github/labeler.yml and .github/labels.yml from the
workspace and authenticate through their own repo-token input, and the
"Ready to merge" job shells out to gh, which uses GH_TOKEN.
The pull_request_target checkout defaults to the base ref, so no untrusted
pull request code runs beside the token -- this is defence in depth rather
than a live hole -- but there is no reason to leave it lying there.
Note the first checkout stays: it looks unused, but gh needs the git remote
to resolve which repo to query. Dropping the credential keeps that working.
Same change in armbian/ci and armbian/armbian.github.io.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* labels: require a canonical PR number before touching labels
Number.parseInt consumes the longest valid prefix rather than rejecting
trailing junk, so "123abc" became 123 and "1e3" became 1 -- both integers,
both greater than zero, both sailing past the isInteger guard. The cleanup
step would then strip labels off whichever pull request that produced.
Require canonical decimal digits and convert with Number instead. Malformed
input now fails the step loudly rather than silently retargeting it.
The value still comes from github.event.pull_request.number by way of an
artifact, so this is not a reachable bug today; it is about the guard
actually guarding what it claims to.
Same change in armbian/ci and armbian/armbian.github.io.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* labels: validate the PR number where it enters the job
The previous commit validated PR_NUMBER inside the github-script cleanup step,
which is too late and too conditional to be the gate.
Everything in the job consumes steps.pr.outputs.number, starting with
label-when-approved-action, which parseInt()s it and then reads reviews and
writes labels. Validating after that step means validating after those writes.
Worse, the cleanup step is gated on isApproved == 'true', so on the
not-approved path the check did not run at all.
Move the check into the `pr` step that produces the value: reject anything
that is not canonical decimal digits, and fail the job there, before any
consumer sees it.
The github-script check stays as a second line of defence, in case the gate
above is ever moved or removed.
Same change in armbian/ci and armbian/armbian.github.io.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
---------
Signed-off-by: Igor Pecovnik <igor@armbian.com>
On Orange Pi 4 Pro, U-Boot fails to detect NVMe drives because it enables the wrong 3.3V regulator. The M.2 slot is powered by dc1sw1, but board-uboot.dts references dc1sw2. As a result, PCIe link training never starts (Link up timeout, LTSSM stays in Detect.Quiet), and nvme scan returns nothing.
Linux works because its device tree marks both dc1sw1 and dc1sw2 as regulator-always-on, hiding the issue in U-Boot.
This patch changes pcie3v3_supply to dc1sw1 and also corrects pcie1v8_supply to bldo1, aligning with the actual board schematic.
v4l2loopback only builds against current kernels from 0.15.3 onwards. Earlier
releases call v4l2_fh_add() with the pre-signature-change argument count and
fail the DKMS build with "too few arguments to function 'v4l2_fh_add'". Debian
trixie still ships 0.15.0-2 in main, so gate on the apt candidate version and
skip the extension rather than failing the whole build.
The candidate lookup goes through chroot_sdcard_custom_with_apt_logic. A plain
apt-cache call cannot work here: the host-side apt lists are bind-mounted into
the chroot only for the duration of a chroot_sdcard_apt_get* call, and the
image's own /var/lib/apt/lists is not filled in until much later in the build,
so this early in post_install_kernel_debs apt-cache sees an empty index and
reports nothing at all. That runner mounts the lists, and pins LC_ALL=C, which
keeps the gettext-translated "Candidate:" label parseable. It logs stdout
rather than returning it, hence the redirect to a file read back host-side.
Both the query and the parse are kept clear of errexit. apt-cache exits 0 even
for an unknown package, but the runner around it can fail -- apt-cacher-ng
restart, the cache bind mounts, the chroot itself -- and an unreadable policy
file would abort from a command substitution; either would kill the build
instead of reaching the fallback. The policy file is removed before the query
so a leftover can never be read as this query's answer, parsed only when the
query succeeded, and removed again afterwards so a partial file is not shipped.
An unreadable candidate is treated as inconclusive and installs as before,
rather than skipping. A silent skip drops the module from the image behind one
warning line, which is a worse failure than letting apt refuse out loud.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* extensions: add @description headers and a list generator
Add a one-line `# @description` header near the top of every extension in
extensions/ (85 files), each ~35-45 words / 3 sentences, source-verified
against the extension's actual behaviour. Two extensions with a dedicated
docs page also carry a `# @doc-page` link.
Add lib/tools/gen-extensions-list.py, which scans extensions/**/*.sh for
these headers and prints the Markdown extensions reference consumed by the
documentation repo. The list is no longer hand-maintained: edit an
extension's `# @description` and the generator brings the change over.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* extensions: correct descriptions flagged in review, validate @doc-page
Seven @description headers claimed more than the code does:
cleanup-space-final-image zerofree globs ${LOOP}p?, so p10+ is not covered
image-output-abl one recovery image from ABL_DTB_LIST[0], not per-DTB
marvell-tools binaries-marvell and cryptopp track branches, not pins
nvidia also skipped without a working headers package
odin2-preset-firstrun ships hardcoded 1234 root/user passwords
preset-firstrun static networking is on by default, not optional
uefi-edk2-rk3588 acpi=off is a default, not forced
Reword each to match, and call out the two credential hazards explicitly
rather than leaving them implied.
In the generator, restrict @doc-page to site-relative paths. The value goes
into a Markdown link target on the published docs site and Python-Markdown
does not sanitize URL schemes, so a "javascript:" target would survive into
the page; unusable values are now dropped with a warning on stderr.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
* gen-extensions-list: close two holes in @doc-page validation
DOC_PAGE_RE accepted "//external.example/x". "/" is in the character class, so
after the required leading slash a second one matched happily -- the protocol-
relative case the comment claimed to reject sailed straight through. Add a
negative lookahead.
The annotation parser also matched a single \S+ token, so "@doc-page /guide
extra" and a bare "@doc-page" failed to match at all and were dropped in
silence, with no warning. Capture the whole value instead and let validation
reject it, so malformed annotations are reported rather than ignored.
Output over the current extensions/ tree is byte-identical.
Signed-off-by: Igor Pecovnik <igor@armbian.com>
---------
Signed-off-by: Igor Pecovnik <igor@armbian.com>
Mali-G52 (Bifrost) is supported by the in-tree panfrost driver with a
plain Mesa userspace. Enable CONFIG_DRM_PANFROST and drop the closed
kbase/libmali stack:
- kernel: PANFROST=y, all MALI_BIFROST/kbase options off, LIMA off
- board: RECOMPUTER_GPU_STACK="panfrost" skips the libmali-bifrost
blob install and the GDM X11 override (Wayland works with Mesa)
- family: extend the panthor userspace cleanup to panfrost, including
a --reinstall of libegl1/libgles2/libegl-mesa0 (the libmali deb
deletes Mesa's .so bodies, not just the symlinks)
Rationale: the 2020 g24p0 blob cannot drive modern GNOME. Mutter
Wayland crashes with it were already known (hence the X11 override),
and GTK4's GSK GL renderer additionally triggers deterministic
DATA_INVALID_FAULT job chains - half-rendered windows, per-frame GPU
fault storms and occasional full-system crashes - while every
non-GTK4 GL path (gbm direct, Wayland via mutter, Xwayland) works.
The closed stack is not advertised as a fallback for this board:
with CONFIG_DRM_PANFROST enabled there is no kbase left to serve the
blob (both drivers cannot bind the same GPU), so the "mali" hooks
stay dormant and MALI_USE_SYSTEM_GBM is dropped as meaningless.
Hardware-verified on reComputer RK3576 devkit: vendor GNOME desktop
image (Ubuntu) boots to an accelerated Wayland session out of the box
(glmark2-es2-wayland score 1064, zero GPU faults).
Ubuntu's gdm greeter runs as dynamic users (gdm-greeter-XXXX), so the
existing `usermod -aG render Debian-gdm` is a no-op there and the
greeter cannot open /dev/dri/renderD* or /dev/dma_heap/*. Mutter then
fails with "Failed to create gbm device" -> "No GPUs found" and gdm
gives up after repeated greeter crashes - the desktop never comes up
(observed on the 26.8.2 Ubuntu image, screen stuck at a blinking
cursor).
Grant access with uaccess ACLs instead of group membership: tag the
render nodes and DMA heaps with uaccess so logind hands the active
session user (dynamic greeter users included) an ACL, keeping the
nodes at 0660. The Debian static-user usermod is kept as a harmless
extra.
Hardware-verified on reComputer RK3576 devkit (Ubuntu image): the
greeter comes up on a cold boot, the ACL follows the session
(gdm-greeter at the login screen, the logged-in user afterwards) and
a GPU workload (glmark2-es2-wayland) runs clean.