rpmio/ugid.c

Go to the documentation of this file.
00001 
00005 #include "system.h"
00006 #include "ugid.h"
00007 #include "debug.h"
00008 
00009 /* unameToUid(), uidTouname() and the group variants are really poorly
00010    implemented. They really ought to use hash tables. I just made the
00011    guess that most files would be owned by root or the same person/group
00012    who owned the last file. Those two values are cached, everything else
00013    is looked up via getpw() and getgr() functions.  If this performs
00014    too poorly I'll have to implement it properly :-( */
00015 
00016 int unameToUid(const char * thisUname, uid_t * uid)
00017 {
00018 /*@only@*/ static char * lastUname = NULL;
00019     static size_t lastUnameLen = 0;
00020     static size_t lastUnameAlloced;
00021     static uid_t lastUid;
00022     struct passwd * pwent;
00023     size_t thisUnameLen;
00024 
00025     if (!thisUname) {
00026         lastUnameLen = 0;
00027         return -1;
00028     } else if (strcmp(thisUname, "root") == 0) {
00029 /*@-boundswrite@*/
00030         *uid = 0;
00031 /*@=boundswrite@*/
00032         return 0;
00033     }
00034 
00035     thisUnameLen = strlen(thisUname);
00036     if (lastUname == NULL || thisUnameLen != lastUnameLen ||
00037         strcmp(thisUname, lastUname) != 0)
00038     {
00039         if (lastUnameAlloced < thisUnameLen + 1) {
00040             lastUnameAlloced = thisUnameLen + 10;
00041             lastUname = xrealloc(lastUname, lastUnameAlloced);  /* XXX memory leak */
00042         }
00043 /*@-boundswrite@*/
00044         strcpy(lastUname, thisUname);
00045 /*@=boundswrite@*/
00046 
00047         pwent = getpwnam(thisUname);
00048         if (pwent == NULL) {
00049             /*@-internalglobs@*/ /* FIX: shrug */
00050             endpwent();
00051             /*@=internalglobs@*/
00052             pwent = getpwnam(thisUname);
00053             if (pwent == NULL) return -1;
00054         }
00055 
00056         lastUid = pwent->pw_uid;
00057     }
00058 
00059 /*@-boundswrite@*/
00060     *uid = lastUid;
00061 /*@=boundswrite@*/
00062 
00063     return 0;
00064 }
00065 
00066 int gnameToGid(const char * thisGname, gid_t * gid)
00067 {
00068 /*@only@*/ static char * lastGname = NULL;
00069     static size_t lastGnameLen = 0;
00070     static size_t lastGnameAlloced;
00071     static gid_t lastGid;
00072     size_t thisGnameLen;
00073     struct group * grent;
00074 
00075     if (thisGname == NULL) {
00076         lastGnameLen = 0;
00077         return -1;
00078     } else if (strcmp(thisGname, "root") == 0) {
00079 /*@-boundswrite@*/
00080         *gid = 0;
00081 /*@=boundswrite@*/
00082         return 0;
00083     }
00084 
00085     thisGnameLen = strlen(thisGname);
00086     if (lastGname == NULL || thisGnameLen != lastGnameLen ||
00087         strcmp(thisGname, lastGname) != 0)
00088     {
00089         if (lastGnameAlloced < thisGnameLen + 1) {
00090             lastGnameAlloced = thisGnameLen + 10;
00091             lastGname = xrealloc(lastGname, lastGnameAlloced);  /* XXX memory leak */
00092         }
00093 /*@-boundswrite@*/
00094         strcpy(lastGname, thisGname);
00095 /*@=boundswrite@*/
00096 
00097         grent = getgrnam(thisGname);
00098         if (grent == NULL) {
00099             /*@-internalglobs@*/ /* FIX: shrug */
00100             endgrent();
00101             /*@=internalglobs@*/
00102             grent = getgrnam(thisGname);
00103             if (grent == NULL) {
00104                 /* XXX The filesystem package needs group/lock w/o getgrnam. */
00105                 if (strcmp(thisGname, "lock") == 0) {
00106 /*@-boundswrite@*/
00107                     *gid = lastGid = 54;
00108 /*@=boundswrite@*/
00109                     return 0;
00110                 } else
00111                 if (strcmp(thisGname, "mail") == 0) {
00112 /*@-boundswrite@*/
00113                     *gid = lastGid = 12;
00114 /*@=boundswrite@*/
00115                     return 0;
00116                 } else
00117                 return -1;
00118             }
00119         }
00120         lastGid = grent->gr_gid;
00121     }
00122 
00123 /*@-boundswrite@*/
00124     *gid = lastGid;
00125 /*@=boundswrite@*/
00126 
00127     return 0;
00128 }
00129 
00130 char * uidToUname(uid_t uid)
00131 {
00132     static uid_t lastUid = (uid_t) -1;
00133 /*@only@*/ static char * lastUname = NULL;
00134     static size_t lastUnameLen = 0;
00135 
00136     if (uid == (uid_t) -1) {
00137         lastUid = (uid_t) -1;
00138         return NULL;
00139     } else if (uid == (uid_t) 0) {
00140         return "root";
00141     } else if (uid == lastUid) {
00142         return lastUname;
00143     } else {
00144         struct passwd * pwent = getpwuid(uid);
00145         size_t len;
00146 
00147         if (pwent == NULL) return NULL;
00148 
00149         lastUid = uid;
00150         len = strlen(pwent->pw_name);
00151         if (lastUnameLen < len + 1) {
00152             lastUnameLen = len + 20;
00153             lastUname = xrealloc(lastUname, lastUnameLen);
00154         }
00155 /*@-boundswrite@*/
00156         strcpy(lastUname, pwent->pw_name);
00157 /*@=boundswrite@*/
00158 
00159         return lastUname;
00160     }
00161 }
00162 
00163 char * gidToGname(gid_t gid)
00164 {
00165     static gid_t lastGid = (gid_t) -1;
00166 /*@only@*/ static char * lastGname = NULL;
00167     static size_t lastGnameLen = 0;
00168 
00169     if (gid == (gid_t) -1) {
00170         lastGid = (gid_t) -1;
00171         return NULL;
00172     } else if (gid == (gid_t) 0) {
00173         return "root";
00174     } else if (gid == lastGid) {
00175         return lastGname;
00176     } else {
00177         struct group * grent = getgrgid(gid);
00178         size_t len;
00179 
00180         if (grent == NULL) return NULL;
00181 
00182         lastGid = gid;
00183         len = strlen(grent->gr_name);
00184         if (lastGnameLen < len + 1) {
00185             lastGnameLen = len + 20;
00186             lastGname = xrealloc(lastGname, lastGnameLen);
00187         }
00188 /*@-boundswrite@*/
00189         strcpy(lastGname, grent->gr_name);
00190 /*@=boundswrite@*/
00191 
00192         return lastGname;
00193     }
00194 }

Generated on Fri Oct 12 08:44:55 2007 for rpm by  doxygen 1.5.2