2019-04-24 18:24:16 +01:00
|
|
|
{
|
|
|
|
config,
|
|
|
|
lib,
|
|
|
|
pkgs,
|
|
|
|
...
|
|
|
|
}:
|
|
|
|
let
|
|
|
|
cfg = config.hardware.deviceTree;
|
2020-02-05 15:35:34 +01:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
overlayType = lib.types.submodule {
|
2020-02-05 15:35:34 +01:00
|
|
|
options = {
|
2024-08-27 20:42:52 +02:00
|
|
|
name = lib.mkOption {
|
|
|
|
type = lib.types.str;
|
2020-02-05 15:35:34 +01:00
|
|
|
description = ''
|
|
|
|
Name of this overlay
|
|
|
|
'';
|
|
|
|
};
|
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
filter = lib.mkOption {
|
|
|
|
type = lib.types.nullOr lib.types.str;
|
2022-08-19 21:34:32 +02:00
|
|
|
default = null;
|
|
|
|
example = "*rpi*.dtb";
|
|
|
|
description = ''
|
|
|
|
Only apply to .dtb files matching glob expression.
|
|
|
|
'';
|
|
|
|
};
|
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtsFile = lib.mkOption {
|
|
|
|
type = lib.types.nullOr lib.types.path;
|
2020-02-05 15:35:34 +01:00
|
|
|
description = ''
|
|
|
|
Path to .dts overlay file, overlay is applied to
|
|
|
|
each .dtb file matching "compatible" of the overlay.
|
|
|
|
'';
|
|
|
|
default = null;
|
2024-08-27 20:42:52 +02:00
|
|
|
example = lib.literalExpression "./dts/overlays.dts";
|
2020-02-05 15:35:34 +01:00
|
|
|
};
|
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtsText = lib.mkOption {
|
|
|
|
type = lib.types.nullOr lib.types.str;
|
2020-02-05 15:35:34 +01:00
|
|
|
default = null;
|
|
|
|
description = ''
|
|
|
|
Literal DTS contents, overlay is applied to
|
|
|
|
each .dtb file matching "compatible" of the overlay.
|
|
|
|
'';
|
2021-10-03 18:06:03 +02:00
|
|
|
example = ''
|
2020-02-05 15:35:34 +01:00
|
|
|
/dts-v1/;
|
|
|
|
/plugin/;
|
|
|
|
/ {
|
|
|
|
compatible = "raspberrypi";
|
2022-06-17 21:29:29 -04:00
|
|
|
};
|
|
|
|
&{/soc} {
|
|
|
|
pps {
|
|
|
|
compatible = "pps-gpio";
|
|
|
|
status = "okay";
|
2020-02-05 15:35:34 +01:00
|
|
|
};
|
|
|
|
};
|
|
|
|
'';
|
|
|
|
};
|
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtboFile = lib.mkOption {
|
|
|
|
type = lib.types.nullOr lib.types.path;
|
2020-02-05 15:35:34 +01:00
|
|
|
default = null;
|
|
|
|
description = ''
|
|
|
|
Path to .dtbo compiled overlay file.
|
|
|
|
'';
|
|
|
|
};
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
2023-03-05 22:08:45 +01:00
|
|
|
filterDTBs =
|
|
|
|
src:
|
|
|
|
if cfg.filter == null then
|
2023-09-24 11:58:13 -07:00
|
|
|
src
|
2020-02-05 15:35:34 +01:00
|
|
|
else
|
|
|
|
pkgs.runCommand "dtbs-filtered" { } ''
|
|
|
|
mkdir -p $out
|
2023-09-24 11:58:13 -07:00
|
|
|
cd ${src}
|
2020-02-05 15:35:34 +01:00
|
|
|
find . -type f -name '${cfg.filter}' -print0 \
|
|
|
|
| xargs -0 cp -v --no-preserve=mode --target-directory $out --parents
|
|
|
|
'';
|
|
|
|
|
2023-09-24 11:58:13 -07:00
|
|
|
filteredDTBs = filterDTBs cfg.dtbSource;
|
2020-02-05 15:35:34 +01:00
|
|
|
|
|
|
|
# Fill in `dtboFile` for each overlay if not set already.
|
|
|
|
# Existence of one of these is guarded by assertion below
|
2024-08-27 20:42:52 +02:00
|
|
|
withDTBOs =
|
|
|
|
xs:
|
|
|
|
lib.flip map xs (
|
|
|
|
o:
|
|
|
|
o
|
|
|
|
// {
|
|
|
|
dtboFile =
|
2023-09-24 11:58:13 -07:00
|
|
|
let
|
2024-08-27 20:42:52 +02:00
|
|
|
includePaths = [
|
|
|
|
"${lib.getDev cfg.kernelPackage}/lib/modules/${cfg.kernelPackage.modDirVersion}/source/scripts/dtc/include-prefixes"
|
|
|
|
] ++ cfg.dtboBuildExtraIncludePaths;
|
2023-09-24 11:58:13 -07:00
|
|
|
extraPreprocessorFlags = cfg.dtboBuildExtraPreprocessorFlags;
|
|
|
|
in
|
2023-03-05 22:08:45 +01:00
|
|
|
if o.dtboFile == null then
|
2023-09-24 11:58:13 -07:00
|
|
|
let
|
|
|
|
dtsFile = if o.dtsFile == null then (pkgs.writeText "dts" o.dtsText) else o.dtsFile;
|
|
|
|
in
|
|
|
|
pkgs.deviceTree.compileDTS {
|
|
|
|
name = "${o.name}-dtbo";
|
|
|
|
inherit includePaths extraPreprocessorFlags dtsFile;
|
2025-04-01 20:10:43 +02:00
|
|
|
}
|
|
|
|
else
|
2020-02-05 15:35:34 +01:00
|
|
|
o.dtboFile;
|
2023-09-24 11:58:13 -07:00
|
|
|
}
|
2020-02-05 15:35:34 +01:00
|
|
|
);
|
|
|
|
|
|
|
|
in
|
|
|
|
{
|
|
|
|
imports = [
|
2024-08-27 20:42:52 +02:00
|
|
|
(lib.mkRemovedOptionModule [
|
|
|
|
"hardware"
|
|
|
|
"deviceTree"
|
|
|
|
"base"
|
|
|
|
] "Use hardware.deviceTree.kernelPackage instead")
|
2020-02-05 15:35:34 +01:00
|
|
|
];
|
|
|
|
|
2019-04-24 18:24:16 +01:00
|
|
|
options = {
|
|
|
|
hardware.deviceTree = {
|
2024-08-27 20:42:52 +02:00
|
|
|
enable = lib.mkOption {
|
2021-01-22 20:33:55 -05:00
|
|
|
default = pkgs.stdenv.hostPlatform.linux-kernel.DTB or false;
|
2024-08-27 20:42:52 +02:00
|
|
|
type = lib.types.bool;
|
2019-04-24 18:24:16 +01:00
|
|
|
description = ''
|
|
|
|
Build device tree files. These are used to describe the
|
|
|
|
non-discoverable hardware of a system.
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
kernelPackage = lib.mkOption {
|
2020-02-05 15:35:34 +01:00
|
|
|
default = config.boot.kernelPackages.kernel;
|
2024-08-27 20:42:52 +02:00
|
|
|
defaultText = lib.literalExpression "config.boot.kernelPackages.kernel";
|
|
|
|
example = lib.literalExpression "pkgs.linux_latest";
|
|
|
|
type = lib.types.path;
|
2019-04-24 18:24:16 +01:00
|
|
|
description = ''
|
2023-09-24 11:58:13 -07:00
|
|
|
Kernel package where device tree include directory is from. Also used as default source of dtb package to apply overlays to
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtboBuildExtraPreprocessorFlags = lib.mkOption {
|
2023-09-24 11:58:13 -07:00
|
|
|
default = [ ];
|
2024-08-27 20:42:52 +02:00
|
|
|
example = lib.literalExpression "[ \"-DMY_DTB_DEFINE\" ]";
|
|
|
|
type = lib.types.listOf lib.types.str;
|
2023-09-24 11:58:13 -07:00
|
|
|
description = ''
|
|
|
|
Additional flags to pass to the preprocessor during dtbo compilations
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtboBuildExtraIncludePaths = lib.mkOption {
|
2023-09-24 11:58:13 -07:00
|
|
|
default = [ ];
|
2024-08-27 20:42:52 +02:00
|
|
|
example = lib.literalExpression ''
|
2023-09-24 11:58:13 -07:00
|
|
|
[
|
|
|
|
./my_custom_include_dir_1
|
|
|
|
./custom_include_dir_2
|
|
|
|
]
|
|
|
|
'';
|
2024-08-27 20:42:52 +02:00
|
|
|
type = lib.types.listOf lib.types.path;
|
2023-09-24 11:58:13 -07:00
|
|
|
description = ''
|
|
|
|
Additional include paths that will be passed to the preprocessor when creating the final .dts to compile into .dtbo
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
dtbSource = lib.mkOption {
|
2023-09-24 11:58:13 -07:00
|
|
|
default = "${cfg.kernelPackage}/dtbs";
|
2024-08-27 20:42:52 +02:00
|
|
|
defaultText = lib.literalExpression "\${cfg.kernelPackage}/dtbs";
|
|
|
|
type = lib.types.path;
|
2023-09-24 11:58:13 -07:00
|
|
|
description = ''
|
|
|
|
Path to dtb directory that overlays and other processing will be applied to. Uses
|
2019-04-24 18:24:16 +01:00
|
|
|
device trees bundled with the Linux kernel by default.
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
name = lib.mkOption {
|
2020-06-21 10:33:09 +02:00
|
|
|
default = null;
|
|
|
|
example = "some-dtb.dtb";
|
2024-08-27 20:42:52 +02:00
|
|
|
type = lib.types.nullOr lib.types.str;
|
2020-06-21 10:33:09 +02:00
|
|
|
description = ''
|
|
|
|
The name of an explicit dtb to be loaded, relative to the dtb base.
|
|
|
|
Useful in extlinux scenarios if the bootloader doesn't pick the
|
|
|
|
right .dtb file from FDTDIR.
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
filter = lib.mkOption {
|
|
|
|
type = lib.types.nullOr lib.types.str;
|
2020-02-05 15:35:34 +01:00
|
|
|
default = null;
|
|
|
|
example = "*rpi*.dtb";
|
|
|
|
description = ''
|
|
|
|
Only include .dtb files matching glob expression.
|
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
overlays = lib.mkOption {
|
2019-04-24 18:24:16 +01:00
|
|
|
default = [ ];
|
2024-08-27 20:42:52 +02:00
|
|
|
example = lib.literalExpression ''
|
2020-02-05 15:35:34 +01:00
|
|
|
[
|
|
|
|
{ name = "pps"; dtsFile = ./dts/pps.dts; }
|
|
|
|
{ name = "spi";
|
|
|
|
dtsText = "...";
|
|
|
|
}
|
|
|
|
{ name = "precompiled"; dtboFile = ./dtbos/example.dtbo; }
|
|
|
|
]
|
|
|
|
'';
|
2024-08-27 20:42:52 +02:00
|
|
|
type = lib.types.listOf (
|
|
|
|
lib.types.coercedTo lib.types.path (path: {
|
2020-02-05 15:35:34 +01:00
|
|
|
name = baseNameOf path;
|
2022-08-19 21:34:32 +02:00
|
|
|
filter = null;
|
2020-02-05 15:35:34 +01:00
|
|
|
dtboFile = path;
|
|
|
|
}) overlayType
|
|
|
|
);
|
2019-04-24 18:24:16 +01:00
|
|
|
description = ''
|
2020-02-05 15:35:34 +01:00
|
|
|
List of overlays to apply to base device-tree (.dtb) files.
|
2019-04-24 18:24:16 +01:00
|
|
|
'';
|
|
|
|
};
|
2025-04-01 20:10:43 +02:00
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
package = lib.mkOption {
|
2019-04-24 18:24:16 +01:00
|
|
|
default = null;
|
2024-08-27 20:42:52 +02:00
|
|
|
type = lib.types.nullOr lib.types.path;
|
2019-05-08 23:25:22 +01:00
|
|
|
internal = true;
|
2019-04-24 18:24:16 +01:00
|
|
|
description = ''
|
2020-02-05 15:35:34 +01:00
|
|
|
A path containing the result of applying `overlays` to `kernelPackage`.
|
2025-04-01 20:10:43 +02:00
|
|
|
'';
|
|
|
|
};
|
|
|
|
};
|
2019-04-24 18:24:16 +01:00
|
|
|
};
|
|
|
|
|
2024-08-27 20:42:52 +02:00
|
|
|
config = lib.mkIf (cfg.enable) {
|
2020-02-05 15:35:34 +01:00
|
|
|
|
|
|
|
assertions =
|
|
|
|
let
|
2023-03-05 22:08:45 +01:00
|
|
|
invalidOverlay = o: (o.dtsFile == null) && (o.dtsText == null) && (o.dtboFile == null);
|
2020-02-05 15:35:34 +01:00
|
|
|
in
|
|
|
|
lib.singleton {
|
|
|
|
assertion = lib.all (o: !invalidOverlay o) cfg.overlays;
|
|
|
|
message = ''
|
|
|
|
deviceTree overlay needs one of dtsFile, dtsText or dtboFile set.
|
|
|
|
Offending overlay(s):
|
|
|
|
${toString (map (o: o.name) (builtins.filter invalidOverlay cfg.overlays))}
|
|
|
|
'';
|
|
|
|
};
|
|
|
|
|
2019-04-24 18:24:16 +01:00
|
|
|
hardware.deviceTree.package =
|
|
|
|
if (cfg.overlays != [ ]) then
|
2022-08-19 19:57:13 +03:00
|
|
|
pkgs.deviceTree.applyOverlays filteredDTBs (withDTBOs cfg.overlays)
|
|
|
|
else
|
|
|
|
filteredDTBs;
|
2019-04-24 18:24:16 +01:00
|
|
|
};
|
|
|
|
}
|