2.9BSD/usr/src/ucb/setquota.c
# include <sys/param.h>
# include <sys/inode.h>
# include <sys/stat.h>
# include <sys/qstat.h>
struct stat sbuf;
struct qstat qsbuf;
int start;
int fdir;
int ldir;
daddr_t nused;
daddr_t nquot;
char dotq[] ".q";
char dot[] ".";
char dotdot[] "..";
char dummy1[] ".1.1.1";
char dummy2[] ".2.2.2";
char dummy3[] ".3.3.3";
extern daddr_t atol();
main(argc, argv)
char *argv[];
{
register i, j;
int flag;
fdir = 1;
start = 0;
for(i=1; i<argc; i++) {
start = 1;
if(isdir(argv[i]))
continue;
ldir = i;
if(fdir >= ldir) {
printf("no directories specified\n");
exit(1);
}
if(!isnumb(argv[i])) {
printf("%s not a directory\n", argv[i]);
exit(1);
}
nused = 0;
flag = 1;
if(i+1 < argc && isnumb(argv[i+1])) {
nused = atol(argv[i]);
flag = 0;
i++;
}
nquot = atol(argv[i]);
for(j=fdir; j<ldir; j++)
setq(argv[j], flag, nused, nquot);
fdir = i;
start = 0;
}
if(start) {
printf("no quota specified\n");
exit(1);
}
exit(0);
}
isdir(s)
char *s;
{
if(stat(s, &sbuf) < 0)
return(0);
if((sbuf.st_mode&S_IFMT)==S_IFDIR)
return(1);
return(0);
}
isnumb(s)
char *s;
{
register c;
while(c = *s++)
if(c < '0' || c > '9')
return(0);
return(1);
}
setq(dir, flg, n, m)
char *dir;
int flg;
daddr_t n, m;
{
register i;
int count, f, junk[25];
if(i=fork()) {
while(wait(junk) != -1)
;
return;
}
if(chdir(dir) < 0) {
printf("chdir:");
perror(dir);
exit(1);
}
count = 0;
loop:
if(count > 2) {
printf("attempts fail\n");
exit(1);
}
count++;
if(qstat(dotq, &qsbuf) >= 0) {
if((qsbuf.qs_mode&S_IFMT) != S_IFQUOT) {
unlink(dotq);
goto loop;
}
if(flg==1)
n=qsbuf.qs_un.qs_qused;
if(quota(dotq, fsbtodb(n), fsbtodb(m)) < 0) {
printf("quota:");
perror(dotq);
exit(1);
}
exit(0);
}
unlink(dummy1);
f = open(dot, 0);
if(f < 0) {
printf("open:");
perror(dir);
exit(1);
}
for(i=0; i<sizeof junk / sizeof (int); i++)
junk[i] = 0;
read(f, junk, 48);
close(f);
for(i=0; i<24; i=+8) {
if(junk[i] == 0) {
if (mknod(dotq, S_IFQUOT, 0) < 0) {
perror("mknod:1");
exit(1);
}
goto slot;
}
if(junk[i+1] == '.')
continue;
if(junk[i+1] == '..' && junk[i+2] == 0)
continue;
junk[i+8] = 0;
link(junk+i+1, dummy1);
unlink(junk+i+1);
if (mknod(dotq, S_IFQUOT, 0) < 0) {
perror("mknod:2");
exit(1);
}
link(dummy1, junk+i+1);
goto slot;
}
printf("first 3 slots contain . and ..\n");
exit(1);
slot:
i = open(dotdot, 0); /* keep .. referenced during procedure */
unlink(dummy1);
unlink(dummy2);
unlink(dummy3);
link(dotq, dummy1);
link(dot, dummy2);
link(dotdot, dummy3);
unlink(dotq);
unlink(dot);
unlink(dotdot);
link(dummy1, dotq);
link(dummy2, dot);
link(dummy3, dotdot);
unlink(dummy1);
unlink(dummy2);
unlink(dummy3);
close(i);
goto loop;
}