2 * Copyright 2000, International Business Machines Corporation and others.
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
10 #include <afsconfig.h>
11 #include <afs/param.h>
17 #include <sys/types.h>
20 #include <WINNT/afsevent.h>
22 #include <netinet/in.h>
30 #include <afs/com_err.h>
31 #include <afs/cellconfig.h>
34 #include <afs/afsutil.h>
37 afs_int32 security = 0;
38 char confdir[AFSDIR_PATH_MAX];
42 #ifndef AFS_PTHREAD_ENV
43 extern struct ubik_client *pruclient;
46 static int ignoreExist = 0;
47 static char line[256];
48 static char *lineProgress;
50 #define WHITESPACE " \t\n"
52 #ifndef AFS_PTHREAD_ENV
56 /* OK, this REALLY sucks bigtime, but I can't tell who is calling
57 * afsconf_CheckAuth easily, and only *SERVERS* should be calling osi_audit
58 * anyway. It's gonna give somebody fits to debug, I know, I know.
62 #endif /* !AFS_PTHREAD_ENV */
65 GetToken(char *format, afs_int32 *l)
70 if (lineProgress == 0)
72 c = sscanf(lineProgress, format, l);
75 /* skip the white space */
76 lineProgress += strspn(lineProgress, WHITESPACE);
77 /* skip to end of token */
78 lineProgress = strpbrk(lineProgress, WHITESPACE);
82 #define GetInt32(l) GetToken ("%d", l)
83 #define GetXInt32(l) GetToken ("%x", l)
94 if (lineProgress == 0)
96 /* skip the white space */
97 lineProgress += strspn(lineProgress, WHITESPACE);
99 /* check for quoted string and find end */
102 l = strcspn(++beg, "\"");
103 if (l == strlen(beg))
104 return -1; /* unbalanced quotes */
105 lineProgress = beg + l + 1;
107 l = strcspn(beg, WHITESPACE);
110 if (l >= slen) { /* don't return too much */
117 s[l] = 0; /* null termination */
127 return code && (code != PREXIST) && (code != PRIDEXIST);
131 PrintEntry(ea, e, indent)
136 /* handle screwed up versions of DumpEntry */
137 if (e->flags & PRCONT) {
138 afs_int32 id = *(afs_int32 *) (e->name);
139 if ((id != PRBADID) && ((id > (1 << 24)) || (id < -(1 << 24)))) {
140 /* assume server incorrectly swapped these bytes... */
142 while (i < sizeof(e->name)) {
145 e->name[i] = e->name[i + 3];
146 e->name[i + 3] = temp;
147 temp = e->name[i + 1];
148 e->name[i + 1] = e->name[i + 2];
149 e->name[i + 2] = temp;
154 return pr_PrintEntry(stdout, /*host order */ 1, ea, e, indent);
157 #ifndef AFS_PTHREAD_ENV
161 #include "AFS_component_version_number.c"
167 register afs_int32 code;
169 char name[PR_MAXNAMELEN];
170 afs_int32 id, oid = ANONYMOUSID, gid;
173 struct prentry entry;
177 struct hostent *hostinfo;
178 struct in_addr *hostaddr;
186 * The following signal action for AIX is necessary so that in case of a
187 * crash (i.e. core is generated) we can include the user's data section
188 * in the core dump. Unfortunately, by default, only a partial core is
189 * generated which, in many cases, isn't too useful.
191 struct sigaction nsa;
193 sigemptyset(&nsa.sa_mask);
194 nsa.sa_handler = SIG_DFL;
195 nsa.sa_flags = SA_FULLDUMP;
196 sigaction(SIGSEGV, &nsa, NULL);
200 initialize_PT_error_table();
202 strcpy(confdir, AFSDIR_CLIENT_ETC_DIRPATH);
206 int arglen = strlen(argv[i]);
208 lcstring(arg, argv[i], sizeof(arg));
209 #define IsArg(a) (strncmp (arg,a, arglen) == 0)
210 if (IsArg("-testconfdir"))
211 strncpy(confdir, argv[++i], sizeof(confdir));
212 else if (IsArg("client"))
213 strncpy(confdir, AFSDIR_CLIENT_ETC_DIRPATH, sizeof(confdir));
214 else if (IsArg("server"))
215 strncpy(confdir, AFSDIR_SERVER_ETC_DIRPATH, sizeof(confdir));
216 else if (IsArg("0") || IsArg("1") || IsArg("2"))
217 security = atoi(argv[i]);
218 else if (IsArg("-ignoreexist"))
220 else if (IsArg("-cell"))
224 ("Usage is: 'prclient [-testconfdir <dir> | server | client] [0 | 1 | 2] [-ignoreExist] [-cell <cellname>]\n");
230 printf("Using CellServDB file in %s\n", confdir);
232 printf("Making unauthenticated connection to prserver\n");
234 code = pr_Initialize(security, confdir, cell);
236 afs_com_err(whoami, code, "Couldn't initialize protection library");
244 s = fgets(line, sizeof(line), stdin);
249 code = GetString(op, sizeof(op));
251 afs_com_err(whoami, PRBADARG,
252 "error reading opcode in line '%s', got '%.*s'", line,
257 continue; /* no input */
259 if (!strcmp(op, "cr")) {
260 if (GetString(name, sizeof(name)) || GetInt32(&id)
263 /* use ubik_Call to do the work, finding an up server and handling
264 * the job of finding a sync site, if need be */
266 code = ubik_PR_INewEntry(pruclient, 0, name, id, oid);
268 afs_com_err(whoami, code, "on %s %s %d %d", op, name, id, oid);
269 } else if (!strcmp(op, "sf")) {
270 afs_int32 mask, access, gq, uq;
271 if (GetInt32(&id) || GetXInt32(&mask) || GetXInt32(&access)
272 || GetInt32(&gq) || GetInt32(&uq))
276 ubik_PR_SetFieldsEntry(pruclient, 0, id, mask,
277 access, gq, uq, 0, 0);
279 afs_com_err(whoami, code, "on %s %d %x %x %d %d", op, id, mask,
281 } else if (!strcmp(op, "ce")) {
282 char newname[PR_MAXNAMELEN];
284 if (GetInt32(&id) || GetString(newname, sizeof(newname))
285 || GetInt32(&oid) || GetInt32(&newid))
289 ubik_PR_ChangeEntry(pruclient, 0, id, newname, oid,
292 afs_com_err(whoami, code, "on %s %d %s %d %d", op, id, newname,
294 } else if (!strcmp(op, "wh")) {
295 /* scanf("%d",&id); */
299 code = ubik_PR_WhereIsIt(pruclient, 0, id, &pos);
301 printf("%s\n", pr_ErrorMsg(code));
303 printf("location %d\n", pos);
304 } else if (!strcmp(op, "du")) {
305 memset(&entry, 0, sizeof(entry));
306 /* scanf("%d",&pos); */
310 code = ubik_PR_DumpEntry(pruclient, 0, pos, &entry);
312 printf("%s\n", pr_ErrorMsg(code));
313 if (code == PRSUCCESS) {
314 PrintEntry(pos, &entry, /*indent */ 0);
316 printf("The contents of the entry for %d are:\n", entry.id);
317 printf("flags %d next %d\n", entry.flags, entry.next);
318 printf("Groups (or members) \n");
319 for (i = 0; i < PRSIZE; i++)
320 printf("%d\n", entry.entries[i]);
321 printf("nextID %d nextname %d name %s\n", entry.nextID,
322 entry.nextName, entry.name);
323 printf("owner %d creator %d\n", entry.owner, entry.creator);
326 } else if (!strcmp(op, "add") || !strcmp(op, "au")) {
327 /* scanf("%d %d",&id,&gid); */
328 if (GetInt32(&id) || GetInt32(&gid))
331 code = ubik_PR_AddToGroup(pruclient, 0, id, gid);
333 afs_com_err(whoami, code, "on %s %d %d", op, id, gid);
334 } else if (!strcmp(op, "iton")) {
335 lid.idlist_val = (afs_int32 *) malloc(20 * sizeof(afs_int32));
336 ptr = lid.idlist_val;
340 while ((lid.idlist_len < 20) && (sscanf(foo, "%d", ptr) != EOF)) {
346 fprintf(stderr, "too many values specified; max is %d\n", 20);
348 lnames.namelist_val = 0;
349 lnames.namelist_len = 0;
350 code = ubik_PR_IDToName(pruclient, 0, &lid, &lnames);
352 printf("%s\n", pr_ErrorMsg(code));
353 if (code == PRSUCCESS) {
354 for (i = 0; i < lnames.namelist_len; i++) {
355 printf("id %d name %s\n", lid.idlist_val[i],
356 lnames.namelist_val[i]);
358 free(lnames.namelist_val);
360 free(lid.idlist_val);
363 } else if (!strcmp(op, "ntoi")) {
364 lnames.namelist_val =
365 (prname *) malloc(PR_MAXLIST * PR_MAXNAMELEN);
366 lnames.namelist_len = 0;
369 for (i = 0; ((lnames.namelist_len < PR_MAXLIST)
370 && (sscanf(foo, "%s", lnames.namelist_val[i]) !=
372 lnames.namelist_len++;
376 fprintf(stderr, "too many values specified; max is %d\n",
381 code = ubik_PR_NameToID(pruclient, 0, &lnames, &lid);
383 printf("%s\n", pr_ErrorMsg(code));
384 if (code == PRSUCCESS) {
385 for (i = 0; i < lid.idlist_len; i++)
386 printf("name %s id %d\n", lnames.namelist_val[i],
388 free(lid.idlist_val);
390 free(lnames.namelist_val);
391 lnames.namelist_val = 0;
392 lnames.namelist_len = 0;
393 } else if (!strcmp(op, "del")) {
394 /* scanf("%d",&id); */
398 code = ubik_PR_Delete(pruclient, 0, id);
400 printf("%s\n", pr_ErrorMsg(code));
401 } else if (!strcmp(op, "dg")) {
402 /* scanf("%d",&id); */
406 code = ubik_PR_Delete(pruclient, 0, id);
408 printf("%s\n", pr_ErrorMsg(code));
409 } else if (!strcmp(op, "rm")) {
410 /* scanf("%d %d",&id,&gid); */
411 if (GetInt32(&id) || GetInt32(&gid))
414 code = ubik_PR_RemoveFromGroup(pruclient, 0, id, gid);
416 printf("%s\n", pr_ErrorMsg(code));
418 #if defined(SUPERGROUPS)
419 else if (!strcmp(op, "lsg")) {
420 alist.prlist_len = 0;
421 alist.prlist_val = 0;
422 /* scanf("%d",&id); */
427 ubik_PR_ListSuperGroups(pruclient, 0, id, &alist,
430 printf("%s\n", pr_ErrorMsg(code));
431 if (code == PRSUCCESS) {
432 ptr = alist.prlist_val;
434 printf("Number of groups greater than PR_MAXGROUPS!\n");
435 printf("Excess of %d.\n", over);
437 for (i = 0; i < alist.prlist_len; i++, ptr++)
438 printf("%d\n", *ptr);
439 free(alist.prlist_val);
440 alist.prlist_len = 0;
441 alist.prlist_val = 0;
444 #endif /* SUPERGROUPS */
445 else if (!strcmp(op, "l")) {
446 alist.prlist_len = 0;
447 alist.prlist_val = 0;
448 /* scanf("%d",&id); */
452 code = ubik_PR_GetCPS(pruclient, 0, id, &alist, &over);
454 printf("%s\n", pr_ErrorMsg(code));
455 if (code == PRSUCCESS) {
456 ptr = alist.prlist_val;
458 printf("Number of groups greater than PR_MAXGROUPS!\n");
459 printf("Excess of %d.\n", over);
461 for (i = 0; i < alist.prlist_len; i++, ptr++)
462 printf("%d\n", *ptr);
463 free(alist.prlist_val);
464 alist.prlist_len = 0;
465 alist.prlist_val = 0;
467 } else if (!strcmp(op, "lh")) {
468 alist.prlist_len = 0;
469 alist.prlist_val = 0;
470 /* scanf("%d",&id); */
471 if (GetString(name, sizeof(name)))
473 else if (!(hostinfo = gethostbyname(name)))
476 hostaddr = hostinfo->h_addr_list[0];
477 id = ntohl(hostaddr->s_addr);
479 ubik_PR_GetHostCPS(pruclient, 0, id, &alist, &over);
482 printf("%s\n", pr_ErrorMsg(code));
483 if (code == PRSUCCESS) {
484 ptr = alist.prlist_val;
486 printf("Number of groups greater than PR_MAXGROUPS!\n");
487 printf("Excess of %d.\n", over);
489 for (i = 0; i < alist.prlist_len; i++, ptr++)
490 printf("%d\n", *ptr);
491 free(alist.prlist_val);
492 alist.prlist_len = 0;
493 alist.prlist_val = 0;
496 #if defined(SUPERGROUPS)
497 else if (!strcmp(op, "m")) {
498 alist.prlist_len = 0;
499 alist.prlist_val = 0;
500 /* scanf("%d",&id); */
505 ubik_PR_ListElements(pruclient, 0, id, &alist,
508 printf("%s\n", pr_ErrorMsg(code));
509 if (code == PRSUCCESS) {
510 ptr = alist.prlist_val;
512 printf("Number of groups greater than PR_MAXGROUPS!\n");
513 printf("Excess of %d.\n", over);
515 for (i = 0; i < alist.prlist_len; i++, ptr++)
516 printf("%d\n", *ptr);
517 free(alist.prlist_val);
518 alist.prlist_len = 0;
519 alist.prlist_val = 0;
522 #endif /* SUPERGROUPS */
523 else if (!strcmp(op, "nu")) {
524 /* scanf("%s",name); */
525 if (GetString(name, sizeof(name)))
528 code = pr_CreateUser(name, &id);
530 printf("%s\n", pr_ErrorMsg(code));
531 if (code == PRSUCCESS)
532 printf("Id is %d.\n", id);
533 } else if (!strcmp(op, "ng")) {
534 /* scanf("%s",name); */
535 if (GetString(name, sizeof(name)))
538 code = ubik_PR_NewEntry(pruclient, 0, name, 1, oid, &id);
540 printf("%s\n", pr_ErrorMsg(code));
541 if (code == PRSUCCESS)
542 printf("Id is %d.\n", id);
543 } else if (!strcmp(op, "lm")) {
544 code = ubik_PR_ListMax(pruclient, 0, &id, &gid);
546 printf("%s\n", pr_ErrorMsg(code));
547 if (code == PRSUCCESS)
548 printf("Max user id is %d, max (really min) group is %d.\n",
550 } else if (!strcmp(op, "smu")) {
551 /* scanf("%d",&id); */
555 code = ubik_PR_SetMax(pruclient, 0, id, 0);
557 printf("%s\n", pr_ErrorMsg(code));
558 } else if (!strcmp(op, "smg")) {
559 /* scanf("%d",&id); */
563 code = ubik_PR_SetMax(pruclient, 0, id, 1);
565 printf("%s\n", pr_ErrorMsg(code));
566 } else if (!strcmp(op, "sin")) {
567 /* scanf("%d",&id); */
571 code = pr_SIdToName(id, name);
573 printf("%s\n", pr_ErrorMsg(code));
574 if (code == PRSUCCESS)
575 printf("id %d name %s\n", id, name);
576 } else if (!strcmp(op, "sni")) {
577 /* scanf("%s",name); */
578 if (GetString(name, sizeof(name)))
581 code = pr_SNameToId(name, &id);
583 printf("%s\n", pr_ErrorMsg(code));
584 if (code == PRSUCCESS)
585 printf("name %s id %d\n", name, id);
586 } else if (!strcmp(op, "fih")) {
588 struct PrUpdateEntry uentry;
589 memset(&uentry, 0, sizeof(uentry));
590 /* scanf("%s",name); */
591 if (GetString(name, sizeof(name))) {
595 code = pr_SNameToId(name, &id);
597 printf("%s\n", pr_ErrorMsg(code));
600 code = pr_SIdToName(id, tname);
601 if (code == PRSUCCESS) {
603 ("Warning: Id hash for %s (id %d) seems correct at the db; rehashing it anyway\n",
607 uentry.Mask = PRUPDATE_IDHASH;
608 code = ubik_PR_UpdateEntry(pruclient, 0, 0, name, &uentry);
610 printf("Failed to update entry %s (err=%d)\n", name, code);
613 } else if (!strcmp(op, "fnh")) {
615 struct PrUpdateEntry uentry;
616 memset(&uentry, 0, sizeof(uentry));
617 /* scanf("%d", &id); */
622 code = pr_SIdToName(id, name);
624 printf("%s\n", pr_ErrorMsg(code));
627 code = pr_SNameToId(name, &tid);
628 if (code == PRSUCCESS) {
630 ("Name hash for %d (name is %s) seems correct at the db; rehashing it anyway\n",
634 uentry.Mask = PRUPDATE_NAMEHASH;
636 ubik_PR_UpdateEntry(pruclient, 0, id, "_foo_", &uentry);
638 printf("Failed to update entry with id %d (err=%d)\n", id,
643 #if defined(SUPERGROUPS)
644 else if (!strcmp(op, "fih")) {
646 struct PrUpdateEntry uentry;
647 memset(&uentry, 0, sizeof(uentry));
648 /* scanf("%s",name); */
649 if (GetString(name, sizeof(name))) {
653 code = pr_SNameToId(name, &id);
655 printf("%s\n", pr_ErrorMsg(code));
658 code = pr_SIdToName(id, tname);
659 if (code == PRSUCCESS) {
661 ("Warning: Id hash for %s (id %d) seems correct at the db; rehashing it anyway\n",
665 uentry.Mask = PRUPDATE_IDHASH;
666 code = ubik_PR_UpdateEntry(pruclient, 0, 0, name, &uentry);
668 printf("Failed to update entry %s (err=%d)\n", name, code);
671 } else if (!strcmp(op, "fnh")) {
673 struct PrUpdateEntry uentry;
674 memset(&uentry, 0, sizeof(uentry));
675 /* scanf("%d", &id); */
680 code = pr_SIdToName(id, name);
682 printf("%s\n", pr_ErrorMsg(code));
685 code = pr_SNameToId(name, &tid);
686 if (code == PRSUCCESS) {
688 ("Name hash for %d (name is %s) seems correct at the db; rehashing it anyway\n",
692 uentry.Mask = PRUPDATE_NAMEHASH;
694 ubik_PR_UpdateEntry(pruclient, 0, id, "_foo_", &uentry);
696 printf("Failed to update entry with id %d (err=%d)\n", id,
701 #endif /* SUPERGROUPS */
702 else if (!strcmp(op, "?"))
704 else if (!strcmp(op, "q"))
707 printf("Unknown op: '%s'! ? for help\n", op);
714 printf("cr name id owner - create entry with name and id.\n");
715 printf("wh id - what is the offset into database for id?\n");
716 printf("du offset - dump the contents of the entry at offset.\n");
717 printf("add uid gid - add user uid to group gid.\n");
718 printf("iton id* - translate the list of id's to names.\n");
719 printf("ntoi name* - translate the list of names to ids.\n");
720 printf("del id - delete the entry for id.\n");
721 printf("dg gid - delete the entry for group gid.\n");
722 printf("rm id gid - remove user id from group gid.\n");
723 printf("l id - get the CPS for id.\n");
724 printf("lh host - get the host CPS for host.\n");
725 #if defined(SUPERGROUPS)
726 printf("lsg id - get the supergroups for id.\n");
727 printf("m id - list elements for id.\n");
729 printf("nu name - create new user with name - returns an id.\n");
730 printf("ng name - create new group with name - returns an id.\n");
731 printf("lm - list max user id and max (really min) group id.\n");
732 printf("smu - set max user id.\n");
733 printf("smg - set max group id.\n");
734 printf("sin id - single iton.\n");
735 printf("sni name - single ntoi.\n");
736 printf("fih name - fix id hash for <name>.\n");
737 printf("fnh id - fix name hash for <id>.\n");
738 printf("q - quit.\n?- this message.\n");
745 while (**s != ' ' && **s != '\0')
750 #endif /* !AFS_PTHREAD_ENV */