/[gentoo-x86]/eclass/eutils.eclass
Gentoo

Contents of /eclass/eutils.eclass

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1.364 - (hide annotations) (download)
Wed Sep 21 21:46:49 2011 UTC (2 years, 11 months ago) by mgorny
Branch: MAIN
Changes since 1.363: +18 -1 lines
Introduce in_iuse() for IUSE checks.

Such checks are used at least in autotools-utils & kde* eclasses, and
are done wrong there. Thus, I've created a little reusable snippet
suitable for eutils.

1 vapier 1.356 # Copyright 1999-2011 Gentoo Foundation
2 azarah 1.1 # Distributed under the terms of the GNU General Public License v2
3 mgorny 1.364 # $Header: /var/cvsroot/gentoo-x86/eclass/eutils.eclass,v 1.363 2011/09/12 20:44:01 mgorny Exp $
4 vapier 1.283
5     # @ECLASS: eutils.eclass
6     # @MAINTAINER:
7     # base-system@gentoo.org
8     # @BLURB: many extra (but common) functions that are used in ebuilds
9     # @DESCRIPTION:
10     # The eutils eclass contains a suite of functions that complement
11     # the ones that ebuild.sh already contain. The idea is that the functions
12     # are not required in all ebuilds but enough utilize them to have a common
13     # home rather than having multiple ebuilds implementing the same thing.
14 swegener 1.286 #
15 vapier 1.283 # Due to the nature of this eclass, some functions may have maintainers
16     # different from the overall eclass!
17 azarah 1.1
18 flameeyes 1.197 inherit multilib portability
19 azarah 1.1
20 vapier 1.22 DESCRIPTION="Based on the ${ECLASS} eclass"
21 azarah 1.1
22 betelgeuse 1.329 if has "${EAPI:-0}" 0 1 2; then
23    
24 vapier 1.283 # @FUNCTION: epause
25     # @USAGE: [seconds]
26     # @DESCRIPTION:
27     # Sleep for the specified number of seconds (default of 5 seconds). Useful when
28     # printing a message the user should probably be reading and often used in
29     # conjunction with the ebeep function. If the EPAUSE_IGNORE env var is set,
30 betelgeuse 1.329 # don't wait at all. Defined in EAPIs 0 1 and 2.
31 ciaranm 1.98 epause() {
32 vapier 1.245 [[ -z ${EPAUSE_IGNORE} ]] && sleep ${1:-5}
33 ciaranm 1.98 }
34    
35 vapier 1.283 # @FUNCTION: ebeep
36     # @USAGE: [number of beeps]
37     # @DESCRIPTION:
38     # Issue the specified number of beeps (default of 5 beeps). Useful when
39     # printing a message the user should probably be reading and often used in
40     # conjunction with the epause function. If the EBEEP_IGNORE env var is set,
41 betelgeuse 1.329 # don't beep at all. Defined in EAPIs 0 1 and 2.
42 ciaranm 1.98 ebeep() {
43     local n
44 vapier 1.245 if [[ -z ${EBEEP_IGNORE} ]] ; then
45 ciaranm 1.98 for ((n=1 ; n <= ${1:-5} ; n++)) ; do
46     echo -ne "\a"
47     sleep 0.1 &>/dev/null ; sleep 0,1 &>/dev/null
48     echo -ne "\a"
49     sleep 1
50     done
51     fi
52     }
53    
54 reavertm 1.331 else
55    
56 reavertm 1.332 ebeep() {
57 reavertm 1.337 ewarn "QA Notice: ebeep is not defined in EAPI=${EAPI}, please file a bug at http://bugs.gentoo.org"
58 reavertm 1.332 }
59 reavertm 1.331
60 reavertm 1.332 epause() {
61 reavertm 1.337 ewarn "QA Notice: epause is not defined in EAPI=${EAPI}, please file a bug at http://bugs.gentoo.org"
62 reavertm 1.332 }
63 reavertm 1.331
64 betelgeuse 1.329 fi
65    
66 betelgeuse 1.348 # @FUNCTION: eqawarn
67     # @USAGE: [message]
68     # @DESCRIPTION:
69 mgorny 1.363 # Proxy to ewarn for package managers that don't provide eqawarn and use the PM
70     # implementation if available. Reuses PORTAGE_ELOG_CLASSES as set by the dev
71     # profile.
72 betelgeuse 1.348 if ! declare -F eqawarn >/dev/null ; then
73     eqawarn() {
74 mgorny 1.363 has qa ${PORTAGE_ELOG_CLASSES} && ewarn "$@"
75 betelgeuse 1.348 }
76     fi
77    
78 hollow 1.298 # @FUNCTION: ecvs_clean
79 vapier 1.299 # @USAGE: [list of dirs]
80 hollow 1.298 # @DESCRIPTION:
81 vapier 1.299 # Remove CVS directories recursiveley. Useful when a source tarball contains
82     # internal CVS directories. Defaults to $PWD.
83 hollow 1.298 ecvs_clean() {
84 vapier 1.299 [[ -z $* ]] && set -- .
85 hollow 1.298 find "$@" -type d -name 'CVS' -prune -print0 | xargs -0 rm -rf
86     find "$@" -type f -name '.cvs*' -print0 | xargs -0 rm -rf
87     }
88    
89     # @FUNCTION: esvn_clean
90 vapier 1.299 # @USAGE: [list of dirs]
91 hollow 1.298 # @DESCRIPTION:
92 vapier 1.299 # Remove .svn directories recursiveley. Useful when a source tarball contains
93     # internal Subversion directories. Defaults to $PWD.
94 hollow 1.298 esvn_clean() {
95 vapier 1.299 [[ -z $* ]] && set -- .
96 hollow 1.298 find "$@" -type d -name '.svn' -prune -print0 | xargs -0 rm -rf
97     }
98    
99 vapier 1.322 # @FUNCTION: eshopts_push
100 vapier 1.330 # @USAGE: [options to `set` or `shopt`]
101 vapier 1.322 # @DESCRIPTION:
102     # Often times code will want to enable a shell option to change code behavior.
103     # Since changing shell options can easily break other pieces of code (which
104     # assume the default state), eshopts_push is used to (1) push the current shell
105     # options onto a stack and (2) pass the specified arguments to set.
106     #
107 vapier 1.330 # If the first argument is '-s' or '-u', we assume you want to call `shopt`
108     # rather than `set` as there are some options only available via that.
109     #
110 vapier 1.322 # A common example is to disable shell globbing so that special meaning/care
111     # may be used with variables/arguments to custom functions. That would be:
112     # @CODE
113     # eshopts_push -o noglob
114     # for x in ${foo} ; do
115     # if ...some check... ; then
116     # eshopts_pop
117     # return 0
118     # fi
119     # done
120     # eshopts_pop
121     # @CODE
122     eshopts_push() {
123     # have to assume __ESHOPTS_SAVE__ isn't screwed with
124     # as a `declare -a` here will reset its value
125     local i=${#__ESHOPTS_SAVE__[@]}
126 vapier 1.330 if [[ $1 == -[su] ]] ; then
127     __ESHOPTS_SAVE__[$i]=$(shopt -p)
128     [[ $# -eq 0 ]] && return 0
129     shopt "$@" || die "eshopts_push: bad options to shopt: $*"
130     else
131     __ESHOPTS_SAVE__[$i]=$-
132     [[ $# -eq 0 ]] && return 0
133     set "$@" || die "eshopts_push: bad options to set: $*"
134     fi
135 vapier 1.322 }
136    
137     # @FUNCTION: eshopts_pop
138     # @USAGE:
139     # @DESCRIPTION:
140     # Restore the shell options to the state saved with the corresponding
141     # eshopts_push call. See that function for more details.
142     eshopts_pop() {
143     [[ $# -ne 0 ]] && die "eshopts_pop takes no arguments"
144     local i=$(( ${#__ESHOPTS_SAVE__[@]} - 1 ))
145     [[ ${i} -eq -1 ]] && die "eshopts_{push,pop}: unbalanced pair"
146     local s=${__ESHOPTS_SAVE__[$i]}
147     unset __ESHOPTS_SAVE__[$i]
148 vapier 1.330 if [[ ${s} == "shopt -"* ]] ; then
149     eval "${s}" || die "eshopts_pop: sanity: invalid shopt options: ${s}"
150     else
151     set +$- || die "eshopts_pop: sanity: invalid shell settings: $-"
152     set -${s} || die "eshopts_pop: sanity: unable to restore saved shell settings: ${s}"
153     fi
154 vapier 1.322 }
155    
156 vapier 1.325 # @VARIABLE: EPATCH_SOURCE
157     # @DESCRIPTION:
158     # Default directory to search for patches.
159 azarah 1.2 EPATCH_SOURCE="${WORKDIR}/patch"
160 vapier 1.325 # @VARIABLE: EPATCH_SUFFIX
161     # @DESCRIPTION:
162     # Default extension for patches (do not prefix the period yourself).
163 azarah 1.2 EPATCH_SUFFIX="patch.bz2"
164 vapier 1.325 # @VARIABLE: EPATCH_OPTS
165     # @DESCRIPTION:
166     # Default options for patch:
167     # @CODE
168     # -g0 - keep RCS, ClearCase, Perforce and SCCS happy #24571
169     # --no-backup-if-mismatch - do not leave .orig files behind
170     # -E - automatically remove empty files
171     # @CODE
172 vapier 1.230 EPATCH_OPTS="-g0 -E --no-backup-if-mismatch"
173 vapier 1.325 # @VARIABLE: EPATCH_EXCLUDE
174     # @DESCRIPTION:
175 mr_bones_ 1.308 # List of patches not to apply. Note this is only file names,
176 vapier 1.325 # and not the full path. Globs accepted.
177 azarah 1.6 EPATCH_EXCLUDE=""
178 vapier 1.325 # @VARIABLE: EPATCH_SINGLE_MSG
179     # @DESCRIPTION:
180 azarah 1.9 # Change the printed message for a single patch.
181     EPATCH_SINGLE_MSG=""
182 vapier 1.325 # @VARIABLE: EPATCH_MULTI_MSG
183     # @DESCRIPTION:
184 vapier 1.173 # Change the printed message for multiple patches.
185     EPATCH_MULTI_MSG="Applying various patches (bugfixes/updates) ..."
186 vapier 1.325 # @VARIABLE: EPATCH_FORCE
187     # @DESCRIPTION:
188     # Only require patches to match EPATCH_SUFFIX rather than the extended
189     # arch naming style.
190 azarah 1.29 EPATCH_FORCE="no"
191 azarah 1.2
192 vapier 1.325 # @FUNCTION: epatch
193     # @USAGE: [patches] [dirs of patches]
194     # @DESCRIPTION:
195     # epatch is designed to greatly simplify the application of patches. It can
196     # process patch files directly, or directories of patches. The patches may be
197     # compressed (bzip/gzip/etc...) or plain text. You generally need not specify
198     # the -p option as epatch will automatically attempt -p0 to -p5 until things
199     # apply successfully.
200 azarah 1.2 #
201 vapier 1.325 # If you do not specify any options, then epatch will default to the directory
202     # specified by EPATCH_SOURCE.
203 azarah 1.2 #
204 vapier 1.325 # When processing directories, epatch will apply all patches that match:
205     # @CODE
206 vapier 1.350 # if ${EPATCH_FORCE} != "yes"
207 vapier 1.325 # ??_${ARCH}_foo.${EPATCH_SUFFIX}
208     # else
209     # *.${EPATCH_SUFFIX}
210     # @CODE
211     # The leading ?? are typically numbers used to force consistent patch ordering.
212     # The arch field is used to apply patches only for the host architecture with
213     # the special value of "all" means apply for everyone. Note that using values
214     # other than "all" is highly discouraged -- you should apply patches all the
215     # time and let architecture details be detected at configure/compile time.
216 azarah 1.2 #
217 vapier 1.325 # If EPATCH_SUFFIX is empty, then no period before it is implied when searching
218     # for patches to apply.
219 azarah 1.2 #
220 vapier 1.325 # Refer to the other EPATCH_xxx variables for more customization of behavior.
221 azarah 1.2 epatch() {
222 swegener 1.231 _epatch_draw_line() {
223 vapier 1.325 # create a line of same length as input string
224 agriffis 1.229 [[ -z $1 ]] && set "$(printf "%65s" '')"
225     echo "${1//?/=}"
226 vapier 1.219 }
227 azarah 1.3
228 vapier 1.195 unset P4CONFIG P4PORT P4USER # keep perforce at bay #56402
229    
230 vapier 1.325 # Let the rest of the code process one user arg at a time --
231     # each arg may expand into multiple patches, and each arg may
232     # need to start off with the default global EPATCH_xxx values
233     if [[ $# -gt 1 ]] ; then
234     local m
235 vapier 1.94 for m in "$@" ; do
236     epatch "${m}"
237     done
238     return 0
239 azarah 1.3 fi
240    
241 vapier 1.325 local SINGLE_PATCH="no"
242     # no args means process ${EPATCH_SOURCE}
243     [[ $# -eq 0 ]] && set -- "${EPATCH_SOURCE}"
244    
245     if [[ -f $1 ]] ; then
246 azarah 1.3 SINGLE_PATCH="yes"
247 vapier 1.325 set -- "$1"
248     # Use the suffix from the single patch (localize it); the code
249     # below will find the suffix for us
250     local EPATCH_SUFFIX=$1
251    
252     elif [[ -d $1 ]] ; then
253     # Some people like to make dirs of patches w/out suffixes (vim)
254     set -- "$1"/*${EPATCH_SUFFIX:+."${EPATCH_SUFFIX}"}
255 danarmak 1.32
256 vapier 1.359 elif [[ -f ${EPATCH_SOURCE}/$1 ]] ; then
257     # Re-use EPATCH_SOURCE as a search dir
258     epatch "${EPATCH_SOURCE}/$1"
259     return $?
260    
261 azarah 1.3 else
262 vapier 1.325 # sanity check ... if it isn't a dir or file, wtf man ?
263     [[ $# -ne 0 ]] && EPATCH_SOURCE=$1
264     echo
265     eerror "Cannot find \$EPATCH_SOURCE! Value for \$EPATCH_SOURCE is:"
266     eerror
267     eerror " ${EPATCH_SOURCE}"
268     eerror " ( ${EPATCH_SOURCE##*/} )"
269     echo
270     die "Cannot find \$EPATCH_SOURCE!"
271 azarah 1.3 fi
272 azarah 1.2
273 vapier 1.325 local PIPE_CMD
274 azarah 1.2 case ${EPATCH_SUFFIX##*\.} in
275 vapier 1.325 xz) PIPE_CMD="xz -dc" ;;
276     lzma) PIPE_CMD="lzma -dc" ;;
277     bz2) PIPE_CMD="bzip2 -dc" ;;
278     gz|Z|z) PIPE_CMD="gzip -dc" ;;
279     ZIP|zip) PIPE_CMD="unzip -p" ;;
280     *) ;;
281 azarah 1.2 esac
282    
283 vapier 1.325 [[ ${SINGLE_PATCH} == "no" ]] && einfo "${EPATCH_MULTI_MSG}"
284    
285     local x
286     for x in "$@" ; do
287     # If the patch dir given contains subdirs, or our EPATCH_SUFFIX
288     # didn't match anything, ignore continue on
289     [[ ! -f ${x} ]] && continue
290    
291     local patchname=${x##*/}
292    
293     # Apply single patches, or forced sets of patches, or
294     # patches with ARCH dependant names.
295 flameeyes 1.266 # ???_arch_foo.patch
296 vapier 1.325 # Else, skip this input altogether
297     local a=${patchname#*_} # strip the ???_
298     a=${a%%_*} # strip the _foo.patch
299     if ! [[ ${SINGLE_PATCH} == "yes" || \
300 ulm 1.354 ${EPATCH_FORCE} == "yes" || \
301     ${a} == all || \
302     ${a} == ${ARCH} ]]
303 azarah 1.2 then
304 vapier 1.325 continue
305     fi
306 azarah 1.6
307 vapier 1.325 # Let people filter things dynamically
308     if [[ -n ${EPATCH_EXCLUDE} ]] ; then
309     # let people use globs in the exclude
310     eshopts_push -o noglob
311    
312 scarabeus 1.328 local ex
313 vapier 1.325 for ex in ${EPATCH_EXCLUDE} ; do
314 scarabeus 1.328 if [[ ${patchname} == ${ex} ]] ; then
315     eshopts_pop
316     continue 2
317     fi
318 vapier 1.325 done
319 vapier 1.326
320 vapier 1.325 eshopts_pop
321     fi
322 danarmak 1.32
323 vapier 1.325 if [[ ${SINGLE_PATCH} == "yes" ]] ; then
324     if [[ -n ${EPATCH_SINGLE_MSG} ]] ; then
325     einfo "${EPATCH_SINGLE_MSG}"
326 azarah 1.3 else
327 vapier 1.325 einfo "Applying ${patchname} ..."
328 azarah 1.3 fi
329 vapier 1.325 else
330     einfo " ${patchname} ..."
331     fi
332 azarah 1.2
333 vapier 1.325 # most of the time, there will only be one run per unique name,
334     # but if there are more, make sure we get unique log filenames
335     local STDERR_TARGET="${T}/${patchname}.out"
336     if [[ -e ${STDERR_TARGET} ]] ; then
337     STDERR_TARGET="${T}/${patchname}-$$.out"
338     fi
339 azarah 1.2
340 vapier 1.325 printf "***** %s *****\n\n" "${patchname}" > "${STDERR_TARGET}"
341 vapier 1.304
342 vapier 1.325 # Decompress the patch if need be
343     local count=0
344     local PATCH_TARGET
345     if [[ -n ${PIPE_CMD} ]] ; then
346     PATCH_TARGET="${T}/$$.patch"
347     echo "PIPE_COMMAND: ${PIPE_CMD} ${x} > ${PATCH_TARGET}" >> "${STDERR_TARGET}"
348 vapier 1.304
349 vapier 1.325 if ! (${PIPE_CMD} "${x}" > "${PATCH_TARGET}") >> "${STDERR_TARGET}" 2>&1 ; then
350     echo
351     eerror "Could not extract patch!"
352     #die "Could not extract patch!"
353     count=5
354     break
355 vapier 1.305 fi
356 vapier 1.325 else
357     PATCH_TARGET=${x}
358     fi
359 vapier 1.305
360 vapier 1.325 # Check for absolute paths in patches. If sandbox is disabled,
361     # people could (accidently) patch files in the root filesystem.
362     # Or trigger other unpleasantries #237667. So disallow -p0 on
363     # such patches.
364     local abs_paths=$(egrep -n '^[-+]{3} /' "${PATCH_TARGET}" | awk '$2 != "/dev/null" { print }')
365     if [[ -n ${abs_paths} ]] ; then
366     count=1
367     printf "NOTE: skipping -p0 due to absolute paths in patch:\n%s\n" "${abs_paths}" >> "${STDERR_TARGET}"
368     fi
369 vapier 1.353 # Similar reason, but with relative paths.
370     local rel_paths=$(egrep -n '^[-+]{3} [^ ]*[.][.]/' "${PATCH_TARGET}")
371     if [[ -n ${rel_paths} ]] ; then
372     eqawarn "QA Notice: Your patch uses relative paths '../'."
373     eqawarn " In the future this will cause a failure."
374     eqawarn "${rel_paths}"
375     fi
376 vapier 1.325
377     # Dynamically detect the correct -p# ... i'm lazy, so shoot me :/
378     while [[ ${count} -lt 5 ]] ; do
379     # Generate some useful debug info ...
380     (
381     _epatch_draw_line "***** ${patchname} *****"
382     echo
383     echo "PATCH COMMAND: patch -p${count} ${EPATCH_OPTS} < '${PATCH_TARGET}'"
384     echo
385     _epatch_draw_line "***** ${patchname} *****"
386 vapier 1.360 patch -p${count} ${EPATCH_OPTS} --dry-run -f < "${PATCH_TARGET}" 2>&1
387     ret=$?
388     echo
389     echo "patch program exited with status ${ret}"
390     exit ${ret}
391 vapier 1.325 ) >> "${STDERR_TARGET}"
392 azarah 1.8
393 vapier 1.360 if [ $? -eq 0 ] ; then
394 vapier 1.325 (
395     _epatch_draw_line "***** ${patchname} *****"
396     echo
397     echo "ACTUALLY APPLYING ${patchname} ..."
398     echo
399     _epatch_draw_line "***** ${patchname} *****"
400     patch -p${count} ${EPATCH_OPTS} < "${PATCH_TARGET}" 2>&1
401 vapier 1.360 ret=$?
402     echo
403     echo "patch program exited with status ${ret}"
404     exit ${ret}
405 vapier 1.325 ) >> "${STDERR_TARGET}"
406 danarmak 1.32
407 vapier 1.325 if [ $? -ne 0 ] ; then
408     echo
409     eerror "A dry-run of patch command succeeded, but actually"
410     eerror "applying the patch failed!"
411     #die "Real world sux compared to the dreamworld!"
412     count=5
413 azarah 1.2 fi
414 vapier 1.325 break
415 azarah 1.8 fi
416    
417 vapier 1.325 : $(( count++ ))
418     done
419 azarah 1.8
420 vapier 1.325 # if we had to decompress the patch, delete the temp one
421     if [[ -n ${PIPE_CMD} ]] ; then
422     rm -f "${PATCH_TARGET}"
423     fi
424 azarah 1.3
425 vapier 1.325 if [[ ${count} -ge 5 ]] ; then
426     echo
427     eerror "Failed Patch: ${patchname} !"
428     eerror " ( ${PATCH_TARGET} )"
429     eerror
430     eerror "Include in your bugreport the contents of:"
431     eerror
432     eerror " ${STDERR_TARGET}"
433     echo
434     die "Failed Patch: ${patchname}!"
435 azarah 1.2 fi
436 vapier 1.325
437     # if everything worked, delete the patch log
438     rm -f "${STDERR_TARGET}"
439     eend 0
440 azarah 1.2 done
441 vapier 1.325
442     [[ ${SINGLE_PATCH} == "no" ]] && einfo "Done with patching"
443     : # everything worked
444 azarah 1.26 }
445 vapier 1.361
446     # @FUNCTION: epatch_user
447     # @USAGE:
448     # @DESCRIPTION:
449     # Applies user-provided patches to the source tree. The patches are
450     # taken from /etc/portage/patches/<CATEGORY>/<PF|P|PN>/, where the first
451     # of these three directories to exist will be the one to use, ignoring
452     # any more general directories which might exist as well.
453     #
454     # User patches are intended for quick testing of patches without ebuild
455     # modifications, as well as for permanent customizations a user might
456     # desire. Obviously, there can be no official support for arbitrarily
457     # patched ebuilds. So whenever a build log in a bug report mentions that
458     # user patches were applied, the user should be asked to reproduce the
459     # problem without these.
460     #
461     # Not all ebuilds do call this function, so placing patches in the
462     # stated directory might or might not work, depending on the package and
463     # the eclasses it inherits and uses. It is safe to call the function
464     # repeatedly, so it is always possible to add a call at the ebuild
465     # level. The first call is the time when the patches will be
466     # applied.
467     #
468     # Ideally, this function should be called after gentoo-specific patches
469     # have been applied, so that their code can be modified as well, but
470     # before calls to e.g. eautoreconf, as the user patches might affect
471     # autotool input files as well.
472 vapier 1.318 epatch_user() {
473     [[ $# -ne 0 ]] && die "epatch_user takes no options"
474    
475 vapier 1.361 # Allow multiple calls to this function; ignore all but the first
476 vapier 1.362 local applied="${T}/epatch_user.applied"
477 vapier 1.361 [[ -e ${applied} ]] && return 2
478    
479 vapier 1.318 # don't clobber any EPATCH vars that the parent might want
480 zmedico 1.323 local EPATCH_SOURCE check base=${PORTAGE_CONFIGROOT%/}/etc/portage/patches
481 vapier 1.318 for check in {${CATEGORY}/${PF},${CATEGORY}/${P},${CATEGORY}/${PN}}; do
482     EPATCH_SOURCE=${base}/${CTARGET}/${check}
483     [[ -r ${EPATCH_SOURCE} ]] || EPATCH_SOURCE=${base}/${CHOST}/${check}
484     [[ -r ${EPATCH_SOURCE} ]] || EPATCH_SOURCE=${base}/${check}
485     if [[ -d ${EPATCH_SOURCE} ]] ; then
486     EPATCH_SOURCE=${EPATCH_SOURCE} \
487     EPATCH_SUFFIX="patch" \
488     EPATCH_FORCE="yes" \
489     EPATCH_MULTI_MSG="Applying user patches from ${EPATCH_SOURCE} ..." \
490     epatch
491 vapier 1.361 echo "${EPATCH_SOURCE}" > "${applied}"
492 vapier 1.349 return 0
493 vapier 1.318 fi
494     done
495 vapier 1.361 echo "none" > "${applied}"
496 vapier 1.349 return 1
497 vapier 1.318 }
498 azarah 1.26
499 vapier 1.283 # @FUNCTION: emktemp
500     # @USAGE: [temp dir]
501     # @DESCRIPTION:
502 vapier 1.52 # Cheap replacement for when debianutils (and thus mktemp)
503 vapier 1.283 # does not exist on the users system.
504 vapier 1.117 emktemp() {
505 vapier 1.119 local exe="touch"
506 vapier 1.194 [[ $1 == -d ]] && exe="mkdir" && shift
507     local topdir=$1
508 mr_bones_ 1.100
509 vapier 1.194 if [[ -z ${topdir} ]] ; then
510     [[ -z ${T} ]] \
511 vapier 1.117 && topdir="/tmp" \
512 vapier 1.194 || topdir=${T}
513 vapier 1.117 fi
514    
515 vapier 1.280 if ! type -P mktemp > /dev/null ; then
516     # system lacks `mktemp` so we have to fake it
517 vapier 1.117 local tmp=/
518 vapier 1.194 while [[ -e ${tmp} ]] ; do
519     tmp=${topdir}/tmp.${RANDOM}.${RANDOM}.${RANDOM}
520 vapier 1.117 done
521 vapier 1.194 ${exe} "${tmp}" || ${exe} -p "${tmp}"
522 vapier 1.117 echo "${tmp}"
523 vapier 1.52 else
524 vapier 1.280 # the args here will give slightly wierd names on BSD,
525     # but should produce a usable file on all userlands
526 flameeyes 1.223 if [[ ${exe} == "touch" ]] ; then
527 vapier 1.280 TMPDIR="${topdir}" mktemp -t tmp.XXXXXXXXXX
528 flameeyes 1.223 else
529 vapier 1.280 TMPDIR="${topdir}" mktemp -dt tmp.XXXXXXXXXX
530 flameeyes 1.223 fi
531 vapier 1.52 fi
532     }
533    
534 vapier 1.283 # @FUNCTION: egetent
535     # @USAGE: <database> <key>
536     # @MAINTAINER:
537     # base-system@gentoo.org (Linux)
538     # Joe Jezak <josejx@gmail.com> (OS X)
539     # usata@gentoo.org (OS X)
540     # Aaron Walker <ka0ttic@gentoo.org> (FreeBSD)
541     # @DESCRIPTION:
542 grobian 1.310 # Small wrapper for getent (Linux),
543     # nidump (< Mac OS X 10.5), dscl (Mac OS X 10.5),
544 ka0ttic 1.108 # and pw (FreeBSD) used in enewuser()/enewgroup()
545 usata 1.91 egetent() {
546 flameeyes 1.205 case ${CHOST} in
547 grobian 1.319 *-darwin[678])
548 grobian 1.310 case "$2" in
549     *[!0-9]*) # Non numeric
550 betelgeuse 1.357 nidump $1 . | awk -F":" "{ if (\$1 ~ /^$2\$/) {print \$0;exit;} }"
551 grobian 1.310 ;;
552     *) # Numeric
553 grobian 1.319 nidump $1 . | awk -F":" "{ if (\$3 == $2) {print \$0;exit;} }"
554 grobian 1.310 ;;
555     esac
556     ;;
557 flameeyes 1.205 *-darwin*)
558 grobian 1.319 local mytype=$1
559     [[ "passwd" == $mytype ]] && mytype="Users"
560     [[ "group" == $mytype ]] && mytype="Groups"
561 usata 1.91 case "$2" in
562 flameeyes 1.205 *[!0-9]*) # Non numeric
563 grobian 1.319 dscl . -read /$mytype/$2 2>/dev/null |grep RecordName
564 usata 1.91 ;;
565 flameeyes 1.205 *) # Numeric
566 grobian 1.319 local mykey="UniqueID"
567     [[ $mytype == "Groups" ]] && mykey="PrimaryGroupID"
568     dscl . -search /$mytype $mykey $2 2>/dev/null
569 usata 1.91 ;;
570     esac
571 flameeyes 1.205 ;;
572 flameeyes 1.220 *-freebsd*|*-dragonfly*)
573 ka0ttic 1.203 local opts action="user"
574     [[ $1 == "passwd" ]] || action="group"
575    
576     # lookup by uid/gid
577     if [[ $2 == [[:digit:]]* ]] ; then
578     [[ ${action} == "user" ]] && opts="-u" || opts="-g"
579 ka0ttic 1.108 fi
580 ka0ttic 1.203
581     pw show ${action} ${opts} "$2" -q
582 flameeyes 1.205 ;;
583 flameeyes 1.218 *-netbsd*|*-openbsd*)
584 flameeyes 1.206 grep "$2:\*:" /etc/$1
585     ;;
586 flameeyes 1.205 *)
587     type -p nscd >& /dev/null && nscd -i "$1"
588 vapier 1.107 getent "$1" "$2"
589 flameeyes 1.205 ;;
590     esac
591 usata 1.91 }
592    
593 vapier 1.283 # @FUNCTION: enewuser
594     # @USAGE: <user> [uid] [shell] [homedir] [groups] [params]
595     # @DESCRIPTION:
596     # Same as enewgroup, you are not required to understand how to properly add
597     # a user to the system. The only required parameter is the username.
598     # Default uid is (pass -1 for this) next available, default shell is
599     # /bin/false, default homedir is /dev/null, there are no default groups,
600     # and default params sets the comment as 'added by portage for ${PN}'.
601 vapier 1.23 enewuser() {
602 vapier 1.233 case ${EBUILD_PHASE} in
603     unpack|compile|test|install)
604     eerror "'enewuser()' called from '${EBUILD_PHASE}()' which is not a pkg_* function."
605     eerror "Package fails at QA and at life. Please file a bug."
606     die "Bad package! enewuser is only for use in pkg_* functions!"
607     esac
608    
609 vapier 1.23 # get the username
610 vapier 1.182 local euser=$1; shift
611     if [[ -z ${euser} ]] ; then
612 vapier 1.23 eerror "No username specified !"
613     die "Cannot call enewuser without a username"
614     fi
615    
616 vapier 1.84 # lets see if the username already exists
617 agriffis 1.256 if [[ -n $(egetent passwd "${euser}") ]] ; then
618 vapier 1.23 return 0
619     fi
620 wolf31o2 1.44 einfo "Adding user '${euser}' to your system ..."
621 vapier 1.23
622     # options to pass to useradd
623 azarah 1.59 local opts=
624 vapier 1.23
625     # handle uid
626 vapier 1.182 local euid=$1; shift
627 agriffis 1.256 if [[ -n ${euid} && ${euid} != -1 ]] ; then
628 vapier 1.182 if [[ ${euid} -gt 0 ]] ; then
629 agriffis 1.256 if [[ -n $(egetent passwd ${euid}) ]] ; then
630 vapier 1.84 euid="next"
631 vapier 1.82 fi
632 vapier 1.23 else
633     eerror "Userid given but is not greater than 0 !"
634     die "${euid} is not a valid UID"
635     fi
636     else
637 vapier 1.84 euid="next"
638     fi
639 vapier 1.182 if [[ ${euid} == "next" ]] ; then
640 agriffis 1.256 for ((euid = 101; euid <= 999; euid++)); do
641 vapier 1.182 [[ -z $(egetent passwd ${euid}) ]] && break
642 vapier 1.84 done
643 vapier 1.23 fi
644 vapier 1.84 opts="${opts} -u ${euid}"
645 vapier 1.23 einfo " - Userid: ${euid}"
646    
647     # handle shell
648 vapier 1.182 local eshell=$1; shift
649     if [[ ! -z ${eshell} ]] && [[ ${eshell} != "-1" ]] ; then
650 vapier 1.221 if [[ ! -e ${ROOT}${eshell} ]] ; then
651 vapier 1.23 eerror "A shell was specified but it does not exist !"
652 vapier 1.221 die "${eshell} does not exist in ${ROOT}"
653     fi
654     if [[ ${eshell} == */false || ${eshell} == */nologin ]] ; then
655     eerror "Do not specify ${eshell} yourself, use -1"
656     die "Pass '-1' as the shell parameter"
657 vapier 1.23 fi
658     else
659 vapier 1.204 for shell in /sbin/nologin /usr/sbin/nologin /bin/false /usr/bin/false /dev/null ; do
660     [[ -x ${ROOT}${shell} ]] && break
661 flameeyes 1.198 done
662    
663 vapier 1.204 if [[ ${shell} == "/dev/null" ]] ; then
664 flameeyes 1.253 eerror "Unable to identify the shell to use, proceeding with userland default."
665     case ${USERLAND} in
666     GNU) shell="/bin/false" ;;
667     BSD) shell="/sbin/nologin" ;;
668     Darwin) shell="/usr/sbin/nologin" ;;
669     *) die "Unable to identify the default shell for userland ${USERLAND}"
670     esac
671 flameeyes 1.198 fi
672    
673     eshell=${shell}
674 vapier 1.23 fi
675     einfo " - Shell: ${eshell}"
676     opts="${opts} -s ${eshell}"
677    
678     # handle homedir
679 vapier 1.182 local ehome=$1; shift
680     if [[ -z ${ehome} ]] || [[ ${ehome} == "-1" ]] ; then
681 azarah 1.59 ehome="/dev/null"
682 vapier 1.23 fi
683     einfo " - Home: ${ehome}"
684     opts="${opts} -d ${ehome}"
685    
686     # handle groups
687 vapier 1.182 local egroups=$1; shift
688     if [[ ! -z ${egroups} ]] ; then
689     local oldifs=${IFS}
690 vapier 1.107 local defgroup="" exgroups=""
691    
692 vapier 1.23 export IFS=","
693 vapier 1.182 for g in ${egroups} ; do
694     export IFS=${oldifs}
695     if [[ -z $(egetent group "${g}") ]] ; then
696 vapier 1.85 eerror "You must add group ${g} to the system first"
697 vapier 1.23 die "${g} is not a valid GID"
698     fi
699 vapier 1.182 if [[ -z ${defgroup} ]] ; then
700     defgroup=${g}
701 vapier 1.107 else
702     exgroups="${exgroups},${g}"
703     fi
704 usata 1.115 export IFS=","
705 vapier 1.23 done
706 vapier 1.182 export IFS=${oldifs}
707 vapier 1.107
708     opts="${opts} -g ${defgroup}"
709 vapier 1.182 if [[ ! -z ${exgroups} ]] ; then
710 vapier 1.107 opts="${opts} -G ${exgroups:1}"
711     fi
712 vapier 1.23 else
713     egroups="(none)"
714     fi
715     einfo " - Groups: ${egroups}"
716    
717     # handle extra and add the user
718 vapier 1.182 local oldsandbox=${SANDBOX_ON}
719 vapier 1.23 export SANDBOX_ON="0"
720 flameeyes 1.205 case ${CHOST} in
721     *-darwin*)
722 usata 1.91 ### Make the user
723 vapier 1.182 if [[ -z $@ ]] ; then
724 usata 1.91 dscl . create /users/${euser} uid ${euid}
725     dscl . create /users/${euser} shell ${eshell}
726     dscl . create /users/${euser} home ${ehome}
727     dscl . create /users/${euser} realname "added by portage for ${PN}"
728     ### Add the user to the groups specified
729 vapier 1.182 local oldifs=${IFS}
730 usata 1.115 export IFS=","
731 vapier 1.182 for g in ${egroups} ; do
732 usata 1.91 dscl . merge /groups/${g} users ${euser}
733     done
734 vapier 1.182 export IFS=${oldifs}
735 usata 1.91 else
736 vapier 1.182 einfo "Extra options are not supported on Darwin yet"
737 usata 1.91 einfo "Please report the ebuild along with the info below"
738 vapier 1.182 einfo "eextra: $@"
739 usata 1.91 die "Required function missing"
740     fi
741 vapier 1.182 ;;
742 flameeyes 1.220 *-freebsd*|*-dragonfly*)
743 vapier 1.182 if [[ -z $@ ]] ; then
744 ka0ttic 1.108 pw useradd ${euser} ${opts} \
745     -c "added by portage for ${PN}" \
746     die "enewuser failed"
747     else
748 vapier 1.182 einfo " - Extra: $@"
749 ka0ttic 1.108 pw useradd ${euser} ${opts} \
750 vapier 1.182 "$@" || die "enewuser failed"
751 ka0ttic 1.108 fi
752 vapier 1.182 ;;
753 flameeyes 1.207
754     *-netbsd*)
755     if [[ -z $@ ]] ; then
756     useradd ${opts} ${euser} || die "enewuser failed"
757     else
758     einfo " - Extra: $@"
759     useradd ${opts} ${euser} "$@" || die "enewuser failed"
760     fi
761     ;;
762 flameeyes 1.218
763     *-openbsd*)
764     if [[ -z $@ ]] ; then
765     useradd -u ${euid} -s ${eshell} \
766     -d ${ehome} -c "Added by portage for ${PN}" \
767     -g ${egroups} ${euser} || die "enewuser failed"
768     else
769     einfo " - Extra: $@"
770     useradd -u ${euid} -s ${eshell} \
771     -d ${ehome} -c "Added by portage for ${PN}" \
772     -g ${egroups} ${euser} "$@" || die "enewuser failed"
773     fi
774     ;;
775    
776 vapier 1.182 *)
777     if [[ -z $@ ]] ; then
778 cardoe 1.345 useradd -r ${opts} \
779 usata 1.91 -c "added by portage for ${PN}" \
780 grobian 1.321 ${euser} \
781 usata 1.91 || die "enewuser failed"
782     else
783 vapier 1.182 einfo " - Extra: $@"
784 cardoe 1.345 useradd -r ${opts} "$@" \
785 grobian 1.321 ${euser} \
786 usata 1.91 || die "enewuser failed"
787     fi
788 vapier 1.182 ;;
789     esac
790 vapier 1.23
791 vapier 1.193 if [[ ! -e ${ROOT}/${ehome} ]] ; then
792     einfo " - Creating ${ehome} in ${ROOT}"
793     mkdir -p "${ROOT}/${ehome}"
794     chown ${euser} "${ROOT}/${ehome}"
795     chmod 755 "${ROOT}/${ehome}"
796 vapier 1.23 fi
797 vapier 1.193
798     export SANDBOX_ON=${oldsandbox}
799 vapier 1.23 }
800    
801 vapier 1.283 # @FUNCTION: enewgroup
802     # @USAGE: <group> [gid]
803     # @DESCRIPTION:
804     # This function does not require you to understand how to properly add a
805     # group to the system. Just give it a group name to add and enewgroup will
806     # do the rest. You may specify the gid for the group or allow the group to
807     # allocate the next available one.
808 vapier 1.23 enewgroup() {
809 vapier 1.233 case ${EBUILD_PHASE} in
810     unpack|compile|test|install)
811     eerror "'enewgroup()' called from '${EBUILD_PHASE}()' which is not a pkg_* function."
812     eerror "Package fails at QA and at life. Please file a bug."
813     die "Bad package! enewgroup is only for use in pkg_* functions!"
814     esac
815    
816 vapier 1.23 # get the group
817     local egroup="$1"; shift
818 azarah 1.59 if [ -z "${egroup}" ]
819     then
820 vapier 1.23 eerror "No group specified !"
821     die "Cannot call enewgroup without a group"
822     fi
823    
824     # see if group already exists
825 agriffis 1.256 if [[ -n $(egetent group "${egroup}") ]]; then
826 vapier 1.23 return 0
827     fi
828 wolf31o2 1.44 einfo "Adding group '${egroup}' to your system ..."
829 vapier 1.23
830     # options to pass to useradd
831 azarah 1.59 local opts=
832 vapier 1.23
833     # handle gid
834     local egid="$1"; shift
835 azarah 1.59 if [ ! -z "${egid}" ]
836     then
837     if [ "${egid}" -gt 0 ]
838     then
839 usata 1.91 if [ -z "`egetent group ${egid}`" ]
840 vapier 1.83 then
841 flameeyes 1.205 if [[ "${CHOST}" == *-darwin* ]]; then
842 usata 1.91 opts="${opts} ${egid}"
843     else
844     opts="${opts} -g ${egid}"
845     fi
846 vapier 1.83 else
847 vapier 1.84 egid="next available; requested gid taken"
848 vapier 1.83 fi
849 vapier 1.23 else
850     eerror "Groupid given but is not greater than 0 !"
851     die "${egid} is not a valid GID"
852     fi
853     else
854     egid="next available"
855     fi
856     einfo " - Groupid: ${egid}"
857    
858     # handle extra
859     local eextra="$@"
860     opts="${opts} ${eextra}"
861    
862     # add the group
863 azarah 1.59 local oldsandbox="${SANDBOX_ON}"
864 vapier 1.23 export SANDBOX_ON="0"
865 flameeyes 1.205 case ${CHOST} in
866     *-darwin*)
867 usata 1.91 if [ ! -z "${eextra}" ];
868     then
869 vapier 1.179 einfo "Extra options are not supported on Darwin/OS X yet"
870 usata 1.91 einfo "Please report the ebuild along with the info below"
871     einfo "eextra: ${eextra}"
872     die "Required function missing"
873     fi
874 mr_bones_ 1.100
875 usata 1.91 # If we need the next available
876     case ${egid} in
877 flameeyes 1.205 *[!0-9]*) # Non numeric
878 agriffis 1.256 for ((egid = 101; egid <= 999; egid++)); do
879     [[ -z $(egetent group ${egid}) ]] && break
880 usata 1.91 done
881     esac
882     dscl . create /groups/${egroup} gid ${egid}
883 mr_bones_ 1.100 dscl . create /groups/${egroup} passwd '*'
884 flameeyes 1.205 ;;
885    
886 flameeyes 1.220 *-freebsd*|*-dragonfly*)
887 ka0ttic 1.108 case ${egid} in
888     *[!0-9]*) # Non numeric
889 agriffis 1.256 for ((egid = 101; egid <= 999; egid++)); do
890     [[ -z $(egetent group ${egid}) ]] && break
891 ka0ttic 1.108 done
892     esac
893     pw groupadd ${egroup} -g ${egid} || die "enewgroup failed"
894 flameeyes 1.205 ;;
895 flameeyes 1.206
896     *-netbsd*)
897     case ${egid} in
898     *[!0-9]*) # Non numeric
899 agriffis 1.256 for ((egid = 101; egid <= 999; egid++)); do
900     [[ -z $(egetent group ${egid}) ]] && break
901 flameeyes 1.206 done
902     esac
903 flameeyes 1.207 groupadd -g ${egid} ${egroup} || die "enewgroup failed"
904 flameeyes 1.206 ;;
905    
906 flameeyes 1.205 *)
907 cardoe 1.345 # We specify -r so that we get a GID in the system range from login.defs
908     groupadd -r ${opts} ${egroup} || die "enewgroup failed"
909 flameeyes 1.205 ;;
910     esac
911 vapier 1.23 export SANDBOX_ON="${oldsandbox}"
912 vapier 1.24 }
913    
914 vapier 1.283 # @FUNCTION: edos2unix
915     # @USAGE: <file> [more files ...]
916     # @DESCRIPTION:
917     # A handy replacement for dos2unix, recode, fixdos, etc... This allows you
918     # to remove all of these text utilities from DEPEND variables because this
919     # is a script based solution. Just give it a list of files to convert and
920     # they will all be changed from the DOS CRLF format to the UNIX LF format.
921 vapier 1.24 edos2unix() {
922 vapier 1.263 echo "$@" | xargs sed -i 's/\r$//'
923 vapier 1.39 }
924    
925     # Make a desktop file !
926     # Great for making those icons in kde/gnome startmenu !
927 flameeyes 1.266 # Amaze your friends ! Get the women ! Join today !
928 vapier 1.39 #
929 vapier 1.341 # make_desktop_entry(<command>, [name], [icon], [type], [fields])
930 vapier 1.39 #
931 tupone 1.238 # binary: what command does the app run with ?
932 vapier 1.39 # name: the name that will show up in the menu
933     # icon: give your little like a pretty little icon ...
934 vapier 1.118 # this can be relative (to /usr/share/pixmaps) or
935     # a full path to an icon
936 flameeyes 1.266 # type: what kind of application is this ? for categories:
937 vapier 1.284 # http://standards.freedesktop.org/menu-spec/latest/apa.html
938 vapier 1.341 # fields: extra fields to append to the desktop file; a printf string
939 vapier 1.39 make_desktop_entry() {
940 vapier 1.341 [[ -z $1 ]] && die "make_desktop_entry: You must specify the executable"
941 vapier 1.39
942 vapier 1.158 local exec=${1}
943     local name=${2:-${PN}}
944 wolf31o2 1.293 local icon=${3:-${PN}}
945 vapier 1.158 local type=${4}
946 vapier 1.341 local fields=${5}
947 vapier 1.158
948     if [[ -z ${type} ]] ; then
949     local catmaj=${CATEGORY%%-*}
950     local catmin=${CATEGORY##*-}
951     case ${catmaj} in
952     app)
953     case ${catmin} in
954 vapier 1.284 accessibility) type=Accessibility;;
955 vapier 1.338 admin) type=System;;
956     antivirus) type=System;;
957     arch) type=Archiving;;
958     backup) type=Archiving;;
959     cdr) type=DiscBurning;;
960     dicts) type=Dictionary;;
961     doc) type=Documentation;;
962     editors) type=TextEditor;;
963     emacs) type=TextEditor;;
964     emulation) type=Emulator;;
965     laptop) type=HardwareSettings;;
966     office) type=Office;;
967     pda) type=PDA;;
968     vim) type=TextEditor;;
969     xemacs) type=TextEditor;;
970 vapier 1.158 esac
971 azarah 1.59 ;;
972 vapier 1.158
973     dev)
974 vapier 1.159 type="Development"
975 vapier 1.158 ;;
976    
977     games)
978     case ${catmin} in
979 wolf31o2 1.265 action|fps) type=ActionGame;;
980 vapier 1.338 arcade) type=ArcadeGame;;
981     board) type=BoardGame;;
982     emulation) type=Emulator;;
983     kids) type=KidsGame;;
984     puzzle) type=LogicGame;;
985     roguelike) type=RolePlaying;;
986     rpg) type=RolePlaying;;
987 vapier 1.158 simulation) type=Simulation;;
988 vapier 1.338 sports) type=SportsGame;;
989     strategy) type=StrategyGame;;
990 vapier 1.158 esac
991 vapier 1.159 type="Game;${type}"
992 vapier 1.158 ;;
993    
994 vapier 1.284 gnome)
995     type="Gnome;GTK"
996     ;;
997    
998     kde)
999     type="KDE;Qt"
1000     ;;
1001    
1002 vapier 1.158 mail)
1003 vapier 1.159 type="Network;Email"
1004 vapier 1.158 ;;
1005    
1006     media)
1007     case ${catmin} in
1008 vapier 1.339 gfx)
1009     type=Graphics
1010     ;;
1011     *)
1012     case ${catmin} in
1013     radio) type=Tuner;;
1014     sound) type=Audio;;
1015     tv) type=TV;;
1016     video) type=Video;;
1017     esac
1018     type="AudioVideo;${type}"
1019     ;;
1020 vapier 1.158 esac
1021 wolf31o2 1.65 ;;
1022 vapier 1.158
1023     net)
1024     case ${catmin} in
1025     dialup) type=Dialup;;
1026 vapier 1.338 ftp) type=FileTransfer;;
1027     im) type=InstantMessaging;;
1028     irc) type=IRCClient;;
1029     mail) type=Email;;
1030     news) type=News;;
1031     nntp) type=News;;
1032     p2p) type=FileTransfer;;
1033     voip) type=Telephony;;
1034 vapier 1.158 esac
1035 vapier 1.159 type="Network;${type}"
1036 vapier 1.158 ;;
1037    
1038     sci)
1039     case ${catmin} in
1040 vapier 1.284 astro*) type=Astronomy;;
1041 vapier 1.338 bio*) type=Biology;;
1042     calc*) type=Calculator;;
1043     chem*) type=Chemistry;;
1044 vapier 1.284 elec*) type=Electronics;;
1045 vapier 1.338 geo*) type=Geology;;
1046     math*) type=Math;;
1047 vapier 1.284 physics) type=Physics;;
1048     visual*) type=DataVisualization;;
1049 vapier 1.159 esac
1050 abcd 1.336 type="Education;Science;${type}"
1051 vapier 1.158 ;;
1052    
1053 vapier 1.284 sys)
1054     type="System"
1055     ;;
1056    
1057 vapier 1.158 www)
1058     case ${catmin} in
1059     client) type=WebBrowser;;
1060     esac
1061 abcd 1.336 type="Network;${type}"
1062 azarah 1.59 ;;
1063 vapier 1.158
1064 azarah 1.59 *)
1065     type=
1066     ;;
1067 vapier 1.39 esac
1068     fi
1069 carlo 1.177 if [ "${SLOT}" == "0" ] ; then
1070     local desktop_name="${PN}"
1071     else
1072     local desktop_name="${PN}-${SLOT}"
1073     fi
1074 vapier 1.272 local desktop="${T}/$(echo ${exec} | sed 's:[[:space:]/:]:_:g')-${desktop_name}.desktop"
1075 vapier 1.271 #local desktop=${T}/${exec%% *:-${desktop_name}}.desktop
1076 vapier 1.39
1077 abcd 1.336 # Don't append another ";" when a valid category value is provided.
1078     type=${type%;}${type:+;}
1079    
1080     eshopts_push -s extglob
1081     if [[ -n ${icon} && ${icon} != /* ]] && [[ ${icon} == *.xpm || ${icon} == *.png || ${icon} == *.svg ]]; then
1082     ewarn "As described in the Icon Theme Specification, icon file extensions are not"
1083     ewarn "allowed in .desktop files if the value is not an absolute path."
1084     icon=${icon%.@(xpm|png|svg)}
1085     fi
1086     eshopts_pop
1087    
1088 vapier 1.271 cat <<-EOF > "${desktop}"
1089     [Desktop Entry]
1090     Name=${name}
1091     Type=Application
1092     Comment=${DESCRIPTION}
1093     Exec=${exec}
1094     TryExec=${exec%% *}
1095     Icon=${icon}
1096 abcd 1.336 Categories=${type}
1097 vapier 1.271 EOF
1098 vapier 1.39
1099 vapier 1.341 if [[ ${fields:-=} != *=* ]] ; then
1100     # 5th arg used to be value to Path=
1101     ewarn "make_desktop_entry: update your 5th arg to read Path=${fields}"
1102     fields="Path=${fields}"
1103     fi
1104 vapier 1.342 [[ -n ${fields} ]] && printf '%b\n' "${fields}" >> "${desktop}"
1105 wolf31o2 1.293
1106 vapier 1.204 (
1107     # wrap the env here so that the 'insinto' call
1108     # doesn't corrupt the env of the caller
1109     insinto /usr/share/applications
1110     doins "${desktop}"
1111 vapier 1.340 ) || die "installing desktop file failed"
1112 danarmak 1.32 }
1113    
1114 vapier 1.283 # @FUNCTION: validate_desktop_entries
1115     # @USAGE: [directories]
1116     # @MAINTAINER:
1117     # Carsten Lohrke <carlo@gentoo.org>
1118     # @DESCRIPTION:
1119 carlo 1.278 # Validate desktop entries using desktop-file-utils
1120 carlo 1.277 validate_desktop_entries() {
1121     if [[ -x /usr/bin/desktop-file-validate ]] ; then
1122     einfo "Checking desktop entry validity"
1123     local directories=""
1124 carlo 1.279 for d in /usr/share/applications $@ ; do
1125     [[ -d ${D}${d} ]] && directories="${directories} ${D}${d}"
1126 carlo 1.277 done
1127 carlo 1.279 if [[ -n ${directories} ]] ; then
1128     for FILE in $(find ${directories} -name "*\.desktop" \
1129     -not -path '*.hidden*' | sort -u 2>/dev/null)
1130     do
1131     local temp=$(desktop-file-validate ${FILE} | grep -v "warning:" | \
1132     sed -e "s|error: ||" -e "s|${FILE}:|--|g" )
1133     [[ -n $temp ]] && elog ${temp/--/${FILE/${D}/}:}
1134     done
1135     fi
1136 carlo 1.277 echo ""
1137     else
1138     einfo "Passing desktop entry validity check. Install dev-util/desktop-file-utils, if you want to help to improve Gentoo."
1139     fi
1140     }
1141    
1142 vapier 1.283 # @FUNCTION: make_session_desktop
1143 vapier 1.314 # @USAGE: <title> <command> [command args...]
1144 vapier 1.283 # @DESCRIPTION:
1145     # Make a GDM/KDM Session file. The title is the file to execute to start the
1146     # Window Manager. The command is the name of the Window Manager.
1147 vapier 1.314 #
1148     # You can set the name of the file via the ${wm} variable.
1149 lanius 1.133 make_session_desktop() {
1150 vapier 1.314 [[ -z $1 ]] && eerror "$0: You must specify the title" && return 1
1151     [[ -z $2 ]] && eerror "$0: You must specify the command" && return 1
1152 lanius 1.133
1153 vapier 1.167 local title=$1
1154     local command=$2
1155 vapier 1.314 local desktop=${T}/${wm:-${PN}}.desktop
1156     shift 2
1157 lanius 1.133
1158 vapier 1.271 cat <<-EOF > "${desktop}"
1159     [Desktop Entry]
1160     Name=${title}
1161     Comment=This session logs you into ${title}
1162 vapier 1.314 Exec=${command} $*
1163 vapier 1.271 TryExec=${command}
1164 vapier 1.314 Type=XSession
1165 vapier 1.271 EOF
1166 lanius 1.133
1167 vapier 1.271 (
1168     # wrap the env here so that the 'insinto' call
1169     # doesn't corrupt the env of the caller
1170 lanius 1.133 insinto /usr/share/xsessions
1171     doins "${desktop}"
1172 vapier 1.271 )
1173 lanius 1.133 }
1174    
1175 vapier 1.283 # @FUNCTION: domenu
1176     # @USAGE: <menus>
1177     # @DESCRIPTION:
1178     # Install the list of .desktop menu files into the appropriate directory
1179     # (/usr/share/applications).
1180 lanius 1.133 domenu() {
1181 vapier 1.271 (
1182     # wrap the env here so that the 'insinto' call
1183     # doesn't corrupt the env of the caller
1184     local i j ret=0
1185 lanius 1.133 insinto /usr/share/applications
1186 vapier 1.167 for i in "$@" ; do
1187     if [[ -f ${i} ]] ; then
1188     doins "${i}"
1189 vapier 1.271 ((ret+=$?))
1190 vapier 1.167 elif [[ -d ${i} ]] ; then
1191     for j in "${i}"/*.desktop ; do
1192     doins "${j}"
1193 vapier 1.271 ((ret+=$?))
1194 lanius 1.133 done
1195 vapier 1.285 else
1196     ((++ret))
1197 swegener 1.190 fi
1198 lanius 1.133 done
1199 vapier 1.271 exit ${ret}
1200     )
1201 lanius 1.133 }
1202 vapier 1.283
1203     # @FUNCTION: newmenu
1204     # @USAGE: <menu> <newname>
1205     # @DESCRIPTION:
1206     # Like all other new* functions, install the specified menu as newname.
1207 vapier 1.167 newmenu() {
1208 vapier 1.271 (
1209     # wrap the env here so that the 'insinto' call
1210     # doesn't corrupt the env of the caller
1211 vapier 1.167 insinto /usr/share/applications
1212 vapier 1.271 newins "$@"
1213     )
1214 vapier 1.167 }
1215 lanius 1.133
1216 vapier 1.283 # @FUNCTION: doicon
1217     # @USAGE: <list of icons>
1218     # @DESCRIPTION:
1219     # Install the list of icons into the icon directory (/usr/share/pixmaps).
1220     # This is useful in conjunction with creating desktop/menu files.
1221 lanius 1.133 doicon() {
1222 vapier 1.271 (
1223     # wrap the env here so that the 'insinto' call
1224     # doesn't corrupt the env of the caller
1225     local i j ret
1226 lanius 1.133 insinto /usr/share/pixmaps
1227 vapier 1.167 for i in "$@" ; do
1228     if [[ -f ${i} ]] ; then
1229     doins "${i}"
1230 vapier 1.271 ((ret+=$?))
1231 vapier 1.167 elif [[ -d ${i} ]] ; then
1232     for j in "${i}"/*.png ; do
1233     doins "${j}"
1234 vapier 1.271 ((ret+=$?))
1235 lanius 1.133 done
1236 vapier 1.285 else
1237     ((++ret))
1238 swegener 1.190 fi
1239 lanius 1.133 done
1240 vapier 1.271 exit ${ret}
1241     )
1242 lanius 1.133 }
1243 vapier 1.283
1244     # @FUNCTION: newicon
1245     # @USAGE: <icon> <newname>
1246     # @DESCRIPTION:
1247     # Like all other new* functions, install the specified icon as newname.
1248 vapier 1.167 newicon() {
1249 vapier 1.271 (
1250     # wrap the env here so that the 'insinto' call
1251     # doesn't corrupt the env of the caller
1252 vapier 1.167 insinto /usr/share/pixmaps
1253 vapier 1.271 newins "$@"
1254     )
1255 vapier 1.167 }
1256 lanius 1.133
1257 vapier 1.70 # for internal use only (unpack_pdv and unpack_makeself)
1258     find_unpackable_file() {
1259 vapier 1.196 local src=$1
1260     if [[ -z ${src} ]] ; then
1261     src=${DISTDIR}/${A}
1262 vapier 1.50 else
1263 vapier 1.196 if [[ -e ${DISTDIR}/${src} ]] ; then
1264     src=${DISTDIR}/${src}
1265     elif [[ -e ${PWD}/${src} ]] ; then
1266     src=${PWD}/${src}
1267     elif [[ -e ${src} ]] ; then
1268     src=${src}
1269 vapier 1.50 fi
1270     fi
1271 vapier 1.196 [[ ! -e ${src} ]] && return 1
1272 vapier 1.70 echo "${src}"
1273     }
1274    
1275 vapier 1.283 # @FUNCTION: unpack_pdv
1276     # @USAGE: <file to unpack> <size of off_t>
1277     # @DESCRIPTION:
1278 vapier 1.70 # Unpack those pesky pdv generated files ...
1279     # They're self-unpacking programs with the binary package stuffed in
1280     # the middle of the archive. Valve seems to use it a lot ... too bad
1281     # it seems to like to segfault a lot :(. So lets take it apart ourselves.
1282 swegener 1.286 #
1283 vapier 1.283 # You have to specify the off_t size ... I have no idea how to extract that
1284     # information out of the binary executable myself. Basically you pass in
1285     # the size of the off_t type (in bytes) on the machine that built the pdv
1286     # archive.
1287 vapier 1.70 #
1288 vapier 1.283 # One way to determine this is by running the following commands:
1289 ulm 1.288 #
1290     # @CODE
1291     # strings <pdv archive> | grep lseek
1292     # strace -elseek <pdv archive>
1293     # @CODE
1294     #
1295 vapier 1.283 # Basically look for the first lseek command (we do the strings/grep because
1296     # sometimes the function call is _llseek or something) and steal the 2nd
1297     # parameter. Here is an example:
1298 ulm 1.288 #
1299     # @CODE
1300     # vapier@vapier 0 pdv_unpack # strings hldsupdatetool.bin | grep lseek
1301     # lseek
1302     # vapier@vapier 0 pdv_unpack # strace -elseek ./hldsupdatetool.bin
1303     # lseek(3, -4, SEEK_END) = 2981250
1304     # @CODE
1305     #
1306 vapier 1.283 # Thus we would pass in the value of '4' as the second parameter.
1307 vapier 1.70 unpack_pdv() {
1308 vapier 1.271 local src=$(find_unpackable_file "$1")
1309 vapier 1.196 local sizeoff_t=$2
1310 vapier 1.70
1311 vapier 1.196 [[ -z ${src} ]] && die "Could not locate source for '$1'"
1312     [[ -z ${sizeoff_t} ]] && die "No idea what off_t size was used for this pdv :("
1313 vapier 1.70
1314 vapier 1.212 local shrtsrc=$(basename "${src}")
1315 vapier 1.70 echo ">>> Unpacking ${shrtsrc} to ${PWD}"
1316 vapier 1.271 local metaskip=$(tail -c ${sizeoff_t} "${src}" | hexdump -e \"%i\")
1317     local tailskip=$(tail -c $((${sizeoff_t}*2)) "${src}" | head -c ${sizeoff_t} | hexdump -e \"%i\")
1318 vapier 1.70
1319     # grab metadata for debug reasons
1320 vapier 1.271 local metafile=$(emktemp)
1321     tail -c +$((${metaskip}+1)) "${src}" > "${metafile}"
1322 vapier 1.70
1323     # rip out the final file name from the metadata
1324 vapier 1.271 local datafile=$(tail -c +$((${metaskip}+1)) "${src}" | strings | head -n 1)
1325     datafile=$(basename "${datafile}")
1326 vapier 1.70
1327 vapier 1.71 # now lets uncompress/untar the file if need be
1328 vapier 1.271 local tmpfile=$(emktemp)
1329 vapier 1.70 tail -c +$((${tailskip}+1)) ${src} 2>/dev/null | head -c 512 > ${tmpfile}
1330 vapier 1.71
1331 vapier 1.271 local iscompressed=$(file -b "${tmpfile}")
1332     if [[ ${iscompressed:0:8} == "compress" ]] ; then
1333 vapier 1.71 iscompressed=1
1334     mv ${tmpfile}{,.Z}
1335     gunzip ${tmpfile}
1336     else
1337     iscompressed=0
1338     fi
1339 vapier 1.271 local istar=$(file -b "${tmpfile}")
1340     if [[ ${istar:0:9} == "POSIX tar" ]] ; then
1341 vapier 1.71 istar=1
1342     else
1343     istar=0
1344     fi
1345    
1346     #for some reason gzip dies with this ... dd cant provide buffer fast enough ?
1347     #dd if=${src} ibs=${metaskip} count=1 \
1348     # | dd ibs=${tailskip} skip=1 \
1349     # | gzip -dc \
1350     # > ${datafile}
1351     if [ ${iscompressed} -eq 1 ] ; then
1352     if [ ${istar} -eq 1 ] ; then
1353     tail -c +$((${tailskip}+1)) ${src} 2>/dev/null \
1354     | head -c $((${metaskip}-${tailskip})) \
1355     | tar -xzf -
1356     else
1357 vapier 1.70 tail -c +$((${tailskip}+1)) ${src} 2>/dev/null \
1358     | head -c $((${metaskip}-${tailskip})) \
1359     | gzip -dc \
1360     > ${datafile}
1361 vapier 1.71 fi
1362     else
1363     if [ ${istar} -eq 1 ] ; then
1364     tail -c +$((${tailskip}+1)) ${src} 2>/dev/null \
1365     | head -c $((${metaskip}-${tailskip})) \
1366 vapier 1.73 | tar --no-same-owner -xf -
1367 vapier 1.71 else
1368 vapier 1.70 tail -c +$((${tailskip}+1)) ${src} 2>/dev/null \
1369     | head -c $((${metaskip}-${tailskip})) \
1370     > ${datafile}
1371 vapier 1.71 fi
1372     fi
1373     true
1374     #[ -s "${datafile}" ] || die "failure unpacking pdv ('${metaskip}' '${tailskip}' '${datafile}')"
1375 vapier 1.70 #assert "failure unpacking pdv ('${metaskip}' '${tailskip}' '${datafile}')"
1376     }
1377    
1378 vapier 1.283 # @FUNCTION: unpack_makeself
1379     # @USAGE: [file to unpack] [offset] [tail|dd]
1380     # @DESCRIPTION:
1381 vapier 1.70 # Unpack those pesky makeself generated files ...
1382     # They're shell scripts with the binary package tagged onto
1383     # the end of the archive. Loki utilized the format as does
1384     # many other game companies.
1385 swegener 1.286 #
1386 vapier 1.283 # If the file is not specified, then ${A} is used. If the
1387     # offset is not specified then we will attempt to extract
1388     # the proper offset from the script itself.
1389 vapier 1.70 unpack_makeself() {
1390 vapier 1.217 local src_input=${1:-${A}}
1391     local src=$(find_unpackable_file "${src_input}")
1392 vapier 1.196 local skip=$2
1393     local exe=$3
1394    
1395 vapier 1.217 [[ -z ${src} ]] && die "Could not locate source for '${src_input}'"
1396 vapier 1.50
1397 vapier 1.196 local shrtsrc=$(basename "${src}")
1398 vapier 1.41 echo ">>> Unpacking ${shrtsrc} to ${PWD}"
1399 vapier 1.212 if [[ -z ${skip} ]] ; then
1400 mr_bones_ 1.343 local ver=$(grep -m1 -a '#.*Makeself' "${src}" | awk '{print $NF}')
1401 vapier 1.41 local skip=0
1402 vapier 1.112 exe=tail
1403 vapier 1.41 case ${ver} in
1404 wolf31o2 1.240 1.5.*|1.6.0-nv) # tested 1.5.{3,4,5} ... guessing 1.5.x series is same
1405 vapier 1.112 skip=$(grep -a ^skip= "${src}" | cut -d= -f2)
1406 vapier 1.41 ;;
1407     2.0|2.0.1)
1408 vapier 1.112 skip=$(grep -a ^$'\t'tail "${src}" | awk '{print $2}' | cut -b2-)
1409 vapier 1.41 ;;
1410 wolf31o2 1.48 2.1.1)
1411 vapier 1.112 skip=$(grep -a ^offset= "${src}" | awk '{print $2}' | cut -b2-)
1412 vapier 1.344 (( skip++ ))
1413 wolf31o2 1.48 ;;
1414 vapier 1.49 2.1.2)
1415 vapier 1.112 skip=$(grep -a ^offset= "${src}" | awk '{print $3}' | head -n 1)
1416 vapier 1.344 (( skip++ ))
1417 vapier 1.49 ;;
1418 wolf31o2 1.48 2.1.3)
1419 vapier 1.112 skip=`grep -a ^offset= "${src}" | awk '{print $3}'`
1420 vapier 1.344 (( skip++ ))
1421 vapier 1.41 ;;
1422 wolf31o2 1.211 2.1.4|2.1.5)
1423 vapier 1.112 skip=$(grep -a offset=.*head.*wc "${src}" | awk '{print $3}' | head -n 1)
1424     skip=$(head -n ${skip} "${src}" | wc -c)
1425     exe="dd"
1426     ;;
1427 vapier 1.41 *)
1428     eerror "I'm sorry, but I was unable to support the Makeself file."
1429     eerror "The version I detected was '${ver}'."
1430     eerror "Please file a bug about the file ${shrtsrc} at"
1431     eerror "http://bugs.gentoo.org/ so that support can be added."
1432     die "makeself version '${ver}' not supported"
1433     ;;
1434     esac
1435     debug-print "Detected Makeself version ${ver} ... using ${skip} as offset"
1436     fi
1437 vapier 1.112 case ${exe} in
1438     tail) exe="tail -n +${skip} '${src}'";;
1439 vapier 1.344 dd) exe="dd ibs=${skip} skip=1 if='${src}'";;
1440 vapier 1.112 *) die "makeself cant handle exe '${exe}'"
1441     esac
1442 vapier 1.41
1443 vapier 1.68 # lets grab the first few bytes of the file to figure out what kind of archive it is
1444 vapier 1.356 local filetype tmpfile=$(emktemp)
1445 vapier 1.112 eval ${exe} 2>/dev/null | head -c 512 > "${tmpfile}"
1446 vapier 1.356 filetype=$(file -b "${tmpfile}") || die
1447 vapier 1.68 case ${filetype} in
1448 vapier 1.257 *tar\ archive*)
1449 vapier 1.112 eval ${exe} | tar --no-same-owner -xf -
1450 vapier 1.68 ;;
1451     bzip2*)
1452 vapier 1.112 eval ${exe} | bzip2 -dc | tar --no-same-owner -xf -
1453 mr_bones_ 1.69 ;;
1454 vapier 1.68 gzip*)
1455 vapier 1.112 eval ${exe} | tar --no-same-owner -xzf -
1456 vapier 1.68 ;;
1457 vapier 1.93 compress*)
1458 vapier 1.112 eval ${exe} | gunzip | tar --no-same-owner -xf -
1459 vapier 1.93 ;;
1460 vapier 1.68 *)
1461 vapier 1.93 eerror "Unknown filetype \"${filetype}\" ?"
1462 vapier 1.68 false
1463     ;;
1464     esac
1465     assert "failure unpacking (${filetype}) makeself ${shrtsrc} ('${ver}' +${skip})"
1466 wolf31o2 1.56 }
1467    
1468 vapier 1.283 # @FUNCTION: check_license
1469     # @USAGE: [license]
1470     # @DESCRIPTION:
1471     # Display a license for user to accept. If no license is
1472     # specified, then ${LICENSE} is used.
1473 wolf31o2 1.56 check_license() {
1474 vapier 1.60 local lic=$1
1475     if [ -z "${lic}" ] ; then
1476     lic="${PORTDIR}/licenses/${LICENSE}"
1477 wolf31o2 1.56 else
1478 wolf31o2 1.199 if [ -e "${PORTDIR}/licenses/${lic}" ] ; then
1479     lic="${PORTDIR}/licenses/${lic}"
1480     elif [ -e "${PWD}/${lic}" ] ; then
1481     lic="${PWD}/${lic}"
1482     elif [ -e "${lic}" ] ; then
1483     lic="${lic}"
1484 wolf31o2 1.56 fi
1485     fi
1486 vapier 1.64 local l="`basename ${lic}`"
1487 wolf31o2 1.56
1488 vapier 1.60 # here is where we check for the licenses the user already
1489     # accepted ... if we don't find a match, we make the user accept
1490     local alic
1491 vapier 1.322 eshopts_push -o noglob # so that bash doesn't expand "*"
1492 wolf31o2 1.104 for alic in ${ACCEPT_LICENSE} ; do
1493 wolf31o2 1.255 if [[ ${alic} == ${l} ]]; then
1494 vapier 1.322 eshopts_pop
1495 wolf31o2 1.106 return 0
1496     fi
1497 vapier 1.60 done
1498 vapier 1.322 eshopts_pop
1499 zmedico 1.324 [ ! -f "${lic}" ] && die "Could not find requested license ${lic}"
1500 vapier 1.60
1501 vapier 1.271 local licmsg=$(emktemp)
1502     cat <<-EOF > ${licmsg}
1503     **********************************************************
1504     The following license outlines the terms of use of this
1505     package. You MUST accept this license for installation to
1506     continue. When you are done viewing, hit 'q'. If you
1507     CTRL+C out of this, the install will not run!
1508     **********************************************************
1509 swegener 1.286
1510 vapier 1.271 EOF
1511 vapier 1.60 cat ${lic} >> ${licmsg}
1512     ${PAGER:-less} ${licmsg} || die "Could not execute pager (${PAGER}) to accept ${lic}"
1513 vapier 1.64 einfon "Do you accept the terms of this license (${l})? [yes/no] "
1514 vapier 1.60 read alic
1515     case ${alic} in
1516     yes|Yes|y|Y)
1517     return 0
1518     ;;
1519     *)
1520     echo;echo;echo
1521     eerror "You MUST accept the license to continue! Exiting!"
1522     die "Failed to accept license"
1523     ;;
1524     esac
1525 vapier 1.23 }
1526 vapier 1.75
1527 vapier 1.283 # @FUNCTION: cdrom_get_cds
1528     # @USAGE: <file on cd1> [file on cd2] [file on cd3] [...]
1529     # @DESCRIPTION:
1530 vapier 1.75 # Aquire cd(s) for those lovely cd-based emerges. Yes, this violates
1531     # the whole 'non-interactive' policy, but damnit I want CD support !
1532 swegener 1.286 #
1533 vapier 1.283 # With these cdrom functions we handle all the user interaction and
1534     # standardize everything. All you have to do is call cdrom_get_cds()
1535 vapier 1.75 # and when the function returns, you can assume that the cd has been
1536     # found at CDROM_ROOT.
1537 swegener 1.286 #
1538 vapier 1.283 # The function will attempt to locate a cd based upon a file that is on
1539     # the cd. The more files you give this function, the more cds
1540     # the cdrom functions will handle.
1541 swegener 1.286 #
1542 vapier 1.283 # Normally the cdrom functions will refer to the cds as 'cd #1', 'cd #2',
1543     # etc... If you want to give the cds better names, then just export
1544 vapier 1.243 # the appropriate CDROM_NAME variable before calling cdrom_get_cds().
1545 vapier 1.283 # Use CDROM_NAME for one cd, or CDROM_NAME_# for multiple cds. You can
1546     # also use the CDROM_NAME_SET bash array.
1547 swegener 1.286 #
1548 vapier 1.283 # For those multi cd ebuilds, see the cdrom_load_next_cd() function.
1549 vapier 1.75 cdrom_get_cds() {
1550     # first we figure out how many cds we're dealing with by
1551     # the # of files they gave us
1552     local cdcnt=0
1553     local f=
1554     for f in "$@" ; do
1555 vapier 1.214 ((++cdcnt))
1556 vapier 1.75 export CDROM_CHECK_${cdcnt}="$f"
1557     done
1558     export CDROM_TOTAL_CDS=${cdcnt}
1559     export CDROM_CURRENT_CD=1
1560    
1561     # now we see if the user gave use CD_ROOT ...
1562     # if they did, let's just believe them that it's correct
1563 vapier 1.215 if [[ -n ${CD_ROOT}${CD_ROOT_1} ]] ; then
1564 vapier 1.75 local var=
1565     cdcnt=0
1566 vapier 1.131 while [[ ${cdcnt} -lt ${CDROM_TOTAL_CDS} ]] ; do
1567 vapier 1.214 ((++cdcnt))
1568 vapier 1.75 var="CD_ROOT_${cdcnt}"
1569 vapier 1.215 [[ -z ${!var} ]] && var="CD_ROOT"
1570 vapier 1.131 if [[ -z ${!var} ]] ; then
1571 vapier 1.75 eerror "You must either use just the CD_ROOT"
1572     eerror "or specify ALL the CD_ROOT_X variables."
1573     eerror "In this case, you will need ${CDROM_TOTAL_CDS} CD_ROOT_X variables."
1574     die "could not locate CD_ROOT_${cdcnt}"
1575     fi
1576     done
1577 vapier 1.215 export CDROM_ROOT=${CD_ROOT_1:-${CD_ROOT}}
1578 vapier 1.75 einfo "Found CD #${CDROM_CURRENT_CD} root at ${CDROM_ROOT}"
1579 vapier 1.215 export CDROM_SET=-1
1580     for f in ${CDROM_CHECK_1//:/ } ; do
1581     ((++CDROM_SET))
1582 cardoe 1.346 [[ -e ${CDROM_ROOT}/${f} ]] && break
1583 vapier 1.215 done
1584     export CDROM_MATCH=${f}
1585 vapier 1.75 return
1586     fi
1587    
1588 vapier 1.215 # User didn't help us out so lets make sure they know they can
1589     # simplify the whole process ...
1590 vapier 1.131 if [[ ${CDROM_TOTAL_CDS} -eq 1 ]] ; then
1591 vapier 1.215 einfo "This ebuild will need the ${CDROM_NAME:-cdrom for ${PN}}"
1592 vapier 1.75 echo
1593     einfo "If you do not have the CD, but have the data files"
1594     einfo "mounted somewhere on your filesystem, just export"
1595     einfo "the variable CD_ROOT so that it points to the"
1596     einfo "directory containing the files."
1597     echo
1598 vapier 1.132 einfo "For example:"
1599     einfo "export CD_ROOT=/mnt/cdrom"
1600     echo
1601 vapier 1.75 else
1602 vapier 1.243 if [[ -n ${CDROM_NAME_SET} ]] ; then
1603     # Translate the CDROM_NAME_SET array into CDROM_NAME_#
1604     cdcnt=0
1605     while [[ ${cdcnt} -lt ${CDROM_TOTAL_CDS} ]] ; do
1606     ((++cdcnt))
1607     export CDROM_NAME_${cdcnt}="${CDROM_NAME_SET[$((${cdcnt}-1))]}"
1608     done
1609     fi
1610    
1611 vapier 1.75 einfo "This package will need access to ${CDROM_TOTAL_CDS} cds."
1612     cdcnt=0
1613 vapier 1.131 while [[ ${cdcnt} -lt ${CDROM_TOTAL_CDS} ]] ; do
1614 vapier 1.214 ((++cdcnt))
1615 vapier 1.75 var="CDROM_NAME_${cdcnt}"
1616 vapier 1.131 [[ ! -z ${!var} ]] && einfo " CD ${cdcnt}: ${!var}"
1617 vapier 1.75 done
1618     echo
1619     einfo "If you do not have the CDs, but have the data files"
1620     einfo "mounted somewhere on your filesystem, just export"
1621     einfo "the following variables so they point to the right place:"
1622 nyhm 1.347 einfon ""
1623 vapier 1.75 cdcnt=0
1624 vapier 1.131 while [[ ${cdcnt} -lt ${CDROM_TOTAL_CDS} ]] ; do
1625 vapier 1.214 ((++cdcnt))
1626 vapier 1.75 echo -n " CD_ROOT_${cdcnt}"
1627     done
1628     echo
1629     einfo "Or, if you have all the files in the same place, or"
1630     einfo "you only have one cdrom, you can export CD_ROOT"
1631     einfo "and that place will be used as the same data source"
1632     einfo "for all the CDs."
1633     echo
1634 vapier 1.132 einfo "For example:"
1635     einfo "export CD_ROOT_1=/mnt/cdrom"
1636     echo
1637 vapier 1.75 fi
1638 vapier 1.215
1639 vapier 1.214 export CDROM_SET=""
1640 vapier 1.75 export CDROM_CURRENT_CD=0
1641     cdrom_load_next_cd
1642     }
1643    
1644 vapier 1.283 # @FUNCTION: cdrom_load_next_cd
1645     # @DESCRIPTION:
1646     # Some packages are so big they come on multiple CDs. When you're done reading
1647     # files off a CD and want access to the next one, just call this function.
1648     # Again, all the messy details of user interaction are taken care of for you.
1649     # Once this returns, just read the variable CDROM_ROOT for the location of the
1650     # mounted CD. Note that you can only go forward in the CD list, so make sure
1651     # you only call this function when you're done using the current CD.
1652 vapier 1.75 cdrom_load_next_cd() {
1653 vapier 1.215 local var
1654     ((++CDROM_CURRENT_CD))
1655 vapier 1.79
1656 vapier 1.75 unset CDROM_ROOT
1657 vapier 1.215 var=CD_ROOT_${CDROM_CURRENT_CD}
1658     [[ -z ${!var} ]] && var="CD_ROOT"
1659 vapier 1.131 if [[ -z ${!var} ]] ; then
1660 vapier 1.75 var="CDROM_CHECK_${CDROM_CURRENT_CD}"
1661 vapier 1.215 _cdrom_locate_file_on_cd ${!var}
1662 vapier 1.75 else
1663 vapier 1.131 export CDROM_ROOT=${!var}
1664 vapier 1.75 fi
1665    
1666     einfo "Found CD #${CDROM_CURRENT_CD} root at ${CDROM_ROOT}"
1667     }
1668    
1669     # this is used internally by the cdrom_get_cds() and cdrom_load_next_cd()
1670     # functions. this should *never* be called from an ebuild.
1671     # all it does is try to locate a give file on a cd ... if the cd isn't
1672     # found, then a message asking for the user to insert the cdrom will be
1673     # displayed and we'll hang out here until:
1674     # (1) the file is found on a mounted cdrom
1675     # (2) the user hits CTRL+C
1676 vapier 1.215 _cdrom_locate_file_on_cd() {
1677 vapier 1.214 local mline=""
1678 wolf31o2 1.296 local showedmsg=0 showjolietmsg=0
1679 vapier 1.214
1680 vapier 1.131 while [[ -z ${CDROM_ROOT} ]] ; do
1681 vapier 1.214 local i=0
1682     local -a cdset=(${*//:/ })
1683     if [[ -n ${CDROM_SET} ]] ; then
1684     cdset=(${cdset[${CDROM_SET}]})
1685     fi
1686    
1687     while [[ -n ${cdset[${i}]} ]] ; do
1688     local dir=$(dirname ${cdset[${i}]})
1689     local file=$(basename ${cdset[${i}]})
1690    
1691 uberlord 1.259 local point= node= fs= foo=
1692     while read point node fs foo ; do
1693 nyhm 1.281 [[ " cd9660 iso9660 udf " != *" ${fs} "* ]] && \
1694 uberlord 1.264 ! [[ ${fs} == "subfs" && ",${opts}," == *",fs=cdfss,"* ]] \
1695     && continue
1696 uberlord 1.259 point=${point//\040/ }
1697 vapier 1.292 [[ ! -d ${point}/${dir} ]] && continue
1698 uberlord 1.259 [[ -z $(find "${point}/${dir}" -maxdepth 1 -iname "${file}") ]] && continue
1699     export CDROM_ROOT=${point}
1700     export CDROM_SET=${i}
1701     export CDROM_MATCH=${cdset[${i}]}
1702     return
1703 kanaka 1.262 done <<< "$(get_mounts)"
1704 vapier 1.214
1705     ((++i))
1706 vapier 1.75 done
1707    
1708 vapier 1.214 echo
1709     if [[ ${showedmsg} -eq 0 ]] ; then
1710     if [[ ${CDROM_TOTAL_CDS} -eq 1 ]] ; then
1711     if [[ -z ${CDROM_NAME} ]] ; then
1712     einfo "Please insert+mount the cdrom for ${PN} now !"
1713     else
1714     einfo "Please insert+mount the ${CDROM_NAME} cdrom now !"
1715     fi
1716     else
1717     if [[ -z ${CDROM_NAME_1} ]] ; then
1718     einfo "Please insert+mount cd #${CDROM_CURRENT_CD} for ${PN} now !"
1719 vapier 1.75 else
1720 vapier 1.214 local var="CDROM_NAME_${CDROM_CURRENT_CD}"
1721     einfo "Please insert+mount the ${!var} cdrom now !"
1722 vapier 1.75 fi
1723     fi
1724 vapier 1.214 showedmsg=1
1725 vapier 1.75 fi
1726 vapier 1.214 einfo "Press return to scan for the cd again"
1727     einfo "or hit CTRL+C to abort the emerge."
1728     echo
1729 wolf31o2 1.296 if [[ ${showjolietmsg} -eq 0 ]] ; then
1730     showjolietmsg=1
1731     else
1732     ewarn "If you are having trouble with the detection"
1733     ewarn "of your CD, it is possible that you do not have"
1734     ewarn "Joliet support enabled in your kernel. Please"
1735     ewarn "check that CONFIG_JOLIET is enabled in your kernel."
1736     ebeep 5
1737     fi
1738 vapier 1.222 read || die "something is screwed with your system"
1739 vapier 1.75 done
1740     }
1741 vapier 1.92
1742 vapier 1.287 # @FUNCTION: strip-linguas
1743     # @USAGE: [<allow LINGUAS>|<-i|-u> <directories of .po files>]
1744     # @DESCRIPTION:
1745 mr_bones_ 1.100 # Make sure that LINGUAS only contains languages that
1746 vapier 1.287 # a package can support. The first form allows you to
1747     # specify a list of LINGUAS. The -i builds a list of po
1748     # files found in all the directories and uses the
1749     # intersection of the lists. The -u builds a list of po
1750     # files found in all the directories and uses the union
1751     # of the lists.
1752 vapier 1.92 strip-linguas() {
1753 vapier 1.242 local ls newls nols
1754 vapier 1.154 if [[ $1 == "-i" ]] || [[ $1 == "-u" ]] ; then
1755     local op=$1; shift
1756 vapier 1.315 ls=$(find "$1" -name '*.po' -exec basename {} .po ';'); shift
1757 vapier 1.92 local d f
1758     for d in "$@" ; do
1759 vapier 1.154 if [[ ${op} == "-u" ]] ; then
1760     newls=${ls}
1761 vapier 1.92 else
1762     newls=""
1763     fi
1764 vapier 1.315 for f in $(find "$d" -name '*.po' -exec basename {} .po ';') ; do
1765 vapier 1.154 if [[ ${op} == "-i" ]] ; then
1766 ssuominen 1.358 has ${f} ${ls} && newls="${newls} ${f}"
1767 vapier 1.92 else
1768 ssuominen 1.358 has ${f} ${ls} || newls="${newls} ${f}"
1769 vapier 1.92 fi
1770     done
1771 vapier 1.154 ls=${newls}
1772 vapier 1.92 done
1773     else
1774 vapier 1.236 ls="$@"
1775 vapier 1.92 fi
1776    
1777 vapier 1.242 nols=""
1778 vapier 1.92 newls=""
1779     for f in ${LINGUAS} ; do
1780 ssuominen 1.358 if has ${f} ${ls} ; then
1781 vapier 1.120 newls="${newls} ${f}"
1782 vapier 1.92 else
1783 vapier 1.242 nols="${nols} ${f}"
1784 vapier 1.92 fi
1785     done
1786 vapier 1.244 [[ -n ${nols} ]] \
1787 vapier 1.316 && ewarn "Sorry, but ${PN} does not support the LINGUAS:" ${nols}
1788 vapier 1.237 export LINGUAS=${newls:1}
1789 vapier 1.92 }
1790 iggy 1.110
1791 vapier 1.283 # @FUNCTION: preserve_old_lib
1792     # @USAGE: <libs to preserve> [more libs]
1793     # @DESCRIPTION:
1794     # These functions are useful when a lib in your package changes ABI SONAME.
1795     # An example might be from libogg.so.0 to libogg.so.1. Removing libogg.so.0
1796 eradicator 1.111 # would break packages that link against it. Most people get around this
1797     # by using the portage SLOT mechanism, but that is not always a relevant
1798 vapier 1.283 # solution, so instead you can call this from pkg_preinst. See also the
1799     # preserve_old_lib_notify function.
1800 eradicator 1.111 preserve_old_lib() {
1801 vapier 1.268 if [[ ${EBUILD_PHASE} != "preinst" ]] ; then
1802 vapier 1.267 eerror "preserve_old_lib() must be called from pkg_preinst() only"
1803 vapier 1.276 die "Invalid preserve_old_lib() usage"
1804 vapier 1.267 fi
1805     [[ -z $1 ]] && die "Usage: preserve_old_lib <library to preserve> [more libraries to preserve]"
1806    
1807 vapier 1.297 # let portage worry about it
1808     has preserve-libs ${FEATURES} && return 0
1809    
1810 vapier 1.267 local lib dir
1811     for lib in "$@" ; do
1812     [[ -e ${ROOT}/${lib} ]] || continue
1813     dir=${lib%/*}
1814     dodir ${dir} || die "dodir ${dir} failed"
1815     cp "${ROOT}"/${lib} "${D}"/${lib} || die "cp ${lib} failed"
1816     touch "${D}"/${lib}
1817     done
1818 eradicator 1.111 }
1819    
1820 vapier 1.283 # @FUNCTION: preserve_old_lib_notify
1821     # @USAGE: <libs to notify> [more libs]
1822     # @DESCRIPTION:
1823     # Spit helpful messages about the libraries preserved by preserve_old_lib.
1824 eradicator 1.111 preserve_old_lib_notify() {
1825 vapier 1.268 if [[ ${EBUILD_PHASE} != "postinst" ]] ; then
1826 vapier 1.267 eerror "preserve_old_lib_notify() must be called from pkg_postinst() only"
1827 vapier 1.276 die "Invalid preserve_old_lib_notify() usage"
1828 vapier 1.267 fi
1829    
1830 vapier 1.297 # let portage worry about it
1831     has preserve-libs ${FEATURES} && return 0
1832    
1833 vapier 1.267 local lib notice=0
1834     for lib in "$@" ; do
1835     [[ -e ${ROOT}/${lib} ]] || continue
1836     if [[ ${notice} -eq 0 ]] ; then
1837     notice=1
1838     ewarn "Old versions of installed libraries were detected on your system."
1839     ewarn "In order to avoid breaking packages that depend on these old libs,"
1840     ewarn "the libraries are not being removed. You need to run revdep-rebuild"
1841     ewarn "in order to remove these old dependencies. If you do not have this"
1842     ewarn "helper program, simply emerge the 'gentoolkit' package."
1843     ewarn
1844     fi
1845 vapier 1.355 # temp hack for #348634 #357225
1846     [[ ${PN} == "mpfr" ]] && lib=${lib##*/}
1847 vapier 1.352 ewarn " # revdep-rebuild --library '${lib}'"
1848 vapier 1.267 done
1849 vapier 1.291 if [[ ${notice} -eq 1 ]] ; then
1850     ewarn
1851     ewarn "Once you've finished running revdep-rebuild, it should be safe to"
1852 vapier 1.300 ewarn "delete the old libraries. Here is a copy & paste for the lazy:"
1853     for lib in "$@" ; do
1854     ewarn " # rm '${lib}'"
1855     done
1856 vapier 1.291 fi
1857 eradicator 1.111 }
1858 vapier 1.125
1859 vapier 1.283 # @FUNCTION: built_with_use
1860     # @USAGE: [--hidden] [--missing <action>] [-a|-o] <DEPEND ATOM> <List of USE flags>
1861     # @DESCRIPTION:
1862 betelgeuse 1.329 #
1863     # Deprecated: Use EAPI 2 use deps in DEPEND|RDEPEND and with has_version calls.
1864     #
1865 vapier 1.283 # A temporary hack until portage properly supports DEPENDing on USE
1866     # flags being enabled in packages. This will check to see if the specified
1867     # DEPEND atom was built with the specified list of USE flags. The
1868     # --missing option controls the behavior if called on a package that does
1869     # not actually support the defined USE flags (aka listed in IUSE).
1870     # The default is to abort (call die). The -a and -o flags control
1871     # the requirements of the USE flags. They correspond to "and" and "or"
1872     # logic. So the -a flag means all listed USE flags must be enabled
1873 opfer 1.302 # while the -o flag means at least one of the listed IUSE flags must be
1874 vapier 1.283 # enabled. The --hidden option is really for internal use only as it
1875     # means the USE flag we're checking is hidden expanded, so it won't be found
1876     # in IUSE like normal USE flags.
1877 swegener 1.286 #
1878 vapier 1.283 # Remember that this function isn't terribly intelligent so order of optional
1879     # flags matter.
1880 vapier 1.125 built_with_use() {
1881 vapier 1.275 local hidden="no"
1882     if [[ $1 == "--hidden" ]] ; then
1883     hidden="yes"
1884     shift
1885     fi
1886    
1887 vapier 1.269 local missing_action="die"
1888     if [[ $1 == "--missing" ]] ; then
1889     missing_action=$2
1890     shift ; shift
1891     case ${missing_action} in
1892     true|false|die) ;;
1893     *) die "unknown action '${missing_action}'";;
1894     esac
1895     fi
1896    
1897 vapier 1.130 local opt=$1
1898     [[ ${opt:0:1} = "-" ]] && shift || opt="-a"
1899    
1900     local PKG=$(best_version $1)
1901 vapier 1.247 [[ -z ${PKG} ]] && die "Unable to resolve $1 to an installed package"
1902 vapier 1.130 shift
1903    
1904 vapier 1.213 local USEFILE=${ROOT}/var/db/pkg/${PKG}/USE
1905 vapier 1.249 local IUSEFILE=${ROOT}/var/db/pkg/${PKG}/IUSE
1906 vapier 1.213
1907 cardoe 1.273 # if the IUSE file doesn't exist, the read will error out, we need to handle
1908     # this gracefully
1909 vapier 1.275 if [[ ! -e ${USEFILE} ]] || [[ ! -e ${IUSEFILE} && ${hidden} == "no" ]] ; then
1910 cardoe 1.273 case ${missing_action} in
1911     true) return 0;;
1912     false) return 1;;
1913     die) die "Unable to determine what USE flags $PKG was built with";;
1914     esac
1915     fi
1916    
1917 vapier 1.275 if [[ ${hidden} == "no" ]] ; then
1918 zmedico 1.301 local IUSE_BUILT=( $(<"${IUSEFILE}") )
1919 vapier 1.275 # Don't check USE_EXPAND #147237
1920     local expand
1921     for expand in $(echo ${USE_EXPAND} | tr '[:upper:]' '[:lower:]') ; do
1922     if [[ $1 == ${expand}_* ]] ; then
1923     expand=""
1924     break
1925     fi
1926     done
1927     if [[ -n ${expand} ]] ; then
1928 zmedico 1.301 if ! has $1 ${IUSE_BUILT[@]#[-+]} ; then
1929 vapier 1.275 case ${missing_action} in
1930     true) return 0;;
1931     false) return 1;;
1932     die) die "$PKG does not actually support the $1 USE flag!";;
1933     esac
1934     fi
1935 vapier 1.269 fi
1936 vapier 1.250 fi
1937 vapier 1.249
1938 vapier 1.125 local USE_BUILT=$(<${USEFILE})
1939 vapier 1.130 while [[ $# -gt 0 ]] ; do
1940     if [[ ${opt} = "-o" ]] ; then
1941     has $1 ${USE_BUILT} && return 0
1942     else
1943     has $1 ${USE_BUILT} || return 1
1944     fi
1945 vapier 1.125 shift
1946     done
1947 vapier 1.130 [[ ${opt} = "-a" ]]
1948 vapier 1.125 }
1949 vapier 1.126
1950 vapier 1.289 # @FUNCTION: epunt_cxx
1951 vapier 1.283 # @USAGE: [dir to scan]
1952     # @DESCRIPTION:
1953     # Many configure scripts wrongly bail when a C++ compiler could not be
1954     # detected. If dir is not specified, then it defaults to ${S}.
1955     #
1956     # http://bugs.gentoo.org/73450
1957 vapier 1.126 epunt_cxx() {
1958 vapier 1.127 local dir=$1
1959     [[ -z ${dir} ]] && dir=${S}
1960     ebegin "Removing useless C++ checks"
1961     local f
1962 vapier 1.294 find "${dir}" -name configure | while read f ; do
1963     patch --no-backup-if-mismatch -p0 "${f}" "${PORTDIR}/eclass/ELT-patches/nocxx/nocxx.patch" > /dev/null
1964 vapier 1.127 done
1965     eend 0
1966 vapier 1.126 }
1967 ka0ttic 1.143
1968 vapier 1.283 # @FUNCTION: make_wrapper
1969 wolf31o2 1.295 # @USAGE: <wrapper> <target> [chdir] [libpaths] [installpath]
1970 vapier 1.283 # @DESCRIPTION:
1971     # Create a shell wrapper script named wrapper in installpath
1972     # (defaults to the bindir) to execute target (default of wrapper) by
1973     # first optionally setting LD_LIBRARY_PATH to the colon-delimited
1974     # libpaths followed by optionally changing directory to chdir.
1975 wolf31o2 1.160 make_wrapper() {
1976 wolf31o2 1.164 local wrapper=$1 bin=$2 chdir=$3 libdir=$4 path=$5
1977 wolf31o2 1.160 local tmpwrapper=$(emktemp)
1978 vapier 1.202 # We don't want to quote ${bin} so that people can pass complex
1979     # things as $bin ... "./someprog --args"
1980 wolf31o2 1.160 cat << EOF > "${tmpwrapper}"
1981     #!/bin/sh
1982 vapier 1.201 cd "${chdir:-.}"
1983 vapier 1.210 if [ -n "${libdir}" ] ; then
1984     if [ "\${LD_LIBRARY_PATH+set}" = "set" ] ; then
1985     export LD_LIBRARY_PATH="\${LD_LIBRARY_PATH}:${libdir}"
1986     else
1987     export LD_LIBRARY_PATH="${libdir}"
1988     fi
1989 vapier 1.201 fi
1990 vapier 1.202 exec ${bin} "\$@"
1991 wolf31o2 1.160 EOF
1992     chmod go+rx "${tmpwrapper}"
1993 vapier 1.201 if [[ -n ${path} ]] ; then
1994 vapier 1.283 (
1995 vapier 1.201 exeinto "${path}"
1996 wolf31o2 1.164 newexe "${tmpwrapper}" "${wrapper}"
1997 vapier 1.283 ) || die
1998 wolf31o2 1.164 else
1999 vapier 1.283 newbin "${tmpwrapper}" "${wrapper}" || die
2000 wolf31o2 1.164 fi
2001 wolf31o2 1.160 }
2002 mr_bones_ 1.311
2003 vapier 1.351 # @FUNCTION: path_exists
2004     # @USAGE: [-a|-o] <paths>
2005     # @DESCRIPTION:
2006     # Check if the specified paths exist. Works for all types of paths
2007     # (files/dirs/etc...). The -a and -o flags control the requirements
2008     # of the paths. They correspond to "and" and "or" logic. So the -a
2009     # flag means all the paths must exist while the -o flag means at least
2010     # one of the paths must exist. The default behavior is "and". If no
2011     # paths are specified, then the return value is "false".
2012     path_exists() {
2013     local opt=$1
2014     [[ ${opt} == -[ao] ]] && shift || opt="-a"
2015    
2016     # no paths -> return false
2017     # same behavior as: [[ -e "" ]]
2018     [[ $# -eq 0 ]] && return 1
2019    
2020     local p r=0
2021     for p in "$@" ; do
2022     [[ -e ${p} ]]
2023     : $(( r += $? ))
2024     done
2025    
2026     case ${opt} in
2027     -a) return $(( r != 0 )) ;;
2028     -o) return $(( r == $# )) ;;
2029     esac
2030     }
2031 mgorny 1.364
2032     # @FUNCTION: in_iuse
2033     # @USAGE: <flag>
2034     # @DESCRIPTION:
2035     # Determines whether the given flag is in IUSE. Strips IUSE default prefixes
2036     # as necessary.
2037     #
2038     # Note that this function should not be used in the global scope.
2039     in_iuse() {
2040     debug-print-function ${FUNCNAME} "${@}"
2041     [[ ${#} -eq 1 ]] || die "Invalid args to ${FUNCNAME}()"
2042    
2043     local flag=${1}
2044     local liuse=( ${IUSE} )
2045    
2046     has "${flag}" "${liuse[@]#[+-]}"
2047     }

  ViewVC Help
Powered by ViewVC 1.1.20