home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 October / usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso / unix / volume18 / mush6.4 / part04 / main.c < prev    next >
Encoding:
C/C++ Source or Header  |  1989-03-12  |  8.3 KB  |  339 lines

  1. /* @(#)main.c    (c) copyright 10/18/86 (Dan Heller) */
  2.  
  3. #include "mush.h"
  4. #include "options.h"
  5.  
  6. #define PATCHDATE "3/12/89" /* Here because EVERYTHING depends on mush.h */
  7.  
  8. #if defined(sun) && defined(M_DEBUG)
  9. cpu()
  10. {
  11.     print("CPU time limit exceeded!\n");
  12. }
  13. #endif /* sun && DEBUG */
  14.  
  15. #ifdef LCKDFLDIR
  16. extern char *lckdfldir;
  17. #endif /* LCKDFLDIR */
  18.  
  19. #ifdef DOT_LOCK
  20. int sgid;
  21. #ifdef BSD
  22. int rgid;
  23. #endif /* BSD */
  24. #endif /* DOT_LOCK */
  25.  
  26. /*ARGSUSED*/   /* we ignore envp */
  27. main(argc, argv)
  28. char **argv;
  29. {
  30.     int              n;
  31.     char           buf[256];
  32.     register char    *p;
  33.     char        **args;
  34.     struct mush_flags Flags;
  35.  
  36. #ifdef LCKDFLDIR
  37.     lckdfldir = LCKDFLDIR;
  38. #endif /* LCKDFLDIR */
  39.     if (prog_name = rindex(*argv, '/'))
  40.     prog_name++;
  41.     else
  42.     prog_name = *argv;
  43.  
  44.     (void) signal(SIGBUS,  bus_n_seg);
  45.     (void) signal(SIGSEGV, bus_n_seg);
  46.     (void) signal(SIGPIPE, SIG_IGN); /* if pager is terminated before end */
  47.  
  48. #if defined(sun) && defined(M_DEBUG)
  49.     (void) signal(SIGXCPU, cpu);
  50.  
  51.     if (p = getenv("MALLOC_DEBUG"))
  52.     malloc_debug(atoi(p));
  53.     else
  54.     malloc_debug(0);
  55. #endif /* sun && debug */
  56.  
  57.     if (!isatty(0))
  58.     turnon(glob_flags, REDIRECT);
  59.  
  60.     n = 0; /* don't ignore no such file or directory */
  61.     p = getpath(COMMAND_HELP, &n);
  62.  
  63.     if (n)
  64.     cmd_help = "cmd_help";
  65.     else
  66.     strdup(cmd_help, p);
  67.  
  68.     init(); /* must be done before checking mail since "login" is set here */
  69. #ifdef HOMEMAIL
  70.     {
  71.     char *home = do_set(set_options, "home");
  72.     if (!home)
  73.         home = "";
  74.     strdup(spoolfile, sprintf(buf, "%s/%s", home, MAILFILE));
  75.     }
  76. #else /* HOMEMAIL */
  77.     strdup(spoolfile, sprintf(buf, "%s/%s", MAILDIR, login));
  78. #endif /* HOMEMAIL */
  79.  
  80.     args = DUBL_NULL;
  81.     n = preparse_opts(&argc,argv,&args);
  82.  
  83.     /* check for any mail at all and exit if we're not continuing */
  84.     if (!n) {
  85.     struct stat statb;
  86.     if (stat(spoolfile, &statb) || statb.st_size == 0) {
  87.         printf("No mail for %s.\n", login);
  88.         exit(0);
  89.     }
  90.     }
  91.  
  92. #ifdef DOT_LOCK
  93.     sgid = getegid();
  94. #ifdef BSD
  95.     rgid = getgid();
  96.     setregid(sgid, rgid);
  97. #else
  98.     setgid(getgid());
  99. #endif /* BSD */
  100. #endif /* DOT_LOCK */
  101.  
  102.     parse_options(&argv, &Flags);
  103.  
  104.     if (Flags.source_rc) {
  105.     /* use cmd_line() in case DEFAULT_RC has expandable chars */
  106.     (void) cmd_line(sprintf(buf, "source %s", DEFAULT_RC), msg_list);
  107.     (void) source(0, DUBL_NULL);
  108.     }
  109.     if (*spoolfile != '/') {
  110.     n = 1;
  111.     p = getpath(spoolfile, &n);
  112.     if (n == -1)
  113.         fputs(p, stderr), exit(1);
  114.     else if (n)
  115.         fprintf(stderr, "\"%s\" is a directory.\n", p), exit(1);
  116.     else
  117.         strdup(spoolfile, p);
  118.     }
  119.  
  120.     set_cwd();  /* call _after_ sourcing files */
  121.  
  122. #ifdef SUNTOOL
  123.     if (istool)
  124.     if (ison(glob_flags, REDIRECT))
  125.         puts("You can't redirect input to a tool."), exit(1);
  126.     else
  127.         make_tool(args), turnon(glob_flags, DO_SHELL);
  128. #endif /* SUNTOOL */
  129.  
  130.     /* now we're ready for I/O */
  131.     if (isoff(glob_flags, REDIRECT)) {
  132.     /* make sure we can always recover from no echo mode */
  133.     (void) signal(SIGINT, catch);
  134.     (void) signal(SIGQUIT, catch);
  135.     (void) signal(SIGHUP, catch);
  136.     if (istool)
  137.         turnon(glob_flags, ECHO_FLAG);
  138.     tty_settings();
  139. #ifdef SIGCONT
  140.     (void) signal(SIGTSTP, stop_start); /* this will take care of SIGCONT */
  141. #endif /* SIGCONT */
  142.     /* echo_off() checks to see if echo_flg is set, so don't worry */
  143.     echo_off();
  144.     }
  145.  
  146.     if (!istool && *argv) { /* we could check IS_SENDING */
  147.     char recipients[BUFSIZ];
  148.     (void) argv_to_string(recipients, argv);
  149.     fix_up_addr(recipients);
  150.     if (Flags.Cc && *(Flags.Cc))
  151.         fix_up_addr(Flags.Cc);
  152.     if (Flags.Bcc && *(Flags.Bcc))
  153.         fix_up_addr(Flags.Bcc);
  154.     /* prompt for subject and Cc list, but not "To: "
  155.      * mail_someone() already takes care of redirection.
  156.      * if -s or -c options are given, they will be passed.
  157.      */
  158.     if (do_set(set_options, "ask"))
  159.         turnon(Flags.flg, NEW_SUBJECT);
  160.     if (do_set(set_options, "autosign"))
  161.         turnon(Flags.flg, SIGN);
  162.     if (do_set(set_options, "autoedit"))
  163.         turnon(Flags.flg, EDIT);
  164.     if (do_set(set_options, "verbose"))
  165.         turnon(Flags.flg, VERBOSE);
  166.     if (do_set(set_options, "fortune"))
  167.         turnon(Flags.flg, DO_FORTUNE);
  168.     /* set now in case user is not running shell, but is running debug */
  169.     (void) signal(SIGCHLD, sigchldcatcher);
  170.     if (!setjmp(jmpbuf))
  171.         (void) mail_someone(recipients,
  172.                 Flags.Subj,
  173.                 Flags.Cc,
  174.                 Flags.Bcc,
  175.                 Flags.flg,
  176.                 NULL);
  177.     /* do shell set from above: "mush -S user" perhaps */
  178.     if (isoff(glob_flags, DO_SHELL) && !*mailfile) {
  179.         if (isoff(glob_flags, REDIRECT))
  180.         echo_on();
  181.         exit(0);
  182.     }
  183.     }
  184.     turnoff(glob_flags, IS_SENDING); /* no longer sending mail; running shell */
  185.  
  186.     if (ison(glob_flags, REDIRECT)) {
  187.     puts("You can't redirect input unless you're sending mail.");
  188.     puts("If you want to run a shell with redirection, use \"-i\"");
  189.     cleanup(0);
  190.     }
  191.     if (!*mailfile) {
  192.     strdup(mailfile, spoolfile);
  193.     if (!mail_size() && isoff(glob_flags, DO_SHELL)) {
  194.         /* we know it's not the spool file here */
  195.         printf("No mail in %s.\n", mailfile);
  196.         echo_on(), exit(0);
  197.     }
  198.     }
  199.  
  200.     if (!hdrs_only) {
  201.     /* catch will test DO_SHELL and try to longjmp if set.  this is a
  202.      * transition state from no-shell to do-shell to ignore sigs to
  203.      * avoid a longjmp botch.  Note setjmp isn't called until do_loop().
  204.      */
  205.     turnon(glob_flags, IGN_SIGS);
  206. #ifdef CURSES
  207.     if (ison(glob_flags, PRE_CURSES))
  208.         (void) curses_init(0, DUBL_NULL);
  209.     turnoff(glob_flags, PRE_CURSES);
  210. #endif /* CURSES */
  211.     }
  212.  
  213.     /* find a free tmpfile */
  214.     if (!(p = do_set(set_options, "tmpdir")) &&
  215.     !(p = do_set(set_options, "home")))
  216. alted:
  217.     p = ALTERNATE_HOME;
  218.     {
  219.     int pid = getpid();
  220.     while (!Access(sprintf(tempfile, "%s/.%s%d", p, prog_name, pid++), F_OK))
  221.     ;
  222.     }
  223.     /* just create the file, make sure it's empty.  It'll close later and
  224.      * be reopened for reading only.
  225.      */
  226.     if (!(tmpf = mask_fopen(tempfile, "w"))) {
  227.     if (strcmp(p, ALTERNATE_HOME))
  228.         goto alted;
  229.     error("Can't create tempfile %s", tempfile);
  230.     cleanup(0);
  231.     }
  232.  
  233.     /* do pseudo-intelligent stuff with certain signals */
  234.     (void) signal(SIGINT,  catch);
  235.     (void) signal(SIGQUIT, catch);
  236.     (void) signal(SIGHUP,  catch);
  237.  
  238.     if (!hdrs_only && !istool && (!Flags.src_file || !Flags.src_n_exit) &&
  239.     !do_set(set_options, "quiet"))
  240.     printf("%s: Type '?' for help.\n", VERSION);
  241.  
  242.     (void) sprintf(buf, "folder %s %s", Flags.f_flags, mailfile);
  243.     if (argv = make_command(buf, TRPL_NULL, &argc)) {
  244.     if (folder(argc, argv, NULL) == -1 && isoff(glob_flags, DO_SHELL))
  245.         turnoff(glob_flags, IGN_SIGS), cleanup(0);
  246. #ifdef CURSES
  247.     if (iscurses)
  248.         (void) curses_help_msg(TRUE);
  249. #endif /* CURSES */
  250.     free_vec(argv);
  251.     }
  252.  
  253.     if (hdrs_only) {
  254.     (void) sprintf(buf, "headers %s", hdrs_only);
  255.     if (argv = make_command(buf, TRPL_NULL, &argc))
  256.         (void) do_hdrs(argc, argv, NULL);
  257.     cleanup(0);
  258.     }
  259.  
  260.     turnon(glob_flags, DO_SHELL);
  261.     if (istool && msg_cnt)
  262.     set_isread(current_msg);
  263.  
  264.     /* finally, if the user wanted to source a file to execute, do it now */
  265.     if (Flags.src_file) {
  266.     char *s_argv[2];
  267.     s_argv[1] = Flags.src_file;
  268.     (void) source(2, s_argv);
  269.     if (!istool && Flags.src_n_exit)
  270.         cleanup(0);
  271.     }
  272.  
  273. #ifdef SUNTOOL
  274.     if (istool) {
  275.     n = 0;
  276.     if (!tool_help) {
  277.         p = getpath(TOOL_HELP, &n);
  278.         if (n) {
  279.         fprintf(stderr, "Warning: can't read %s: %s\n", TOOL_HELP, p);
  280.         tool_help = "tool_help";
  281.         } else
  282.         strdup(tool_help, p);
  283.     }
  284.     if (time_out < 30)
  285.         time_out = 60;
  286.     turnoff(glob_flags, IGN_SIGS);
  287.     (void) do_hdrs(0, DUBL_NULL, NULL);
  288.     timerclear(&(mail_timer.it_interval));
  289.     timerclear(&(mail_timer.it_value));
  290.     mail_timer.it_value.tv_sec = time_out;
  291.     setitimer(ITIMER_REAL, &mail_timer, NULL);
  292.     (void) signal(SIGALRM, check_new_mail);
  293.     unlock_cursors();
  294.     while (!(tool->tl_flags & TOOL_DONE))
  295.         tool_select(tool, 1);
  296.     cleanup(0);
  297.     }
  298. #endif /* SUNTOOL */
  299.     do_loop();
  300. }
  301.  
  302. do_version()
  303. {
  304. #ifdef PATCHDATE
  305.     print("%s [%s]\n", VERSION, PATCHDATE);
  306. #else /* !PATCHDATE */
  307.     print("%s\n", VERSION);
  308. #endif /* PATCHDATE */
  309.     return -1;
  310. }
  311.  
  312. /* set the current working directory */
  313. set_cwd()
  314. {
  315.     char buf[MAXPATHLEN], cwd[MAXPATHLEN];
  316. #ifndef SYSV
  317.     extern char *getwd();
  318. #else /* SYSV */
  319.     extern char *getcwd();
  320. #endif /* SYSV */
  321.  
  322. #ifndef SYSV
  323.     if (getwd(cwd) == NULL)
  324. #else
  325.     if (getcwd(cwd, MAXPATHLEN) == NULL)
  326. #endif /* SYSV */
  327.     {
  328.     error("getcwd: %s", cwd);
  329.     (void) un_set(&set_options, "cwd");
  330.     } else {
  331.     char *argv[4];
  332.     argv[0] = "cwd";
  333.     argv[1] = "=";
  334.     argv[2] = cwd;
  335.     argv[3] = NULL;
  336.     (void) add_option(&set_options, argv);
  337.     }
  338. }
  339.