A read-eval loop function shared between mail.c and
source.c. Quits gracefully upon reading EOF. Expand '~' in pathnames. Upon startup in read mode, display first screenfull of from lines, instead of listing the whole mailbox. This is compatible with existing implementations. Do not display prompt when stdin is not a terminal.
Showing
1 changed file
with
63 additions
and
32 deletions
... | @@ -125,10 +125,20 @@ parse_opt (int key, char *arg, struct argp_state *state) | ... | @@ -125,10 +125,20 @@ parse_opt (int key, char *arg, struct argp_state *state) |
125 | 125 | ||
126 | static struct argp argp = { options, parse_opt, args_doc, doc }; | 126 | static struct argp argp = { options, parse_opt, args_doc, doc }; |
127 | 127 | ||
128 | static char * | ||
129 | mail_cmdline(void *closure, int cont) | ||
130 | { | ||
131 | struct mail_env_entry *pev = closure; | ||
132 | char *prompt = NULL; | ||
133 | |||
134 | if (mail_is_terminal()) | ||
135 | prompt = pev->set && pev->value != NULL ? pev->value : "? "; | ||
136 | return readline (prompt); | ||
137 | } | ||
138 | |||
128 | int | 139 | int |
129 | main (int argc, char **argv) | 140 | main (int argc, char **argv) |
130 | { | 141 | { |
131 | char *command = NULL, *cmd = NULL; | ||
132 | struct mail_env_entry *mode = NULL, *prompt = NULL; | 142 | struct mail_env_entry *mode = NULL, *prompt = NULL; |
133 | int modelen = 0; | 143 | int modelen = 0; |
134 | struct arguments args; | 144 | struct arguments args; |
... | @@ -153,12 +163,15 @@ main (int argc, char **argv) | ... | @@ -153,12 +163,15 @@ main (int argc, char **argv) |
153 | 163 | ||
154 | /* set up the default environment */ | 164 | /* set up the default environment */ |
155 | if (!getenv ("HOME")) | 165 | if (!getenv ("HOME")) |
156 | exit (1); /* FIXME: how to start with no $HOME ? */ | 166 | { |
157 | setenv ("DEAD", "~/dead.letter", 0); /* FIXME: expand ~ */ | 167 | char *p = util_get_homedir(); |
168 | setenv ("HOME", p, 0); | ||
169 | } | ||
170 | setenv ("DEAD", util_fullpath("~/dead.letter"), 0); | ||
158 | setenv ("EDITOR", "ed", 0); | 171 | setenv ("EDITOR", "ed", 0); |
159 | setenv ("LISTER", "ls", 0); | 172 | setenv ("LISTER", "ls", 0); |
160 | setenv ("MAILRC", "~/.mailrc", 0); /* FIXME: expand ~ */ | 173 | setenv ("MAILRC", util_fullpath("~/.mailrc"), 0); |
161 | setenv ("MBOX", "~/mbox", 0); /* FIXME: expand ~ */ | 174 | setenv ("MBOX", util_fullpath("~/mbox"), 0); |
162 | setenv ("PAGER", "more", 0); | 175 | setenv ("PAGER", "more", 0); |
163 | setenv ("SHELL", "sh", 0); | 176 | setenv ("SHELL", "sh", 0); |
164 | setenv ("VISUAL", "vi", 0); | 177 | setenv ("VISUAL", "vi", 0); |
... | @@ -267,7 +280,7 @@ main (int argc, char **argv) | ... | @@ -267,7 +280,7 @@ main (int argc, char **argv) |
267 | else if (mailbox_create (&mbox, args.file) != 0) | 280 | else if (mailbox_create (&mbox, args.file) != 0) |
268 | exit (EXIT_FAILURE); | 281 | exit (EXIT_FAILURE); |
269 | 282 | ||
270 | if (mailbox_open (mbox, MU_STREAM_READ) != 0) | 283 | if (mailbox_open (mbox, MU_STREAM_RDWR) != 0) |
271 | exit (EXIT_FAILURE); | 284 | exit (EXIT_FAILURE); |
272 | 285 | ||
273 | if (mailbox_messages_count (mbox, &total) != 0) | 286 | if (mailbox_messages_count (mbox, &total) != 0) |
... | @@ -283,38 +296,56 @@ main (int argc, char **argv) | ... | @@ -283,38 +296,56 @@ main (int argc, char **argv) |
283 | 296 | ||
284 | /* initial commands */ | 297 | /* initial commands */ |
285 | if ((util_find_env("header"))->set) | 298 | if ((util_find_env("header"))->set) |
286 | util_do_command ("from *"); | 299 | util_do_command ("z."); |
287 | 300 | ||
288 | prompt = util_find_env ("prompt"); | 301 | prompt = util_find_env ("prompt"); |
302 | mail_set_is_terminal(isatty(0)); | ||
303 | mail_mainloop(mail_cmdline, (void*) prompt, 1); | ||
304 | fprintf (ofile, "\n"); | ||
305 | util_do_command ("quit"); | ||
306 | return 0; | ||
307 | } | ||
308 | /* We should never reach this point */ | ||
309 | return 1; | ||
310 | } | ||
311 | |||
289 | 312 | ||
290 | while (1) | 313 | void |
314 | mail_mainloop(char *(*input) __P((void *, int)), void *closure, int do_history) | ||
315 | { | ||
316 | char *command, *cmd; | ||
317 | while ((command = (*input)(closure, 0)) != NULL) | ||
318 | { | ||
319 | int len = strlen (command); | ||
320 | while (command[len-1] == '\\') | ||
291 | { | 321 | { |
292 | int len; | 322 | char *buf; |
293 | if (command) | 323 | char *command2 = (*input) (closure, 1); |
294 | free (command); | 324 | |
295 | command = readline (prompt->set && prompt->value != NULL | 325 | if (!command2) |
296 | ? prompt->value : "? "); | ||
297 | len = strlen (command); | ||
298 | while (command[len-1] == '\\') | ||
299 | { | 326 | { |
300 | char *buf; | 327 | command[len-1] = 0; |
301 | char *command2 = readline ("> "); | 328 | break; |
302 | |||
303 | command[len-1] = '\0'; | ||
304 | buf = malloc ((len + strlen (command2)) * sizeof (char)); | ||
305 | strcpy (buf, command); | ||
306 | strcat (buf, command2); | ||
307 | free (command); | ||
308 | command = buf; | ||
309 | len = strlen (command); | ||
310 | } | 329 | } |
311 | cmd = util_stripwhite (command); | 330 | command[len-1] = '\0'; |
312 | util_do_command (cmd); | 331 | buf = malloc ((len + strlen (command2)) * sizeof (char)); |
332 | strcpy (buf, command); | ||
333 | strcat (buf, command2); | ||
334 | free (command); | ||
335 | command = buf; | ||
336 | len = strlen (command); | ||
337 | } | ||
338 | cmd = util_stripwhite (command); | ||
339 | util_do_command (cmd); | ||
313 | #ifdef WITH_READLINE | 340 | #ifdef WITH_READLINE |
314 | add_history (cmd); | 341 | if (do_history) |
342 | add_history (cmd); | ||
315 | #endif | 343 | #endif |
316 | } | 344 | if (command) |
345 | free (command); | ||
317 | } | 346 | } |
318 | /* We should never reach this point */ | 347 | } |
319 | return 1; | 348 | |
320 | } | 349 | |
350 | |||
351 | ... | ... |
-
Please register or sign in to post a comment