1 # The base package for automatic multiple-output splitting. Used in stdenv as well.
2 preConfigureHooks
+=(_multioutConfig
)
3 preFixupHooks
+=(_multioutDocs
)
4 preFixupHooks
+=(_multioutDevs
)
5 postFixupHooks
+=(_multioutPropagateDev
)
7 # _assignFirst varName otherVarNames*
9 # Set the value of the variable named $varName to the first of otherVarNames
10 # that refers to a non-empty variable name.
12 # If none of otherVarNames refers to a non-empty variable, the error message is
13 # specific to this function's use case, which is setting up the output variables.
17 local REMOVE
=REMOVE
# slightly hacky - we allow REMOVE (i.e. not a variable name)
20 if [ -n "${!_var-}" ]; then eval "${varName}"="${_var}"; return; fi
23 echo "error: _assignFirst: could not find a non-empty variable whose name to assign to ${varName}."
24 echo " The following variables were all unset or empty:"
26 if [ -z "${out:-}" ]; then
27 echo ' If you do not want an "out" output in your derivation, make sure to define'
28 echo ' the other specific required outputs. This can be achieved by picking one'
29 echo " of the above as an output."
30 echo ' You do not have to remove "out" if you want to have a different default'
31 echo ' output, because the first output is taken as a default.'
37 # Same as _assignFirst, but only if "$1" = ""
39 if [ -z "${!1-}" ]; then
45 # Setup chains of sane default values with easy overridability.
46 # The variables are global to be usable anywhere during the build.
47 # Typical usage in package is defining outputBin = "dev";
49 _overrideFirst outputDev
"dev" "out"
50 _overrideFirst outputBin
"bin" "out"
52 _overrideFirst outputInclude
"$outputDev"
54 # so-libs are often among the main things to keep, and so go to $out
55 _overrideFirst outputLib
"lib" "out"
57 _overrideFirst outputDoc
"doc" "out"
58 _overrideFirst outputDevdoc
"devdoc" REMOVE
# documentation for developers
59 # man and info pages are small and often useful to distribute with binaries
60 _overrideFirst outputMan
"man" "$outputBin"
61 _overrideFirst outputDevman
"devman" "devdoc" "$outputMan"
62 _overrideFirst outputInfo
"info" "$outputBin"
65 # Add standard flags to put files into the desired outputs.
67 if [ "$(getAllOutputNames)" = "out" ] ||
[ -z "${setOutputFlags-1}" ]; then return; fi;
69 # try to detect share/doc/${shareDocName}
70 # Note: sadly, $configureScript detection comes later in configurePhase,
71 # and reordering would cause more trouble than worth.
72 if [ -z "${shareDocName:-}" ]; then
73 local confScript
="${configureScript:-}"
74 if [ -z "$confScript" ] && [ -x .
/configure
]; then
75 confScript
=.
/configure
77 if [ -f "$confScript" ]; then
78 local shareDocName
="$(sed -n "s
/^PACKAGE_TARNAME
='\(.*\)'$
/\
1/p
" < "$confScript")"
80 # PACKAGE_TARNAME sometimes contains garbage.
81 if [ -z "$shareDocName" ] ||
echo "$shareDocName" |
grep -q '[^a-zA-Z0-9_-]'; then
82 shareDocName
="$(echo "$name" | sed 's/-[^a-zA-Z].*//')"
86 prependToVar configureFlags \
87 --bindir="${!outputBin}"/bin
--sbindir="${!outputBin}"/sbin \
88 --includedir="${!outputInclude}"/include
--oldincludedir="${!outputInclude}"/include \
89 --mandir="${!outputMan}"/share
/man
--infodir="${!outputInfo}"/share
/info \
90 --docdir="${!outputDoc}"/share
/doc
/"${shareDocName}" \
91 --libdir="${!outputLib}"/lib
--libexecdir="${!outputLib}"/libexec \
92 --localedir="${!outputLib}"/share
/locale
94 prependToVar installFlags \
95 pkgconfigdir
="${!outputDev}"/lib
/pkgconfig \
96 m4datadir
="${!outputDev}"/share
/aclocal aclocaldir
="${!outputDev}"/share
/aclocal
100 # Add rpath prefixes to library paths, and avoid stdenv doing it for $out.
101 _addRpathPrefix
"${!outputLib}"
105 # Move subpaths that match pattern $1 from under any output/ to the $2 output/
106 # Beware: only globbing patterns are accepted, e.g.: * ? [abc]
107 # A special target "REMOVE" is allowed: moveToOutput foo REMOVE
112 for output
in $
(getAllOutputNames
); do
113 if [ "${!output}" = "$dstOut" ]; then continue; fi
115 for srcPath
in "${!output}"/$patt; do
116 # apply to existing files/dirs, *including* broken symlinks
117 if [ ! -e "$srcPath" ] && [ ! -L "$srcPath" ]; then continue; fi
119 if [ "$dstOut" = REMOVE
]; then
120 echo "Removing $srcPath"
123 local dstPath
="$dstOut${srcPath#${!output}}"
124 echo "Moving $srcPath to $dstPath"
126 if [ -d "$dstPath" ] && [ -d "$srcPath" ]
127 then # attempt directory merge
128 # check the case of trying to move an empty directory
129 rmdir "$srcPath" --ignore-fail-on-non-empty
130 if [ -d "$srcPath" ]; then
131 mv -t "$dstPath" "$srcPath"/*
135 mkdir
-p "$(readlink -m "$dstPath/..
")"
136 mv "$srcPath" "$dstPath"
140 # remove empty directories, printing iff at least one gets removed
141 local srcParent
="$(readlink -m "$srcPath/..
")"
142 if [ -n "$(find "$srcParent" -maxdepth 0 -type d -empty 2>/dev/null)" ]; then
143 echo "Removing empty $srcParent/ and (possibly) its parents"
144 rmdir -p --ignore-fail-on-non-empty "$srcParent" \
145 2> /dev
/null || true
# doesn't ignore failure for some reason
151 # Move documentation to the desired outputs.
153 local REMOVE
=REMOVE
# slightly hacky - we expand ${!outputFoo}
155 moveToOutput
share
/info
"${!outputInfo}"
156 moveToOutput
share
/doc
"${!outputDoc}"
157 moveToOutput
share
/gtk-doc
"${!outputDevdoc}"
158 moveToOutput
share
/devhelp
/books
"${!outputDevdoc}"
160 # the default outputMan is in $bin
161 moveToOutput
share
/man
"${!outputMan}"
162 moveToOutput
share
/man
/man3
"${!outputDevman}"
165 # Move development-only stuff to the desired outputs.
167 if [ "$(getAllOutputNames)" = "out" ] ||
[ -z "${moveToDev-1}" ]; then return; fi;
168 moveToOutput include
"${!outputInclude}"
169 # these files are sometimes provided even without using the corresponding tool
170 moveToOutput lib
/pkgconfig
"${!outputDev}"
171 moveToOutput
share
/pkgconfig
"${!outputDev}"
172 moveToOutput lib
/cmake
"${!outputDev}"
173 moveToOutput
share
/aclocal
"${!outputDev}"
174 # don't move *.la, as libtool needs them in the directory of the library
176 for f
in "${!outputDev}"/{lib
,share
}/pkgconfig
/*.pc
; do
177 echo "Patching '$f' includedir to output ${!outputInclude}"
178 sed -i "/^includedir=/s,=\${prefix},=${!outputInclude}," "$f"
182 # Make the "dev" propagate other outputs needed for development.
183 _multioutPropagateDev
() {
184 if [ "$(getAllOutputNames)" = "out" ]; then return; fi;
187 for outputFirst
in $
(getAllOutputNames
); do
190 local propagaterOutput
="$outputDev"
191 if [ -z "$propagaterOutput" ]; then
192 propagaterOutput
="$outputFirst"
195 # Default value: propagate binaries, includes and libraries
196 if [ -z "${propagatedBuildOutputs+1}" ]; then
197 local po_dirty
="$outputBin $outputInclude $outputLib"
199 propagatedBuildOutputs
=`echo "$po_dirty" \
200 | tr -s ' ' '\n' | grep -v -F "$propagaterOutput" \
201 | sort -u | tr '\n' ' ' `
205 # The variable was explicitly set to empty or we resolved it so
206 if [ -z "$propagatedBuildOutputs" ]; then
210 mkdir
-p "${!propagaterOutput}"/nix-support
211 for output
in $propagatedBuildOutputs; do
212 echo -n " ${!output}" >> "${!propagaterOutput}"/nix-support
/propagated-build-inputs