~ubuntu-branches/ubuntu/precise/rpm/precise-proposed

« back to all changes in this revision

Viewing changes to lib/rpmts.c

  • Committer: Bazaar Package Importer
  • Author(s): Michal Čihař
  • Date: 2010-06-28 11:12:30 UTC
  • mfrom: (17.2.5 sid)
  • Revision ID: james.westby@ubuntu.com-20100628111230-8ggjjhgpvrnr3ybx
Tags: 4.8.1-5
Fix compilation on hurd and kfreebsd (Closes: #587366).

Show diffs side-by-side

added added

removed removed

Lines of Context:
15
15
#include <rpm/rpmkeyring.h>
16
16
 
17
17
#include <rpm/rpmdb.h>
18
 
#include <rpm/rpmal.h>
19
18
#include <rpm/rpmds.h>
20
19
#include <rpm/rpmfi.h>
21
20
#include <rpm/rpmlog.h>
22
21
#include <rpm/rpmte.h>
23
22
 
24
23
#include "rpmio/digest.h"
 
24
#include "lib/rpmal.h"
25
25
#include "lib/rpmlock.h"
26
26
#include "lib/rpmts_internal.h"
27
27
#include "lib/misc.h"
28
28
 
29
 
/* XXX FIXME: merge with existing (broken?) tests in system.h */
30
 
/* portability fiddles */
31
 
#if STATFS_IN_SYS_STATVFS
32
 
#include <sys/statvfs.h>
33
 
 
34
 
#else
35
 
# if STATFS_IN_SYS_VFS
36
 
#  include <sys/vfs.h>
37
 
# else
38
 
#  if STATFS_IN_SYS_MOUNT
39
 
#   include <sys/mount.h>
40
 
#  else
41
 
#   if STATFS_IN_SYS_STATFS
42
 
#    include <sys/statfs.h>
43
 
#   endif
44
 
#  endif
45
 
# endif
46
 
#endif
47
 
 
48
29
#include "debug.h"
49
30
 
50
31
static void loadKeyring(rpmts ts);
249
230
        if (ts->keyring == NULL && autoload) {
250
231
            loadKeyring(ts);
251
232
        }
252
 
        keyring = ts->keyring;
 
233
        keyring = rpmKeyringLink(ts->keyring);
253
234
    }
254
 
    return rpmKeyringLink(keyring);
 
235
    return keyring;
255
236
}
256
237
 
257
238
int rpmtsSetKeyring(rpmts ts, rpmKeyring keyring)
321
302
            if (b64decode(key, (void **) &pkt, &pktlen) == 0) {
322
303
                rpmPubkey key = rpmPubkeyNew(pkt, pktlen);
323
304
                if (rpmKeyringAddKey(ts->keyring, key) == 0) {
324
 
                    char *nvr = headerGetNEVR(h, NULL);
 
305
                    char *nvr = headerGetAsString(h, RPMTAG_NVR);
325
306
                    rpmlog(RPMLOG_DEBUG, "added key %s to keyring\n", nvr);
326
307
                    free(nvr);
327
308
                    nkeys++;
631
612
    return ovsflags;
632
613
}
633
614
 
634
 
int rpmtsUnorderedSuccessors(rpmts ts, int first)
635
 
{
636
 
    int unorderedSuccessors = 0;
637
 
    if (ts != NULL) {
638
 
        unorderedSuccessors = ts->unorderedSuccessors;
639
 
        if (first >= 0)
640
 
            ts->unorderedSuccessors = first;
641
 
    }
642
 
    return unorderedSuccessors;
643
 
}
644
 
 
645
615
const char * rpmtsRootDir(rpmts ts)
646
616
{
647
617
    const char * rootDir = NULL;
675
645
    ts->rootDir = _free(ts->rootDir);
676
646
    /* Ensure clean path with a trailing slash */
677
647
    ts->rootDir = rootDir ? rpmGetPath(rootDir, NULL) : xstrdup("/");
678
 
    if (strcmp(ts->rootDir, "/") != 0) {
 
648
    if (!rstreq(ts->rootDir, "/")) {
679
649
        rstrcat(&ts->rootDir, "/");
680
650
    }
681
651
    return 0;
772
742
    return rdb;
773
743
}
774
744
 
775
 
int rpmtsInitDSI(const rpmts ts)
776
 
{
777
 
    rpmDiskSpaceInfo dsi;
778
 
    struct stat sb;
779
 
    int rc;
780
 
    int i;
781
 
 
782
 
    if (rpmtsFilterFlags(ts) & RPMPROB_FILTER_DISKSPACE)
783
 
        return 0;
784
 
 
785
 
    rpmlog(RPMLOG_DEBUG, "mounted filesystems:\n");
786
 
    rpmlog(RPMLOG_DEBUG,
787
 
        "    i        dev    bsize       bavail       iavail mount point\n");
788
 
 
789
 
    rc = rpmGetFilesystemList(&ts->filesystems, &ts->filesystemCount);
790
 
    if (rc || ts->filesystems == NULL || ts->filesystemCount <= 0)
791
 
        return rc;
792
 
 
793
 
    /* Get available space on mounted file systems. */
794
 
 
795
 
    ts->dsi = _free(ts->dsi);
796
 
    ts->dsi = xcalloc((ts->filesystemCount + 1), sizeof(*ts->dsi));
797
 
 
798
 
    dsi = ts->dsi;
799
 
 
800
 
    if (dsi != NULL)
801
 
    for (i = 0; (i < ts->filesystemCount) && dsi; i++, dsi++) {
802
 
#if STATFS_IN_SYS_STATVFS
803
 
        struct statvfs sfb;
804
 
        memset(&sfb, 0, sizeof(sfb));
805
 
        rc = statvfs(ts->filesystems[i], &sfb);
806
 
#else
807
 
        struct statfs sfb;
808
 
        memset(&sfb, 0, sizeof(sfb));
809
 
#  if STAT_STATFS4
810
 
/* This platform has the 4-argument version of the statfs call.  The last two
811
 
 * should be the size of struct statfs and 0, respectively.  The 0 is the
812
 
 * filesystem type, and is always 0 when statfs is called on a mounted
813
 
 * filesystem, as we're doing.
814
 
 */
815
 
        rc = statfs(ts->filesystems[i], &sfb, sizeof(sfb), 0);
816
 
#  else
817
 
        rc = statfs(ts->filesystems[i], &sfb);
818
 
#  endif
819
 
#endif
820
 
        if (rc)
821
 
            break;
822
 
 
823
 
        rc = stat(ts->filesystems[i], &sb);
824
 
        if (rc)
825
 
            break;
826
 
        dsi->dev = sb.st_dev;
827
 
 
828
 
        dsi->bsize = sfb.f_bsize;
829
 
        dsi->bneeded = 0;
830
 
        dsi->ineeded = 0;
831
 
#ifdef STATFS_HAS_F_BAVAIL
832
 
        dsi->bavail = (sfb.f_flag & ST_RDONLY) ? 0 : sfb.f_bavail;
833
 
#else
834
 
/* FIXME: the statfs struct doesn't have a member to tell how many blocks are
835
 
 * available for non-superusers.  f_blocks - f_bfree is probably too big, but
836
 
 * it's about all we can do.
837
 
 */
838
 
        dsi->bavail = sfb.f_blocks - sfb.f_bfree;
839
 
#endif
840
 
        /* XXX Avoid FAT and other file systems that have not inodes. */
841
 
        /* XXX assigning negative value to unsigned type */
842
 
        dsi->iavail = !(sfb.f_ffree == 0 && sfb.f_files == 0)
843
 
                                ? sfb.f_ffree : -1;
844
 
        rpmlog(RPMLOG_DEBUG, 
845
 
                "%5d 0x%08x %8" PRId64 " %12" PRId64 " %12" PRId64" %s\n",
846
 
                i, (unsigned) dsi->dev, dsi->bsize,
847
 
                dsi->bavail, dsi->iavail,
848
 
                ts->filesystems[i]);
849
 
    }
850
 
    return rc;
851
 
}
852
 
 
853
 
void rpmtsUpdateDSI(const rpmts ts, dev_t dev,
854
 
                rpm_loff_t fileSize, rpm_loff_t prevSize, rpm_loff_t fixupSize,
855
 
                rpmFileAction action)
856
 
{
857
 
    rpmDiskSpaceInfo dsi;
858
 
    int64_t bneeded;
859
 
 
860
 
    dsi = ts->dsi;
861
 
    if (dsi) {
862
 
        while (dsi->bsize && dsi->dev != dev)
863
 
            dsi++;
864
 
        if (dsi->bsize == 0)
865
 
            dsi = NULL;
866
 
    }
867
 
    if (dsi == NULL)
868
 
        return;
869
 
 
870
 
    bneeded = BLOCK_ROUND(fileSize, dsi->bsize);
871
 
 
872
 
    switch (action) {
873
 
    case FA_BACKUP:
874
 
    case FA_SAVE:
875
 
    case FA_ALTNAME:
876
 
        dsi->ineeded++;
877
 
        dsi->bneeded += bneeded;
878
 
        break;
879
 
 
880
 
    /*
881
 
     * FIXME: If two packages share a file (same md5sum), and
882
 
     * that file is being replaced on disk, will dsi->bneeded get
883
 
     * adjusted twice? Quite probably!
884
 
     */
885
 
    case FA_CREATE:
886
 
        dsi->bneeded += bneeded;
887
 
        dsi->bneeded -= BLOCK_ROUND(prevSize, dsi->bsize);
888
 
        break;
889
 
 
890
 
    case FA_ERASE:
891
 
        dsi->ineeded--;
892
 
        dsi->bneeded -= bneeded;
893
 
        break;
894
 
 
895
 
    default:
896
 
        break;
897
 
    }
898
 
 
899
 
    if (fixupSize)
900
 
        dsi->bneeded -= BLOCK_ROUND(fixupSize, dsi->bsize);
901
 
}
902
 
 
903
 
void rpmtsCheckDSIProblems(const rpmts ts, const rpmte te)
904
 
{
905
 
    rpmDiskSpaceInfo dsi;
906
 
    rpmps ps;
907
 
    int fc;
908
 
    int i;
909
 
 
910
 
    if (ts->filesystems == NULL || ts->filesystemCount <= 0)
911
 
        return;
912
 
 
913
 
    dsi = ts->dsi;
914
 
    if (dsi == NULL)
915
 
        return;
916
 
    fc = rpmfiFC(rpmteFI(te));
917
 
    if (fc <= 0)
918
 
        return;
919
 
 
920
 
    ps = rpmtsProblems(ts);
921
 
    for (i = 0; i < ts->filesystemCount; i++, dsi++) {
922
 
 
923
 
        if (dsi->bavail >= 0 && adj_fs_blocks(dsi->bneeded) > dsi->bavail) {
924
 
            if (dsi->bneeded != dsi->obneeded) {
925
 
                rpmpsAppend(ps, RPMPROB_DISKSPACE,
926
 
                        rpmteNEVRA(te), rpmteKey(te),
927
 
                        ts->filesystems[i], NULL, NULL,
928
 
                   (adj_fs_blocks(dsi->bneeded) - dsi->bavail) * dsi->bsize);
929
 
                dsi->obneeded = dsi->bneeded;
930
 
            }
931
 
        }
932
 
 
933
 
        if (dsi->iavail >= 0 && adj_fs_blocks(dsi->ineeded) > dsi->iavail) {
934
 
            if (dsi->ineeded != dsi->oineeded) {
935
 
                rpmpsAppend(ps, RPMPROB_DISKNODES,
936
 
                        rpmteNEVRA(te), rpmteKey(te),
937
 
                        ts->filesystems[i], NULL, NULL,
938
 
                        (adj_fs_blocks(dsi->ineeded) - dsi->iavail));
939
 
                dsi->oineeded = dsi->ineeded;
940
 
            }
941
 
        }
942
 
    }
943
 
    ps = rpmpsFree(ps);
944
 
}
945
 
 
946
745
void * rpmtsNotify(rpmts ts, rpmte te,
947
746
                rpmCallbackType what, rpm_loff_t amount, rpm_loff_t total)
948
747
{
1034
833
    return (ts != NULL ? ts->prefcolor : 0);
1035
834
}
1036
835
 
 
836
rpm_color_t rpmtsSetPrefColor(rpmts ts, rpm_color_t color)
 
837
{
 
838
    rpm_color_t ocolor = 0;
 
839
    if (ts != NULL) {
 
840
        ocolor = ts->prefcolor;
 
841
        ts->prefcolor = color;
 
842
    }
 
843
    return ocolor;
 
844
}
 
845
 
1037
846
rpmop rpmtsOp(rpmts ts, rpmtsOpX opx)
1038
847
{
1039
848
    rpmop op = NULL;
1053
862
    return 0;
1054
863
}
1055
864
 
1056
 
int rpmtsGetKeys(const rpmts ts, fnpyKey ** ep, int * nep)
1057
 
{
1058
 
    int rc = 0;
1059
 
 
1060
 
    if (nep) *nep = ts->orderCount;
1061
 
    if (ep) {
1062
 
        rpmtsi pi;      rpmte p;
1063
 
        fnpyKey * e;
1064
 
 
1065
 
        *ep = e = xmalloc(ts->orderCount * sizeof(*e));
1066
 
        pi = rpmtsiInit(ts);
1067
 
        while ((p = rpmtsiNext(pi, 0)) != NULL) {
1068
 
            switch (rpmteType(p)) {
1069
 
            case TR_ADDED:
1070
 
                *e = rpmteKey(p);
1071
 
                break;
1072
 
            case TR_REMOVED:
1073
 
            default:
1074
 
                *e = NULL;
1075
 
                break;
1076
 
            }
1077
 
            e++;
1078
 
        }
1079
 
        pi = rpmtsiFree(pi);
1080
 
    }
1081
 
    return rc;
1082
 
}
1083
 
 
1084
865
rpmts rpmtsCreate(void)
1085
866
{
1086
867
    rpmts ts;
1088
869
    ts = xcalloc(1, sizeof(*ts));
1089
870
    memset(&ts->ops, 0, sizeof(ts->ops));
1090
871
    (void) rpmswEnter(rpmtsOp(ts, RPMTS_OP_TOTAL), -1);
1091
 
    ts->filesystemCount = 0;
1092
 
    ts->filesystems = NULL;
1093
872
    ts->dsi = NULL;
1094
873
 
1095
874
    ts->solve = NULL;
1119
898
            argvSplit(&langs, tmp, ":");        
1120
899
            /* If we'll be installing all languages anyway, don't bother */
1121
900
            for (ARGV_t l = langs; *l; l++) {
1122
 
                if (strcmp(*l, "all") == 0) {
 
901
                if (rstreq(*l, "all")) {
1123
902
                    langs = argvFree(langs);
1124
903
                    break;
1125
904
                }