Magellan Linux

Diff of /trunk/mkinitrd-magellan/busybox/mailutils/mail.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 983 by niro, Fri Apr 24 18:33:46 2009 UTC revision 984 by niro, Sun May 30 11:32:42 2010 UTC
# Line 11  Line 11 
11    
12  static void kill_helper(void)  static void kill_helper(void)
13  {  {
14   // TODO!!!: is there more elegant way to terminate child on program failure?   if (G.helper_pid > 0) {
  if (G.helper_pid > 0)  
15   kill(G.helper_pid, SIGTERM);   kill(G.helper_pid, SIGTERM);
16     G.helper_pid = 0;
17     }
18  }  }
19    
20  // generic signal handler  // generic signal handler
# Line 26  static void signal_handler(int signo) Line 27  static void signal_handler(int signo)
27   }   }
28    
29   // SIGCHLD. reap zombies   // SIGCHLD. reap zombies
30   if (safe_waitpid(G.helper_pid, &err, WNOHANG) > 0)   if (safe_waitpid(G.helper_pid, &err, WNOHANG) > 0) {
31     if (WIFSIGNALED(err))
32     bb_error_msg_and_die("helper killed by signal %u", WTERMSIG(err));
33   if (WIFEXITED(err)) {   if (WIFEXITED(err)) {
34   G.helper_pid = 0;   G.helper_pid = 0;
35   if (WEXITSTATUS(err))   if (WEXITSTATUS(err))
36   bb_error_msg_and_die("child exited (%d)", WEXITSTATUS(err));   bb_error_msg_and_die("helper exited (%u)", WEXITSTATUS(err));
37   }   }
38     }
39  #undef err  #undef err
40  }  }
41    
42  void FAST_FUNC launch_helper(const char **argv)  void FAST_FUNC launch_helper(const char **argv)
43  {  {
44   // setup vanilla unidirectional pipes interchange   // setup vanilla unidirectional pipes interchange
45   int idx;   int i;
46   int pipes[4];   int pipes[4];
47    
48   xpipe(pipes);   xpipe(pipes);
49   xpipe(pipes+2);   xpipe(pipes + 2);
50    
51     // NB: handler must be installed before vfork
52     bb_signals(0
53     + (1 << SIGCHLD)
54     + (1 << SIGALRM)
55     , signal_handler);
56    
57   G.helper_pid = vfork();   G.helper_pid = vfork();
58   if (G.helper_pid < 0)   if (G.helper_pid < 0)
59   bb_perror_msg_and_die("vfork");   bb_perror_msg_and_die("vfork");
60   idx = (!G.helper_pid) * 2;  
61   xdup2(pipes[idx], STDIN_FILENO);   i = (!G.helper_pid) * 2; // for parent:0, for child:2
62   xdup2(pipes[3-idx], STDOUT_FILENO);   close(pipes[i + 1]); // 1 or 3 - closing one write end
63   if (ENABLE_FEATURE_CLEAN_UP)   close(pipes[2 - i]); // 2 or 0 - closing one read end
64   for (int i = 4; --i >= 0; )   xmove_fd(pipes[i], STDIN_FILENO); // 0 or 2 - using other read end
65   if (pipes[i] > STDOUT_FILENO)   xmove_fd(pipes[3 - i], STDOUT_FILENO); // 3 or 1 - other write end
66   close(pipes[i]);  
67   if (!G.helper_pid) {   if (!G.helper_pid) {
68   // child: try to execute connection helper   // child: try to execute connection helper
69     // NB: SIGCHLD & SIGALRM revert to SIG_DFL on exec
70   BB_EXECVP(*argv, (char **)argv);   BB_EXECVP(*argv, (char **)argv);
71   _exit(127);   _exit(127);
72   }   }
73   // parent: check whether child is alive  
74   bb_signals(0   // parent
75   + (1 << SIGCHLD)   // check whether child is alive
76   + (1 << SIGALRM)   //redundant:signal_handler(SIGCHLD);
  , signal_handler);  
  signal_handler(SIGCHLD);  
77   // child seems OK -> parent goes on   // child seems OK -> parent goes on
78   atexit(kill_helper);   atexit(kill_helper);
79  }  }
# Line 77  const FAST_FUNC char *command(const char Line 87  const FAST_FUNC char *command(const char
87   msg = xasprintf(fmt, param);   msg = xasprintf(fmt, param);
88   printf("%s\r\n", msg);   printf("%s\r\n", msg);
89   }   }
90   fflush(stdout);   fflush_all();
91   return msg;   return msg;
92  }  }
93    
# Line 226  void FAST_FUNC decode_base64(FILE *src_s Line 236  void FAST_FUNC decode_base64(FILE *src_s
236   */   */
237  void FAST_FUNC get_cred_or_die(int fd)  void FAST_FUNC get_cred_or_die(int fd)
238  {  {
  // either from TTY  
239   if (isatty(fd)) {   if (isatty(fd)) {
240   G.user = xstrdup(bb_askpass(0, "User: "));   G.user = xstrdup(bb_ask(fd, /* timeout: */ 0, "User: "));
241   G.pass = xstrdup(bb_askpass(0, "Password: "));   G.pass = xstrdup(bb_ask(fd, /* timeout: */ 0, "Password: "));
  // or from STDIN  
242   } else {   } else {
243   FILE *fp = fdopen(fd, "r");   G.user = xmalloc_reads(fd, /* pfx: */ NULL, /* maxsize: */ NULL);
244   G.user = xmalloc_fgetline(fp);   G.pass = xmalloc_reads(fd, /* pfx: */ NULL, /* maxsize: */ NULL);
  G.pass = xmalloc_fgetline(fp);  
  fclose(fp);  
245   }   }
246   if (!G.user || !*G.user || !G.pass || !*G.pass)   if (!G.user || !*G.user || !G.pass)
247   bb_error_msg_and_die("no username or password");   bb_error_msg_and_die("no username or password");
248  }  }

Legend:
Removed from v.983  
changed lines
  Added in v.984