Commit f19d700c f19d700c852e5ca16b96a02d1f4f6b7d0c227657 by Sergey Poznyakoff

util_expand_msglist(): return 1 and set msglist[0]=cursor if argc == 1.

util_do_command(): Added missing va_end().
util_get_sender(): Returns sender email for the given msgno.
		Optionally strips off domain part.
util_slist_.*(): "string lists" used by alias,alt,retain,ignore.
util_strcat(): Concat two strings, reallocating first to the necessary length
(Rather clumsy, we'd be better off using obstack I guess).
util_escape_percent(): Excape % signs in a string, so it can be used as
format in .*printf calls.
1 parent 6686bc3a
Showing 1 changed file with 140 additions and 5 deletions
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
17 17
18 #include "mail.h" 18 #include "mail.h"
19 #include <mailutils/mutil.h> 19 #include <mailutils/mutil.h>
20 #include <pwd.h>
20 21
21 typedef struct _node { 22 typedef struct _node {
22 /* for the msglist expander */ 23 /* for the msglist expander */
...@@ -250,7 +251,8 @@ util_do_command (const char *c, ...) ...@@ -250,7 +251,8 @@ util_do_command (const char *c, ...)
250 function_t *command; 251 function_t *command;
251 char *cmd = NULL; 252 char *cmd = NULL;
252 va_list ap; 253 va_list ap;
253 254 int i, zcnt = 0;
255
254 va_start (ap, c); 256 va_start (ap, c);
255 status = vasprintf (&cmd, c, ap); 257 status = vasprintf (&cmd, c, ap);
256 va_end (ap); 258 va_end (ap);
...@@ -266,6 +268,28 @@ util_do_command (const char *c, ...) ...@@ -266,6 +268,28 @@ util_do_command (const char *c, ...)
266 268
267 if (argcv_get (cmd, &argc, &argv) != 0) 269 if (argcv_get (cmd, &argc, &argv) != 0)
268 return argcv_free (argc, argv); 270 return argcv_free (argc, argv);
271
272 /* Eliminate empty strings */
273 for (i = 0; i < argc; i++)
274 {
275 if (argv[i][0] == 0)
276 {
277 int d;
278 for (d = i; d < argc && argv[d][0] == 0; d++)
279 ;
280 if (d == argc)
281 {
282 break;
283 }
284 else
285 {
286 char *s = argv[d];
287 argv[d] = argv[i];
288 argv[i] = s;
289 }
290 zcnt++;
291 }
292 }
269 293
270 entry = util_find_entry (argv[0]); 294 entry = util_find_entry (argv[0]);
271 295
...@@ -280,7 +304,7 @@ util_do_command (const char *c, ...) ...@@ -280,7 +304,7 @@ util_do_command (const char *c, ...)
280 command = util_command_get ("quit"); 304 command = util_command_get ("quit");
281 305
282 if (command != NULL) 306 if (command != NULL)
283 status = command (argc, argv); 307 status = command (argc - zcnt, argv);
284 else 308 else
285 { 309 {
286 fprintf (ofile, "Unknown command: %s\n", argv[0]); 310 fprintf (ofile, "Unknown command: %s\n", argv[0]);
...@@ -296,10 +320,13 @@ util_do_command (const char *c, ...) ...@@ -296,10 +320,13 @@ util_do_command (const char *c, ...)
296 * func is the function to run 320 * func is the function to run
297 * argc is the number of arguments inculding the command and msglist 321 * argc is the number of arguments inculding the command and msglist
298 * argv is the list of strings containing the command and msglist 322 * argv is the list of strings containing the command and msglist
323 * set_cursor means whether the function should set the cursor to
324 * the number of the last message processed. If set_cursor = 0, the
325 * cursor is not altered.
299 */ 326 */
300 327
301 int 328 int
302 util_msglist_command (function_t *func, int argc, char **argv) 329 util_msglist_command (function_t *func, int argc, char **argv, int set_cursor)
303 { 330 {
304 int i; 331 int i;
305 int *list = NULL; 332 int *list = NULL;
...@@ -315,7 +342,10 @@ util_msglist_command (function_t *func, int argc, char **argv) ...@@ -315,7 +342,10 @@ util_msglist_command (function_t *func, int argc, char **argv)
315 } 342 }
316 free (list); 343 free (list);
317 344
318 cursor = realcursor; 345 if (set_cursor)
346 realcursor = cursor;
347 else
348 cursor = realcursor;
319 return status; 349 return status;
320 } 350 }
321 351
...@@ -389,6 +419,18 @@ util_getlines (void) ...@@ -389,6 +419,18 @@ util_getlines (void)
389 return strtol (getenv("LINES"), NULL, 10); 419 return strtol (getenv("LINES"), NULL, 10);
390 } 420 }
391 421
422 int
423 util_screen_lines()
424 {
425 struct mail_env_entry *ep = util_find_env("screen");
426 size_t n;
427
428 if (ep && ep->set && (n = atoi(ep->value)) != 0)
429 return n;
430 return util_getlines();
431 }
432
433
392 /* 434 /*
393 * find environment entry var 435 * find environment entry var
394 */ 436 */
...@@ -783,8 +825,101 @@ util_escape_percent (char **str) ...@@ -783,8 +825,101 @@ util_escape_percent (char **str)
783 *str = newstr; 825 *str = newstr;
784 } 826 }
785 827
828 char *
829 util_outfolder_name (char *str)
830 {
831 struct mail_env_entry *ep = util_find_env("outfolder");
786 832
787 833 switch (*str)
834 {
835 case '/':
836 case '~':
837 case '+':
838 str = util_fullpath (str);
839 break;
840
841 default:
842 if (ep && ep->set)
843 {
844 char *ns = NULL;
845 asprintf (&ns, "%s/%s", ep->value, str);
846 str = util_fullpath (ns);
847 free (ns);
848 }
849 break;
850
851 }
852
853 return str;
854 }
855
856 char *
857 util_whoami()
858 {
859 struct passwd *pw = getpwuid(getuid());
860 return pw ? pw->pw_name : "unknown";
861 }
862
863 /* Save an outgoing message. "savefile" allows to override the setting
864 of the "record" variable. */
865 void
866 util_save_outgoing (message_t msg, char *savefile)
867 {
868 struct mail_env_entry *ep = util_find_env("record");
869 if (ep->set)
870 {
871 FILE *outfile;
872 char *filename = util_outfolder_name (savefile ? savefile : ep->value);
873
874 outfile = fopen (filename, "a");
875 if (!outfile)
876 {
877 fprintf (outfile, "can't open save file %s: %s",
878 filename, strerror (errno));
879 }
880 else
881 {
882 char *buf;
883 size_t bsize = 0;
884
885 message_size (msg, &bsize);
886
887 /* Try to allocate large buffer */
888 for (; bsize > 1; bsize /= 2)
889 if ((buf = malloc (bsize)))
890 break;
891
892 if (!bsize)
893 {
894 fprintf (ofile, "not enough memory for creating save file\n");
895 }
896 else
897 {
898 stream_t stream;
899 size_t n, off = 0;
900 time_t t;
901 struct tm *tm;
902 char date[64];
903
904 time(&t);
905 tm = gmtime(&t);
906 strftime (date, sizeof (date), "%a %b %e %H:%M:%S %Y%n", tm);
907 fprintf (outfile, "From %s %s\n", util_whoami(), date);
908
909 message_get_stream (msg, &stream);
910 while (stream_read (stream, buf, bsize, off, &n) == 0
911 && n != 0)
912 {
913 fwrite (buf, 1, n, outfile);
914 off += n;
915 }
916 free (buf);
917 }
918 fclose (outfile);
919 }
920 free (filename);
921 }
922 }
788 923
789 924
790 925
......