8 #include <moira_site.h>
12 #include <sys/socket.h>
13 #include <netinet/in.h>
23 /* Called with moira data that is to be modified. */
25 int ModifyCallback(argc, argv, form)
36 switch (form->menu->operation) {
39 f = GetAndClearForm("mod_user");
41 display_error("Unknown form in ModifyCallback!\n");
44 f->extrastuff = form->extrastuff;
46 for (i = 0; i < U_SIGNATURE; i++)
47 if (f->inputlines[i]->type == FT_BOOLEAN)
48 f->inputlines[i]->returnvalue.booleanvalue =
49 strcmp(argv[i + offset], "0") ? 1 : 0;
51 StoreField(f, i, argv[i + offset]);
52 f->inputlines[U_SIGNATURE]->keyword_name = strsave(argv[U_SIGNATURE]);
53 f->inputlines[U_SIGNATURE]->returnvalue.booleanvalue =
54 strcmp(argv[U_SECURE], "0") ? 1 : 0;
55 f->inputlines[U_COMMENT]->keyword_name = strsave(argv[U_SECURE]);
59 count = F_MODTIME - 1;
64 form->extrastuff = NULL;
66 form->extrastuff = strsave(argv[U_UID]);
78 f = GetAndClearForm("mod_nfs");
80 display_error("Unknown form in ModifyCallback of mod_nfs\n");
83 f->extrastuff = form->extrastuff;
85 StoreField(f, 0, argv[0]);
86 StoreField(f, 1, argv[1]);
87 StoreField(f, 2, argv[2]);
88 f->inputlines[3]->keywords = nfs_states;
89 for (i = 0; nfs_states[i]; i++)
90 if (atoi(nfs_states[i]) & atoi(argv[3]))
91 StoreField(f, 3, nfs_states[i]);
92 if (atoi(argv[3]) & MR_FS_GROUPQUOTA)
93 f->inputlines[4]->returnvalue.booleanvalue = 1;
95 f->inputlines[4]->returnvalue.booleanvalue = 0;
96 StoreField(f, 5, argv[4]);
97 StoreField(f, 6, argv[5]);
109 count = PCAP_MODTIME;
112 f = GetAndClearForm("mod_service");
114 display_error("Unknown form in ModifyCallback of mod_service\n");
117 f->extrastuff = form->extrastuff;
118 f->menu = form->menu;
119 for (i = 0; i < 4; i++) StoreField(f, i, argv[i]);
120 StoreField(f, 4, argv[6]);
121 f->inputlines[5]->returnvalue.booleanvalue = atoi(argv[7]);
122 StoreField(f, 6, argv[11]);
123 StoreField(f, 7, argv[12]);
127 f = GetAndClearForm("mod_host");
129 display_error("Unknown form in ModifyCallback of mod_host\n");
132 f->extrastuff = form->extrastuff;
133 f->menu = form->menu;
134 StoreField(f, 0, argv[0]);
135 StoreField(f, 1, argv[1]);
136 f->inputlines[2]->returnvalue.booleanvalue = atoi(argv[2]);
137 StoreField(f, 3, argv[10]);
138 StoreField(f, 4, argv[11]);
139 StoreField(f, 5, argv[12]);
145 f = GetAndClearForm(fn);
147 display_error("Unknown form in ModifyCallback!\n");
150 f->extrastuff = form->extrastuff;
151 f->menu = form->menu;
152 for (i = 0; i < count; i++)
153 if (f->inputlines[i]->type == FT_BOOLEAN)
154 f->inputlines[i]->returnvalue.booleanvalue =
155 strcmp(argv[i + offset], "0") ? 1 : 0;
157 StoreField(f, i, argv[i + offset]);
159 display_error("Unknown function in ModifyCallback!\n");
165 /* Generate a new cryptographic signature for the user record */
166 SignUser(argv, offset)
175 if (strcmp(argv[U_NAME + offset], UNIQUE_LOGIN)) {
176 sprintf(buf, "%s:%s", argv[U_NAME + offset], argv[U_MITID + offset]);
178 i = GDSS_Verify(buf, strlen(buf), argv[U_SIGNATURE + offset], &si);
179 /* If it's already signed OK, don't resign it. */
180 if (i != GDSS_SUCCESS) {
181 free(argv[U_SIGNATURE + offset]);
182 argv[U_SIGNATURE + offset] = (char *) malloc(GDSS_Sig_Size() * 2);
184 i = GDSS_Sign(buf, strlen(buf), argv[U_SIGNATURE + offset]);
185 if (i != GDSS_SUCCESS)
186 com_err(program_name, gdss2et(i),
187 "Failed to create signature");
189 unsigned char newbuf[256];
191 i = GDSS_Verify(buf, strlen(buf),
192 argv[U_SIGNATURE + offset], &si);
193 if (strlen(newbuf) > 68) {
195 AppendLog("Signature too long, trying again\n");
201 AppendLog("Made signature:");hex_dump(argv[U_SIGNATURE + offset]);
203 AppendLog("Don't need to remake signature\n");
208 argv[U_SIGNATURE + offset] = strsave("");
213 /* when OK pressed */
215 MoiraFormComplete(dummy1, form)
219 process_form(form, TRUE);
223 /* when APPLY pressed */
225 MoiraFormApply(dummy1, form)
232 /* undocumented Motif internal routine to advance in tab group.
233 * In this case we're going backwards because for some reason
234 * the form advances whenever this button is pressed.
235 * However, it doesn't seem to go backwards even though source
236 * implies that it should. So we go forward until we wrap.
239 for (p = form->inputlines; *p; p++)
242 _XmMgrTraversal(form->formpointer, XmTRAVERSE_PREV_TAB_GROUP);
243 process_form(form, FALSE);
247 int CollectData(argc, argv, form)
252 struct save_queue *sq;
254 sq = (struct save_queue *) form->extrastuff;
255 sq_save_data(sq, strsave(argv[0]));
260 /* callback when form is complete to process the data */
262 process_form(form, remove)
266 char *qy, *argv[32], buf[256], *s, **aargv;
267 int (*retfunc)(), argc, i;
270 retfunc = DisplayCallback;
273 for (i = 0; form->inputlines[i]; i++)
274 argv[i] = StringValue(form, i);
275 qy = form->menu->query;
276 argc = form->menu->argc;
278 switch (form->menu->operation) {
280 if (*stringval(form, 0)) {
281 qy = "get_user_account_by_login";
282 argv[0] = stringval(form, 0);
284 } else if (*stringval(form, 3)) {
285 qy = "get_user_account_by_uid";
286 argv[0] = stringval(form, 3);
288 } else if (*stringval(form, 4)) {
289 qy = "get_user_account_by_class";
290 argv[0] = stringval(form, 4);
292 } else if (*stringval(form, 1) == 0 &&
293 *stringval(form, 2) == 0) {
294 display_error("Must fill in at least one blank.");
297 if (*stringval(form, 1) == 0)
298 StoreField(form, 1, "*");
299 if (*stringval(form, 2) == 0)
300 StoreField(form, 2, "*");
301 qy = "get_user_account_by_name";
302 argv[0] = stringval(form, 1);
303 argv[1] = stringval(form, 2);
308 argv[U_STATE][1] = 0;
309 argv[U_SECURE] = argv[U_SIGNATURE];
314 if (!strcmp(form->formname, "mod_user")) {
315 qy = "update_user_account";
316 for (i = 0; i < U_SIGNATURE; i++)
317 argv[i + 1] = StringValue(form, i);
318 argv[0] = form->extrastuff;
319 argv[U_STATE + 1][1] = 0;
320 argv[U_SIGNATURE + 1] = form->inputlines[U_SIGNATURE]->keyword_name;
321 argv[U_SECURE + 1] = StringValue(form, U_SIGNATURE);
322 if (*argv[U_SECURE + 1] == '1')
323 if (atoi(form->inputlines[U_COMMENT]->keyword_name))
324 argv[U_SECURE + 1] = form->inputlines[U_COMMENT]->keyword_name;
328 gettimeofday(&tv, NULL);
329 printf("Got %ld, %ld\n", tv.tv_sec, tv.tv_usec);
330 sprintf(buf, "%ld", tv.tv_sec);
331 argv[U_SECURE + 1] = strsave(buf);
334 argc = U_MODTIME + 1;
337 form->extrastuff = (caddr_t) "mod_user";
338 retfunc = ModifyCallback;
341 if (*stringval(form, 2)) {
342 argv[0] = stringval(form, 2);
344 argv[0] = stringval(form, 0);
345 argv[1] = stringval(form, 1);
346 form->extrastuff = NULL;
347 i = MoiraQuery("get_user_account_by_name", 2, argv,
348 ModifyCallback, (char *)form);
350 com_err(program_name, i, " looking up user by name");
353 if (form->extrastuff == NULL) {
354 display_error("Ambiguous user specification");
357 argv[0] = (char *)form->extrastuff;
359 qy = "register_user";
360 argv[1] = stringval(form, 3);
368 display_error("Expunge is not yet implemented");
372 if (!strcmp(form->formname, "mod_finger")) {
373 qy = "update_finger_by_login";
374 for (i = 0; i < F_MODTIME - 1; i++)
375 argv[i + 1] = StringValue(form, i);
376 argv[0] = form->extrastuff;
380 form->extrastuff = (caddr_t) "mod_finger";
381 retfunc = ModifyCallback;
384 if (!*stringval(form, 0))
386 if (!*stringval(form, 1))
390 if (!strcmp(argv[1], "POP"))
391 argv[2] = stringval(form, 3);
393 case MM_SHOW_ACE_USE:
394 if (boolval(form, 2)) {
395 sprintf(buf, "R%s", stringval(form, 0));
400 if (!strcmp(form->formname, "mod_list")) {
402 for (i = 0; i < L_MODTIME; i++)
403 argv[i + 1] = StringValue(form, i);
404 argv[0] = form->extrastuff;
405 argc = L_MODTIME + 1;
408 form->extrastuff = (caddr_t) "mod_list";
409 retfunc = ModifyCallback;
411 case MM_SHOW_MEMBERS:
412 if (!*stringval(form, 0)) {
413 qy = "get_lists_of_member";
414 argv[0] = stringval(form, 1);
415 sprintf(buf, "Lists of %s %s:\n", stringval(form, 1), argv[2]);
417 if (boolval(form, 3)) {
418 sprintf(buf, "R%s", stringval(form, 1));
421 argv[1] = stringval(form, 2);
424 if (boolval(form, 3)) {
425 qy = "get_end_members_of_list";
426 sprintf(buf, "Recursive members of list: %s\n", argv[0]);
428 sprintf(buf, "Members of list: %s\n", argv[0]);
432 case MM_DEL_ALL_MEMBER:
433 form->extrastuff = (caddr_t) sq_create();
434 retfunc = CollectData;
437 if (*stringval(form, 0)) {
438 qy = "get_filesys_by_label";
439 argv[0] = stringval(form, 0);
441 } else if (*stringval(form, 1)) {
442 StoreHost(form, 1, &argv[0]);
443 if (*stringval(form, 2)) {
444 qy = "get_filesys_by_nfsphys";
445 argv[1] = stringval(form, 2);
448 qy = "get_filesys_by_machine";
451 } else if (*stringval(form, 3)) {
452 qy = "get_filesys_by_group";
453 argv[0] = stringval(form, 3);
455 } else if (*stringval(form, 4)) {
456 qy = "get_filesys_by_path";
457 argv[0] = stringval(form, 4);
460 /* fall through to */
461 case MM_SHOW_FSGROUP:
462 form->extrastuff = (caddr_t) sq_create();
465 StoreHost(form, FS_MACHINE, &argv[FS_MACHINE]);
466 if (!strcmp(stringval(form, FS_TYPE), "AFS") ||
467 !strcmp(stringval(form, FS_TYPE), "FSGROUP") ||
468 !strcmp(stringval(form, FS_TYPE), "MUL"))
469 argv[FS_MACHINE] = "\\[NONE\\]";
472 if (!strcmp(form->formname, "mod_filsys")) {
473 qy = "update_filesys";
474 for (i = 0; i < FS_MODTIME; i++)
475 argv[i + 1] = StringValue(form, i);
476 StoreHost(form, FS_MACHINE, &argv[FS_MACHINE + 1]);
477 argv[0] = form->extrastuff;
478 argc = FS_MODTIME + 1;
481 form->extrastuff = (caddr_t) "mod_filsys";
482 retfunc = ModifyCallback;
485 argv[1] = strsave(stringval(form, 1));
486 s = index(argv[1], ' ');
488 i = MoiraQuery("remove_filesys_from_fsgroup", 2, argv, ModifyCallback,
491 com_err(program_name, i, " removing filesystem from FS group");
495 /* fall through to: */
497 /* find the two keys to sort between */
498 argv[2] = strsave(argv[2]);
499 s = index(argv[2], ' ');
502 s = index(argv[2], ')');
506 if (*argv[2] == 0) argv[2] = "A";
507 /* Finding the after key is gross. We look through the widgets
508 * in the radiobox to find the one selected and the one after
509 * it. The name of the widget is also the member name.
515 w = form->inputlines[2]->mywidget;
516 for (i = 0; i < NumChildren(w); i++) {
517 kid = NthChild(w, i);
518 if (!strcmp(XtName(kid), stringval(form, 2))) {
520 if (i < NumChildren(w)) {
521 argv[3] = strsave(XtName(NthChild(w, i)));
522 s = index(argv[3], ' ');
525 s = index(argv[3], ')');
534 if (*argv[3] == 0) argv[3] = "Z";
536 printf("Got before key of \"%s\" and after key of \"%s\"\n",
539 /* copy the matching chars */
540 for (s = buf; *argv[2] && *argv[2] == *argv[3]; argv[3]++)
542 /* and set the last char */
548 if (*argv[3] == 0) *argv[3] = 'Z';
549 if (*argv[3] - *argv[2] > 1) {
550 *s++ = (*argv[3] + *argv[2])/2;
556 argv[2] = strsave(buf);
559 argv[1] = strsave(stringval(form, 1));
560 s = index(argv[1], ' ');
563 case MM_SHOW_FS_ALIAS:
564 if (!*stringval(form, 0))
567 argv[2] = stringval(form, 0);
568 if (!*stringval(form, 1))
571 argv[0] = stringval(form, 1);
574 case MM_ADD_FS_ALIAS:
575 case MM_DEL_FS_ALIAS:
576 argv[0] = stringval(form, 1);
578 argv[2] = stringval(form, 0);
581 StoreHost(form, NFS_NAME, &argv[NFS_NAME]);
582 if (!*stringval(form, 1))
586 StoreHost(form, NFS_NAME, &argv[NFS_NAME]);
587 sprintf(buf, "%d", atoi(stringval(form, NFS_STATUS)) +
588 (boolval(form, 4) ? MR_FS_GROUPQUOTA : 0));
589 argv[NFS_STATUS] = buf;
590 argv[NFS_ALLOC] = stringval(form, 5);
591 argv[NFS_SIZE] = stringval(form, 6);
594 StoreHost(form, NFS_NAME, &argv[NFS_NAME]);
595 if (!strcmp(form->formname, "mod_nfs")) {
596 qy = "update_nfsphys";
598 StoreHost(form, NFS_NAME, &argv[NFS_NAME]);
599 sprintf(buf, "%d", atoi(stringval(form, NFS_STATUS)) +
600 (boolval(form, 4) ? MR_FS_GROUPQUOTA : 0));
601 argv[NFS_STATUS] = buf;
602 argv[NFS_ALLOC] = stringval(form, 5);
603 argv[NFS_SIZE] = stringval(form, 6);
606 form->extrastuff = (caddr_t) "mod_nfs";
607 retfunc = ModifyCallback;
610 StoreHost(form, NFS_NAME, &argv[NFS_NAME]);
613 if (!*stringval(form, 0))
615 if (*stringval(form, 1)) {
617 argv[2] = stringval(form, 1);
618 } else if (*stringval(form, 2)) {
620 argv[2] = stringval(form, 2);
621 } else if (!*stringval(form, 0)) {
622 display_error("Must specify something.");
625 qy = "get_quota_by_filesys";
632 StoreHost(form, 0, &argv[0]);
635 if (!strcmp(form->formname, "mod_machine")) {
636 qy = "update_machine";
637 for (i = 0; i < M_MODTIME; i++)
638 argv[i + 1] = StringValue(form, i);
639 argv[0] = form->extrastuff;
640 argc = M_MODTIME + 1;
643 StoreHost(form, 0, &argv[0]);
644 form->extrastuff = (caddr_t) "mod_machine";
645 retfunc = ModifyCallback;
648 if (!strcmp(form->formname, "mod_cluster")) {
649 qy = "update_cluster";
650 for (i = 0; i < C_MODTIME; i++)
651 argv[i + 1] = StringValue(form, i);
652 argv[0] = form->extrastuff;
653 argc = C_MODTIME + 1;
656 form->extrastuff = (caddr_t) "mod_cluster";
657 retfunc = ModifyCallback;
660 if (!*stringval(form, 0))
663 StoreHost(form, 0, &argv[0]);
664 if (!*stringval(form, 1))
666 AppendToLog("Cluster mappings:\n");
670 StoreHost(form, 0, &argv[0]);
673 if (!*stringval(form, 1))
677 StoreHost(form, PCAP_SPOOL_HOST, &argv[PCAP_SPOOL_HOST]);
678 StoreHost(form, PCAP_QSERVER, &argv[PCAP_QSERVER]);
681 if (!strcmp(form->formname, "mod_printer")) {
682 qy = "update_printcap_entry";
686 form->extrastuff = (caddr_t) "mod_printer";
687 retfunc = ModifyCallback;
690 if (!strcmp(form->formname, "mod_service")) {
691 qy = "update_server_info";
695 form->extrastuff = (caddr_t) "mod_service";
696 retfunc = ModifyCallback;
699 if (!*stringval(form, 0))
701 if (!*stringval(form, 1))
704 StoreHost(form, 1, &argv[1]);
707 if (!strcmp(form->formname, "mod_host")) {
708 qy = "update_server_host_info";
712 StoreHost(form, 1, &argv[1]);
713 form->extrastuff = (caddr_t) "mod_host";
714 retfunc = ModifyCallback;
717 if (!write_log_to_file(stringval(form, 0)) && remove)
718 XtUnmanageChild(form->formpointer);
721 argv[0] = form->extrastuff;
723 argv[2] = StringValue(form, 0);
724 for (s = argv[2]; *s; s++)
725 if (islower(*s)) *s = toupper(*s);
730 display_error("Unknown function in form callback.\n");
733 i = MoiraQuery(qy, argc, argv, retfunc, (char *)form);
735 com_err(program_name, i, " executing database query");
740 if (form->extrastuff && (f = GetForm((char *)(form->extrastuff)))) {
741 if (form->formpointer)
742 XtUnmanageChild(form->formpointer);
743 f->extrastuff = (caddr_t) strsave(stringval(form, 0));
744 f->menu = form->menu;
747 switch (form->menu->operation) {
750 f->inputlines[U_STATE]->keywords = user_states;
751 StoreField(f, U_STATE, user_states[atoi(stringval(f, U_STATE))]);
752 GetKeywords(f, U_CLASS, "class");
754 AppendToLog("Done.\n");
759 AppendToLog("Done.\n");
763 GetKeywords(f, L_ACE_TYPE, "ace_type");
764 f->inputlines[L_GROUP]->valuechanged = MoiraValueChanged;
765 f->inputlines[L_ACE_TYPE]->valuechanged = MoiraValueChanged;
767 AppendToLog("Done.\n");
771 GetKeywords(f, SC_TYPE, "service");
772 GetKeywords(f, SC_ACE_TYPE, "ace_type");
777 GetKeywords(f, FS_TYPE, "filesys");
778 sprintf(buf, "fs_access_%s", stringval(f, FS_TYPE));
779 GetKeywords(f, FS_ACCESS, buf);
780 GetKeywords(f, FS_L_TYPE, "lockertype");
781 if (!strcmp(stringval(f, FS_MACHINE), "[NONE]"))
782 StoreField(f, FS_MACHINE, "\\[NONE\\]");
783 f->inputlines[FS_TYPE]->valuechanged = MoiraValueChanged;
785 AppendToLog("Done.\n");
789 GetKeywords(f, 1, "mac_type");
791 AppendToLog("Done.\n");
795 f->inputlines[3]->keywords = nfs_states;
797 AppendToLog("Done.\n");
799 case MM_DEL_ALL_MEMBER:
800 argv[1] = StringValue(form, 0);
801 argv[2] = StringValue(form, 1);
802 while (sq_get_data(form->extrastuff, &(argv[0]))) {
803 sprintf(buf, "Delete %s %s from list %s?", StringValue(form, 0),
804 StringValue(form, 1), argv[0]);
805 if (!boolval(form, 2) ||
806 AskQuestion(buf, "confirm_del_all")) {
807 i = MoiraQuery("delete_member_from_list", 3, argv,
808 DisplayCallback, NULL);
810 com_err(program_name, i, " while removing member from list");
812 sprintf(buf, "Member %s %s removed from list %s.\n",
813 argv[1], argv[2], argv[0]);
819 AppendToLog("Done.\n");
822 case MM_SHOW_FSGROUP:
823 while (sq_get_data(form->extrastuff, &aargv)) {
826 sq_destroy(form->extrastuff);
834 case MM_CLEAR_SERVICE:
835 case MM_RESET_SERVICE:
859 case MM_ADD_FS_ALIAS:
860 case MM_DEL_FS_ALIAS:
875 AppendToLog("Done.\n");
878 CacheNewValue(GetForm(form->menu->form), (int) form->menu->accel,
879 form->extrastuff, StringValue(form, 0));
882 if (remove && form->formpointer)
883 XtUnmanageChild(form->formpointer);
894 int (*retfunc)(), argc, i;
897 retfunc = DisplayCallback;
903 switch (m->operation) {
904 case MM_SHOW_MAILLIST:
905 argv[0] = argv[1] = argv[3] = "TRUE";
907 argv[4] = "DONTCARE";
908 AppendToLog("Public Mailinglists:\n");
911 argv[0] = "def_quota";
914 AppendToLog("Services and Hosts with failed updates:\n");
915 argv[0] = argv[2] = "DONTCARE";
917 i = MoiraQuery("qualified_get_server", 3, argv, retfunc, NULL);
918 if (i && i != MR_NO_MATCH)
919 com_err(program_name, i, " executing database query");
921 argv[1] = argv[2] = argv[3] = argv[5] = "DONTCARE";
923 i = MoiraQuery("qualified_get_server_host", 6, argv, retfunc, NULL);
924 if (i && i != MR_NO_MATCH)
925 com_err(program_name, i, " executing database query");
929 case MM_HELP_WILDCARDS:
930 case MM_HELP_AUTHORS:
933 case MM_HELP_KEYBOARD:
941 display_error("Unknown function in menu callback.\n");
944 i = MoiraQuery(qy, argc, argv, retfunc, (char *)&dummy);
946 com_err(program_name, i, " executing database query");