]> andersk Git - moira.git/blame - clients/mailmaint/mailmaint.c
build libmrclient
[moira.git] / clients / mailmaint / mailmaint.c
CommitLineData
c441a31a 1/* $Id$
7ac48069 2 *
3 * Simple add-me-to/remove-me-from list client
4 *
5 * mailmaint.c - pjlevine - 20 August 1987
6 *
7 * Copyright (C) 1988-1998 by the Massachusetts Institute of Technology.
8 * For copying and distribution information, please see the file
9 * <mit-copyright.h>.
3b3cb07f 10 */
11
7ac48069 12#include <mit-copyright.h>
13#include <moira.h>
14#include <moira_site.h>
3b3cb07f 15
7ac48069 16#include <ctype.h>
ea0caf4a 17#ifdef HAVE_CURSES
3b3cb07f 18#include <curses.h>
ea0caf4a 19#endif
7ac48069 20#include <pwd.h>
21#include <stdio.h>
5eaef520 22#include <stdlib.h>
7ac48069 23#include <string.h>
24#include <unistd.h>
3b3cb07f 25
7a40dcd4 26#include <krb.h>
27
7ac48069 28RCSID("$Header$");
c1102c07 29
3b3cb07f 30#define STARTCOL 0
31#define STARTROW 3
3b3cb07f 32#define DISPROW 15
33#define LISTMAX 50
34#define LISTSIZE 32
5eaef520 35#define CTL(ch) ((ch) & 037)
6d6e2701 36#ifdef MAX
37#undef MAX
38#endif
5eaef520 39#define MAX(A, B) ((A) > (B) ? (A) : (B))
3b3cb07f 40
c7c64ef0 41char *whoami; /* should not be static, for logging package */
3b3cb07f 42static int status;
3b3cb07f 43
44typedef struct list_info {
5eaef520 45 int active;
46 int public;
47 int hidden;
48 int maillist;
49 int group;
50 char *acl_type;
51 char *acl_name;
52 char *desc;
53 char *modtime;
54 char *modby;
55 char *modwith;
56} List_info;
0faf7bee 57
58static char *ascbuff = {"0123456789"};
3b3cb07f 59static List_info *current_li = (List_info *) NULL;
3b3cb07f 60
3b3cb07f 61typedef struct _menu {
5eaef520 62 int num_items;
63 char *title;
64 char **items;
65} MENU;
3b3cb07f 66
67MENU *main_menu, *help_menu;
68
69int position[2], oldpos[2];
70int level, found_some, currow, page, num_members;
71int moreflg, toggle, first_time;
655d829e 72char *username;
3b3cb07f 73
7ac48069 74void get_main_input(void);
75void show_list_info(void);
76void display_buff(char *buf);
77void start_display_buff(char *buff);
78void add_member(void);
79void delete_member(void);
80void list_by_member(void);
81void show_all(void);
82static int print_1(int argc, char *argv[], void *callback);
83static int print_all(int argc, char *argv[], void *callback);
84void list_all_groups(void);
85void list_members(void);
86static int print_2(int argc, char *argv[], void *callback);
87void start_display(char *buff);
88void end_display(void);
89void display_menu(MENU *menu);
90void pack_main_menu(void);
91void pack_help_menu(void);
92void highlight(MENU *menu);
93void title(char *buff);
94void center_text(int row, char *buff);
95void show_text(int row, int col, char *buff);
96void erase_line(int row, int col);
97void cls(void);
98void clrwin(int erase_row);
99static int fetch_list_info(char *list, List_info *li);
100static int get_list_info(int argc, char **argv, void *hint);
101int Prompt(char *prompt, char *buf, int buflen, int crok);
102void menu_err_hook(const char *who, long code, const char *fmt, va_list args);
103
8f54c2a7 104/* This crock is because the original code was very broken and this makes
105 * it work. Someday, we should abandon the code or fix it right.
106 */
5eaef520 107#define mvcur(oy, ox, ny, nx) move(ny, nx)
3b3cb07f 108
109/****************************************************/
0faf7bee 110
5eaef520 111int main(int argc, char *argv[])
0faf7bee 112{
5eaef520 113 void (*old_hook)(const char *, long, const char *, va_list);
7a40dcd4 114 int use_menu = 1, k_errno;
115 char buf[BUFSIZ], pname[ANAME_SZ], *motd;
5eaef520 116
117 if ((whoami = strrchr(argv[0], '/')) == NULL)
118 whoami = argv[0];
119 else
120 whoami++;
121 if (!(current_li = malloc(sizeof(List_info))))
122 {
123 sprintf(buf, ": allocating list info");
124 goto punt;
0faf7bee 125 }
5eaef520 126 else
127 {
128 current_li->acl_type = NULL;
129 current_li->acl_name = NULL;
130 current_li->desc = NULL;
131 current_li->modtime = NULL;
132 current_li->modby = NULL;
133 current_li->modwith = NULL;
0faf7bee 134 }
7a40dcd4 135
136 if ((k_errno = tf_init(TKT_FILE, R_TKT_FIL)) ||
137 (k_errno = tf_get_pname(pname)))
138 {
139 com_err(whoami, k_errno, "reading Kerberos ticket file");
140 exit(1);
141 }
142 tf_close();
143 username = pname;
3b3cb07f 144
5eaef520 145 printf("Connecting to database for %s...please hold on.\n", username);
3b3cb07f 146
5eaef520 147 status = mr_connect(NULL);
148 if (status)
149 {
150 sprintf(buf, "\nConnection to Moira server failed");
151 goto punt;
0faf7bee 152 }
3b3cb07f 153
5eaef520 154 status = mr_motd(&motd);
155 if (status)
156 {
157 com_err(whoami, status, " unable to check server status");
158 mr_disconnect();
159 exit(2);
262ca740 160 }
5eaef520 161 if (motd)
162 {
163 fprintf(stderr, "The Moira server is currently unavailable:\n%s\n",
164 motd);
165 mr_disconnect();
166 exit(2);
262ca740 167 }
5eaef520 168 status = mr_auth("mailmaint");
169 if (status)
170 {
171 sprintf(buf, "\nAuthorization failed.\n");
172 goto punt;
0faf7bee 173 }
3b3cb07f 174
ea0caf4a 175 initscr();
176 if ((LINES < 24) || (COLS < 60))
5eaef520 177 {
ea0caf4a 178 display_buff("Display window too small.\n\n");
179 sprintf(buf, "Current window parameters are (%d lines, %d columns)\n",
180 LINES, COLS);
181 display_buff(buf);
182 display_buff("Please resize your window\n");
183 display_buff("to at least 24 lines and 60 columns.\n");
184 exit(0);
0faf7bee 185 }
ea0caf4a 186 raw();
187 noecho();
188 old_hook = set_com_err_hook(menu_err_hook);
189 position[0] = oldpos[0] = 1;
190 level = 0;
191 pack_main_menu();
192 pack_help_menu();
193 display_menu(main_menu);
194 get_main_input();
195 cls();
196 endwin();
197 set_com_err_hook(old_hook);
5eaef520 198 exit(0);
3b3cb07f 199
200punt:
5eaef520 201 com_err(whoami, status, buf);
202 exit(1);
3b3cb07f 203}
204
205/****************************************************/
7ac48069 206void get_main_input(void)
3b3cb07f 207{
5eaef520 208 int c;
209 int retflg;
210
211 while (1)
212 {
213 oldpos[level] = position[level];
214 retflg = 0;
215 currow = DISPROW + 2;
216 page = 1;
217 toggle = num_members = moreflg = 0;
218 c = getchar() & 0x7f; /* mask parity bit */
219 if (c == '\r' || c == '\n')
220 {
221 if (position[level] == 7)
222 c = 'q';
223 else
224 c = ascbuff[position[level]];
225 retflg = 1;
3b3cb07f 226 }
5eaef520 227 switch (c)
228 {
0faf7bee 229 case 'L' & 037: /* clear screen */
5eaef520 230 display_menu(main_menu);
231 break;
0faf7bee 232 case 'q':
233 case 'Q': /* quit */
5eaef520 234 position[level] = 7;
235 highlight(main_menu);
236 if (retflg)
237 {
238 cls();
239 return;
3b3cb07f 240 }
5eaef520 241 break;
0faf7bee 242 case '1': /* show all lists */
5eaef520 243 position[level] = 1;
244 if (retflg)
245 show_all();
246 break;
0faf7bee 247 case '2': /* get all members of a list */
5eaef520 248 position[level] = 2;
249 if (retflg)
250 list_members();
251 break;
0faf7bee 252 case '3': /* display list which user is a recipient */
5eaef520 253 position[level] = 3;
254 if (retflg)
255 list_by_member();
256 break;
0faf7bee 257 case '4': /* show description */
5eaef520 258 position[level] = 4;
259 if (retflg)
260 show_list_info();
261 break;
0faf7bee 262 case '5': /* add to list */
5eaef520 263 position[level] = 5;
264 if (retflg)
265 add_member();
266 break;
0faf7bee 267 case '6': /* delete */
5eaef520 268 position[level] = 6;
269 if (retflg)
270 delete_member();
271 break;
272 case 27: /* escape */
273 c = getchar() & 0x7f;
274 if (c == 91)
275 {
276 c = getchar() & 0x7f;
277 if (c == 65) /* up arrow */
278 {
279 position[level]--;
280 if (!position[level])
281 position[level] = 7;
3b3cb07f 282 }
5eaef520 283 else
284 {
285 if (c == 66) /* down arrow */
286 {
287 position[level]++;
288 if (position[level] > 7)
289 position[level] = 1;
3b3cb07f 290 }
291 }
292 }
5eaef520 293 break;
3b3cb07f 294 default:
5eaef520 295 printf("%c", 7);
296 break;
3b3cb07f 297 }
5eaef520 298 highlight(main_menu);
3b3cb07f 299 }
300}
0faf7bee 301
3b3cb07f 302/****************************************************/
7ac48069 303void show_list_info(void)
3b3cb07f 304{
5eaef520 305 char *buf;
306
307 show_text(DISPROW, STARTCOL, "Show information about a list.\n");
308 buf = calloc(1024, 1);
309 if (Prompt("Enter List Name: ", buf, LISTSIZE, 1) == 1)
310 {
311 display_buff("\n");
312 if (fetch_list_info(buf, current_li) == 0)
313 {
314 sprintf(buf, "Description: %s\n", current_li->desc);
315 if (strlen(buf) > 60)
316 display_buff(buf);
317 else
3b3cb07f 318 show_text(currow, STARTCOL, buf);
5eaef520 319 currow++;
320 sprintf(buf, "List Administrator: %s %s",
321 current_li->acl_type, current_li->acl_name);
322 show_text(currow, STARTCOL, buf);
323 currow++;
324 sprintf(buf, "Modified on %s by user %s with %s",
325 current_li->modtime, current_li->modby,
326 current_li->modwith);
327 show_text(currow, STARTCOL, buf);
328 currow++;
3b3cb07f 329 }
5eaef520 330 else
331 {
332 show_text(currow, STARTCOL, "mailmaint: No such list found.");
333 currow++;
3b3cb07f 334 }
5eaef520 335 show_text(currow, STARTCOL, "Press any Key to continue...");
336 getchar();
3b3cb07f 337 }
5eaef520 338 clrwin(DISPROW);
3b3cb07f 339}
0faf7bee 340
3b3cb07f 341/****************************************************/
7ac48069 342void display_buff(char *buf)
3b3cb07f 343{
5eaef520 344 int i, cnt;
345 char *printbuf;
346 int maxcol;
347
348 maxcol = COLS;
349
350 cnt = 0;
351 printbuf = calloc(maxcol, 1);
352 for (i = 0; i <= strlen(buf); i++)
353 {
354 printbuf[cnt] = buf[i];
355 cnt++;
356 if (cnt >= maxcol)
357 {
358 start_display_buff(printbuf);
359 cnt = 0;
360 free(printbuf);
361 printbuf = calloc(maxcol, 1);
3b3cb07f 362 }
363 }
5eaef520 364 if (strlen(buf) % maxcol != 0)
365 {
366 start_display_buff(printbuf);
367 free(printbuf);
3b3cb07f 368 }
7ac48069 369 return;
3b3cb07f 370}
0faf7bee 371
3b3cb07f 372/****************************************************/
7ac48069 373void start_display_buff(char *buff)
3b3cb07f 374{
5eaef520 375 char buffer[5];
376
377 num_members++;
378 if (moreflg)
7ac48069 379 return;
5eaef520 380 if (currow >= LINES - 2)
381 {
382 page++;
383 currow++;
384 mvcur(0, 0, currow, STARTCOL);
385 refresh();
386 if (Prompt("--RETURN for more, ctl-c to exit--", buffer, 1, 0) == 0)
387 {
388 erase_line(currow, STARTCOL);
389 show_text(currow, STARTCOL, "Flushing query...");
390 moreflg = 1;
7ac48069 391 return;
3b3cb07f 392 }
5eaef520 393 clrwin(DISPROW + 2);
394 currow = DISPROW + 2;
395 show_text(currow, STARTCOL, "continued");
396 currow++;
3b3cb07f 397 }
5eaef520 398 show_text(currow, STARTCOL, buff);
399 currow++;
7ac48069 400 return;
3b3cb07f 401}
0faf7bee 402
3b3cb07f 403/****************************************************/
7ac48069 404void add_member(void)
3b3cb07f 405{
5eaef520 406 char *argv[3];
407 char *buf;
408
409 show_text(DISPROW, STARTCOL, "Add yourself to a list\n");
410 buf = calloc(LISTMAX, 1);
411 if (Prompt("Enter List Name: ", buf, LISTSIZE, 1) == 1)
412 {
413 display_buff("\n");
7ac48069 414 argv[0] = strdup(buf);
415 argv[1] = strdup("user");
416 argv[2] = strdup(username);
417 if ((status = mr_query("add_member_to_list", 3, argv, NULL, NULL)))
5eaef520 418 {
419 display_buff("\n");
420 com_err(whoami, status, " found.\n");
3b3cb07f 421 }
5eaef520 422 else
423 {
424 sprintf(buf, "User %s added to list\n", username);
425 show_text(DISPROW + 3, STARTCOL, buf);
3b3cb07f 426 }
5eaef520 427 currow = DISPROW + 4;
428 show_text(DISPROW + 4, STARTCOL, "Press any Key to continue...");
429 getchar();
3b3cb07f 430 }
5eaef520 431 clrwin(DISPROW);
3b3cb07f 432}
433
434/****************************************************/
7ac48069 435void delete_member(void)
3b3cb07f 436{
5eaef520 437 char *argv[3];
438 char *buf;
439
440 show_text(DISPROW, STARTCOL, "Remove yourself from a list\n");
441 buf = calloc(LISTMAX, 1);
442 if (Prompt("Enter List Name: ", buf, LISTSIZE, 1) == 1)
443 {
444 display_buff("\n");
7ac48069 445 argv[0] = strdup(buf);
446 argv[1] = strdup("user");
447 argv[2] = strdup(username);
448 if ((status = mr_query("delete_member_from_list", 3, argv, NULL, NULL)))
5eaef520 449 {
450 display_buff("\n");
451 com_err(whoami, status, " found.\n");
3b3cb07f 452 }
5eaef520 453 else
454 {
455 sprintf(buf, "User %s deleted from list\n", username);
456 show_text(DISPROW + 3, STARTCOL, buf);
3b3cb07f 457 }
5eaef520 458 currow = DISPROW + 4;
459 show_text(DISPROW + 4, STARTCOL, "Press any Key to continue...");
460 getchar();
3b3cb07f 461 }
5eaef520 462 clrwin(DISPROW);
3b3cb07f 463}
3b3cb07f 464
0faf7bee 465/****************************************************/
7ac48069 466void list_by_member(void)
3b3cb07f 467{
5eaef520 468 char *nargv[3];
469 char *buf;
470
7ac48069 471 nargv[1] = strdup("ruser");
472 nargv[2] = strdup(username);
5eaef520 473 buf = calloc(BUFSIZ, 1);
474 sprintf(buf, "%s is on the following lists:\n", username);
475 show_text(DISPROW, STARTCOL, buf);
476 mvcur(0, 0, currow, STARTCOL);
477 refresh();
478 if ((status = mr_query("get_lists_of_member", 2, nargv + 1, print_1, NULL)))
479 {
480 display_buff("\n");
481 com_err(whoami, status, " in get_lists_of_member");
3b3cb07f 482 }
5eaef520 483 currow++;
484 show_text(currow, STARTCOL, "Press any Key to continue...");
485 getchar();
486 clrwin(DISPROW);
3b3cb07f 487}
0faf7bee 488
3b3cb07f 489/****************************************************/
7ac48069 490void show_all(void)
3b3cb07f 491{
5eaef520 492 char c;
493
494 show_text(DISPROW, STARTCOL, "This function may take a while... proceed? [n] ");
495 c = getchar() & 0x7f;
496 if (c == 'y' || c == 'Y')
497 {
498 move(DISPROW + 1, STARTCOL);
499 addstr("Processing query...please hold");
500 refresh();
501 list_all_groups();
3b3cb07f 502 }
5eaef520 503 else
504 erase_line(DISPROW, STARTCOL);
3b3cb07f 505}
506
507/****************************************************/
7ac48069 508static int print_1(int argc, char *argv[], void *callback)
3b3cb07f 509{
5eaef520 510 char buf[BUFSIZ];
3b3cb07f 511
5eaef520 512 /* no newline 'cause display_buff adds one */
513 sprintf(buf, "%s\n", argv[0]);
514 start_display(buf);
3b3cb07f 515
7ac48069 516 return MR_CONT;
3b3cb07f 517}
0faf7bee 518
3b3cb07f 519/****************************************************/
7ac48069 520static int print_all(int argc, char *argv[], void *callback)
0faf7bee 521{
5eaef520 522 char buf[BUFSIZ];
523
524 if (moreflg)
525 return 0;
526 if (first_time)
527 {
528 erase_line(DISPROW + 1, STARTCOL);
529 show_text(DISPROW + 1, STARTCOL, "All mailing lists:");
530 first_time = 0;
0faf7bee 531 }
5eaef520 532 sprintf(buf, "%s\n", argv[0]);
533 start_display(buf);
0faf7bee 534
7ac48069 535 return MR_CONT;
3b3cb07f 536}
537
538/****************************************************/
7ac48069 539void list_all_groups(void)
3b3cb07f 540{
5eaef520 541 char *argv[5];
542 argv[0] = argv[1] = argv[3] = "true";
543 argv[4] = "dontcare";
544 argv[2] = "false";
545 first_time = 1;
546 if ((status = mr_query("qualified_get_lists", 5, argv, print_all, NULL)))
547 {
548 display_buff("\n");
549 com_err(whoami, status, " in list_all_groups\n");
3b3cb07f 550 }
5eaef520 551 end_display();
3b3cb07f 552}
0faf7bee 553
3b3cb07f 554/****************************************************/
7ac48069 555void list_members(void)
3b3cb07f 556{
5eaef520 557 char *argv[1];
558 char *buf;
559 char buffer[80];
560
561 found_some = 0;
562 move(DISPROW, STARTCOL);
563 mvcur(0, 0, DISPROW, STARTCOL);
564 refresh();
565 buf = calloc(LISTMAX, 1);
566 if (Prompt("Enter List Name: ", buf, LISTSIZE, 1) == 1)
567 {
568 sprintf(buffer, "The members of list '%s' are:", buf);
569 show_text(DISPROW + 1, STARTCOL, buffer);
570 argv[0] = buf;
571 if ((status = mr_query("get_members_of_list", 1, argv, print_2, NULL)))
572 {
573 display_buff("\n");
574 com_err(whoami, status, " found.\n");
575 currow++;
3b3cb07f 576 }
5eaef520 577 if (!found_some)
578 {
579 show_text(currow, STARTCOL, "List is empty (no members).");
580 currow++;
581 show_text(currow, STARTCOL, "Press any key to continue...");
582 getchar();
583 clrwin(DISPROW);
584 return;
3b3cb07f 585 }
5eaef520 586 end_display();
7ac48069 587 return;
3b3cb07f 588 }
5eaef520 589 clrwin(DISPROW);
3b3cb07f 590}
591
592/****************************************************/
7ac48069 593static int print_2(int argc, char *argv[], void *callback)
3b3cb07f 594{
5eaef520 595 char buf[BUFSIZ];
3b3cb07f 596
5eaef520 597 found_some = 1;
598 sprintf(buf, "%s %s", argv[0], argv[1]);
599 start_display(buf);
3b3cb07f 600
7ac48069 601 return MR_CONT;
3b3cb07f 602}
0faf7bee 603
3b3cb07f 604/****************************************************/
7ac48069 605void start_display(char *buff)
3b3cb07f 606{
5eaef520 607 char *buffer;
608 int secondcol; /* where to start the second column of text */
609
610 secondcol = (COLS / 2); /* 1/2 was accross the screen */
611 num_members++;
612 if (moreflg)
7ac48069 613 return;
5eaef520 614 buffer = calloc(50, 1);
615 if (currow >= LINES - 2)
616 {
617 page++;
618 mvcur(0, 0, currow, STARTCOL);
619 refresh();
620 if (Prompt("--RETURN for more, ctl-c to exit--", buffer, 1, 0) == 0)
621 {
622 erase_line(currow, STARTCOL);
623 show_text(currow, STARTCOL, "Flushing query...");
624 moreflg = 1;
7ac48069 625 return;
3b3cb07f 626 }
5eaef520 627 clrwin(DISPROW + 2);
628 currow = DISPROW + 2;
629 sprintf(buffer, "Continued (Page %d)", page);
630 show_text(currow, STARTCOL, buffer);
631 currow++;
632 toggle = 0;
3b3cb07f 633 }
5eaef520 634 if (!toggle)
635 show_text(currow, STARTCOL, buff);
636 else
637 {
638 erase_line(currow, secondcol - 1); /* in case the 1st col is too long */
639 show_text(currow, secondcol, buff);
640 currow++;
3b3cb07f 641 }
5eaef520 642 toggle = !toggle;
3b3cb07f 643}
0faf7bee 644
3b3cb07f 645/****************************************************/
7ac48069 646void end_display(void)
3b3cb07f 647{
5eaef520 648 char *buffer;
3b3cb07f 649
5eaef520 650 if (moreflg)
651 {
652 clrwin(DISPROW);
653 return;
3b3cb07f 654 }
655
5eaef520 656 buffer = calloc(50, 1);
657 currow++;
658 sprintf(buffer, "End of List. %d Total Members\n", num_members - 1);
659 show_text(currow, STARTCOL, buffer);
660 currow++;
661 show_text(currow, STARTCOL, "Press any key to continue...");
662 getchar();
663 clrwin(DISPROW);
3b3cb07f 664}
0faf7bee 665
3b3cb07f 666/****************************************************/
7ac48069 667void display_menu(MENU *menu)
3b3cb07f 668{
5eaef520 669 int i;
670
671 cls();
672 title(menu->title);
673 mvcur(0, 0, STARTROW, STARTCOL);
674 refresh();
675 for (i = 0; i <= menu->num_items - 1; i++)
676 {
677 move(STARTROW + i, STARTCOL);
678 standend();
679 addstr(menu->items[i]);
680 refresh();
681 }
682 center_text(STARTROW + menu->num_items + 2,
683 "Enter a number, <up arrow>, or <down arrow>.");
684 if (!level)
685 {
686 center_text(STARTROW + menu->num_items + 3,
687 "Press 'q' to exit, <return> to confirm choice.");
688 }
689 else
690 {
691 center_text(STARTROW + menu->num_items + 3,
692 "Press 'q' to exit, 'r' for main menu, "
693 "<return> to confirm choice.");
3b3cb07f 694 }
5eaef520 695
696 if (!level)
697 highlight(main_menu);
0faf7bee 698}
3b3cb07f 699
700/****************************************************/
7ac48069 701void pack_main_menu(void)
3b3cb07f 702{
5eaef520 703 char *buf;
704
705 main_menu = malloc(sizeof(MENU));
706 main_menu->num_items = 7;
707 main_menu->items = malloc(sizeof(char *) * main_menu->num_items);
708
709 buf = calloc(50, 1);
710 sprintf(buf, "Mail List Program for %s", username);
7ac48069 711 main_menu->title = strdup(buf);
712 main_menu->items[0] = strdup("1. Show all public mailing lists.");
713 main_menu->items[1] = strdup("2. Get all members of a mailing list.");
714 main_menu->items[2] = strdup("3. Display lists of which you are a member.");
715 main_menu->items[3] = strdup("4. Show description of list.");
716 main_menu->items[4] = strdup("5. Add yourself to a mailing list.");
717 main_menu->items[5] = strdup("6. Delete yourself from a mailing list.");
718 main_menu->items[6] = strdup("q. Quit.");
3b3cb07f 719}
720
721/****************************************************/
7ac48069 722void pack_help_menu(void)
3b3cb07f 723{
5eaef520 724 help_menu = malloc(sizeof(MENU));
725 help_menu->num_items = 5;
726 help_menu->items = malloc(sizeof(char *) * help_menu->num_items);
727
7ac48069 728 help_menu->title = strdup("mailmaint is designed as a basic mail list administration program.");
729 help_menu->items[0] = strdup("if you need to perform more advanced list manipulation like");
730 help_menu->items[1] = strdup("adding lists, or changing list characteristics, refer to the");
731 help_menu->items[2] = strdup("program listmaint.");
732 help_menu->items[3] = strdup(" ");
733 help_menu->items[4] = strdup("Press any key to continue.");
3b3cb07f 734}
3b3cb07f 735
3b3cb07f 736/****************************************************/
7ac48069 737void highlight(MENU *menu)
3b3cb07f 738{
5eaef520 739 if (oldpos[level] != position[level])
740 {
741 move(STARTROW + oldpos[level] - 1, STARTCOL);
742 standend();
743 addstr(menu->items[oldpos[level] - 1]);
744 refresh();
3b3cb07f 745 }
746
5eaef520 747 move(STARTROW + position[level] - 1, STARTCOL);
748 standout();
749 addstr(menu->items[position[level] - 1]);
750 refresh();
751 standend();
752 refresh();
3b3cb07f 753}
754
755/****************************************************/
7ac48069 756void title(char *buff)
3b3cb07f 757{
2349681b 758 move(0, MAX(0, (COLS - (int)strlen(buff)) >> 1));
5eaef520 759 standout();
760 addstr(buff);
761 refresh();
762 standend();
3b3cb07f 763}
764
3b3cb07f 765/****************************************************/
7ac48069 766void center_text(int row, char *buff)
3b3cb07f 767{
2349681b 768 move(row, MAX(0, (COLS - (int)strlen(buff)) >> 1));
5eaef520 769 addstr(buff);
770 refresh();
3b3cb07f 771}
772
773/****************************************************/
7ac48069 774void show_text(int row, int col, char *buff)
3b3cb07f 775{
5eaef520 776 mvcur(0, 0, row, col);
777 addstr(buff);
778 refresh();
3b3cb07f 779}
780
781/****************************************************/
7ac48069 782void erase_line(int row, int col)
3b3cb07f 783{
5eaef520 784 char *buff;
785 int i;
786
787 buff = calloc(COLS, 1);
788 for (i = 0; i <= COLS - 2; i++)
789 buff[i] = ' ';
790 buff[i] = 0; /* just to be sure ! */
791 move(row, col);
792 mvcur(0, 0, row, col);
793 addstr(buff);
794 refresh();
795 free(buff); /* close mem. leak */
3b3cb07f 796}
797
798/****************************************************/
7ac48069 799void cls(void)
3b3cb07f 800{
5eaef520 801 clear();
802 refresh();
3b3cb07f 803}
804
805/****************************************************/
7ac48069 806void clrwin(int erase_row)
3b3cb07f 807{
5eaef520 808 int i;
809 char *buff;
810 int maxcol;
811
812 maxcol = COLS;
813
814 buff = calloc(maxcol + 1, 1);
815 for (i = 0; i <= maxcol - 1; i++)
816 buff[i] = ' ';
817 buff[i] = 0; /* just to be sure ! */
818 mvcur(0, 0, erase_row, STARTCOL);
819 refresh();
820 for (i = erase_row; i <= currow - 1; i++)
8f54c2a7 821 addstr(buff);
5eaef520 822 addstr(buff);
823 mvcur(erase_row, STARTCOL, STARTROW + oldpos[level] - 1, STARTCOL);
824 refresh();
825 free(buff);
3b3cb07f 826}
827
3b3cb07f 828/****************************************************/
5eaef520 829static int fetch_list_info(char *list, List_info *li)
3b3cb07f 830{
5eaef520 831 char *argv[1];
3b3cb07f 832
5eaef520 833 argv[0] = list;
834 return mr_query("get_list_info", 1, argv, get_list_info, NULL);
3b3cb07f 835}
836
7ac48069 837static int get_list_info(int argc, char **argv, void *hint)
0faf7bee 838{
5eaef520 839 if (current_li->acl_type)
840 free(current_li->acl_type);
7ac48069 841 current_li->acl_type = strdup(argv[7]);
5eaef520 842 if (current_li->acl_name)
843 free(current_li->acl_name);
7ac48069 844 current_li->acl_name = strdup(argv[8]);
5eaef520 845 if (current_li->desc)
846 free(current_li->desc);
7ac48069 847 current_li->desc = strdup(argv[9]);
5eaef520 848 if (current_li->modtime)
849 free(current_li->modtime);
7ac48069 850 current_li->modtime = strdup(argv[10]);
5eaef520 851 if (current_li->modby)
852 free(current_li->modby);
7ac48069 853 current_li->modby = strdup(argv[11]);
5eaef520 854 if (current_li->modwith)
855 free(current_li->modwith);
7ac48069 856 current_li->modwith = strdup(argv[12]);
857 return MR_CONT;
3b3cb07f 858}
859
860
3b3cb07f 861/****************************************************/
862/* Prompt the user for input */
5eaef520 863int Prompt(char *prompt, char *buf, int buflen, int crok)
3b3cb07f 864{
5eaef520 865 int c;
866 char *p;
867
868 addstr(prompt);
869 refresh();
870 for (p = buf; abs(strlen(p) - strlen(buf)) <= buflen;)
871 {
872 refresh();
873 c = getchar() & 0x7f;
874 switch (c)
875 {
3b3cb07f 876 case CTL('C'):
5eaef520 877 return 0;
3b3cb07f 878 case CTL('Z'):
5eaef520 879 return 0;
3b3cb07f 880 case CTL('L'):
5eaef520 881 cls();
882 display_menu(main_menu);
883 return 0;
3b3cb07f 884 case '\n':
885 case '\r':
5eaef520 886 if (crok)
887 display_buff("\n");
888 *p = '\0';
889 if (strlen(buf) < 1) /* only \n or \r in buff */
890 return -1;
891 else
892 return 1;
3b3cb07f 893 case '\b':
894 case '\177':
5eaef520 895 if (p > buf)
896 {
897 p--;
898 printf("\b \b");
3b3cb07f 899 }
5eaef520 900 break;
3b3cb07f 901 case CTL('U'):
902 case CTL('G'):
903 case CTL('['):
5eaef520 904 while (p-- > buf)
905 printf("\b \b");
906 p = buf;
907 break;
3b3cb07f 908 default:
5eaef520 909 if (abs(strlen(p) - strlen(buf)) >= buflen)
910 {
911 printf("%c", 7);
912 break;
3b3cb07f 913 }
5eaef520 914 if (isprint(c))
915 {
916 addch(c);
917 *p++ = c;
0faf7bee 918 }
5eaef520 919 else
920 putchar(CTL('G'));
921 break;
3b3cb07f 922 }
923 }
5eaef520 924 return 0;
3b3cb07f 925}
926
32e1a4a9 927
928/*
929 * Hook function to cause error messages to be printed through
930 * curses instead of around it.
931 */
932
5eaef520 933void menu_err_hook(const char *who, long code, const char *fmt, va_list args)
32e1a4a9 934{
5eaef520 935 char buf[BUFSIZ], *cp;
936
937 strcpy(buf, who);
938 for (cp = buf; *cp; cp++)
939 ;
940 *cp++ = ':';
941 *cp++ = ' ';
942 if (code)
943 {
944 strcpy(cp, error_message(code));
945 while (*cp)
946 cp++;
32e1a4a9 947 }
5eaef520 948 vsprintf(cp, fmt, args);
949 display_buff(buf);
32e1a4a9 950}
This page took 0.375022 seconds and 5 git commands to generate.