2 Proprietary Rand Corporation
, 1981.
3 Further distribution of
this software
4 subject to the terms of the Rand
12 #include <sys/types.h>
16 #define NFOLD 20 /* Allow 20 folder specs */
18 extern struct swit anoyes
[]; /* Std no/yes gans array */
21 * pick [-src folder] [msgs] search [-scan] [-show] [file-op]
32 * file-op = -file [-preserve] [-link] +folder ...
33 * -keep [-stay] [+folder ...]
39 char grep
[256], *grepp
, *folder
, maildir
[128];
40 int showf
, scanfl
, filef
, keepf
, linkf
, noteold
, prsrvf
, stayf
;
41 int grep_lowsel
= 5000,
45 struct st_fold folders
[NFOLD
];
47 struct swit switches
[] = {
48 "cc pattern", 0, /* 0 */
49 "date pattern", 0, /* 1 */
50 "from pattern", 0, /* 2 */
51 "search pattern", 0, /* 3 */
52 "subject pattern", 0, /* 4 */
53 "to pattern", 0, /* 5 */
54 "-othercomponent pattern", 15, /* 6 */
56 "file +folder ...", 0, /* 8 */
58 "keep [+folder ...]", 0, /* 10 */
62 "preserve", 0, /* 14 */
63 "nopreserve", 0, /* 15 */
68 "src +folder", 0, /* 20 */
79 char *msgs
[128], buf
[128];
84 char *arguments
[50], **argp
, **arrp
;
93 cp
= r1bindex(argv
[0], '/');
94 if((cp
= m_find(cp
)) != NULL
) {
95 ap
= brkstring(cp
= getcpy(cp
), " ", "\n");
96 ap
= copyip(ap
, arguments
);
99 VOID
copyip(argv
+1, ap
);
101 while(cp
= *argp
++) {
103 if(*++cp
== '-') { /* --component */
104 toomany
: if(grepp
!= grep
) {
105 fprintf(stderr
, "Only one search string.\n");
108 grepp
= copy("^", grepp
);
109 grepp
= copy(++cp
, grepp
);
110 grepp
= copy(":.*", grepp
);
113 switch(i
= smatch(cp
, switches
)) {
114 case -2:ambigsw(cp
, switches
); /* ambiguous */
117 case -1:fprintf(stderr
, "pick: -%s unknown\n", cp
);
120 case 0: case 1: case 2: case 4: case 5:
123 grepp
= copy("^", grepp
);
124 arrp
= brkstring(switches
[i
].sw
, " ", NULLCP
);
125 grepp
= copy(*arrp
, grepp
);
126 grepp
= copy(":.*", grepp
);
127 case 3: /* -search */
128 pattern
: grepp
= copy(*argp
++, grepp
);
130 case 6: fprintf(stderr
, "pick: can't get here\n");
133 case 7: fprintf(stderr
, "\"-all\" changed to \"all\"\n");
135 case 8: filef
= 1; continue; /* -file */
136 case 9: filef
= 0; continue; /* -nofile */
137 case 10:keepf
= 1; continue; /* -keep */
138 case 11:keepf
= 0; continue; /* -nokeep */
139 case 12:linkf
= 1; continue; /* -link */
140 case 13:linkf
= 0; continue; /* -nolink */
141 case 14:prsrvf
= 1; continue; /* -preserve */
142 case 15:prsrvf
= 0; continue; /* -nopreserve */
143 case 16:scanfl
= 1; continue; /* -scan */
144 case 17:scanfl
= 0; continue; /* -noscan */
145 case 18:showf
= 1; continue; /* -show */
146 case 19:showf
= 0; continue; /* -noshow */
147 case 21:stayf
= 1; continue; /* -stay */
148 case 22:stayf
= 0; continue; /* -nostay */
149 case 20:if(folder
) { /* -src */
150 fprintf(stderr
, "Only one src folder.\n");
153 if(!(folder
= *argp
++) || *folder
== '-') {
154 fprintf(stderr
, "pick: Missing argument for %s switch\n", argp
[-2]);
159 folder
= path(folder
, TFOLDER
);
162 case 23:help("pick [msgs] [switches]", switches
);
165 } else if(*cp
== '+') {
167 folders
[foldp
++].f_name
= path(cp
+1, TFOLDER
);
169 fprintf(stderr
, "Only %d folders allowed.\n", NFOLD
);
175 if(!m_find("path")) free(path("./", TFOLDER
));
177 fprintf(stderr
, "No search pattern specified.\n");
181 fprintf(stderr
, "-file and -keep don't go together.\n");
184 if(!scanfl
&& !showf
&& !filef
)
185 keepf
++; /* The default is -keep */
187 prsrvf
++; /* -keep forces -preserve */
188 linkf
++; /* and -link */
191 folder
= m_getfolder(); /* use cur folder if no -src */
192 VOID
copy(m_maildir(folder
), maildir
);
193 if(chdir(maildir
) < 0) {
194 fprintf(stderr
, "Can't chdir to: ");
198 if(!(mp
= m_gmsg(folder
))) {
199 fprintf(stderr
, "Can't read folder!?\n");
202 if(mp
->hghmsg
== 0) {
203 fprintf(stderr
, "No messages in \"%s\".\n", folder
);
206 if(!foldp
) { /* if no +folder given... */
207 if(filef
) { /* -file requires one */
208 fprintf(stderr
, "-file requires at least one folder arg.\n");
211 if(keepf
) { /* use default selection-list name */
212 VOID
copy(listname
, copy("/", copy(folder
, buf
)));
213 folders
[foldp
++].f_name
= getcpy(buf
);
214 noteold
++; /* tell user if existing folder */
216 } else if(keepf
) { /* make folders sub-folders */
217 for(msgnum
= 0; msgnum
< foldp
; msgnum
++)
218 if(*(cp
= folders
[msgnum
].f_name
) != '.' &&
220 VOID
copy(cp
, copy("/", copy(folder
, buf
)));
221 folders
[msgnum
].f_name
= getcpy(buf
);
226 msgs
[msgp
++] = "first-last";
227 for(msgnum
= 0; msgnum
< msgp
; msgnum
++)
228 if(!m_convert(msgs
[msgnum
]))
230 if(mp
->numsel
== 0) {
231 fprintf(stderr
, "pick: Peanut butter 'n jelly\n");/* never get here */
235 fprintf(stderr
, "Pattern Error.\n");
238 for(msgnum
= mp
->lowsel
; msgnum
<= mp
->hghsel
; msgnum
++)
239 if(mp
->msgstats
[msgnum
]&SELECTED
)
241 if(mp
->numsel
== 0) {
242 fprintf(stderr
, "No messages match specification.\n");
245 mp
->lowsel
= grep_lowsel
;
246 mp
->hghsel
= grep_hghsel
;
248 if((((delprog
= m_find("delete-prog")) != NULL
) &&
249 ((filef
|| keepf
) && !linkf
)) ||
251 if(mp
->numsel
> MAXARGS
-2) {
252 fprintf(stderr
, "pick: more than %d messages for %s exec\n",
254 scanfl
? "scan" : showf
? "show" : delprog
);
257 nvec
= (char **) malloc(MAXARGS
* sizeof nvec
[0]);
258 for(msgnum
= mp
->lowsel
; msgnum
<= mp
->hghsel
; msgnum
++)
259 if(mp
->msgstats
[msgnum
]&SELECTED
)
260 nvec
[nvecp
++] = getcpy(m_name(msgnum
));
266 if(!noteold
|| foldp
> 1)
267 m_replace(pfolder
, folder
);
269 scanfn(showf
|filef
|keepf
);
271 printf("%d hit%s.\n", mp
->numsel
, mp
->numsel
== 1 ? "" : "s");
278 for(msgnum
= mp
->lowsel
; msgnum
<= mp
->hghsel
; msgnum
++)
279 if(mp
->msgstats
[msgnum
]&SELECTED
)
280 if(m_file(folder
, cp
= getcpy(m_name(msgnum
)),
281 folders
, foldp
, prsrvf
, 1))
288 struct st_fold
*fptr
;
289 if(!stayf
&& foldp
== 1) {
290 m_replace(pfolder
, cp
= folders
[0].f_name
);
291 printf("[+%s now current]\n", cp
); VOID
fflush(stdout
);
293 for(fptr
= folders
; fptr
< &folders
[foldp
]; fptr
++)
294 if(!fptr
->f_reused
) {
295 VOID
chdir(m_maildir(fptr
->f_name
));
296 m_setcur(fptr
->f_mp
->curmsg
);
306 if(execute(m_name(msg
))) { /* a match */
307 if(msg
< grep_lowsel
)
309 if(msg
> grep_hghsel
)
312 mp
->msgstats
[msg
] &= ~SELECTED
; /* clear SELECTED bit */
321 register char *cp
, *ap
;
325 for(i
= 0; i
< foldp
; i
++) {
326 VOID
copy(m_maildir(cp
= folders
[i
].f_name
), nmaildir
);
327 if(stat(nmaildir
, &stbuf
) < 0) {
329 ap
= concat("Create folder \"",
330 nmaildir
, "\"? ", 0);
331 if(!gans(ap
, anoyes
))
334 if(!makedir(nmaildir
)) {
335 fprintf(stderr
, "Can't create folder.\n");
339 printf("[Folder %s being re-used.]\n", cp
);
341 folders
[i
].f_reused
++; /* Don't change cur in old fold */
343 if(chdir(nmaildir
) < 0) {
344 fprintf(stderr
, "Can't chdir to: ");
348 if(!(folders
[i
].f_mp
= m_gmsg(folders
[i
].f_name
))) {
349 fprintf(stderr
, "Can't read folder %s\n", folders
[i
].f_name
);
352 folders
[i
].f_mp
->curmsg
= 0;
354 VOID
chdir(maildir
); /* return to src folder */
363 nvec
[0] = r1bindex(scanproc
, '/');
364 if(forkf
&& (pid
= fork())) {
366 fprintf(stderr
, "No forks!\n");
369 while(wait((int *)NULL
) != pid
) ;
373 execv(scanproc
, nvec
);
383 int (*sint
)(), (*sqit
)();
385 nvec
[0] = r1bindex(showproc
, '/');
387 sint
= signal(SIGINT
, SIG_IGN
);
388 sqit
= signal(SIGQUIT
, SIG_IGN
);
390 if(forkf
&& (pid
= fork())) {
392 fprintf(stderr
, "No forks!\n");
395 while(wait((int *)NULL
) != pid
) ;
396 VOID
signal(SIGINT
, sint
);
397 VOID
signal(SIGQUIT
, sqit
);
401 putenv("mhfolder", folder
);
402 execv(showproc
, nvec
);
414 if(delprog
!= NULL
) {
415 nvec
[0] = r1bindex(delprog
, '/');
418 execv(delprog
, nvec
);
419 fprintf(stderr
, "Can't exec deletion-prog--");
422 for(i
= mp
->lowsel
; i
<= mp
->hghsel
; i
++)
423 if(mp
->msgstats
[i
]&SELECTED
)
424 if(unlink(cp
= m_name(i
)) == -1) {
425 fprintf(stderr
, "Can't unlink %s:",folder
);