1 #include <u.h> 2 #include <libc.h> 3 #include <auth.h> 4 #include <fcall.h> 5 #include <tapefs.h> 6 #include <bio.h> 7 8 Idmap * 9 getpass(char *file) 10 { 11 Biobuf *bp; 12 char *cp; 13 Idmap *up; 14 int nid, maxid; 15 char *line[4]; 16 17 if ((bp = Bopen(file, OREAD)) == 0) 18 error("Can't open passwd/group"); 19 up = emalloc(1*sizeof(Idmap)); 20 maxid = 1; 21 nid = 0; 22 while ((cp = Brdline(bp, '\n'))) { 23 int nf; 24 cp[Blinelen(bp)-1] = 0; 25 nf = getfields(cp, line, 3, 0, ":\n"); 26 if (nf<3) { 27 fprint(2, "bad format in %s\n", file); 28 break; 29 } 30 if (nid>=maxid) { 31 maxid *= 2; 32 up = (Idmap *)erealloc(up, maxid*sizeof(Idmap)); 33 } 34 up[nid].id = atoi(line[2]); 35 up[nid].name = strdup(line[0]); 36 nid++; 37 } 38 Bterm(bp); 39 up[nid].name = 0; 40 return up; 41 } 42 43 char * 44 mapid(Idmap *up, int id) 45 { 46 char buf[16]; 47 48 if (up) 49 while (up->name){ 50 if (up->id==id) 51 return strdup(up->name); 52 up++; 53 } 54 sprint(buf, "%d", id); 55 return strdup(buf); 56 } 57 58 Ram * 59 poppath(Fileinf fi, int new) 60 { 61 char *suffix; 62 Ram *dir, *ent; 63 Fileinf f; 64 65 if (*fi.name=='\0') 66 return 0; 67 if (suffix=strrchr(fi.name, '/')){ 68 *suffix = 0; 69 suffix++; 70 if (*suffix=='\0'){ 71 fi.mode |= DMDIR; 72 return poppath(fi, 1); 73 } 74 f = fi; 75 f.size = 0; 76 f.addr = 0; 77 f.mode = 0555|DMDIR; 78 dir = poppath(f, 0); 79 if (dir==0) 80 dir = ram; 81 } else { 82 suffix = fi.name; 83 dir = ram; 84 if (strcmp(suffix, ".")==0) 85 return dir; 86 } 87 ent = lookup(dir, suffix); 88 fi.mode |= 0400; /* at least user read */ 89 if (ent){ 90 if (((fi.mode&DMDIR)!=0) != ((ent->qid.type&QTDIR)!=0)){ 91 fprint(2, "%s/%s directory botch\n", fi.name, suffix); 92 exits(""); 93 } 94 if (new) { 95 ent->ndata = fi.size; 96 ent->data = fi.addr; 97 ent->perm = fi.mode; 98 ent->mtime = fi.mdate; 99 ent->user = mapid(uidmap, fi.uid); 100 ent->group = mapid(gidmap, fi.gid); 101 } 102 } else { 103 fi.name = suffix; 104 ent = popfile(dir, fi); 105 } 106 return ent; 107 } 108 109 Ram * 110 popfile(Ram *dir, Fileinf fi) 111 { 112 Ram *ent = (Ram *)emalloc(sizeof(Ram)); 113 if (*fi.name=='\0') 114 return 0; 115 ent->busy = 1; 116 ent->open = 0; 117 ent->parent = dir; 118 ent->next = dir->child; 119 dir->child = ent; 120 ent->child = 0; 121 ent->qid.path = ++path; 122 ent->qid.vers = 0; 123 if(fi.mode&DMDIR) 124 ent->qid.type = QTDIR; 125 else 126 ent->qid.type = QTFILE; 127 ent->perm = fi.mode; 128 ent->name = estrdup(fi.name); 129 ent->atime = ent->mtime = fi.mdate; 130 ent->user = mapid(uidmap, fi.uid); 131 ent->group = mapid(gidmap, fi.gid); 132 ent->ndata = fi.size; 133 ent->data = fi.addr; 134 ent->replete |= replete; 135 return ent; 136 } 137 138 Ram * 139 lookup(Ram *dir, char *name) 140 { 141 Ram *r; 142 143 if (dir==0) 144 return 0; 145 for (r=dir->child; r; r=r->next){ 146 if (r->busy==0 || strcmp(r->name, name)!=0) 147 continue; 148 return r; 149 } 150 return 0; 151 } 152