Magellan Linux

Annotation of /trunk/mage/usr/lib/mage/mage4.functions.sh

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2724 - (hide annotations) (download) (as text)
Tue Jul 22 14:21:01 2014 UTC (9 years, 9 months ago) by niro
File MIME type: application/x-sh
File size: 81956 byte(s)
-fixed a typo MAGE_FEATURE_CURRENT -> MAGE_FEATURES_CURRENT
1 niro 226 #!/bin/bash
2     # Magellan Linux Installer Functions (mage.functions.sh)
3 niro 2268 # $Id$
4 niro 226
5 niro 1547 COLRED="\033[1;6m\033[31m"
6     COLGREEN="\033[1;6m\033[32m"
7     COLYELLOW="\033[1;6m\033[33m"
8     COLBLUE="\033[1;6m\033[34m"
9     COLMAGENTA="\033[1;6m\033[35m"
10     COLWHITE="\033[1;6m\033[37m"
11     COLGRAY="\033[0;6m\033[37m"
12     COLBOLD="\033[1m"
13     COLDEFAULT="\033[0m"
14    
15     if [[ ${NOCOLORS} = true ]]
16     then
17     COLRED=""
18     COLGREEN=""
19     COLYELLOW=""
20     COLBLUE=""
21     COLMAGENTA=""
22     COLWHITE=""
23     COLGRAY=""
24     COLBOLD=""
25     COLDEFAULT=""
26     fi
27    
28 niro 226 mage_setup()
29     {
30     [ ! -d ${MROOT}${INSTALLDB} ] && \
31     install -d ${MROOT}${INSTALLDB}
32     [ ! -f ${MROOT}${VIRTUALDB_FILE} ] && \
33     touch ${MROOT}${VIRTUALDB_FILE}
34     [ ! -d ${PKGDIR} ] && install -d ${PKGDIR}
35     [ ! -d ${BUILDDIR} ] && install -d ${BUILDDIR}
36     [ ! -d ${MAGEDIR} ] && install -d ${MAGEDIR}
37    
38     return 0
39     }
40    
41 niro 1549 mchecksum()
42     {
43     local i
44     local rundir
45     local file
46     local method
47     local cmd
48     local retval
49 niro 2225 local sum
50     local dest
51 niro 1549
52     # very basic getops
53     for i in $*
54     do
55     case $1 in
56     --rundir|-r) shift; rundir="$1" ;;
57     --file|-f) shift; file="$1" ;;
58     --method|-m) shift; method="$1" ;;
59     esac
60     shift
61     done
62    
63     # sanity checks
64     [[ -z ${rundir} ]] && die "mchecksum(): rundir missing"
65     [[ -z ${file} ]] && die "mchecksum(): file missing"
66     [[ -z ${method} ]] && die "mchecksum(): method missing"
67    
68     case ${method} in
69     md5) cmd="md5sum" ;;
70     sha256) cmd="sha256sum" ;;
71 niro 1625 *) die "mchecksum(): unknown method '${method}'" ;;
72 niro 1549 esac
73    
74     if [[ -d ${rundir} ]]
75     then
76     pushd ${rundir} &> /dev/null
77 niro 2225
78     # all file must be non-zero
79     retval=0
80     while read sum dest
81     do
82 niro 2232 if [ ! -s ${dest} ]
83 niro 2225 then
84     echo "${dest}: file is empty ;("
85     retval=127
86     fi
87     done < ${file}
88     if [[ ${retval} != 127 ]]
89     then
90     # be verbose here
91     ${cmd} -c ${file} #&> /dev/null
92     retval="$?"
93     fi
94    
95 niro 1549 popd &> /dev/null
96     else
97     retval=1
98     fi
99    
100     return "${retval}"
101     }
102    
103 niro 1653 mcheckemptydir()
104     {
105     local dir="$1"
106     local retval=1
107    
108     if [[ ! -d ${dir} ]]
109     then
110     echo "mcheckemptydir(): '${dir}' is not a directory!"
111     retval=3
112     else
113     shopt -s nullglob dotglob
114     files=( ${dir}/* )
115     (( ${#files[*]} )) || retval=0
116     shopt -u nullglob dotglob
117     fi
118    
119     return ${retval}
120     }
121    
122 niro 2156 unpack_package()
123     {
124     local magefile="$1"
125 niro 2271 local pkgname
126     local pkgfile
127 niro 2156 local pkgtype
128     local tar_opts
129    
130 niro 2271 pkgname="$(get_value_from_magefile PKGNAME ${magefile})"
131     pkgfile="${pkgname}.${PKGSUFFIX}"
132 niro 2156 pkgtype="$(get_value_from_magefile PKGTYPE ${magefile})"
133    
134     xtitle "[ Unpacking ${pkg} ]"
135    
136     # abort on virtual pkg
137     if [[ ${pkgtype} = virtual ]]
138     then
139     echo -ne " ${COLBLUE}---${COLDEFAULT}"
140 niro 2271 echo " !unpack virtual ${pkgname} ... "
141 niro 2156 continue
142     fi
143    
144     # abort on sources pkg
145     if [[ ${pkgtype} = sources ]]
146     then
147     echo -ne " ${COLBLUE}---${COLDEFAULT}"
148 niro 2271 echo " !unpack sources ${pkgname} ... "
149 niro 2156 continue
150     fi
151    
152     # busybox?
153     if need_busybox_support tar
154     then
155     tar_opts="xjf"
156     else
157     tar_opts="xjmf"
158     fi
159    
160 niro 2271 echo -e " ${COLBLUE}***${COLDEFAULT} unpacking ${pkgfile} ... "
161     tar ${tar_opts} ${PKGDIR}/${pkgfile} -C ${BUILDDIR} || die "Unpacking package ${pkgfile}"
162 niro 2156 }
163    
164 niro 226 unpack_packages()
165     {
166     local list="$@"
167     local magefile
168     local count_current
169     local count_total
170 niro 1273 local tar_opts
171 niro 226
172     # get count of total packages
173     declare -i count_current=0
174     declare -i count_total=0
175    
176     for i in ${list}; do (( count_total++ )); done
177    
178     for magefile in ${list}
179     do
180 niro 2156 unpack_package "${magefile}"
181 niro 226 (( count_current++ ))
182     done
183    
184     # add a crlf for a better view
185     if [ ${count_total} -gt 1 ]; then echo; fi
186     }
187    
188    
189     # fix_mtime path/to/$mtime/reffile $pathto/file
190     # creates a given reference file and fixes given file
191     # returns new mtime
192     fix_mtime()
193     {
194     local reference="$1"
195     local pathto="$2"
196     local mtime
197    
198     mtime=$(stat -c %Y "${reference}")
199     touch \
200     --no-create \
201 niro 1690 --no-dereference \
202 niro 226 --time=mtime \
203 niro 1690 --reference="${reference}" \
204 niro 226 "${pathto}"
205    
206     echo "${mtime}"
207     }
208    
209     # fix_descriptor pkgname/.dir "foo1" "foo2"
210     fix_descriptor()
211     {
212     local descriptor="$1"
213     local output
214     local i
215     shift
216    
217     for i in $@
218     do
219     if [[ -z ${output} ]]
220     then
221     output="${i}"
222     else
223     output="${output}§${i}"
224     fi
225     done
226    
227     echo "${output}" >> ${BUILDDIR}/${descriptor}_fixed
228     }
229    
230     ###################################################
231     # function install_direcories #
232     # install_direcories $PKGNAME #
233     ###################################################
234     install_directories()
235     {
236     local pkgname="$1"
237     local pathto
238     local posix
239     local user
240     local group
241     local IFS
242    
243     # sanity checks; abort if not given
244     [ -z "${pkgname}" ] && die "install_directories() \$pkgname not given."
245    
246     # check needed global vars
247     [ -z "${BUILDDIR}" ] && die "install_directories() \$BUILDDIR not set."
248    
249     [ ! -f ${BUILDDIR}/${pkgname}/.dirs ] && die "install_directories() .dirs not found"
250    
251     # sets fieldseperator to "§" instead of " "
252     IFS=§
253    
254     while read pathto posix user group
255     do
256     [ -z "${pathto}" ] && continue
257 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> DIR: ${MROOT}${pathto}"
258 niro 226
259     # monitors /etc/env.d -> env-rebuild
260     [[ ${pathto} = /etc/env.d ]] && export MAGE_ENV_REBUILD=true
261    
262     # monitors /usr/share/info -> info-rebuild
263     [[ ${pathto} = /usr/share/info ]] && export MAGE_INFO_REBUILD=true
264    
265     install -m "${posix}" -o "${user}" -g "${group}" -d "${MROOT}${pathto}"
266     done < ${BUILDDIR}/${pkgname}/.dirs
267    
268     # very important: unsetting the '§' fieldseperator
269     IFS=$'\n'
270     }
271    
272    
273     ###################################################
274     # function install_files #
275     # install_files $PKGNAME #
276     ###################################################
277     install_files()
278     {
279    
280     local pkgname="$1"
281     local pathto
282     local posix
283     local user
284     local group
285     local mtime
286     local md5sum
287    
288     local retval
289     local counter
290     local filename
291     local dest_dirname
292     local dest_protected
293     local IFS
294    
295     # sanity checks; abort if not given
296     [ -z "${pkgname}" ] && die "install_files() \$pkgname not given."
297    
298     # check needed global vars
299     [ -z "${BUILDDIR}" ] && die "install_files() \$BUILDDIR not set."
300    
301     [ ! -f ${BUILDDIR}/${pkgname}/.files ] && die "install_files() .files not found"
302    
303     # delete old files
304     [ -f ${BUILDDIR}/${pkgname}/.files_fixed ] && rm ${BUILDDIR}/${pkgname}/.files_fixed
305    
306     # sets fieldseperator to "§" instead of " "
307     IFS=§
308    
309     while read pathto posix user group mtime md5sum
310     do
311     [ -z "${pathto}" ] && continue
312    
313     # final destination dir of file ${pathto}
314     dest_dirname="$(dirname "${MROOT}${pathto}")"
315    
316     ### small hotfix fix ###
317     [ ! -d "${dest_dirname}" ] && install -d "${dest_dirname}"
318    
319     # check if the file is config_protected
320     # ${MROOT} will automatically added if set !!
321     is_config_protected "${pathto}"
322     retval="$?"
323    
324 niro 942 # 0 - not protected #
325     # 1 - error #
326     # 2 - protected #
327     # 3 - protected but masked #
328     # 4 - protected but ignored #
329 niro 226
330     case ${retval} in
331     # file is not protected - (over)write it
332     0|3)
333 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> FILE: ${MROOT}${pathto}"
334 niro 226 install -m "${posix}" -o "${user}" -g "${group}" \
335     ${BUILDDIR}/${pkgname}/binfiles/"${pathto}" \
336     "${MROOT}${pathto}"
337    
338     # fix mtime and db
339     fix_descriptor ${pkgname}/.files \
340     "${pathto}" \
341     "${posix}" \
342     "${user}" \
343     "${group}" \
344     "$(fix_mtime "${BUILDDIR}/${pkgname}"/.mtime \
345 niro 1289 "${MROOT}${pathto}")" \
346 niro 226 "${md5sum}"
347     ;;
348    
349     # file is protected, write backup file
350     2)
351 niro 1584 if mqueryfeature "verbose"
352 niro 226 then
353     echo -en "${COLRED}"
354     echo -n "! prot "
355     echo -en "${COLDEFAULT}"
356     echo " === FILE: ${MROOT}${pathto}"
357     fi
358     filename="$(basename "${pathto}")"
359     counter=$(count_protected_files "${pathto}")
360     dest_protected="${dest_dirname}/._cfg${counter}_${filename}"
361     install -m "${posix}" -o "${user}" -g "${group}" \
362     ${BUILDDIR}/${pkgname}/binfiles/"${pathto}" \
363     "${dest_protected}"
364    
365     # fix mtime and db
366     fix_descriptor ${pkgname}/.files \
367     "${pathto}" \
368     "${posix}" \
369     "${user}" \
370     "${group}" \
371     "$(fix_mtime "${BUILDDIR}/${pkgname}"/.mtime \
372 niro 1289 "${dest_protected}")" \
373 niro 226 "${md5sum}"
374    
375     # update global MAGE_PROTECT_COUNTER
376     (( MAGE_PROTECT_COUNTER++ ))
377     export MAGE_PROTECT_COUNTER
378     ;;
379 niro 942
380     # file is protected but ignored, delete the update/do nothing
381     4)
382 niro 1584 if mqueryfeature "verbose"
383 niro 942 then
384     echo -en "${COLRED}"
385     echo -n "! ignr "
386     echo -en "${COLDEFAULT}"
387     echo " === FILE: ${MROOT}${pathto}"
388     fi
389 niro 1289 # simply do nothing here - only fix mtime
390     fix_descriptor ${pkgname}/.files \
391     "${pathto}" \
392     "${posix}" \
393     "${user}" \
394     "${group}" \
395     "$(fix_mtime "${BUILDDIR}/${pkgname}"/.mtime \
396     "${MROOT}${pathto}")" \
397     "${md5sum}"
398 niro 942 ;;
399 niro 226 esac
400     done < ${BUILDDIR}/${pkgname}/.files
401    
402     # now copy the fixed file over the old one
403     [ -f ${BUILDDIR}/${pkgname}/.files_fixed ] && \
404     cp ${BUILDDIR}/${pkgname}/.files{_fixed,}
405    
406     # very important: unsetting the '§' fieldseperator
407     IFS=$'\n'
408     }
409    
410    
411     ###################################################
412     # function install_symlinks #
413     # install_symlinks $PKGNAME #
414     ###################################################
415     install_symlinks()
416     {
417     local pkgname="$1"
418     local pathto
419     local posix
420     local link
421     local mtime
422     local IFS
423    
424     # sanity checks; abort if not given
425     [ -z "${pkgname}" ] && die "install_symlinks() \$pkgname not given."
426    
427     # check needed global vars
428     [ -z "${BUILDDIR}" ] && die "install_symlinks() \$BUILDDIR not set."
429    
430     [ ! -f ${BUILDDIR}/${pkgname}/.symlinks ] && die "install_symlinks() .symlinks not found"
431    
432     # delete old files
433     [ -f ${BUILDDIR}/${pkgname}/.symlinks_fixed ] && rm ${BUILDDIR}/${pkgname}/.symlinks_fixed
434    
435     # sets fieldseperator to "§" instead of " "
436     IFS=§
437    
438     while read pathto posix link mtime
439     do
440     [ -z "${pathto}" ] && continue
441 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> LINK: ${MROOT}${pathto}"
442 niro 226
443     ln -snf "${link}" "${MROOT}${pathto}"
444    
445 niro 1690 # fix mtime and db
446     fix_descriptor ${pkgname}/.symlinks \
447     "${pathto}" \
448     "${posix}" \
449     "${link}" \
450     "$(fix_mtime "${BUILDDIR}/${pkgname}"/.mtime \
451     "${MROOT}${pathto}")"
452 niro 226
453     done < ${BUILDDIR}/${pkgname}/.symlinks
454    
455 niro 858 # # now copy the fixed file over the old one
456     # [ -f ${BUILDDIR}/${pkgname}/.symlinks_fixed ] && \
457     # cp -f ${BUILDDIR}/${pkgname}/.symlinks{_fixed,}
458 niro 226
459     # very important: unsetting the '§' fieldseperator
460     IFS=$'\n'
461     }
462    
463    
464     ###################################################
465     # function install_blockdevices #
466     # install_blockdevices $PKGNAME #
467     ###################################################
468     install_blockdevices()
469     {
470     local pkgname="$1"
471     local pathto
472     local posix
473 niro 1209 local user
474     local group
475 niro 226 local IFS
476    
477     # sanity checks; abort if not given
478     [ -z "${pkgname}" ] && die "install_blockdevices() \$pkgname not given."
479    
480     # check needed global vars
481     [ -z "${BUILDDIR}" ] && die "install_blockdevices() \$BUILDDIR not set."
482    
483     [ ! -f ${BUILDDIR}/${pkgname}/.pipes ] && die "install_blockdevices() .pipes not found"
484    
485     # sets fieldseperator to "§" instead of " "
486     IFS=§
487    
488 niro 1271 while read pathto posix major minor user group
489 niro 226 do
490     [ -z "${pathto}" ] && continue
491 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> PIPE: ${MROOT}${pathto}"
492 niro 226
493 niro 1271 mknod -m "${posix}" "${MROOT}${pathto}"
494 niro 1211 # make it optional atm !!
495     if [[ ! -z ${user} ]] && [[ ! -z ${group} ]]
496     then
497 niro 1271 chown "${user}:${group}" "${MROOT}${pathto}" b "${major}" "${minor}"
498 niro 1211 fi
499 niro 226 done < ${BUILDDIR}/${pkgname}/.pipes
500    
501     # very important: unsetting the '§' fieldseperator
502     IFS=$'\n'
503     }
504    
505    
506     ###################################################
507     # function install_characterdevices #
508     # install_characterdevices $PKGNAME #
509     ###################################################
510     install_characterdevices()
511     {
512     local pkgname="$1"
513     local pathto
514     local posix
515 niro 312 local major
516     local minor
517 niro 1209 local user
518     local group
519 niro 226 local IFS
520    
521     # sanity checks; abort if not given
522     [ -z "${pkgname}" ] && die "install_characterdevices() \$pkgname not given."
523    
524     # check needed global vars
525     [ -z "${BUILDDIR}" ] && die "install_characterdevices() \$BUILDDIR not set."
526    
527     [ ! -f ${BUILDDIR}/${pkgname}/.char ] && die "install_characterdevices() .char not found"
528    
529     # sets fieldseperator to "§" instead of " "
530     IFS=§
531    
532 niro 1209 while read pathto posix major minor user group
533 niro 226 do
534     [ -z "${pathto}" ] && continue
535 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> CHAR: ${MROOT}${pathto}"
536 niro 226
537 niro 1271 mknod -m ${posix} "${MROOT}${pathto}" b "${major}" "${minor}"
538 niro 1211
539     # make it optional atm !!
540     if [[ ! -z ${user} ]] && [[ ! -z ${group} ]]
541     then
542     chown "${user}:${group}" "${MROOT}${pathto}"
543     fi
544 niro 226 done < ${BUILDDIR}/${pkgname}/.char
545    
546     # very important: unsetting the '§' fieldseperator
547     IFS=$'\n'
548     }
549    
550 niro 1209 ###################################################
551     # function install_fifos #
552     # install_fifos $PKGNAME #
553     ###################################################
554     install_fifos()
555     {
556     local pkgname="$1"
557     local pathto
558     local posix
559     local user
560     local group
561     local IFS
562 niro 226
563 niro 1209 # sanity checks; abort if not given
564     [ -z "${pkgname}" ] && die "install_fifos() \$pkgname not given."
565    
566     # check needed global vars
567     [ -z "${BUILDDIR}" ] && die "install_fifos() \$BUILDDIR not set."
568    
569 niro 1211 # make it optional atm !!
570     #[ ! -f ${BUILDDIR}/${pkgname}/.fifo ] && die "install_fifos() .fifo not found"
571     [ ! -f ${BUILDDIR}/${pkgname}/.fifo ] && return
572 niro 1209
573     # sets fieldseperator to "§" instead of " "
574     IFS=§
575    
576     while read pathto posix user group
577     do
578     [ -z "${pathto}" ] && continue
579 niro 1584 mqueryfeature "verbose" && echo -e "\t>>> FIFO: ${MROOT}${pathto}"
580 niro 1209
581     mkfifo -m "${posix}" "${MROOT}${pathto}"
582     chown "${user}:${group}" "${MROOT}${pathto}"
583     done < ${BUILDDIR}/${pkgname}/.fifo
584    
585     # very important: unsetting the '§' fieldseperator
586     IFS=$'\n'
587     }
588    
589    
590 niro 226 ###################################################
591     # function build_doinstall #
592     # build_doinstall $PKGNAME #
593 niro 1209 # NOTE: this is an wrapper to install packages #
594 niro 226 ###################################################
595     build_doinstall()
596     {
597     local pkgname="$1"
598    
599     # sanity checks; abort if not given
600     [ -z "${pkgname}" ] && die "build_doinstall() \$pkgname not given."
601 niro 1289
602 niro 226 # this is only a wrapper
603    
604     # NOTE:
605     # !! we use § as field seperator !!
606     # doing so prevent us to get errors by filenames with spaces
607    
608     # create a new mtime reference file
609     touch ${BUILDDIR}/${pkgname}/.mtime
610    
611     install_directories ${pkgname} || die "install directories ${pkgname}"
612     install_files ${pkgname} || die "install files ${pkgname}"
613     install_symlinks ${pkgname} || die "install symlinks ${pkgname}"
614     install_blockdevices ${pkgname} || die "install blockdevices ${pkgname}"
615     install_characterdevices ${pkgname} || die "install chardevices ${pkgname}"
616 niro 1209 install_fifos ${pkgname} || die "install fifos ${pkgname}"
617 niro 226 }
618    
619    
620     ###################################################
621     # function install_database_entry #
622     # install_database_entry $PKGNAME $PKGTYPE #
623     # PKGTYPE can be "virtual", "sources" or nothing #
624     ###################################################
625     install_database_entry()
626     {
627     local pcat
628     local pname
629     local pver
630     local pbuild
631     local pkgtype
632     local pkgname
633     local magefile
634     local dbrecorddir
635     local provide
636 niro 273 local i
637 niro 226
638     # very basic getops
639     for i in $*
640     do
641     case $1 in
642     --pcat|-c) shift; pcat="$1" ;;
643     --pname|-n) shift; pname="$1" ;;
644     --pver|-v) shift; pver="$1" ;;
645     --pbuild|-b) shift; pbuild="$1" ;;
646     --pkgname|-a) shift; pkgname="$1" ;;
647     --pkgtype|-t) shift; pkgtype="$1" ;;
648     esac
649     shift
650     done
651    
652     # sanity checks; abort if not given
653     [ -z "${pcat}" ] && die "install_database_entry() \$pcat not given."
654     [ -z "${pname}" ] && die "install_database_entry() \$pname not given."
655     [ -z "${pver}" ] && die "install_database_entry() \$pver not given."
656     [ -z "${pbuild}" ] && die "install_database_entry() \$pbuild not given."
657     [ -z "${pkgname}" ] && die "install_database_entry() \$pkgname not given."
658    
659     # check needed global vars
660     [ -z "${MAGEDIR}" ] && die "install_database_entry() \$MAGEDIR not set."
661     [ -z "${INSTALLDB}" ] && die "install_database_entry() \$INSTALLDB not set."
662    
663     # set needed vars
664     magefile="${MAGEDIR}/${pcat}/${pname}/${pname}-${pver}-${pbuild}.mage"
665     dbrecorddir="${MROOT}${INSTALLDB}/${pcat}/${pname}-${pver}-${pbuild}"
666    
667     # abort if mage file not exists
668     [ ! -f ${magefile} ] && die "install_database_entry() ${magefile} not exist."
669    
670     # add package to database
671     install -d ${dbrecorddir}
672    
673     # install mage-file to database
674     install -m 0644 -o root -g root ${magefile} ${dbrecorddir}
675    
676     # create fake file descriptors
677     # used by virtual and source packages
678 niro 1209 for i in .dirs .symlinks .files .pipes .char .fifo
679 niro 226 do
680     touch ${dbrecorddir}/${i}
681     done
682    
683     # put the category to database
684     echo ${pcat} > ${dbrecorddir}/.categorie
685    
686     # now install PKGTYPE specific files
687     case ${pkgtype} in
688     virtual) touch ${dbrecorddir}/.virtual ;;
689     sources) touch ${dbrecorddir}/.sources ;;
690     *)
691     # !move! .mtime to database (only mv modifies not the mtime!!)
692     mv ${BUILDDIR}/${pkgname}/.mtime ${dbrecorddir}/.mtime
693    
694     # normal packages needs these files
695     local i
696 niro 1209 for i in .char .dirs .files .pipes .symlinks .fifo
697 niro 226 do
698 niro 1214 # make .fifo optional atm
699     if [[ -f ${BUILDDIR}/${pkgname}/${i} ]]
700     then
701     install -m 0644 ${BUILDDIR}/${pkgname}/${i} ${dbrecorddir}/${i}
702     fi
703 niro 226 done
704     ;;
705     esac
706    
707     # last but not least register virtuals
708     provide="$(get_value_from_magefile PROVIDE ${magefile})"
709     if [ -n "${provide}" ]
710     then
711 niro 273 for i in ${provide}
712     do
713     virtuals_add "${i}" "${pcat}/${pname}"
714     done
715 niro 226 fi
716     }
717    
718    
719     ###################################################
720     # function remove_database_entry #
721     # remove_database_entry $PKGNAME $PKGTYPE #
722     # PKGTYPE can be "virtual", "sources" or nothing #
723     ###################################################
724     remove_database_entry()
725     {
726     local pcat
727     local pname
728     local pver
729     local pbuild
730     local magefile
731     local dbrecorddir
732     local provide
733 niro 273 local i
734 niro 226
735     # very basic getops
736     for i in $*
737     do
738     case $1 in
739     --pcat|-c) shift; pcat="$1" ;;
740     --pname|-n) shift; pname="$1" ;;
741     --pver|-v) shift; pver="$1" ;;
742     --pbuild|-b) shift; pbuild="$1" ;;
743     esac
744     shift
745     done
746    
747     # sanity checks; abort if not given
748     [ -z "${pcat}" ] && die "remove_database_entry() \$pcat not given."
749     [ -z "${pname}" ] && die "remove_database_entry() \$pname not given."
750     [ -z "${pver}" ] && die "remove_database_entry() \$pver not given."
751     [ -z "${pbuild}" ] && die "remove_database_entry() \$pbuild not given."
752    
753     # check needed global vars
754     [ -z "${INSTALLDB}" ] && die "remove_database_entry() \$INSTALLDB not set."
755    
756     # set needed vars
757     magefile="${MROOT}${INSTALLDB}/${pcat}/${pname}-${pver}-${pbuild}/${pname}-${pver}-${pbuild}.mage"
758     dbrecorddir="${MROOT}${INSTALLDB}/${pcat}/${pname}-${pver}-${pbuild}"
759    
760     # abort if mage file not exists
761     [ ! -f ${magefile} ] && die "remove_database_entry() ${magefile} not exist."
762    
763 niro 294 # remove virtuals only if no other exist
764     if [[ $(count_installed_pkgs --pcat ${pcat} --pname ${pname}) -le 1 ]]
765 niro 226 then
766 niro 294 # first unregister virtuals
767     provide="$(get_value_from_magefile PROVIDE ${magefile})"
768     if [ -n "${provide}" ]
769     then
770     for i in ${provide}
771     do
772     virtuals_del "${i}" "${pcat}/${pname}"
773     done
774     fi
775 niro 226 fi
776    
777     # removes database entry
778     if [ -d ${dbrecorddir} ]
779     then
780     rm -rf ${dbrecorddir}
781     fi
782     }
783    
784 niro 294 # get the number of installed packages
785     count_installed_pkgs()
786     {
787     local pcat
788     local pname
789     local pkg
790     local i
791 niro 226
792 niro 294 # very basic getops
793     for i in $*
794     do
795     case $1 in
796     --pcat|-c) shift; pcat="$1" ;;
797     --pname|-n) shift; pname="$1" ;;
798     esac
799     shift
800     done
801    
802     # sanity checks; abort if not given
803     [ -z "${pcat}" ] && die "pkg_count() \$pcat not given."
804     [ -z "${pname}" ] && die "pkg_count() \$pname not given."
805    
806     declare -i i=0
807     for pkg in $(get_uninstall_candidates --pcat ${pcat} --pname ${pname})
808     do
809     (( i++ ))
810     #echo "$i ${pkg}"
811     done
812    
813     # return the value
814     echo "${i}"
815     }
816    
817    
818 niro 226 ###################################################
819     # function compare_mtime #
820     # compare_mtime $pcat/$PKGNAME /path/to/file #
821     # #
822     # returns: #
823     # 0=delete me #
824     # 1=keep me #
825     # #
826     # compares mtime of given files in packages #
827     ###################################################
828     compare_mtime()
829     {
830     local pfull="$1"
831     local pathto="$2"
832     local mtime
833     local pcat
834     local x
835    
836     mtime="$(stat -c %Y ${MROOT}${INSTALLDB}/${pfull}/.mtime)"
837    
838 niro 1690 # no extra handlink for symlinks anymore as fix_mtime
839     # uses --no-dereference, compare directly
840     x=$(stat -c %Y "${MROOT}${pathto}")
841 niro 226
842     [[ ${mtime} = ${x} ]] && return 0
843    
844     # echo "keep me : ${pathto}"
845     return 1
846     }
847    
848    
849     ###################################################
850     # function remove_symlinks #
851     # remove_symlinks $PKGNAME #
852     ###################################################
853     remove_symlinks()
854     {
855     local pathto
856     local posix
857     local link
858     local mtime
859     local IFS
860     local retval
861     local pcat
862     local pname
863     local pver
864     local pbuild
865     local i
866     local pfull
867    
868     IFS=$'\n'
869    
870     # very basic getops
871     for i in $*
872     do
873     case $1 in
874     --pcat|-c) shift; pcat="$1" ;;
875     --pname|-n) shift; pname="$1" ;;
876     --pver|-v) shift; pver="$1" ;;
877     --pbuild|-b) shift; pbuild="$1" ;;
878     esac
879     shift
880     done
881    
882     # sanity checks; abort if not given
883     [ -z "${pcat}" ] && die "remove_symlinks() \$pcat not given."
884     [ -z "${pname}" ] && die "remove_symlinks() \$pname not given."
885     [ -z "${pver}" ] && die "remove_symlinks() \$pver not given."
886     [ -z "${pbuild}" ] && die "remove_symlinks() \$pbuild not given."
887     pfull="${pcat}/${pname}-${pver}-${pbuild}"
888    
889     # check needed global vars
890     [ -z "${BUILDDIR}" ] && die "remove_symlinks() \$BUILDDIR not set."
891    
892     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.symlinks ] && die "remove_symlinks() .symlinks not found"
893    
894     # sets fieldseperator to "§" instead of " "
895     IFS=§
896    
897     while read pathto posix link mtime
898     do
899     [ -z "${pathto}" ] && continue
900     if [ ! -L "${MROOT}${pathto}" ]
901     then
902 niro 1584 mqueryfeature "verbose" && \
903 niro 226 echo -e "${COLRED}! exist${COLDEFAULT} === LINK: ${MROOT}${pathto}"
904     continue
905     fi
906    
907     # *no* ${MROOT}, will be set internal
908     compare_mtime "${pfull}" "${pathto}"
909     retval=$?
910     # 0=delete me #
911     # 1=keep me #
912     case ${retval} in
913     0)
914 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< LINK: ${MROOT}${pathto}"
915 niro 226 rm "${MROOT}${pathto}"
916     ;;
917    
918     1)
919 niro 1584 mqueryfeature "verbose" && \
920 niro 226 echo -e "${COLRED}! mtime${COLDEFAULT} === LINK: ${MROOT}${pathto}"
921     ;;
922     esac
923     done < ${MROOT}${INSTALLDB}/${pfull}/.symlinks
924    
925     # very important: unsetting the '§' fieldseperator
926     IFS=$'\n'
927     }
928    
929    
930     ###################################################
931     # function remove_files #
932     # remove_files $PKGNAME #
933     ###################################################
934     remove_files()
935     {
936     local pathto
937     local posix
938     local user
939     local group
940     local mtime
941     local md5sum
942     local IFS
943     local retval
944     local pcat
945     local pname
946     local pver
947     local pbuild
948     local i
949     local pfull
950    
951     IFS=$'\n'
952    
953     # very basic getops
954     for i in $*
955     do
956     case $1 in
957     --pcat|-c) shift; pcat="$1" ;;
958     --pname|-n) shift; pname="$1" ;;
959     --pver|-v) shift; pver="$1" ;;
960     --pbuild|-b) shift; pbuild="$1" ;;
961     esac
962     shift
963     done
964    
965     # sanity checks; abort if not given
966 niro 1209 [ -z "${pcat}" ] && die "remove_files() \$pcat not given."
967     [ -z "${pname}" ] && die "remove_files() \$pname not given."
968     [ -z "${pver}" ] && die "remove_files() \$pver not given."
969     [ -z "${pbuild}" ] && die "remove_files() \$pbuild not given."
970 niro 226 pfull="${pcat}/${pname}-${pver}-${pbuild}"
971    
972     # check needed global vars
973     [ -z "${BUILDDIR}" ] && die "remove_files() \$BUILDDIR not set."
974    
975     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.files ] && die "remove_files() .files not found"
976    
977     # sets fieldseperator to "§" instead of " "
978     IFS=§
979    
980     while read pathto posix user group mtime md5sum
981     do
982     [ -z "${pathto}" ] && continue
983    
984 niro 240 if [ ! -e "${MROOT}${pathto}" ]
985 niro 226 then
986 niro 1584 mqueryfeature "verbose" && \
987 niro 226 echo -e "${COLRED}! exist${COLDEFAULT} === FILE: ${MROOT}${pathto}"
988     continue
989     fi
990    
991     # *no* ${MROOT}, will be set internal
992     compare_mtime "${pfull}" "${pathto}"
993     retval=$?
994     # 0=delete me #
995     # 1=keep me #
996     case ${retval} in
997     0)
998 niro 280 # check if the file is config_protected
999     # ${MROOT} will automatically added if set !!
1000     is_config_protected "${pathto}"
1001     retval="$?"
1002    
1003 niro 942 # 0 - not protected #
1004     # 1 - error #
1005     # 2 - protected #
1006     # 3 - protected but masked #
1007     # 4 - protected but ignored #
1008 niro 280
1009     case ${retval} in
1010     # file is not protected - delete it
1011     0|3)
1012 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< FILE: ${MROOT}${pathto}"
1013 niro 280 rm "${MROOT}${pathto}"
1014     ;;
1015    
1016     # file is protected, do not delete
1017     2)
1018 niro 1584 if mqueryfeature "verbose"
1019 niro 280 then
1020     echo -en "${COLRED}"
1021     echo -n "! prot "
1022     echo -en "${COLDEFAULT}"
1023     echo " === FILE: ${MROOT}${pathto}"
1024     fi
1025     ;;
1026 niro 942
1027     # file is protected but ignored, delete the update/do nothing
1028     4)
1029 niro 1584 if mqueryfeature "verbose"
1030 niro 942 then
1031     echo -en "${COLRED}"
1032     echo -n "! ignr "
1033     echo -en "${COLDEFAULT}"
1034     echo " === FILE: ${MROOT}${pathto}"
1035     fi
1036     # simply do nothing here
1037     ;;
1038 niro 280 esac
1039 niro 226 ;;
1040     1)
1041 niro 1584 mqueryfeature "verbose" && \
1042 niro 226 echo -e "${COLRED}! mtime${COLDEFAULT} === FILE: ${MROOT}${pathto}"
1043     ;;
1044     esac
1045     done < ${MROOT}${INSTALLDB}/${pfull}/.files
1046    
1047     # very important: unsetting the '§' fieldseperator
1048     IFS=$'\n'
1049     }
1050    
1051    
1052     ###################################################
1053     # function remove_blockdevices #
1054     # remove_blockdevices $PKGNAME #
1055     ###################################################
1056     remove_blockdevices()
1057     {
1058     local pathto
1059     local posix
1060 niro 1209 local user
1061     local group
1062 niro 226 local IFS
1063     local pcat
1064     local pname
1065     local pver
1066     local pbuild
1067     local i
1068     local pfull
1069    
1070     IFS=$'\n'
1071    
1072     # very basic getops
1073     for i in $*
1074     do
1075     case $1 in
1076     --pcat|-c) shift; pcat="$1" ;;
1077     --pname|-n) shift; pname="$1" ;;
1078     --pver|-v) shift; pver="$1" ;;
1079     --pbuild|-b) shift; pbuild="$1" ;;
1080     esac
1081     shift
1082     done
1083    
1084     # sanity checks; abort if not given
1085 niro 1209 [ -z "${pcat}" ] && die "remove_blockdevices() \$pcat not given."
1086     [ -z "${pname}" ] && die "remove_blockdevices() \$pname not given."
1087     [ -z "${pver}" ] && die "remove_blockdevices() \$pver not given."
1088     [ -z "${pbuild}" ] && die "remove_blockdevices() \$pbuild not given."
1089 niro 226 pfull="${pcat}/${pname}-${pver}-${pbuild}"
1090    
1091     # check needed global vars
1092     [ -z "${BUILDDIR}" ] && die "remove_blockdevices() \$BUILDDIR not set."
1093    
1094     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.pipes ] && die "remove_blockdevices() .pipes not found"
1095    
1096     # sets fieldseperator to "§" instead of " "
1097     IFS=§
1098    
1099 niro 1209 while read pathto posix user group
1100 niro 226 do
1101     [ -z "${pathto}" ] && continue
1102    
1103 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< PIPE: ${MROOT}${pathto}"
1104 niro 226 rm "${MROOT}${pathto}"
1105     done < ${MROOT}${INSTALLDB}/${pfull}/.pipes
1106    
1107     # very important: unsetting the '§' fieldseperator
1108     IFS=$'\n'
1109     }
1110    
1111    
1112     ###################################################
1113     # function remove_characterdevices #
1114     # remove_characterdevices $PKGNAME #
1115     ###################################################
1116     remove_characterdevices()
1117     {
1118     local pathto
1119     local posix
1120 niro 1209 local user
1121     local group
1122 niro 226 local IFS
1123     local pcat
1124     local pname
1125     local pver
1126     local pbuild
1127     local i
1128     local pfull
1129    
1130     IFS=$'\n'
1131    
1132     # very basic getops
1133     for i in $*
1134     do
1135     case $1 in
1136     --pcat|-c) shift; pcat="$1" ;;
1137     --pname|-n) shift; pname="$1" ;;
1138     --pver|-v) shift; pver="$1" ;;
1139     --pbuild|-b) shift; pbuild="$1" ;;
1140     esac
1141     shift
1142     done
1143    
1144     # sanity checks; abort if not given
1145 niro 1209 [ -z "${pcat}" ] && die "remove_characterdevices() \$pcat not given."
1146     [ -z "${pname}" ] && die "remove_characterdevices() \$pname not given."
1147     [ -z "${pver}" ] && die "remove_characterdevices() \$pver not given."
1148     [ -z "${pbuild}" ] && die "remove_characterdevices() \$pbuild not given."
1149 niro 226 pfull="${pcat}/${pname}-${pver}-${pbuild}"
1150    
1151     # check needed global vars
1152     [ -z "${BUILDDIR}" ] && die "remove_characterdevices() \$BUILDDIR not set."
1153    
1154     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.char ] && die "remove_characterdevices() .char not found"
1155    
1156     # sets fieldseperator to "§" instead of " "
1157     IFS=§
1158    
1159 niro 1209 while read pathto posix user group
1160 niro 226 do
1161     [ -z "${pathto}" ] && continue
1162    
1163 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< CHAR: ${MROOT}${pathto}"
1164 niro 226 rm "${MROOT}${pathto}"
1165     done < ${MROOT}${INSTALLDB}/${pfull}/.char
1166    
1167     # very important: unsetting the '§' fieldseperator
1168     IFS=$'\n'
1169     }
1170    
1171    
1172     ###################################################
1173 niro 1209 # function remove_fifos #
1174     # remove_fifos $PKGNAME #
1175     ###################################################
1176     remove_fifos()
1177     {
1178     local pathto
1179     local posix
1180     local user
1181     local group
1182     local IFS
1183     local pcat
1184     local pname
1185     local pver
1186     local pbuild
1187     local i
1188     local pfull
1189    
1190     IFS=$'\n'
1191    
1192     # very basic getops
1193     for i in $*
1194     do
1195     case $1 in
1196     --pcat|-c) shift; pcat="$1" ;;
1197     --pname|-n) shift; pname="$1" ;;
1198     --pver|-v) shift; pver="$1" ;;
1199     --pbuild|-b) shift; pbuild="$1" ;;
1200     esac
1201     shift
1202     done
1203    
1204     # sanity checks; abort if not given
1205     [ -z "${pcat}" ] && die "remove_fifos() \$pcat not given."
1206     [ -z "${pname}" ] && die "remove_fifos() \$pname not given."
1207     [ -z "${pver}" ] && die "remove_fifos() \$pver not given."
1208     [ -z "${pbuild}" ] && die "remove_fifos() \$pbuild not given."
1209     pfull="${pcat}/${pname}-${pver}-${pbuild}"
1210    
1211     # check needed global vars
1212     [ -z "${BUILDDIR}" ] && die "remove_fifos() \$BUILDDIR not set."
1213    
1214 niro 1211 # make it optional atm !!
1215     #[ ! -f ${MROOT}${INSTALLDB}/${pfull}/.fifo ] && die "remove_fifos() .fifo not found"
1216     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.fifo ] && return
1217 niro 1209
1218     # sets fieldseperator to "§" instead of " "
1219     IFS=§
1220    
1221     while read pathto posix user group
1222     do
1223     [ -z "${pathto}" ] && continue
1224    
1225 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< FIFO: ${MROOT}${pathto}"
1226 niro 1209 rm "${MROOT}${pathto}"
1227     done < ${MROOT}${INSTALLDB}/${pfull}/.fifo
1228    
1229     # very important: unsetting the '§' fieldseperator
1230     IFS=$'\n'
1231     }
1232    
1233    
1234     ###################################################
1235 niro 226 # function remove_direcories #
1236     # remove_direcories $PKGNAME #
1237     ###################################################
1238     remove_directories()
1239     {
1240     local pathto
1241     local posix
1242     local IFS
1243     local pcat
1244     local pname
1245     local pver
1246     local pbuild
1247     local i
1248     local pfull
1249    
1250     IFS=$'\n'
1251    
1252     # very basic getops
1253     for i in $*
1254     do
1255     case $1 in
1256     --pcat|-c) shift; pcat="$1" ;;
1257     --pname|-n) shift; pname="$1" ;;
1258     --pver|-v) shift; pver="$1" ;;
1259     --pbuild|-b) shift; pbuild="$1" ;;
1260     esac
1261     shift
1262     done
1263    
1264     # sanity checks; abort if not given
1265 niro 1209 [ -z "${pcat}" ] && die "remove_directories() \$pcat not given."
1266     [ -z "${pname}" ] && die "remove_directories() \$pname not given."
1267     [ -z "${pver}" ] && die "remove_directories() \$pver not given."
1268     [ -z "${pbuild}" ] && die "remove_directories() \$pbuild not given."
1269 niro 226 pfull="${pcat}/${pname}-${pver}-${pbuild}"
1270    
1271     # check needed global vars
1272     [ -z "${BUILDDIR}" ] && die "remove_directories() \$BUILDDIR not set."
1273    
1274     [ ! -f ${MROOT}${INSTALLDB}/${pfull}/.char ] && die "remove_directories() .dirs not found"
1275    
1276     # sets fieldseperator to "§" instead of " "
1277     IFS=§
1278    
1279 niro 240 # reversed order is mandatory !
1280     tac ${MROOT}${INSTALLDB}/${pfull}/.dirs | while read pathto posix
1281 niro 226 do
1282     [ -z "${pathto}" ] && continue
1283    
1284     if [ ! -d "${MROOT}${pathto}" ]
1285     then
1286 niro 1584 mqueryfeature "verbose" && \
1287 niro 226 echo -e "${COLRED}! exist${COLDEFAULT} === DIR: ${MROOT}${pathto}"
1288     continue
1289     fi
1290    
1291     # exclude .keep directories
1292     if [ -f "${MROOT}${pathto}/.keep" ]
1293     then
1294 niro 1584 mqueryfeature "verbose" && \
1295 niro 240 echo -e "${COLRED}! .keep${COLDEFAULT} === DIR: ${MROOT}${pathto}"
1296 niro 226 continue
1297     fi
1298    
1299     # monitors /etc/env.d -> env-rebuild
1300     [[ ${pathto} = /etc/env.d ]] && export MAGE_ENV_REBUILD=true
1301    
1302     # monitors /usr/share/info -> info-rebuild
1303     [[ ${pathto} = /usr/share/info ]] && export MAGE_INFO_REBUILD=true
1304    
1305     if rmdir "${MROOT}${pathto}" &> /dev/null
1306     then
1307 niro 1584 mqueryfeature "verbose" && echo -e "\t<<< DIR: ${MROOT}${pathto}"
1308 niro 226 else
1309 niro 1584 mqueryfeature "verbose" && \
1310 niro 226 echo -e "${COLRED}! empty${COLDEFAULT} === DIR: ${MROOT}${pathto}"
1311     fi
1312 niro 240 done
1313 niro 226
1314     # very important: unsetting the '§' fieldseperator
1315     IFS=$'\n'
1316     }
1317    
1318    
1319     ###################################################
1320     # function build_douninstall #
1321     # build_douninstall $PKGNAME #
1322 niro 1209 # NOTE: this is an wrapper to remove packages #
1323 niro 226 ###################################################
1324     build_douninstall()
1325     {
1326     local pcat
1327     local pname
1328     local pver
1329     local pbuild
1330     local i
1331    
1332     # very basic getops
1333     for i in $*
1334     do
1335     case $1 in
1336     --pcat|-c) shift; pcat="$1" ;;
1337     --pname|-n) shift; pname="$1" ;;
1338     --pver|-v) shift; pver="$1" ;;
1339     --pbuild|-b) shift; pbuild="$1" ;;
1340     esac
1341     shift
1342     done
1343    
1344     # sanity checks; abort if not given
1345     [ -z "${pcat}" ] && die "build_douninstall() \$pcat not given."
1346     [ -z "${pname}" ] && die "build_douninstall() \$pname not given."
1347     [ -z "${pver}" ] && die "build_douninstall() \$pver not given."
1348     [ -z "${pbuild}" ] && die "build_douninstall() \$pbuild not given."
1349    
1350     # this is only a wrapper
1351    
1352     # NOTE:
1353     # !! we use § as field seperator !!
1354     # doing so prevent us to get errors by filenames with spaces
1355    
1356 niro 1209 for i in symlinks files blockdevices characterdevices directories fifos
1357 niro 226 do
1358     remove_${i} \
1359     --pcat "${pcat}" \
1360     --pname "${pname}" \
1361     --pver "${pver}" \
1362     --pbuild "${pbuild}" \
1363     || die "remove ${i} ${pcat}/${pname}-${pver}-${pbuild}"
1364     done
1365     }
1366    
1367 niro 1549 # convertmirrors [uri]
1368     convertmirrors()
1369     {
1370     local uri="$1"
1371     local scheme
1372     local mirror
1373     local mirrors
1374     local addon
1375     local real_uri
1376     local output
1377    
1378     # needs
1379     [[ -z ${MIRRORS} ]] && die "convertmirrors(): no mirrors defined!"
1380     [[ -z ${SOURCEFORGE_MIRRORS} ]] && die "convertmirrors(): no sourceforge mirrors defined!"
1381     [[ -z ${GNU_MIRRORS} ]] && die "convertmirrors(): no gnu mirrors defined!"
1382     [[ -z ${GNOME_MIRRORS} ]] && die "convertmirrors(): no gnome mirrors defined!"
1383     [[ -z ${KDE_MIRRORS} ]] && die "convertmirrors(): no kde mirrors defined!"
1384    
1385     # check known uri schemes
1386     case ${uri} in
1387     http://*|https://*|ftp://*|ftps://*) mirrors="" ;;
1388     mirror://*) mirrors="${MIRRORS}"; scheme="mirror://"; addon="/sources" ;;
1389     package://*) mirrors="${MIRRORS}"; scheme="package://"; addon="/${PACKAGES_SERVER_PATH}" ;;
1390     gnu://*) mirrors="${GNU_MIRRORS}"; scheme="gnu://" ;;
1391     sourceforge://*) mirrors="${SOURCEFORGE_MIRRORS}"; scheme="sourceforge://" ;;
1392     gnome://*) mirrors="${GNOME_MIRRORS}"; scheme="gnome://" ;;
1393     kde://*) mirrors="${KDE_MIRRORS}"; scheme="kde://" ;;
1394     *) die "convertmirror(): unsupported uri scheme in '${uri}'!" ;;
1395     esac
1396    
1397     if [[ ! -z ${mirrors} ]]
1398     then
1399     for mirror in ${mirrors}
1400     do
1401     # add a whitespace to the output
1402     [[ -z ${output} ]] || output+=" "
1403     output+="${mirror}${addon}/${uri/${scheme}/}"
1404     done
1405     else
1406 niro 2270 output="${uri}"
1407 niro 1549 fi
1408    
1409     echo "${output}"
1410     }
1411    
1412     mdownload()
1413     {
1414     local i
1415     local uri
1416     local real_uris
1417     local mirror
1418     local outputfile
1419     local outputdir
1420     local retval
1421     local wget_opts
1422    
1423     # very basic getops
1424     for i in $*
1425     do
1426     case $1 in
1427     --uri|-u) shift; uri="$1" ;;
1428     --dir|-d) shift; outputdir="$1" ;;
1429     esac
1430     shift
1431     done
1432    
1433     # sanity checks; abort if not given
1434     [[ -z ${uri} ]] && die "mdownload(): no uri given!"
1435     [[ -z ${outputdir} ]] && die "mdownload(): no dir given!"
1436    
1437     # convert mirrored uris to the real ones
1438     real_uris="$(convertmirrors ${uri})"
1439    
1440     # verbose or not
1441 niro 1626 mqueryfeature "!verbose" && wget_opts+=" --quiet"
1442 niro 1549
1443     # filter wget options if busybox was found
1444 niro 1626 wget_opts+=" $(busybox_filter_wget_options ${WGET_FETCH_OPTIONS})"
1445 niro 1549
1446     # create outputdir
1447     [[ ! -d ${outputdir} ]] && install -d "${outputdir}"
1448    
1449     for mirror in ${real_uris}
1450     do
1451     # get the name of the output file
1452     outputfile="${mirror##*/}"
1453    
1454     wget ${wget_opts} --output-document="${outputdir}/${outputfile}" "${mirror}"
1455     retval="$?"
1456     if [[ ${retval} = 0 ]]
1457     then
1458     break
1459     else
1460     continue
1461     fi
1462     done
1463    
1464     # return wget retval
1465     return "${retval}"
1466     }
1467    
1468 niro 226 # fetch_packages /path/to/mage/file1 /path/to/mage/file2
1469     fetch_packages()
1470     {
1471 niro 1549 local i
1472 niro 226 local list="$@"
1473 niro 2271 local pkgname
1474     local pkgfile
1475 niro 2272 local pcat
1476     local pname
1477 niro 226 local mirr
1478     local magefile
1479     local md5file
1480     local opt
1481     local count_current
1482     local count_total
1483 niro 1273 local wget_opts
1484 niro 2272 local fetching
1485 niro 226
1486 niro 419 [ -z "${MIRRORS}" ] && die "You have no mirrors defined. Please edit your ${MAGERC}."
1487 niro 226
1488 niro 1273 # filter wget command if busybox was found
1489     wget_opts="$(busybox_filter_wget_options ${WGET_FETCH_OPTIONS})"
1490    
1491 niro 226 # get count of total packages
1492     declare -i count_current=0
1493     declare -i count_total=0
1494    
1495     for i in ${list}; do (( count_total++ )); done
1496    
1497     for magefile in ${list}
1498     do
1499 niro 2271 pkgname="$(get_value_from_magefile PKGNAME ${magefile})"
1500     pkgfile="${pkgname}.${PKGSUFFIX}"
1501 niro 226 pkgtype="$(get_value_from_magefile PKGTYPE ${magefile})"
1502    
1503 niro 2272 pcat=$(magename2pcat ${magefile})
1504     pname=$(magename2pname ${magefile})
1505     md5file="${MAGEDIR}/${pcat}/${pname}/md5/${pkgname}.md5"
1506    
1507 niro 226 (( count_current++ ))
1508 niro 2271 xtitle "[ (${count_current}/${count_total}) Fetching ${pkgfile} ]"
1509 niro 226
1510     # abort on virtual pkg
1511     if [[ ${pkgtype} = virtual ]]
1512     then
1513     echo -ne " ${COLBLUE}---${COLDEFAULT}"
1514 niro 2271 echo " !fetch virtual (${count_current}/${count_total}): ${pkgname} ... "
1515 niro 226 continue
1516     fi
1517    
1518     # abort on sources pkg
1519     if [[ ${pkgtype} = sources ]]
1520     then
1521     echo -ne " ${COLBLUE}---${COLDEFAULT}"
1522 niro 2271 echo " !fetch sources (${count_current}/${count_total}): ${pkgname} ... "
1523 niro 226 continue
1524     fi
1525    
1526 niro 2272 # check if FETCHING is required
1527     if [ ! -f "${md5file}" ]
1528 niro 226 then
1529 niro 2272 fetching=true
1530     else
1531     if mchecksum --rundir "${PKGDIR}" --file "${md5file}" --method md5 &> /dev/null
1532     then
1533     # md5's ok, no fetching required
1534     fetching=false
1535     else
1536     fetching=true
1537     fi
1538     fi
1539    
1540     if [[ ${fetching} = false ]]
1541     then
1542 niro 226 echo -ne " ${COLBLUE}***${COLDEFAULT}"
1543 niro 2271 echo " fetch complete (${count_current}/${count_total}): ${pkgfile} ... "
1544 niro 226 continue
1545 niro 2272 else
1546     echo -ne " ${COLBLUE}***${COLDEFAULT}"
1547     echo -e " fetching (${count_current}/${count_total}): ${pkgfile} ... "
1548     mdownload --uri "package://${pkgfile}" --dir "${PKGDIR}" || die "Could not download ${pkgfile}"
1549 niro 226 fi
1550    
1551 niro 2272 # sanity check, not really needed but to be sure
1552 niro 2271 if [ ! -f ${PKGDIR}/${pkgfile} ]
1553 niro 226 then
1554 niro 2271 die "Package '${pkgfile}' after download not found in '${PKGDIR}'"
1555 niro 226 fi
1556     done
1557    
1558     # add a crlf for a better view
1559     if [ ${count_total} -gt 1 ]; then echo; fi
1560     }
1561    
1562     syncmage()
1563     {
1564     if [ -z "${RSYNC}" ]
1565     then
1566 niro 419 die "You have no rsync-mirrors defined. Please edit your ${MAGERC}."
1567 niro 226 fi
1568    
1569     local i
1570     for i in ${RSYNC}
1571     do
1572 niro 386 rsync ${RSYNC_FETCH_OPTIONS} ${i} ${MAGEDIR}
1573 niro 226 if [[ $? = 0 ]]
1574     then
1575     break
1576     else
1577     continue
1578     fi
1579     done
1580    
1581     # clean up backup files (foo~)
1582 niro 1438 find ${MAGEDIR} -name \*~ -exec rm '{}' ';'
1583 niro 226
1584 niro 966 # check if a newer mage version is available
1585 niro 226 is_newer_mage_version_available
1586     }
1587    
1588 niro 739 syncmage_tarball()
1589     {
1590     local latest_tarball
1591 niro 1083 local latest_md5
1592 niro 739 local temp="$(mktemp -d)"
1593     local mirr mymirr
1594 niro 1087 local opt
1595 niro 1273 local tar_opts
1596 niro 1293 local wget_opts
1597 niro 739
1598 niro 1083 # try to get the md5 marked as latest on the server
1599     latest_md5="mage-latest.md5"
1600    
1601 niro 739 # try to get the tarball marked as latest on the server
1602     latest_tarball="mage-latest.tar.bz2"
1603    
1604 niro 1293 # filter wget command if busybox was found
1605     wget_opts="$(busybox_filter_wget_options ${WGET_FETCH_OPTIONS})"
1606    
1607 niro 739 for mirr in ${MIRRORS}
1608     do
1609 niro 1675 # path without distribution
1610     # (only for stable|testing|unstable and not DISTROTAG)
1611     case ${mirr##*/} in
1612     stable|testing|unstable) mymirr="${mirr%/*}";;
1613     *) mymirr="${mirr}";;
1614     esac
1615 niro 739
1616     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1617 niro 1083 echo "fetching latest md5 from ${mymirr} ..."
1618 niro 1584 mqueryfeature "!verbose" && opt="--quiet"
1619 niro 1083 wget \
1620 niro 1293 ${wget_opts} \
1621 niro 1083 --directory-prefix=${temp} \
1622 niro 1087 ${opt} ${mymirr}/rsync/tarballs/${latest_md5}
1623 niro 1083
1624     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1625 niro 739 echo "fetching latest tarball from ${mymirr} ..."
1626     wget \
1627 niro 1293 ${wget_opts} \
1628 niro 739 --directory-prefix=${temp} \
1629 niro 1087 ${opt} ${mymirr}/rsync/tarballs/${latest_tarball}
1630 niro 739 if [[ $? = 0 ]]
1631     then
1632     break
1633     else
1634     continue
1635     fi
1636     done
1637    
1638     if [[ -f ${temp}/${latest_tarball} ]]
1639     then
1640 niro 1083 # check md5
1641     if [[ ! -f ${temp}/${latest_md5} ]]
1642     then
1643     die "md5 is missing ... aborting"
1644     else
1645 niro 1087 echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1646     echo -n "checking md5sum... "
1647 niro 1652 mchecksum --rundir "${temp}" --file "${latest_md5}" --method md5 || die "md5 for ${latest_tarball} failed"
1648 niro 1083 fi
1649    
1650 niro 739 if [[ -d ${MAGEDIR} ]]
1651     then
1652     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1653     echo "cleaning old mage-tree ${MAGEDIR}..."
1654 niro 1654 # honor mountpoints and empty dirs
1655     if mountpoint -q ${MAGEDIR}
1656     then
1657     if ! mcheckemptydir ${MAGEDIR}
1658     then
1659 niro 1963 find ${MAGEDIR} -mindepth 1 -maxdepth 1 | xargs --no-run-if-empty rm -r
1660 niro 1654 fi
1661     else
1662     rm -rf ${MAGEDIR}
1663     fi
1664 niro 739 fi
1665    
1666 niro 1273 if need_busybox_support tar
1667     then
1668     tar_opts="xjf"
1669     else
1670     tar_opts="xjmf"
1671     fi
1672    
1673 niro 739 echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1674     echo "updating mage-tree from tarball ..."
1675     # unpack in dirname of MAGEDIR, as the tarball has already the mage
1676 niro 1273 tar ${tar_opts} ${temp}/${latest_tarball} -C ${MAGEDIR%/*} || die "Unpacking tarball"
1677 niro 739
1678     if [[ -d ${temp} ]]
1679     then
1680     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
1681 niro 972 echo "cleaning temp-files ..."
1682 niro 739 rm -rf ${temp}
1683     fi
1684 niro 966
1685     # check if a newer mage version is available
1686     is_newer_mage_version_available
1687 niro 739 else
1688     die "Could not fetch the latest tarball ... aborting"
1689     fi
1690     }
1691    
1692 niro 226 cleanpkg()
1693     {
1694     if [ -d "${PKGDIR}" ]
1695     then
1696     echo -n "Removing downloaded packages... "
1697     rm -rf ${PKGDIR}/*
1698     echo "done."
1699     fi
1700     }
1701    
1702     xtitle()
1703     {
1704     if [[ ${TERM} = xterm ]]
1705     then
1706     echo -ne "\033]0;Mage: $1\007"
1707     fi
1708     return 0
1709     }
1710    
1711    
1712     xtitleclean()
1713     {
1714     if [[ ${TERM} = xterm ]]
1715     then
1716     echo -ne "\033]0;\007"
1717     fi
1718     return 0
1719     }
1720    
1721    
1722 niro 1650 # unused?
1723     #
1724     # # cuts full pathnames or versionized names down to basename
1725     # choppkgname()
1726     # {
1727     # #we want this only if full name was used
1728     # if [ -n "$(echo ${MAGENAME}|fgrep .mage)" ]
1729     # then
1730     # #cuts ARCH and PBUILD
1731     # #ARCH comes from ${MAGERC}
1732     # MAGENAME=$(echo ${MAGENAME} |sed -e "s:-${ARCH}$(print_distrotag)-r*.::g")
1733     #
1734     # #cuts version number
1735     # MAGENAME=$(basename ${MAGENAME%-*} .mage)
1736     # fi
1737     # }
1738 niro 226
1739    
1740     # get_categorie $PNAME, returns CATEGORIE
1741     # $1=pname
1742     # ret 0=ok, 1=not_found
1743     pname2pcat()
1744     {
1745     local pname="$1"
1746     local repo="$2"
1747     local pcat
1748     local categorie
1749    
1750     for pcat in ${MAGEDIR}/*
1751     do
1752     if [ -d ${pcat}/${pname} ]
1753     then
1754     categorie=$(basename ${pcat})
1755     fi
1756     done
1757    
1758     echo "${categorie}"
1759     }
1760    
1761     # check_stable_package /path/to/foo.mage
1762     # returns 0=stable 1=unstable
1763     check_stable_package()
1764     {
1765 niro 370 # first check if this magefile is not blacklisted
1766     blacklisted "$1" || return 1
1767    
1768 niro 226 local STATE
1769     STATE="$(get_value_from_magefile STATE "$1")"
1770    
1771     # state testing
1772 niro 286 if [[ ${USE_TESTING} = true ]] || [[ ${MAGE_DISTRIBUTION} = testing ]]
1773 niro 226 then
1774     case ${STATE} in
1775     testing|stable) return 0 ;;
1776     *) return 1 ;;
1777     esac
1778     fi
1779    
1780     # state unstable
1781 niro 286 if [[ ${USE_UNSTABLE} = true ]] || [[ ${MAGE_DISTRIBUTION} = unstable ]]
1782 niro 226 then
1783     case ${STATE} in
1784     unstable|testing|stable) return 0 ;;
1785     *) return 1 ;;
1786     esac
1787     fi
1788    
1789     # no use_state given = stable
1790     case ${STATE} in
1791     stable) return 0 ;;
1792     *) return 1 ;;
1793     esac
1794     }
1795    
1796    
1797     # get_highest_magefile ${PCAT} ${PNAME}
1798     # fake at moment returns only stable pkgs (must set to be one)
1799     # return $HIGHEST_MAGEFILE
1800     get_highest_magefile()
1801     {
1802     local HIGHEST_MAGEFILE
1803     local PCAT="$1"
1804     local PNAME="$2"
1805     local magefile
1806    
1807 niro 676 # do not list the content of a directory, only the name (-d)
1808 niro 1438 for magefile in $(ls --format=single-column -v -d ${MAGEDIR}/${PCAT}/${PNAME}/* 2> /dev/null)
1809 niro 226 do
1810 niro 676 [[ -z ${magefile} ]] && continue
1811 niro 226 # we exclude subdirs (for stuff like a md5sum dir)
1812 niro 676 [[ -d ${magefile} ]] && continue
1813 niro 226 if check_stable_package ${magefile}
1814     then
1815     HIGHEST_MAGEFILE=${magefile}
1816     #for debug only
1817 niro 2224 mqueryfeature "debug" && echo "HIGHEST_MAGEFILE=${HIGHEST_MAGEFILE}" >&2
1818 niro 226 fi
1819     done
1820    
1821     echo "${HIGHEST_MAGEFILE}"
1822     return 0
1823     }
1824    
1825    
1826     ###################################################
1827     # function is_config_protected #
1828     # is_config_protected /path/to/file #
1829     # #
1830     # returns: #
1831     # 0 - not protected #
1832     # 1 - error #
1833     # 2 - protected #
1834     # 3 - protected but masked #
1835 niro 942 # 4 - protected but ignored #
1836 niro 226 # #
1837     ###################################################
1838     is_config_protected()
1839     {
1840     local EXPFILE
1841     local TEST
1842     local PROTECTED
1843     local IFS
1844 niro 942 local i
1845     local x
1846 niro 226
1847     EXPFILE="${MROOT}$1"
1848    
1849     # file does not exist; it can be written
1850 niro 451 [[ ! -e ${EXPFILE} ]] && return 0
1851 niro 226
1852     # to be safe; it may be '§'
1853     IFS=' '
1854    
1855 niro 942 # check if config protected
1856 niro 226 for i in ${CONFIG_PROTECT}
1857     do
1858 niro 942 # only replace $i in the beginning of the variable
1859 niro 226 TEST="${EXPFILE/#${MROOT}${i}/Protected}"
1860 niro 451 if [[ ${TEST} != ${EXPFILE} ]]
1861 niro 226 then
1862 niro 942 # file is config proteced
1863 niro 226 PROTECTED=TRUE
1864    
1865 niro 942 # check if not masked
1866 niro 226 for x in ${CONFIG_PROTECT_MASK}
1867     do
1868     TEST="${EXPFILE/#${MROOT}${x}/Protect_Masked}"
1869 niro 451 if [[ ${TEST} != ${EXPFILE} ]]
1870 niro 226 then
1871     PROTECTED=MASKED
1872     fi
1873     done
1874 niro 942
1875     # check if not ignored
1876     for x in ${CONFIG_PROTECT_IGNORE}
1877     do
1878     TEST="${EXPFILE/#${MROOT}${x}/Protect_Ignored}"
1879     if [[ ${TEST} != ${EXPFILE} ]]
1880     then
1881     PROTECTED=IGNORED
1882     fi
1883     done
1884 niro 226 fi
1885     done
1886    
1887     unset IFS
1888    
1889     case ${PROTECTED} in
1890     TRUE)
1891     #echo "I'm protected"
1892     return 2
1893     ;;
1894     MASKED)
1895     #echo "I'm protected, but masked - delete me"
1896     return 3
1897     ;;
1898 niro 942 IGNORED)
1899     #echo "I'm protected, but ignored - keep me, del update"
1900     return 4
1901     ;;
1902 niro 226 *)
1903     #echo "delete me"
1904     return 0
1905     ;;
1906     esac
1907     }
1908    
1909    
1910     ###################################################
1911     # function count_protected_files #
1912     # count_protected_files /path/to/file #
1913     # #
1914     # note: prints number of protected files #
1915     # exp: 0012 #
1916     ###################################################
1917     count_protected_files()
1918     {
1919 niro 603 local file="$1"
1920     local dirname="${file%/*}"
1921     local filename="${file##*/}"
1922     local count
1923     local output
1924 niro 1758 local oldprotected
1925 niro 603 local i
1926 niro 1758 local x
1927 niro 603
1928 niro 1758 # hack; do not honor a global set IFS like '§'
1929     local IFS
1930 niro 603
1931 niro 1758 count=0
1932    
1933 niro 603 # check if there are already protected files
1934 niro 1758 for oldprotected in $(find ${dirname} -iname "._cfg????_${filename}" |
1935 niro 603 sed -e "s:\(^.*/\)\(._cfg*_\)\(/.*$\):\1\2\3\%\2\%\3:" |
1936     sort -t'%' -k3 -k2 | cut -f1 -d'%')
1937     do
1938 niro 1758 count="$(echo ${oldprotected} | sed 's:.*\/._cfg\(.*\)_.*:\1:')"
1939 niro 603 done
1940    
1941 niro 1962 # convert 0001 -> 1; 0120 -> 120 etc
1942     # use bash internal base functions to this task
1943     x="$((10#${count}))"
1944 niro 1758 for (( i=0; i<x; i++ ))
1945     do
1946     if [[ ${count:${i}:1} != 0 ]]
1947     then
1948     count="${count:${i}}"
1949     break
1950     fi
1951     done
1952    
1953 niro 1762 count="$(( ${count}+1 ))"
1954 niro 1758
1955 niro 603 # fill output up with zeros
1956     for (( i=${#count}; i < 4; i++ )); do output="${output}0"; done
1957     output="${output}${count}"
1958    
1959     echo "${output}"
1960 niro 226 }
1961    
1962     # call with
1963     # 'get_uninstall_candidates (--pcat cat --protected pcat/pfull) --pname PNAME'
1964     # returns /path/to/magefile(s)
1965     get_uninstall_candidates()
1966     {
1967     local search_pname
1968     local pkg
1969     local pcat
1970     local pname
1971     local pver
1972     local pbuild
1973     local list
1974     local pcatdir
1975     local protected
1976 niro 449 local i
1977 niro 226
1978     # very basic getops
1979     for i in $*
1980     do
1981     case $1 in
1982     --pcat|-c) shift; pcatdir="$1" ;;
1983     --pname|-n) shift; search_pname="$1" ;;
1984     --protected|-p) shift; protected="$1" ;;
1985     esac
1986     shift
1987     done
1988    
1989 niro 329 # it's not good to complain here about empty pnames; better to continue later anyway
1990     # # sanity checks; abort if not given
1991     # [ -z "${search_pname}" ] && die "get_uninstall_candidates() \$search_pname not given."
1992 niro 226
1993    
1994     # check needed global vars
1995     [ -z "${INSTALLDB}" ] && die "get_uninstall_candidates() \$INSTALLDB not set."
1996    
1997     # set pcatdir to '*' if empty
1998 niro 329 [ -z "${pcatdir}" ] && pcatdir='*'
1999 niro 226
2000     for pkg in ${MROOT}${INSTALLDB}/${pcatdir}/*
2001     do
2002     # abort if not a dir
2003     [ ! -d ${pkg} ] && continue
2004    
2005     pname="$(magename2pname ${pkg})"
2006    
2007     if [[ ${search_pname} = ${pname} ]]
2008     then
2009     pcat="$(magename2pcat ${pkg} installdb)"
2010     pver="$(magename2pver ${pkg})"
2011     pbuild="$(magename2pbuild ${pkg})"
2012    
2013     # exclude proteced
2014     [[ ${protected} = ${pcat}/${pname}-${pver}-${pbuild} ]] && continue
2015    
2016     list="${list} ${pcat}/${pname}-${pver}-${pbuild}"
2017     fi
2018     done
2019    
2020     echo "${list}"
2021     }
2022    
2023     # reads virtualdb file
2024     #$1 = virtualname; $2 commands: showpkgs, showline
2025     #return 0 == installed -> shows installed pkg as well
2026     #return 1 == not installed
2027     virtuals_read()
2028     {
2029     local virtualname="$1"
2030     local command="$2"
2031     local virtline
2032     local line x i
2033    
2034     # parse file to get virtual_name line
2035     IFS=$'\n'
2036     for line in $(< ${MROOT}${VIRTUALDB_FILE})
2037     do
2038     IFS=$' '
2039     for x in ${line}
2040     do
2041     if [[ ${x} = ${virtualname} ]]
2042     then
2043     virtline="${line}"
2044     [[ ${command} = showline ]] && echo "${line}"
2045     fi
2046     done
2047     IFS=$'\n'
2048     done
2049    
2050     unset IFS
2051    
2052     # now read the packages linked to VIRTUAL_NAME and output them
2053     if [ -n "${virtline}" ]
2054     then
2055     if [[ ${command} = showpkgs ]]
2056     then
2057     declare -i x=0
2058     for i in ${virtline}
2059     do
2060     if [ ${x} -ge 1 ]
2061     then
2062     echo "${i}"
2063     fi
2064     ((x++))
2065     done
2066     fi
2067     return 0
2068     fi
2069     return 1
2070     }
2071    
2072    
2073     #add pkg to virtualdb
2074     # $1 == virtualname $2= pkgname
2075     # retvals: 0=ok,added; 1=error; 3=pkg already in virtual
2076     virtuals_add()
2077     {
2078     local virtualname="$1"
2079     local pkgname="$2"
2080     local oldline
2081     local line i
2082     local installed_file
2083 niro 273 local OLDIFS
2084 niro 226
2085     if virtuals_read ${virtualname}
2086     then
2087 niro 329 # make sure ${PKG_NAME} is *not* in ${VIRTUAL_NAME} already
2088 niro 226 for i in $(virtuals_read ${virtualname} showpkgs)
2089     do
2090     if [[ ${i} = ${pkgname} ]]
2091     then
2092     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2093     echo "${pkgname} already linked as ${virtualname} ..."
2094     #return 3
2095     return 0
2096     fi
2097     done
2098    
2099     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
2100     echo "updating ${virtualname} entry with ${pkgname} ..."
2101     oldline="$(virtuals_read ${virtualname} showline)"
2102    
2103     # make a backup
2104     mv ${MROOT}${VIRTUALDB_FILE} ${MROOT}${VIRTUALDB_FILE}.old
2105    
2106 niro 273 OLDIFS="${IFS}"
2107 niro 226 IFS=$'\n'
2108     for line in $(< ${MROOT}${VIRTUALDB_FILE}.old)
2109     do
2110     # if the right line, append ${pkgname}, else do nothing
2111     if [[ ${line} = ${oldline} ]]
2112     then
2113     echo "${line} ${pkgname}" >> ${MROOT}${VIRTUALDB_FILE}
2114     else
2115     echo "${line}" >> ${MROOT}${VIRTUALDB_FILE}
2116     fi
2117     done
2118 niro 273 # unset IFS
2119     IFS="${OLDIFS}"
2120 niro 226 else
2121 niro 273 echo -ne "${COLBLUE} >>> ${COLDEFAULT}"
2122 niro 226 echo "register ${pkgname} as ${virtualname} ..."
2123     echo "${virtualname} ${pkgname}" >> ${MROOT}${VIRTUALDB_FILE}
2124     fi
2125    
2126     return 0
2127     }
2128    
2129     #deletes pakages from virtual database
2130     #$1 virtualname; $2 pkgname
2131 niro 1209 virtuals_del()
2132     {
2133 niro 226
2134 niro 273 local virtualname="$1"
2135     local pkgname="$2"
2136     local oldline
2137     local method
2138     local line i x
2139     local pkg_installed
2140     local OLDIFS
2141    
2142     # first check if exists
2143     if virtuals_read ${virtualname}
2144 niro 226 then
2145 niro 273 # get method -> delall or update and check if ${PKG_NAME} exists in ${VIRTUAL_NAME}
2146 niro 226 declare -i x=0
2147 niro 273 for i in $(virtuals_read ${virtualname} showpkgs)
2148 niro 226 do
2149 niro 273 if [[ ${i} = ${pkgname} ]]
2150 niro 226 then
2151 niro 273 pkg_installed=true
2152 niro 226 fi
2153     ((x++))
2154     done
2155 niro 273
2156     # abort if not installed
2157     if [[ ${pkg_installed} != true ]]
2158 niro 226 then
2159 niro 273 echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2160     echo "${pkgname} does not exists in ${virtualname}."
2161 niro 226 return 0
2162     fi
2163 niro 273
2164 niro 226 if [ ${x} -ge 2 ]
2165     then
2166 niro 273 method=update
2167 niro 226 else
2168 niro 273 method=delall
2169 niro 226 fi
2170 niro 273
2171     # get the complete line
2172     oldline="$(virtuals_read ${virtualname} showline)"
2173    
2174     # make a backup of the db
2175 niro 226 mv ${VIRTUALDB_FILE} ${VIRTUALDB_FILE}.old
2176 niro 273
2177     # parse virtualdb
2178     OLDIFS="${IFS}"
2179 niro 226 IFS=$'\n'
2180     for line in $(< ${VIRTUALDB_FILE}.old)
2181     do
2182 niro 273 if [[ ${line} = ${oldline} ]]
2183 niro 226 then
2184     #delall or update?
2185 niro 273 case ${method} in
2186 niro 226 update)
2187 niro 273 echo -ne "${COLBLUE} *** ${COLDEFAULT}"
2188     echo "Unlinking ${pkgname} from ${virtualname} in virtual database ..."
2189     # del PKG_NAME from line
2190     echo "${line/ ${pkgname}/}" >> ${VIRTUALDB_FILE}
2191 niro 226 ;;
2192     delall)
2193 niro 273 echo -ne "${COLBLUE} <<< ${COLDEFAULT}"
2194     echo "Deleting ${virtualname} in virtual database ..."
2195     # continue; do not write anything
2196 niro 226 continue
2197     ;;
2198     esac
2199     else
2200     echo "${line}" >> ${VIRTUALDB_FILE}
2201     fi
2202     done
2203 niro 273 # unset IFS
2204     IFS="${OLDIFS}"
2205 niro 226 else
2206 niro 273 echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2207     echo "${virtualname} does not exists in virtual database."
2208 niro 226 fi
2209     }
2210    
2211     # gets real pkgname from virtuals.default
2212     #$1=VIRTUAL_NAME; returns PKG_NAME
2213     default_virtualname_to_pkgname()
2214     {
2215     local VIRTUAL_NAME PKG_NAME db_virtualname db_pkgname
2216    
2217     VIRTUAL_NAME=$1
2218    
2219     while read db_virtualname db_pkgname
2220     do
2221     if [ "${db_virtualname}" == "${VIRTUAL_NAME}" ]
2222     then
2223     PKG_NAME="${db_pkgname}"
2224     fi
2225     done << EOF
2226     $(< ${VIRTUALDB_DEFAULTS})
2227     EOF
2228    
2229     if [ -n "${PKG_NAME}" ]
2230     then
2231     echo "${PKG_NAME}"
2232     fi
2233     }
2234    
2235     minclude()
2236     {
2237     local i
2238    
2239 niro 437 if [[ -n $* ]]
2240 niro 226 then
2241 niro 437 for i in $*
2242 niro 226 do
2243 niro 1584 mqueryfeature "debug" && \
2244 niro 226 echo "--- Including ${MAGEDIR}/include/${i}.minc"
2245     source ${MAGEDIR}/include/${i}.minc
2246     done
2247 niro 1584 mqueryfeature "debug" && echo
2248 niro 226 fi
2249     }
2250    
2251     sminclude()
2252     {
2253     local i
2254    
2255 niro 437 if [[ -n $* ]]
2256 niro 226 then
2257 niro 437 for i in $*
2258 niro 226 do
2259 niro 2364 [[ ${SILENT} = 1 ]] || echo "--- Including ${SMAGESCRIPTSDIR}/include/${i}.sminc"
2260 niro 226 source ${SMAGESCRIPTSDIR}/include/${i}.sminc
2261     done
2262 niro 2364 [[ ${SILENT} = 1 ]] || echo
2263 niro 226 fi
2264     }
2265    
2266     # checks if an newer mage version is available
2267     is_newer_mage_version_available()
2268     {
2269     local newest_mage
2270     local installed_mage
2271    
2272 niro 252 newest_mage="$(basename $(get_highest_magefile app-mage mage) .mage)"
2273 niro 226 installed_mage="$(magequery -n mage | cut -d' ' -f5)"
2274    
2275     if [[ ${newest_mage} > ${installed_mage} ]]
2276     then
2277     echo
2278     echo -en ${COLRED}"An update for your packetmanager is available. "${COLDEFAULT}
2279     echo -e ${COLBLUE}"[ ${newest_mage} ]"${COLDEFAULT}
2280     echo "It is recommened to install this newer version"
2281 niro 373 echo "or your current system installation may break."
2282 niro 226 echo
2283     echo -en "Please update mage by running "
2284     echo -e ${COLGREEN}"'mage install mage'"${COLDEFAULT}
2285     echo
2286     fi
2287     }
2288    
2289    
2290     # returns pname from pkgname
2291     # pkgname2pname $PKGNAME
2292     pkgname2pname()
2293     {
2294     local pname
2295    
2296     pname="${1%-*-*-*}"
2297     echo "${pname}"
2298     }
2299    
2300     # returns pver from pkgname
2301     # pkgname2pver $PKGNAME
2302     pkgname2pver()
2303     {
2304     local i pver
2305    
2306     i="${1/$(pkgname2pname $1)-/}"
2307     pver="${i%-*-*}"
2308     echo "${pver}"
2309     }
2310    
2311     # returns pbuild from pkgname
2312     # pkgname2pbuild $PKGNAME
2313     pkgname2pbuild()
2314     {
2315     local pbuild
2316    
2317     pbuild="${1##*-}"
2318     echo "${pbuild}"
2319     }
2320    
2321     # returns parch from pkgname
2322     # pkgname2parch $PKGNAME
2323     pkgname2parch()
2324     {
2325     local i x parch
2326    
2327     i="${1%-*-*}-"
2328     x="${1%-*}"
2329     parch="${x/${i}/}"
2330     echo "${parch}"
2331     }
2332    
2333     # returns pname from magename
2334     # magename2pname /PATH/TO/MAGE/FILE
2335     magename2pname()
2336     {
2337     local i pname
2338    
2339     i="$(basename $1 .mage)"
2340     pname="${i%-*-*}"
2341     echo "${pname}"
2342     }
2343    
2344     # returns pver from magename
2345     # magename2pver /PATH/TO/MAGE/FILE
2346     magename2pver()
2347     {
2348     local i pver
2349    
2350     i="$(basename $1 .mage)"
2351     i="${i/$(magename2pname $1)-/}"
2352     pver="${i%-*}"
2353     echo "${pver}"
2354     }
2355    
2356     # returns pbuild from magename
2357     # magename2pbuild /PATH/TO/MAGE/FILE
2358     magename2pbuild()
2359     {
2360     local i pbuild
2361    
2362     i="$(basename $1 .mage)"
2363     pbuild="${i##*-}"
2364     echo "${pbuild}"
2365     }
2366    
2367     # returns pcat from magename
2368     # magename2pcat /PATH/TO/MAGE/FILE
2369     magename2pcat()
2370     {
2371     local i pcat
2372    
2373     if [[ ${2} = installdb ]]
2374     then
2375     # go 1 dir back
2376     i="${1%/*}"
2377     else
2378     # go 2 dirs back
2379     i="${1%/*/*}"
2380     fi
2381    
2382     # get basename
2383     pcat="${i##*/}"
2384     echo "${pcat}"
2385     }
2386    
2387     # returns pcat from DEPEND (without operand ! PCAT/PNAME-VERSION)
2388     # dep2pcat DEPEND
2389     dep2pcat()
2390     {
2391     local pcat
2392    
2393     pcat="${1%/*}"
2394     echo "${pcat}"
2395     }
2396    
2397     # returns pname from DEPEND (without operand ! PCAT/PNAME-VERSION)
2398     # $2=virtual is used to resolv VDEPEND from virtual packages
2399     # dep2pcat DEPEND (virtual)
2400     dep2pname()
2401     {
2402     local pname
2403    
2404     pname="${1##*/}"
2405    
2406     # cut version only if not virtual or it will cut the name
2407     if [[ $(dep2pcat $1) != virtual ]] && \
2408     [[ $2 != virtual ]]
2409     then
2410     pname="${pname%-*}"
2411     fi
2412    
2413     echo "${pname}"
2414     }
2415    
2416     dep2highest_magefile()
2417     {
2418     local pcat
2419     local pname
2420     local magefile
2421     local installed_virtuals
2422    
2423     pcat="$(dep2pcat $1)"
2424     pname="$(dep2pname $1)"
2425    
2426     if [[ ${pcat} = virtual ]]
2427     then
2428     # first check if virtual is already installed
2429     installed_virtuals="$(virtuals_read ${pcat}/${pname} showpkgs)"
2430     if [ -n "${installed_virtuals}" ]
2431     then
2432     for vpkg in ${installed_virtuals}
2433     do
2434     realpkgname="${vpkg}"
2435     virtualpkgname="${pcat}/${pname}"
2436     pcat="$(dep2pcat ${realpkgname})"
2437     pname="$(dep2pname ${realpkgname} virtual)"
2438     done
2439     else
2440     # choose one from virtualdb defaults (virtuals.defaults)
2441     realpkgname="$(default_virtualname_to_pkgname ${pcat}/${pname})"
2442     virtualpkgname="${pcat}/${pname}"
2443     pcat="$(dep2pcat ${realpkgname})"
2444     pname="$(dep2pname ${realpkgname} virtual)"
2445     fi
2446     fi
2447    
2448     magefile="$(get_highest_magefile ${pcat} ${pname})"
2449     echo "${magefile}"
2450     }
2451    
2452     # is_installed ${PCAT}/${PNAME}-${PVER}-${PBUILD}
2453     is_installed()
2454     {
2455     local fullpkgname="$1"
2456    
2457     # return 0 if installed
2458     [ -d ${MROOT}${INSTALLDB}/${fullpkgname} ] && return 0
2459    
2460     return 1
2461     }
2462    
2463     install_packages()
2464     {
2465     local list="$@"
2466     local pkg
2467     local pcat
2468     local pname
2469     local pver
2470     local pbuild
2471     local total_pkgs
2472     local current_pkg
2473     local src_install
2474     local uninstall_list
2475    
2476     # check for --src-install
2477     if [[ $1 = --src-install ]]
2478     then
2479     # remove --src-install from list
2480     list=${list/--src-install/}
2481     # enable src-install
2482     src_install="--src-install"
2483     fi
2484    
2485     # reset MAGE_PROTECT_COUNTER
2486     declare -i MAGE_PROTECT_COUNTER=0
2487     export MAGE_PROTECT_COUNTER
2488    
2489     # get count of total packages
2490     declare -i total_pkgs=0
2491     declare -i current_pkg=0
2492     for i in ${list}; do (( total_pkgs++ )); done
2493    
2494     echo
2495    
2496     if [[ -n ${MROOT} ]]
2497     then
2498     echo -ne ${COLRED}
2499     echo "!! installing in MROOT=${MROOT}"
2500     echo -ne ${COLDEFAULT}
2501     echo
2502     fi
2503    
2504     for pkg in ${list}
2505     do
2506     (( current_pkg++ ))
2507     pcat=$(magename2pcat ${pkg})
2508     pname=$(magename2pname ${pkg})
2509     pver=$(magename2pver ${pkg})
2510     pbuild=$(magename2pbuild ${pkg})
2511    
2512     mage_install \
2513     --pcat ${pcat} \
2514     --pname ${pname} \
2515     --pver ${pver} \
2516     --pbuild ${pbuild} \
2517     --count-total ${total_pkgs} \
2518     --count-current ${current_pkg} \
2519     ${src_install}
2520    
2521     # check for allready installed packages and remove them
2522     # except the package we have installed
2523     uninstall_list="$(get_uninstall_candidates \
2524     --pcat "${pcat}" \
2525     --pname "${pname}" \
2526     --protected ${pcat}/${pname}-${pver}-${pbuild})"
2527    
2528     # uninstall all packges in uninstall_list if not empty
2529     if [ -n "${uninstall_list}" ]
2530     then
2531     echo
2532     uninstall_packages ${uninstall_list} \
2533     || die "install_packges() uninstalling not-needed."
2534     fi
2535    
2536     # crlf for better view in VERBOSE mode
2537     #if [[ ${VERBOSE} = on ]]; then echo; fi
2538     echo
2539     done
2540    
2541     #echo "DEBUG MAGE_PROTECT_COUNTER=${MAGE_PROTECT_COUNTER}"
2542     show_etc_update_mesg
2543     }
2544    
2545     # get_value_from_magefile VARIABLE
2546     # returns the content of this VAR
2547     get_value_from_magefile()
2548     {
2549     local var="$1"
2550     local magefile="$2"
2551     local value
2552    
2553 niro 370 [[ -z ${var} ]] && return 1
2554     [[ -z ${magefile} ]] && return 1
2555    
2556 niro 226 # local all possible vars of a mage file
2557     # to prevent bad issues
2558     local PKGNAME
2559     local STATE
2560     local DESCRIPTION
2561     local HOMEPAGE
2562     local DEPEND
2563     local SDEPEND
2564     local PROVIDE
2565     local PKGTYPE
2566 niro 943 local SPLIT_PACKAGE_BASE
2567 niro 226 local preinstall
2568     local postinstall
2569 niro 248 local preremove
2570     local postremove
2571 niro 226
2572     # sanity checks
2573     [ -f ${magefile} ] && source ${magefile} || \
2574     die "get_value_from_magefile: ${magefile} not found."
2575     [ -z "${var}" ] && die "get_value_from_magefile: \$var not given."
2576    
2577     source ${magefile}
2578     eval value=\$$(echo ${var})
2579     echo "${value}"
2580 niro 248
2581 niro 258 # unset these functions
2582     unset -f preinstall
2583     unset -f postinstall
2584     unset -f preremove
2585     unset -f postremove
2586 niro 226 }
2587    
2588     mage_install()
2589     {
2590     # local all possible vars of a mage file
2591     # to prevent bad issues
2592     local PKGNAME
2593     local STATE
2594     local DESCRIPTION
2595     local HOMEPAGE
2596     local DEPEND
2597     local SDEPEND
2598     local PROVIDE
2599     local PKGTYPE
2600     local preinstall
2601     local postinstall
2602 niro 248 local preremove
2603     local postremove
2604 niro 226
2605     local pcat
2606     local pname
2607     local pver
2608     local pbuild
2609     local count_total
2610     local count_current
2611     local magefile
2612     local src_install
2613 niro 876 local i
2614 niro 226
2615     # very basic getops
2616     for i in $*
2617     do
2618     case $1 in
2619     --pcat|-c) shift; pcat="$1" ;;
2620     --pname|-n) shift; pname="$1" ;;
2621     --pver|-v) shift; pver="$1" ;;
2622     --pbuild|-b) shift; pbuild="$1" ;;
2623     --count-total) shift; count_total="$1" ;;
2624     --count-current) shift; count_current="$1" ;;
2625     --src-install|-s) shift; src_install=true ;;
2626     esac
2627     shift
2628     done
2629    
2630     # sanity checks; abort if not given
2631     [ -z "${pcat}" ] && die "mage_install() \$pcat not given."
2632     [ -z "${pname}" ] && die "mage_install() \$pname not given."
2633     [ -z "${pver}" ] && die "mage_install() \$pver not given."
2634     [ -z "${pbuild}" ] && die "mage_install() \$pbuild not given."
2635    
2636     # check needed global vars
2637     [ -z "${MAGEDIR}" ] && die "mage_install() \$MAGEDIR not set."
2638     [ -z "${INSTALLDB}" ] && die "mage_install() \$INSTALLDB not set."
2639     [ -z "${BUILDDIR}" ] && die "mage_install() \$BUILDDIR not set."
2640    
2641     xtitle "[ (${count_current}/${count_total}) Installing ${pcat}/${pname}-${pver}-${pbuild} ]"
2642     echo -ne "${COLBLUE} >>> ${COLDEFAULT}"
2643     echo -n "installing (${count_current}/${count_total}): "
2644     echo -ne "${COLBLUE}${pcat}/${COLDEFAULT}"
2645     echo -e "${COLGREEN}${pname}-${pver}-${pbuild}${COLDEFAULT}"
2646    
2647     magefile="${MAGEDIR}/${pcat}/${pname}/${pname}-${pver}-${pbuild}.mage"
2648     source ${magefile}
2649    
2650     # abort on sources if no srcinstall
2651     if [[ ${PKGTYPE} = sources ]] && [[ ${src_install} != true ]]
2652     then
2653     echo
2654     echo -e "This Package is a Source Package."
2655     echo
2656     echo -e "Only 'srcinstall' works with this type of packages"
2657     echo -en "If you have done a srcinstall before, "
2658     echo -e "you will find the files in /usr/src."
2659     echo
2660     exit 1
2661     fi
2662    
2663     ## preinstall scripts
2664     if [ -n "$(typeset -f preinstall)" ]
2665     then
2666     echo -e " ${COLBLUE}***${COLDEFAULT} running preinstall ... "
2667     preinstall
2668     unset preinstall
2669     fi
2670    
2671     if [[ ${src_install} = true ]]
2672     then
2673     local smage2file
2674     # check needed global vars
2675     [ -z "${SMAGESCRIPTSDIR}" ] && die "\$SMAGESCRIPTSDIR not set."
2676     [ -z "${SOURCEDIR}" ] && die "\$SOURCEDIR not set."
2677     [ -z "${BINDIR}" ] && die "\$BINDIR not set."
2678    
2679     # build the package first
2680     if [[ ${MAGEDEBUG} = on ]]
2681     then
2682     echo M:${pname}
2683     echo V:${pver}
2684     echo B:${pbuild}
2685     fi
2686    
2687 niro 2365 if [[ -n ${SPLIT_PACKAGE_BASE} ]]
2688 niro 675 then
2689 niro 876 # basic svn compat
2690 niro 1502 if [[ -d ${SMAGESCRIPTSDIR}/.svn ]]
2691 niro 876 then
2692 niro 1502 for i in ${SMAGESCRIPTSDIR}/*/${SPLIT_PACKAGE_BASE}/${SPLIT_PACKAGE_BASE}-${pver}-${pbuild}.smage2
2693 niro 943 do
2694     smage2file="${i}"
2695     done
2696     else
2697     smage2file=${SMAGESCRIPTSDIR}/${SPLIT_PACKAGE_BASE}/${SPLIT_PACKAGE_BASE}-${pver}-${pbuild}.smage2
2698     fi
2699    
2700 niro 675 else
2701 niro 876 # basic svn compat
2702 niro 1502 if [[ -d ${SMAGESCRIPTSDIR}/.svn ]]
2703 niro 876 then
2704 niro 1502 for i in ${SMAGESCRIPTSDIR}/*/${pname}/${pname}-${pver}-${pbuild}.smage2
2705 niro 876 do
2706     smage2file="${i}"
2707     done
2708     else
2709 niro 943 smage2file=${SMAGESCRIPTSDIR}/${pname}/${pname}-${pver}-${pbuild}.smage2
2710 niro 876 fi
2711 niro 675 fi
2712 niro 943
2713 niro 226 if [ -f "${smage2file}" ]
2714     then
2715 niro 385 echo -e " ${COLBLUE}***${COLDEFAULT} building package from source ... "
2716 niro 226 smage2 ${smage2file} || die "compile failed"
2717     else
2718     echo
2719     echo "$(basename ${SMAGEFILE}) not found."
2720     echo "update your smage-tree and try it again."
2721     echo
2722     die
2723     fi
2724     fi
2725    
2726     if [[ ${PKGTYPE} != virtual ]] && \
2727     [[ ${PKGTYPE} != sources ]]
2728     then
2729 niro 2156 unpack_package "${magefile}"
2730 niro 385 echo -e " ${COLBLUE}***${COLDEFAULT} merging files into system ... "
2731 niro 226 build_doinstall ${PKGNAME}
2732     fi
2733    
2734     ## postinstall scripts
2735     if [ -n "$(typeset -f postinstall)" ]
2736     then
2737     echo -e " ${COLBLUE}***${COLDEFAULT} running postinstall ... "
2738     postinstall
2739     unset postinstall
2740     fi
2741    
2742     # install a database entry
2743     install_database_entry \
2744     --pcat "${pcat}" \
2745     --pname "${pname}" \
2746     --pver "${pver}" \
2747     --pbuild "${pbuild}" \
2748     --pkgname "${PKGNAME}" \
2749     --pkgtype "${PKGTYPE}" \
2750     || die "error in mage_install() running install_database_entry()."
2751    
2752     # remove the package dir now
2753     if [ -d ${BUILDDIR}/${PKGNAME} ]
2754     then
2755     rm -rf ${BUILDDIR}/${PKGNAME}
2756     fi
2757    
2758     # rebuilds toplevel info node
2759     if [[ ${MAGE_INFO_REBUILD} = true ]]
2760     then
2761     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
2762     echo -n "rebuilding top-level info node ... "
2763     ${MLIBDIR}/mkinfodir ${MROOT}/usr/share/info \
2764     > ${MROOT}/usr/share/info/dir && \
2765     echo "done." || echo "failure."
2766     unset MAGE_INFO_REBUILD
2767     fi
2768    
2769     # rebuilds the enviroment with the content of /etc/env.d
2770     if [[ ${MAGE_ENV_REBUILD} = true ]]
2771     then
2772     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
2773     echo -n "rebuilding environment ... "
2774     ${MLIBDIR}/env-rebuild.sh > /dev/null && \
2775     echo "done." || echo "failure."
2776     unset MAGE_ENV_REBUILD
2777     fi
2778    
2779     xtitleclean
2780    
2781     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2782     echo -n "package "
2783     # echo -ne "${COLBLUE}${pcat}/${COLDEFAULT}"
2784     # echo -ne "${COLGREEN}${pname}-${pver}-${pbuild}${COLDEFAULT} "
2785     echo "successfully installed."
2786 niro 248
2787 niro 258 # unset these functions
2788     unset -f preinstall
2789     unset -f postinstall
2790     unset -f preremove
2791     unset -f postremove
2792 niro 226 }
2793    
2794     md5sum_packages()
2795     {
2796     local list="$@"
2797     local magefile
2798     local pcat
2799     local pname
2800     local pkgname
2801     local pkgfile
2802     local pkgtype
2803     local count_current
2804     local count_total
2805    
2806     # get count of total packages
2807     declare -i count_current=0
2808     declare -i count_total=0
2809    
2810     for i in ${list}; do (( count_total++ )); done
2811    
2812     for magefile in ${list}
2813     do
2814     pcat=$(magename2pcat ${magefile})
2815     pname=$(magename2pname ${magefile})
2816     pkgname="$(get_value_from_magefile PKGNAME ${magefile})"
2817     md5file="${MAGEDIR}/${pcat}/${pname}/md5/${pkgname}.md5"
2818 niro 2271 pkgfile="${pkgname}.${PKGSUFFIX}"
2819 niro 226 pkgtype="$(get_value_from_magefile PKGTYPE ${magefile})"
2820    
2821     (( count_current++ ))
2822     xtitle "[ (${count_current}/${count_total}) MD5SUM: ${pkgfile} ]"
2823    
2824     # abort on virtual pkg
2825     if [[ ${pkgtype} = virtual ]]
2826     then
2827     echo -ne " ${COLBLUE}---${COLDEFAULT}"
2828 niro 2271 echo " !md5sum virtual (${count_current}/${count_total}): ${pkgname} ... "
2829 niro 226 continue
2830     fi
2831    
2832     # abort on sources pkg
2833     if [[ ${pkgtype} = sources ]]
2834     then
2835     echo -ne " ${COLBLUE}---${COLDEFAULT}"
2836 niro 2271 echo " !md5sum sources (${count_current}/${count_total}): ${pkgname} ... "
2837 niro 226 continue
2838     fi
2839    
2840     if [ -f "${md5file}" ]
2841     then
2842     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
2843     echo -ne "checking md5sum (${count_current}/${count_total}): "
2844 niro 1652 mchecksum --rundir "${PKGDIR}" --file "${md5file}" --method md5 || die "md5 for ${pkgfile} failed"
2845 niro 226 else
2846     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2847     echo -e "!! no md5sum file found for ${pkgfile} :("
2848     fi
2849     done
2850    
2851     # add a crlf for a better view
2852     if [ ${count_total} -gt 1 ]; then echo; fi
2853     }
2854    
2855     ## uninstall_packages ulist
2856     uninstall_packages()
2857     {
2858     local list="$@"
2859     local pcat
2860     local pname
2861     local pver
2862     local pbuild
2863     local can_pcat
2864     local can_pname
2865     local can_ver_list
2866    
2867     if [[ -n ${MROOT} ]]
2868     then
2869     echo -ne ${COLRED}
2870     echo "!! uninstalling from MROOT=${MROOT}"
2871     echo -ne ${COLDEFAULT}
2872     echo
2873     fi
2874    
2875     # generate a candidates list
2876     for pkg in ${list}
2877     do
2878     pcat=$(dep2pcat ${pkg})
2879     pname=$(magename2pname ${pkg})
2880     pver=$(magename2pver ${pkg})
2881     pbuild=$(magename2pbuild ${pkg})
2882     can_pcat="${pcat}"
2883     can_pname="${pname}"
2884 niro 2270
2885 niro 226 if [ -z "${can_ver_list}" ]
2886     then
2887     can_ver_list=" ${pver}-${pbuild}"
2888     else
2889     can_ver_list="${can_ver_list}, ${pver}-${pbuild}"
2890     fi
2891     done
2892    
2893     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2894     echo "following candidate(s) will be removed:"
2895     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2896 niro 240 echo -ne "${COLBOLD}${can_pcat}/${can_pname}:${COLDEFAULT}"
2897 niro 226 echo -e "${COLRED} ${can_ver_list} ${COLDEFAULT}"
2898 niro 501 echo
2899 niro 240 if [ ${MAGE_UNINSTALL_TIMEOUT} -gt 0 ]
2900     then
2901     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2902     echo "( Press [CTRL+C] to abort )"
2903     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
2904     echo -n "Waiting ${MAGE_UNINSTALL_TIMEOUT} seconds ..."
2905     for ((i=MAGE_UNINSTALL_TIMEOUT; i >= 0; i--))
2906     do
2907     echo -ne "${COLRED} ${i}${COLDEFAULT}"
2908     sleep 1
2909     done
2910     echo
2911     echo
2912     fi
2913 niro 226
2914     for pkg in ${list}
2915     do
2916     pcat=$(dep2pcat ${pkg})
2917     pname=$(magename2pname ${pkg})
2918     pver=$(magename2pver ${pkg})
2919     pbuild=$(magename2pbuild ${pkg})
2920    
2921     mage_uninstall \
2922     --pcat ${pcat} \
2923     --pname ${pname} \
2924     --pver ${pver} \
2925     --pbuild ${pbuild} \
2926     --count-total ${total_pkgs} \
2927     --count-current ${current_pkg} \
2928     ${src_install}
2929    
2930     # crlf for better view in VERBOSE mode
2931     #if [[ ${VERBOSE} = on ]]; then echo; fi
2932     echo
2933     done
2934     }
2935    
2936     mage_uninstall()
2937     {
2938     # local all possible vars of a mage file
2939     # to prevent bad issues
2940     local PKGNAME
2941     local STATE
2942     local DESCRIPTION
2943     local HOMEPAGE
2944     local DEPEND
2945     local SDEPEND
2946     local PROVIDE
2947     local PKGTYPE
2948     local preinstall
2949     local postinstall
2950 niro 248 local preremove
2951     local postremove
2952 niro 226
2953     local pcat
2954     local pname
2955     local pver
2956     local pbuild
2957     local magefile
2958     local i
2959    
2960     # very basic getops
2961     for i in $*
2962     do
2963     case $1 in
2964 niro 501 --pcat|-c) shift; pcat="$1" ;;
2965 niro 226 --pname|-n) shift; pname="$1" ;;
2966     --pver|-v) shift; pver="$1" ;;
2967 niro 501 --pbuild|-b) shift; pbuild="$1" ;;
2968 niro 226 esac
2969     shift
2970 niro 501 done
2971 niro 226
2972     # sanity checks; abort if not given
2973 niro 501 [ -z "${pcat}" ] && die "mage_uninstall() \$pcat not given."
2974 niro 226 [ -z "${pname}" ] && die "mage_uninstall() \$pname not given."
2975     [ -z "${pver}" ] && die "mage_uninstall() \$pver not given."
2976 niro 501 [ -z "${pbuild}" ] && die "mage_uninstall() \$pbuild not given."
2977 niro 226
2978     # check needed global vars
2979     [ -z "${MAGEDIR}" ] && die "mage_uninstall() \$MAGEDIR not set."
2980     [ -z "${INSTALLDB}" ] && die "mage_uninstall() \$INSTALLDB not set."
2981     [ -z "${BUILDDIR}" ] && die "mage_uninstall() \$BUILDDIR not set."
2982    
2983     xtitle "[ (${count_current}/${count_total}) Removing ${pcat}/${pname}-${pver}-${pbuild} ]"
2984     echo -ne "${COLBLUE} <<< ${COLDEFAULT}"
2985     echo -n "removing: "
2986     echo -ne "${COLBLUE}${pcat}/${COLDEFAULT}"
2987 niro 416 echo -e "${COLRED}${pname}-${pver}-${pbuild}${COLDEFAULT}"
2988 niro 226
2989 niro 499 magefile="${MROOT}${INSTALLDB}/${pcat}/${pname}-${pver}-${pbuild}/${pname}-${pver}-${pbuild}.mage"
2990 niro 226 source ${magefile}
2991    
2992     ## preremove scripts
2993     if [ -n "$(typeset -f preremove)" ]
2994     then
2995     echo -e " ${COLBLUE}***${COLDEFAULT} running preremove ... "
2996     preremove
2997     unset preremove
2998     fi
2999    
3000     # runs uninstall
3001     build_douninstall \
3002     --pcat "${pcat}" \
3003     --pname "${pname}" \
3004     --pver "${pver}" \
3005     --pbuild "${pbuild}"
3006    
3007     ## postremove scripts
3008     if [ -n "$(typeset -f postremove)" ]
3009     then
3010     echo -e " ${COLBLUE}***${COLDEFAULT} running postremove ... "
3011     postremove
3012     unset postremove
3013     fi
3014    
3015     # removes the database entry
3016     remove_database_entry \
3017     --pcat "${pcat}" \
3018     --pname "${pname}" \
3019     --pver "${pver}" \
3020     --pbuild "${pbuild}" \
3021     || die "error in mage_uninstall() running remove_database_entry()."
3022    
3023     # rebuilds toplevel info node
3024     if [[ ${MAGE_INFO_REBUILD} = true ]]
3025     then
3026     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
3027     echo -n "rebuilding top-level info node ... "
3028     ${MLIBDIR}/mkinfodir ${MROOT}/usr/share/info \
3029     > ${MROOT}/usr/share/info/dir && \
3030     echo "done." || echo "failure."
3031     unset MAGE_INFO_REBUILD
3032     fi
3033    
3034     # rebuilds the enviroment with the content of /etc/env.d
3035     if [[ ${MAGE_ENV_REBUILD} = true ]]
3036     then
3037     echo -ne "${COLBLUE} *** ${COLDEFAULT}"
3038     echo -n "rebuilding environment ... "
3039     ${MLIBDIR}/env-rebuild.sh > /dev/null && \
3040     echo "done." || echo "failure."
3041     unset MAGE_ENV_REBUILD
3042     fi
3043    
3044     echo -ne "${COLBLUE} --- ${COLDEFAULT}"
3045     echo -n "package "
3046     # echo -ne "${COLBLUE}${pcat}/${COLDEFAULT}"
3047     # echo -ne "${COLGREEN}${pname}-${pver}-${pbuild}${COLDEFAULT} "
3048     echo "successfully removed."
3049 niro 248
3050 niro 258 # unset these functions
3051     unset -f preinstall
3052     unset -f postinstall
3053     unset -f preremove
3054     unset -f postremove
3055 niro 226 }
3056    
3057 niro 2371 # rerun_pkgfunctions [method] pkg1 pkg2 pkg3
3058     rerun_pkgfunctions()
3059     {
3060     local method
3061     local list
3062     local pcat
3063     local pname
3064     local pver
3065     local pbuild
3066     local magefile
3067     local i
3068    
3069     # very basic getops
3070 niro 2372 case $1 in
3071     --method) shift; method="$1" ;;
3072     esac
3073     shift
3074 niro 2371 local list="$@"
3075    
3076     # sanity check
3077     case ${method} in
3078     preinstall|postinstall) ;;
3079     preremove|postremove) ;;
3080     *) die "rerun_pkgfunctions(): Unknown method '${method}'." ;;
3081     esac
3082    
3083     if [[ -n ${MROOT} ]]
3084     then
3085     echo -ne ${COLRED}
3086     echo "!! running in MROOT=${MROOT}"
3087     echo -ne ${COLDEFAULT}
3088     echo
3089     fi
3090    
3091     for pkg in ${list}
3092     do
3093     pcat=$(dep2pcat ${pkg})
3094     pname=$(magename2pname ${pkg})
3095     pver=$(magename2pver ${pkg})
3096     pbuild=$(magename2pbuild ${pkg})
3097     magefile="${MROOT}${INSTALLDB}/${pcat}/${pname}-${pver}-${pbuild}/${pname}-${pver}-${pbuild}.mage"
3098    
3099     if [ -e ${magefile} ]
3100     then
3101     source ${magefile}
3102     if [ -n "$(typeset -f ${method})" ]
3103     then
3104     echo -e " ${COLBLUE}***${COLDEFAULT} running ${method} for ${pkg} ... "
3105     ${method}
3106     else
3107     echo "No ${method}() for pkg '${pkg}' defined. Doing nothing."
3108     fi
3109     unset -f preinstall postinstall preremove postremove
3110     else
3111     die "Magefile '${magefile}' does not exist."
3112     fi
3113     done
3114     }
3115    
3116 niro 1209 show_etc_update_mesg()
3117     {
3118 niro 226 [ ${MAGE_PROTECT_COUNTER} -eq 0 ] && return 0
3119    
3120     echo
3121     echo -ne "${COLRED}"
3122     echo "Important:"
3123     echo -ne ${COLDEFAULT}
3124     echo "${MAGE_PROTECT_COUNTER} protected file(s) were installed."
3125     echo
3126     echo "Please run 'etc-update' to update your configuration files."
3127     echo
3128     }
3129 niro 237
3130     pkgsearch()
3131     {
3132     local string="$1"
3133     local result
3134     local pkg
3135     local pcat
3136     local pname
3137     local magefile
3138     local pver
3139     local pbuild
3140     local state
3141     local descriptiom
3142     local homepage
3143 niro 1648 local license
3144 niro 237 local i
3145     local all_installed
3146     local ipver
3147     local ipbuild
3148 niro 445 local latest_available
3149 niro 458 local depsfull
3150     local sdepsfull
3151     local deps
3152     local sdeps
3153     local dep
3154     local sign
3155 niro 237
3156     # only names no versions
3157 niro 391 result="$(find ${MAGEDIR} -mindepth 2 -maxdepth 2 -type d -name '*'${string}'*'| sed '/profiles/d' | sed '/includes/d')"
3158 niro 328 #result="$(find ${MAGEDIR} -type f -name '*'${string}'*'.mage | sort)"
3159 niro 237
3160     # nothing found
3161     [[ -z ${result} ]] && die "No package found containing '${string}' in the name."
3162    
3163     for pkg in ${result}
3164     do
3165     # dirty, but does the job
3166     pcat="$(magename2pcat ${pkg}/foo)"
3167     pname="$(magename2pname ${pkg}-foo-foo)"
3168    
3169     # get highest version available
3170     magefile=$(get_highest_magefile ${pcat} ${pname})
3171    
3172 niro 445 if [[ ! -z ${magefile} ]]
3173     then
3174     # now get all needed infos to print a nice output
3175     pver="$(magename2pver ${magefile})"
3176     pbuild="$(magename2pbuild ${magefile})"
3177     state="$(get_value_from_magefile STATE ${magefile})"
3178     description="$(get_value_from_magefile DESCRIPTION ${magefile})"
3179     homepage="$(get_value_from_magefile HOMEPAGE ${magefile})"
3180 niro 1648 license="$(get_value_from_magefile LICENSE ${magefile})"
3181    
3182 niro 445 # all installed
3183     for i in $(get_uninstall_candidates --pname ${pname} --pcat ${pcat})
3184     do
3185     ipver="$(magename2pver ${i})"
3186     ipbuild="$(magename2pbuild ${i})"
3187 niro 1648
3188 niro 445 if [[ -z ${all_installed} ]]
3189     then
3190     all_installed="${ipver}-${ipbuild}"
3191     else
3192     all_installed="${all_installed} ${ipver}-${ipbuild}"
3193     fi
3194     done
3195     [[ -z ${all_installed} ]] && all_installed="none"
3196 niro 1648
3197 niro 445 case ${state} in
3198     stable) state=${COLGREEN}"[s] ";;
3199     testing) state=${COLYELLOW}"[t] ";;
3200     unstable) state=${COLRED}"[u] ";;
3201     old) state=${COLGRAY}"[o] ";;
3202     esac
3203 niro 237
3204 niro 445 latest_available="${pver}-${pbuild}"
3205     else
3206     # package is masked
3207     state="${COLRED}[m] "
3208     latest_available="${COLRED}masked for this distribution.${COLDEFAULT}"
3209     fi
3210 niro 237
3211 niro 458 depsfull="$(get_value_from_magefile DEPEND ${magefile})"
3212     sdepsfull="$(get_value_from_magefile SDEPEND ${magefile})"
3213    
3214     while read sign dep
3215     do
3216     case ${dep} in
3217     "") continue;;
3218     esac
3219    
3220 niro 1961 if [[ -z ${deps} ]]
3221     then
3222     deps="$(basename ${dep%-*})"
3223     else
3224     deps="${deps} $(basename ${dep%-*})"
3225     fi
3226 niro 458 done << EOF
3227     ${depsfull}
3228     EOF
3229    
3230     while read sign dep
3231     do
3232     case ${dep} in
3233     "") continue;;
3234     esac
3235    
3236 niro 1961 if [[ -z ${sdeps} ]]
3237     then
3238     sdeps="$(basename ${dep%-*})"
3239     else
3240     sdeps="${sdeps} $(basename ${dep%-*})"
3241     fi
3242 niro 458 done << EOF
3243     ${sdepsfull}
3244     EOF
3245    
3246 niro 237 echo -e "${state}${pcat}/${pname}"${COLDEFAULT}
3247 niro 445 echo -e " Latest available: ${latest_available}"
3248 niro 237 echo " Installed versions: ${all_installed}"
3249     echo " Description: ${description}"
3250     echo " Homepage: ${homepage}"
3251 niro 1648 if [[ ! -z ${license} ]]
3252     then
3253     echo " License: ${license}"
3254     fi
3255 niro 1961 echo " Depends: ${deps}"
3256 niro 458 echo " SDepends: ${sdeps}"
3257 niro 237 echo
3258    
3259     unset pcat
3260     unset pname
3261     unset magefile
3262     unset pver
3263     unset pbuild
3264     unset state
3265     unset descriptiom
3266     unset homepage
3267     unset all_installed
3268     unset ipver
3269     unset ipbuild
3270 niro 458 unset depsfull
3271     unset sdepsfull
3272     unset deps
3273     unset sdeps
3274     unset dep
3275     unset sign
3276 niro 237 done
3277     }
3278 niro 249
3279     export_inherits()
3280     {
3281     local include="$1"
3282     shift
3283    
3284     while [ "$1" ]
3285     do
3286     local functions="$1"
3287    
3288     # sanity checks
3289     [ -z "${include}" ] && die "export_inherits(): \$include not given."
3290     [ -z "${functions}" ] && die "export_inherits(): \$functions not given."
3291    
3292     eval "${functions}() { ${include}_${functions} ; }"
3293    
3294     # debug
3295 niro 1584 mqueryfeature "debug" && typeset -f "${functions}"
3296 niro 249
3297     shift
3298     done
3299     }
3300 niro 350
3301     mlibdir()
3302     {
3303     local libdir=lib
3304     [[ ${ARCH} = x86_64 ]] && libdir=lib64
3305    
3306     echo "${libdir}"
3307     }
3308 niro 370
3309     ## blacklisted ${magefile}
3310     blacklisted()
3311     {
3312     [[ -z ${MAGE_DISTRIBUTION} ]] && local MAGE_DISTRIBUTION=stable
3313    
3314     # compat
3315     [[ ${USE_UNSTABLE} = true ]] && local MAGE_DISTRIBUTION=unstable
3316     [[ ${USE_TESTING} = true ]] && local MAGE_DISTRIBUTION=testing
3317    
3318 niro 892 # support both types for the moment
3319     if [[ -f /etc/mage-profile/package.blacklist-${ARCH}-${MAGE_DISTRIBUTION} ]]
3320     then
3321     local EXCLUDED="/etc/mage-profile/package.blacklist-${ARCH}-${MAGE_DISTRIBUTION}"
3322     else
3323     local EXCLUDED="/etc/mage-profile/package.blacklist-${ARCH}"
3324     fi
3325 niro 370
3326     # return 0 if the list not exist; nothin is masked
3327     [[ ! -f ${EXCLUDED} ]] && return 0
3328    
3329     local MAGEFILE="$1"
3330    
3331     local PCAT="$(magename2pcat ${MAGEFILE})"
3332     local PNAME="$(magename2pname ${MAGEFILE})"
3333     local PVER="$(magename2pver ${MAGEFILE})"
3334     local PBUILD="$(magename2pbuild ${MAGEFILE})"
3335    
3336     local EXPCAT EXPNAME EXPVER EXPBUILD
3337     while read EXPCAT EXPNAME EXPVER EXPBUILD
3338     do
3339     # ignore spaces and comments
3340     case "${EXPCAT}" in
3341     \#*|"") continue ;;
3342     esac
3343    
3344     # exclude full pver
3345     if [[ -n ${PCAT} ]] && [[ -n ${PNAME} ]] &&
3346     [[ -n ${EXPCAT} ]] && [[ -n ${EXPNAME} ]] &&
3347     [[ -n ${PVER} ]] && [[ -n ${PBUILD} ]] &&
3348     [[ -n ${EXPVER} ]] && [[ -n ${EXPBUILD} ]]
3349     then
3350     [[ ${EXPCAT}/${EXPNAME}-${EXPVER}-${EXPBUILD} = ${PCAT}/${PNAME}-${PVER}-${PBUILD} ]] && return 1
3351     fi
3352    
3353     # exclude pcat/pname only
3354     if [[ -n ${PCAT} ]] && [[ -n ${PNAME} ]] &&
3355     [[ -n ${EXPCAT} ]] && [[ -n ${EXPNAME} ]] &&
3356     [[ -z ${EXPVER} ]] && [[ -z ${EXPBUILD} ]]
3357     then
3358     [[ ${EXPCAT}/${EXPNAME} = ${PCAT}/${PNAME} ]] && return 1
3359     fi
3360     done << EOF
3361     $( cat ${EXCLUDED}; echo)
3362     EOF
3363    
3364     return 0
3365     }
3366    
3367 niro 1273 # need_busybox_support ${cmd}
3368     # return 0 (no error = needs busybox support) or return 1 (error = no busybox support required)
3369     need_busybox_support()
3370     {
3371     local cmd
3372 niro 1952 local busybox
3373 niro 1273 cmd="$1"
3374    
3375 niro 1952 for busybox in {,/usr}/bin/busybox
3376     do
3377     if [[ -x ${busybox} ]]
3378 niro 1273 then
3379 niro 2223 if [[ $(readlink $(type -P ${cmd})) = ${busybox} ]]
3380 niro 1952 then
3381     # needs busybox support
3382     return 0
3383     fi
3384 niro 1273 fi
3385 niro 1952 done
3386 niro 1318
3387     # no busybox
3388     return 1
3389 niro 1273 }
3390    
3391     # busybox_filter_wget_options ${wget_opts}
3392     busybox_filter_wget_options()
3393     {
3394     local opts="$@"
3395     local i
3396     local fixed_opts
3397    
3398     if need_busybox_support wget
3399     then
3400     for i in ${opts}
3401     do
3402     # show only the allowed ones
3403     case ${i} in
3404     -c|--continue) fixed_opts+=" -c" ;;
3405     -s|--spider) fixed_opts+=" -s" ;;
3406     -q|--quiet) fixed_opts+=" -q" ;;
3407     -O|--output-document) shift; fixed_opts+=" -O $1" ;;
3408     --header) shift; fixed_opts+=" --header $1" ;;
3409     -Y|--proxy) shift; fixed_opts+=" -Y $1" ;;
3410     -P) shift; fixed_opts+=" -P $1" ;;
3411     --no-check-certificate) fixed_opts+=" --no-check-certificate ${i}" ;;
3412     -U|--user-agent) shift; fixed_opts+=" -U ${i}" ;;
3413     # simply drop all other opts
3414     *) continue ;;
3415     esac
3416     done
3417    
3418     echo "${fixed_opts}"
3419     else
3420     echo "${opts}"
3421     fi
3422     }
3423 niro 1541
3424     have_root_privileges()
3425     {
3426     local retval
3427    
3428     if [[ $(id -u) = 0 ]]
3429     then
3430     retval=0
3431     else
3432     retval=1
3433     fi
3434    
3435     return ${retval}
3436     }
3437 niro 1584
3438     known_mage_feature()
3439     {
3440     local feature="$1"
3441     local retval
3442 niro 2167
3443 niro 1584 case "${feature}" in
3444     autosvc|!autosvc) retval=0 ;;
3445     buildlog|!buildlog) retval=0 ;;
3446     ccache|!ccache) retval=0 ;;
3447     check|!check) retval=0 ;;
3448     compressdoc|!compressdoc) retval=0 ;;
3449 niro 1627 debug|!debug) retval=0 ;;
3450 niro 1584 distcc|!distcc) retval=0 ;;
3451 niro 2167 icecc|!icecc) retval=0 ;;
3452 niro 1584 kernelsrcunpack|!kernelsrcunpack) retval=0 ;;
3453     libtool|!libtool) retval=0 ;;
3454     linuxsymlink|!linuxsymlink) retval=0 ;;
3455     pkgbuild|!pkgbuild) retval=0 ;;
3456 niro 1649 pkgdistrotag|!pkgdistrotag) retval=0 ;;
3457 niro 1584 purge|!purge) retval=0 ;;
3458     qalint|!qalint) retval=0 ;;
3459     regentree|!regentree) retval=0 ;;
3460 niro 1620 resume|!resume) retval=0 ;;
3461 niro 1584 srcpkgbuild|!srcpkgbuild) retval=0 ;;
3462     srcpkgtarball|!srcpkgtarball) retval=0 ;;
3463 niro 1627 static|!static) retval=0 ;;
3464     stepbystep|!stepbystep) retval=0 ;;
3465 niro 1584 strip|!strip) retval=0 ;;
3466 niro 1627 verbose|!verbose) retval=0 ;;
3467 niro 1584 *) retval=1 ;;
3468     esac
3469    
3470     return "${retval}"
3471     }
3472    
3473     load_mage_features()
3474     {
3475     for i in ${MAGE_FEATURES_GLOBAL[*]} ${MAGE_FEATURES[*]}
3476     do
3477     FVERBOSE=off msetfeature ${i}
3478     done
3479     }
3480    
3481     msetfeature()
3482     {
3483     local feature
3484     local count
3485     local i
3486     local found
3487    
3488     for feature in $@
3489     do
3490     found=0
3491     count="${#MAGE_FEATURES_CURRENT[*]}"
3492    
3493     if ! known_mage_feature "${feature}"
3494     then
3495 niro 1628 [[ ${FVERBOSE} = off ]] || echo -e "${COLRED}Unknown feature '${feature}', ignoring it${COLDEFAULT}"
3496 niro 1584 return 3
3497     fi
3498    
3499     for ((i=0; i<count; i++))
3500     do
3501     if [[ ${MAGE_FEATURES_CURRENT[${i}]} = ${feature} ]]
3502     then
3503 niro 1599 [[ ${FVERBOSE} = off ]] || echo -e "${COLBLUE}---${COLGREEN} Feature '${feature}' already enabled${COLDEFAULT}"
3504 niro 1584 MAGE_FEATURES_CURRENT[${i}]="${feature}"
3505     found=1
3506     elif [[ ${MAGE_FEATURES_CURRENT[${i}]} = !${feature} ]]
3507     then
3508 niro 1599 [[ ${FVERBOSE} = off ]] || echo -e "${COLBLUE}---${COLGREEN} Feature '${feature}' currently disabled, enabling it!${COLDEFAULT}"
3509 niro 1584 MAGE_FEATURES_CURRENT[${i}]="${feature}"
3510     found=1
3511     elif [[ ${MAGE_FEATURES_CURRENT[${i}]} = ${feature//!} ]]
3512     then
3513 niro 1599 [[ ${FVERBOSE} = off ]] || echo -e "${COLBLUE}---${COLGREEN} Feature '${feature//!}' currently enabled, disabling it!${COLDEFAULT}"
3514 niro 1584 MAGE_FEATURES_CURRENT[${i}]="${feature}"
3515     found=1
3516     fi
3517     done
3518    
3519     # if the feature was not found after proccessing the whole array
3520     # it was not declared. in this case enable it
3521     if [[ ${found} = 0 ]]
3522     then
3523 niro 1599 [[ ${FVERBOSE} = off ]] || echo -e "${COLBLUE}---${COLGREEN} Feature '${feature}' was not declared, enabling it!${COLDEFAULT}"
3524 niro 1584 MAGE_FEATURES_CURRENT=( ${MAGE_FEATURES_CURRENT[*]} "${feature}" )
3525     fi
3526    
3527 niro 2724 export MAGE_FEATURES_CURRENT
3528 niro 1584 done
3529     }
3530    
3531     mqueryfeature()
3532     {
3533     local feature="$1"
3534     local retval=1
3535     local i
3536    
3537     if known_mage_feature "${feature}"
3538     then
3539     for i in ${MAGE_FEATURES_CURRENT[*]}
3540     do
3541     if [[ ${i} = ${feature} ]]
3542     then
3543     retval=0
3544     break # found break here
3545     fi
3546     done
3547     else
3548 niro 1628 [[ ${FVERBOSE} = off ]] || echo -e "${COLRED}Unknown feature '${feature}', ignoring it${COLDEFAULT}"
3549 niro 1584 retval=3
3550     fi
3551    
3552     return ${retval}
3553     }
3554    
3555     mprintfeatures()
3556     {
3557 niro 1781 echo -e "${COLRED}Global features:${COLDEFAULT} ${MAGE_FEATURES_GLOBAL[*]}"
3558     echo -e "${COLYELLOW}Local features:${COLDEFAULT} ${MAGE_FEATURES[*]}"
3559     echo -e "${COLGREEN}Current features:${COLDEFAULT} ${MAGE_FEATURES_CURRENT[*]}"
3560 niro 1584 }