Main Page   Modules   Compound List   File List   Compound Members   File Members   Related Pages  

lib/package.c

Go to the documentation of this file.
00001 
00005 #include "system.h"
00006 
00007 #if !defined(__LCLINT__)
00008 #include <netinet/in.h>
00009 #endif  /* __LCLINT__ */
00010 
00011 #include <rpmlib.h>
00012 
00013 #include "misc.h"
00014 #include "rpmlead.h"
00015 #include "signature.h"
00016 #include "debug.h"
00017 
00018 #define alloca_strdup(_s)       strcpy(alloca(strlen(_s)+1), (_s))
00019 
00020 /*@access Header@*/             /* XXX compared with NULL */
00021 
00022 void headerMergeLegacySigs(Header h, const Header sig)
00023 {
00024     HeaderIterator hi;
00025     int_32 tag, type, count;
00026     const void * ptr;
00027 
00028     for (hi = headerInitIterator(sig);
00029         headerNextIterator(hi, &tag, &type, &ptr, &count);
00030         ptr = headerFreeData(ptr, type))
00031     {
00032         if (tag < RPMSIGTAG_SIZE)
00033             continue;
00034         switch (tag) {
00035         case RPMSIGTAG_SIZE:    tag = RPMTAG_SIGSIZE;   break;
00036         case RPMSIGTAG_LEMD5_1: tag = RPMTAG_SIGLEMD5_1;break;
00037         case RPMSIGTAG_PGP:     tag = RPMTAG_SIGPGP;    break;
00038         case RPMSIGTAG_LEMD5_2: tag = RPMTAG_SIGLEMD5_2;break;
00039         case RPMSIGTAG_MD5:     tag = RPMTAG_SIGMD5;    break;
00040         case RPMSIGTAG_GPG:     tag = RPMTAG_SIGGPG;    break;
00041         case RPMSIGTAG_PGP5:    tag = RPMTAG_SIGPGP5;   break;
00042         default:                                        break;
00043         }
00044         if (!headerIsEntry(h, tag))
00045             headerAddEntry(h, tag, type, ptr, count);
00046     }
00047     headerFreeIterator(hi);
00048 }
00049 
00058 static int readPackageHeaders(FD_t fd, /*@out@*/ struct rpmlead * leadPtr, 
00059                               /*@out@*/ Header * sigs, /*@out@*/ Header *hdrPtr)
00060         /*@modifies fd, *leadPtr, *sigs, *hdrPtr @*/
00061 {
00062     Header hdrBlock;
00063     struct rpmlead leadBlock;
00064     Header * hdr = NULL;
00065     struct rpmlead * lead;
00066     char * defaultPrefix;
00067     struct stat sb;
00068     int_32 true = 1;
00069 
00070     hdr = hdrPtr ? hdrPtr : &hdrBlock;
00071     lead = leadPtr ? leadPtr : &leadBlock;
00072 
00073     fstat(Fileno(fd), &sb);
00074     /* if fd points to a socket, pipe, etc, sb.st_size is *always* zero */
00075     if (S_ISREG(sb.st_mode) && sb.st_size < sizeof(*lead)) return 1;
00076 
00077     if (readLead(fd, lead))
00078         return 2;
00079 
00080     if (lead->magic[0] != RPMLEAD_MAGIC0 || lead->magic[1] != RPMLEAD_MAGIC1 ||
00081         lead->magic[2] != RPMLEAD_MAGIC2 || lead->magic[3] != RPMLEAD_MAGIC3) {
00082         return 1;
00083     }
00084 
00085     switch (lead->major) {
00086     case 1:
00087         rpmError(RPMERR_NEWPACKAGE,
00088             _("packaging version 1 is not supported by this version of RPM\n"));
00089         return 2;
00090         /*@notreached@*/ break;
00091     case 2:
00092     case 3:
00093     case 4:
00094         if (rpmReadSignature(fd, sigs, lead->signature_type))
00095             return 2;
00096         *hdr = headerRead(fd, (lead->major >= 3)
00097                           ? HEADER_MAGIC_YES : HEADER_MAGIC_NO);
00098         if (*hdr == NULL) {
00099             if (sigs != NULL)
00100                 headerFree(*sigs);
00101             return 2;
00102         }
00103 
00104         /* We don't use these entries (and rpm >= 2 never have) and they are
00105            pretty misleading. Let's just get rid of them so they don't confuse
00106            anyone. */
00107         if (headerIsEntry(*hdr, RPMTAG_FILEUSERNAME))
00108             headerRemoveEntry(*hdr, RPMTAG_FILEUIDS);
00109         if (headerIsEntry(*hdr, RPMTAG_FILEGROUPNAME))
00110             headerRemoveEntry(*hdr, RPMTAG_FILEGIDS);
00111 
00112         /* We switched the way we do relocateable packages. We fix some of
00113            it up here, though the install code still has to be a bit 
00114            careful. This fixup makes queries give the new values though,
00115            which is quite handy. */
00116         if (headerGetEntry(*hdr, RPMTAG_DEFAULTPREFIX, NULL,
00117                            (void **) &defaultPrefix, NULL)) {
00118             defaultPrefix =
00119                 stripTrailingChar(alloca_strdup(defaultPrefix), '/');
00120             headerAddEntry(*hdr, RPMTAG_PREFIXES, RPM_STRING_ARRAY_TYPE,
00121                            &defaultPrefix, 1); 
00122         }
00123 
00124         /* The file list was moved to a more compressed format which not
00125            only saves memory (nice), but gives fingerprinting a nice, fat
00126            speed boost (very nice). Go ahead and convert old headers to
00127            the new style (this is a noop for new headers) */
00128         if (lead->major < 4)
00129             compressFilelist(*hdr);
00130 
00131     /* XXX binary rpms always have RPMTAG_SOURCERPM, source rpms do not */
00132         if (lead->type == RPMLEAD_SOURCE) {
00133             if (!headerIsEntry(*hdr, RPMTAG_SOURCEPACKAGE))
00134                 headerAddEntry(*hdr, RPMTAG_SOURCEPACKAGE, RPM_INT32_TYPE,
00135                                 &true, 1);
00136         } else if (lead->major < 4) {
00137     /* Retrofit "Provide: name = EVR" for binary packages. */
00138             providePackageNVR(*hdr);
00139         }
00140         break;
00141 
00142     default:
00143         rpmError(RPMERR_NEWPACKAGE, _("only packaging with major numbers <= 4 "
00144                 "is supported by this version of RPM\n"));
00145         return 2;
00146         /*@notreached@*/ break;
00147     } 
00148 
00149     if (hdrPtr == NULL)
00150         headerFree(*hdr);
00151     
00152     return 0;
00153 }
00154 
00155 int rpmReadPackageInfo(FD_t fd, Header * sigp, Header * hdrp)
00156 {
00157     int rc = readPackageHeaders(fd, NULL, sigp, hdrp);
00158     if (rc)
00159         return rc;
00160     if (hdrp && *hdrp && sigp && *sigp)
00161         headerMergeLegacySigs(*hdrp, *sigp);
00162     return rc;
00163 }
00164 
00165 int rpmReadPackageHeader(FD_t fd, Header * hdrp, int * isSource, int * major,
00166                   int * minor)
00167 {
00168     struct rpmlead lead;
00169     Header sig = NULL;
00170     int rc = readPackageHeaders(fd, &lead, &sig, hdrp);
00171 
00172     if (rc)
00173         goto exit;
00174 
00175     if (hdrp && *hdrp && sig) {
00176         headerMergeLegacySigs(*hdrp, sig);
00177         headerFree(sig);
00178     }
00179    
00180     if (isSource) *isSource = lead.type == RPMLEAD_SOURCE;
00181     if (major) *major = lead.major;
00182     if (minor) *minor = lead.minor;
00183    
00184 exit:
00185     return rc;
00186 }

Generated at Mon May 21 08:53:39 2001 for rpm by doxygen1.2.6 written by Dimitri van Heesch, © 1997-2001