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
49 additions
and
18 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,23 +296,37 @@ main (int argc, char **argv) | ... | @@ -283,23 +296,37 @@ 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) | ||
291 | { | 318 | { |
292 | int len; | 319 | int len = strlen (command); |
293 | if (command) | ||
294 | free (command); | ||
295 | command = readline (prompt->set && prompt->value != NULL | ||
296 | ? prompt->value : "? "); | ||
297 | len = strlen (command); | ||
298 | while (command[len-1] == '\\') | 320 | while (command[len-1] == '\\') |
299 | { | 321 | { |
300 | char *buf; | 322 | char *buf; |
301 | char *command2 = readline ("> "); | 323 | char *command2 = (*input) (closure, 1); |
302 | 324 | ||
325 | if (!command2) | ||
326 | { | ||
327 | command[len-1] = 0; | ||
328 | break; | ||
329 | } | ||
303 | command[len-1] = '\0'; | 330 | command[len-1] = '\0'; |
304 | buf = malloc ((len + strlen (command2)) * sizeof (char)); | 331 | buf = malloc ((len + strlen (command2)) * sizeof (char)); |
305 | strcpy (buf, command); | 332 | strcpy (buf, command); |
... | @@ -311,10 +338,14 @@ main (int argc, char **argv) | ... | @@ -311,10 +338,14 @@ main (int argc, char **argv) |
311 | cmd = util_stripwhite (command); | 338 | cmd = util_stripwhite (command); |
312 | util_do_command (cmd); | 339 | util_do_command (cmd); |
313 | #ifdef WITH_READLINE | 340 | #ifdef WITH_READLINE |
341 | if (do_history) | ||
314 | add_history (cmd); | 342 | add_history (cmd); |
315 | #endif | 343 | #endif |
344 | if (command) | ||
345 | free (command); | ||
316 | } | 346 | } |
317 | } | ||
318 | /* We should never reach this point */ | ||
319 | return 1; | ||
320 | } | 347 | } |
348 | |||
349 | |||
350 | |||
351 | ... | ... |
-
Please register or sign in to post a comment