source: src-sh/pbi-manager10/pbi-manager @ c65ccb6

9.2-releasereleng/10.0releng/10.0.1
Last change on this file since c65ccb6 was c65ccb6, checked in by Kris Moore <kris@…>, 6 months ago

Fix an issue getting PBI_PROGVERSION from pkgng

  • Property mode set to 100755
File size: 221.1 KB
Line 
1#!/bin/sh
2#
3# Copyright 2013 iXsystems (Kris Moore)
4# All rights reserved
5#
6# Redistribution and use in source and binary forms, with or without
7# modification, are permitted providing that the following conditions
8# are met:
9# 1. Redistributions of source code must retain the above copyright
10#    notice, this list of conditions and the following disclaimer.
11# 2. Redistributions in binary form must reproduce the above copyright
12#    notice, this list of conditions and the following disclaimer in the
13#    documentation and/or other materials provided with the distribution.
14#
15# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18# ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
19# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
23# STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
24# IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25# POSSIBILITY OF SUCH DAMAGE.
26
27usage_add_pbi() {
28        cat <<EOF
29usage: `basename $0` [options] pbi
30
31Options:
32  -e             -- Extract Only
33  -f             -- Force install, overwriting existing installation
34  -g             -- Get and show path to icon / images for gui installer
35  -i             -- Display information about this PBI
36  -l             -- Display LICENSE text
37  -o outdir      -- Extract to target directory
38  -r             -- Fetch and install PBI
39  -R             -- Fetch install file and save to disk (Do not install)
40  -v             -- Enable verbose output
41  --checkscript  -- Display any custom install / removal scripts
42  --licagree     -- Agree to LICENSE terms for installation
43  --meta         -- Display any custom meta-file supplied with the PBI
44  --no-checksum  -- Skip the checksum verification during installation
45  --no-checksig  -- Ignore signature verification and force install
46  --no-hash      -- Disable using shared hash folder for PBI
47  --rArch arch   -- Used with -r to specify the specific PBI machine type
48  --rVer ver     -- Used with -r to specify the specific PBI version
49  --repo repoid  -- Used with -r to specify the specific repo to pull from
50
51EOF
52        exit_trap
53}
54
55usage_autob_pbi() {
56        cat <<EOF
57usage: `basename $0` [options]
58
59Options:
60  -c confdir   -- Directory to traverse looking for meta-data modules <required>
61  -d portdir   -- Use different ports dir (Default: /usr/ports)
62  -h script    -- Call the following helper script after each build
63  -o outdir    -- Where to place the finished PBI file(s) <required>
64  -p <num>     -- Number of PBI builds to run concurrently (Defaults to 1)
65  -32          -- Build i386 PBIs on amd64 host
66  -32fallback  -- On amd64 host, build 32bit PBIs if only i386 can be built
67  --genpatch   -- Generate patch files (*.pbp) from archived PBIs to current
68  --keep <num> -- Keep <num> old versions in archive folder for each built PBI
69  --prune      -- Remove files from 'outdir' that no longer have a module
70  --pkgbuild   -- Build the PBIs using packages from PKGNG
71  --tmpfs      -- Use TMPFS for port WRKDIRPREFIX
72  --sign key   -- Sign the PBI(s) with specified openssl key
73
74EOF
75        exit_trap
76}
77
78
79usage_create_pbi() {
80        cat <<EOF
81usage: `basename $0` [options] pbidir
82
83Options:
84  -a author    -- Application Author
85  -b           -- Make a backup of an already installed PBI
86  -c confdir   -- PBI configuration meta-data directory
87  -d portdir   -- Use different ports dir (Default: /usr/ports)
88  -i icon      -- Application Icon, relative to pbidir/
89  -n name      -- Application Name
90  -o outdir    -- Output directory for finished .pbi file
91  -p port      -- Pull name / version from FreeBSD Port
92  -r version   -- Application Version
93  -w url       -- Application Website
94  --meta file  -- Include the specified <file> inside the PBI header
95                  for display with "pbi_add --meta"
96  --no-hash    -- Disable using shared hash folder for PBI
97  --sign key   -- Sign the PBI with specified openssl key
98
99EOF
100        exit_trap
101}
102
103usage_delete_pbi() {
104        cat <<EOF
105usage: `basename $0` [options] pbi
106
107Options:
108  -v             -- Enable verbose output
109  --clean-hdir   -- Perform a full cleaning of hash dir (Does not remove any PBIs)
110
111EOF
112        exit_trap
113}
114
115usage_make_pbi() {
116        cat <<EOF
117usage: `basename $0` [options] port
118
119Options:
120  -B           -- Build-only, do not run pbi_create when finished
121  -c confdir   -- PBI configuration meta-data directory
122  -d portdir   -- Use different ports dir (Default: /usr/ports)
123  -k           -- Keep build files, don't delete when finished
124  -o outdir    -- Where to place the finished PBI file
125  -p prefix    -- Specify alternate PBI Compile PREFIX
126  -32          -- Build i386 PBI on amd64 host
127  --delbuild   -- Delete existing build dirs if they exist
128  --meta file  -- Include the specified meta file in the PBI header
129  --mkdebug    -- Drop to debug shell if port make fails
130  --pkgbuild   -- Build PBI from PKGNG package repo
131  --tmpfs      -- Use TMPFS for port WRKDIRPREFIX
132  --no-prune   -- Do not prune non REQUIREDBY ports
133  --sign key   -- Sign the PBI with specified openssl key
134
135EOF
136        exit_trap
137}
138
139usage_icon_pbi() {
140        cat <<EOF
141usage: `basename $0` [options] pbi
142
143Options:
144  add-desktop          -- Add desktop icons
145  add-menu             -- Add menu icons
146  add-mime             -- Add mime registration
147  add-pathlnk          -- Add PATH links
148  del-desktop          -- Remove desktop icons
149  del-menu             -- Remove menu icons
150  del-mime             -- Remove mime registration
151  del-pathlnk          -- Remove PATH links
152
153EOF
154        exit_trap
155}
156
157usage_info_pbi() {
158        cat <<EOF
159usage: `basename $0` [options] pbi
160
161Options:
162  -a             -- Show all installed PBIs
163  -v             -- Enable verbose output
164
165EOF
166        exit_trap
167}
168
169usage_makepatch_pbi() {
170        cat <<EOF
171usage: `basename $0` [options] oldpbi newpbi
172               
173Options:
174  -o outdir      -- Save the .PBP file to outdir
175  --tmpfs        -- Use TMPFS for extracting PBIs
176  --sign key     -- Sign the PBI with specified openssl key
177  --no-checksig  -- Ignore signature verification and force install
178
179
180EOF
181        exit_trap
182}
183
184usage_addrepo_pbi() {
185        cat <<EOF
186usage: `basename $0` <Repo File>
187               
188EOF
189        exit_trap
190}
191
192usage_deleterepo_pbi() {
193        cat <<EOF
194usage: `basename $0` <Repo ID>
195               
196EOF
197        exit_trap
198}
199
200usage_mt_add() {
201        cat <<EOF
202usage: `basename $0` add [options] metafile
203               
204Options:
205  --cat         -- Adding a new category metadata
206  --app         -- Adding a new application metadata
207  -a author     -- Application author
208  -c category   -- Application category
209  -d desc       -- Description for application / category (Required)
210  -i icon       -- URL pointing to 64x64 PNG application / category icon (Required)
211  -k keywords   -- Application keywords for searching
212  -l license    -- Application license type
213                   Example: BSD, GPL, Commercial
214  -n name       -- Application / category name (Required)
215  -t type       -- Application interface type
216                   Example; Graphical, Text, Service
217  -u url        -- Application homepage URL
218  -r            -- Application must be installed as root
219
220EOF
221        exit_trap
222}
223
224usage_it_add() {
225        cat <<EOF
226usage: `basename $0` add [options] indexfile
227               
228Options:
229  -b vers       -- Mark previous versions as having binary diff patches available
230                   I.E. (2.7.3,2.8.1,2.8.2)
231  -f pbifile    -- The PBI file we are adding to the index (Required)
232  -k num        -- The number of previous versions of this PBI to keep in the index
233  -u fileurl    -- The URL to this PBI on the mirror server(s) (Required)
234
235EOF
236        exit_trap
237}
238
239usage_mt_rem() {
240        cat <<EOF
241usage: `basename $0` rem [options] metafile
242               
243Options:
244  --cat         -- Removing category metadata
245  --app         -- Removing application metadata
246  -n name       -- The name we are removing from the metafile (Required)
247
248EOF
249        exit_trap
250}
251
252usage_mt_syncpbi() {
253        cat <<EOF
254usage: `basename $0` syncpbi pbifile metafile
255
256This command will sync the meta-data from a PBI into the repo metafile
257               
258EOF
259        exit_trap
260}
261
262usage_it_rem() {
263        cat <<EOF
264usage: `basename $0` rem [options] indexfile
265               
266Options:
267  -m arch       -- The PBI architecture to remove (Required)
268                   I.E. (i386,amd64,etc)
269  -n pbiname    -- The PBI name we are removing from the index (Required)
270  -v version    -- The version of the PBI to remove (Required)
271
272EOF
273        exit_trap
274}
275
276usage_mt_unknown() {
277        cat <<EOF
278usage: `basename $0` [options] metafile
279               
280Options:
281  add           -- Add a new entry to the specified metafile
282  rem           -- Remove an entry in the metafile
283  syncpbi       -- Sync meta-data from a PBI file
284
285EOF
286        exit_trap
287}
288
289usage_it_unknown() {
290        cat <<EOF
291usage: `basename $0` [options] indexfile
292               
293Options:
294  add           -- Add a new entry to the specified indexfile
295  rem           -- Remove an entry in the indexfile
296
297EOF
298        exit_trap
299}
300
301usage_browse_pbi() {
302        cat <<EOF
303usage: `basename $0` [options] [repoid]
304               
305Options:
306  -c category   -- List PBIs from the specified category
307  -s search     -- Search for the specified string
308  --listcats    -- List the available categories in this repository
309
310EOF
311        exit_trap
312}
313
314usage_listrepo_pbi() {
315        cat <<EOF
316usage: `basename $0` [options] [repoid]
317               
318Options:
319  --down        -- Move the specified repoid down in priority
320  --mirror url  -- Change the target repoid's mirror url
321  --up          -- Move the specified repoid up in priority
322
323EOF
324        exit_trap
325}
326
327usage_makerepo_pbi() {
328        cat <<EOF
329usage: `basename $0` [options] [outdir]
330               
331Options:
332  --desc description    -- Description for this new repo
333  --key key             -- Path to the public key file for this repo
334  --url url             -- Base URL for fetching the INDEX files
335  --mirror mirrorurl    -- Mirror url(s) for fetching PBIs, use ',' as
336                           seperator for multiple
337
338EOF
339        exit_trap
340}
341
342usage_patch_pbi() {
343        cat <<EOF
344usage: `basename $0` [options] pbp
345               
346Options:
347  -e             -- Extract Only
348  -g             -- Get and show path to icon / images for gui installer
349  -i             -- Display information about this PBI
350  -o outdir      -- Extract to target directory
351  --checkscript  -- Display any custom install / removal scripts
352  --no-checksig  -- Ignore signature verification and force install
353  --no-hash      -- Disable using shared hash folder for PBI
354
355EOF
356        exit_trap
357}
358
359# update usage
360usage_update_pbi() {
361        cat <<EOF
362usage: `basename $0` [options] pbi
363
364Options:
365  -c              -- Check-only, do not update target PBI
366  --check-all     -- Perform a full check of all PBIs for updates
367  --disable-auto  -- Disable auto-updating for the target PBI
368  --enable-auto   -- Enable auto-updating for the target PBI
369  --update-all    -- Update all PBIs to latest versions
370
371EOF
372        exit_trap
373}
374
375# Parse the command line for info
376parse_delete_pbi_cmdline() {
377        while [ $# -gt 0 ]; do
378                case "$1" in
379                -v)     PBI_VERBOSE="YES" 
380                        ;;
381      --clean-hdir)     pbi_clean_hashdir
382                        exit_trap
383                        ;;
384                 *)     if [ $# -gt 1 ]; then usage_delete_pbi; fi
385                        if [ ! -e "${PBI_DBAPPDIR}/${1}" ] ; then
386                                find_pbi_namematch "$1"
387                                if [ -z "$PBI_NAMEMATCH" ] ; then
388                                        exit_err "can't find installed pbi (${1})"
389                                fi
390                                PBI_DELETENAME="$PBI_NAMEMATCH"
391                        else
392                                PBI_DELETENAME="$1"
393                        fi
394                        ;;
395                esac
396                shift
397        done
398        if [ -z "${PBI_DELETENAME}" ];then usage_delete_pbi; fi
399}
400
401find_pbi_namematch()
402{
403        _fLow="`echo ${1} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
404        PBI_NAMEMATCH=""
405        for i in `ls -d ${PBI_DBAPPDIR}/* 2>/dev/null`
406        do
407                if [ ! -e "$i/pbi_name" ] ; then continue ; fi
408                _tLow="`cat $i/pbi_name | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
409                if [ "$_tLow" = "$_fLow" ] ; then
410                        PBI_NAMEMATCH="`basename ${i}`"
411                        break
412                fi
413        done
414}
415
416# Parse the command line for icon
417parse_icon_pbi_cmdline() {
418        while [ $# -gt 0 ]; do
419                case "$1" in
420                add-desktop)    PBI_DESKADD="YES" ;;
421                add-menu)       PBI_MENUADD="YES" ;;
422                add-mime)       PBI_MIMEADD="YES" ;;
423                add-pathlnk)    PBI_PATHADD="YES" ;;
424                del-desktop)    PBI_DESKDEL="YES" ;;
425                del-menu)       PBI_MENUDEL="YES" ;;
426                del-mime)       PBI_MIMEDEL="YES" ;;
427                del-pathlnk)    PBI_PATHDEL="YES" ;;
428                 *)
429                        if [ $# -gt 1 ]; then usage_icon_pbi; fi
430                        if [ ! -e "${PBI_DBAPPDIR}/${1}" ] ; then
431                                find_pbi_namematch "$1"
432                                if [ -z "$PBI_NAMEMATCH" ] ; then
433                                        exit_err "can't find installed pbi (${1})"
434                                fi
435                                PBI_ICONTARGETAPP="${PBI_NAMEMATCH}"
436                        else
437                                PBI_ICONTARGETAPP="$1"
438                        fi
439                        ;;
440                esac
441                shift
442        done
443        if [ -z "${PBI_ICONTARGETAPP}" ] ; then
444                usage_icon_pbi
445        fi
446}
447
448# Parse the command line for pbid
449parse_pbid_cmdline() {
450        while [ $# -gt 0 ]; do
451                case "$1" in
452                -v)     PBI_VERBOSE="YES" 
453                        ;;
454         --refresh)     # Schedule us to refresh the index
455                        echo "Your meta and index files will begin refreshing in a moment..."
456                        echo "Details available in /var/log/pbid.log"
457                        rm ${PBI_DBINDEXDIR}/*.time >/dev/null 2>/dev/null
458                        if [ -e "${PROGBASE}/etc/rc.d/pbid" ]; then
459                           ${PROGBASE}/etc/rc.d/pbid restart >/dev/null 2>/dev/null
460                        fi
461                        exit 0
462                        ;;
463                esac
464                shift
465        done
466}
467
468# Parse the command line for info
469parse_info_pbi_cmdline() {
470        while [ $# -gt 0 ]; do
471                case "$1" in
472                -a)     PBI_INFONAME="--ALL--"
473                        ;;
474                -i)     PBI_INFOINDEX="YES"     
475                        ;;
476                -v)     PBI_VERBOSE="YES" 
477                        ;;
478                 *)
479                        if [ $# -gt 1 ]; then usage_info_pbi; fi
480                        if [ ! -e "${PBI_DBAPPDIR}/${1}" ] ; then
481                                find_pbi_namematch "$1"
482                                if [ -z "$PBI_NAMEMATCH" ] ; then
483                                        exit_err "can't find installed pbi (${1})"
484                                fi
485                                PBI_INFONAME="$PBI_NAMEMATCH"
486                        else
487                                PBI_INFONAME="$1"
488                        fi
489                        ;;
490                esac
491                shift
492        done
493        if [ -z "${PBI_INFONAME}" ] ; then
494                PBI_INFONAME="--ALL--" 
495        fi
496}
497
498# Parse the command line for patching
499parse_makepatch_pbi_cmdline() {
500        while [ $# -gt 0 ]; do
501                case "$1" in
502                -o)     if [ $# -eq 1 ]; then usage_makepatch_pbi; fi
503                        shift; PBI_PATCHOUTDIR="$1"
504                        ;;
505            --sign)     if [ $# -eq 1 ]; then usage_makepatch_pbi; fi
506                        shift; PBI_SSLPRIVKEY="$1"
507                        ;;
508           --tmpfs)     PBI_MP_TMPFS="YES" 
509                        ;;
510     --no-checksig)     PBI_SKIPSIGVERIFY="YES" ;;
511                 *)     if [ $# -gt 2  ]; then usage_makepatch_pbi; fi
512                        PBI_OLDFILENAME="$1"
513                        shift
514                        PBI_FILENAME="$1"
515                        ;;
516                esac
517                shift
518        done
519
520        if [ -z "${PBI_FILENAME}" ]; then usage_makepatch_pbi ; fi
521        if [ -z "${PBI_OLDFILENAME}" ]; then usage_makepatch_pbi ; fi
522        if [ -z "${PBI_PATCHOUTDIR}" ]; then PBI_PATCHOUTDIR=`pwd` ; fi
523
524        # Load all the information about this PBI / PBP
525        load_info_from_header
526}
527
528# Parse the command line for editing a meta file
529parse_mt_pbi_cmdline() {
530
531        case $1 in
532        syncpbi) PBI_MT_MODE="SYNCPBI" ; shift ;
533                PBI_MT_PBIFILE="$1"
534                PBI_MT_METAFILE="$2"
535                if [ -z "${PBI_MT_PBIFILE}" ] ; then usage_mt_syncpbi ; fi
536                if [ -z "${PBI_MT_METAFILE}" ] ; then usage_mt_syncpbi ; fi
537                return
538                ;;
539           add) PBI_MT_MODE="ADD" ; shift ;
540                while [ $# -gt 0 ]; do
541                        case "$1" in
542                      --cat) PBI_MT_TYPE="CAT" ;;
543                      --app) PBI_MT_TYPE="APP" ;;
544                        -n) if [ $# -eq 1  ]; then usage_mt_add; fi
545                            shift; PBI_MT_ADDNAME="$1"
546                            ;;
547                        -i) if [ $# -eq 1  ]; then usage_mt_add; fi
548                            shift; PBI_MT_ADDICON="$1"
549                            ;;
550                        -d) if [ $# -eq 1  ]; then usage_mt_add; fi
551                            shift; PBI_MT_ADDDESC="$1"
552                            ;;
553                        -c) if [ $# -eq 1  ]; then usage_mt_add; fi
554                            shift; PBI_MT_ADDCAT="$1"
555                            ;;
556                        -a) if [ $# -eq 1  ]; then usage_mt_add; fi
557                            shift; PBI_MT_ADDAUTHOR="$1"
558                            ;;
559                        -u) if [ $# -eq 1  ]; then usage_mt_add; fi
560                            shift; PBI_MT_ADDURL="$1"
561                            ;;
562                        -l) if [ $# -eq 1  ]; then usage_mt_add; fi
563                            shift; PBI_MT_ADDLIC="$1"
564                            ;;
565                        -t) if [ $# -eq 1  ]; then usage_mt_add; fi
566                            shift; PBI_MT_ADDTYPE="$1"
567                            ;;
568                        -k) if [ $# -eq 1  ]; then usage_mt_add; fi
569                            shift; PBI_MT_ADDKEYWORDS="$1"
570                            ;;
571                        -r) PBI_MT_REQUIRESROOT="YES"
572                            ;;
573                         *) if [ $# -gt 1  ]; then usage_mt_add; fi
574                            PBI_MT_METAFILE="$1"
575                            ;;
576                        esac
577                        shift
578                done
579                if [ -z "${PBI_MT_METAFILE}" ] ; then usage_mt_add ; fi
580                ;;
581           rem) PBI_MT_MODE="REM" ; shift ;
582                while [ $# -gt 0 ]; do
583                        case "$1" in
584                      --cat) PBI_MT_TYPE="CAT" ;;
585                      --app) PBI_MT_TYPE="APP" ;;
586                        -n) if [ $# -eq 1  ]; then usage_mt_rem; fi
587                            shift; PBI_MT_REMNAME="$1"
588                            ;;
589                         *) if [ $# -gt 1  ]; then usage_mt_rem; fi
590                            PBI_MT_METAFILE="$1"
591                            ;;
592                        esac
593                        shift
594                done
595                if [ -z "${PBI_MT_METAFILE}" ] ; then usage_mt_rem ; fi
596                ;;
597             *) usage_mt_unknown ;;
598        esac
599
600        if [ ! -f "${PBI_MT_METAFILE}" ] ; then
601                exit_err "No such file ${PBI_MT_METAFILE}"
602        fi
603
604        # Sanity check the values
605        case ${PBI_MT_MODE} in
606                ADD) # Check the common values
607                     if [ -z "${PBI_MT_ADDNAME}" ] ; then usage_mt_add ; fi
608                     if [ -z "${PBI_MT_ADDICON}" ] ; then usage_mt_add ; fi
609                     if [ -z "${PBI_MT_ADDDESC}" ] ; then usage_mt_add ; fi
610
611                     if [ "$PBI_MT_TYPE" = "CAT" ]; then             
612                     elif [ "$PBI_MT_TYPE" = "APP" ]; then
613                        if [ -z "${PBI_MT_ADDCAT}" ]; then usage_mt_add ; fi
614                        if [ -z "${PBI_MT_ADDAUTHOR}" ]; then usage_mt_add ; fi
615                        if [ -z "${PBI_MT_ADDURL}" ]; then usage_mt_add ; fi
616                        if [ -z "${PBI_MT_ADDLIC}" ]; then usage_mt_add ; fi
617                        if [ -z "${PBI_MT_ADDTYPE}" ]; then usage_mt_add ; fi
618                        if [ -z "${PBI_MT_ADDKEYWORDS}" ]; then usage_mt_add;fi
619                     else
620                       usage_mt_add
621                     fi
622                ;;
623                REM) if [ "$PBI_MT_TYPE" != "CAT" -a "$PBI_MT_TYPE" != "APP" ]
624                     then
625                        usage_mt_rem
626                     fi
627                     if [ -z "${PBI_MT_REMNAME}" ] ; then usage_mt_rem ; fi
628                ;;
629        esac
630
631}
632
633# Parse the command line for editing a index file
634parse_it_pbi_cmdline() {
635
636        case $1 in
637           add) PBI_IT_MODE="ADD" ; shift ;
638                while [ $# -gt 0 ]; do
639                        case "$1" in
640                        -b) if [ $# -eq 1  ]; then usage_it_add; fi
641                            shift; PBI_IT_ADDBPVERS="$1"
642                            ;;
643                        -f) if [ $# -eq 1  ]; then usage_it_add; fi
644                            shift; PBI_IT_ADDFILE="$1"
645                            ;;
646                        -k) if [ $# -eq 1  ]; then usage_it_add; fi
647                            shift; PBI_IT_ADDKEEP="$1"
648                            ;;
649                        -u) if [ $# -eq 1  ]; then usage_it_add; fi
650                            shift; PBI_IT_ADDURL="$1"
651                            ;;
652                         *) if [ $# -gt 1  ]; then usage_it_add; fi
653                            PBI_IT_ADDINDEX="$1"
654                            ;;
655                        esac
656                        shift
657                done
658                ;;
659           rem) PBI_IT_MODE="REM" ; shift ;
660                while [ $# -gt 0 ]; do
661                        case "$1" in
662                        -m) if [ $# -eq 1  ]; then usage_it_rem; fi
663                            shift; PBI_IT_REMARCH="$1"
664                            ;;
665                        -n) if [ $# -eq 1  ]; then usage_it_rem; fi
666                            shift; PBI_IT_REMNAME="$1"
667                            ;;
668                        -v) if [ $# -eq 1  ]; then usage_it_rem; fi
669                            shift; PBI_IT_REMVER="$1"
670                            ;;
671                         *) if [ $# -gt 1  ]; then usage_it_rem; fi
672                            PBI_IT_REMINDEX="$1"
673                            ;;
674                        esac
675                        shift
676                done
677                ;;
678             *) usage_it_unknown ;;
679        esac
680
681        # Sanity check the values
682        case ${PBI_IT_MODE} in
683                ADD) if [ -z "${PBI_IT_ADDFILE}" ] ; then usage_it_add ; fi
684                     if [ -z "${PBI_IT_ADDURL}" ] ; then usage_it_add ; fi
685                     if [ -z "${PBI_IT_ADDINDEX}" ] ; then usage_it_add ; fi
686                     if [ ! -f "${PBI_IT_ADDFILE}" ] ; then
687                        exit_err "No such file ${PBI_IT_ADDFILE}"
688                     fi
689                     if [ ! -f "${PBI_IT_ADDINDEX}" ] ; then
690                        exit_err "No such file ${PBI_IT_ADDINDEX}"
691                     fi
692                     if [ -n "${PBI_IT_ADDKEEP}" ] ; then
693                        expr ${PBI_IT_ADDKEEP} + 1 >/dev/null 2>/dev/null
694                        if [ "$?" != "0" ] ; then
695                                exit_err "-k option must be a integer!"
696                        fi
697                     fi
698                ;;
699                REM) if [ -z "${PBI_IT_REMNAME}" ] ; then usage_it_rem ; fi
700                     if [ -z "${PBI_IT_REMVER}" ] ; then usage_it_rem ; fi
701                     if [ -z "${PBI_IT_REMARCH}" ] ; then usage_it_rem ; fi
702                     if [ -z "${PBI_IT_REMINDEX}" ] ; then usage_it_rem ; fi
703                ;;
704        esac
705
706}
707
708# Parse the command line for browsing a repo
709parse_browse_pbi_cmdline() {
710        while [ $# -gt 0 ]; do
711                case "$1" in
712        --listcats)     PBI_BROWSE_LISTCATS="YES" ;;
713         --viewall)     PBI_BROWSE_LISTALLPBI="YES" ;;
714                -c)     if [ $# -eq 1  ]; then usage_browse_pbi; fi
715                        shift; PBI_BROWSE_CAT="$1"
716                        ;;
717                -s)     if [ $# -eq 1  ]; then usage_browse_pbi; fi
718                        shift; PBI_BROWSE_SEARCH="$1"
719                        ;;
720                 *)     if [ $# -gt 1  ]; then usage_browse_pbi; fi
721                        PBI_BROWSE_RID="$1"
722                        ;;
723                esac
724                shift
725        done
726
727        # Get / check the repoid
728        if [ -n "${PBI_BROWSE_RID}" ] ; then
729                ls ${PBI_DBREPODIR}/${PBI_BROWSE_RID}.* >/dev/null 2>/dev/null
730                if [ "$?" != "0" ] ; then
731                        exit_err "The specified repoid ${PBI_BROWSE_RID} does not exist!"
732                fi
733        else
734                for _repo in `ls ${PBI_DBREPODIR} 2>/dev/null`
735                do
736                        PBI_BROWSE_RID=`echo $_repo | cut -d '.' -f 1`
737                        break;
738                done
739                if [ -z "$PBI_BROWSE_RID" ] ; then exit_err "No available repos!" ; fi
740        fi
741
742        PBI_BROWSE_REPOMD5=`ls ${PBI_DBREPODIR}/${PBI_BROWSE_RID}.* 2>/dev/null | cut -d '.' -f 2`
743        PBI_BROWSE_METAFILE=`ls ${PBI_DBINDEXDIR}/${PBI_BROWSE_REPOMD5}*meta 2>/dev/null`
744        if [ -z "${PBI_BROWSE_METAFILE}" ] ; then
745                exit_err "The specified repo has no meta-file."
746        fi
747
748}
749
750# Parse the command line for listing repos
751parse_listrepo_pbi_cmdline() {
752        while [ $# -gt 0 ]; do
753                case "$1" in
754              --up)     PBI_LISTREPO_UP="YES" ;;
755            --down)     PBI_LISTREPO_DOWN="YES" ;;
756          --mirror)     if [ $# -eq 1  ]; then usage_listrepo_pbi; fi
757                        shift; PBI_LISTREPO_MIRROR="$1"
758                        ;;
759                 *)     if [ $# -gt 1  ]; then usage_listrepo_pbi; fi
760                        PBI_LISTREPO_ID="$1"
761                        ;;
762                esac
763                shift
764        done
765
766        if [ "${PBI_LISTREPO_UP}" = "YES" -a "${PBI_LISTREPO_DOWN}" = "YES" ]; then
767                exit_err "Options --up and --down can't both be used at once!"
768        fi
769        if [ "${PBI_LISTREPO_UP}" = "YES" -a -z "${PBI_LISTREPO_ID}" ]; then
770                exit_err "Missing Repo ID to move up in priority."
771        fi
772        if [ "${PBI_LISTREPO_DOWN}" = "YES" -a -z "${PBI_LISTREPO_ID}" ]; then
773                exit_err "Missing Repo ID to move down in priority."
774        fi
775        if [ -n "${PBI_LISTREPO_MIRROR}" -a -z "${PBI_LISTREPO_ID}" ]; then
776                exit_err "Missing Repo ID to change a specific mirror URL."
777        fi
778
779        if [ -n "${PBI_LISTREPO_ID}" ] ; then
780                ls ${PBI_DBREPODIR}/${PBI_LISTREPO_ID}.* >/dev/null 2>/dev/null
781                if [ "$?" != "0" ] ; then
782                        exit_err "The specified repoid ${PBI_LISTREPO_ID} does not exist!"
783                fi
784        fi
785}
786
787# Parse the command line for adding a new repo file
788parse_addrepo_pbi_cmdline() {
789        while [ $# -gt 0 ]; do
790                case "$1" in
791                 *)     if [ $# -gt 1  ]; then usage_addrepo_pbi; fi
792                        PBI_ADDREPO_FILE="$1"
793                        ;;
794                esac
795                shift
796        done
797
798        if [ -z "$PBI_ADDREPO_FILE" ] ; then
799                usage_addrepo_pbi
800        fi
801        if [ ! -f "$PBI_ADDREPO_FILE" ] ; then
802                exit_err "Repo file ${PBI_ADDREPO_FILE} does not exist!"
803        fi
804}
805
806# Parse the command line for deleting a repo
807parse_deleterepo_pbi_cmdline() {
808        while [ $# -gt 0 ]; do
809                case "$1" in
810                 *)     if [ $# -gt 1  ]; then usage_deleterepo_pbi; fi
811                        PBI_DELREPO_ID="$1"
812                        ;;
813                esac
814                shift
815        done
816
817        if [ -z "$PBI_DELREPO_ID" ] ; then
818                usage_deleterepo_pbi
819        fi
820}
821
822
823# Parse the command line for making a new repo file
824parse_makerepo_pbi_cmdline() {
825        while [ $# -gt 0 ]; do
826                case "$1" in
827             --key)     if [ $# -eq 1 ]; then usage_makerepo_pbi; fi
828                        shift; PBI_MKREPO_KEY="$1"
829                        ;;
830             --url)     if [ $# -eq 1 ]; then usage_makerepo_pbi; fi
831                        shift; PBI_MKREPO_URL="$1"
832                        ;;
833            --desc)     if [ $# -eq 1 ]; then usage_makerepo_pbi; fi
834                        shift; PBI_MKREPO_DESC="$1"
835                        ;;
836          --mirror)     if [ $# -eq 1 ]; then usage_makerepo_pbi; fi
837                        shift; PBI_MKREPO_MIRROR="$1"
838                        ;;
839                 *)     if [ $# -gt 1  ]; then usage_makerepo_pbi; fi
840                        PBI_MKREPO_OUTDIR="$1"
841                        ;;
842                esac
843                shift
844        done
845
846        if [ -z "${PBI_MKREPO_DESC}" ]; then usage_makerepo_pbi ; fi
847        if [ -z "${PBI_MKREPO_KEY}" ]; then usage_makerepo_pbi ; fi
848        if [ -z "${PBI_MKREPO_MIRROR}" ]; then usage_makerepo_pbi ; fi
849        if [ -z "${PBI_MKREPO_URL}" ]; then usage_makerepo_pbi ; fi
850        if [ -z "${PBI_MKREPO_OUTDIR}" ]; then PBI_MKREPO_OUTDIR="${HOME}"; fi
851        if [ ! -f "${PBI_MKREPO_KEY}" ]; then exit_err "The key file ${PBI_MKREPO_KEY} does not exist." ; fi
852       
853        # Make sure we have a valid URL format
854        echo "${PBI_MKREPO_URL}" | grep -q -e "^http://" -e "^https://" -e "^ftp://"
855        if [ $? -ne 0 ] ; then
856                exit_err "Repo URL must begin with http://, https://, or ftp://"
857        fi
858       
859
860}
861
862# Parse the command line for patching
863parse_patch_pbi_cmdline() {
864        while [ $# -gt 0 ]; do
865                case "$1" in
866                -e)     PBI_EXTRACTONLY="YES"
867                        ;;
868                -g)     PBI_ADD_GUIDISPLAY="YES" 
869                        ;;
870                -i)     PBI_ADD_INFODISPLAY="YES" 
871                        ;;
872                -o)
873                        if [ $# -eq 1 ]; then usage_patch_pbi; fi
874                        shift; PBI_ALTEXTRACT_DIR="$1"
875                        ;;
876     --checkscript)     PBI_CHECKSCRIPTS="YES" ;;
877         --no-hash)     PBI_DISABLEHASHDIR="YES" ;;
878     --no-checksum)     PBI_SKIPCHECKSUM="YES" ;;
879     --no-checksig)     PBI_SKIPSIGVERIFY="YES" ;;
880                 *)     if [ $# -gt 1 ]; then usage_patch_pbi; fi
881                        PBI_FILENAME="$1"
882                        ;;
883                esac
884                shift
885        done
886
887        if [ -z "${PBI_FILENAME}" ]; then usage_patch_pbi ; fi
888
889        # Get the absolute patch to the file
890        get_abspath "$PBI_FILENAME"
891        PBI_FILENAME="$_ABSPATH"
892
893        if [ ! -e "${PBI_FILENAME}" ]; then usage_patch_pbi ; fi
894
895        # Load all the information about this PBI / PBP
896        load_info_from_header
897
898        # Make sure this isn't a patch file
899        is_pbi_patch
900        if [ "$?" = "1" ] ; then
901                exit_err "This is not a PBP patch file"
902        fi
903
904        if [ -z "${PBI_ORIGPROGDIRPATH}" ]; then usage_patch_pbi ; fi
905
906        # Lastly set PBI_PROGDIRNAME
907        PBI_PROGDIRNAME="`echo ${PBI_ORIGPROGDIRPATH} | rev | cut -d '/' -f 1 | rev`"
908                       
909        if [ "${PBI_EXTRACTONLY}" = "YES" ] ; then
910                # If extracting to a alt-outdir, set it now
911                PBI_PROGDIRPATH="`pwd`/${PBI_PROGDIRNAME}"
912       
913                if [ -n "${PBI_ALTEXTRACT_DIR}" ]; then
914                        PBI_PROGDIRPATH="${PBI_ALTEXTRACT_DIR}/${PBI_PROGDIRNAME}"
915                fi     
916        else
917                # Set the extraction dir
918                PBI_PROGDIRPATH="${PBI_ORIGPROGDIRPATH}-patch"
919        fi
920}
921
922# Parse the command line for adding
923parse_add_pbi_cmdline() {
924        while [ $# -gt 0 ]; do
925                case "$1" in
926                -e)     PBI_EXTRACTONLY="YES"
927                        ;;
928                -f)     PBI_FORCEADD="YES"
929                        ;;
930                -g)     PBI_ADD_GUIDISPLAY="YES" 
931                        ;;
932                -i)     PBI_ADD_INFODISPLAY="YES" 
933                        ;;
934            --meta)     PBI_ADD_METADISPLAY="YES" 
935                        ;;
936                -l)     PBI_ADD_LICDISPLAY="YES" 
937                        ;;
938                -o)     if [ $# -eq 1 ]; then usage_add_pbi; fi
939                        shift; PBI_ALTEXTRACT_DIR="$1"
940                        ;;
941                -r)     PBI_REMOTEFETCH="YES" 
942                        ;;
943                -R)     PBI_REMOTEFETCH="YES" 
944                        PBI_REMOTEFETCHONLY="YES"
945                        ;;
946                -v)     PBI_VERBOSE="YES" 
947                        ;;
948           --rArch)     
949                        if [ $# -eq 1 ]; then usage_add_pbi; fi
950                        shift; PBI_ADD_ALTARCH="$1"
951                        ;;
952           --rVer)     
953                        if [ $# -eq 1 ]; then usage_add_pbi; fi
954                        shift; PBI_ADD_ALTVER="$1"
955                        ;;
956     --checkscript)     PBI_CHECKSCRIPTS="YES" ;;
957        --licagree)     PBI_LICAGREE="YES" ;;
958         --no-hash)     PBI_DISABLEHASHDIR="YES" ;;
959     --no-checksum)     PBI_SKIPCHECKSUM="YES" ;;
960     --no-checksig)     PBI_SKIPSIGVERIFY="YES" ;;
961            --repo)     if [ $# -eq 1 ]; then usage_add_pbi; fi
962                        shift; PBI_ADDREPO_ID="$1"
963                        ;;
964                 *)
965                        if [ $# -gt 1 ]; then usage_add_pbi; fi
966                        # If there is no file, try fetching from repo
967                        if [ ! -e "${1}" ] ; then PBI_REMOTEFETCH="YES"; fi
968                        PBI_FILENAME="$1"
969                        ;;
970                esac
971                shift
972        done
973
974        if [ -z "${PBI_FILENAME}" ]; then usage_add_pbi ; fi
975
976        # If we are doing a remote fetch / install then do it now
977        if [ "$PBI_REMOTEFETCH" = "YES" ] ; then
978                if [ -z "${PBI_ADDREPO_ID}" ] ; then
979                        PBI_ADDREPO_ID="AUTO"
980                else
981                        ls ${PBI_DBREPODIR}/${PBI_ADDREPO_ID}.* >/dev/null 2>/dev/null
982                        if [ "$?" != "0" ] ; then
983                                exit_err "No such repo ID: ${PBI_DELREPO_ID}"
984                        fi
985                fi
986
987                # Start fetching file
988                pbi_add_fetch_remote
989       
990        fi
991
992        # Load all the information about this PBI
993        load_info_from_header
994
995        if [ -z "${PBI_ORIGPROGDIRPATH}" ]; then usage_add_pbi ; fi
996
997        # Make sure this isn't a patch file
998        is_pbi_patch
999        if [ "$?" = "0" ] ; then
1000                exit_err "This is a PBP patch file, use 'pbi_patch' instead"
1001        fi
1002
1003        # Lastly set PBI_PROGDIRNAME
1004        PBI_PROGDIRNAME="`echo ${PBI_ORIGPROGDIRPATH} | rev | cut -d '/' -f 1 | rev`"
1005
1006
1007        if [ "${PBI_EXTRACTONLY}" = "YES" ] ; then
1008                # If extracting to a alt-outdir, set it now
1009                PBI_PROGDIRPATH="`pwd`/${PBI_PROGDIRNAME}"
1010
1011                if [ -n "${PBI_ALTEXTRACT_DIR}" ]; then
1012                        PBI_PROGDIRPATH="${PBI_ALTEXTRACT_DIR}/${PBI_PROGDIRNAME}"
1013                fi
1014        else
1015                # Set the installation dir
1016                PBI_PROGDIRPATH="${PBI_ORIGPROGDIRPATH}"
1017        fi
1018}
1019
1020# Parse the command line
1021parse_autob_pbi_cmdline() {
1022        while [ $# -gt 0 ]; do
1023                case "$1" in
1024                -c)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1025                        if [ -n "${PBI_AB_CONFDIR}" ]; then usage_autob_pbi; fi
1026                        shift
1027                        get_abspath "$1"
1028                        PBI_AB_CONFDIR="$_ABSPATH"
1029                        if [ ! -d "${PBI_AB_CONFDIR}" ] ; then
1030                                exit_err "Invalid confdir (${PBI_AB_CONFDIR})"
1031                        fi
1032                        ;;
1033                -d)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1034                        shift
1035                        get_abspath "$1"
1036                        PORTSDIR="$_ABSPATH"
1037                        ;;
1038                -o)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1039                        shift
1040                        get_abspath "$1"
1041                        PBI_AB_OUTDIR="$_ABSPATH"
1042                        ;;
1043                -p)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1044                        shift
1045                        PBI_AB_BUILDERS="$1"
1046                        if [ ! $(is_num "$PBI_AB_BUILDERS") ] ; then
1047                                exit_err "Invalid process number specifed!"
1048                        fi
1049                        ;;
1050                -h)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1051                        shift
1052                        get_abspath "$1"
1053                        PBI_AB_HELPS="$_ABSPATH"
1054                        ;;
1055                -32)    if [ "$REALARCH" != "amd64" ] ; then
1056                                exit_err "-32 can only be used on amd64 host"
1057                        fi     
1058                        PBI_AB32="YES"
1059                        ARCH=i386
1060                        ;;
1061        -32fallback)    if [ "$REALARCH" != "amd64" ] ; then
1062                                exit_err "-32fallback can only be used on amd64 host"
1063                        fi     
1064                        PBI_ABFB32="YES"
1065                        ;;
1066
1067        --genpatch)     PBI_AB_GENPATCH="YES" 
1068                        ;;
1069        --pkgbuild)     PBI_AB_PKGBUILD="YES" 
1070                        ;;
1071            --keep)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1072                        shift; PBI_AB_ARCHIVENUM="$1"
1073                        expr $PBI_AB_ARCHIVENUM + 1 >/dev/null 2>/dev/null
1074                        if [ $? != 0 ] ; then usage_autob_pbi; fi
1075                        ;;
1076           --prune)     PBI_AB_PRUNE="YES" 
1077                        ;;
1078           --tmpfs)     PBI_AB_TMPFS="YES" 
1079                        ;;
1080            --sign)     if [ $# -eq 1 ]; then usage_autob_pbi; fi
1081                        shift; PBI_AB_SSLPRIVKEY="$1"
1082                        ;;
1083                 *)     usage_autob_pbi ;;
1084                esac
1085                shift
1086        done
1087
1088        if [ -z "$PBI_AB_OUTDIR" ] ; then usage_autob_pbi ; fi
1089        if [ -z "$PBI_AB_CONFDIR" ] ; then usage_autob_pbi ; fi
1090}
1091
1092
1093# Parse the command line
1094parse_create_pbi_cmdline() {
1095        while [ $# -gt 0 ]; do
1096                case "$1" in
1097                -a)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1098                        shift; PBI_CAUTHOR="$1"
1099                        ;;
1100                -b)     PBI_CBACKUP="YES"
1101                        ;;
1102                -c)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1103                        shift;
1104                        get_abspath "$1"
1105                        PBI_CONFDIR="$_ABSPATH"
1106                        if [ ! -d "${PBI_CONFDIR}" ] ; then
1107                                exit_err "Invalid confdir (${PBI_CONFDIR})"
1108                        fi
1109                        load_pbi_conffile
1110                        ;;
1111                -d)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1112                        shift; PORTSDIR="$1"
1113                        ;;
1114               --meta)  if [ $# -eq 1 ]; then usage_create_pbi; fi
1115                        shift; PBI_CREATE_USERMETA="$1"
1116                        if [ ! -e "$PBI_CREATE_USERMETA" ] ; then
1117                                exit_err "No such file: $PBI_CREATE_USERMETA"
1118                        fi
1119                        ;;
1120                -i)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1121                        shift; PBI_CICON="$1"
1122                        ;;
1123                -n)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1124                        shift; PBI_CNAME="$1"
1125                        ;;
1126                -o)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1127                        shift; PBI_CREATE_OUTDIR="$1"
1128                        ;;
1129                -p)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1130                        shift; PBI_MAKEPORT="$1"
1131                        ;;
1132                -r)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1133                        shift; PBI_CVERSION="$1"
1134                        ;;
1135                -w)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1136                        shift; PBI_CWEB="$1"
1137                        ;;
1138         --no-hash)     PBI_DISABLEHASHDIR="YES" ;;
1139            --sign)     if [ $# -eq 1 ]; then usage_create_pbi; fi
1140                        shift; PBI_SSLPRIVKEY="$1"
1141                        ;;
1142                 *)
1143                        if [ $# -gt 1 ]; then usage_create_pbi; fi
1144                        if [ "$PBI_CBACKUP" = "YES" ] ; then
1145                                if [ ! -e "${PBI_DBAPPDIR}/${1}" ] ; then
1146                                        find_pbi_namematch "$1"
1147                                        if [ -z "$PBI_NAMEMATCH" ] ; then
1148                                                exit_err "can't find installed pbi (${1})"
1149                                        fi
1150                                        PBI_CBACKUPTARGET="${PBI_NAMEMATCH}"
1151                                        PBI_PROGDIRPATH="${PBI_NAMEMATCH}"
1152                                else
1153                                        PBI_CBACKUPTARGET="${1}"
1154                                        PBI_PROGDIRPATH="${1}"
1155                                fi
1156                        else
1157                                get_abspath "$1"
1158                                PBI_PROGDIRPATH="$_ABSPATH"
1159                                if [ ! -d "${PBI_PROGDIRPATH}" ] ; then
1160                                        exit_err "Invalid pbidir (${1})"
1161                                fi
1162                        fi
1163                        ;;
1164                esac
1165                shift
1166        done
1167
1168        # Make sure this port exists
1169        if [ -n "${PBI_MAKEPORT}" -a ! -d "${PORTSDIR}/${PBI_MAKEPORT}" ]; then
1170                exit_err "No port (${PORTSDIR}/${PBI_MAKEPORT})"
1171        fi
1172
1173        # Load the name / version from specified port
1174        if [ -n "${PBI_MAKEPORT}" ]; then
1175                get_pbi_progversion
1176                get_pbi_progname
1177        fi
1178
1179        if [ -z "${PBI_PROGDIRPATH}" ]; then usage_create_pbi ; fi
1180
1181        # Lastly set PBI_PROGDIRNAME
1182        PBI_PROGDIRNAME="`echo ${PBI_PROGDIRPATH} | rev | cut -d '/' -f 1 | rev`"
1183}
1184
1185# Override any pbi.conf values with passed command-line values
1186parse_cmdline_overrides() {
1187        if [ -n "${PBI_CNAME}" ] ; then PBI_PROGNAME="${PBI_CNAME}" ; fi
1188        if [ -n "${PBI_CVERSION}" ] ; then PBI_PROGVERSION="${PBI_CVERSION}" ; fi
1189        if [ -n "${PBI_CWEB}" ] ; then PBI_PROGWEB="${PBI_CWEB}" ; fi
1190        if [ -n "${PBI_CAUTHOR}" ] ; then PBI_PROGAUTHOR="${PBI_CAUTHOR}" ; fi
1191        if [ -n "${PBI_CICON}" ] ; then PBI_PROGICON="${PBI_CICON}" ; fi
1192}
1193
1194# Parse the command line
1195parse_make_pbi_cmdline() {
1196        while [ $# -gt 0 ]; do
1197                case "$1" in
1198                -B)     PBI_BUILDONLY="YES"
1199                        ;;
1200                -c)
1201                        if [ $# -eq 1 ]; then usage_make_pbi; fi
1202                        if [ -n "${PBI_CONFDIR}" ]; then usage_make_pbi; fi
1203                        shift
1204                        get_abspath "$1"
1205                        PBI_CONFDIR="$_ABSPATH"
1206                        ;;
1207                -d)
1208                        if [ $# -eq 1 ]; then usage_make_pbi; fi
1209                        shift; PORTSDIR="$1" ; export PORTSDIR
1210                        ;;
1211
1212                -32)    if [ "$REALARCH" != "amd64" -a "`basename $0`" != "pbi_makeport_chroot" ] ; then
1213                                exit_err "-32 can only be used on amd64 host"
1214                        fi     
1215                        ARCH=i386
1216                        ;;
1217
1218                -k)     PBI_KEEPBUILDFILES="YES"
1219                        ;;
1220
1221                --delbuild)     MKDELBUILD="YES"
1222                        ;;
1223                --no-prune)     PBI_PRUNEBUILDPORTS="NO"
1224                        ;;
1225                --mkdebug)      MKDEBUG="YES"
1226                        ;;
1227                --pkgbuild)     PBI_PKGNGBUILD="YES"
1228                        ;;
1229                --tmpfs)        MKTMPFS="YES"
1230                        ;;
1231               --meta)  if [ $# -eq 1 ]; then usage_make_pbi; fi
1232                        shift; PBI_CREATE_USERMETA="$1"
1233
1234                        # If running the chroot portion, reset the location
1235                        if [ "`basename $0`" = "pbi_makeport_chroot" ] ; then
1236                                PBI_CREATE_USERMETA="/user-meta"
1237                        fi
1238
1239                        # Check to ensure it exists
1240                        if [ ! -e "$PBI_CREATE_USERMETA" ] ; then
1241                                exit_err "No such file: $PBI_CREATE_USERMETA"
1242                        fi
1243                        ;;
1244                -o)     if [ $# -eq 1 ]; then usage_make_pbi; fi
1245                        shift
1246                        get_abspath "$1"
1247                        PBI_CREATE_OUTDIR="$_ABSPATH"
1248                        ;;
1249                -p)     if [ $# -eq 1 ]; then usage_make_pbi; fi
1250                        if [ -n "${PBI_MAKEPREFIX}" ]; then usage_make_pbi; fi
1251                        shift; PBI_MAKEPREFIX="$1"
1252                        ;;
1253            --sign)     if [ $# -eq 1 ]; then usage_make_pbi; fi
1254                        shift
1255                        get_abspath "$1"
1256                        PBI_SSLPRIVKEY="$_ABSPATH"
1257                        ;;
1258                 *)
1259                        if [ $# -gt 1 ]; then usage_make_pbi; fi
1260                        PBI_MAKEPORT="$1"
1261                        ;;
1262                esac
1263                shift
1264        done
1265
1266        # Override some locations if working in chroot environment
1267        if [ "`basename $0`" = "pbi_makeport_chroot" ] ; then
1268                if [ -n "${PBI_CONFDIR}" ] ; then PBI_CONFDIR="/pbimodule" ; fi
1269                if [ -n "${PBI_SSLPRIVKEY}" ] ; then PBI_SSLPRIVKEY="/privkey.pem" ; fi
1270                if [ -n "${PBI_CREATE_OUTDIR}" ] ; then PBI_CREATE_OUTDIR="/pbiout" ; fi
1271                if [ -n "${PORTSDIR}" ] ; then PORTSDIR="/usr/ports" ; fi
1272        fi
1273
1274
1275        # Make sure this port exists
1276        if [ ! -d "${PORTSDIR}/${PBI_MAKEPORT}" ] ; then
1277                exit_err "No port (${PORTSDIR}/${PBI_MAKEPORT})"
1278        fi
1279
1280        # Make sure we have a valid PBI_CONFDIR
1281        if [ -n "${PBI_CONFDIR}" -a ! -d "${PBI_CONFDIR}" ] ; then
1282                exit_err "Invalid confdir (${PBI_CONFDIR})"
1283        fi
1284
1285        # Source the config file
1286        if [ -n "${PBI_CONFDIR}" ]; then load_pbi_conffile ; fi
1287
1288        if [ -z "${PBI_MAKEPORT}" ]; then
1289                usage_make_pbi
1290        fi
1291}
1292
1293# Parse the update command line
1294parse_update_pbi_cmdline() {
1295        while [ $# -gt 0 ]; do
1296                case "$1" in
1297                -c)     PBI_UPCHECK="YES" ;;
1298       --check-all)     PBI_UPCHECK="ALL" ;;
1299    --disable-auto)     PBI_UPENABLEAUTO="NO" ;;
1300     --enable-auto)     PBI_UPENABLEAUTO="YES" ;;
1301      --update-all)     PBI_UPDATEAPP="ALL" ;;
1302                 *)     if [ $# -gt 1 ]; then usage_update_pbi; fi
1303                        if [ -n "$PBI_UPDATEAPP" ] ; then usage_update_pbi ; fi
1304                        if [ ! -e "${PBI_DBAPPDIR}/${1}" ] ; then
1305                                find_pbi_namematch "$1"
1306                                if [ -z "$PBI_NAMEMATCH" ] ; then
1307                                        exit_err "can't find installed pbi (${1})"
1308                                fi
1309                                PBI_UPDATEAPP="$PBI_NAMEMATCH"
1310                        else
1311                                PBI_UPDATEAPP="$1"
1312                        fi
1313                        ;;
1314                esac
1315                shift
1316        done
1317
1318        if [ "${PBI_UPDATEAPP}" = "ALL" -a -n "${PBI_UPCHECK}" ] ; then
1319                usage_update_pbi
1320        fi
1321
1322        # Make sure we aren't trying to enable auto-updating for ALL
1323        if [ "${PBI_UPDATEAPP}" = "ALL" -a -n "${PBI_UPENABLEAUTO}" ] ; then
1324                usage_update_pbi
1325        fi
1326        if [ -z "${PBI_UPDATEAPP}" -a -n "${PBI_UPENABLEAUTO}" ] ; then
1327                usage_update_pbi
1328        fi
1329
1330        if [ -z "${PBI_UPDATEAPP}" -a "${PBI_UPCHECK}" != "ALL" ]; then
1331                usage_update_pbi
1332        fi
1333}
1334
1335# Make some of our required PBI dirs
1336mk_required_dirs() {
1337        if [ ! -d "${PBI_APPDIR}" ] ; then mkdir -p ${PBI_APPDIR} >/dev/null 2>/dev/null ; fi
1338        if [ ! -d "${PBI_XDGCFGDIR}" ] ; then mkdir -p ${PBI_XDGCFGDIR} >/dev/null 2>/dev/null ; fi
1339        if [ ! -d "${PBI_XDGAPPDIR}" ] ; then mkdir -p ${PBI_XDGAPPDIR} >/dev/null 2>/dev/null ; fi
1340        if [ ! -d "${PBI_XDGDIRDIR}" ] ; then mkdir -p ${PBI_XDGDIRDIR} >/dev/null 2>/dev/null ; fi
1341        if [ ! -d "${PBI_XDGICONDIR}" ] ; then mkdir -p ${PBI_XDGICONDIR} >/dev/null 2>/dev/null ; fi
1342        if [ ! -d "${PBI_XDGMIMEDIR}" ] ; then mkdir -p ${PBI_XDGMIMEDIR} >/dev/null 2>/dev/null ; fi
1343        if [ ! -d "${PBI_RCDIR}" ] ; then mkdir -p ${PBI_RCDIR} >/dev/null 2>/dev/null ; fi
1344        if [ ! -d "${PBI_BINDIR}" ] ; then mkdir -p ${PBI_BINDIR} >/dev/null 2>/dev/null ; fi
1345        if [ ! -d "${PBI_MANDIR}" ] ; then mkdir -p ${PBI_MANDIR} >/dev/null 2>/dev/null ; fi
1346        if [ ! -d "${PBI_HASHDIR}" ] ; then mkdir -p ${PBI_HASHDIR} >/dev/null 2>/dev/null ; fi
1347        if [ ! -d "${PBI_DBAPPDIR}" ] ; then mkdir -p ${PBI_DBAPPDIR} >/dev/null 2>/dev/null ; fi
1348        if [ ! -d "${PBI_DBKEYDIR}" ] ; then mkdir -p ${PBI_DBKEYDIR} >/dev/null 2>/dev/null ; fi
1349        if [ ! -d "${PBI_DBMIRRORDIR}" ] ; then mkdir -p ${PBI_DBMIRRORDIR} >/dev/null 2>/dev/null ; fi
1350        if [ ! -d "${PBI_DBICONDIR}" ] ; then mkdir -p ${PBI_DBICONDIR} >/dev/null 2>/dev/null ; fi
1351        if [ ! -d "${PBI_DBINDEXDIR}" ] ; then mkdir -p ${PBI_DBINDEXDIR} >/dev/null 2>/dev/null ; fi
1352        if [ ! -d "${PBI_DBREPODIR}" ] ; then mkdir -p ${PBI_DBREPODIR} >/dev/null 2>/dev/null ; fi
1353        if [ ! -d "${PBI_DBHASHQUEUEDIR}" ] ; then mkdir -p ${PBI_DBHASHQUEUEDIR} >/dev/null 2>/dev/null ; fi
1354
1355        # Set the permissions for directories if we are running as root
1356        if [ `id -u` != "0" ] ; then return ; fi
1357
1358        for cDir in $PBI_APPDIR $PBI_DBAPPDIR $PBI_DBHASHQUEUEDIR $PBI_XDGCFGDIR $PBI_XDGAPPDIR $PBI_XDGDIRDIR $PBI_XDGICONDIR $PBI_XDGMIMEDIR
1359        do     
1360                chown root:${PBI_INSTALLGROUP} ${cDir}
1361                chmod 775 ${cDir}
1362        done
1363
1364        # Make sure the hash-dirty file can be written to by all
1365        touch ${PBI_DBDIRTYFILE}
1366        chown root:${PBI_INSTALLGROUP} ${PBI_DBDIRTYFILE}
1367        chmod 664 ${PBI_DBDIRTYFILE}
1368}
1369
1370# Get the absolute path of a dir, even a realative dir. 'realpath' doesn't work here
1371get_abspath() {
1372        D=`dirname "$1"`
1373        B=`basename "$1"`
1374        if [ "$D" = "/" ] ; then
1375                _ABSPATH="/$B"
1376        else
1377                _ABSPATH="`cd \"$D\" 2>/dev/null && pwd || echo \"$D\"`/$B"
1378        fi
1379}
1380
1381
1382# Initialize some vars
1383init_vars() {
1384
1385        # Set sys vars
1386        REALARCH="`uname -m`"
1387        ARCH="$REALARCH"
1388
1389        # Where is pbi-manager installed?
1390        PROGBASE=/usr/local
1391        SYS_LOCALBASE=/usr/local
1392        PBI_SHARE_DIR="${PROGBASE}/share/pbi-manager"
1393        if [ -z "${PBI_APPDIR}" -o "`basename $0`" = "pbi_makeport_chroot" ] ; then
1394                PBI_APPDIR="/usr/pbi"
1395        fi
1396        # Set the FreeBSD Major & Release
1397        FBSDREL=`uname -r | cut -d "-" -f 1-2`
1398        FBSDMAJOR=`echo $FBSDREL | cut -d "-" -f 1 | cut -d '.' -f 1`
1399
1400        PBI_WORLDCHROOT="${PBI_APPDIR}/.pbi-world-$ARCH"
1401        if [ `id -u` = "0" ] ; then
1402                PBI_HASHDIR="${PBI_APPDIR}/.hashdir"
1403        else
1404                PBI_HASHDIR="${PBI_APPDIR}/.hashdir-`whoami`"
1405        fi
1406        PBI_AB_BUILDERS=1
1407        PBI_XDGCFGDIR="${PBI_APPDIR}/etc/xdg/menus"
1408        PBI_XDGAPPDIR="${PBI_APPDIR}/share/applications"
1409        PBI_XDGDIRDIR="${PBI_APPDIR}/share/desktop-directories"
1410        PBI_XDGICONDIR="${PBI_APPDIR}/share/icons/hicolor"
1411        PBI_XDGMIMEDIR="${PBI_APPDIR}/share/mime/packages"
1412        PBI_RCDIR="${PBI_APPDIR}/rc.d"
1413        PBI_BINDIR="${PBI_APPDIR}/bin"
1414        PBI_MANDIR="${PBI_APPDIR}/man"
1415        PBI_ETCCONF="${SYS_LOCALBASE}/etc/pbi.conf"
1416        PCBSD_ETCCONF="${SYS_LOCALBASE}/etc/pcbsd.conf"
1417        PBI_DEFAULT_ICON="${PROGBASE}/share/pbi-manager/icons/default.png"
1418        PBI_DEFAULT_ICON_CHROOT="/default.png"
1419        PBI_PATCH_ICON="${PROGBASE}/share/pbi-manager/icons/patch.png"
1420        PBI_LDCONFIGFILE="${PROGBASE}/etc/ldpbiconfig"
1421        PBI_LDCONFIGRC="${PROGBASE}/etc/rc.d/ldpbiconfig"
1422
1423        # Set the PBI DB dir
1424        if [ -z "${PBI_DBDIR}" ] ; then
1425                PBI_DBDIR="/var/db/pbi"
1426        fi
1427        PBI_DBKEYDIR="${PBI_DBDIR}/keys"
1428        PROGVERSION="1.0"
1429
1430        # Load the etc/pbi.conf file
1431        load_pbi_etcconf
1432
1433        # Overrides from pbi.conf
1434        if [ -z "$PBIDSLEEP" ] ; then
1435                PBIDSLEEP="300" # Amount of time to sleep before waking up pbid
1436        fi
1437        if [ -z "$PBI_INDEXREFRESH" ] ; then
1438                PBI_INDEXREFRESH="24" # Hours to wait until we re-download PBI indexes
1439        fi
1440        if [ -n "$PBI_MAJORVERSION" ] ; then
1441                FBSDMAJOR=${PBI_FBSDMAJOR}
1442        fi
1443
1444        PBI_LOG_LINES="500"
1445        PBI_INSTALLGROUP="operator"
1446
1447        # What dirs do we build hash-lists of
1448        HASH_SEARCH_DIRS="lib share include info man"
1449
1450        # What dbus dirs do we parse for setting up services
1451        DBUS_SEARCH_DIRS="share/dbus-1 kde4/share/dbus-1 gnome/share/dbus-1"
1452
1453        # Don't modify unless you know what your doing!
1454        MOD_PREINS="pre-install.sh"
1455        MOD_POSTINS="post-install.sh"
1456        MOD_PREREM="pre-remove.sh"
1457        MOD_XDGDESK_DIR="xdg-desktop"
1458        MOD_XDGMENU_DIR="xdg-menu"
1459        MOD_XDGMIME_DIR="xdg-mime"
1460        MOD_EXTLINKFILE="external-links"
1461        MOD_AUTOEXTLINKFILE=".auto-external-links"
1462        PBI_ADD_GUIDISPLAY="NO"
1463        PBI_ADD_INFODISPLAY="NO"
1464        PBI_ADD_METADISPLAY="NO"
1465        PBI_ADD_LICDISPLAY="NO"
1466        PBI_APPDESK_DIR=".${MOD_XDGDESK_DIR}"
1467        PBI_APPMENU_DIR=".${MOD_XDGMENU_DIR}"
1468        PBI_APPMIME_DIR=".${MOD_XDGMIME_DIR}"
1469        PBI_BUILD_USERS=""
1470        PBI_BUILD_GROUPS=""
1471        PBI_INS_USERSFILE=".pbi-uids"
1472        PBI_INS_GROUPSFILE=".pbi-gids"
1473        PBI_DESKADD="NO"
1474        PBI_MENUADD="NO"
1475        PBI_MIMEADD="NO"
1476        PBI_PATHADD="NO"
1477        PBI_DESKDEL="NO"
1478        PBI_MAKECONF="/etc/pbi-make.conf"
1479        PBI_MENUDEL="NO"
1480        PBI_MIMEDEL="NO"
1481        PBI_PATHDEL="NO"
1482        PBI_DELETENAME=""
1483        PBI_FAKEBIN_DIR="bin"
1484        PBI_FAKERC_DIR="rc.d"
1485        PBI_FILENAME=""
1486        PBI_FORCEADD="NO"
1487        PBI_HASHLIST=".pbi-hash-list"
1488        PBI_INDEXUPFILE="pbi-index-$FBSDMAJOR"
1489        PBI_METAUPFILE="pbi-meta-$FBSDMAJOR"
1490        PBI_INFONAME=""
1491        PBI_INS_DESKSCRIPT="install-desktop-icons.sh"
1492        PBI_INS_MENUSCRIPT="install-menu-icons.sh"
1493        PBI_INS_MIMESCRIPT="install-mime.sh"
1494        PBI_INS_PATHSCRIPT="install-pathlinks.sh"
1495        PBI_ICDIR="pbi-shared-icons"
1496        PBI_LISTREPO_UP=""
1497        PBI_LISTREPO_DOWN=""
1498        PBI_LISTREPO_MIRROR=""
1499        PBI_LICAGREE="NO"
1500        PBI_LICENSEFILE="LICENSE"
1501        PBI_USERMETAFILE="metafile"
1502        PBI_PATCHVERSION=""
1503        PBI_PATCHTARGET=""
1504        PBI_REMOTEFETCH=""
1505        PBI_REMOTEFETCHONLY=""
1506        PBI_RESOURCE_DIR="resources"
1507        PBI_SS_ICON="__PBI_ICON__"
1508        PBI_SS_ARCHIVE="__PBI_ARCHIVE__"
1509        PBI_SSLPRIVKEY=""
1510        PBI_TMPDIR="/tmp/.PBI.$$"
1511        PBI_TMPHASHLIST=""
1512        PBI_UPCHECK=""
1513        PBI_UPDATEAPP=""
1514        PBI_UNINS_DESKSCRIPT="uninstall-desktop-icons.sh"
1515        PBI_UNINS_MENUSCRIPT="uninstall-menu-icons.sh"
1516        PBI_UNINS_MIMESCRIPT="uninstall-mime.sh"
1517        PBI_UNINS_PATHSCRIPT="uninstall-pathlinks.sh"
1518
1519        # User overridable variables
1520        MKDELBUILD=""
1521        MKDEBUG=""
1522        MKTMPFS=""
1523        PBI_AB_ARCHIVENUM=""
1524        PBI_AB_CONFDIR=""
1525        PBI_AB_GENPATCH="NO"
1526        PBI_AB_HELPS=""
1527        PBI_AB_OUTDIR=""
1528        PBI_AB_SSLPRIVKEY=""
1529        PBI_AB_PRUNE=""
1530        PBI_AB_TMPFS=""
1531        PBI_BUILDONLY="NO"
1532        PBI_CAUTHOR=""
1533        PBI_CBACKUP=""
1534        PBI_CBACKUPTARGET=""
1535        PBI_CHECKSCRIPTS=""
1536        PBI_CICON=""
1537        PBI_CNAME=""
1538        PBI_CONFDIR=""
1539        PBI_CONFFILE="pbi.conf"
1540        PBI_CONF_SCRIPTSDIR="scripts/"
1541        PBI_CREATE_OUTDIR="$HOME"
1542        PBI_CREATE_HASHLIST="YES"
1543        PBI_CUPDATE=""
1544        PBI_CWEB=""
1545        PBI_DBAPPDIR="${PBI_DBDIR}/installed"
1546        PBI_DBDIRTYFILE="${PBI_DBDIR}/.hashdirty"
1547        PBI_DBHASHQUEUEDIR="${PBI_DBDIR}/.hashqueue"
1548        PBI_DBICONDIR="${PBI_DBDIR}/repo-icons"
1549        PBI_DBINDEXDIR="${PBI_DBDIR}/index"
1550        PBI_DBMIRRORDIR="${PBI_DBDIR}/mirrors"
1551        PBI_DBREPODIR="${PBI_DBDIR}/repos"
1552        PBI_DISABLEHASHDIR="NO"
1553        PBI_GUITOPBANNER="gui_banner.png"
1554        PBI_GUISIDEBANNER="gui_sidebanner.png"
1555        PBI_KEEPBUILDFILES="NO"
1556        PBI_MAKEPORT=""
1557        PBI_MAKEPREFIX=""
1558        PBI_MAKEOPTS=""
1559        PBI_MKPORTBEFORE=""
1560        PBI_MKPORTAFTER=""
1561        PBI_PORTSDIR=""
1562        PBI_PROGAUTHOR=""
1563        PBI_PROGMDATE=""
1564        PBI_PROGEPOCH=""
1565        PBI_PROGNAME=""
1566        PBI_PROGDIRNAME=""
1567        PBI_PROGDIRPATH=""
1568        PBI_PROGICON=""
1569        PBI_PROGREVISION=""
1570        PBI_PROGVERSION=""
1571        PBI_PROGWEB=""
1572        PBI_PRUNEBUILDPORTS="YES"
1573        PBI_SKIPCHECKSUM=""
1574        PBI_SKIPSIGVERIFY=""
1575        PBI_USESYSGL="YES"
1576        PBI_USESYSFONTS="YES"
1577        PBI_VERBOSE="NO"
1578        PORTSDIR="/usr/ports"
1579
1580}
1581
1582detect_pkgng()
1583{
1584        export PKG_ADD="pkg add"
1585        export PKG_DELETE="pkg delete -y -f"
1586}
1587
1588# Set and export vars used by module scripts
1589export_script_vars() {
1590        # Load some initial values
1591        get_pbi_progdir
1592        get_pbi_progversion
1593
1594        export PBI_PROGNAME PBI_PROGDIRNAME PBI_PROGDIRPATH PBI_PROGVERSION PBI_RCDIR PBI_MANDIR PBI_BINDIR
1595        export SYS_LOCALBASE PBI_FAKEBIN_DIR PBI_FAKERC_DIR
1596}
1597
1598# init tmpdir
1599init_tmpdir() {
1600        if [ -d "${PBI_TMPDIR}" ] ; then return; fi
1601        if [ -z "${PBI_TMPDIR}" ] ; then return ; fi
1602        if [ "${PBI_TMPDIR}" = "/" ] ; then return ; fi
1603        if [ -e "${PBI_TMPDIR}" ] ; then rm -rf "${PBI_TMPDIR}" ; fi
1604        mkdir -p "${PBI_TMPDIR}"
1605}
1606
1607# rm tmpdir
1608rm_tmpdir() {
1609        if [ -z "${PBI_TMPDIR}" -o "${PBI_TMPDIR}" = "/" ] ; then return 0; fi
1610        if [ -e "${PBI_TMPDIR}" ] ; then rm -rf "${PBI_TMPDIR}" ; fi
1611}
1612
1613# rm tmpdir
1614rm_buildfiles() {
1615        if [ "${PBI_KEEPBUILDFILES}" = "YES" ] ; then return ; fi
1616        if [ -z "$PBI_CHROOTDIR" ] ; then return ; fi
1617        chroot_make_cleanup
1618}
1619
1620# Load PBI conf options
1621load_pbi_conffile() {
1622        if [ ! -d "${PBI_CONFDIR}" ] ; then return 0 ; fi
1623        if [ -e "${PBI_CONFDIR}/${PBI_CONFFILE}" ] ; then
1624                unset PBI_MAKEPORT PBI_BUILDKEY PBI_REQUIRESROOT PBI_PROGNAME PBI_PROGWEB PBI_PROGAUTHOR PBI_PROGICON PBI_MKPORTBEFORE PBI_MKPORTAFTER PBI_MAKEOPTS PBI_EXCLUDELIST PBI_AB_PRIORITY PBI_HASH_EXCLUDES PBI_AB_NOTMPFS PBI_PROGREVISION
1625                . ${PBI_CONFDIR}/${PBI_CONFFILE}
1626        fi
1627}
1628
1629# Get the PBI_PROGVERSION
1630get_pbi_progversion() {
1631
1632        if [ -z "${PBI_PROGVERSION}" ] ; then
1633                load_pbi_conffile
1634
1635                # If we have PBI_PROGVERSION now set
1636                if [ -n "${PBI_PROGVERSION}" ] ; then return 0 ; fi
1637        else
1638                return 0
1639        fi
1640
1641        # Check first if we have this pkg in PKGNG
1642        if [ -e "/usr/local/sbin/pkg-static" -a -n "${PBI_MAKEPORT}" ] ; then
1643                local testPkgVer="`pkg query %v ${PBI_MAKEPORT}`"
1644                if [ -n "$testPkgVer" ] ; then
1645                        export PBI_PROGVERSION="$testPkgVer"
1646                        return 0
1647                fi
1648        fi
1649
1650        # Get the version from ports
1651        if [ -z "${PBI_PROGVERSION}" -a -n "${PORTSDIR}" -a -n "${PBI_MAKEPORT}" ] ; then
1652                PORTVER="`make -C ${PORTSDIR}/${PBI_MAKEPORT} -V DISTVERSION PORTSDIR=${PORTSDIR} 2>/dev/null`"
1653
1654                # Check if we have a portrevision to use in version number
1655                PORTREV=""
1656                PORTREV="`make -C ${PORTSDIR}/${PBI_MAKEPORT} -V PORTREVISION PORTSDIR=${PORTSDIR} 2>/dev/null`"
1657                if [ -n "${PORTREV}" -a "${PORTREV}" != "0" ]
1658                then
1659                        PBI_PROGVERSION="${PORTVER}_${PORTREV}"
1660                else
1661                        PBI_PROGVERSION="${PORTVER}"
1662                fi
1663
1664                if [ -z "${PBI_PROGVERSION}" ] ; then
1665                        echo "Warning: Unable to set PBI_PROGVERSION with:"
1666                        echo "make -C ${PORTSDIR}/${PBI_MAKEPORT} -V DISTVERSION PORTSDIR=${PORTSDIR}"
1667                fi
1668        else
1669                echo "PBI_PROGVERSION - $PBI_PROGVERSION - PORTSDIR - ${PORTSDIR} - $PBI_MAKEPORT - $PBI_MAKE_PORT - pbi - $pbi"
1670                exit_err "Failed to locate PBI_PROGVERSION"
1671        fi
1672
1673        # If we have a REVISION, use it as well
1674        if [ -n "$PBI_PROGREVISION" ] ; then
1675                PBI_PROGVERSION="${PBI_PROGVERSION}_${PBI_PROGREVISION}"
1676        fi
1677}
1678
1679
1680# Get the PBI_PROGNAME
1681get_pbi_progname() {
1682        if [ -z "${PBI_PROGNAME}" -o "${PBI_PROGNAME}" = " " ] ; then
1683                load_pbi_conffile
1684        else
1685                return 0
1686        fi
1687
1688        if [ -z "${PBI_PROGNAME}" -a -n "${PORTSDIR}" -a -n "${PBI_MAKEPORT}" ] ; then
1689                # Get the proper package name from the prefix + name + suffix
1690                local pkgPrefix="`make -C ${PORTSDIR}/${PBI_MAKEPORT} -V PKGNAMEPREFIX PORTSDIR=${PORTSDIR}`"
1691                local pkgName="`make -C ${PORTSDIR}/${PBI_MAKEPORT} -V PORTNAME PORTSDIR=${PORTSDIR}`"
1692                local pkgSuffix="`make -C ${PORTSDIR}/${PBI_MAKEPORT} -V PKGNAMESUFFIX PORTSDIR=${PORTSDIR}`"
1693                PBI_PROGNAME="${pkgPrefix}${pkgName}${pkgSuffix}"
1694        else
1695                exit_err "Failed to locate PBI_PROGNAME"
1696        fi
1697}
1698
1699# Get the PBI PROGDIR Name
1700get_pbi_progdir() {
1701        if [ -z "${PBI_PROGNAME}" ] ; then
1702                get_pbi_progname
1703        fi
1704
1705        tmp="`echo ${PBI_PROGNAME} | tr -d ' ' | tr '[A-Z]' '[a-z]'`"
1706        if [ -z "${PBI_PROGDIRNAME}" ] ; then
1707                PBI_PROGDIRNAME="${tmp}-${ARCH}"
1708        fi
1709        if [ -z "${PBI_PROGDIRPATH}" ] ; then
1710                PBI_PROGDIRPATH="${PBI_APPDIR}/${PBI_PROGDIRNAME}"
1711        fi
1712}
1713
1714# Helper function to exit after a error, and do some cleanup
1715exit_err() {
1716        echo -e "`basename ${0}`: ${1}"
1717        rm_tmpdir
1718        rm_buildfiles
1719        rm_pbipatchfiles
1720        chroot_make_cleanup
1721        clean_remote_dl
1722        exit 255
1723}
1724
1725# Check if we need to cleanup patch files
1726rm_pbipatchfiles() {
1727        if [ -z "${_pbiNewDir}${_pbiOldDir}${_pbiPatchDir}" ] ; then
1728                return
1729        else
1730                echo "Cleaning up patch data..."
1731        fi
1732
1733        # If we used tmpfs, unmount the dirs
1734        if [ "$PBI_MP_TMPFS" = "YES" ] ; then
1735                umount "${_pbiNewDir}" 2>/dev/null
1736                umount "${_pbiOldDir}" 2>/dev/null
1737                umount "${_pbiPatchDir}" 2>/dev/null
1738        fi
1739
1740        if [ -n "${_pbiNewDir}" -a -d "${_pbiNewDir}" -a "${_pbiNewDir}" != "/" ] ; then
1741                rm -rf "${_pbiNewDir}" >/dev/null 2>/dev/null
1742                chflags -R noschg "${_pbiNewDir}" >/dev/null 2>/dev/null
1743                rm -rf "${_pbiNewDir}" >/dev/null 2>/dev/null
1744        fi
1745        if [ -n "${_pbiOldDir}" -a -d "${_pbiOldDir}" -a "${_pbiOldDir}" != "/" ] ; then
1746                rm -rf "${_pbiOldDir}" >/dev/null 2>/dev/null
1747                chflags -R noschg "${_pbiOldDir}" >/dev/null 2>/dev/null
1748                rm -rf "${_pbiOldDir}" >/dev/null 2>/dev/null
1749        fi
1750        if [ -n "${_pbiPatchDir}" -a -d "${_pbiPatchDir}" -a "${_pbiPatchDir}" != "/" ] ; then
1751                rm -rf "${_pbiPatchDir}" >/dev/null 2>/dev/null
1752                chflags -R noschg "${_pbiPatchDir}" >/dev/null 2>/dev/null
1753                rm -rf "${_pbiPatchDir}" >/dev/null 2>/dev/null
1754        fi
1755}
1756
1757# Check if we need to delete a remotely dl'd file
1758clean_remote_dl() {
1759        # If this was a remote fetch, remove dl'd file
1760        if [ "$PBI_REMOTEFETCH" = "YES" -a -n "$PBI_FILENAME" ]; then
1761                rm "$PBI_FILENAME" >/dev/null 2>/dev/null
1762        fi
1763}
1764
1765# Set port make options from config
1766set_make_options() {
1767
1768        local MAKE_CONF="/etc/make.conf"
1769
1770        echo "PACKAGE_BUILDING=yes" >> ${MAKE_CONF}
1771        echo "BATCH=yes" >> ${MAKE_CONF}
1772        echo "NO_IGNORE=yes" >> ${MAKE_CONF}
1773        echo "PACKAGE_BUILDING=yes" >> ${MAKE_CONF}
1774        echo "WITH_PKGNG=yes" >> ${MAKE_CONF}
1775
1776        echo "WRKDIRPREFIX=/usr/wrkdirprefix" >> ${MAKE_CONF}
1777        echo "DEPENDS_CLEAN=YES" >> ${MAKE_CONF}
1778
1779        if [ -n "$PBI_MAKEOPTS" ] ; then
1780                # Check if we have custom make opts
1781                echo "${PBI_MAKEOPTS}" >> ${MAKE_CONF}
1782        fi
1783
1784        if [ ! -d "/usr/local" ] ; then
1785                mkdir -p /usr/local
1786        fi 
1787
1788        # Make sure ldconfig is primed
1789        /etc/rc.d/ldconfig start
1790
1791        if [ "$PBI_PKGNGBUILD" ] ; then
1792                echo "Installing pkgng..."
1793                pkgFetchURL=`grep "^packagesite:" /usr/local/etc/pkg.conf | awk '{print $2}'`
1794                cd /tmp
1795                fetch -o pkg.txz ${pkgFetchURL}/Latest/pkg.txz
1796                if [ $? -ne 0 ] ; then exit_err "Failed fetching pkgng..."; fi
1797                tar xvf pkg.txz >/dev/null 2>/dev/null
1798                ./usr/local/sbin/pkg-static add pkg.txz
1799                if [ $? -ne 0 ] ; then exit_err "Failed installing pkgng..."; fi
1800                rm pkg.txz
1801        else
1802                echo "Building pkgng..."
1803                cd /usr/ports/ports-mgmt/pkg
1804                make install clean
1805                if [ $? -ne 0 ] ; then exit_err "Failed building pkgng!" ; fi
1806        fi
1807
1808        # Check if using ccache directory
1809        if [ -d "/.ccache" ] ; then
1810                echo "Enabling ccache..."
1811                cd /usr/ports/devel/ccache
1812                make install clean
1813                if [ $? -eq 0 ] ; then
1814                        # Setup environment variables
1815                        CCACHE_PATH="/usr/bin:/usr/local/bin"
1816                        export CCACHE_PATH
1817                        CCACHE_DIR="/.ccache"
1818                        export CCACHE_DIR
1819                        PATH="/usr/local/libexec/ccache:${PATH}"
1820                        export PATH
1821
1822                        # Setup make configuration
1823                        echo ".if !defined(NO_CCACHE)" >> ${MAKE_CONF}
1824                        echo "  CC=/usr/local/libexec/ccache/world/cc" >> ${MAKE_CONF}
1825                        echo "  CXX=/usr/local/libexec/ccache/world/c++" >> ${MAKE_CONF}
1826                        echo ".endif" >> ${MAKE_CONF}
1827                else
1828                        echo "Failed installing ccache! Continuing without it..."
1829                fi
1830        fi
1831
1832        PATH="${PATH}:/usr/local/bin:/usr/local/sbin"
1833        export PATH
1834
1835        FORCE_PKG_REGISTER="Y"
1836        export FORCE_PKG_REGISTER
1837
1838}
1839
1840# Confirm we are running as root
1841require_root() {
1842  if [ `id -u` != "0" ] ; then
1843     exit_err "Must be run as root!"
1844  fi 
1845}
1846
1847# Confirm we are running as root or the proper group for installation
1848require_root_or_group() {
1849  if [ `id -u` = "0" ] ; then return 0 ; fi
1850  touch ${PBI_APPDIR}/.ptest.$$ >/dev/null 2>/dev/null
1851  if [ "$?" = "0" ] ; then
1852        rm ${PBI_APPDIR}/.ptest.$$ >/dev/null 2>/dev/null
1853        return 0
1854  fi
1855  exit_err "Must be run as root or a member of the $PBI_INSTALLGROUP group!"
1856}
1857
1858# Function to get the username from a file
1859get_username_from_file() {
1860        if [ -f "${1}" ] ; then
1861                FILEUSER=`ls -al ${1} | awk '{print $3}'`
1862                export FILEUSER
1863                return 0
1864        fi
1865        if [ -d "${1}" ] ; then
1866                FILEUSER=`ls -al ${1} | grep -v "total" | head -n 1 | awk '{print $3}'`
1867                export FILEUSER
1868                return 0
1869        fi
1870        exit_err "Invalid file for usercheck!"
1871}
1872
1873# Start the make patch process
1874pbi_makepatch_init() {
1875        require_root
1876        init_tmpdir
1877        parse_makepatch_pbi_cmdline "$@"
1878
1879        # Create a new patch file from the two PBIs specified
1880        make_pbi_patchfile "${PBI_FILENAME}" "${PBI_OLDFILENAME}" "${PBI_PATCHOUTDIR}"
1881}
1882
1883# Remove a repo from the DB
1884pbi_deleterepo_init() {
1885        require_root
1886        parse_deleterepo_pbi_cmdline "$@"
1887
1888        delete_pbi_repo
1889}
1890
1891# Do the removal of a PBI repo
1892delete_pbi_repo() {
1893        # Make sure this repo exists
1894        ls ${PBI_DBREPODIR}/${PBI_DELREPO_ID}.* >/dev/null 2>/dev/null
1895        if [ "$?" != "0" ] ; then
1896                exit_err "No such repo ID: ${PBI_DELREPO_ID}"
1897        fi
1898       
1899        _md5=`ls ${PBI_DBREPODIR}/${PBI_DELREPO_ID}.* | sed "s|^${PBI_DBREPODIR}/${PBI_DELREPO_ID}.||g"`
1900        if [ -e "${PBI_DBREPODIR}/${PBI_DELREPO_ID}.${_md5}" ] ; then
1901                rm "${PBI_DBREPODIR}/${PBI_DELREPO_ID}.${_md5}"
1902        else
1903                echo "Warning: ${PBI_DELREPO_ID}.${_md5} does not exist in the database."
1904        fi
1905        if [ -e "${PBI_DBKEYDIR}/${_md5}.ssl" ] ; then
1906                rm "${PBI_DBKEYDIR}/${_md5}.ssl"
1907        else
1908                echo "Warning: ${_md5}.ssl does not exist in the keys database."
1909        fi
1910        if [ -e "${PBI_DBMIRRORDIR}/${_md5}" ] ; then
1911                rm "${PBI_DBMIRRORDIR}/${_md5}"
1912        else
1913                echo "Warning: ${_md5} does not exist in the mirror database."
1914        fi
1915       
1916        # See if we need to remove a downloaded index file
1917        if [ -e "${PBI_DBINDEXDIR}/${_md5}-index" ] ; then
1918                rm "${PBI_DBINDEXDIR}/${_md5}-index"
1919                rm "${PBI_DBINDEXDIR}/${_md5}-index.time"
1920        fi
1921
1922        # Make sure we renumber the repos
1923        renumber_repos
1924
1925        echo "Deleted Repository ${PBI_DELREPO_ID}."
1926
1927}
1928
1929# After deleting a repo, this can be run to renumber the IDs
1930renumber_repos() {
1931        _rNum="1"
1932        for i in `ls ${PBI_DBREPODIR} | sort`
1933        do
1934                case `echo ${_rNum} | wc -m | tr -d ' '` in
1935                        2) _rNum="00${_rNum}" ;;
1936                        3) _rNum="0${_rNum}" ;;
1937                        *) ;;
1938                esac
1939
1940                _md5=`echo ${i} | cut -d '.' -f 2`
1941                mv "${PBI_DBREPODIR}/${i}" "${PBI_DBREPODIR}/${_rNum}.${_md5}"
1942
1943                _rNum=`expr ${_rNum} + 1`
1944        done
1945}
1946
1947# Add a new repo to the db
1948pbi_addrepo_init() {
1949        require_root
1950        parse_addrepo_pbi_cmdline "$@"
1951
1952        # Create a new repo file
1953        add_pbi_repo
1954}
1955
1956# Extract the repo and add it to the DB
1957add_pbi_repo() {
1958        init_tmpdir
1959        tar xvf "${PBI_ADDREPO_FILE}" -C ${PBI_TMPDIR} >/dev/null 2>/dev/null
1960        if [ "$?" != "0" ] ; then
1961                exit_err "Failed to read ${PBI_ADDREPO_FILE}"
1962        fi
1963        if [ ! -f "${PBI_TMPDIR}/repokey.ssl" -o ! -f "${PBI_TMPDIR}/repo-url" -o ! -f "${PBI_TMPDIR}/repo-desc" -o ! -f "${PBI_TMPDIR}/repo-mirror" ] ; then
1964                exit_err "Improperly packaged repo file!"
1965        fi
1966
1967        # Make sure we don't have a duplicate repo key
1968        for tr in ${PBI_PUBKEYS}
1969        do
1970                diff -q ${tr} ${PBI_TMPDIR}/repokey.ssl >/dev/null 2>/dev/null
1971                if [ "$?" = "0" ] ; then
1972                        exit_err "Repo with identical key already registered!"
1973                fi
1974        done
1975
1976        # Figure out the next repo number
1977        get_next_repo_num
1978
1979        _md5=`md5 -q ${PBI_TMPDIR}/repo-url`
1980        _url=`cat ${PBI_TMPDIR}/repo-url`
1981        _desc=`cat ${PBI_TMPDIR}/repo-desc`
1982        echo "URL: ${_url}" > ${PBI_DBREPODIR}/${_rNum}.${_md5}
1983        echo "Desc: ${_desc}" >> ${PBI_DBREPODIR}/${_rNum}.${_md5}
1984        cp ${PBI_TMPDIR}/repo-mirror ${PBI_DBMIRRORDIR}/${_md5}
1985        cp "${PBI_TMPDIR}/repokey.ssl" "${PBI_DBKEYDIR}/${_md5}.ssl"
1986        chmod 755 "${PBI_DBKEYDIR}/${_md5}.ssl"
1987       
1988        rm_tmpdir
1989
1990        echo "Added new repo: \"${_desc}\" to the database."
1991
1992}
1993
1994# Function to do listing of installed repos, and return next available number
1995get_next_repo_num() {
1996        _rNum="0"
1997        for i in `ls ${PBI_DBREPODIR} | sort`
1998        do
1999                _rNum=`expr ${_rNum} + 1`
2000        done
2001
2002        _rNum=`expr ${_rNum} + 1`
2003
2004        case `echo ${_rNum} | wc -m | tr -d ' '` in
2005                2) _rNum="00${_rNum}" ;;
2006                3) _rNum="0${_rNum}" ;;
2007                *) ;;
2008        esac
2009
2010        export _rNum
2011}
2012
2013# Start the make patch process
2014pbi_makerepo_init() {
2015        require_root
2016        parse_makerepo_pbi_cmdline "$@"
2017
2018        # Create a new repo file
2019        make_pbi_repo
2020}
2021
2022# Create the repo .rpo file
2023make_pbi_repo() {
2024        init_tmpdir
2025
2026        mkdir ${PBI_TMPDIR}/.mkrepo
2027        cp ${PBI_MKREPO_KEY} ${PBI_TMPDIR}/.mkrepo/repokey.ssl
2028        echo "${PBI_MKREPO_URL}" >  ${PBI_TMPDIR}/.mkrepo/repo-url
2029        echo "${PBI_MKREPO_DESC}" >  ${PBI_TMPDIR}/.mkrepo/repo-desc
2030        echo "${PBI_MKREPO_MIRROR}" | sed 's|,|\
2031|g' > ${PBI_TMPDIR}/.mkrepo/repo-mirror
2032
2033
2034        tar cvzf ${PBI_MKREPO_OUTDIR}/pbi-repo.rpo -C ${PBI_TMPDIR}/.mkrepo . >/dev/null 2>/dev/null
2035        echo "New PBI Repo created: ${PBI_MKREPO_OUTDIR}/pbi-repo.rpo"
2036
2037        rm_tmpdir
2038}
2039
2040do_pbi_mt_syncpbi()
2041{
2042        # First load values from the target PBI
2043        PBI_FILENAME="${PBI_MT_PBIFILE}"
2044        load_info_from_header
2045
2046        mFlags="add --app"
2047        if [ -n "$PBI_PROGAUTHOR" ] ; then mFlags="$mFlags -a \"${PBI_PROGAUTHOR}\""; fi
2048        if [ -n "$PBI_CATEGORY" ] ; then mFlags="$mFlags -c \"${PBI_CATEGORY}\""; fi
2049        if [ -n "$PBI_LICENSE" ] ; then mFlags="$mFlags -l \"${PBI_LICENSE}\""; fi
2050        if [ -n "$PBI_TAGS" ] ; then mFlags="$mFlags -k \"${PBI_TAGS}\""; fi
2051        if [ -n "$PBI_ICONURL" ] ; then mFlags="$mFlags -i \"${PBI_ICONURL}\""; fi
2052        if [ -n "$PBI_PROGWEB" ] ; then mFlags="$mFlags -u \"${PBI_PROGWEB}\""; fi
2053        if [ -n "$PBI_PROGTYPE" ] ; then mFlags="$mFlags -t \"${PBI_PROGTYPE}\""; fi
2054        if [ -n "$PBI_DESC" ] ; then mFlags="$mFlags -d \"`echo $PBI_DESC | sed 's|;||g'`\""; fi
2055        if [ -n "$PBI_PROGTYPE" ] ; then mFlags="$mFlags -t \"$PBI_PROGTYPE\""; fi
2056        if [ "$PBI_REQUIRESROOT" = "YES" ] ; then mFlags="$mFlags -r"; fi
2057
2058
2059        # Add the app
2060        echo "pbi_metatool ${mFlags} -n \"${PBI_PROGNAME}\" `realpath ${PBI_MT_METAFILE}`" >/tmp/.pbiCmd.$$
2061        chmod 755 /tmp/.pbiCmd.$$
2062        /tmp/.pbiCmd.$$
2063        err=$?
2064        #rm /tmp/.pbiCmd.$$
2065        exit $err
2066}
2067
2068# Init the metatool
2069pbi_mt_init() {
2070        parse_mt_pbi_cmdline "$@"
2071        case $PBI_MT_MODE in
2072            SYNCPBI) do_pbi_mt_syncpbi ;;
2073                ADD) if [ "$PBI_MT_TYPE" = "CAT" ] ; then
2074                        do_pbi_mt_add_cat
2075                     else
2076                        do_pbi_mt_add_app
2077                     fi ;;
2078                REM) if [ "$PBI_MT_TYPE" = "CAT" ] ; then
2079                        do_pbi_mt_rem_cat "${PBI_MT_REMNAME}" "${PBI_MT_METAFILE}"
2080                     else
2081                        do_pbi_mt_rem_app "${PBI_MT_REMNAME}" "${PBI_MT_METAFILE}"
2082                     fi ;;
2083                  *) ;;
2084        esac
2085}
2086
2087do_pbi_mt_add_cat() {
2088        init_tmpdir
2089
2090        # Remove any duplicate name
2091        do_pbi_mt_rem_cat "${PBI_MT_ADDNAME}" "${PBI_MT_METAFILE}"
2092
2093        cp ${PBI_MT_METAFILE} ${PBI_TMPDIR}/.meta.$$
2094        echo "Cat=${PBI_MT_ADDNAME};${PBI_MT_ADDICON};${PBI_MT_ADDDESC};" \
2095        >> ${PBI_TMPDIR}/.meta.$$
2096        sort ${PBI_TMPDIR}/.meta.$$ > "${PBI_MT_METAFILE}"
2097        rm ${PBI_TMPDIR}/.meta.$$
2098       
2099}
2100
2101do_pbi_mt_add_app() {
2102        init_tmpdir
2103        # Remove any duplicate name
2104        do_pbi_mt_rem_app "${PBI_MT_ADDNAME}" "${PBI_MT_METAFILE}"
2105
2106        local _date=`date '+%s'`
2107
2108        cp ${PBI_MT_METAFILE} ${PBI_TMPDIR}/.meta.$$
2109        echo "App=${PBI_MT_ADDNAME};${PBI_MT_ADDCAT};${PBI_MT_ADDICON};${PBI_MT_ADDAUTHOR};${PBI_MT_ADDURL};${PBI_MT_ADDLIC};${PBI_MT_ADDTYPE};${PBI_MT_ADDKEYWORDS};${PBI_MT_ADDDESC};$PBI_MT_REQUIRESROOT;${_date}" \
2110        >> ${PBI_TMPDIR}/.meta.$$
2111        sort ${PBI_TMPDIR}/.meta.$$ > "${PBI_MT_METAFILE}"
2112        rm ${PBI_TMPDIR}/.meta.$$
2113}
2114
2115do_pbi_mt_rem_cat() {
2116        sed -i '' "\|^Cat=${1};|d" "${2}"
2117}
2118
2119do_pbi_mt_rem_app() {
2120        sed -i '' "\|^App=${1};|d" "${2}"
2121}
2122
2123# Init the indextool
2124pbi_it_init() {
2125        parse_it_pbi_cmdline "$@"
2126        case $PBI_IT_MODE in
2127                ADD) do_pbi_it_add ;;
2128                REM) do_pbi_it_rem ;;
2129                  *) ;;
2130        esac
2131}
2132
2133# Remove a target PBI from an index
2134do_pbi_it_rem() {
2135        init_tmpdir
2136        _pbilow="`echo ${PBI_IT_REMNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
2137
2138        cat "${PBI_IT_REMINDEX}" | grep -v "^${_pbilow}:${PBI_IT_REMARCH}:${PBI_IT_REMVER}" \
2139                > "${PBI_TMPDIR}/.indextmp"
2140        sort ${PBI_TMPDIR}/.indextmp > "${PBI_IT_REMINDEX}"
2141
2142        rm_tmpdir
2143}
2144
2145# Add a new PBI to the specified INDEX file
2146do_pbi_it_add() {
2147        init_tmpdir
2148
2149        # First load values from the target PBI
2150        PBI_FILENAME="$PBI_IT_ADDFILE"
2151        load_info_from_header
2152
2153        # Get the name in lower-case
2154        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
2155       
2156        # Prune any old copies of this app from the index
2157        prune_from_index "$_pbilow" "$PBI_APPARCH"
2158       
2159        # Prune any old copies of this app from the index
2160        mark_current_active_index "$_pbilow" "$PBI_APPARCH"
2161
2162        # Add the new index entry
2163        add_to_index
2164        rm_tmpdir
2165}
2166
2167# Mark any current versions of this PBI as active in the index
2168mark_current_active_index() {
2169
2170        while read iLine
2171        do
2172                echo "$iLine" | grep "^${1}:${2}:" >/dev/null 2>/dev/null
2173                if [ "$?" != "0" ] ; then
2174                        echo "$iLine" >> ${PBI_TMPDIR}/.indextmp       
2175                        continue
2176                fi
2177                echo "$iLine" | sed 's|:current|:active|' >> ${PBI_TMPDIR}/.indextmp   
2178
2179        done < $PBI_IT_ADDINDEX 
2180        mv "${PBI_TMPDIR}/.indextmp" "${PBI_IT_ADDINDEX}"
2181}
2182
2183# Add the specified PBI to the index
2184add_to_index() {
2185        mv "${PBI_IT_ADDINDEX}" "${PBI_TMPDIR}/.indextmp"
2186        local _date=`date '+%s'`
2187        local _sha256=`sha256 -q ${PBI_FILENAME}`
2188        local _psize=`du -k ${PBI_FILENAME} | cut -f 1`
2189        echo "${_pbilow}:${PBI_APPARCH}:${PBI_PROGVERSION}:${_sha256}:${PBI_PROGMDATE}:${PBI_IT_ADDURL}:$_date:${PBI_IT_ADDBPVERS}:current:${_psize}:" >>"${PBI_TMPDIR}/.indextmp"
2190        sort ${PBI_TMPDIR}/.indextmp > "${PBI_IT_ADDINDEX}"
2191}
2192
2193
2194# Remove a set number of PBIs from the index
2195prune_from_index() {
2196        if [ -z "$PBI_IT_ADDKEEP" ]; then return ; fi
2197
2198        local found="0"
2199        local added="0"
2200        while read iLine
2201        do
2202                echo "$iLine" | grep "^${1}:${2}:" >/dev/null 2>/dev/null
2203                if [ "$?" != "0" ] ; then
2204                        # Ready to add back the saved lines
2205                        if [ $found -ne 0 ] ; then
2206                                while read fLine
2207                                do
2208                                  if [ $found -le $PBI_IT_ADDKEEP ] ; then
2209                                     echo "$fLine" >> ${PBI_TMPDIR}/.indextmp   
2210                                  fi
2211                                  found=`expr $found - 1`
2212                                done < ${PBI_TMPDIR}/.foundtmp
2213                        fi
2214                        echo "$iLine" >> ${PBI_TMPDIR}/.indextmp       
2215                        continue
2216                fi
2217                found=`expr $found + 1`
2218                echo "$iLine" >> ${PBI_TMPDIR}/.foundtmp       
2219        done < $PBI_IT_ADDINDEX 
2220        mv "${PBI_TMPDIR}/.indextmp" "${PBI_IT_ADDINDEX}"
2221}
2222
2223# Add a new repo to the db
2224pbi_browser_init() {
2225        parse_browse_pbi_cmdline "$@"
2226        init_tmpdir
2227
2228        # Check if we are doing a category listing, the default if no options
2229        if [ "$PBI_BROWSE_LISTCATS" = "YES" -o -z "${PBI_BROWSE_LISTALLPBI}${PBI_BROWSE_CAT}${PBI_BROWSE_SEARCH}" ] ; then
2230                pbi_browse_listcats
2231        else
2232                pbi_browse_listpbi
2233        fi
2234
2235}
2236
2237# List PBIs from a repo
2238pbi_browse_listpbi() {
2239        _rArch=`uname -m`
2240
2241        # Figure out which type of display we are doing
2242        if [ -n "$PBI_BROWSE_LISTALLPBI" ] ; then
2243                echo "Using RepoID: $PBI_BROWSE_RID"
2244                echo "Listing all available PBIs"
2245                grep -i -e "^App=" $PBI_BROWSE_METAFILE > ${PBI_TMPDIR}/.meta.$$
2246        elif [ -n "$PBI_BROWSE_CAT" ] ; then
2247                echo "Using RepoID: $PBI_BROWSE_RID"
2248                echo "Available PBIs for Category: $PBI_BROWSE_CAT"
2249                grep -i -e "^App=" -i -e ";${PBI_BROWSE_CAT};" $PBI_BROWSE_METAFILE > ${PBI_TMPDIR}/.meta.$$
2250        elif [ -n "$PBI_BROWSE_SEARCH" ] ; then
2251                echo "Using RepoID: $PBI_BROWSE_RID"
2252                echo "Searching for: $PBI_BROWSE_SEARCH"
2253                grep -i -e "^App=" $PBI_BROWSE_METAFILE > ${PBI_TMPDIR}/.meta.$$
2254        else
2255                exit_err "No valid search variable set!"
2256        fi
2257
2258        while read app
2259        do
2260                line=`echo $app | sed 's|^App=||g'`
2261                catCheck=`echo $line | cut -d ';' -f 2 2>/dev/null`
2262                aName=`echo $line | cut -d ';' -f 1 2>/dev/null`
2263
2264                # Make sure this is from the correct category
2265                if [ -n "$PBI_BROWSE_CAT" ] ; then
2266                        _cCheck=`echo $catCheck | tr '[:lower:]' '[:upper:]'`
2267                        _cCheck2=`echo $PBI_BROWSE_CAT | tr '[:lower:]' '[:upper:]'`
2268                        if [ "$_cCheck" != "$_cCheck2" ]; then
2269                        continue
2270                        fi
2271                fi
2272
2273                # Set the displayed arch type
2274                aArch="$_rArch"
2275
2276                # Make sure this application has an associated PBI available
2277                check_pbi_update "$aName" "nodisplay" \
2278                 "$aName" "current" \
2279                 "$FBSDMAJOR" "$_rArch" "${PBI_BROWSE_RID}"
2280                if [ "$?" != "0" ] ; then
2281                        # On amd64, see if 32bit version exists
2282                        if [ "$_rArch" = "amd64" ] ; then
2283                                check_pbi_update "$aName" "nodisplay" \
2284                                "$aName" "current" \
2285                                "$FBSDMAJOR" "i386" "${PBI_BROWSE_RID}"
2286                                if [ "$?" != "0" ] ; then
2287                                        continue
2288                                else
2289                                        # Found a 32bit version of the app
2290                                        aArch="i386"
2291                                fi
2292                        else
2293                                # Not on amd64, continue on
2294                                continue
2295                        fi
2296                fi
2297
2298                aIcon=`echo $line | cut -d ';' -f 3`
2299                aAuthor=`echo $line | cut -d ';' -f 4`
2300                aUrl=`echo $line | cut -d ';' -f 5`
2301                aLic=`echo $line | cut -d ';' -f 6`
2302                aType=`echo $line | cut -d ';' -f 7`
2303                aKeywords=`echo $line | cut -d ';' -f 8`
2304                aDesc=`echo $line | cut -d ';' -f 9`
2305                aRoot=`echo $line | cut -d ';' -f 10`
2306
2307                # Check for a translation to the description
2308                get_meta_trans "App" "$cName" "${PBI_BROWSE_METAFILE}"
2309                if [ -n "$MTRANS" ] ; then
2310                        aDesc="$MTRANS"
2311                fi
2312
2313                # Search the description / keywords
2314                if [ -n "$PBI_BROWSE_SEARCH" ] ; then
2315                        echo "$aName,$aDesc,$aKeywords,$MTRANS" | grep -i "$PBI_BROWSE_SEARCH" >/dev/null 2>/dev/null
2316                        if [ "$?" != "0" ]; then continue ; fi
2317                fi
2318
2319                # Get the local icon file
2320                ext=`echo $aIcon | sed 's/.*\.//'`
2321                aIcon="${PBI_DBICONDIR}/${PBI_BROWSE_REPOMD5}-${aName}.${ext}"
2322
2323                echo "------------------------------------"
2324                echo "Application: $aName"
2325                echo "Version: $PBI_UPNVER"
2326                if [ -n "$PBI_UPSIZE" ] ; then
2327                        echo "Size: $PBI_UPSIZE"
2328                fi
2329                if [ -n "$PBI_BROWSE_LISTALLPBI" ] ; then
2330                        echo "Category: $catCheck"
2331                fi
2332                echo "Created: `echo $PBI_UPMDATE`"
2333                if [ "$aRoot" = "YES" ] ; then
2334                        echo "RootInstall: YES"
2335                else
2336                        echo "RootInstall: NO"
2337                fi
2338                echo "Arch: $aArch"
2339                echo "Author: $aAuthor"
2340                echo "URL: $aUrl"
2341                echo "License: $aLic"
2342                echo "Type: $aType"
2343                echo "Keywords: $aKeywords"
2344                echo "Icon: $aIcon"
2345                echo "Description: $aDesc"
2346                echo ""
2347                if [ "$aRoot" = "YES" ] ; then
2348                        echo "To install this PBI (As Root):"
2349                else
2350                        echo "To install this PBI:"
2351                fi
2352                echo "# pbi_add --rArch $aArch --repo $PBI_BROWSE_RID -r $aName"
2353                echo ""
2354
2355               
2356        done < ${PBI_TMPDIR}/.meta.$$
2357
2358}
2359
2360# List available categories for this repository
2361pbi_browse_listcats() {
2362
2363        echo "Using RepoID: $PBI_BROWSE_RID"
2364        echo "Available Categories:"
2365        grep "^Cat=" $PBI_BROWSE_METAFILE > ${PBI_TMPDIR}/.meta.$$
2366        while read cat
2367        do
2368                line=`echo $cat | sed 's|^Cat=||g'`
2369                cName=`echo $line | cut -d ';' -f 1`
2370                cIcon=`echo $line | cut -d ';' -f 2`
2371                cDesc=`echo $line | cut -d ';' -f 3`
2372               
2373                # Check for a translation to the description
2374                get_meta_trans "Cat" "$cName" "${PBI_BROWSE_METAFILE}"
2375                if [ -n "$MTRANS" ] ; then
2376                        cDesc="$MTRANS"
2377                fi
2378
2379                # Get the local icon file
2380                ext=`echo $cIcon | sed 's/.*\.//'`
2381                cIcon="${PBI_DBICONDIR}/${PBI_BROWSE_REPOMD5}-${cName}.${ext}"
2382
2383                echo "------------------------------------"
2384                echo "Category: $cName"
2385                echo "Icon: $cIcon"
2386                echo "Description: $cDesc"
2387                echo ""
2388
2389        done < ${PBI_TMPDIR}/.meta.$$
2390
2391        echo "To view available PBIs for a particular category:"
2392        echo " % pbi_browser -c <category> <repoid>"
2393}
2394
2395# Function to check if we have a translated description
2396get_meta_trans() {
2397        local tag="$1"
2398        local name="$2"
2399        local metaFile="$3"
2400
2401        # Check if we have a translation to overwrite with
2402        MTRANS=""
2403        if [ -z "$LANG" ] ; then return; fi
2404
2405        lCheck="`echo $LANG | cut -d '_' -f 1` `echo $LANG | cut -d '.' -f 1`"
2406        for l in $lCheck
2407        do
2408                catTrans=`grep "^${tag}\[$l\]=${name}" ${metaFile}`     
2409                if [ -n "$catTrans" ] ; then
2410                        MTRANS=`echo $catTrans | cut -d ";" -f 2`
2411                        return
2412                fi
2413        done
2414}
2415
2416# List repos in the db
2417pbi_listrepo_init() {
2418        require_root_or_group
2419        parse_listrepo_pbi_cmdline "$@"
2420
2421        # List the repos
2422        if [ -z "$PBI_LISTREPO_ID" ] ; then
2423                list_all_pbi_repo
2424        else
2425                if [ -n "${PBI_LISTREPO_UP}" ]; then
2426                        require_root
2427                        move_repo_up "${PBI_LISTREPO_ID}" 
2428                        list_all_pbi_repo
2429                elif [ -n "${PBI_LISTREPO_DOWN}" ] ; then
2430                        require_root
2431                        move_repo_down "${PBI_LISTREPO_ID}"
2432                        list_all_pbi_repo
2433                elif [ -n "${PBI_LISTREPO_MIRROR}" ] ; then
2434                        require_root
2435                        change_repo_mirror "${PBI_LISTREPO_ID}"
2436                        listrepo_details "${PBI_LISTREPO_ID}"
2437                else
2438                        listrepo_details "${PBI_LISTREPO_ID}"
2439                fi
2440        fi
2441}
2442
2443# Function to change a specific repos mirror URL
2444change_repo_mirror() {
2445        local _rMd5=`ls ${PBI_DBREPODIR}/${1}.* | cut -d '.' -f 2`
2446        echo "$PBI_LISTREPO_MIRROR" | sed 's|,|\
2447|g' > "${PBI_DBMIRRORDIR}/${_rMd5}"
2448}
2449
2450# Move a repo down in priority
2451move_repo_down() {
2452        _rFile=`ls ${PBI_DBREPODIR}/${1}.*`
2453        _uNum=`expr ${1} + 1`
2454
2455        case `echo ${_uNum} | wc -m | tr -d ' '` in
2456                2) _uNum="00${_uNum}" ;;
2457                3) _uNum="0${_uNum}" ;;
2458                *) ;;
2459        esac
2460        _uFile=`ls ${PBI_DBREPODIR}/${_uNum}.* 2>/dev/null`
2461        if [ -z "$_uFile" ] ; then exit_err "This repo is already at the lowest priority!" ; fi
2462
2463        _umd5=`echo $_uFile | cut -d '.' -f 2`
2464        mv "${_uFile}" "${PBI_DBREPODIR}/${1}.${_umd5}"
2465        _rmd5=`echo $_rFile | cut -d '.' -f 2`
2466        mv "${_rFile}" "${PBI_DBREPODIR}/${_uNum}.${_rmd5}"
2467}
2468
2469# Move a repo up in priority
2470move_repo_up() {
2471        _rFile=`ls ${PBI_DBREPODIR}/${1}.*`
2472        _uNum=`expr ${1} - 1`
2473
2474        case `echo ${_uNum} | wc -m | tr -d ' '` in
2475                2) _uNum="00${_uNum}" ;;
2476                3) _uNum="0${_uNum}" ;;
2477                *) ;;
2478        esac
2479        _uFile=`ls ${PBI_DBREPODIR}/${_uNum}.* 2>/dev/null`
2480        if [ -z "$_uFile" ] ; then exit_err "This repo is already at the highest priority!" ; fi
2481
2482        _umd5=`echo $_uFile | cut -d '.' -f 2`
2483        mv "${_uFile}" "${PBI_DBREPODIR}/${1}.${_umd5}"
2484        _rmd5=`echo $_rFile | cut -d '.' -f 2`
2485        mv "${_rFile}" "${PBI_DBREPODIR}/${_uNum}.${_rmd5}"
2486}
2487
2488# List all PBI repos
2489listrepo_details() {
2490        _rFile=`ls ${PBI_DBREPODIR}/${1}.*`
2491        _md5=`ls ${PBI_DBREPODIR}/${1}.* | cut -d '.' -f 2`
2492        _desc=`cat ${_rFile} | grep "Desc: " | sed "s|Desc: ||g"` 
2493        _url=`cat ${_rFile} | grep "URL: " | sed "s|URL: ||g"` 
2494        _mirror=`cat ${PBI_DBMIRRORDIR}/$_md5` 
2495        echo "Repo ID: ${1}"
2496        echo "Description: ${_desc}"
2497        echo "IndexURL: ${_url}"
2498        echo "MD5: ${_md5}"
2499        echo "LocalMeta: `ls ${PBI_DBINDEXDIR}/${_md5}*meta 2>/dev/null`"
2500        echo "LocalIndex: `ls ${PBI_DBINDEXDIR}/${_md5}*index 2>/dev/null`"
2501        echo "Mirror(s):"
2502        echo "$_mirror"
2503}
2504
2505# List all PBI repos
2506list_all_pbi_repo() {
2507        echo "[ID]      [Description]"
2508        echo "-----------------------------------------------------"
2509        for repo in `ls ${PBI_DBREPODIR} | sort `
2510        do
2511                _id=`echo $repo | cut -d '.' -f 1`
2512                _desc=`cat ${PBI_DBREPODIR}/${repo} | grep "Desc: " | sed "s|Desc: ||g"` 
2513                echo "${_id}    ${_desc}"
2514        done
2515}
2516
2517# Start the patch process
2518pbi_patch_init() {
2519        require_root_or_group
2520        init_tmpdir
2521        parse_patch_pbi_cmdline "$@"
2522
2523        # Check if we are only displaying information
2524        check_pbi_info_display
2525        check_pbi_gui_display
2526        check_pbi_scripts_display
2527        check_pbi_license_display
2528        if [ "$PBI_ADD_GUIDISPLAY" = "YES" -o "$PBI_ADD_INFODISPLAY" = "YES" -o "$PBI_CHECKSCRIPTS" = "YES" -o "${PBI_ADD_LICDISPLAY}" = "YES" -o "${PBI_ADD_METADISPLAY}" = "YES" ] 
2529        then
2530                exit_trap
2531        fi
2532
2533        # Try to apply this patch file
2534        do_pbi_patch
2535}
2536
2537# Start the PBI patch process
2538do_pbi_patch() {
2539       
2540        # Verify the target PBI is installed
2541        verify_pbi_update_target
2542
2543        pbi_verify_signatures
2544        pbi_verify_archivesum
2545       
2546        # Extract the archive contents
2547        mk_pbi_extract_dir
2548        pbi_extract_archive
2549
2550        set_patch_wrkdir
2551
2552        init_tmpdir
2553
2554        # Run the uninstall script
2555        if [ -e "${PBI_PATCHWRKDIR}/.sbin/.pbi-uninstall.sh" ] ; then
2556                echo "Removing old xdg data..."
2557                sh "${PBI_PATCHWRKDIR}/.sbin/.pbi-uninstall.sh" >/dev/null 2>/dev/null
2558        fi
2559
2560        # Remove old files from the installed PBI
2561        patch_rm_old_files
2562       
2563        # Extract the new files
2564        patch_extract_new_files
2565
2566        # Merge in the bsdiffs
2567        patch_merge_bsdiffs
2568
2569        # Make sure we have good permissions on this PBI
2570        patch_apply_chmod
2571
2572        # Run the install script
2573        if [ -e "${PBI_PATCHWRKDIR}/.sbin/.pbi-install.sh" ] ; then
2574                echo "Adding new xdg data..."
2575                sh "${PBI_PATCHWRKDIR}/.sbin/.pbi-install.sh"   >/dev/null 2>/dev/null
2576        fi
2577
2578        # If running as user, add bin path-links
2579        if [ "`id -u`" != "0" ] ; then add_app_path_links "${PBI_PATCHWRKDIR}" ; fi
2580
2581        # Update the registered version of the PBI
2582        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
2583        oldDir="${PBI_DBAPPDIR}/${_pbilow}-${PBI_PATCHTARGET}-${PBI_APPARCH}"
2584        newDir="${PBI_DBAPPDIR}/${_pbilow}-${PBI_PATCHVERSION}-${PBI_APPARCH}"
2585        mv "$oldDir" "$newDir"
2586        rm ${newDir}/*.sha1 >/dev/null 2>/dev/null
2587
2588        # Register the app
2589        pbi_add_register_app   
2590
2591        # Check if we need to run a post-install.sh script again
2592        if [ -e "${newDir}/${MOD_POSTINS}" ] ; then
2593          export_script_vars
2594          sh "${newDir}/${MOD_POSTINS}"
2595        fi
2596
2597        # Cleanup after our selves
2598        if [ -d "$PBI_EXTRACTDIR" ] ; then
2599                echo "Cleaning up..."
2600                rm -rf "$PBI_EXTRACTDIR"
2601        fi
2602
2603        # Update the hashdir
2604        add_hashdir_trigger
2605
2606        # Mark the hash-dir as dirty as well
2607        make_hashdir_dirty
2608
2609        echo "Finished patching ${_pbilow}: $PBI_PATCHTARGET -> $PBI_PATCHVERSION"
2610}
2611
2612# Mark the hashdir as dirty
2613make_hashdir_dirty() {
2614        date "+%s" > "${PBI_DBDIRTYFILE}"
2615}
2616
2617# Do any chmod stuff after patching
2618patch_apply_chmod()
2619{
2620        if [ ! -e "${PBI_EXTRACTDIR}/PBI-permList" ] ; then return; fi
2621
2622        cuDir=`pwd`
2623
2624        cd "${PBI_PATCHWRKDIR}"
2625        echo "Applying updated permissions..."
2626        while read chLine
2627        do
2628                $chLine >/dev/null 2>/dev/null
2629        done < "${PBI_EXTRACTDIR}/PBI-permList"
2630
2631        cd "$cuDir"
2632}
2633
2634# Function which does the merge of bsdiff files
2635patch_merge_bsdiffs()
2636{
2637        echo "Applying patch data..."
2638        find ${PBI_EXTRACTDIR} | grep '.bsdiff' | sed "s|${PBI_EXTRACTDIR}/||g" > ${PBI_TMPDIR}/.PBI.bspatch.$$
2639
2640        while read pLine
2641        do
2642                if [ -z "$pLine" ] ; then continue; fi
2643                _tFile="`echo $pLine | sed 's|.bsdiff$||g'`"
2644               
2645                if [ ! -e "${PBI_EXTRACTDIR}/${_tFile}.sha256" ] ; then
2646                        exit_err "Missing checksums for \"${_tFile}\" this patch is corrupt"
2647                fi
2648
2649                if [ ! -e "${PBI_PATCHWRKDIR}/${_tFile}" ] ; then
2650                        echo "Warning: Missing target file for patching: $_tFile"
2651                        continue
2652                fi
2653               
2654                # Make sure we really are trying to patch the same file
2655                sha1="`sha256 -q ${PBI_PATCHWRKDIR}/${_tFile}`"
2656                sha2="`cat ${PBI_EXTRACTDIR}/${_tFile}.sha256`"
2657                if [ "$sha1" != "$sha2" ] ; then
2658                        exit_err "Error: Checksum failed for ${_tFile}, you may need to re-install this PBI."
2659                fi
2660
2661                _fPerm=`stat -f %Op "${PBI_PATCHWRKDIR}/${_tFile}"  | cut -c 3-6`
2662
2663                # See if we have a hard-link to take care of first
2664                get_hard_link_count "${PBI_PATCHWRKDIR}/${_tFile}"
2665                if [ "$HLINKS" != "1" ] ; then
2666                        mv "${PBI_PATCHWRKDIR}/${_tFile}" "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$"
2667                        cp "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$" "${PBI_PATCHWRKDIR}/${_tFile}"
2668                        rm -f "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$"
2669                fi
2670               
2671                # Now do the patching
2672                #echo "Patching $_tFile"       
2673                mv "${PBI_PATCHWRKDIR}/${_tFile}" "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$"
2674                bspatch "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$" \
2675                        "${PBI_PATCHWRKDIR}/${_tFile}" \
2676                        "${PBI_EXTRACTDIR}/$pLine" >/dev/null 2>/dev/null
2677                if [ "$?" != "0" ] ; then
2678                        echo "Warning: Failed to apply patch to \"$_tFile\""
2679                fi
2680
2681                # Re-apply the same permissions to the new file
2682                chmod $_fPerm "${PBI_PATCHWRKDIR}/${_tFile}"
2683
2684                # Remove the old file
2685                rm "${PBI_PATCHWRKDIR}/${_tFile}.patch.$$"
2686
2687        done < "${PBI_TMPDIR}/.PBI.bspatch.$$"
2688
2689        rm "${PBI_TMPDIR}/.PBI.bspatch.$$"
2690}
2691
2692# Function which does the new file extraction for this PBI
2693patch_extract_new_files()
2694{
2695        if [ ! -e "${PBI_EXTRACTDIR}/PBI-newFiles.tar" ] ; then return; fi
2696        echo "Installing new files..."
2697        tar xvf "${PBI_EXTRACTDIR}/PBI-newFiles.tar" -C "${PBI_PATCHWRKDIR}" >/dev/null 2>/dev/null
2698        if [ "$?" != "0" ] ; then
2699                echo "Warning: Error during new file extraction, PBI may not function correctly."
2700        fi
2701}
2702
2703# Function which removes files that no longer exist in this updated PBI
2704patch_rm_old_files()
2705{
2706        if [ ! -e "${PBI_EXTRACTDIR}/PBI-rmList" ] ; then return; fi
2707       
2708        echo "Removing old files..."
2709        while read rmLine
2710        do
2711                if [ -z "$rmLine" ] ; then continue ; fi
2712                if [ ! -e "${PBI_PATCHWRKDIR}/$rmLine" ] ; then
2713                        continue
2714                fi
2715
2716                rm -rf "${PBI_PATCHWRKDIR}/${rmLine}"
2717        done < "${PBI_EXTRACTDIR}/PBI-rmList"
2718
2719}
2720
2721# Sets the workdir of the target PBI we are patching
2722set_patch_wrkdir()
2723{
2724        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
2725        oldDir="${PBI_DBAPPDIR}/${_pbilow}-${PBI_PATCHTARGET}-${PBI_APPARCH}"
2726
2727        if [ ! -e "${oldDir}/pbi_defaultpath" ] ; then
2728                exit_err "Can not fild default path for \"$PBI_PROGNAME\"!"
2729        fi
2730
2731        PBI_PATCHWRKDIR="`cat ${oldDir}/pbi_defaultpath`"
2732
2733        if [ ! -d "$PBI_PATCHWRKDIR" ] ; then
2734                exit_err "Path for \"$PBI_PROGNAME\" does not exist!"
2735        fi
2736}
2737
2738# Confirms that the target PBI for this patch is installed
2739# Exits if not and we are not doing a extract only
2740verify_pbi_update_target()
2741{
2742        if [ "${PBI_EXTRACTONLY}" = "YES" ] ; then return ; fi
2743       
2744        # Make sure the target PBI is installed
2745        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
2746        oldDir="${PBI_DBAPPDIR}/${_pbilow}-${PBI_PATCHTARGET}-${PBI_APPARCH}"
2747
2748        if [ ! -e "${oldDir}" ] ; then
2749                exit_err "\"${_pbilow}\" does not appear to be installed!"
2750        fi
2751
2752        # Check the arch type
2753        if [ "`cat ${oldDir}/pbi_arch`" != "$PBI_APPARCH" ] ; then
2754                exit_err "Installed \"${PBI_PROGNAME}\" is not compiled for $PBI_APPARCH"
2755        fi
2756
2757        # Check the taret version
2758        if [ "`cat ${oldDir}/pbi_version`" != "$PBI_PATCHTARGET" ] ; then
2759                exit_err "\"${_pbilow}\" patch is for \"$PBI_PROGVERSION\" only!"
2760        fi
2761
2762        # Check the fbsd version
2763        _pFbsdVer="`cat ${oldDir}/pbi_fbsdver | cut -c 1`"
2764        _sFbsdVer="`echo $PBI_FBSDVER | cut -c 1`"
2765        if [ "$_pFbsdVer" != "$_sFbsdVer" ] ; then
2766                exit_err "\"${_pbilow}\" patch is for FreeBSD ${_sFbsdVer}.X only!"
2767        fi
2768
2769        # Check the mdate of the pbi
2770        _pMDate="`cat ${oldDir}/pbi_mdate`"
2771        _sMDate="$PBI_PATCHMDATE"
2772        if [ "$_pMDate" != "$_sMDate" ] ; then
2773                exit_err "\"${_pbilow}\" patch is for the $PBI_PATCHMDATE build!"
2774        fi
2775}
2776
2777# Start the pbi_add process
2778pbi_add_init() {
2779        init_tmpdir
2780        parse_add_pbi_cmdline "$@"
2781
2782
2783        # Check if we are only displaying information
2784        check_pbi_info_display
2785        check_pbi_gui_display
2786        check_pbi_scripts_display
2787        check_pbi_license_display
2788        check_pbi_meta_display
2789        if [ "$PBI_ADD_GUIDISPLAY" = "YES" -o "$PBI_ADD_INFODISPLAY" = "YES" -o "$PBI_CHECKSCRIPTS" = "YES" -o "${PBI_ADD_LICDISPLAY}" = "YES" -o "${PBI_ADD_METADISPLAY}" = "YES" ] 
2790        then
2791                clean_remote_dl
2792                exit_trap
2793        fi
2794
2795        require_root_or_group
2796
2797        # If this app can only be installed as root
2798        if [ "$PBI_REQUIRESROOT" = "YES" ] ; then require_root ; fi
2799
2800        check_agree_lic
2801        check_existing_pbi
2802        do_pbi_add
2803}
2804
2805# Check if this PBI exists and exit if so
2806check_existing_pbi() {
2807        if [ "${PBI_EXTRACTONLY}" = "YES" ] ; then return 0; fi
2808        get_dbdir
2809        dir="${APPDBDIR}"
2810
2811        # See if this PBI is already installed
2812        if [ -d "$dir" ]; then
2813                get_username_from_file "${APPDBDIR}/pbi_name"
2814                if [ "$FILEUSER" != `whoami` -a `id -u` != "0" ] ; then
2815                        exit_err "Permission denied to modify PBI installed by: $FILEUSER"     
2816                fi
2817
2818                if [ "${PBI_FORCEADD}" = "YES" ] ; then return 0; fi
2819                exit_err "${PBI_PROGNAME} ${PBI_PROGVERSION} is already installed! Use -f to force installation."
2820        fi
2821
2822        if [ -e "${PBI_PROGDIRPATH}" ]; then
2823                get_username_from_file "${PBI_PROGDIRPATH}"
2824                if [ "$FILEUSER" != `whoami` -a `id -u` != "0" ] ; then
2825                        exit_err "Permission denied to modify PBI installed by: $FILEUSER"     
2826                fi
2827                if [ "${PBI_FORCEADD}" = "YES" ] ; then return 0; fi
2828                exit_err "${PBI_PROGDIRPATH} already exists! Use -f to force installation."
2829        fi
2830
2831
2832}
2833
2834# Check if we have a license to agree to, and if we've provided the flag to do so
2835check_agree_lic() {
2836        open_header_tmp
2837        if [ -f "${PBI_HEADER_TMPDIR}/${PBI_LICENSEFILE}" -a "${PBI_LICAGREE}" = "NO" ] ; then
2838                delete_header_tmp
2839                exit_err "LICENSE must be agreed to (--licagree) before this PBI can be installed."
2840        fi
2841        delete_header_tmp
2842}
2843
2844# See if we need to display pbi meta file
2845check_pbi_meta_display() {
2846        if [ "$PBI_ADD_METADISPLAY" != "YES" ] ; then return 0 ; fi
2847        open_header_tmp
2848       
2849        if [ -f "${PBI_HEADER_TMPDIR}/${PBI_USERMETAFILE}" ] ; then
2850                cat "${PBI_HEADER_TMPDIR}/${PBI_USERMETAFILE}" 
2851        else
2852                echo "`basename $0`: No user metafile included with this PBI"
2853        fi
2854        delete_header_tmp
2855}
2856
2857# See if we need to display pbi license
2858check_pbi_license_display() {
2859        if [ "$PBI_ADD_LICDISPLAY" != "YES" ] ; then return 0 ; fi
2860        open_header_tmp
2861       
2862        if [ -f "${PBI_HEADER_TMPDIR}/${PBI_LICENSEFILE}" ] ; then
2863                echo "LICENSE:"
2864                cat "${PBI_HEADER_TMPDIR}/${PBI_LICENSEFILE}"   
2865        else
2866                echo "`basename $0`: No LICENSE included with this PBI"
2867        fi
2868        delete_header_tmp
2869}
2870
2871# See if we need to display pbi info
2872check_pbi_info_display() {
2873        if [ "$PBI_ADD_INFODISPLAY" != "YES" ] ; then return 0 ; fi
2874        pbi_display_info
2875}
2876
2877# Display pbi information to stdout
2878pbi_display_info() {
2879
2880        tmp="`echo ${PBI_PROGNAME} | tr -d ' ' | tr '[A-Z]' '[a-z]'`"
2881        _appname="${tmp}-${PBI_PROGVERSION}-${PBI_APPARCH}"
2882
2883        if [ -z "$PBI_PATCHVERSION" ] ; then
2884                echo "PBI Information for: $_appname"
2885        else
2886                echo "PBP Information for: $_appname"
2887        fi
2888        echo "-----------------------------------------------------"
2889        echo "Name: ${PBI_PROGNAME}"
2890
2891        if [ -n "$PBI_PATCHVERSION" ] ; then
2892                echo "PatchTarget: $PBI_PATCHTARGET"
2893        fi
2894
2895        if [ -n "$PBI_INSTALLED_BY" ] ; then
2896                echo "InstalledBy: $PBI_INSTALLED_BY"
2897        fi
2898
2899        # Does this PBI need root to install?
2900        if [ "$PBI_REQUIRESROOT" = "YES" ] ; then
2901                echo "RootInstall: YES"
2902        else
2903                echo "RootInstall: NO"
2904        fi
2905
2906        echo "Version: ${PBI_PROGVERSION}"
2907        echo "Built: ${PBI_PROGMDATE}"
2908        echo "Prefix: ${PBI_ORIGPROGDIRPATH}"
2909        echo "Author: ${PBI_PROGAUTHOR}"
2910        echo "Website: ${PBI_PROGWEB}"
2911        echo "Arch: ${PBI_APPARCH}"
2912        echo "FbsdVer: ${PBI_FBSDVER}"
2913        echo "CreatorVer: ${PBI_APPCREATEVER}"
2914        echo "ArchiveCount: ${PBI_ARCHIVE_COUNT}"
2915        echo "ArchiveSum: ${PBI_ARCHIVE_CHECKSUM}"
2916        case ${PBI_SIGVALID} in
2917                0) echo "Signature: Verified" ;;
2918               -1) echo "Signature: Not Signed" ;;
2919                1) echo "Signature: Bad" ;;
2920                *) echo "Signature: <Unknown>" ;;
2921        esac
2922
2923        if [ -n "$PBI_LICENSE" ] ; then
2924                echo "License: $PBI_LICENSE"
2925        fi
2926
2927        if [ -n "${PBI_REPO}" ] ; then
2928                local _rDesc="`cat ${PBI_DBREPODIR}/*.${PBI_REPO} | grep "Desc:" | sed 's|Desc: ||g'`"
2929                local _rID="`ls ${PBI_DBREPODIR}/*.${PBI_REPO}`"
2930                _rID=`basename $_rID | cut -d '.' -f 1`
2931                echo "Associated Repo: ${_rID} (${_rDesc})"
2932        fi
2933       
2934        # Check if autoupdate is enable or not
2935        if [ "${PBI_ENABLEAUTOUPDATE}" = "YES" ] ; then
2936                echo "AutoUpdate: YES"
2937        else
2938                echo "AutoUpdate: NO"
2939        fi
2940
2941        # See if we have any XDG stuff
2942        if [ -e "${PBI_ORIGPROGDIRPATH}/.xdg-desktop/install-desktop-icons.sh" ] ; then
2943                echo "DesktopIcons: YES"
2944        fi
2945        if [ -e "${PBI_ORIGPROGDIRPATH}/.xdg-menu/install-menu-icons.sh" ] ; then
2946                echo "MenuIcons: YES"
2947        fi
2948        if [ -e "${PBI_ORIGPROGDIRPATH}/.xdg-mime/install-mime.sh" ] ; then
2949                echo "MimeRegistration: YES"
2950        fi
2951
2952        # If verbose mode, show file contents
2953        if [ "$PBI_VERBOSE" = "YES" ] ; then
2954                if [ -n "${PBI_FILENAME}" -a -e "${PBI_FILENAME}" ] ; then
2955                        pbi_find_archive_header
2956                        echo "TOTALFILES: ${PBI_ARCHIVE_COUNT}"
2957                        echo "Archive Contents:"
2958                        echo "--------------------------------------"
2959                        tail +$PBI_SKIP_ARCHLINES "${PBI_FILENAME}" | tar tvf -
2960                fi
2961        fi
2962}
2963
2964# See if we need to display gui header info
2965check_pbi_gui_display() {
2966        if [ "$PBI_ADD_GUIDISPLAY" != "YES" ] ; then return 0 ; fi
2967        open_header_tmp
2968       
2969        pbi_display_gui "$PBI_HEADER_TMPDIR" "COPY"
2970
2971        delete_header_tmp
2972
2973}
2974
2975# Display location of PBI graphics
2976pbi_display_gui() {
2977        dir="$1"
2978        copy="$2"
2979        if [ -e "${dir}/top-banner.png" ] ; then
2980                if [ "$copy" = "COPY" ] ; then
2981                        pbi_guitop="/tmp/.PBI-top.$$.png"
2982                        cp "${dir}/top-banner.png" "$pbi_guitop"
2983                else
2984                        pbi_guitop="${dir}/top-banner.png"
2985                fi
2986                echo "TopBanner: ${pbi_guitop}"
2987        fi
2988        if [ -e "${dir}/side-banner.png" ] ; then
2989                if [ "$copy" = "COPY" ] ; then
2990                        pbi_guiside="/tmp/.PBI-side.$$.png"
2991                        cp "${dir}/side-banner.png" "$pbi_guiside"
2992                else
2993                        pbi_guiside="${dir}/side-banner.png"
2994                fi
2995                echo "SideBanner: ${pbi_guiside}"
2996        fi
2997
2998        # Try to find an icon
2999        ls ${dir}/pbi_icon.* >/dev/null 2>/dev/null
3000        if [ "$?" = "0" ] ; then
3001                _iconExt=`ls ${dir}/pbi_icon.* | head -n 1 | awk -F . '{print $NF}'`
3002                if [ "$copy" = "COPY" ] ; then
3003                        pbi_guiicon="/tmp/.PBI-icon.$$.${_iconExt}"
3004                        cp "${dir}/pbi_icon.${_iconExt}" "$pbi_guiicon"
3005                else
3006                        pbi_guiicon="${dir}/pbi_icon.${_iconExt}"
3007                fi
3008                echo "Icon: ${pbi_guiicon}"
3009        fi
3010
3011}
3012
3013open_header_tmp() {
3014        init_tmpdir
3015
3016        # If we have a custom extract dir, use it
3017        if [ -z "$1" ] ; then
3018                PBI_HEADER_TMPDIR="${PBI_TMPDIR}/.PBI-header.$$"
3019        else
3020                PBI_HEADER_TMPDIR="${1}/.PBI-header.$$"
3021        fi
3022
3023        if [ -e "${PBI_HEADER_TMPDIR}" ] ; then rm -rf "${PBI_HEADER_TMPDIR}" ; fi
3024        mkdir -p "${PBI_HEADER_TMPDIR}"
3025       
3026        # Extract the header files
3027        tar xvf "${PBI_FILENAME}" -C "${PBI_HEADER_TMPDIR}" >/dev/null 2>/dev/null
3028        if [ "$?" != "0" ] ; then exit_err "Failed to read PBI header! Possible corrupt PBI, or wrong PBI version for this OS." ; fi
3029
3030}
3031
3032delete_header_tmp() {
3033        if [ -z "${PBI_HEADER_TMPDIR}" ] ; then return 0 ; fi
3034        if [ -d "${PBI_HEADER_TMPDIR}" ] ; then rm -rf "${PBI_HEADER_TMPDIR}" ; fi
3035}
3036
3037# Load in all the configuration data from the header
3038load_info_from_header() {
3039        open_header_tmp
3040
3041        # Start loading our variables
3042        load_info_from_dir "${PBI_HEADER_TMPDIR}"
3043
3044        delete_header_tmp
3045}
3046
3047# See if we need to display scripts
3048check_pbi_scripts_display() {
3049        if [ "$PBI_CHECKSCRIPTS" != "YES" ] ; then return 0 ; fi
3050
3051        # Display our scripts
3052        open_header_tmp
3053        if [ -e "${PBI_HEADER_TMPDIR}/${MOD_PREINS}" ] ; then
3054                echo -e "\n${MOD_PREINS}:"
3055                echo "--------------------------------"
3056                cat "${PBI_HEADER_TMPDIR}/${MOD_PREINS}"
3057        fi
3058        if [ -e "${PBI_HEADER_TMPDIR}/${MOD_POSTINS}" ] ; then
3059                echo -e "\n${MOD_POSTINS}:"
3060                echo "--------------------------------"
3061                cat "${PBI_HEADER_TMPDIR}/${MOD_POSTINS}"
3062        fi
3063        if [ -e "${PBI_HEADER_TMPDIR}/${MOD_PREREM}" ] ; then
3064                echo -e "\n${MOD_PREREM}:"
3065                echo "--------------------------------"
3066                cat "${PBI_HEADER_TMPDIR}/${MOD_PREREM}"
3067        fi
3068        delete_header_tmp
3069}
3070
3071# Load pbi information from the specified directory
3072load_info_from_dir() {
3073        REQUIRED_FILES="pbi_defaultpath pbi_name pbi_version pbi_author pbi_web pbi_arch pbi_fbsdver pbi_createver"
3074        for f in $REQUIRED_FILES
3075        do
3076                if [ ! -e "${1}/${f}" ] ; then echo "Warning: Missing file: ${f}" ; fi
3077        done
3078        PBI_APPARCH=""
3079        PBI_APPCREATEVER=""
3080        PBI_ARCHIVE_CHECKSUM=""
3081        PBI_ARCHIVE_COUNT=""
3082        PBI_ENABLEAUTOUPDATE=""
3083        PBI_FBSDVER=""
3084        PBI_ORIGPROGDIRPATH=""
3085        PBI_PATCHMDATE=""
3086        PBI_PATCHVERSION=""
3087        PBI_PATCHTARGET=""
3088        PBI_PROGNAME=""
3089        PBI_PROGVERSION=""
3090        PBI_PROGAUTHOR=""
3091        PBI_PROGMDATE=""
3092        PBI_PROGWEB=""
3093        PBI_REPO=""
3094        PBI_REQUIRESROOT=""
3095        PBI_SIGVALID=""
3096        PBI_DESC=""
3097        PBI_SHORTDESC=""
3098        PBI_TAGS=""
3099        PBI_PROGTYPE=""
3100        PBI_CATEGORY=""
3101        PBI_ICONURL=""
3102        PBI_LICENSE=""
3103
3104        PBI_ORIGPROGDIRPATH="`cat ${1}/pbi_defaultpath`"
3105        PBI_PROGNAME="`cat ${1}/pbi_name`"
3106        PBI_PROGVERSION="`cat ${1}/pbi_version`"
3107        PBI_PROGAUTHOR="`cat ${1}/pbi_author`"
3108        PBI_PROGWEB="`cat ${1}/pbi_web 2>/dev/null`"
3109        PBI_PROGMDATE="`cat ${1}/pbi_mdate 2>/dev/null`"
3110        PBI_APPARCH="`cat ${1}/pbi_arch 2>/dev/null`"
3111        PBI_FBSDVER="`cat ${1}/pbi_fbsdver 2>/dev/null`"
3112        PBI_APPCREATEVER="`cat ${1}/pbi_createver 2>/dev/null`"
3113        PBI_ARCHIVE_COUNT="`cat ${1}/pbi_archivecount 2>/dev/null`"
3114        PBI_ARCHIVE_CHECKSUM="`cat ${1}/pbi_archivesum 2>/dev/null`"
3115
3116        if [ -e "${1}/pbi_license" ] ; then
3117                PBI_LICENSE="`cat ${1}/pbi_license`"
3118        fi
3119        if [ -e "${1}/pbi_tags" ] ; then
3120                PBI_TAGS="`cat ${1}/pbi_tags`"
3121        fi
3122        if [ -e "${1}/pbi_type" ] ; then
3123                PBI_PROGTYPE="`cat ${1}/pbi_type`"
3124        fi
3125        if [ -e "${1}/pbi_category" ] ; then
3126                PBI_CATEGORY="`cat ${1}/pbi_category`"
3127        fi
3128        if [ -e "${1}/pbi_iconurl" ] ; then
3129                PBI_ICONURL="`cat ${1}/pbi_iconurl`"
3130        fi
3131        if [ -e "${1}/pbi_desc" ] ; then
3132                PBI_DESC="`cat ${1}/pbi_desc`"
3133        fi
3134        if [ -e "${1}/pbi_shortdesc" ] ; then
3135                PBI_SHORTDESC="`cat ${1}/pbi_shortdesc`"
3136        fi
3137
3138        # Check if auto-update is enabled
3139        if [ -e "${1}/autoupdate-enable" ] ; then
3140                PBI_ENABLEAUTOUPDATE="YES"
3141        fi
3142
3143        # Does this PBI need to be installed as root
3144        if [ -e "${1}/pbi_requiresroot" ] ; then
3145                PBI_REQUIRESROOT="YES"
3146        fi
3147       
3148        # Check if this is a patch file
3149        if [ -e "${1}/pbi_patchfile" ] ; then
3150                PBI_PATCHVERSION=`cat ${1}/pbi_patchfile | cut -d ':' -f 2`
3151                PBI_PATCHTARGET=`cat ${1}/pbi_patchfile | cut -d ':' -f 1`
3152        fi
3153       
3154        # Check if this associates with a particular repo
3155        if [ -e "${1}/pbi_repo" ] ; then
3156                PBI_REPO=`cat ${1}/pbi_repo`
3157        fi
3158
3159        # See if this patch is for a particular mdate
3160        if [ -e "${1}/pbi_patchmdate" ] ; then
3161                PBI_PATCHMDATE=`cat ${1}/pbi_patchmdate`
3162        fi
3163
3164        # See if this PBI was signed
3165        if [ -e "${1}/pbi_archivesum.sha1" ] ; then
3166                check_valid_sigs "${1}"
3167                if [ "$?" = "0" ] ; then
3168                        PBI_SIGVALID="0"
3169                else
3170                        PBI_SIGVALID="1"
3171                fi
3172        else
3173                PBI_SIGVALID="-1"
3174        fi
3175}
3176
3177# Start installing the PBI
3178do_pbi_add() {
3179        pbi_verify_signatures
3180        pbi_verify_archivesum
3181
3182        check_preinstall_script
3183
3184        mk_pbi_extract_dir
3185        pbi_extract_archive
3186       
3187        pbi_add_check_uids
3188        pbi_add_check_gids
3189
3190        pbi_add_run_script
3191        check_postinstall_script
3192
3193        pbi_add_register_app
3194
3195        # Be sure to let the pbid know we have a new hash-dir to register
3196        add_hashdir_trigger
3197
3198        clean_remote_dl
3199}
3200
3201# Check for any GIDs we need to create
3202pbi_add_check_gids() {
3203        if [ ! -e "${PBI_PROGDIRPATH}/${PBI_INS_GROUPSFILE}" ] ; then return ; fi
3204        runUID=`id -u`
3205
3206        while read gidLine
3207        do
3208                gName=`echo $gidLine | cut -d ':' -f 1`
3209                gID=`echo $gidLine | cut -d ':' -f 3`
3210                gUsers=`echo $gidLine | cut -d ':' -f 4`
3211
3212                # Is this group already on the system?
3213                pw groupshow $gName >/dev/null 2>/dev/null
3214                if [ $? -eq 0 ] ; then
3215                        echo "Using existing group: $gName"
3216                else
3217                        # Are we installing as root?
3218                        if [ "$runUID" != "0" ] ; then
3219                                echo "Please create group \"$gName\" manually or re-install PBI as root."
3220                        else
3221                                echo "Adding group: $gName"
3222                                pw groupadd $gName -g $gID;
3223                        fi
3224                fi
3225
3226                if [ -n "$gUsers" ] ; then
3227                        for gUser in `echo $gUsers | sed 's|,| |g'`
3228                        do
3229                                pw groupshow ${gName} | grep -qw ${gUser}
3230                                if [ $? -ne 0 ] ; then
3231                                        # Are we installing as root?
3232                                        if [ "$runUID" != "0" ] ; then
3233                                                echo "Please add user \"$gUser\" to group \"$gName\" manually or re-install PBI as root."
3234                                                continue
3235                                        fi
3236
3237                                        echo "Adding user ${gUser} to group ${gName}"
3238                                        pw groupmod ${gName} -m ${gUser}
3239                                fi
3240                        done
3241                fi
3242        done < ${PBI_PROGDIRPATH}/${PBI_INS_GROUPSFILE}
3243}
3244
3245# Check for any UIDs we need to create
3246pbi_add_check_uids() {
3247        if [ ! -e "${PBI_PROGDIRPATH}/${PBI_INS_USERSFILE}" ] ; then return ; fi
3248        runUID=`id -u`
3249
3250        while read uidLine
3251        do
3252                uName=`echo $uidLine | cut -d ':' -f 1`
3253
3254                # Is this user already on the system?
3255                pw usershow $uName >/dev/null 2>/dev/null
3256                if [ $? -eq 0 ] ; then echo "Using existing user: $uName"; continue ; fi
3257
3258                # Are we installing as root?
3259                if [ "$runUID" != "0" ] ; then
3260                        echo "Please create user \"$uName\" manually or re-install PBI as root."
3261                        continue
3262                fi
3263
3264                uID=`echo $uidLine | cut -d ':' -f 3`
3265                gID=`echo $uidLine | cut -d ':' -f 4`
3266                uClass=`echo $uidLine | cut -d ':' -f 5`
3267                uGecos=`echo $uidLine | cut -d ':' -f 8`
3268                uHomedir=`echo $uidLine | cut -d ':' -f 9 | sed "s|^/usr/local|${PBI_PROGDIRPATH}|"`
3269                uShell=`echo $uidLine | cut -d ':' -f 10`
3270
3271                echo "Adding user: $uName"
3272                pw useradd $uName -u $uID -g $gID $uClass -c "$uGecos" -d $uHomedir -s $uShell;
3273
3274                # Create homedir
3275                case $uHomedir in
3276                        /nonexistent|/var/empty) ;;
3277                        *) install -d -g $gID -o $uID $uHomedir ;;
3278                esac
3279        done < ${PBI_PROGDIRPATH}/${PBI_INS_USERSFILE}
3280}
3281
3282add_hashdir_trigger() {
3283        get_dbdir
3284        _htrig=`echo ${APPDBDIR} | sed "s|${PBI_DBAPPDIR}|${PBI_DBHASHQUEUEDIR}|g"`
3285        if [ ! -e "${_htrig}" ] ; then
3286                touch "${_htrig}"
3287        fi
3288}
3289
3290# Run the install script if exists
3291pbi_add_run_script() {
3292
3293        # If running as user, add bin path-links
3294        if [ "`id -u`" != "0" ] ; then add_app_path_links "${PBI_PROGDIRPATH}" ; fi
3295
3296        insc="${PBI_PROGDIRPATH}/${PBI_FAKEBIN_DIR}/.pbi-install.sh"
3297        if [ ! -e "${insc}" ] ; then return 0 ; fi
3298        export_script_vars
3299        if [ "$PBI_VERBOSE" = "YES" ] ; then
3300                ${insc}
3301        else
3302                ${insc} >/dev/null 2>/dev/null
3303        fi
3304
3305}
3306
3307# If we need to, update the hashdir
3308pbi_add_update_hashdir() {
3309        if [ "${PBI_NOHASHDIR}" = "YES" ] ; then return 0 ; fi
3310        if [ ! -e "${1}/${PBI_HASHLIST}" ] ; then return 0; fi
3311
3312        if [ "$PBI_VERBOSE" = "YES" ] ; then
3313                echo "HASHCOUNT: `wc -l ${1}/${PBI_HASHLIST} | tr -d ' ' | cut -d '/' -f 1`"
3314        else
3315       
3316                echo -e "Merging with hashdir...\c"
3317        fi
3318       
3319        # Read the hashfile, and start making links to identical files
3320        while read hl
3321        do
3322                file="`echo $hl | sed 's/:::.*$//g'`"
3323
3324                # If we are trying to merge a PBI which was deleted, stop
3325                if [ -n "${2}" -a -e "${2}" ] ; then
3326                        echo "HASHDONE - Deleted" 
3327                        return
3328                fi
3329
3330                # Make sure the target file hasnt been removed
3331                if [ ! -e "${1}/${file}" ] ; then continue ; fi
3332
3333                # We dont need no stinking sym-links
3334                if [ -h "${1}/${file}" ] ; then continue ; fi
3335
3336                if [ -f "${PBI_HASHDIR}/${hl}" ] ; then
3337                        use_hashfile "$hl" "${1}/$file"
3338                else
3339                        mv_ln_hashfile "$hl" "${1}/$file"
3340                fi
3341        done < "${1}/${PBI_HASHLIST}"
3342
3343        if [ "$PBI_VERBOSE" = "YES" ] ; then
3344                echo "HASHDONE"
3345        else
3346                echo -e "Done!" 
3347        fi
3348}
3349
3350# Use an existing hashfile
3351use_hashfile() {
3352        tfile="$1"
3353        file="$2"
3354        dir="`dirname ${tfile}`"
3355        if [ ! -d "${PBI_HASHDIR}/${dir}" ] ; then
3356                mkdir -p ${PBI_HASHDIR}/${dir}
3357        fi
3358
3359        # We have a match!
3360        ln -f "${PBI_HASHDIR}/${tfile}" "${file}"
3361        if [ $? -ne 0 ] ; then
3362                echo "Warning: Unable to make hash-link ${PBI_HASHDIR}/${tfile} -> ${file}"
3363                return
3364        fi
3365       
3366        # Make sure the hard-linked file doesn't get changed
3367        chmod u-w,g-w,o-w "${file}"
3368        if [ $? -ne 0 ] ; then
3369                echo "Warning: Unable to chmod ${file}"
3370                return
3371        fi
3372       
3373}
3374
3375# New file we can save to hashdir
3376mv_ln_hashfile() {
3377        tfile="$1"
3378        file="$2"
3379        dir="`dirname ${tfile}`"
3380        if [ ! -d "${PBI_HASHDIR}/${dir}" ] ; then
3381                mkdir -p ${PBI_HASHDIR}/${dir}
3382        fi
3383
3384        ln -f "${file}" "${PBI_HASHDIR}/${tfile}"
3385        if [ $? -ne 0 ] ; then
3386                echo "Warning: Unable to make hash-link ${file} -> ${PBI_HASHDIR}/${tfile}"
3387                return
3388        fi
3389
3390        # Make sure the hard-linked file doesn't get changed
3391        chmod u-w,g-w,o-w "${file}"
3392        if [ $? -ne 0 ] ; then
3393                echo "Warning: Unable to chmod ${file}"
3394                return
3395        fi
3396
3397        # Make sure the hard-linked file doesn't get changed
3398        chmod u-w,g-w,o-w "${PBI_HASHDIR}/${tfile}"
3399        if [ $? -ne 0 ] ; then
3400                echo "Warning: Unable to chmod ${PBI_HASHDIR}/${tfile}"
3401                return
3402        fi
3403
3404        if [ "$PBI_VERBOSE" = "YES" ] ; then echo "L" ; fi
3405}
3406
3407# Return the dbdir for this PBI
3408get_dbdir() {
3409        tmp="`echo ${PBI_PROGNAME} | tr -d ' ' | tr '[A-Z]' '[a-z]'`"
3410        APPDBDIR="${PBI_DBAPPDIR}/${tmp}-${PBI_PROGVERSION}-${PBI_APPARCH}"
3411}
3412
3413# Register this app as installed
3414pbi_add_register_app() {
3415        if [ ! -d "$PBI_DBAPPDIR" ] ; then mkdir -p ${PBI_DBAPPDIR} ; fi
3416        open_header_tmp
3417        get_dbdir
3418        dir="${APPDBDIR}"
3419
3420        # Make sure we remove any existing meta-data if forcing an installation
3421        if [ "$PBI_FORCEADD" = "YES" ] ; then
3422                tmp="`echo ${PBI_PROGNAME} | tr -d ' ' | tr '[A-Z]' '[a-z]'`"
3423                rm -rf ${PBI_DBAPPDIR}/${tmp}-*-${PBI_APPARCH}
3424        fi
3425
3426        mkdir -p "${dir}"
3427       
3428        tar cvf - -C "${PBI_HEADER_TMPDIR}" . 2>/dev/null | tar xvf - -C "$dir" 2>/dev/null
3429
3430        # If this was a patch, use the original path
3431        if [ -n "${PBI_ORIGPROGDIRPATH}" ] ; then
3432                echo "${PBI_ORIGPROGDIRPATH}" >${dir}/pbi_installedpath
3433        else
3434                echo "${PBI_PROGDIRPATH}" >${dir}/pbi_installedpath
3435        fi
3436
3437        # See which repo / key this PBI associates to, if any
3438        check_valid_sigs "${dir}"
3439        if [ -n "$PBI_VALIDKEYSIG" ] ; then
3440                _rMd5="`echo ${PBI_VALIDKEYSIG} | cut -d '.' -f 1`"
3441                echo "$_rMd5" | sed "s|${PBI_DBKEYDIR}/||g" > ${dir}/pbi_repo
3442        fi
3443
3444        # Dont need any patch version info
3445        if [ -e "${dir}/pbi_patchfile" ] ; then
3446                rm "${dir}/pbi_patchfile"
3447        fi
3448
3449        delete_header_tmp
3450
3451        echo "Installed: ${PBI_PROGNAME}-${PBI_PROGVERSION}"
3452}
3453
3454# Check if we have a postinstall script we need to use
3455check_postinstall_script() {
3456        open_header_tmp
3457
3458        if [ ! -e "${PBI_HEADER_TMPDIR}/${MOD_POSTINS}" ] ; then
3459                delete_header_tmp
3460                return 0
3461        fi
3462
3463        export_script_vars
3464        sh "${PBI_HEADER_TMPDIR}/${MOD_POSTINS}"
3465        delete_header_tmp
3466}
3467
3468# Check if we have a preinstall script we need to use
3469check_preinstall_script() {
3470        open_header_tmp
3471
3472        if [ ! -e "${PBI_HEADER_TMPDIR}/${MOD_PREINS}" ] ; then
3473                delete_header_tmp
3474                return 0
3475        fi
3476
3477        export_script_vars
3478        sh "${PBI_HEADER_TMPDIR}/${MOD_PREINS}"
3479        if [ "$?" != "0" ] ; then
3480                delete_header_tmp
3481                exit_err "${MOD_PREINS} returned error status"
3482        fi
3483        delete_header_tmp
3484}
3485
3486# Verify if we have valid openssl signatures on important parts of PBI
3487pbi_verify_signatures() {
3488        if [ "${PBI_SKIPSIGVERIFY}" = "YES" ] ; then return 0 ; fi
3489        if [ "$PBI_SIGVALID" = "0" ] ; then return ; fi
3490        if [ "$PBI_SIGVALID" = "1" ] ; then kw="Invalid" ; else kw="No" ; fi
3491        exit_err "$kw digital signature! If you are *SURE* you trust this PBI, re-install with --no-checksig option. "
3492
3493}
3494
3495# Check if we have valid signatures, and return "0" if success, "1" if failure
3496check_valid_sigs() {
3497        PBI_VALIDKEYSIG=""
3498
3499        for _pk in ${PBI_PUBKEYS}
3500        do
3501                good="true"
3502                _sf="${1}/pbi_archivesum ${1}/${MOD_PREINS} ${1}/${MOD_POSTINS} ${1}/${MOD_PREREM}"
3503                for _ts in $_sf
3504                do
3505                        openssl dgst -sha1 \
3506                        -verify ${_pk} \
3507                        -signature ${_ts}.sha1 \
3508                        ${_ts} >/dev/null 2>/dev/null
3509                        if [ "$?" != "0" ] ; then
3510                                good="false" ; break
3511                        fi
3512                        PBI_VALIDKEYSIG="$_pk"
3513                done
3514                if [ "$good" = "true" ] ; then return 0 ; fi
3515        done
3516        return 1       
3517}
3518
3519# Verify if the archive checksum is good
3520pbi_verify_archivesum() {
3521        if [ "${PBI_SKIPCHECKSUM}" = "YES" ] ; then return 0 ; fi
3522        echo -e "Verifying Checksum...\c"
3523
3524        pbi_find_archive_header
3525        sum=`tail +$PBI_SKIP_ARCHLINES "${PBI_FILENAME}" | sha256 -q`
3526        if [ "$PBI_VERBOSE" = "YES" ] ; then
3527                echo "Archive checksum: ${sum}"
3528                echo "Saved checksum: ${PBI_ARCHIVE_CHECKSUM}"
3529        fi
3530        if [ "$sum" != "$PBI_ARCHIVE_CHECKSUM" ] ; then
3531                exit_err "${PBI_FILENAME} failed checksum, the archive may be corrupt."
3532        fi
3533        echo -e "OK"
3534
3535}
3536
3537# Make our PBI extraction dir
3538mk_pbi_extract_dir() {
3539        PBI_EXTRACTDIR="${PBI_PROGDIRPATH}"
3540        if [ -e "${PBI_EXTRACTDIR}" ] ; then
3541               rm -rf "$PBI_EXTRACTDIR"
3542        fi
3543        mkdir -p "${PBI_EXTRACTDIR}" >/dev/null 2>/dev/null
3544        if [ "$?" != "0" ] ; then
3545                exit_err "Failed to create directory: ${PBI_PROGDIRPATH}"
3546        fi
3547}
3548
3549pbi_find_archive_header() {
3550        # Find the header for the archive
3551        # SEARCH FOR: $PBI_SS_ARCHIVE
3552        PBI_SKIP_ARCHLINES=`awk "/^${PBI_SS_ARCHIVE}/ { print NR + 1; exit 0; }" "${PBI_FILENAME}"`
3553        if [ "$PBI_VERBOSE" = "YES" ] ; then
3554                echo "SKIP_ARCHLINES: $PBI_SKIP_ARCHLINES"
3555        fi
3556}
3557
3558# Extract the PBI archive file
3559pbi_extract_archive() {
3560        pbi_find_archive_header
3561
3562        echo "Extracting to: ${PBI_EXTRACTDIR}"
3563        tar="xvf -"
3564
3565        if [ "$PBI_VERBOSE" = "YES" ] ; then
3566                echo "TOTALFILES: ${PBI_ARCHIVE_COUNT}"
3567                tail +$PBI_SKIP_ARCHLINES "${PBI_FILENAME}" | tar ${tar} -C "${PBI_EXTRACTDIR}"
3568                err="$?"
3569        else
3570                tail +$PBI_SKIP_ARCHLINES "${PBI_FILENAME}" | tar ${tar} -C "${PBI_EXTRACTDIR}" >/dev/null 2>/dev/null
3571                err="$?"
3572        fi
3573       
3574        if [ "$err" != "0" ] ; then exit_err "Failed extracting ${PBI_FILENAME}" ; fi
3575
3576        if [ "$PBI_VERBOSE" = "YES" ] ; then echo "Extraction Finished!" ; fi
3577
3578        # If this is an extract only, do it and exit
3579        if [ "${PBI_EXTRACTONLY}" = "YES" ] ; then exit_trap ; fi
3580}
3581       
3582
3583# Starting pbi_create
3584pbi_create_init() {
3585
3586        require_root
3587
3588        parse_create_pbi_cmdline "$@"
3589
3590        # If we are making a backup copy of an installed PBI
3591        if [ "$PBI_CBACKUP" = "YES" ] ; then
3592                init_tmpdir
3593                do_pbi_create_backup
3594                exit_trap
3595        fi
3596
3597        load_pbi_conffile
3598
3599        parse_cmdline_overrides
3600
3601        # Copy over the application to the correct location
3602        echo ${PBI_PROGDIRPATH} | grep -q "^${PBI_APPDIR}/"
3603        if [ $? -ne 0 ] ; then
3604           _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
3605           newPDP="${PBI_APPDIR}/${_pbilow}-${ARCH}"
3606           if [ -d "${newPDP}" ] ; then exit_err "Error: ${newPDP} already exists!" ; fi       
3607           cp -r ${PBI_PROGDIRPATH} ${newPDP}
3608           PBI_PROGDIRPATH="${newPDP}"
3609           export PBI_PROGDIRPATH
3610        fi
3611
3612        PBI_CREATEONLY="YES"
3613
3614        check_create_required_vars
3615
3616        do_pbi_create
3617
3618        # Cleanup the copy dir
3619        if [ -n "$newPDP" ] ; then
3620                if [ "${newPDP}" != "/" -a "${newPDP}" != "${PBI_APPDIR}/-" ] ; then
3621                        rm -rf "${newPDP}"
3622                fi
3623        fi
3624}
3625
3626# Start the pbi_create backup process
3627do_pbi_create_backup() {
3628
3629        load_info_from_dir "${PBI_DBAPPDIR}/${PBI_CBACKUPTARGET}"
3630        echo "Creating backup PBI: ${PBI_PROGNAME}-${PBI_PROGVERSION}"
3631
3632        # Start by making a fresh archive of the installed PBI
3633        PBI_STAGEDIR="$PBI_ORIGPROGDIRPATH"
3634        mk_archive_file
3635
3636        # Now make the header dir
3637        _hDir="${PBI_TMPDIR}/.header.$$"
3638        PBI_HEADERDIR="${_hDir}"
3639        mkdir -p "${_hDir}"
3640        cp ${PBI_DBAPPDIR}/${PBI_CBACKUPTARGET}/* "${_hDir}"
3641        rm ${_hDir}/*.sha1 >/dev/null 2>/dev/null
3642
3643        # Get the total number of files in the STAGEDIR
3644        get_filetotal_dir "${PBI_STAGEDIR}"
3645        echo "${FILETOTAL}" > "${PBI_HEADERDIR}/pbi_archivecount"
3646
3647        # Save a checksum of archive file
3648        sha256 -q "${PBI_CREATE_ARCHIVE}" > "${PBI_HEADERDIR}/pbi_archivesum"
3649
3650        # Sign any header files
3651        sign_pbi_files "$PBI_HEADERDIR"
3652
3653        # Make the header archive
3654        mk_header_file
3655
3656        # Now finish up and make the resulting PBI file
3657        mk_output_pbi
3658
3659}
3660
3661
3662# Vars required for creation
3663check_create_required_vars() {
3664        if [ -z "${PBI_PROGNAME}" ] ; then exit_err "Missing PBI_PROGNAME"; fi
3665        if [ -z "${PBI_PROGVERSION}" ] ; then exit_err "Missing PBI_PROGVERSION"; fi
3666        if [ -z "${PBI_PROGAUTHOR}" ] ; then exit_err "Missing PBI_PROGAUTHOR"; fi
3667        if [ -z "${PBI_PROGWEB}" ] ; then exit_err "Missing PBI_PROGWEB"; fi
3668}
3669
3670# Start the pbi_create process
3671do_pbi_create() {
3672        get_pbi_progname
3673        echo "Creating PBI: ${PBI_PROGNAME}-${PBI_PROGVERSION}"
3674
3675
3676        if [ "`basename $0`" = "pbi_makeport" -o "`basename $0`" = "pbi_makeport_chroot" ] ; then
3677          #PBI_STAGEDIR="/usr/local"
3678          # KPM REMOVE ME
3679          mk_stage_dir "/usr/local" "move"
3680
3681          # Check if we created a linux app, and need to copy files for it
3682          auto_copy_linuxbase
3683        else
3684          mk_stage_dir
3685        fi
3686
3687        copy_resource_dir
3688        clean_stage_dir
3689
3690        mk_extlink_entries
3691        clean_icons_dir
3692        mk_xdg_scripts
3693
3694        run_pbi_prepkgscript
3695
3696        mk_install_script
3697        mk_deinstall_script
3698
3699        mk_hash_list
3700
3701        mk_archive_file
3702
3703        mk_header_dir
3704        save_pbi_details_to_header
3705        mk_header_file
3706
3707        mk_output_pbi
3708
3709        rm_stage_dir
3710        exit 0
3711}
3712
3713# Start looping through and creating a hash-list of files
3714mk_hash_list() {
3715        if [ "${PBI_CREATE_HASHLIST}" = "NO" ] ; then return 0 ; fi
3716        echo "Creating hash list..."
3717
3718        hashfile="${PBI_STAGEDIR}/${PBI_HASHLIST}"
3719
3720        if [ -e "${hashfile}" ] ; then rm "${hashfile}" ; fi
3721
3722        for hdir in ${HASH_SEARCH_DIRS}
3723        do
3724                if [ ! -d "${PBI_STAGEDIR}/${hdir}" ] ; then continue ; fi
3725                save_dir_hash_list "${hdir}" "${hashfile}"     
3726        done
3727}
3728
3729#  Read the specified directory and save hashsums of each file
3730save_dir_hash_list() {
3731        cd ${PBI_STAGEDIR}
3732        tmp_hashdir="${PBI_STAGEDIR}/.tmp-hash.$$"
3733        find "${1}" -type f > ${tmp_hashdir}
3734        while read line
3735        do
3736                if [ ! -f "$line" -o -h "$line" ] ; then continue ; fi
3737               
3738                # Check if this hash file is excluded
3739                _hfound="0"
3740                if [ -n "${PBI_HASH_EXCLUDES}" ] ; then
3741                        for _hexcl in ${PBI_HASH_EXCLUDES}
3742                        do
3743                                if [ "$_hexcl" = "$line" ] ; then
3744                                        _hfound="1"
3745                                fi
3746                        done
3747                        if [ "$_hfound" = "1" ] ; then
3748                                continue
3749                        fi
3750                fi     
3751
3752                # Add to the hash-dir
3753                sha=`sha256 -q "$line"`
3754                echo "${line}:::${sha}" >> ${2}
3755
3756        done < ${tmp_hashdir}
3757        rm ${tmp_hashdir}
3758        cd /
3759}
3760
3761# Parse any external link directives
3762mk_extlink_entries() {
3763        echo "Creating external link entries..."
3764        init_tmpdir
3765        _extf="${PBI_CONFDIR}/${MOD_EXTLINKFILE}"
3766        _autoextf="${PBI_TMPDIR}/${MOD_AUTOEXTLINKFILE}"
3767        _tmpextf="${PBI_TMPDIR}/${MOD_AUTOEXTLINKFILE}.$$"
3768        if [ ! -e "${_extf}" -a ! -e "${_autoextf}" ] ; then return 0 ; fi
3769
3770        dir="${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}"
3771        if [ ! -d "${dir}" ] ; then mkdir -p "${dir}" ; fi
3772
3773        # Create the headers for the PATH link scripts
3774        echo "#!/bin/sh" >"${dir}/${PBI_INS_PATHSCRIPT}"
3775        echo "#!/bin/sh" >"${dir}/${PBI_UNINS_PATHSCRIPT}"
3776
3777        # Make sure we also set SYS_LOCALBASE in case user runs these stand-alone at some point
3778        echo "if [ -z \"\$SYS_LOCALBASE\" ]; then SYS_LOCALBASE=\"${SYS_LOCALBASE}\" ; fi" >>"${dir}/${PBI_INS_PATHSCRIPT}"
3779        echo "if [ -z \"\$SYS_LOCALBASE\" ]; then SYS_LOCALBASE=\"${SYS_LOCALBASE}\" ; fi" >>"${dir}/${PBI_UNINS_PATHSCRIPT}"
3780        echo "if [ -z \"\$PBI_RCDIR\" ]; then PBI_RCDIR=\"${PBI_RCDIR}\" ; fi" >>"${dir}/${PBI_INS_PATHSCRIPT}"
3781        echo "if [ -z \"\$PBI_RCDIR\" ]; then PBI_RCDIR=\"${PBI_RCDIR}\" ; fi" >>"${dir}/${PBI_UNINS_PATHSCRIPT}"
3782        echo "if [ -z \"\$PBI_MANDIR\" ]; then PBI_MANDIR=\"${PBI_MANDIR}\" ; fi" >>"${dir}/${PBI_INS_PATHSCRIPT}"
3783        echo "if [ -z \"\$PBI_MANDIR\" ]; then PBI_MANDIR=\"${PBI_MANDIR}\" ; fi" >>"${dir}/${PBI_UNINS_PATHSCRIPT}"
3784        echo "if [ -z \"\$PBI_BINDIR\" ]; then PBI_BINDIR=\"${PBI_BINDIR}\" ; fi" >>"${dir}/${PBI_INS_PATHSCRIPT}"
3785        echo "if [ -z \"\$PBI_BINDIR\" ]; then PBI_BINDIR=\"${PBI_BINDIR}\" ; fi" >>"${dir}/${PBI_UNINS_PATHSCRIPT}"
3786
3787        touch "$_tmpextf"
3788        if [ -e "$_autoextf" ]; then cat "${_autoextf}" >> "${_tmpextf}" ; fi
3789        if [ -e "$_extf" ]; then cat "${_extf}" >> "${_tmpextf}" ; fi
3790
3791        while read line
3792        do
3793                _bin="NO"
3794                _wraponly="NO"
3795                _crashhandle="YES"
3796                _keep="YES"
3797                _linux="NO"
3798                echo $line | tr '\t' ' ' | tr -s ' ' | grep "^#" >/dev/null 2>/dev/null
3799                if [ "$?" != "0" ] ; then
3800                        src="`echo $line | tr '\t' ' ' | tr -s ' ' | cut -d ' ' -f 1`"
3801                        tar="`echo $line | tr '\t' ' ' | tr -s ' ' | cut -d ' ' -f 2`"
3802                        act="`echo $line | tr '\t' ' ' | tr -s ' ' | cut -d ' ' -f 3`"
3803
3804                        if [ -z "$src" -o -z "$tar" ] ; then continue ; fi
3805
3806                        # Check if this is an icon we need to preserve
3807                        echo $src | grep -q "^share/icons/"
3808                        if [ $? -eq 0 -a "${PBI_USESYSFONTS}" != "NO" ] ; then
3809                                iDir=`dirname $src`
3810                                if [ ! -d "${PBI_STAGEDIR}/${PBI_ICDIR}/${iDir}" ] ; then
3811                                        mkdir -p "${PBI_STAGEDIR}/${PBI_ICDIR}/${iDir}"
3812                                fi
3813                                cp "${PBI_STAGEDIR}/${src}" "${PBI_STAGEDIR}/${PBI_ICDIR}/${iDir}"
3814                                src="${PBI_ICDIR}/${src}"
3815                        fi
3816
3817                        if [ ! -e "${PBI_STAGEDIR}/$src" ] ; then
3818                                echo "WARN: external_link target: \"$src -> $tar $act\" does not exist!"
3819                                continue
3820                        fi
3821
3822                        # Check for act directives
3823                        for i in `echo ${act} | sed 's|,| |g'`
3824                        do
3825                                case ${i} in
3826                                        binary) _bin="YES" ;;
3827                                    binwrapper) _bin="YES" ; _wraponly="YES" ;;
3828                                       nocrash) _crashhandle="NO" ;;
3829                                          keep) _keep="YES" ;;
3830                                       replace) _keep="NO" ;;
3831                                         linux) _bin="YES" ; _linux="YES" ;;
3832                                        *) echo "Warning: Unknown option \"$i\" in ${MOD_EXTLINKFILE}";;
3833                                esac
3834                               
3835                        done
3836
3837
3838                        # If we are doing a binary, run special function to make wrapper
3839                        if [ "$_bin" = "YES" ] ; then
3840
3841                                # Make sure we don't create any duplicates
3842                                echo "$_donewrap" | grep "#${src}#" >/dev/null 2>/dev/null
3843                                if [ "$?" = "0" ] ; then continue ; fi
3844                               
3845                                # Make the binary wrapper
3846                                mk_path_wrappers "$src" "$tar" "$_crashhandle" "$_wraponly" "$_linux"
3847
3848                                # This binary is done, save it now so we don't duplicate later
3849                                _donewrap="$_donewrap #${src}#"
3850                        else
3851                                # Make our link commands
3852                                if [ "$_keep" = "YES" ] ; then _lop="-fs"; else _lop="-s"; fi
3853                                echo $tar | grep -q "^man/"
3854                                if [ $? -eq 0 ] ; then
3855                                        # Strip off the man/ path
3856                                        _mTar=`echo $tar | sed 's|^man/||g'`
3857                                        _dTar="\$PBI_MANDIR/${_mTar}"
3858                                        echo "_bd=\"\`dirname ${_dTar}\`\"" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3859                                        echo "if [ ! -d \"\$_bd\" ] ; then mkdir -p \"\${_bd}\"; fi" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3860                                        echo "ln ${_lop} $PBI_PROGDIRPATH/local/${src} \$PBI_MANDIR/${_mTar}" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3861                                else
3862                                        _dTar="\$SYS_LOCALBASE/${tar}"
3863                                        echo "_bd=\"\`dirname ${_dTar}\`\"" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3864                                        echo "if [ ! -d \"\$_bd\" ] ; then mkdir -p \"\${_bd}\"; fi" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3865                                        echo "ln ${_lop} $PBI_PROGDIRPATH/local/${src} \$SYS_LOCALBASE/${tar}" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3866
3867                                fi
3868                        fi
3869
3870                        # Make the uninstall command
3871                        echo "ls -al \"${_dTar}\" | grep \"> $PBI_PROGDIRPATH\" >/dev/null 2>/dev/null " \
3872                                >> "${dir}/${PBI_UNINS_PATHSCRIPT}"
3873                        echo "if [ \"\$?\" = \"0\" ] ; then" >> "${dir}/${PBI_UNINS_PATHSCRIPT}"
3874                        echo "  rm \"${_dTar}\"" >> "${dir}/${PBI_UNINS_PATHSCRIPT}"
3875                        echo "fi" >> "${dir}/${PBI_UNINS_PATHSCRIPT}"
3876
3877                        echo " " >> "${dir}/${PBI_INS_PATHSCRIPT}"
3878                        echo " " >> "${dir}/${PBI_UNINS_PATHSCRIPT}"
3879
3880                fi
3881
3882        done < "${_tmpextf}"
3883        rm "${_tmpextf}"
3884
3885        chmod 755 "${dir}/${PBI_INS_PATHSCRIPT}"
3886        chmod 755 "${dir}/${PBI_UNINS_PATHSCRIPT}"
3887}
3888
3889
3890# Create the wrapper scripts for the specified binaries
3891mk_path_wrappers() {
3892        dir="${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}"
3893        rcdir="${PBI_STAGEDIRMNT}/${PBI_FAKERC_DIR}"
3894        if [ ! -d "${dir}" ] ; then mkdir -p "${dir}" ; fi
3895
3896        bin="${1}"
3897        fbin="`basename ${bin}`"
3898        tar="${2}"
3899        ch="${3}"
3900        onlywrap="${4}"
3901        linwrap="${5}"
3902
3903        # Check if the fake-bin wrapper already exists, and if so use
3904        # a different name
3905        if [ -e "${dir}/${fbin}" ] ; then
3906                fbin=`echo $bin | sed 's|/|-|g'`
3907        fi
3908
3909        # If this is an rc.d script, add it to the PBI_RCDIR
3910        if [ "`dirname $tar`" = "etc/rc.d" ] ; then
3911                        >> "${dir}/${PBI_INS_PATHSCRIPT}"
3912                _dTar="\$PBI_RCDIR/`basename ${tar}`"
3913                echo "_bd=\"\`dirname ${_dTar}\`\"" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3914                echo "if [ ! -d \"\$_bd\" ] ; then mkdir -p \"\${_bd}\"; fi" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3915                echo "ln -fs $PBI_PROGDIRPATH/${PBI_FAKERC_DIR}/${fbin} \$PBI_RCDIR/`basename ${tar}`" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3916
3917                # Copy the wrapper binary
3918                PBI_WRAPPERFILE="/.pbiwrapper-$ARCH"
3919                cp ${PBI_WRAPPERFILE} ${rcdir}/${fbin}
3920                chmod 755 ${rcdir}/${fbin}
3921
3922                # Create the wrapper .pbiopt
3923                echo "PROGDIR: ${PBI_PROGDIRPATH}" >${rcdir}/${fbin}.pbiopt
3924                echo "TARGET: ${bin}" >>${rcdir}/${fbin}.pbiopt
3925                return
3926        fi
3927
3928        # Make our link to the system localbase if its not a wrapper only
3929        if [ "$onlywrap" != "YES" ] ; then     
3930                _mTar=`echo $tar | sed "s|^bin/||g" | sed "s|^sbin/||g"`
3931                _dTar="\$PBI_BINDIR/${_mTar}"
3932
3933                        >> "${dir}/${PBI_INS_PATHSCRIPT}"
3934                echo "_bd=\"\`dirname ${_dTar}\`\"" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3935                echo "if [ ! -d \"\$_bd\" ] ; then mkdir -p \"\${_bd}\"; fi" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3936                echo "ln -fs $PBI_PROGDIRPATH/${PBI_FAKEBIN_DIR}/${fbin} \$PBI_BINDIR/${_mTar}" >> "${dir}/${PBI_INS_PATHSCRIPT}"
3937        fi
3938
3939
3940        # Copy the wrapper binary
3941        PBI_WRAPPERFILE="/.pbiwrapper-$ARCH"
3942        cp ${PBI_WRAPPERFILE} ${dir}/${fbin}
3943        chmod 755 ${dir}/${fbin}
3944
3945        # Create the wrapper .pbiopt
3946        echo "PROGDIR: ${PBI_PROGDIRPATH}" >${dir}/${fbin}.pbiopt
3947        echo "TARGET: ${bin}" >>${dir}/${fbin}.pbiopt
3948}
3949
3950# Create any XDG script for install / deinstall
3951mk_xdg_scripts() {
3952        echo "Creating xdg scripts..."
3953        mk_xdg_desktop_script
3954        mk_xdg_menu_script
3955        mk_xdg_mime_script
3956}
3957
3958# Create any XDG script for desktop icons
3959mk_xdg_desktop_script() {
3960        if [ ! -d "${PBI_CONFDIR}/${MOD_XDGDESK_DIR}" ] ; then return 0 ; fi
3961        _dFound=0
3962
3963        dir="${PBI_STAGEDIR}/${PBI_APPDESK_DIR}"
3964        if [ ! -d "${dir}" ] ; then mkdir -p "${dir}" ; fi
3965        echo "#!/bin/sh" >"${dir}/${PBI_INS_DESKSCRIPT}"
3966        echo "#!/bin/sh" >"${dir}/${PBI_UNINS_DESKSCRIPT}"
3967
3968        cd "${PBI_CONFDIR}/${MOD_XDGDESK_DIR}"
3969        for i in `ls *.desktop 2>/dev/null`
3970        do
3971                _dFound=1
3972
3973                # Copy over the .desktop file, modifying any variables within
3974                cat "${i}" \
3975                | sed "s|%%PBI_EXEDIR%%|$PBI_PROGDIRPATH/$PBI_FAKEBIN_DIR|g" \
3976                | sed "s|%%PBI_APPDIR%%|$PBI_PROGDIRPATH|g" \
3977                > "${dir}/PBI-${i}"
3978
3979                # Set the correct permissions on the desktop file
3980                chmod 744 "${dir}/PBI-${i}"
3981
3982                ifi="$PBI_PROGDIRPATH/${PBI_APPDESK_DIR}/PBI-${i}"
3983
3984                echo "xdg-desktop-icon install --novendor ${ifi}" \
3985                         >> "${dir}/${PBI_INS_DESKSCRIPT}"
3986                echo "xdg-desktop-icon uninstall ${ifi}" \
3987                         >> "${dir}/${PBI_UNINS_DESKSCRIPT}"
3988               
3989        done
3990
3991        chmod 755 "${dir}/${PBI_INS_DESKSCRIPT}"
3992        chmod 755 "${dir}/${PBI_UNINS_DESKSCRIPT}"
3993
3994        # No desktop entries
3995        if [ "$_dFound" = "0" ] ; then
3996                rm "${dir}/${PBI_INS_DESKSCRIPT}"
3997                rm "${dir}/${PBI_UNINS_DESKSCRIPT}"
3998        fi
3999}
4000
4001# Create any XDG script for menu icons
4002mk_xdg_menu_script() {
4003        if [ ! -d "${PBI_CONFDIR}/${MOD_XDGMENU_DIR}" ] ; then return 0 ; fi
4004
4005        _mFound=0
4006
4007        dir="${PBI_STAGEDIR}/${PBI_APPMENU_DIR}"
4008        if [ ! -d "${dir}" ] ; then mkdir -p "${dir}" ; fi
4009        echo "#!/bin/sh" >"${dir}/${PBI_INS_MENUSCRIPT}"
4010        echo "#!/bin/sh" >"${dir}/${PBI_UNINS_MENUSCRIPT}"
4011
4012        cd "${PBI_CONFDIR}/${MOD_XDGMENU_DIR}"
4013        for i in `ls *.desktop 2>/dev/null`
4014        do
4015                _mFound=1
4016
4017                # Copy the desktop file, changing any included vars
4018                cat "${i}" \
4019                | sed "s|%%PBI_EXEDIR%%|$PBI_PROGDIRPATH/$PBI_FAKEBIN_DIR|g" \
4020                | sed "s|%%PBI_APPDIR%%|$PBI_PROGDIRPATH|g" \
4021                > "${dir}/PBI-${i}"
4022
4023                # Set the correct permissions on the menu file
4024                chmod 744 "${dir}/PBI-${i}"
4025
4026                ifi="$PBI_PROGDIRPATH/${PBI_APPMENU_DIR}/PBI-${i}"
4027
4028                # Check for a .directory file associated with this .desktop
4029                ifd=""
4030                dirfile="`basename -s .desktop ${i}`"
4031                if [ -e "${dirfile}.directory" ] ; then
4032                        cat "${dirfile}.directory" \
4033                        | sed "s|%%PBI_EXEDIR%%|$PBI_PROGDIRPATH/$PBI_FAKEBIN_DIR|g" \
4034                        | sed "s|%%PBI_APPDIR%%|$PBI_PROGDIRPATH|g" \
4035                        > "${dir}/PBI-${dirfile}.directory"
4036                        #cp "${dirfile}.directory" "${dir}/PBI-${dirfile}.directory"
4037                        ifd="$PBI_PROGDIRPATH/${PBI_APPMENU_DIR}/PBI-${dirfile}.directory "     
4038                fi
4039
4040                echo "xdg-desktop-menu install --novendor ${ifd}${ifi}" \
4041                         >> "${dir}/${PBI_INS_MENUSCRIPT}"
4042                echo "xdg-desktop-menu uninstall ${ifd}${ifi}" \
4043                         >> "${dir}/${PBI_UNINS_MENUSCRIPT}"
4044
4045        done
4046
4047        chmod 755 "${dir}/${PBI_INS_MENUSCRIPT}"
4048        chmod 755 "${dir}/${PBI_UNINS_MENUSCRIPT}"
4049
4050        # No mime entries
4051        if [ "$_mFound" = "0" ] ; then
4052                rm "${dir}/${PBI_INS_MENUSCRIPT}"
4053                rm "${dir}/${PBI_UNINS_MENUSCRIPT}"
4054        fi
4055}
4056
4057# Create any XDG script for mime types
4058mk_xdg_mime_script() {
4059        if [ ! -d "${PBI_CONFDIR}/${MOD_XDGMIME_DIR}" ] ; then return 0 ; fi
4060        _mFound=0
4061
4062        dir="${PBI_STAGEDIR}/${PBI_APPMIME_DIR}"
4063        if [ ! -d "${dir}" ] ; then mkdir -p "${dir}" ; fi
4064        echo "#!/bin/sh" >"${dir}/${PBI_INS_MIMESCRIPT}"
4065        echo "#!/bin/sh" >"${dir}/${PBI_UNINS_MIMESCRIPT}"
4066
4067
4068        cd "${PBI_CONFDIR}/${MOD_XDGMIME_DIR}"
4069        for i in `ls *.xml 2>/dev/null`
4070        do
4071                _mFound=1
4072                cp "${i}" "${dir}/PBI-${i}"
4073                ifi="$PBI_PROGDIRPATH/${PBI_APPMIME_DIR}/PBI-${i}"
4074
4075                # Check for a .directory file associated with this .desktop
4076                ifp=""
4077                iconfile="`basename -s .xml ${i}`"
4078                if [ -e "${iconfile}.png" ] ; then
4079                        cp "${iconfile}.png" "${dir}/${iconfile}.png"
4080                        ifp="$PBI_PROGDIRPATH/${PBI_APPMIME_DIR}/${iconfile}.png"
4081                        mi=`cat "$i" | grep '<mime-type' | cut -d '"' -f 2 | sed 's|/|-|g'`
4082                        echo "xdg-icon-resource install --novendor --context mimetypes ${ifp} --size 64 $mi" \
4083                                 >> "${dir}/${PBI_INS_MIMESCRIPT}"
4084                        echo "xdg-icon-resource uninstall --context mimetypes ${ifp} --size 64" \
4085                                 >> "${dir}/${PBI_UNINS_MIMESCRIPT}"
4086                fi
4087
4088                echo "xdg-mime install --novendor ${ifi}" \
4089                         >> "${dir}/${PBI_INS_MIMESCRIPT}"
4090                echo "xdg-mime uninstall ${ifi}" \
4091                         >> "${dir}/${PBI_UNINS_MIMESCRIPT}"
4092        done
4093
4094        chmod 755 "${dir}/${PBI_INS_MIMESCRIPT}"
4095        chmod 755 "${dir}/${PBI_UNINS_MIMESCRIPT}"
4096
4097        # No mime entries
4098        if [ "$_mFound" = "0" ] ; then
4099                rm "${dir}/${PBI_INS_MIMESCRIPT}"
4100                rm "${dir}/${PBI_UNINS_MIMESCRIPT}"
4101        fi
4102}
4103
4104
4105# Create the install script for the PBI
4106mk_install_script() {
4107        echo "Creating install script..."
4108        if [ ! -d "${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}" ] ; then mkdir -p "${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}" ; fi
4109        if [ ! -d "${PBI_STAGEDIRMNT}/${PBI_FAKERC_DIR}" ] ; then mkdir -p "${PBI_STAGEDIRMNT}/${PBI_FAKERC_DIR}" ; fi
4110        insc="${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}/.pbi-install.sh"
4111        echo "#!/bin/sh" > "$insc"
4112        echo "PBI_WRAPPERBIN=\"${PBI_FAKEBIN_DIR}\"" >> "$insc"
4113        echo "PBI_PROGDIRPATH=\"${PBI_PROGDIRPATH}\"" >> "$insc"
4114        echo "SYS_LOCALBASE=\"${SYS_LOCALBASE}\"" >> "$insc"
4115        echo "cd \"\$PBI_PROGDIRPATH\"" >> "$insc"
4116
4117        # Add the binary wrapper sym-links
4118        if [ -e "${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}/${PBI_INS_PATHSCRIPT}" ] ; then
4119                echo 'if [ `id -u` = "0" ] ; then ' >>${insc}
4120                echo "  $PBI_PROGDIRPATH/${PBI_FAKEBIN_DIR}/${PBI_INS_PATHSCRIPT}" >>${insc}
4121                echo "fi" >>${insc}
4122        fi
4123
4124        # Look for any XDG scripts
4125        if [ -e "${PBI_STAGEDIR}/${PBI_APPMIME_DIR}/${PBI_INS_MIMESCRIPT}" ] ; then
4126                echo "$PBI_PROGDIRPATH/${PBI_APPMIME_DIR}/${PBI_INS_MIMESCRIPT}" >>${insc}
4127        fi
4128        if [ -e "${PBI_STAGEDIR}/${PBI_APPMENU_DIR}/${PBI_INS_MENUSCRIPT}" ] ; then
4129                echo "$PBI_PROGDIRPATH/${PBI_APPMENU_DIR}/${PBI_INS_MENUSCRIPT}" >>${insc}
4130        fi
4131
4132        chmod 755 "${insc}"
4133       
4134}
4135
4136# Create the deinstall script for the PBI
4137mk_deinstall_script() {
4138        echo "Creating deinstall script..."
4139        uisc="${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}/.pbi-uninstall.sh"
4140
4141        echo "#!/bin/sh" > "$uisc"
4142        echo "PBI_PROGDIRPATH=\"${PBI_PROGDIRPATH}\"" >> "$uisc"
4143        echo "SYS_LOCALBASE=\"${SYS_LOCALBASE}\"" >> "$uisc"
4144
4145        # Remove the binary wrapper sym-links
4146        if [ -e "${PBI_STAGEDIRMNT}/${PBI_FAKEBIN_DIR}/${PBI_UNINS_PATHSCRIPT}" ] ; then
4147                echo 'if [ `id -u` = "0" ] ; then ' >>${uisc}
4148                echo "  $PBI_PROGDIRPATH/${PBI_FAKEBIN_DIR}/${PBI_UNINS_PATHSCRIPT}" >>${uisc}
4149                echo "fi" >>${uisc}
4150        fi
4151
4152        # Look for any XDG scripts
4153        if [ -e "${PBI_STAGEDIR}/${PBI_APPMIME_DIR}/${PBI_UNINS_MIMESCRIPT}" ] ; then
4154                echo "$PBI_PROGDIRPATH/${PBI_APPMIME_DIR}/${PBI_UNINS_MIMESCRIPT}" >>${uisc}
4155        fi
4156        if [ -e "${PBI_STAGEDIR}/${PBI_APPMENU_DIR}/${PBI_UNINS_MENUSCRIPT}" ] ; then
4157                echo "$PBI_PROGDIRPATH/${PBI_APPMENU_DIR}/${PBI_UNINS_MENUSCRIPT}" >>${uisc}
4158        fi
4159        chmod 755 "${uisc}"
4160}
4161
4162# Create a dir for manipulating header info
4163mk_header_dir() {
4164        PBI_HEADERDIR="${PBI_STAGEDIRMNT}/pbimeta"
4165        if [ -e "${PBI_HEADERDIR}" ] ; then rm -rf "${PBI_HEADERDIR}" ; fi
4166        mkdir -p ${PBI_HEADERDIR}
4167}
4168
4169# Create a dir for staging the final archive
4170mk_stage_dir() {
4171        if [ -n "$1" ] ; then
4172                cpDir="$1"
4173        else
4174                cpDir="${PBI_PROGDIRPATH}"
4175        fi
4176
4177        PBI_STAGEDIR="${PBI_PROGDIRPATH}/.stagedir"
4178        echo "Creating Stage Dir: ${PBI_STAGEDIR}"
4179        if [ -e "${PBI_STAGEDIR}" ] ; then
4180                rm -rf "${PBI_STAGEDIR}" 2>/dev/null
4181                chflags -R noschg ${PBI_STAGEDIR} 2>/dev/null
4182                rm -rf "${PBI_STAGEDIR}" 2>/dev/null
4183        fi
4184        mkdir -p ${PBI_STAGEDIR}
4185
4186        mkdir -p ${PBI_STAGEDIR}/local
4187        mkdir -p ${PBI_STAGEDIR}/etc
4188        mkdir -p ${PBI_STAGEDIR}/rc.d
4189        mkdir -p ${PBI_STAGEDIR}/pbimeta
4190        mkdir -p ${PBI_STAGEDIR}/virtbase
4191        mkdir -p ${PBI_STAGEDIR}/linux
4192        mkdir -p ${PBI_STAGEDIR}/run
4193
4194        # If we built with a module / conf directory, lets include it
4195        if [ -d "${PBI_CONFDIR}" ] ; then cp -r ${PBI_CONFDIR} ${PBI_STAGEDIR}/pbiconf; fi
4196
4197        local _excOpts=""
4198
4199        # Build module list of excludes
4200        if [ -n "$PBI_EXCLUDELIST" ] ; then
4201                for excl in $PBI_EXCLUDELIST
4202                do
4203                        if [ -z "$_excOpts" ] ; then
4204                                _excOpts="--exclude ${excl}"
4205                        else
4206                                _excOpts="$_excOpts --exclude ${excl}"
4207                        fi
4208                done
4209        fi
4210
4211        if [ "$2" = "move" ] ; then
4212                rmdir ${PBI_STAGEDIR}/local
4213                mv ${cpDir} ${PBI_STAGEDIR}/local
4214                ln -s ${PBI_STAGEDIR}/local /usr/local
4215        else
4216                # Now copy the stagedir
4217                tar cvf - ${_excOpts} --exclude .stagedir \
4218                --exclude .pkgdb --exclude .ld-elf.hints --exclude make.conf \
4219                --exclude make.conf.bak --exclude .keepports \
4220                -C "${cpDir}" . 2>/dev/null \
4221                | tar xvpf - -C ${PBI_STAGEDIR}/local 2>/dev/null
4222        fi
4223
4224        cd ${PBI_PROGDIRPATH}
4225        PBI_STAGEDIRMNT="${PBI_STAGEDIR}"
4226        PBI_STAGEDIR="${PBI_STAGEDIR}/local"
4227}
4228
4229# Remove the stagedir
4230rm_stage_dir() {
4231        # If this is in the chroot we can exit and let the parent cleanup
4232        if [ "$0" = "pbi_makeport_chroot" ] ; then return; fi
4233
4234        cd /
4235        PBI_STAGEDIR="${PBI_PROGDIRPATH}/.stagedir"
4236        if [ -e "${PBI_STAGEDIR}" ] ; then
4237                rm -rf "${PBI_STAGEDIR}" 2>/dev/null
4238                chflags -R noschg ${PBI_STAGEDIR} 2>/dev/null
4239                rm -rf "${PBI_STAGEDIR}" 2>/dev/null
4240        fi
4241}
4242
4243# See if we need to clean the icons dir
4244clean_icons_dir() {
4245        if [ "${PBI_USESYSFONTS}" != "NO" ] ; then
4246                rm -rf ${PBI_STAGEDIR}/share/icons >/dev/null 2>/dev/null
4247                mkdir ${PBI_STAGEDIR}/share/icons >/dev/null 2>/dev/null
4248        fi
4249}
4250
4251# See if we need to clean the stagedir
4252clean_stage_dir() {
4253
4254        if [ "${PBI_USESYSGL}" != "NO" ] ; then
4255                rm ${PBI_STAGEDIR}/lib/libGl.* >/dev/null 2>/dev/null
4256                rm ${PBI_STAGEDIR}/lib/libGL.* >/dev/null 2>/dev/null
4257                rm ${PBI_STAGEDIR}/lib/libGLU.* >/dev/null 2>/dev/null
4258        fi
4259        if [ "${PBI_USESYSFONTS}" != "NO" ] ; then
4260                rm -rf ${PBI_STAGEDIR}/etc/fonts/* >/dev/null 2>/dev/null
4261                rm -rf ${PBI_STAGEDIR}/lib/X11/fonts/* >/dev/null 2>/dev/null
4262                rm -rf ${PBI_STAGEDIR}/lib/X11/icons/* >/dev/null 2>/dev/null
4263        fi
4264        if [ -e "${PBI_STAGEDIR}/lib/X11" ] ; then
4265                mkdir -p ${PBI_STAGEDIR}/lib/X11/icons/ >/dev/null 2>/dev/null
4266                mkdir -p ${PBI_STAGEDIR}/lib/X11/fonts/ >/dev/null 2>/dev/null
4267                mkdir -p ${PBI_STAGEDIR}/etc/fonts/ >/dev/null 2>/dev/null
4268        fi
4269}
4270
4271# Copy over any resource files into the PBI dir
4272copy_resource_dir() {
4273        if [ -d "${PBI_CONFDIR}/${PBI_RESOURCE_DIR}" ] ; then
4274                echo "Copying ${PBI_CONFDIR}/${PBI_RESOURCE_DIR} -> ${PBI_STAGEDIR}"
4275                tar cvf - -C ${PBI_CONFDIR}/${PBI_RESOURCE_DIR} --exclude .svn . 2>/dev/null \
4276                | tar xvpf - -C ${PBI_STAGEDIR} 2>/dev/null
4277        fi
4278}
4279
4280# Check if tar supports lzma compression
4281test_tar_lzma() {
4282        touch /tmp/.pbilzma.$$ >/dev/null 2>/dev/null
4283        tar cvJf /tmp/.pbilzma.tar.$$ /tmp/.pbilzma.$$ >/dev/null 2>/dev/null
4284        _exitcode=$?
4285        rm /tmp/.pbilzma.$$ >/dev/null 2>/dev/null
4286        rm /tmp/.pbilzma.tar.$$ >/dev/null 2>/dev/null
4287        return $_exitcode
4288}
4289
4290# Start creating the application archive
4291mk_archive_file() {
4292        # Build module list of excludes
4293        if [ -n "$PBI_EXCLUDELIST" ] ; then
4294                for excl in $PBI_EXCLUDELIST
4295                do
4296                        if [ -z "$_excOpts" ] ; then
4297                                _excOpts="--exclude ${excl}"
4298                        else
4299                                _excOpts="$_excOpts --exclude ${excl}"
4300                        fi
4301                done
4302        fi
4303        PBI_CREATE_ARCHIVE="${PBI_CREATE_OUTDIR}/.PBI.$$.tbz"
4304        if test_tar_lzma ; then _tcmp="J" ; else _tcmp="j" ; fi
4305        echo "Creating compressed archive..."
4306        tar cv${_tcmp}f "${PBI_CREATE_ARCHIVE}" ${_excOpts} -C ${PBI_STAGEDIRMNT} . 2>/dev/null
4307}
4308
4309# Start creating the header archive
4310mk_header_file() {
4311        PBI_HEADER_ARCHIVE="${PBI_CREATE_OUTDIR}/.PBI-header.$$.tbz"
4312        tar cvjf ${PBI_HEADER_ARCHIVE} -C ${PBI_HEADERDIR} . >/dev/null 2>/dev/null
4313}
4314
4315# Start copying pbi details into header file
4316save_pbi_details_to_header() {
4317        local _osArch="$ARCH"
4318        local _osRel="$FBSDREL"
4319        if [ -n "${PBI_OSREL}" ] ; then
4320                _osRel="${PBI_OSREL}"
4321        fi
4322
4323        if [ "${PBI_CREATEONLY}" = "YES" ] ; then
4324                _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
4325                echo "${PBI_APPDIR}/${_pbilow}-${_osArch}" > "${PBI_HEADERDIR}/pbi_defaultpath"
4326        else   
4327                echo "${PBI_PROGDIRPATH}" > "${PBI_HEADERDIR}/pbi_defaultpath"
4328        fi
4329        echo "${PBI_PROGNAME}" > "${PBI_HEADERDIR}/pbi_name"
4330        echo "${PBI_PROGVERSION}" > "${PBI_HEADERDIR}/pbi_version"
4331        echo "${PBI_PROGAUTHOR}" > "${PBI_HEADERDIR}/pbi_author"
4332        echo "${PBI_PROGWEB}" > "${PBI_HEADERDIR}/pbi_web"
4333        date "+%Y%m%d %H%M%S" > "${PBI_HEADERDIR}/pbi_mdate"
4334
4335        if [ "${PBI_REQUIRESROOT}" = "YES" ] ; then
4336                touch ${PBI_HEADERDIR}/pbi_requiresroot
4337        fi
4338
4339        # Do we have a license to accept?
4340        if [ -e "${PBI_CONFDIR}/${PBI_LICENSEFILE}" ] ; then
4341                cp "${PBI_CONFDIR}/${PBI_LICENSEFILE}" "${PBI_HEADERDIR}/${PBI_LICENSEFILE}"
4342        fi
4343
4344        # Do we have a conf-supplied meta-file to copy?
4345        if [ -e "${PBI_CONFDIR}/${PBI_USERMETAFILE}" ] ; then
4346                cp "${PBI_CONFDIR}/${PBI_USERMETAFILE}" "${PBI_HEADERDIR}/${PBI_USERMETAFILE}"
4347        fi
4348        # Do we have a user-supplied meta-file to copy?
4349        if [ -n "$PBI_CREATE_USERMETA" ] ; then
4350                cp "$PBI_CREATE_USERMETA" "${PBI_HEADERDIR}/${PBI_USERMETAFILE}"
4351        fi
4352
4353        # Check for additional meta-data
4354        if [ -n "$PBI_LICENSE" ] ; then
4355                echo "$PBI_LICENSE" > ${PBI_HEADERDIR}/pbi_license
4356        fi
4357        if [ -n "$PBI_TAGS" ] ; then
4358                echo "$PBI_TAGS" > ${PBI_HEADERDIR}/pbi_tags
4359        fi
4360        if [ -n "$PBI_PROGTYPE" ] ; then
4361                echo "$PBI_PROGTYPE" > ${PBI_HEADERDIR}/pbi_type
4362        fi
4363        if [ -n "$PBI_CATEGORY" ] ; then
4364                echo "$PBI_CATEGORY" > ${PBI_HEADERDIR}/pbi_category
4365        fi
4366        if [ -n "$PBI_ICONURL" ] ; then
4367                echo "$PBI_ICONURL" > ${PBI_HEADERDIR}/pbi_iconurl
4368        fi
4369        if [ -n "$PBI_DESC" ] ; then
4370                echo "$PBI_DESC" > ${PBI_HEADERDIR}/pbi_desc
4371        fi
4372        if [ -n "$PBI_SHORTDESC" ] ; then
4373                echo "$PBI_SHORTDESC" > ${PBI_HEADERDIR}/pbi_shortdesc
4374        fi
4375
4376        # Custom install / remove scripts
4377        if [ -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_PREINS}" ] ; then
4378                cp "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_PREINS}" \
4379                        "${PBI_HEADERDIR}/${MOD_PREINS}"
4380        else
4381                echo "#!/bin/sh" > ${PBI_HEADERDIR}/${MOD_PREINS}
4382        fi
4383        if [ -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_POSTINS}" ] ; then
4384                cp "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_POSTINS}" \
4385                        "${PBI_HEADERDIR}/${MOD_POSTINS}"
4386        else
4387                echo "#!/bin/sh" > ${PBI_HEADERDIR}/${MOD_POSTINS}
4388        fi
4389        if [ -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_PREREM}" ] ; then
4390                cp "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/${MOD_PREREM}" \
4391                        "${PBI_HEADERDIR}/${MOD_PREREM}"
4392        else
4393                echo "#!/bin/sh" > ${PBI_HEADERDIR}/${MOD_PREREM}
4394        fi
4395
4396        # Copy over our icon
4397        if [ -n "${PBI_PROGICON}" -a -e "${PBI_STAGEDIR}/${PBI_PROGICON}" ] ; then
4398                # Get the file extension
4399                _iconExt=`echo "$PBI_PROGICON" | awk -F . '{print $NF}'`
4400                cp "${PBI_STAGEDIR}/${PBI_PROGICON}" "${PBI_HEADERDIR}/pbi_icon.${_iconExt}" >/dev/null 2>/dev/null
4401        else
4402                _iconExt=`echo "$PBI_DEFAULT_ICON_CHROOT" | awk -F . '{print $NF}'`
4403                cp "${PBI_DEFAULT_ICON_CHROOT}" "${PBI_HEADERDIR}/pbi_icon.${_iconExt}" >/dev/null 2>/dev/null
4404        fi
4405
4406        # Check for any gui images
4407        if [ -e "${PBI_STAGEDIR}/${PBI_GUITOPBANNER}" ] ; then
4408                cp "${PBI_STAGEDIR}/${PBI_GUITOPBANNER}" "${PBI_HEADERDIR}/top-banner.png"
4409        fi
4410        if [ -e "${PBI_STAGEDIR}/${PBI_GUISIDEBANNER}" ] ; then
4411                cp "${PBI_STAGEDIR}/${PBI_GUISIDEBANNER}" "${PBI_HEADERDIR}/side-banner.png"
4412        fi
4413
4414        # Save the uname details
4415        echo "${_osArch}" > "${PBI_HEADERDIR}/pbi_arch"
4416        echo "${_osRel}" > "${PBI_HEADERDIR}/pbi_fbsdver"
4417        echo "${PROGVERSION}" > "${PBI_HEADERDIR}/pbi_createver"
4418
4419        # Get the total number of files in the STAGEDIR
4420        get_filetotal_dir "${PBI_STAGEDIR}"
4421        echo "${FILETOTAL}" > "${PBI_HEADERDIR}/pbi_archivecount"
4422
4423        # Save a checksum of archive file
4424        sha256 -q "${PBI_CREATE_ARCHIVE}" > "${PBI_HEADERDIR}/pbi_archivesum"
4425
4426        sign_pbi_files "$PBI_HEADERDIR"
4427}
4428
4429# Use openssl to sign parts of the pbi header structure and archive
4430sign_pbi_files() {
4431        if [ -z "${PBI_SSLPRIVKEY}" ] ; then return 0 ; fi
4432        _sf="${1}/pbi_archivesum ${1}/${MOD_PREINS} ${1}/${MOD_POSTINS} ${1}/${MOD_PREREM}"
4433        for i in $_sf
4434        do
4435                openssl dgst -sha1 \
4436                        -sign ${PBI_SSLPRIVKEY} \
4437                        -out ${i}.sha1 \
4438                        ${i} >/dev/null 2>/dev/null
4439        done
4440}
4441
4442# All the pieces are ready, spit out the final PBI file
4443mk_output_pbi() {
4444        if [ -n "${PBI_PROGICON}" -a -e "${PBI_STAGEDIR}/${PBI_PROGICON}" ] ; then
4445                icon="${PBI_STAGEDIR}/${PBI_PROGICON}"
4446        else
4447                icon="${PBI_DEFAULT_ICON_CHROOT}"
4448        fi
4449
4450        # Set PBI name all lower-case
4451        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
4452        outfile="${PBI_CREATE_OUTDIR}/${_pbilow}-${PBI_PROGVERSION}-${ARCH}.pbi"
4453
4454        mark1="${PBI_CREATE_OUTDIR}/.pbimark1.$$"
4455        mark2="${PBI_CREATE_OUTDIR}/.pbimark2.$$"
4456        echo "
4457${PBI_SS_ICON}" >$mark1
4458        echo "
4459${PBI_SS_ARCHIVE}" >$mark2
4460
4461
4462        # DO IT, DO IT NOW!!!
4463        cat ${PBI_HEADER_ARCHIVE} $mark1 ${icon} $mark2 ${PBI_CREATE_ARCHIVE} > ${outfile}
4464        sha256 -q ${outfile} > ${outfile}.sha256
4465
4466        echo "Created PBI: ${outfile}"
4467
4468        rm $mark1
4469        rm $mark2
4470        rm ${PBI_HEADER_ARCHIVE}
4471        rm ${PBI_CREATE_ARCHIVE}
4472}
4473
4474get_filetotal_dir() {
4475        FILETOTAL="`find ${1} | wc -l | tr -d ' '`"
4476}
4477
4478pbi_delete_init() {
4479        require_root_or_group
4480        init_tmpdir
4481        parse_delete_pbi_cmdline "$@"
4482        do_pbi_delete
4483}
4484
4485# Delete this PBI
4486do_pbi_delete() {
4487        load_info_from_dir "${PBI_DBAPPDIR}/${PBI_DELETENAME}"
4488        PBI_PROGDIRPATH="${PBI_ORIGPROGDIRPATH}"
4489
4490        # Unmount the PBI if its mounted
4491        /usr/pbi/.pbime umount "/usr/pbi/.mounts/`basename $PBI_PROGDIRPATH`"
4492
4493        get_username_from_file "${PBI_DBAPPDIR}/${PBI_DELETENAME}/pbi_name"
4494        if [ "$FILEUSER" != `whoami` -a `id -u` != "0" ] ; then
4495                exit_err "Permission denied to modify PBI installed by: $FILEUSER"
4496        fi
4497
4498        # Set the dirty flag that we are removing this PBI
4499        touch ${PBI_DBAPPDIR}/${PBI_DELETENAME}/.pbiDeleted
4500
4501        check_preremove_script
4502        run_remove_script
4503        remove_pbidir
4504        unregister_pbi
4505       
4506        # Mark the hashdir as dirty
4507        make_hashdir_dirty
4508}
4509
4510# Save the hash-list to run a cleanup afterwards
4511pbirm_save_hashlist() {
4512        if [ "${PBI_DISABLEHASHDIR}" = "YES" ] ; then return 0 ; fi
4513        if [ -e "${PBI_PROGDIRPATH}/${PBI_HASHLIST}" ] ; then
4514                PBI_TMPHASHLIST="${PBI_TMPDIR}/.pbi-hash.$$"
4515                cp ${PBI_PROGDIRPATH}/${PBI_HASHLIST} ${PBI_TMPHASHLIST}
4516        fi
4517}
4518
4519# Function which removes all empty dirs from the hash-dir
4520pbi_clean_emptyhdirs() {
4521        if [ ! -d "${PBI_HASHDIR}" ] ; then return 0 ; fi
4522        cd ${PBI_HASHDIR}
4523        found="0"
4524        for i in `find . -empty -type d 2>/dev/null`
4525        do
4526                if [ "${i}" = "." ] ; then continue ; fi
4527                if [ -d "${PBI_HASHDIR}/${i}" ] ; then
4528                        rmdir "${PBI_HASHDIR}/${i}"
4529                        found="1"
4530                fi     
4531        done
4532
4533        # Run recursively
4534        if [ "$found" = "1" ];then pbi_clean_emptyhdirs ; fi
4535}
4536
4537# Read through and clean the given hash-list
4538pbi_clean_hashlist() {
4539        if [ -z "${PBI_TMPHASHLIST}" ] ; then return 0 ; fi
4540        while read hl
4541        do
4542                file="`echo $hl | sed 's/:::.*$//g'`"
4543                hash="`echo $hl | sed 's/^.*::://g'`"
4544                tfile="${file}:::${hash}"
4545                if [ -f "${PBI_HASHDIR}/${tfile}" ] ; then
4546                        check_remove_hashfile "${tfile}"
4547                fi
4548
4549        done < ${PBI_TMPHASHLIST}
4550        rm ${PBI_TMPHASHLIST}
4551}
4552
4553# Read through and clean the entire hashdir
4554pbi_clean_hashdir() {
4555        if [ ! -d "${PBI_HASHDIR}" ] ; then return 0 ; fi
4556        echo "Cleaning shared-hash dir..."
4557        cd ${PBI_HASHDIR}
4558        tmphashlist="${PBI_TMPDIR}/.pbi-hashdir.$$"
4559        find * -type f -links 1 > "${tmphashlist}" 2>/dev/null
4560        while read hl
4561        do
4562                if [ ! -f "$hl" -o -h "$hl" ] ; then continue ; fi
4563                if [ -f "${PBI_HASHDIR}/${hl}" ] ; then
4564                        check_remove_hashfile "${hl}"
4565                fi
4566
4567        done < $tmphashlist
4568        rm "$tmphashlist"
4569        pbi_clean_emptyhdirs
4570}
4571
4572# Check if this hash-file is ready to be removed from the hash-dir
4573check_remove_hashfile() {
4574        tfile="${PBI_HASHDIR}/${1}"
4575        get_hard_link_count "${tfile}"
4576        if [ "$HLINKS" = "1" ] ; then
4577                if [ "${PBI_VERBOSE}" = "YES" ] ; then
4578                        echo "Removing unused hashfile: $tfile"
4579                fi
4580                rm -f "${tfile}"
4581        fi
4582}
4583
4584# Run the removal script for this PBI
4585run_remove_script() {
4586        uisc="${PBI_PROGDIRPATH}/${PBI_FAKEBIN_DIR}/.pbi-uninstall.sh"
4587        if [ ! -e "$uisc" ] ; then return 0 ; fi
4588
4589        # If not running as root, be sure to cleanup path links
4590        if [ "`id -u`" != "0" ]; then
4591                cat ${PBI_PROGDIRPATH}/${PBI_FAKEBIN_DIR}/${PBI_UNINS_PATHSCRIPT} | grep 'rm "$SYS_LOCALBASE/bin' | sed 's|$SYS_LOCALBASE|${HOME}|g' >${PBI_TMPDIR}/.binlnks
4592                while read lnk
4593                do
4594                        /bin/sh -c "${lnk}"
4595                done <${PBI_TMPDIR}/.binlnks
4596                rm ${PBI_TMPDIR}/.binlnks
4597        fi
4598        export_script_vars
4599        if [ "$PBI_VERBOSE" = "YES" ] ; then
4600                sh "${uisc}"
4601        else
4602                sh "${uisc}" >/dev/null 2>/dev/null
4603        fi
4604}
4605
4606# Function to check the supplied $1 dir for any mounts before we
4607# do a rm -rf
4608umount_before_rm()
4609{
4610        if [ -z "${1}" ] ; then return 0 ; fi
4611
4612        local _ddir="$1"
4613        echo "$_ddir" | rev | grep -q '^/'     
4614        if [ $? -ne 0 ] ; then
4615           _ddir="${_ddir}/"
4616        fi
4617       
4618        mount | grep -q "on ${_ddir}"
4619        if [ $? -ne 0 ] ; then return 0; fi
4620
4621        for i in `mount | grep "on ${_ddir}" | awk '{print $3}'`
4622        do
4623           umount -f ${i} >/dev/null 2>/dev/null
4624           if [ $? -ne 0 ] ; then
4625                exit_err "Could not umount ${i} before rm -rf, bailing!"
4626           fi
4627        done
4628        return 0
4629}
4630
4631# Remove the pbi directory
4632remove_pbidir() {
4633        if [ -z "${PBI_PROGDIRPATH}" ] ; then return 0 ; fi
4634        if [ ! -d "${PBI_PROGDIRPATH}" ] ; then return 0 ; fi
4635        if [ "${PBI_PROGDIRPATH}" = "/" ] ; then return 0 ; fi
4636        if [ "$PBI_VERBOSE" = "YES" ] ; then
4637                echo "Removing: ${PBI_PROGDIRPATH}"
4638        fi
4639
4640        # Make sure we are unmounted
4641        umount_before_rm "${PBI_PROGDIRPATH}"
4642       
4643        rm -rf "${PBI_PROGDIRPATH}" >/dev/null 2>/dev/null
4644
4645        # Do we have leftovers?
4646        if [ -d "${PBI_PROGDIRPATH}" ] ; then
4647                chflags -R noschg "${PBI_PROGDIRPATH}" >/dev/null 2>/dev/null
4648                chmod -R 777 "${PBI_PROGDIRPATH}" >/dev/null 2>/dev/null
4649                rm -rf "${PBI_PROGDIRPATH}" >/dev/null 2>/dev/null
4650        fi
4651}
4652
4653# Remove this PBI registration
4654unregister_pbi() {
4655        if [ -z "${PBI_DBAPPDIR}" ] ; then return 0 ; fi
4656        if [ -z "${PBI_DELETENAME}" ] ; then return 0 ; fi
4657        if [ ! -d "${PBI_DBAPPDIR}/${PBI_DELETENAME}" ] ; then return 0 ; fi
4658        if [ "$PBI_VERBOSE" = "YES" ] ; then
4659                echo "Removing: ${PBI_DBAPPDIR}/${PBI_DELETENAME}"
4660        fi
4661        rm -rf "${PBI_DBAPPDIR}/${PBI_DELETENAME}"
4662
4663}
4664
4665# Check if we have a preinstall script we need to use
4666check_preremove_script() {
4667        if [ ! -e "${PBI_DBAPPDIR}/${PBI_DELETENAME}/${MOD_PREREM}" ] ; then return 0 ; fi
4668
4669        if [ "$PBI_VERBOSE" = "YES" ] ; then
4670                echo "Running pre-removal script: ${PBI_DBAPPDIR}/${PBI_DELETENAME}/${MOD_PREREM}"
4671        fi
4672        export_script_vars
4673        sh "${PBI_DBAPPDIR}/${PBI_DELETENAME}/${MOD_PREREM}"
4674}
4675
4676add_app_path_links()
4677{
4678        # If root, run the regular path script
4679        if [ `id -u` = "0" ] ; then
4680                sh "${1}/${PBI_FAKEBIN_DIR}/${PBI_INS_PATHSCRIPT}" >/dev/null 2>/dev/null
4681                return
4682        fi
4683
4684        # Running as user add to ~/bin
4685        init_tmpdir
4686        if [ ! -d "${HOME}/bin" ] ; then mkdir -p "${HOME}/bin"; fi
4687        cat ${1}/${PBI_FAKEBIN_DIR}/${PBI_INS_PATHSCRIPT} | grep "${1}/${PBI_FAKEBIN_DIR}" | grep '$SYS_LOCALBASE/bin' | sed 's|$SYS_LOCALBASE|${HOME}|g' >${PBI_TMPDIR}/.binlnks
4688        while read lnk
4689        do
4690                /bin/sh -c "${lnk}"
4691               
4692        done <${PBI_TMPDIR}/.binlnks
4693        rm ${PBI_TMPDIR}/.binlnks
4694       
4695}
4696
4697del_app_path_links()
4698{
4699        # If root, run the regular path script
4700        if [ `id -u` = "0" ] ; then
4701                sh "${1}/${PBI_FAKEBIN_DIR}/${PBI_UNINS_PATHSCRIPT}" >/dev/null 2>/dev/null
4702                return
4703        fi
4704
4705        # Running as user remove from ~/bin
4706        if [ ! -d "${HOME}/bin" ] ; then mkdir -p "${HOME}/bin"; fi
4707        for lnk in `ls ${1}/${PBI_FAKEBIN_DIR}`
4708        do
4709                if [ "$lnk" = "$PBI_INS_PATHSCRIPT" -o "$lnk" = "$PBI_UNINS_PATHSCRIPT" ]
4710                then
4711                        continue
4712                fi
4713
4714                if [ ! -e "${HOME}/bin/$lnk" ] ; then continue ; fi
4715                if [ ! -h "${HOME}/bin/$lnk" ] ; then continue ; fi
4716                       
4717                ls -al "${HOME}/bin/$lnk" | awk '{print $11}' | grep $1 >/dev/null 2>/dev/null
4718                if [ "$?" = "0" ] ; then
4719                        rm ${HOME}/bin/$lnk
4720                fi
4721        done
4722       
4723}
4724
4725pbi_icon_init() {
4726        parse_icon_pbi_cmdline "$@"
4727       
4728        do_pbi_icon
4729}
4730
4731# Start the PBI icon process
4732do_pbi_icon() {
4733        # Get the dir for this PBI
4734        _appDir=`cat ${PBI_DBAPPDIR}/${PBI_ICONTARGETAPP}/pbi_installedpath`
4735
4736        if [ "${PBI_PATHADD}" = "YES" ] ; then
4737                add_app_path_links "$_appDir"
4738        fi
4739        if [ "${PBI_PATHDEL}" = "YES" ] ; then
4740                del_app_path_links "$_appDir"
4741        fi
4742
4743        if [ "${PBI_DESKADD}" = "YES" ] ; then
4744                if [ ! -e "${_appDir}/.xdg-desktop/${PBI_INS_DESKSCRIPT}" ] ; then
4745                        exit_err "No desktop icons for this PBI"
4746                fi
4747                sh "${_appDir}/.xdg-desktop/${PBI_INS_DESKSCRIPT}"
4748        fi
4749        if [ "${PBI_DESKDEL}" = "YES" ] ; then
4750                if [ ! -e "${_appDir}/.xdg-desktop/${PBI_UNINS_DESKSCRIPT}" ] ; then
4751                        exit_err "No desktop icons for this PBI"
4752                fi
4753                sh "${_appDir}/.xdg-desktop/${PBI_UNINS_DESKSCRIPT}"
4754        fi
4755        if [ "${PBI_MENUADD}" = "YES" ] ; then
4756                require_root_or_group
4757                if [ ! -e "${_appDir}/.xdg-menu/${PBI_INS_MENUSCRIPT}" ] ; then
4758                        exit_err "No menu icons for this PBI"
4759                fi
4760                sh "${_appDir}/.xdg-menu/${PBI_INS_MENUSCRIPT}"
4761        fi
4762        if [ "${PBI_MENUDEL}" = "YES" ] ; then
4763                require_root_or_group
4764                if [ ! -e "${_appDir}/.xdg-menu/${PBI_UNINS_MENUSCRIPT}" ] ; then
4765                        exit_err "No menu icons for this PBI"
4766                fi
4767                sh "${_appDir}/.xdg-menu/${PBI_UNINS_MENUSCRIPT}"
4768        fi
4769        if [ "${PBI_MIMEADD}" = "YES" ] ; then
4770                require_root_or_group
4771                if [ ! -e "${_appDir}/.xdg-mime/${PBI_INS_MIMESCRIPT}" ] ; then
4772                        exit_err "No mime registration for this PBI"
4773                fi
4774                sh "${_appDir}/.xdg-mime/${PBI_INS_MIMESCRIPT}"
4775        fi
4776        if [ "${PBI_MIMEDEL}" = "YES" ] ; then
4777                require_root_or_group
4778                if [ ! -e "${_appDir}/.xdg-mime/${PBI_UNINS_MIMESCRIPT}" ] ; then
4779                        exit_err "No mime registration for this PBI"
4780                fi
4781                sh "${_appDir}/.xdg-mime/${PBI_UNINS_MIMESCRIPT}"
4782        fi
4783}
4784
4785pbid_init() {
4786        require_root
4787
4788        parse_pbid_cmdline "$@"
4789
4790        do_pbid
4791}
4792
4793# Start the PBID daemon
4794do_pbid() {
4795
4796        # Start by sourcing /etc/profile
4797        # This grabs any HTTP_ / FTP_ PROXY variables
4798        . /etc/profile
4799
4800        # Allow user supplied logfile
4801        if [ -z "${PBID_LOGFILE}" ] ; then
4802          _pbid_log="/var/log/pbid.log"
4803        else
4804          _pbid_log="${PBID_LOGFILE}"
4805        fi
4806
4807        # Set verbosity
4808        _redir="&1"
4809        if [ "${PBI_VERBOSE}" != "YES" ] ; then _redir="/dev/null" ; fi
4810        echo "Started pbid: `date`" > ${_pbid_log}
4811
4812        while
4813        i=1
4814        do
4815                # Do regular sleeps
4816                qslp=0
4817
4818                # Check if we have any out of date index files to update
4819                for _dbIndex in `ls ${PBI_DBREPODIR}`
4820                do
4821                        _iMd5=`echo ${_dbIndex} | cut -d '.' -f 2`
4822                        check_update_index "${_iMd5}"
4823
4824                        # If we failed to get an index try again sooner
4825                        # This is useful if the user has just installed and has not setup
4826                        # the network yet. We want to fetch indexes quickly after net
4827                        # comes up so they dont need to wait 15 min or whatever its set to
4828                        if [ ! -e "${PBI_DBINDEXDIR}/${_iMd5}-index" ] ; then qslp=1; fi
4829                done
4830
4831                # Check if we have a dirty hash-dir to cleanup
4832                check_clean_hashdir "$_pbid_log" "$_redir"
4833
4834                # Check if we have any PBIs to auto-update
4835                check_autoupdate_pbis "$_pbid_log" "$_redir"
4836
4837                # Check if we need to merge files into the hashdir
4838                if [ -n "`ls ${PBI_DBHASHQUEUEDIR}`" ] ; then
4839                        init_tmpdir
4840                        for _hpbi in `ls ${PBI_DBHASHQUEUEDIR}`
4841                        do
4842                                if [ ! -e "${PBI_DBAPPDIR}/${_hpbi}/pbi_installedpath" ] ; then
4843                                        rm ${PBI_DBHASHQUEUEDIR}/${_hpbi}
4844                                        continue
4845                                fi
4846
4847                                _hpbipath=""
4848                                _hpbipath=`cat ${PBI_DBAPPDIR}/${_hpbi}/pbi_installedpath`
4849                                if [ ! -e "${_hpbipath}/${PBI_HASHLIST}" ] ; then
4850                                        rm ${PBI_DBHASHQUEUEDIR}/${_hpbi}
4851                                        continue
4852                                fi
4853
4854                                # Get the username this PBI was installed as
4855                                get_username_from_file "${_hpbipath}"
4856
4857                                # Lets start this hash merge
4858                                echo "Adding ${_hpbipath} to hash-dir ($FILEUSER): `date`" >> ${_pbid_log}
4859
4860                                if [ "$FILEUSER" = "root" ];then
4861                                        pbi_add_update_hashdir "${_hpbipath}" "${PBI_DBAPPDIR}/${_hpbi}/.pbiDeleted" >${_redir} 2>${_redir}
4862                                else
4863                                        # Run hashdir command as a user
4864                                        su $FILEUSER -c "pbi_update_hashdir \"${_hpbipath}\" \"${PBI_DBAPPDIR}/${_hpbi}/.pbiDeleted\"" >${_redir} 2>${_redir}
4865                                fi
4866                                echo "Finished adding ${_hpbipath} to hash-dir: `date`" >> ${_pbid_log}
4867                               
4868                                # Now remove the trigger file
4869                                rm ${PBI_DBHASHQUEUEDIR}/${_hpbi}
4870
4871                        done
4872                        rm_tmpdir
4873
4874                fi
4875               
4876                # Check if we should rotate the logfile
4877                _pbidLines=`wc -l ${_pbid_log} | awk '{ print $1 }'`
4878                if [ $(is_num "$_pbidLines") ] ; then
4879                        if [ $_pbidLines -gt $PBI_LOG_LINES ] ; then
4880                                echo "Logfile turnover: `date`" >${_pbid_log}
4881                        fi
4882                fi
4883               
4884
4885                # Done with our check, lets go back to sleep now
4886                if [ $qslp -eq 1 ] ; then
4887                        sleep 60
4888                else
4889                        sleep ${PBIDSLEEP}
4890                fi
4891        done
4892
4893}
4894
4895# Check if there are any PBIs which are flagged for auto-updates
4896check_autoupdate_pbis() {
4897
4898        for i in `ls ${PBI_DBAPPDIR}/ 2>/dev/null`
4899        do
4900                if [ ! -e "${PBI_DBAPPDIR}/${i}/autoupdate-enable" ] ; then
4901                        continue
4902                fi
4903
4904                # Check if this app is already updating
4905                if [ -e "${PBI_DBAPPDIR}/${i}/.updating" ] ; then
4906                        ps -p `cat ${PBI_DBAPPDIR}/${i}/.updating` >/dev/null 2>/dev/null
4907                        if [ "$?" != "0" ] ; then
4908                                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
4909                        else
4910                                continue
4911                        fi
4912                fi
4913
4914                # Found an auto-update enabled APP, see if it needs upping
4915                PBI_UPDATEAPP="$i"
4916
4917                # Load the details about this app
4918                load_info_from_dir "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
4919                if [ -z "${PBI_REPO}" ]; then
4920                        pbi_checksig_repomatch "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
4921                fi
4922                if [ -z "${PBI_REPO}" ]; then continue ; fi
4923                local _repoID=`ls ${PBI_DBREPODIR}/*.${PBI_REPO} | cut -d '.' -f 1 | sed "s|${PBI_DBREPODIR}/||g"`
4924
4925                # Does this need an update?
4926                check_pbi_update "$PBI_UPDATEAPP" "nodisplay" \
4927                        "$PBI_PROGNAME" "current" \
4928                        "$PBI_FBSDVER" "$PBI_APPARCH" "$_repoID" "$PBI_PROGMDATE"
4929                if [ "$?" != "0" ] ; then
4930                        continue
4931                fi
4932               
4933                # Get the username this PBI was installed as
4934                get_username_from_file "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
4935
4936                # Its Update Time!
4937                echo "Starting Auto-Update of ${PBI_UPDATEAPP} ($FILEUSER): `date`" >>${_pbid_log}
4938
4939                su ${FILEUSER} -c "pbi_update ${PBI_UPDATEAPP}" >>${_pbid_log} 2>>${_pbid_log}
4940                if [ "$?" = "0" ] ; then
4941                        echo "Success! Update of ${PBI_UPDATEAPP}: `date`" >>${_pbid_log}
4942                else
4943                        echo "Failed! Update of ${PBI_UPDATEAPP}: `date`" >>${_pbid_log}
4944                fi
4945
4946                rm "${PBI_DBAPPDIR}/${i}/.updating" >/dev/null 2>/dev/null
4947        done
4948}
4949
4950check_clean_hashdir() {
4951        if [ ! -e "${PBI_DBDIRTYFILE}" ] ; then return ; fi
4952
4953        # Get the date of the last hash-cleaning done
4954        local _curDate="`cat ${PBI_DBDIRTYFILE}`"
4955        if [ -e "${PBI_DBDIRTYFILE}.last" ] ; then
4956                local _lastDate="`cat ${PBI_DBDIRTYFILE}.last`"
4957        else
4958                local _lastDate="0"
4959        fi
4960
4961        # See if we have a new date trigger to do a cleaning
4962        if [ "$_curDate" = "${_lastDate}" ]; then return; fi
4963
4964        # Loop through and clean any hash-dirs as the appropriate user
4965        for cHdir in `ls -d ${PBI_HASHDIR}*`
4966        do
4967                get_username_from_file "${cHdir}"
4968                echo "Cleaning hash-dir ($FILEUSER): `date`" >> ${1}
4969                su ${FILEUSER} -c "pbi_delete --clean-hdir" >>${2} 2>>${2}
4970                echo "Finished cleaning hash-dir ($FILEUSER): `date`" >> ${1}
4971                echo "$_curDate" > ${PBI_DBDIRTYFILE}.last 2>/dev/null
4972        done
4973}
4974
4975pbi_info_init() {
4976        parse_info_pbi_cmdline "$@"
4977       
4978        do_pbi_info
4979}
4980
4981# Display information on the PBI / PBIs
4982do_pbi_info() {
4983
4984        # If we are listing available PBIs via the index file
4985        if [ "$PBI_INFOINDEX" = "YES" ] ; then
4986               
4987                # List the available PBIs from the index
4988                do_index_listing
4989               
4990                exit_trap
4991        fi
4992
4993        if [ "$PBI_INFONAME" = "--ALL--" ] ; then
4994                for i in `ls ${PBI_DBAPPDIR}/ 2>/dev/null`
4995                do
4996                        if [ -e "${PBI_DBAPPDIR}/${i}/pbi_name" ] ; then
4997                                if [ "$PBI_VERBOSE" = "YES" ] ; then
4998                                        load_info_from_dir "${PBI_DBAPPDIR}/${i}"
4999                                        get_username_from_file "${PBI_DBAPPDIR}/${i}"
5000                                        PBI_INSTALLED_BY=$FILEUSER
5001                                        pbi_display_info
5002                                        pbi_display_gui "${PBI_DBAPPDIR}/${i}" ""
5003                                        echo " "
5004                                else
5005                                        echo "${i}"
5006                                fi
5007                        fi
5008                done
5009        else
5010                # Start loading our variables
5011                load_info_from_dir "${PBI_DBAPPDIR}/${PBI_INFONAME}"
5012                get_username_from_file "${PBI_DBAPPDIR}/${PBI_INFONAME}"
5013                PBI_INSTALLED_BY=$FILEUSER
5014                pbi_display_info
5015        fi
5016}
5017
5018# Read through the master index file and provide listing of available PBIs for installation
5019do_index_listing()
5020{
5021        # Make sure we have a master index
5022        ls ${PBI_DBINDEXDIR}/* >/dev/null 2>/dev/null
5023        if [ "$?" != "0" ] ; then return ; fi
5024
5025        for _rIndex in `ls ${PBI_DBINDEXDIR}/*index* | grep -v '.time'`
5026        do
5027                _rMd5=`basename ${_rIndex} | sed 's|-index||g'`
5028                _rDesc=`cat ${PBI_DBREPODIR}/*.${_rMd5} | grep 'Desc: ' | sed 's|Desc: ||g'`
5029                echo "Current and available PBIs. * = current"
5030                echo "Repository: $_rDesc"
5031                echo "----------------------------------------------------------------"
5032
5033                sort "${_rIndex}" | while read _iLine
5034                do
5035                        PBI_UPNAME="`echo $_iLine | cut -d ':' -f 1`"
5036                        PBI_UPARCH="`echo $_iLine | cut -d ':' -f 2`"
5037                        PBI_UPNVER="`echo $_iLine | cut -d ':' -f 3`"
5038                        PBI_UPSTATUS="`echo $_iLine | cut -d ':' -f 9`"
5039                        pad_var "${PBI_UPNAME}" "30"
5040                        PBI_UPNAME="${PAD_VAR}"
5041                        pad_var "${PBI_UPNVER}" "15"
5042                        PBI_UPNVER="${PAD_VAR}"
5043                        pad_var "${PBI_UPARCH}" "6"
5044                        PBI_UPARCH="${PAD_VAR}"
5045       
5046                        if [ "$PBI_UPSTATUS" = "current" ] ; then
5047                                echo "$PBI_UPNAME   $PBI_UPNVER $PBI_UPARCH *"
5048                        fi
5049                        if [ "$PBI_UPSTATUS" = "active" ] ; then
5050                                echo "$PBI_UPNAME   $PBI_UPNVER $PBI_UPARCH"
5051                        fi
5052                done
5053        done
5054
5055}
5056
5057# Function to pad a variable to X spaces
5058pad_var() {
5059        local _pVar="$1"
5060        local _pNum="$2"
5061        PAD_VAR="`echo \"$_pVar                                                                                    x\" | cut -c 1-$_pNum`"
5062}
5063
5064# Checks if we have a custom script to run prior to port make
5065run_pbi_preportmake()
5066{
5067        if [ ! -d "${PBI_CONFDIR}" ] ; then return 0 ; fi
5068        if [ ! -d "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}" ] ; then return 0 ; fi
5069        if [ ! -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/pre-portmake.sh" ] ; then return 0 ; fi
5070
5071        export_script_vars
5072
5073        sh "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/pre-portmake.sh"
5074        if [ "$?" != "0" ] ; then
5075                exit_err "pre-portmake.sh failed!"
5076        fi
5077}
5078
5079# Checks if we have a custom script to run prior to port make
5080run_pbi_postportmake()
5081{
5082        if [ ! -d "${PBI_CONFDIR}" ] ; then return 0 ; fi
5083        if [ ! -d "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}" ] ; then return 0 ; fi
5084        if [ ! -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/post-portmake.sh" ] ; then return 0 ; fi
5085
5086        export_script_vars
5087
5088        sh "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/post-portmake.sh"
5089        if [ "$?" != "0" ] ; then
5090                echo "Warning: post-portmake.sh returned non-0 status!"
5091        fi
5092}
5093
5094# Checks if we have a custom script to run prior to pbi create
5095run_pbi_prepkgscript()
5096{
5097        if [ ! -d "${PBI_CONFDIR}" ] ; then return 0 ; fi
5098        if [ ! -d "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}" ] ; then return 0 ; fi
5099        if [ ! -e "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/pre-pbicreate.sh" ] ; then return 0 ; fi
5100
5101        export_script_vars
5102
5103        sh "${PBI_CONFDIR}/${PBI_CONF_SCRIPTSDIR}/pre-pbicreate.sh"
5104        if [ "$?" != "0" ] ; then
5105                echo "Warning: post-portmake.sh returned non-0 status!"
5106        fi
5107}
5108
5109# Begins the port make
5110start_pbi_makeport()
5111{
5112        do_port_build "${PBI_MAKEPORT}"
5113}
5114
5115# Prune any ports which aren't required for runtime
5116start_pbi_prune_ports()
5117{
5118        if [ "${PBI_PRUNEBUILDPORTS}" = "NO" ] ; then return ; fi
5119
5120        get_pkgname "${PBI_MAKEPORT}"
5121        echo "${PKGNAME}" > /.keepports
5122        make -C "${PORTSDIR}/${PBI_MAKEPORT}" PORTSDIR=${PORTSDIR} package-depends | cut -d: -f1 >> /.keepports
5123
5124        # Do the same for any OTHERPORTS
5125        for port in ${PBI_MKPORTBEFORE}
5126        do
5127                if [ ! -d "${PORTSDIR}/${port}" ] ; then continue ; fi
5128                get_pkgname "${port}"
5129                echo "${PKGNAME}" >> /.keepports
5130                make -C "${PORTSDIR}/${port}" PORTSDIR=${PORTSDIR} package-depends | cut -d: -f1 >> /.keepports
5131        done
5132
5133        for port in ${PBI_MKPORTAFTER}
5134        do
5135                if [ ! -d "${PORTSDIR}/${port}" ] ; then continue ; fi
5136                get_pkgname "${port}"
5137                echo "${PKGNAME}" >> /.keepports
5138                make -C "${PORTSDIR}/${port}" PORTSDIR=${PORTSDIR} package-depends | cut -d: -f1 >> /.keepports
5139        done
5140
5141        # Don't strip out pkgng
5142        pkg info pkg >> /.keepports
5143       
5144        # Sort and clean the ports
5145        cat /.keepports | sort | uniq > /.keepports.tmp
5146        mv /.keepports.tmp /.keepports
5147
5148        # Now remove any unused ports
5149        for j in `pkg info -a | cut -d " " -f 1`
5150        do
5151                grep -q "^${j}" "/.keepports"
5152                if [ $? -ne 0 ] ; then
5153                        echo "Removing non-required port: ${j}"
5154                        $PKG_DELETE ${j} 
5155                fi
5156        done
5157}
5158
5159# Get the full package-name for a target port
5160get_pkgname() {
5161        name="`pkg info -O ${1} | awk '{print $1}'`"
5162        PKGNAME="${name}"
5163}
5164
5165# Make any additional required ports
5166start_pbi_mkportbefore()
5167{
5168        if [ -z "${PBI_MKPORTBEFORE}" ] ; then return ; fi
5169       
5170        for port in ${PBI_MKPORTBEFORE}
5171        do
5172                if [ ! -d "/usr/ports/${port}" ] ; then
5173                        exit_err "/usr/ports/${port} does not exist!"
5174                fi
5175                do_port_build "${port}"
5176        done
5177
5178}
5179
5180# Make any additional required ports
5181start_pbi_mkportafter()
5182{
5183        if [ -z "${PBI_MKPORTAFTER}" ] ; then return ; fi
5184       
5185        for port in ${PBI_MKPORTAFTER}
5186        do
5187                if [ ! -d "/usr/ports/${port}" ] ; then
5188                        exit_err "/usr/ports/${port} does not exist!"
5189                fi
5190                do_port_build "${port}"
5191        done
5192
5193}
5194
5195# Start pbi_update_hashdir
5196pbi_update_hashdir_init() {
5197        pbi_add_update_hashdir "$1" "$2"
5198}
5199
5200# Start pbi_update processing
5201pbi_update_init() {
5202
5203        parse_update_pbi_cmdline "$@"
5204
5205        check_enable_disable_auto
5206
5207        # Stop here if we are just enabling / disabling auto-update
5208        if [ -n "$PBI_UPENABLEAUTO" ] ; then return 0 ; fi
5209
5210        start_update_checks
5211        if [ "$?" != "0" ] ; then rm_tmpdir ; exit 1 ; fi
5212
5213        # Stop here if only doing update checks
5214        if [ -n "${PBI_UPCHECK}" ]; then return 0 ; fi
5215
5216        require_root_or_group
5217
5218        do_pbi_update
5219}
5220
5221# Check if we are enabling / disabling auto-updating
5222check_enable_disable_auto()
5223{
5224        if [ -z "$PBI_UPENABLEAUTO" ] ; then return ; fi
5225        if [ ! -d "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}" ] ; then return ; fi
5226
5227        # Enable / disable auto-updating now
5228        if [ "$PBI_UPENABLEAUTO" = "YES" ]; then
5229                touch ${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/autoupdate-enable
5230        else
5231                rm ${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/autoupdate-enable >/dev/null 2>/dev/null
5232        fi
5233}
5234
5235# Function which checks the digital signature of a PBI to match it to a particular repo
5236pbi_checksig_repomatch() {
5237        if [ `id -u` != "0" ] ; then return ; fi
5238
5239        # See which repo / key this PBI associates to, if any
5240        check_valid_sigs "${1}"
5241        if [ "$?" = "0" -a -n "$PBI_VALIDKEYSIG" ] ; then
5242                _rMd5="`echo ${PBI_VALIDKEYSIG} | cut -d '.' -f 1`"
5243                echo "$_rMd5" | sed "s|${PBI_DBKEYDIR}/||g" > ${1}/pbi_repo
5244        fi
5245}
5246
5247# See if we are checking for updates and do it
5248start_update_checks() {
5249        if [ "${PBI_UPCHECK}" != "YES" -a "${PBI_UPCHECK}" != "ALL" ]; then return 0; fi
5250
5251        # Open up the tmpdir
5252        init_tmpdir
5253
5254        if [ "${PBI_UPCHECK}" = "YES" ] ; then
5255                load_info_from_dir "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
5256                if [ -z "${PBI_REPO}" ]; then
5257                        pbi_checksig_repomatch "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
5258                fi
5259                if [ -z "${PBI_REPO}" ]; then
5260                        return 1
5261                else
5262                        local _repoID=`ls ${PBI_DBREPODIR}/*.${PBI_REPO} | cut -d '.' -f 1 | sed "s|${PBI_DBREPODIR}/||g"`
5263                fi
5264
5265                check_pbi_update "$PBI_UPDATEAPP" "display" \
5266                 "$PBI_PROGNAME" "current" \
5267                 "$PBI_FBSDVER" "$PBI_APPARCH" "$_repoID" "$PBI_PROGMDATE"
5268                return $?
5269        else
5270                # Loop and check all PBIs for updates
5271                for i in `ls ${PBI_DBAPPDIR}/ 2>/dev/null`
5272                do
5273                        PBI_REPO=""
5274                        if [ -e "${PBI_DBAPPDIR}/${i}/pbi_name" ] ; then
5275                                load_info_from_dir "${PBI_DBAPPDIR}/${i}"
5276                                if [ -z "${PBI_REPO}" ]; then
5277                                        pbi_checksig_repomatch "${PBI_DBAPPDIR}/${i}"
5278                                fi
5279                                if [ -z "${PBI_REPO}" ]; then
5280                                        continue
5281                                else
5282                                        local _repoID=`ls ${PBI_DBREPODIR}/*.${PBI_REPO} | cut -d '.' -f 1 | sed "s|${PBI_DBREPODIR}/||g"`
5283                                fi
5284
5285                                check_pbi_update "$i" "display" \
5286                                 "$PBI_PROGNAME" "current" \
5287                                 "$PBI_FBSDVER" "$PBI_APPARCH" "$_repoID" "$PBI_PROGMDATE"
5288                        fi
5289                done
5290                return 0
5291        fi
5292
5293}
5294
5295# Check if we need to pull down the updated INDEX file
5296check_update_index() {
5297
5298        init_tmpdir
5299       
5300        local _repoMd5="$1"
5301        local _rURL=`cat ${PBI_DBREPODIR}/*${_repoMd5} | grep URL: | sed 's|URL: ||g'`
5302
5303        _pbiIndex="${PBI_DBINDEXDIR}/${_repoMd5}-index"
5304        _pbiMeta="${PBI_DBINDEXDIR}/${_repoMd5}-meta"
5305        _pbiIndexTime="${_pbiIndex}.time"
5306        _tmpPbiIndex="${PBI_TMPDIR}/.upcheck$$"
5307        _tmpPbiMeta="${PBI_TMPDIR}/.upcheck$$"
5308               
5309        # Check if its been greater than $PBI_INDEXREFRESH hours since the last update
5310        if [ -e "${_pbiIndexTime}" ] ; then
5311                _curTime=`date +%s`
5312                _oTime=`cat ${_pbiIndexTime}`
5313                _trigTime=`expr ${PBI_INDEXREFRESH} \* 60 \* 60`
5314                expr $_curTime - $_oTime >/dev/null 2>/dev/null
5315                if [ "$?" = "0" ] ; then
5316                        _passed=`expr $_curTime - $_oTime`
5317                        if [ "$_passed" -lt "$_trigTime" ] ; then
5318                                return;
5319                        fi
5320                fi
5321               
5322        fi
5323
5324        if [ "${PBI_VERBOSE}" = "YES" ] ; then
5325                echo "Updating index ${_pbiIndex}"
5326                echo "Updating index ${_pbiIndex}: `date`" >> ${_pbid_log}
5327        fi
5328
5329        # Check that the last char isn't a '/'
5330        _tmp=`echo ${_rURL} | wc -m | tr -s ' ' | tr -d ' '`
5331        _tmp2=`expr $_tmp - 1`
5332        _lastC=`echo ${_tmp} | cut -c ${_tmp2}-${_tmp}`
5333        if [ "${_lastC}" = "/" ] ; then
5334                _upURL="`echo ${_rURL} | sed 's|\(.*\).|\1|'`"
5335        else
5336                _upURL="${_rURL}"
5337        fi
5338
5339        fetch -o "${_tmpPbiIndex}.bz2" "${_upURL}/${PBI_INDEXUPFILE}.bz2" >/dev/null 2>/dev/null
5340        if [ "$?" != "0" ] ; then
5341                return
5342        fi
5343
5344        bzip2 -d "${_tmpPbiIndex}.bz2" >/dev/null 2>/dev/null
5345        if [ "$?" != "0" ] ; then
5346                return
5347        fi
5348
5349        # Move the uncompressed file
5350        mv "${_tmpPbiIndex}" "${_pbiIndex}" >/dev/null 2>/dev/null
5351
5352        # Wait a sec
5353        sleep 1
5354
5355        # Now check for an optional meta file update
5356        fetch -o "${_tmpPbiMeta}.bz2" "${_upURL}/${PBI_METAUPFILE}.bz2" >/dev/null 2>/dev/null
5357        if [ "$?" = "0" ] ; then
5358                bzip2 -d "${_tmpPbiMeta}.bz2" >/dev/null 2>/dev/null
5359                if [ "$?" = "0" ] ; then
5360                        mv "${_tmpPbiMeta}" "${_pbiMeta}" >/dev/null 2>/dev/null
5361                fi
5362        fi
5363
5364        # Update the icons for this repos meta file
5365        update_repo_icons "${_repoMd5}" "${_pbiMeta}"
5366
5367        echo "Finished updating index ${_pbiIndex}: `date`" >> ${_pbid_log}
5368        if [ "${PBI_VERBOSE}" = "YES" ] ; then
5369                echo "Finished updating index ${_pbiIndex}"
5370        fi
5371
5372        # Save the time that we are done
5373        date +%s > ${_pbiIndexTime}
5374
5375}
5376
5377# Check if we need to update any repository icons
5378update_repo_icons() {
5379        _repoMd5="$1"
5380        _repoMeta="$2"
5381
5382        echo "Updating meta-icons for $_repoMeta: `date`" >> ${_pbid_log}
5383
5384        # Loop through, downloading icons we find
5385        while read mLine
5386        do
5387                # Make sure this is an app / cat
5388                echo "$mLine" | grep -e "^App=" -e "^Cat=" >/dev/null 2>/dev/null
5389                if [ "$?" != "0" ] ; then continue ; fi
5390
5391                # Get the icon URL
5392                echo "$mLine" | grep "^App=" >/dev/null 2>/dev/null
5393                if [ "$?" = "0" ] ; then
5394                        line=`echo $mLine | sed 's|^App=||g'`
5395                        aIcon=`echo $line | cut -d ';' -f 3`
5396                else
5397                        line=`echo $mLine | sed 's|^Cat=||g'`
5398                        aIcon=`echo $line | cut -d ';' -f 2`
5399                fi
5400                iName=`echo $line | cut -d ';' -f 1`
5401                ext=`echo $aIcon | sed 's/.*\.//'`
5402       
5403                # If we already have this icon, we can skip
5404                if [ -e "${PBI_DBICONDIR}/${_repoMd5}-${iName}.${ext}" ] ; then
5405                        continue
5406                fi
5407
5408                # Now fetch the file
5409                sFile="${PBI_DBICONDIR}/${_repoMd5}-${iName}.${ext}"
5410                fetch -o "${sFile}" "${aIcon}" >/dev/null 2>/dev/null
5411                if [ $? -ne 0 ]; then
5412                  # Wait a moment before trying the next
5413                  sleep 40
5414                fi
5415               
5416        done < ${_repoMeta}
5417}
5418
5419# Check a specific PBI for updates
5420check_pbi_update() {
5421
5422        # Init the tmpdir
5423        init_tmpdir
5424
5425        # Set the vars
5426        _upbi="${1}"
5427        _udisp="${2}"
5428        _uprog="${3}"
5429        _uver="${4}"
5430        _ufbsdver="${5}"
5431        _uarch="${6}"
5432        _urepo="${7}"
5433        _omdate="${8}"
5434
5435        _uprog="`echo ${_uprog} | tr -d ' '`"
5436        appname="`echo ${_uprog} | tr '[:lower:]' '[:upper:]'`"
5437
5438        PBI_UPNVER=""
5439        PBI_UPFILE=""
5440        PBI_UPPATCHES=""
5441        PBI_UPCSUM=""
5442        PBI_UPMDATE=""
5443        PBI_UPREPO=""
5444        PBI_UPSIZE=""
5445
5446        # If we are looking for the current app, set _uver accordingly
5447        if [ "$_uver" = "current" ] ; then
5448                _uver=":current"
5449        else
5450                _uver=":${_uver}:"
5451        fi
5452
5453
5454        for _repo in `ls ${PBI_DBINDEXDIR}`
5455        do
5456
5457                if [ "$_urepo" = "AUTO" ] ; then
5458                        _pbiIndex="${PBI_DBINDEXDIR}/${_repo}"
5459                        _rMd5="`echo ${_repo} | sed 's|-index||g'`"
5460                else
5461                        _rMd5=`ls ${PBI_DBREPODIR}/${_urepo}.* | cut -d '.' -f 2`
5462                        _pbiIndex="${PBI_DBINDEXDIR}/${_rMd5}-index"
5463                fi
5464
5465                if [ ! -e "${_pbiIndex}" ] ; then continue ; fi
5466
5467                # Search the update index for the specified PBI
5468                _upLine=`grep -i -e "^$_uprog:" ${_pbiIndex} | grep ":$_uarch:" | grep "$_uver" | head -n 1`
5469
5470                PBI_UPNVER="`echo $_upLine | cut -d ':' -f 3`"
5471                PBI_UPFILE="`echo $_upLine | cut -d ':' -f 6`"
5472                PBI_UPPATCHES="`echo $_upLine | cut -d ':' -f 8`"
5473                PBI_UPCSUM="`echo $_upLine | cut -d ':' -f 4`"
5474                PBI_UPMDATE="`echo $_upLine | cut -d ':' -f 5`"
5475                PBI_UPSIZE="`echo $_upLine | cut -d ':' -f 8`"
5476                PBI_UPMIRROR="`cat ${PBI_DBMIRRORDIR}/${_rMd5} 2>/dev/null`"
5477                PBI_UPREPO="${_rMd5}"
5478
5479                if [ -n "${PBI_UPNVER}" ] ; then break; fi
5480                if [ "${_urepo}" != "AUTO" ] ; then break; fi
5481
5482        done
5483
5484        # If no new version
5485        if [ -z "$PBI_UPNVER" ] ; then return 1 ; fi
5486
5487        # See if this update is newer than the installed date
5488        if [ -n "$_omdate" ] ; then
5489                nDay=`echo $PBI_UPMDATE | cut -d ' ' -f 1`
5490                nHour=`echo $PBI_UPMDATE | cut -d ' ' -f 2`
5491                oDay=`echo $_omdate | cut -d ' ' -f 1`
5492                oHour=`echo $_omdate | cut -d ' ' -f 2`
5493         
5494                # Make sure we have all legit numbers
5495                if [ $(is_num "$nDay") -a $(is_num "$nHour") \
5496                        -a $(is_num "$oDay") -a $(is_num "$oHour") ] ; then
5497                        if [ $oDay -gt $nDay ] ; then return 1 ; fi
5498                        if [ "$oDay" = "$nDay" -a $oHour -gt $nHour ] ; then return 1 ; fi
5499                fi
5500        fi
5501
5502        if [ "$PBI_UPNVER" != "$PBI_PROGVERSION" ] ; then
5503                if [ "$_udisp" = "display" ] ; then
5504                        echo "${_upbi} - Available: ${PBI_UPNVER}"
5505                fi
5506                return 0
5507        else
5508                return 1
5509        fi
5510}
5511
5512# Start PBI update process
5513do_pbi_update() {
5514        if [ -n "${PBI_UPCHECK}" ]; then return 0 ; fi
5515
5516        if [ "$PBI_UPDATEAPP" = "ALL" ] ; then
5517                # Loop and check all PBIs for updates
5518                for i in `ls ${PBI_DBAPPDIR}/ 2>/dev/null`
5519                do
5520                        if [ -e "${PBI_DBAPPDIR}/${i}/.updating" ] ; then
5521                                ps -p `cat ${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating` >/dev/null 2>/dev/null
5522                                if [ "$?" = "0" ] ; then
5523                                        continue
5524                                fi
5525                                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5526                        fi
5527                        if [ -e "${PBI_DBAPPDIR}/${i}/pbi_name" ] ; then
5528                                PBI_UPDATEAPP="${i}"
5529                                start_pbi_updateapp "all"
5530                        fi
5531                done
5532        else
5533                if [ -e "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating" ] ; then
5534                        ps -p `cat ${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating` >/dev/null 2>/dev/null
5535                        if [ "$?" = "0" ] ; then
5536                                exit_err "This application is currently updating."
5537                        fi
5538                        rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5539                fi
5540                start_pbi_updateapp "single"
5541                exit $?
5542        fi
5543}
5544
5545# Attempt to download a PBI from the update server for "pbi_add -r"
5546pbi_add_fetch_remote() {
5547        # Set the target program we want to download
5548        _rtar="$PBI_FILENAME"
5549        unset PBI_FILENAME
5550
5551        # Check if the user overrode the arch / versions we want to install
5552        _rArch=`uname -m`
5553        if [ -n "$PBI_ADD_ALTARCH" ] ; then _rArch=$PBI_ADD_ALTARCH ; fi
5554
5555        _rVer="current"
5556        if [ -n "$PBI_ADD_ALTVER" ] ; then _rVer=$PBI_ADD_ALTVER ; fi
5557
5558        check_pbi_update "$_rtar" "nodisplay" \
5559         "$_rtar" "$_rVer" \
5560         "$FBSDMAJOR" "$_rArch" "${PBI_ADDREPO_ID}"
5561        if [ "$?" != "0" ] ; then 
5562                # If we are on amd64, do a fallback check to i386 for this PBI
5563                # This catches apps like wine / skype and others
5564                if [ "$_rArch" = "amd64" ] ; then
5565                        _rArch="i386"
5566                        check_pbi_update "$_rtar" "nodisplay" \
5567                        "$_rtar" "$_rVer" \
5568                        "$FBSDMAJOR" "$_rArch" "${PBI_ADDREPO_ID}"
5569                        if [ "$?" != "0" ] ; then
5570                                exit_err "Could not find \"$_rtar\" in any indexes" 
5571                        fi
5572                else
5573                        exit_err "Could not find \"$_rtar\" in any indexes" 
5574                fi
5575        fi
5576
5577        # We've gotten this far, now download the updated PBI
5578        pbi_update_dl
5579        if [ "$?" != "0" ] ; then
5580                exit_err "Failed downloading PBI"
5581        fi
5582
5583        # Now overwrite the PBI_FILENAME and let us proceed to regular install
5584        PBI_FILENAME="$PBI_UPDLFILE"
5585
5586        # If we are only fetching, finish up now
5587        if [ "$PBI_REMOTEFETCHONLY" = "YES" ] ; then
5588                mv $PBI_FILENAME ./`basename ${PBI_UPFILE}`
5589                echo "PBI saved to ./`basename ${PBI_UPFILE}`"
5590                exit_trap
5591        fi
5592
5593}
5594
5595# Update the targed PBI
5596start_pbi_updateapp() {
5597        _upact="${1}"
5598        if [ "$2" = "pbid" ] ; then
5599                _pbidlog="$2"
5600        else
5601                _pbidlog=""
5602        fi
5603
5604        echo "$$" > "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5605
5606        # Check for update to this app, and exit or return if not available
5607        load_info_from_dir "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
5608        if [ -z "${PBI_REPO}" ]; then
5609                pbi_checksig_repomatch "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}"
5610        fi
5611        if [ -z "${PBI_REPO}" ]; then
5612                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5613                return 1
5614        else
5615                local _repoID=`ls ${PBI_DBREPODIR}/*.${PBI_REPO} | cut -d '.' -f 1 | sed "s|${PBI_DBREPODIR}/||g"`
5616        fi
5617
5618        check_pbi_update "$PBI_UPDATEAPP" "nodisplay" \
5619         "$PBI_PROGNAME" "current" \
5620         "$PBI_FBSDVER" "$PBI_APPARCH" "$_repoID" "$PBI_PROGMDATE"
5621        if [ "$?" != "0" ] ; then
5622                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5623                if [ "$_upact" = "single" ] ; then
5624                        exit_err "$PBI_UPDATEAPP - no update available!"
5625                else
5626                        return 1
5627                fi
5628        fi
5629       
5630       
5631        echo "Starting update of ${PBI_UPDATEAPP} to ${PBI_UPNVER}..."
5632        _pbilow="`echo ${PBI_PROGNAME} | tr '[:upper:]' '[:lower:]' | sed 's| ||g'`"
5633
5634        # Check if there is a possible patch file for this update
5635        # new filename to download
5636        _pFile="${_pbilow}-${PBI_PROGVERSION}_to_${PBI_UPNVER}-${PBI_APPARCH}.pbp"
5637
5638        # Try downloading the patch file
5639        echo "Trying update via patchfile..."
5640        pbi_update_dl "$_pFile" "OFF"
5641        if [ "$?" = "0" ] ; then
5642                # We had a good patch download, try applying it now
5643                echo "Updating via patch file..."
5644                pbi_patch "$PBI_UPDLFILE" #>/dev/null 2>/dev/null
5645                if [ "$?" != "0" ] ; then
5646                        # Patching failed, we'll grab a fresh copy next
5647                        echo "Failed to patch with ${_pFile}"
5648                        echo "Will try full file update"
5649                else
5650                        echo "Patch successful!"
5651                        rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating" >/dev/null 2>/dev/null
5652                        rm "${PBI_UPDLFILE}" >/dev/null 2>/dev/null
5653                        return 0
5654                fi
5655                       
5656        fi
5657
5658        # No patch file, grab the full app
5659        echo "Trying update via full-file..."
5660        pbi_update_dl
5661        if [ "$?" != "0" ] ; then
5662                if [ "$_upact" = "single" ] ; then
5663                        rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating"
5664                        exit_err "Failed downloading update!"
5665                fi
5666        fi
5667
5668        echo " "
5669
5670        # Save the auto-update status
5671        if [ -e "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/autoupdate-enable" ] ; then
5672                _autoUpEnable="YES"
5673        else
5674                _autoUpEnable="NO"
5675        fi
5676       
5677        echo -e "Removing old version...\c"
5678        pbi_delete "${PBI_UPDATEAPP}"
5679        echo "Done"
5680
5681        # Now install new PBI
5682        echo -e "Installing new version...\c"
5683        pbi_add --licagree -f "$PBI_UPDLFILE" >/dev/null 2>/dev/null
5684        if [ "$?" != "0" ] ; then
5685                echo "Failed to install PBI: ${PBI_UPDLFILE}"
5686                rm "${PBI_UPDLFILE}"
5687                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating" 2>/dev/null
5688                return 1
5689        else
5690                if [ "$_autoUpEnable" = "YES" ] ; then
5691                        touch "${PBI_DBAPPDIR}/${_pbilow}-${PBI_UPNVER}-${PBI_APPARCH}/autoupdate-enable"
5692                fi
5693                echo "Done"
5694                rm "${PBI_UPDLFILE}"
5695                rm "${PBI_DBAPPDIR}/${PBI_UPDATEAPP}/.updating" 2>/dev/null
5696                return 0
5697        fi     
5698}
5699
5700# Start downloading the update
5701pbi_update_dl() {
5702
5703        _tPatch=$1
5704        local _CKSUM="$2"
5705       
5706        # Set local download location
5707        _dl_loc="${PBI_APPDIR}/.`basename $PBI_UPFILE`"
5708
5709        # Have a patch file to download instead, make that the active file to try
5710        if [ -n "$_tPatch" ] ; then
5711                _bDir=`dirname $PBI_UPFILE`
5712                _uFile="${_bDir}/${_tPatch}"
5713        else
5714                _uFile="${PBI_UPFILE}"
5715        fi
5716
5717        _mirrorList=`echo $PBI_UPMIRROR | sed 's|\n| |g'`
5718
5719        # Start download from repos mirror(s) in order
5720        for _cMirror in $_mirrorList
5721        do
5722                if [ "$_cMirror" = "PCBSDCDN" -o "$_cMirror" = "http://pbi.cdn.pcbsd.org" ] ; then
5723
5724                        # Strip the /PBI from the mirror URL
5725                        _uFile="`echo ${_uFile} | sed 's|^/PBI||g'`"
5726                        if [ -e "$_dl_loc" ] ; then rm "$_dl_loc" ; fi 
5727
5728                        get_file_from_mirrors "${_uFile}" "$_dl_loc" "pbi"
5729                        if [ "$?" != "0" ]  ; then
5730                                rm "${_dl_loc}" >/dev/null 2>/dev/null
5731                                echo "Download Failed: ${_furl}"
5732                                continue
5733                        fi
5734                else
5735                        _furl="`echo $_cMirror | sed 's/\/*$//'`${_uFile}"
5736                        if [ -e "$_dl_loc" ] ; then rm "${_dl_loc}" ; fi       
5737
5738                        echo "Downloading ${_furl}"
5739                        pbi_get_file "$_furl" "$_dl_loc"
5740                        if [ "$?" != "0" ]  ; then
5741                                rm "${_dl_loc}" >/dev/null 2>/dev/null
5742                                echo "Download Failed: ${_furl}"
5743                                continue
5744                        fi
5745                fi
5746                sync
5747                sleep 1
5748                _upcsum=`sha256 -q "$_dl_loc"`
5749                if [ "$_CKSUM" != "OFF" -a "$_upcsum" != "$PBI_UPCSUM" ] ; then
5750                        rm "${_dl_loc}" >/dev/null 2>/dev/null
5751                        echo "Download fails checksum: ${_furl}"
5752                        continue
5753                fi
5754
5755                # If we get this far, we have a good file!
5756                PBI_UPDLFILE="$_dl_loc"
5757                sync
5758                return 0
5759        done
5760
5761        return 1
5762}
5763
5764# Function to download a file from remote using fetch
5765pbi_get_file() {
5766        _rf="${1}"
5767        _lf="${2}"
5768
5769        init_tmpdir
5770        if [ -e "${_lf}" ] ; then
5771                echo "Resuming download of: ${_lf}"
5772        fi
5773
5774        if [ "$PBI_FETCH_PARSING" != "YES" ] ; then
5775                fetch -r -o "${_lf}" "${_rf}"
5776                _err=$?
5777        else
5778                # Doing a front-end download, parse the output of fetch
5779                _eFile="${PBI_TMPDIR}/.fetch-exit.$$"
5780                fetch -s "${_rf}" > ${PBI_TMPDIR}/.fetch-size.$$ 2>/dev/null
5781                _fSize=`cat ${PBI_TMPDIR}/.fetch-size.$$ 2>/dev/null`
5782                _fSize="`expr ${_fSize} / 1024 2>/dev/null`"
5783                rm "${PBI_TMPDIR}/.fetch-size.$$" 2>/dev/null
5784                _time=1
5785
5786                ( fetch -r -o "${_lf}" "${_rf}" >/dev/null 2>/dev/null ; echo "$?" > ${_eFile} ) &
5787                FETCH_PID=`ps -auwwwx | grep -v grep | grep "fetch -r -o ${_lf}" | awk '{print $2}'`
5788                while :
5789                do
5790                        if [ -e "${_lf}" ] ; then
5791                                _dSize=`du -k ${_lf} | tr -d '\t' | cut -d '/' -f 1`
5792                                if [ $(is_num "$_dSize") ] ; then
5793                                        if [ ${_fSize} -lt ${_dSize} ] ; then _dSize="$_fSize" ; fi
5794                                        _kbs=`expr ${_dSize} \/ $_time`
5795                                        echo "SIZE: ${_fSize} DOWNLOADED: ${_dSize} SPEED: ${_kbs} KB/s"
5796                                fi
5797                        fi
5798
5799                        # Make sure download isn't finished
5800                        ps -p $FETCH_PID >/dev/null 2>/dev/null
5801                        if [ "$?" != "0" ] ; then break ; fi
5802                        sleep 2
5803                        _time=`expr $_time + 2`
5804                done
5805
5806                _err="`cat ${_eFile}`"
5807                if [ "$_err" = "0" ]; then echo "FETCHDONE" ; fi
5808                unset FETCH_PID
5809        fi
5810
5811        echo ""
5812        return $_err
5813}
5814
5815is_num()
5816{
5817        expr $1 + 1 2>/dev/null
5818        return $?
5819}
5820
5821# Function to check if the port is flagged to only build on specific arch
5822# Returns 0 for OK, 1 for invalid arch
5823check_port_compat_arch()
5824{
5825        local sPort=$1
5826        have32="false";
5827        local cValues="`make -C $sPort -V ONLY_FOR_ARCHS PORTSDIR=${PORTSDIR}`"
5828        if [ -z "$cValues" ] ; then return 0 ; fi
5829
5830        for cArch in $cValues
5831        do
5832                if [ "$cArch" = "$ARCH" ] ; then return 0; fi
5833                if [ "$cArch" = "i386" ] ; then have32="true" ; fi
5834        done
5835        return 1
5836}
5837
5838# start processing autobuild
5839pbi_autob_init() {
5840
5841        require_root
5842
5843        parse_autob_pbi_cmdline "$@"
5844
5845        do_pbi_autob
5846}
5847
5848check_zfs_ab_destroy()
5849{
5850        local bNum=$1
5851        if [ -e "${PBI_TMPDIR}/${bNum}.zmnt" ] ; then
5852                zDir=`cat ${PBI_TMPDIR}/${bNum}.zmnt`
5853                # Make sure this zfs dataset is in the PBI_APPDIR directory
5854                echo $zDir | grep -q "${PBI_APPDIR}/" 
5855                if [ $? -eq 0 ] ; then
5856                  # Make sure all is unmounted
5857                  umount -f ${PBI_CHROOTDIR}/dev >/dev/null 2>/dev/null
5858                  umount -f ${PBI_CHROOTDIR}/compat/linux/proc >/dev/null 2>/dev/null
5859                  umount -f ${PBI_CHROOTDIR}/usr/ports >/dev/null 2>/dev/null
5860                  umount -f ${PBI_CHROOTDIR}/pkgs >/dev/null 2>/dev/null
5861                  umount -f ${PBI_CHROOTDIR}/.ccache >/dev/null 2>/dev/null
5862                  umount -f ${PBI_CHROOTDIR}/usr/wrkdirprefix >/dev/null 2>/dev/null
5863                  sleep 3
5864                  umount -f ${PBI_CHROOTDIR}/dev >/dev/null 2>/dev/null
5865                  sync
5866                  sleep 3
5867                  zfs destroy -r ${zDir}
5868                  rmdir ${zDir} >/dev/null 2>/dev/null
5869                fi
5870        fi
5871}
5872
5873ab_clean_build_tmpfiles()
5874{
5875        local build=$1
5876
5877        # Cleanup
5878        rm ${PBI_TMPDIR}/${build}.result 2>/dev/null
5879        rm ${PBI_TMPDIR}/${build}.pid 2>/dev/null
5880        rm ${PBI_TMPDIR}/${build}.bPort 2>/dev/null
5881        rm ${PBI_TMPDIR}/${build}.od 2>/dev/null
5882        rm ${PBI_TMPDIR}/${build}.mp 2>/dev/null
5883        rm ${PBI_TMPDIR}/${build}.cd 2>/dev/null
5884        rm ${PBI_TMPDIR}/${build}.pv 2>/dev/null
5885        rm ${PBI_TMPDIR}/${build}.zmnt 2>/dev/null
5886}
5887
5888# Start the auto-build traversal process
5889do_pbi_autob() {
5890
5891        echo "`basename ${0}` started: `date`"
5892
5893        # Prune any outdir files which we don't have modules for
5894        do_pbi_autob_prune
5895
5896        cd "${PBI_AB_CONFDIR}"
5897        init_tmpdir
5898
5899        # Get this runs timestamp
5900        PBI_AB_TIMESTAMP=`date | md5`
5901
5902
5903        # Build our list of targets first
5904        echo "=> Creating build queue list..."
5905        ab_get_build_list
5906
5907        done=0
5908        rebuildlist=0
5909        while :; do
5910          activity=0
5911          # Start checking each job
5912          for build in ${JOBS-$(jot -w %02d ${PBI_AB_BUILDERS})}; do
5913                # Is this builder running?
5914                if [ -e "${PBI_TMPDIR}/${build}.pid" ] ; then
5915                        if pgrep -qF "${PBI_TMPDIR}/${build}.pid" >/dev/null 2>&1; then
5916                                activity=1
5917                                continue;
5918                        else
5919                                # Do the ZFS destroy here if necessary
5920                                check_zfs_ab_destroy "$build"
5921                               
5922                                # Run the post-build process
5923                                ab_post_build ${build}
5924
5925                                # Cleanup
5926                                ab_clean_build_tmpfiles ${build}
5927                        fi
5928                fi
5929                if [ $done -eq 1 ] ; then continue ; fi
5930
5931                # Builder idle, lets figure out the next build
5932                echo "==> Finding target for build process [$build]"
5933                start_next_ab_target "$build"
5934                if [ $? -eq 0 ] ; then 
5935                        # Nothing left to build, lets wait for any existing build to finish before exiting
5936                        done=1
5937                fi
5938                activity=1
5939          done
5940
5941          # Every 2 hours, we can re-scan the modules directory, catch any ones which may have been added / changed
5942          if [ $rebuildlist -eq 7200 ] ; then
5943             rebuildlist=0
5944             ab_get_build_list
5945          else
5946             rebuildlist=`expr $rebuildlist + 1`
5947          fi
5948
5949          # Wait before checking again
5950          [ $activity -eq 1 ] && sleep 1
5951          # Nothing to do? We can end now
5952          [ $activity -eq 0 ] && break
5953        done
5954
5955        echo "`basename ${0}` Finished: `date`"
5956};
5957
5958ab_get_build_list()
5959{
5960
5961   AB_FOUND="0"
5962   unset CUR_PRIORITY_PBI CUR_WORKING_PBI
5963
5964   # Clear the tmp build list
5965   rm ${PBI_TMPDIR}/.ablist 2>/dev/null
5966               
5967   cd "${PBI_AB_CONFDIR}"
5968   for pbi in `find . -type f -name "${PBI_CONFFILE}" | grep -v '\.svn' | sort`
5969   do
5970        # Figure out the target port for this build
5971        unset PBI_MAKEPORT PBI_BUILDKEY PBI_PROGVERSION PBI_REQUIRESROOT PBI_PROGNAME PBI_PROGWEB PBI_PROGAUTHOR PBI_PROGICON PBI_MKPORTBEFORE PBI_MKPORTAFTER PBI_MAKEOPTS PBI_EXCLUDELIST PBI_AB_PRIORITY PBI_HASH_EXCLUDES PBI_AB_NOTMPFS PBI_PROGREVISION
5972        . ${pbi}
5973
5974        _cd=$(dirname $pbi | sed 's|./||')
5975        PBI_CONFDIR="$_cd"
5976
5977        # Make sure PBI_MAKEPORT is set
5978        if [ -z "${PBI_MAKEPORT}" ] ; then
5979                PBI_MAKEPORT=`echo $pbi | sed 's|./||'`
5980                export PBI_MAKEPORT
5981        fi     
5982
5983        if [ ! -d "${PORTSDIR}/${PBI_MAKEPORT}" ] ; then 
5984                #echo "Skipping invalid port ${PORTSDIR}/${PBI_MAKEPORT}"
5985                continue
5986        fi
5987       
5988        # Check if this port can be built on this architecture
5989        check_port_compat_arch "${PORTSDIR}/${PBI_MAKEPORT}"
5990        if [ "$?" = "1" ] ; then
5991           if [ "$PBI_ABFB32" != "YES" ] ; then
5992                echo "${PBI_MAKEPORT} - Skipping for invalid system arch"
5993                continue
5994           fi
5995           if [ "$have32" != "true" ] ; then
5996                echo "${PBI_MAKEPORT} - Skipping for invalid system arch"
5997                continue
5998           fi
5999        fi
6000       
6001        # Check for missing port target
6002        if [ -z "$PBI_MAKEPORT" ] ; then
6003                #echo "Warning: Missing PBI_MAKEPORT for ${pbi}"
6004                continue
6005        fi
6006
6007        # Check if another builder is already doing this port
6008        pBuilding=0
6009        for p in `ls ${PBI_TMPDIR}/*.bPort 2>/dev/null`
6010        do
6011                if [ "`cat $p`" = "$PBI_MAKEPORT" ] ; then
6012                        pBuilding=1
6013                        break
6014                fi
6015        done
6016        if [ $pBuilding -eq 1 ] ; then
6017                continue
6018        fi
6019
6020        check_ab_needed "$PBI_MAKEPORT" "${PBI_BUILDKEY}" "$_cd" "$PBI_AB_TIMESTAMP"
6021        if [ "$?" = "0" ] ; then       
6022           AB_FOUND="1"
6023
6024                   # Unset the priority if set to 00 / 0
6025           if [ "${PBI_AB_PRIORITY}" = "00" -o "${PBI_AB_PRIORITY}" = "0" ] ; then
6026                unset PBI_AB_PRIORITY
6027           fi
6028
6029           # Check the priority of this PBI, see if it rises to the top
6030           if [ -z "${CUR_PRIORITY_PBI}" ] ; then
6031             CUR_WORKING_PBI="${pbi}"
6032             if [ -z "$PBI_AB_PRIORITY" ] ; then
6033                     CUR_PRIORITY_PBI="$internal_ab_priority"
6034             else
6035                     CUR_PRIORITY_PBI=`expr $PBI_AB_PRIORITY + 10`
6036             fi
6037             #echo "Setting higher priority target: ${pbi} - Priority: ${CUR_PRIORITY_PBI}"
6038             echo "${CUR_PRIORITY_PBI} $pbi" >> ${PBI_TMPDIR}/.abtmp
6039             continue
6040           fi
6041
6042           # Bump up the supplied AB priority
6043           if [ -n "${PBI_AB_PRIORITY}" ] ; then
6044              internal_ab_priority=`expr $PBI_AB_PRIORITY + 10`
6045           fi
6046
6047           # Check if this PBI is a higher priority
6048           if [ $CUR_PRIORITY_PBI -lt $internal_ab_priority ] ; then
6049             #echo "Setting higher priority target: ${pbi} - Priority: ${internal_ab_priority}"
6050             CUR_WORKING_PBI="${pbi}"
6051             CUR_PRIORITY_PBI="$internal_ab_priority"
6052             echo "${internal_ab_priority} $pbi" >> ${PBI_TMPDIR}/.abtmp
6053             continue
6054           else
6055             echo "${internal_ab_priority} $pbi" >> ${PBI_TMPDIR}/.abtmp
6056           fi
6057           continue
6058         fi
6059
6060  done
6061
6062  # Sort the list
6063  if [ -e "${PBI_TMPDIR}/.abtmp" ] ; then
6064    sort -n -r ${PBI_TMPDIR}/.abtmp > ${PBI_TMPDIR}/.ablist
6065    rm ${PBI_TMPDIR}/.abtmp
6066  fi
6067}
6068
6069start_next_ab_target()
6070{
6071  local curBuilder="$1"
6072  # No list to parse?
6073  if [ ! -e "${PBI_TMPDIR}/.ablist" ] ; then return 0; fi
6074
6075  # Get the last on the list
6076  CUR_WORKING_PBI=`cat ${PBI_TMPDIR}/.ablist | head -1 | cut -d ' ' -f 2`
6077  if [ -z "${CUR_WORKING_PBI}" ] ; then return 0; fi
6078
6079  cd "${PBI_AB_CONFDIR}"
6080
6081  # We have something to build lets do it!
6082  pbi="$CUR_WORKING_PBI"
6083  unset PBI_MAKEPORT PBI_BUILDKEY PBI_PROGVERSION PBI_REQUIRESROOT PBI_PROGNAME PBI_PROGWEB PBI_PROGAUTHOR PBI_PROGICON PBI_MKPORTBEFORE PBI_MKPORTAFTER PBI_MAKEOPTS PBI_EXCLUDELIST PBI_AB_PRIORITY PBI_HASH_EXCLUDES PBI_AB_NOTMPFS PBI_PROGREVISION
6084  . ${pbi}
6085
6086  _cd=$(dirname $pbi | sed 's|./||')
6087  PBI_CONFDIR="$_cd"
6088
6089  # Get the prog version
6090  get_pbi_progversion
6091
6092  if [ -z "${PBI_MAKEPORT}" ] ; then
6093     PBI_MAKEPORT=$(dirname $pbi | sed 's|./||')
6094  fi   
6095
6096  echo "==> Starting build process [$curBuilder]: $PBI_MAKEPORT"
6097  echo "$PBI_MAKEPORT" >${PBI_TMPDIR}/${curBuilder}.bPort
6098
6099  # Remove this from the queue
6100  cat ${PBI_TMPDIR}/.ablist | tail -n +2 > ${PBI_TMPDIR}/.abtmp
6101  mv ${PBI_TMPDIR}/.abtmp ${PBI_TMPDIR}/.ablist
6102
6103  # Start the build now
6104  start_ext_ab "$PBI_MAKEPORT" \
6105  "${PBI_BUILDKEY}" "${PBI_PROGVERSION}" \
6106  "${_cd}" "${PBI_AB_OUTDIR}" "${PBI_AB_TIMESTAMP}" "${curBuilder}"
6107
6108  return 1
6109};
6110
6111# Prune any outdir files which don't have matching modules
6112do_pbi_autob_prune() {
6113        if [ "${PBI_AB_PRUNE}" != "YES" ] ; then return 0 ; fi
6114
6115        echo "=> Cleaning outgoing directory..."
6116        # Prune outgoing dirs which don't have matching modules anymore
6117        cd "${PBI_AB_OUTDIR}"
6118        for i in `find . -type d | grep -v '\.svn'`
6119        do
6120                if [ "${i}" = "." -o "${i}" = ".." ] ; then continue ; fi
6121                _pDir=`dirname ${i}`
6122                if [ -d "${i}" -a -n "${i}" ] ; then
6123                        if [ ! -e "${PBI_AB_CONFDIR}/${_pDir}" ] ; then
6124                        # Not in our module tree anymore, remove it
6125                        echo "Auto-Prune: ${PBI_AB_OUTDIR}/${_pDir}"
6126                        rm -rf "${PBI_AB_OUTDIR}/${_pDir}"
6127                        fi
6128                fi
6129        done
6130        cd
6131}
6132
6133# Start the pbi_makeport process
6134start_ext_ab() {
6135        _mp="${1}"
6136        _bk="${2}"
6137        _pv="${3}"
6138        _cd="${4}"
6139        _od="${5}/${_cd}"
6140        local _abkey="$6"
6141        local eBuilder="$7"
6142        _flags=""
6143        _flags="-c ${_cd} -d ${PORTSDIR} -o ${_od} --delbuild"
6144        if [ -n "${PBI_AB_SSLPRIVKEY}" ] ; then
6145                _flags="${_flags} --sign ${PBI_AB_SSLPRIVKEY}"
6146        fi
6147
6148        # Check if we need to enable tmpfs
6149        if [ "$PBI_AB_TMPFS" = "YES" ] ; then
6150                if [ -z "${PBI_AB_NOTMPFS}" -o "$PBI_AB_NOTMPFS" != "YES" ] ; then
6151                        _flags="${_flags} --tmpfs"
6152                fi
6153        fi
6154
6155        # Check if we need to enable pkgbuilding
6156        if [ "$PBI_AB_PKGBUILD" = "YES" -a -z "$PBI_AB_NOPKGBUILD"  ] ; then
6157                _flags="${_flags} --pkgbuild"
6158        fi
6159
6160        # Are we doing 32bit builds?
6161        if [ "$PBI_AB32" = "YES" ] ; then _flags="${_flags} -32"; fi
6162
6163        # Check if this port can be built on this architecture
6164        check_port_compat_arch "${PORTSDIR}/${_mp}"
6165        if [ $? -ne 0 ] ; then
6166           if [ "$PBI_ABFB32" = "YES" -a "$have32" = "true" ] ; then
6167              _flags="${_flags} -32"
6168           fi
6169        fi
6170
6171        get_pbi_progversion
6172
6173        #echo "Starting build of ${_mp} - ${_pv}"
6174        #echo "pbi_makeport ${_flags} ${_mp}"
6175
6176        if [ ! -d "${_od}" ] ; then mkdir -p "${_od}" ; fi
6177
6178        # Save the autobuild hash key
6179        echo "$_abkey" > ${_od}/.abkey
6180       
6181        # Save the build key for this PBI
6182        if [ -n "$_bk" ] ; then
6183                echo "$_bk" > "${_od}/pbi-buildkey"
6184        else
6185                echo "__NONE__" > "${_od}/pbi-buildkey"
6186        fi
6187
6188        # Clean old log files
6189        if [ -e "${_od}/build.log" ] ; then
6190                rm "${_od}/build.log"
6191        fi
6192        if [ -e "${_od}/build.log.bz2" ] ; then
6193                rm "${_od}/build.log.bz2"
6194        fi
6195        if [ -e "${_od}/.failed-csum" ] ; then
6196                rm ${_od}/.failed-csum
6197        fi
6198
6199        # Move old PBIs to archived folder
6200        oldVersion=`cat ${_od}/pbi-version 2>/dev/null`
6201        if [ "$oldVersion" != "$PBI_PROGVERSION" ]; then
6202                #echo "Archiving old PBIs..."
6203                archive_old_pbis "${_od}" "$PBI_AB_ARCHIVENUM"
6204        fi
6205
6206        # Set some variables we can call in pbi_makeport
6207        PBI_AB_TMPDIR="${PBI_TMPDIR}"
6208        PBI_AB_BUILDER="$eBuilder"
6209        export PBI_AB_TMPDIR PBI_AB_BUILDER
6210
6211        # Add some header info to log file
6212        echo "Starting build: `date`" >${_od}/build.log
6213        echo "Build Command:" >>${_od}/build.log
6214        echo "pbi_makeport ${_flags} ${_mp}" >>${_od}/build.log
6215        echo "------------------------------------------------------" >>${_od}/build.log
6216       
6217        echo "${_od}" > "${PBI_TMPDIR}/${PBI_AB_BUILDER}.od"
6218        echo "${_mp}" > "${PBI_TMPDIR}/${PBI_AB_BUILDER}.mp"
6219        echo "${_cd}" > "${PBI_TMPDIR}/${PBI_AB_BUILDER}.cd"
6220        echo "${PBI_PROGVERSION}" > "${PBI_TMPDIR}/${PBI_AB_BUILDER}.pv"
6221        pbi_makeport ${_flags} ${_mp} >>${_od}/build.log 2>>${_od}/build.log &
6222        echo "$!" > ${PBI_TMPDIR}/${eBuilder}.pid
6223
6224}
6225
6226ab_post_build() 
6227{
6228        local build=$1
6229        _od="`cat ${PBI_TMPDIR}/${build}.od`"
6230        _mp="`cat ${PBI_TMPDIR}/${build}.mp`"
6231        _cd="`cat ${PBI_TMPDIR}/${build}.cd`"
6232        _pv="`cat ${PBI_TMPDIR}/${build}.pv`"
6233        sleep 1
6234
6235        if [ -e "${PBI_TMPDIR}/${build}.result" -a "`cat ${PBI_TMPDIR}/${build}.result`" = "0" ] ; then
6236                echo "$_pv" > "${_od}/pbi-version"
6237                echo "OK" > "${_od}/pbi-result"
6238
6239                # Save the mdate file
6240                date "+%Y%m%d %H%M%S" >${_od}/pbi-mdate
6241
6242                if [ -n "${PBI_AB_HELPS}" ] ; then
6243                        ${PBI_AB_HELPS} "OK" "${_od}"
6244                fi
6245
6246                # Copy over a description file
6247                if [ -e "${PORTSDIR}/${_mp}/pkg-descr" ] ; then
6248                        cp "${PORTSDIR}/${_mp}/pkg-descr" "${_od}/pbi-descr"
6249                fi
6250                if [ -e "${PBI_AB_CONFDIR}/${_cd}/pbi-descr" ] ; then
6251                        cp "${PBI_AB_CONFDIR}/${_cd}/pbi-descr" "${_od}/pbi-descr"
6252                fi
6253
6254                # Check if we need to rebuild patches
6255                if [ "$PBI_AB_GENPATCH" = "YES" -a -d "${_od}/archived" ] ; then
6256                        echo "===> Generating patches for [$build]"
6257                        gen_pbi_patches "${_od}" "${_od}/archived"
6258                fi
6259
6260                rm "${_od}/build.log.bz2" >/dev/null 2>/dev/null
6261                bzip2 "${_od}/build.log"
6262
6263        else
6264                # Save the md5sum of the ports directory
6265                tar cvf - -C "${PORTSDIR}/${_mp}" . 2>/dev/null | md5 -q >${_od}/.failed-csum
6266
6267                echo "Failed" > "${_od}/pbi-result"
6268                if [ -n "${PBI_AB_HELPS}" ] ; then
6269                        ${PBI_AB_HELPS} "FAILED" "${_od}"
6270                fi
6271        fi
6272
6273}
6274
6275# Function which begins to generate patch files from archived PBIs to current
6276gen_pbi_patches()
6277{
6278        _curPBIdir="$1"
6279        _oldPBIdir="$2"
6280
6281        _curPBI=`ls ${_curPBIdir}/*.pbi 2>/dev/null`
6282
6283        # First remove any old patches
6284        rm ${_curPBIdir}/*.pbp 2>/dev/null
6285        rm ${_curPBIdir}/*.pbp.sha256 2>/dev/null
6286
6287        # Make sure to enable signing of the patch files
6288        if [ -n "${PBI_AB_SSLPRIVKEY}" ] ; then
6289                local _mpflags="-o $_curPBIdir --sign ${PBI_AB_SSLPRIVKEY}"
6290        else
6291                local _mpflags="-o $_curPBIdir"
6292        fi
6293
6294        # Check if we need to enable tmpfs
6295        if [ "$PBI_AB_TMPFS" = "YES" ] ; then _mpflags="${_mpflags} --tmpfs" ; fi
6296
6297        # Build a list of old PBIs we need to make patches from
6298        for _oPBI in `ls ${_oldPBIdir}/*.pbi 2>/dev/null`
6299        do
6300                # Make sure we don't try to make a patch of identical files
6301                if [ "`basename $_oPBI`" != "`basename $_curPBI`" ] ; then     
6302                        #echo "Building pbp patch of ${_oPBI} -> ${_curPBI}"
6303                        pbi_makepatch $_mpflags "$_oPBI" "$_curPBI" >/dev/null 2>/dev/null
6304                        if [ "$?" != "0" ] ; then
6305                                echo "pbi_makepatch: Failed creating patchfile for $_oPBI -> $_curPBI"
6306                        fi
6307                       
6308                fi
6309        done
6310}
6311
6312# Function which compares two PBIs, and creates a .pbp file from the differences
6313make_pbi_patchfile()
6314{
6315        _pbiNew="$1"
6316        _pbiOld="$2"
6317        _cDir="$3"
6318
6319        init_tmpdir
6320
6321        # Load all the information about this PBI / PBP
6322        PBI_FILENAME="$1"
6323        load_info_from_header
6324
6325        _pbiNewDir="${PBI_APPDIR}/.newPBI-$$"
6326        _pbiOldDir="${PBI_APPDIR}/.oldPBI-$$"
6327        _pbiPatchDir="${PBI_APPDIR}/.patchPBI-$$"
6328        _pbiPatchHeaderDir="${PBI_APPDIR}/.patchPBIHeaderDir-$$"
6329        _pbiPatchArchiveFile="${PBI_APPDIR}/.patchPBIArchive-$$"
6330        _pbiPatchHeaderFile="${PBI_APPDIR}/.patchPBIHeaderFile-$$"
6331
6332        # Get the PBI Versions
6333        get_ver_from_pbi_file "$_pbiNew"
6334        _pbiNewVer="$VAL"
6335        get_ver_from_pbi_file "$_pbiOld"
6336        _pbiOldVer="$VAL"
6337
6338        # Get the PBI directory names
6339        get_prefix_from_pbi_file "$_pbiNew"
6340        _pbiNewPrefix="`basename $VAL`"
6341        get_prefix_from_pbi_file "$_pbiOld"
6342        _pbiOldPrefix="`basename $VAL`"
6343
6344        # Get the mdate of the old PBI
6345        get_mdate_from_pbi_file "$_pbiOld"
6346        _pbiOldMDate="$VAL"
6347
6348        # Sanity check these prefixes
6349        if [ "${_pbiNewPrefix}" != "${_pbiOldPrefix}" ] ; then
6350                echo "Error: Prefix mismatch between $_pbiNew and $_pbiOld"
6351                return
6352        fi
6353
6354        # Get the arch type
6355        get_arch_from_pbi_file "$_pbiNew"
6356        _pbiNewArch="$VAL"
6357        get_arch_from_pbi_file "$_pbiOld"
6358        _pbiOldArch="$VAL"
6359
6360        # Sanity check these system types
6361        if [ "${_pbiNewArch}" != "${_pbiOldArch}" ] ; then
6362                echo "Error: Arch mismatch between $_pbiNew and $_pbiOld"
6363                return
6364        fi
6365
6366        # Make our extraction directories
6367        if [ -e "$_pbiNewDir" ] ; then rm -rf "$_pbiNewDir"; fi
6368        if [ -e "$_pbiOldDir" ] ; then rm -rf "$_pbiOldDir"; fi
6369        if [ -e "$_pbiPatchDir" ] ; then rm -rf "$_pbiPatchDir"; fi
6370        mkdir -p "$_pbiNewDir"
6371        mkdir -p "$_pbiOldDir"
6372        mkdir -p "$_pbiPatchDir"
6373
6374        # If using tmpfs to speed up patch process
6375        if [ "$PBI_MP_TMPFS" = "YES" ] ; then
6376                mount -t tmpfs tmpfs "${_pbiNewDir}"
6377                mount -t tmpfs tmpfs "${_pbiOldDir}"
6378                mount -t tmpfs tmpfs "${_pbiPatchDir}"
6379        fi
6380
6381        local _opts="-e --licagree"
6382        if [ "${PBI_SKIPSIGVERIFY}" = "YES" ] ; then
6383                _opts="${_opts} --no-checksig"
6384        fi
6385
6386        # Extract the two PBIs
6387        echo "Extracting PBI: $_pbiNew"
6388        pbi_add ${_opts} -o "${_pbiNewDir}" "${_pbiN