home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Source Code 1992 March
/
Source_Code_CD-ROM_Walnut_Creek_March_1992.iso
/
usenet
/
altsrcs
/
2
/
2284
/
lid.c
Wrap
C/C++ Source or Header
|
1990-12-28
|
21KB
|
1,011 lines
static char copyright[] = "@(#)Copyright (c) 1986, Greg McGary";
static char sccsid[] = "@(#)lid.c 1.4 86/11/06";
#include <bool.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <signal.h>
#include <errno.h>
#include <radix.h>
#include <id.h>
#include <bitops.h>
#include <extern.h>
#ifdef REGEX
extern char *regex();
extern char *regcmp();
#endif
#ifdef RE_EXEC
extern char *re_comp();
extern int re_exec();
#endif
bool isMagic();
char **bitsToArgv();
char *fileRE();
char *strcpos();
int skipToArgv();
int findAnchor();
int findApropos();
#if REGEX || RE_EXEC
int findRegExp();
#endif
int matchPaths();
int findNonUnique();
int findNumber();
int findPlain();
int idCompare();
long searchName();
void editId();
void grepId();
void lookId();
#ifdef USG
#define TOLOWER(c) (isupper(c) ? _tolower(c) : (c))
#else
#define TOLOWER(c) (isupper(c) ? tolower(c) : (c))
#endif
/*
* Sorry about all the globals, but it's really cleaner this way.
*/
FILE *IdFILE;
bool Merging;
bool Radix;
bool EchoOn = TRUE;
bool CrunchOn = TRUE;
bool pathRegExp = FALSE;
bool matchBase = FALSE;
char IdDir[BUFSIZ];
long AnchorOffset;
int BitArraySize;
char PWDname[BUFSIZ];
struct idhead Idh;
struct idarg *IdArgs;
int (*FindFunc)() = NULL;
int Solo = 0;
#define IGNORE_SOLO(buf) \
( \
(Solo == '-' && !(ID_FLAGS(buf) & IDN_SOLO)) \
|| (Solo == '+' && (ID_FLAGS(buf) & IDN_SOLO)) \
)
char *MyName;
static void
usage()
{
fprintf(stderr, "Usage: %s [-f<file>] [-u<n>] [-r<dir>] [-mewdoxasknc] patterns...\n", MyName);
exit(1);
}
main(argc, argv)
int argc;
char **argv;
{
char *idFile = IDFILE;
char *arg;
long val;
void (*doit)();
bool forceMerge = FALSE;
int uniqueLimit = 0;
int useIDpath = TRUE;
int usePWDpath = FALSE;
int useRELpath = FALSE;
char * RELpath;
int op;
MyName = basename(GETARG(argc, argv));
while (argc) {
arg = GETARG(argc, argv);
switch (op = *arg++)
{
case '-':
case '+':
break;
default:
UNGETARG(argc, argv);
goto argsdone;
}
while (*arg) switch (*arg++)
{
case 'f': idFile = arg; goto nextarg;
case 'u': uniqueLimit = stoi(arg); goto nextarg;
case 'm': forceMerge = TRUE; break;
#if REGEX || RE_EXEC
case 'e': FindFunc = findRegExp; pathRegExp = TRUE; break;
#endif
case 'w': FindFunc = findPlain; break;
case 'd': Radix |= RADIX_DEC; break;
case 'o': Radix |= RADIX_OCT; break;
case 'x': Radix |= RADIX_HEX; break;
case 'a': Radix |= RADIX_ALL; break;
case 's': Solo = op; break;
case 'k': CrunchOn = FALSE; break;
case 'n': EchoOn = FALSE; break;
case 'c': useIDpath = FALSE; usePWDpath = TRUE; break;
case 'b': matchBase = TRUE; break;
case 'r': useIDpath = FALSE; useRELpath = TRUE;
RELpath = arg; goto nextarg;
default:
usage();
}
nextarg:;
}
argsdone:
if (usePWDpath && useRELpath) {
fprintf(stderr,"%s: please use only one of -c or -r\n",MyName);
usage();
}
/* Look for the ID database up the tree */
if ((idFile = LookUp(idFile)) == NULL) {
filerr("open", idFile);
exit(1);
}
/* Find out current directory to relate names to */
if (kshgetwd(PWDname) == NULL) {
fprintf(stderr,"%s: cannot determine current directory\n",MyName);
exit(1);
}
strcat(PWDname,"/");
/* Determine absolute path name that database files are relative to */
if (useIDpath) {
strcpy(IdDir, spanPath(PWDname, idFile));
*(strrchr(IdDir, '/') + 1) = '\0';
} else if (usePWDpath) {
strcpy(IdDir, PWDname);
} else {
strcpy(IdDir, spanPath(PWDname, RELpath));
strcat(IdDir, "/");
}
if ((IdFILE = initID(idFile, &Idh, &IdArgs)) == NULL) {
filerr("open", idFile);
exit(1);
}
BitArraySize = (Idh.idh_pthc + 7) >> 3;
switch (MyName[0])
{
case 'a':
FindFunc = findApropos;
/*FALLTHROUGH*/
case 'l':
doit = lookId;
break;
case 'g':
doit = grepId;
break;
case 'e':
doit = editId;
break;
case 'p':
FindFunc = matchPaths;
doit = lookId;
break;
default:
MyName = "[algep]id";
usage();
}
if (argc == 0) {
UNGETARG(argc, argv);
*argv = ".";
}
while (argc) {
arg = GETARG(argc, argv);
if (FindFunc)
;
else if ((radix(arg)) && (val = stoi(arg)) >= 0)
FindFunc = findNumber;
#if REGEX || RE_EXEC
else if (isMagic(arg))
FindFunc = findRegExp;
#endif
else if (arg[0] == '^')
FindFunc = findAnchor;
else
FindFunc = findPlain;
if ((doit == lookId && !forceMerge)
|| (FindFunc == findNumber && bitCount(Radix) > 1 && val > 7))
Merging = FALSE;
else
Merging = TRUE;
if (uniqueLimit) {
if (!findNonUnique(uniqueLimit, doit))
fprintf(stderr, "All identifiers are unique within the first %d characters\n", uniqueLimit);
exit(0);
} else if (!(*FindFunc)(arg, doit)) {
fprintf(stderr, "%s: not found\n", arg);
continue;
}
}
exit(0);
}
void
lookId(name, argv)
char *name;
register char **argv;
{
register char *arg;
register bool crunching = FALSE;
register char *dir;
if (EchoOn) printf("%-14s ", name);
while (*argv) {
arg = *argv++;
if (*argv && CrunchOn && canCrunch(arg, *argv)) {
if (crunching)
printf(",%s", rootName(arg));
else if ((dir = dirname(arg)) && dir[0] == '.' && dir[1] == '\0')
printf("{%s", rootName(arg));
else
printf("%s/{%s", dir, rootName(arg));
/*}}*/
crunching = TRUE;
} else {
if (crunching) /*{*/
printf(",%s}%s", rootName(arg), suffName(arg));
else
fputs(arg, stdout);
crunching = FALSE;
if (*argv)
putchar(' ');
}
}
putchar('\n');
}
void
grepId(name, argv)
char *name;
char **argv;
{
FILE *gidFILE;
char *gidName;
char buf[BUFSIZ];
char *delimit = "[^a-zA-Z0-9_]";
char *re;
char *reCompiled;
int lineNumber;
if (!Merging || (re = fileRE(name, delimit, delimit)) == NULL)
re = NULL;
#ifdef REGEX
else if ((reCompiled = regcmp(re, 0)) == NULL) {
fprintf(stderr, "%s: Syntax Error: %s\n", MyName, re);
return;
}
#endif
#ifdef RE_EXEC
else if ((reCompiled = re_comp(re)) != NULL) {
fprintf(stderr, "%s: Syntax Error: %s (%s)\n", MyName, re, reCompiled);
return;
}
#endif
buf[0] = ' '; /* sentry */
while (*argv) {
if ((gidFILE = fopen(gidName = *argv++, "r")) == NULL) {
filerr("open", gidName);
continue;
}
lineNumber = 0;
while (fgets(&buf[1], sizeof(buf), gidFILE)) {
lineNumber++;
if (re) {
#ifdef REGEX
if (regex(reCompiled, buf) == NULL)
#endif
#ifdef RE_EXEC
if (!re_exec(buf))
#endif
continue;
} else if (!wordMatch(name, buf))
continue;
printf("%s:%d: %s", gidName, lineNumber, &buf[1]);
}
fclose(gidFILE);
}
}
void
editId(name, argv)
char *name;
char **argv;
{
char reBuf[BUFSIZ];
char edArgBuf[BUFSIZ];
char *re;
int c;
int skip;
static char *editor, *eidArg, *eidRightDel, *eidLeftDel;
if (editor == NULL && (editor = getenv("EDITOR")) == NULL) {
char *ucb_vi = "/usr/ucb/vi";
char *bin_vi = "/usr/bin/vi";
if (access(ucb_vi, 01) == 0)
editor = ucb_vi;
else if (access(bin_vi, 01) == 0)
editor = bin_vi;
else
editor = "/bin/ed"; /* YUCK! */
if (editor == ucb_vi || editor == bin_vi) {
eidArg = "+1;/%s/";
eidLeftDel = "\\<";
eidRightDel = "\\>";
}
}
if (eidLeftDel == NULL) {
eidArg = getenv("EIDARG");
if ((eidLeftDel = getenv("EIDLDEL")) == NULL)
eidLeftDel = "";
if ((eidRightDel = getenv("EIDRDEL")) == NULL)
eidRightDel = "";
}
lookId(name, argv);
savetty();
for (;;) {
printf("Edit? [y1-9^S/nq] "); fflush(stdout);
chartty();
c = (getchar() & 0177);
restoretty();
switch (TOLOWER(c))
{
case '/': case ('s'&037):
putchar('/');
/*FALLTHROUGH*/
if ((skip = skipToArgv(argv)) < 0)
continue;
argv += skip;
goto editit;
case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
putchar(c);
skip = c - '0';
break;
case 'y':
putchar(c);
/*FALLTHROUGH*/
case '\n':
case '\r':
skip = 0;
break;
case 'q':
putchar(c);
putchar('\n');
exit(0);
case 'n':
putchar(c);
putchar('\n');
return;
default:
putchar(c);
putchar('\n');
continue;
}
putchar('\n');
while (skip--)
if (*++argv == NULL)
continue;
break;
}
editit:
if (!Merging || (re = fileRE(name, eidLeftDel, eidRightDel)) == NULL)
sprintf(re = reBuf, "%s%s%s", eidLeftDel, name, eidRightDel);
switch (fork())
{
case -1:
fprintf(stderr, "%s: Cannot fork (%s)\n", MyName, uerror());
exit(1);
case 0:
argv--;
if (eidArg) {
argv--;
sprintf(edArgBuf, eidArg, re);
argv[1] = edArgBuf;
}
argv[0] = editor;
execv(editor, argv);
filerr("exec", editor);
default:
{
int (*oldint)() = signal(SIGINT, SIG_IGN);
int (*oldquit)() = signal(SIGQUIT, SIG_IGN);
while(wait(0) == -1 && errno == EINTR)
/* loop */;
(void) signal(SIGINT, oldint);
(void) signal(SIGQUIT, oldquit);
}
break;
}
}
int
skipToArgv(argv)
char **argv;
{
char pattern[BUFSIZ];
int count;
if (gets(pattern) == NULL)
return -1;
for (count = 0; *argv; count++, argv++)
if (strcpos(*argv, pattern))
return count;
return -1;
}
int
findPlain(arg, doit)
char *arg;
void (*doit)();
{
static char *buf, *bitArray;
int size;
if (searchName(arg) == 0)
return 0;
if (buf == NULL) {
buf = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
if ((size = fgets0(buf, Idh.idh_bsiz, IdFILE)) == 0)
return 0;
size++;
getsFF(&buf[size], IdFILE);
if (IGNORE_SOLO(buf))
return 0;
vecToBits(bitArray, &buf[size], Idh.idh_vecc);
(*doit)(ID_STRING(buf), bitsToArgv(bitArray));
return 1;
}
int
findAnchor(arg, doit)
register char *arg;
void (*doit)();
{
static char *buf, *bitArray;
int count, size;
int len;
if (searchName(++arg) == 0)
return 0;
if (buf == NULL) {
buf = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
len = strlen(arg);
count = 0;
while ((size = fgets0(buf, Idh.idh_bsiz, IdFILE)) > 0) {
size++;
getsFF(&buf[size], IdFILE);
if (IGNORE_SOLO(buf))
continue;
if (!strnequ(arg, ID_STRING(buf), len))
break;
vecToBits(bitArray, &buf[size], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(buf), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
if (Merging && count)
(*doit)(--arg, bitsToArgv(bitArray));
return count;
}
#if REGEX || RE_EXEC
int
findRegExp(re, doit)
char *re;
void (*doit)();
{
static char *buf, *bitArray;
int count, size;
char *reCompiled;
#ifdef REGEX
if ((reCompiled = regcmp(re, 0)) == NULL) {
fprintf(stderr, "%s: Syntax Error: %s\n", MyName, re);
return 0;
}
#endif
#ifdef RE_EXEC
if ((reCompiled = re_comp(re)) != NULL) {
fprintf(stderr, "%s: Syntax Error: %s (%s)\n", MyName, re, reCompiled);
return 0;
}
#endif
fseek(IdFILE, Idh.idh_namo, 0);
if (buf == NULL) {
buf = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
count = 0;
while ((size = fgets0(buf, Idh.idh_bsiz, IdFILE)) > 0) {
size++;
getsFF(&buf[size], IdFILE);
if (IGNORE_SOLO(buf))
continue;
#ifdef REGEX
if (regex(reCompiled, ID_STRING(buf)) == NULL)
#endif
#ifdef RE_EXEC
if (!re_exec(ID_STRING(buf)))
#endif
continue;
vecToBits(bitArray, &buf[size], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(buf), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
if (Merging && count)
(*doit)(re, bitsToArgv(bitArray));
return count;
}
#endif
int
findNumber(arg, doit)
char *arg;
void (*doit)();
{
static char *buf, *bitArray;
int count, size;
register int rdx = 0;
register int val;
register bool hitDigits = FALSE;
if ((val = stoi(arg)) <= 7)
rdx |= RADIX_ALL;
else
rdx = radix(arg);
fseek(IdFILE, Idh.idh_namo, 0);
if (buf == NULL) {
buf = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
count = 0;
while ((size = fgets0(buf, Idh.idh_bsiz, IdFILE)) > 0) {
size++;
getsFF(&buf[size], IdFILE);
if (hitDigits) {
if (!isdigit(*ID_STRING(buf)))
break;
} else if (isdigit(*ID_STRING(buf)))
hitDigits = TRUE;
if (!((Radix ? Radix : rdx) & radix(ID_STRING(buf)))
|| stoi(ID_STRING(buf)) != val)
continue;
vecToBits(bitArray, &buf[size], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(buf), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
if (Merging && count)
(*doit)(arg, bitsToArgv(bitArray));
return count;
}
/*
Find identifiers that are non-unique within
the first `count' characters.
*/
int
findNonUnique(limit, doit)
int limit;
void (*doit)();
{
static char *buf1, *buf2, *bitArray;
register char *old;
register char *new;
register int consecutive;
char *cptmp;
int itmp;
int count, oldsize, newsize;
char *name;
if (limit <= 1)
usage();
fseek(IdFILE, Idh.idh_namo, 0);
if (buf1 == NULL) {
buf1 = malloc(Idh.idh_bsiz);
buf2 = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
name = calloc(1, limit+2);
name[0] = '^';
old = buf1;
*ID_STRING(new = buf2) = '\0';
count = consecutive = 0;
while ((oldsize = fgets0(old, Idh.idh_bsiz, IdFILE)) > 0) {
oldsize++;
getsFF(&old[oldsize], IdFILE);
if (!(ID_FLAGS(old) & IDN_NAME))
continue;
cptmp = old; old = new; new = cptmp;
itmp = oldsize; oldsize = newsize; newsize = itmp;
if (!strnequ(ID_STRING(new), ID_STRING(old), limit)) {
if (consecutive && Merging) {
strncpy(&name[1], ID_STRING(old), limit);
(*doit)(name, bitsToArgv(bitArray));
}
consecutive = 0;
continue;
}
if (!consecutive++) {
vecToBits(bitArray, &old[oldsize], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(old), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
vecToBits(bitArray, &new[newsize], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(new), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
return count;
}
int
findApropos(arg, doit)
char *arg;
void (*doit)();
{
static char *buf, *bitArray;
int count, size;
fseek(IdFILE, Idh.idh_namo, 0);
if (buf == NULL) {
buf = malloc(Idh.idh_bsiz);
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
count = 0;
while ((size = fgets0(buf, Idh.idh_bsiz, IdFILE)) > 0) {
size++;
getsFF(&buf[size], IdFILE);
if (IGNORE_SOLO(buf))
continue;
if (strcpos(ID_STRING(buf), arg) == NULL)
continue;
vecToBits(bitArray, &buf[size], Idh.idh_vecc);
if (!Merging) {
(*doit)(ID_STRING(buf), bitsToArgv(bitArray));
bzero(bitArray, BitArraySize);
}
count++;
}
if (Merging && count)
(*doit)(arg, bitsToArgv(bitArray));
return count;
}
/*
if string `s2' occurs in `s1', return a pointer to the
first match. Ignore differences in alphabetic case.
*/
char *
strcpos(s1, s2)
char *s1;
char *s2;
{
register char *s1p;
register char *s2p;
char *s1last;
for (s1last = &s1[strlen(s1) - strlen(s2)]; s1 <= s1last; s1++)
for (s1p = s1, s2p = s2; TOLOWER(*s1p) == TOLOWER(*s2p); s1p++)
if (*++s2p == '\0')
return s1;
return NULL;
}
/*
Convert the regular expression that we used to
locate identifiers in the id database into one
suitable for locating the identifiers in files.
*/
char *
fileRE(name0, leftDelimit, rightDelimit)
char *name0;
char *leftDelimit;
char *rightDelimit;
{
static char reBuf[BUFSIZ];
register char *name = name0;
if (FindFunc == findNumber && Merging) {
sprintf(reBuf, "%s0*[Xx]*0*%d[Ll]*%s", leftDelimit, stoi(name), rightDelimit);
return reBuf;
}
if (!isMagic(name) && name[0] != '^')
return NULL;
if (name[0] == '^')
name0++;
else
leftDelimit = "";
while (*++name)
;
if (*--name == '$')
*name = '\0';
else
rightDelimit = "";
sprintf(reBuf, "%s%s%s", leftDelimit, name0, rightDelimit);
return reBuf;
}
long
searchName(name)
char *name;
{
long offset;
AnchorOffset = 0;
offset = (long)bsearch(name, (char *)(Idh.idh_namo-1), Idh.idh_endo-(Idh.idh_namo-1), 1, idCompare);
if (offset == 0)
offset = AnchorOffset;
if (offset == 0)
return 0;
fseek(IdFILE, offset, 0);
skipFF(IdFILE);
return ftell(IdFILE);
}
int
idCompare(key, offset)
register char *key;
long offset;
{
register int c;
fseek(IdFILE, offset, 0);
skipFF(IdFILE);
getc(IdFILE);
while (*key == (c = getc(IdFILE)))
if (*key++ == '\0')
return 0;
if (*key == '\0' && FindFunc == findAnchor)
AnchorOffset = offset;
return *key - c;
}
/*
Are there any magic Regular Expression meta-characters in name??
*/
bool
isMagic(name)
register char *name;
{
char *magichar = "[]{}().*+^$";
int backslash = 0;
if (*name == '^')
name++;
while (*name) {
if (*name == '\\')
name++, backslash++;
else if (strchr(magichar, *name))
return TRUE;
name++;
}
if (backslash)
while (*name) {
if (*name == '\\')
strcpy(name, name+1);
name++;
}
return FALSE;
}
char **
bitsToArgv(bitArray)
char *bitArray;
{
char * absname;
char * relname;
static char **argv;
struct idarg *idArgs;
register char **av;
register int i;
#define ARGV1stPATH 3 /* available argv[] slots before first pathname */
if (argv == NULL)
argv = (char **)malloc(sizeof(char *) * (Idh.idh_pthc + ARGV1stPATH + 2));
av = argv + ARGV1stPATH;
for (idArgs = IdArgs, i = 0; i < Idh.idh_pthc; i++, idArgs++) {
if (!BITTST(bitArray, i))
continue;
if (idArgs->ida_flags & IDA_BLANK) {
printf("BOTCH: blank index!\n");
abort();
}
if (!(idArgs->ida_flags & IDA_ADJUST)) {
absname = spanPath(IdDir, idArgs->ida_arg);
relname = relPath(PWDname, absname);
idArgs->ida_arg = strsav(strlen(relname) > strlen(absname) ? absname : relname);
idArgs->ida_flags |= IDA_ADJUST;
}
*av++ = idArgs->ida_arg;
}
*av = NULL;
return (argv + ARGV1stPATH);
}
/* pathWildCard implements a simple pattern matcher that emulates the
* shell wild card capability.
*
* * - any string of chars
* ? - any char
* [] - any char in set (if first char is !, any not in set)
* \ - literal match next char
*/
int
pathWildCard(re, fn)
char *re;
char *fn;
{
register int c;
register int i;
char set[256];
int revset;
while ((c = *re++) != '\0') {
if (c == '*') {
if (*re == '\0') return 1; /* match anything at end */
while (*fn != '\0') {
if (pathWildCard(re,fn)) return 1;
++fn;
}
return 0;
} else if (c == '?') {
if (*fn++ == '\0') return 0;
} else if (c == '[') {
c = *re++;
bzero(set,256);
if (c == '!') {
revset=1;
c = *re++;
} else {
revset=0;
}
while (c != ']') {
if (c == '\\') c = *re++;
set[c]=1;
if ((*re == '-') && (*(re+1) != ']')) {
re+=1;
while (++c <= *re) set[c]=1;
++re;
}
c = *re++;
}
if (revset) for (i=1;i<256;++i) set[i] = ! set[i];
if (! set[*fn++]) return 0;
} else {
if (c == '\\') c = *re++;
if (c != *fn++) return 0;
}
}
return(*fn == '\0');
}
/* matchPaths implements the pid tool. This matches the *names* of files
* in the database against the input pattern rather than the *contents*
* of the files.
*/
int
matchPaths(re, doit)
char *re;
void (*doit)();
{
char * absname;
static char *bitArray;
struct idarg *idArgs;
register int i;
char *reCompiled;
int count=0;
int matched;
if (pathRegExp) {
#ifdef REGEX
if ((reCompiled = regcmp(re, 0)) == NULL) {
fprintf(stderr, "%s: Syntax Error: %s\n", MyName, re);
return 0;
}
#endif
#ifdef RE_EXEC
if ((reCompiled = re_comp(re)) != NULL) {
fprintf(stderr, "%s: Syntax Error: %s (%s)\n", MyName, re, reCompiled);
return 0;
}
#endif
}
if (bitArray == NULL) {
bitArray = malloc(BitArraySize);
}
bzero(bitArray, BitArraySize);
for (idArgs = IdArgs, i = 0; i < Idh.idh_pthc; i++, idArgs++) {
if (idArgs->ida_flags & IDA_BLANK) continue;
if (matchBase) {
absname = strrchr(idArgs->ida_arg, '/');
if (absname == NULL) {
absname = idArgs->ida_arg;
}
} else {
absname = spanPath(IdDir, idArgs->ida_arg);
}
if (pathRegExp) {
#ifdef REGEX
matched = (regex(reCompiled, absname) != NULL);
#endif
#ifdef RE_EXEC
matched = (re_exec(absname));
#endif
} else {
matched = pathWildCard(re, absname);
}
if (matched) {
BITSET(bitArray, i);
++count;
}
}
if (count)
(*doit)(re, bitsToArgv(bitArray));
return count;
}