Add initial support for building with extensions

This commit is contained in:
2026-05-19 00:26:53 +09:00
parent 72b6cf722a
commit 9cd0e995bd
8 changed files with 281 additions and 29 deletions
+4 -2
View File
@@ -11,8 +11,10 @@
zlib,
icu,
features,
featureFlags,
extensions ? [ ],
extraLibraries ? [ ],
features ? { },
featureFlags ? [ ],
enableInteractive ? false,
...
+87
View File
@@ -0,0 +1,87 @@
{
lib,
extensions,
nameSuffix,
version,
stdenv,
writeText,
...
}:
assert lib.assertMsg (extensions != [ ]) "This derivation should not be evaluated if there are no extensions to build.";
# TODO: assert no colliding init/shutdown symbols across extensions.
let
initSymbols = builtins.catAttrs "init" extensions;
shutdownSymbols = builtins.catAttrs "shutdown" extensions;
coreInitHeaders = writeText "sqlite-core-init.h" ''
int core_init(const char *dummy);
void core_shutdown(void);
${lib.concatMapStringsSep "\n" (sym: "int ${sym}(const char *dummy);") initSymbols}
${lib.concatMapStringsSep "\n" (sym: "void ${sym}(void);") shutdownSymbols}
'';
coreInitImpl = writeText "sqlite-core-init.c" ''
#include "${coreInitHeaders}"
int core_init(const char *dummy) {
int err = 0;
${lib.concatMapStringsSep "\n" (sym: "err += ${sym}(dummy);") initSymbols}
return err;
}
void core_shutdown(void) {
${lib.concatMapStringsSep "\n" (sym: "${sym}();") shutdownSymbols}
}
'';
in stdenv.mkDerivation (finalAttrs: {
pname = "sqlite-core-init${nameSuffix}";
version = version;
src = null;
dontUnpack = true;
buildPhase = ''
runHook preBuild
"$CC" -c '${coreInitImpl}' -o sqlite-core-init.o
runHook postBuild
'';
installPhase = ''
runHook preInstall
install -Dm644 '${coreInitHeaders}' "$out/include/sqlite-core-init.h"
mkdir -p "$out/lib"
"$AR" rcs "$out/lib/libsqlite-core-init.a" sqlite-core-init.o
runHook postInstall
'';
# TODO: Add a checkphase that runs nm on the provided extensions to ensure the expected symbols are present.
# Also verify that the `sqlite_api` symbol is not present, and give a nice warning about using -DSQLITE_CORE
# if it is.
passthru = {
extraLDFLAGS = [
"-L${finalAttrs.finalPackage}/lib"
"-lsqlite-core-init"
] ++ lib.concatMap (ext: [
"-L${lib.dirOf ext.library}"
"-l${lib.removeSuffix ".so" (lib.removeSuffix ".a" (lib.removePrefix "lib" (lib.baseNameOf ext.library)))}"
]) extensions;
extraMakeFlags = let
opts = [
"-DSQLITE_EXTRA_INIT=core_init"
"-DSQLITE_EXTRA_SHUTDOWN=core_shutdown"
"-DSQLITE_CUSTOM_INCLUDE=${placeholder "out"}/include/sqlite-core-init.h"
];
in map (opt: "OPTIONS+=${lib.escapeShellArg opt}") opts;
};
})
+42 -9
View File
@@ -25,12 +25,21 @@
features ? { },
# Custom SQLite extensions and their entrypoints.
# extensions ? [ ],
#
# extensions :: [{ library :: str, init :: str, shutdown :: nullOr str }]
extensions ? [ ],
# Additional libraries to link against, useful when the extensions
# use external libraries.
# extraLibraries ? [ ],
}: let
extraLibraries ? [ ],
}:
assert lib.assertMsg (extensions == [ ] -> extraLibraries == [ ]) "If no extensions are specified, extraLibraries must be empty.";
# TODO: fix compiling with extensions with amalgamation turned off
assert lib.assertMsg (extensions != [ ] -> amalgamate) "Building with extensions without amalgamation is not currently supported.";
let
config = (lib.evalModules {
modules = [
./build-config.nix
@@ -53,32 +62,56 @@
(lib.concatStringsSep "-")
(x: if x == "" then "" else "-${x}")
];
coreInitExt = if extensions == [ ]
then null
else pkgs.callPackage ./core-init-ext.nix ({
inherit version src;
inherit extensions;
inherit extraLibraries;
nameSuffix = suffix;
} // config);
in {
inherit config;
inherit suffix;
_config = config;
_suffix = suffix;
_coreInitExt = coreInitExt;
sqlite = pkgs.callPackage ./sqlite.nix ({
inherit (pkgs.sqlite) version src;
inherit version src;
inherit amalgamate;
inherit features;
inherit extensions;
inherit extraLibraries;
inherit coreInitExt;
nameSuffix = suffix;
static = false;
} // config);
sqlite-static = pkgs.callPackage ./sqlite.nix ({
inherit (pkgs.sqlite) version src;
inherit version src;
inherit amalgamate;
inherit features;
inherit extensions;
inherit extraLibraries;
inherit coreInitExt;
nameSuffix = suffix;
static = true;
} // config);
sqlite-cli = pkgs.callPackage ./sqlite-cli.nix ({
inherit (pkgs.sqlite) version src;
inherit version src;
inherit amalgamate;
inherit features;
inherit extensions;
inherit extraLibraries;
nameSuffix = suffix;
} // config);
} // lib.optionalAttrs amalgamate {
amalgamation = pkgs.callPackage ./amalgamation.nix ({
inherit (pkgs.sqlite) version src;
inherit version src;
inherit features;
inherit extensions;
inherit extraLibraries;
nameSuffix = suffix;
} // config);
}
+8 -6
View File
@@ -11,9 +11,10 @@
zlib,
icu,
amalgamate,
features,
featureFlags,
amalgamate ? true,
coreInitExt ? null,
features ? { },
featureFlags ? [ ],
enableInteractive ? false,
...
@@ -57,8 +58,9 @@ stdenv.mkDerivation (finalAttrs: {
"--with-icu-config=${lib.getExe' icu.dev "icu-config"}"
];
env.NIX_CFLAGS_COMPILE = lib.concatStringsSep " " featureFlags;
env.NIX_CFLAGS_LINK = lib.optionalString features.ENABLE_FTS5 "-lm";
makeTarget = "sqlite3";
makeFlags = (coreInitExt.passthru.makeFlags or [ ]) ++ map (opt: "OPTIONS+=${lib.escapeShellArg opt}") featureFlags;
env.NIX_CFLAGS_LINK = lib.optionalString features.ENABLE_FTS5 "-lm";
env.NIX_LDFLAGS = lib.concatStringsSep " " (coreInitExt.passthru.extraLDFLAGS or [ ]);
})
+9 -6
View File
@@ -13,9 +13,10 @@
zlib,
icu,
amalgamate,
features,
featureFlags,
amalgamate ? true,
coreInitExt ? null,
features ? { },
featureFlags ? [ ],
enableInteractive ? false,
...
@@ -54,13 +55,15 @@ stdenv.mkDerivation (finalAttrs: {
"--${if static then "disable" else "enable"}-shared"
"--${if static then "enable" else "disable"}-static"
"--${if amalgamate then "enable" else "disable"}-amalgamation"
] ++ lib.optional features.ENABLE_ICU [
"--enable-icu-collations"
"--with-icu-config=${lib.getExe' icu.dev "icu-config"}"
];
env.NIX_CFLAGS_COMPILE = lib.concatStringsSep " " featureFlags;
env.NIX_CFLAGS_LINK = lib.optionalString features.ENABLE_FTS5 "-lm";
makeTarget = if static then "lib" else "so";
makeFlags = (coreInitExt.passthru.makeFlags or [ ]) ++ map (opt: "OPTIONS+=${lib.escapeShellArg opt}") featureFlags;
makeTarget = "sqlite3.la";
env.NIX_CFLAGS_LINK = lib.optionalString features.ENABLE_FTS5 "-lm";
env.NIX_LDFLAGS = lib.concatStringsSep " " (coreInitExt.passthru.extraLDFLAGS or [ ]);
})