babel-1.6
|
Makefile,
README.1ST,
addh.c,
addh2.c,
aromatic.c,
assbnd.c,
asstypes.c,
babel.h,
bblmacs.h,
bblmast.h,
bbltyp.h,
block.c,
bndord.c,
bo.c,
buildct.c,
combine.c,
convert.c,
delatms.c,
delh2o.c,
element.lis,
filesrch.c,
fileutil.c,
gastchg.c,
gauss.hdr,
htoend.c,
int2cart.c,
intcart.c,
menus.c,
miniums.c,
molwt.c,
new.lis,
nodummy.c,
orient.c,
precip.c,
printbad.c,
progress.c,
psgvb.hdr,
quanta.lis,
rdalch.c,
rdampout.c,
rdbalst.c,
rdbgf.c,
rdboogie.c,
rdc3d.c,
rdcacao.c,
rdcadpac.c,
rdcharmm.c,
rdcsd.c,
rddock.c,
rddpdb.c,
rdelmnts.c,
rdfdat.c,
rdfeat.c,
rdfract.c,
rdg96.c,
rdgamout.c,
rdgauout.c,
rdgzmat.c,
rdhin.c,
rdinsite.c,
rdint.c,
rdirc.c,
rdisis.c,
rdm3d.c,
rdmacmod.c,
rdmacmol.c,
rdmdl.c,
rdmicro.c,
rdmm2.c,
rdmm2in.c,
rdmm3.c,
rdmolen.c,
rdmopac.c,
rdmopcrt.c,
rdpcmod.c,
rdpdb.c,
rdprep.c,
rdpsgout.c,
rdpsgvin.c,
rdquanta.c,
rdschak.c,
rdshelx.c,
rdsmiles.c,
rdspart.c,
rdspmm.c,
rdspsemi.c,
rdsybmol.c,
rdsybyl.c,
rdtypes.c,
rdunichm.c,
rdwiz.c,
rdxed.c,
rdxyz.c,
renum.c,
report.c,
rings.c,
ringutil.c,
sets.c,
smilesto.c,
spline.c,
strngutl.c,
tokenst.c,
tosmiles.c,
tree.c,
typbybo.c,
types.lis,
umslist.c,
utils.c,
vectors.c,
wralch.c,
wrbalst.c,
wrbgf.c,
wrbmin.c,
wrbox.c,
wrc3d.c,
wrcacao.c,
wrcache.c,
wrcacint.c,
wrchdrw.c,
wrcontmp.c,
wrcsr.c,
wrcssr.c,
wrdock.c,
wrdpdb.c,
wrfeat.c,
wrfh.c,
wrg96.c,
wrgamess.c,
wrgau.c,
wrgaucrt.c,
wrhin.c,
wricon.c,
wrint.c,
wrisis.c,
wrm3d.c,
wrmaccs.c,
wrmacmod.c,
wrmcmol.c,
wrmdl.c,
wrmicro.c,
wrmimic.c,
wrmiv.c,
wrmm2.c,
wrmm3.c,
wrmopac.c,
wrpcmod.c,
wrpdb.c,
wrpsgv.c,
wrpsgvz.c,
wrsmiles.c,
wrspart.c,
wrsybmol.c,
wrsybyl.c,
wrtinker.c,
wrtorlst.c,
wrunichm.c,
wrwiz.c,
wrxed.c,
wrxyz.c
|
|
|
/*
** SRCHFILE.C - Functions for searching files
**
** public domain by Bob Stout
**
** Note: Although this snippet demonstrates some useful techniques, even
** the fast text searching algorithm used can't provide particularly
** good performance. Left as an exercise for the user is to perform
** explicit buffering using fread() rather than fgets() as is used
** here. See CHBYTES.C in SNIPPETS for how to perform searches in
** user-managed buffers.
*/
#include
#include
#include
#define SUCCESS 0
/*
** Allocate a big buffer, use it to buffer a specified stream
*/
static size_t fsetup(FILE *fp, size_t minbuf)
{
register size_t bufsize;
register char *buffer;
/* Allocate the largest buffer we can */
for (bufsize = 0x4000; bufsize >= minbuf; bufsize >>= 1)
{
if (NULL != (buffer = (char *) malloc(bufsize)))
break;
}
if (NULL == buffer)
return 0;
/* Use the buffer to buffer the file */
if (SUCCESS == setvbuf(fp, buffer, _IOFBF, bufsize))
return bufsize;
else return 0;
}
/*
** Search a file for a pattern match (forward)
**
** Arguments: FILE pointer
** pattern to search for
** size of pattern
** find Nth occurance
**
** Returns: -1L if pattern not found
** -2L in case of error
*/
long ffsearch(FILE *fp, const char *pattern, const size_t size, int N)
{
long pos = -2L, tempos = 0L;
char *sbuf, *p;
size_t i, skip;
int ch = 0;
/* Allocate a search buffer */
if (NULL == (sbuf = (char *)malloc(size - 1)))
goto FDONE;
/* Buffer the file and position us within it */
if (0 == fsetup(fp, size))
goto FDONE;
pos = -1L;
fseek(fp, 0L, SEEK_SET);
/* Set up for smart searching */
if (1 < strlen(pattern) && NULL != (p = strchr(pattern + 1, *pattern)))
skip = p - (char *)pattern;
else skip = strlen(pattern);
/* Look for the pattern */
while (EOF != ch)
{
if (EOF == (ch = fgetc(fp)))
break;
if ((int)*pattern == ch)
{
tempos = ftell(fp);
if (size - 1 > fread(sbuf, sizeof(char), size - 1, fp))
goto FDONE;
if (SUCCESS == memcmp(sbuf, &pattern[1], size - 1))
{
if (0 == --N)
{
pos = tempos - 1L;
goto FDONE;
}
}
fseek(fp, tempos + skip, SEEK_SET);
}
}
/* Clean up and leave */
FDONE:
free(sbuf);
return pos;
}
/*
** Search a file for a pattern match (backwards)
**
** Arguments: FILE pointer
** pattern to search for
** size of pattern
** find Nth occurance
**
** Returns: -1L if pattern not found
** -2L in case of error
*/
long rfsearch(FILE *fp, const char *pattern, const size_t size, int N)
{
long pos = -2L, tempos;
char *sbuf, *p;
size_t i, skip;
int ch = 0;
/* Allocate a search buffer */
if (NULL == (sbuf = (char *)malloc(size - 1)))
goto RDONE;
/* Buffer the file and position us within it */
if (0 == fsetup(fp, size))
goto RDONE;
pos = -1L;
fseek(fp, -1L, SEEK_END);
tempos = ftell(fp) - strlen(pattern);
/* Set up for smart searching */
if (1 < strlen(pattern) && NULL != (p = strrchr(pattern + 1, *pattern)))
skip = strlen(pattern) - (p - (char *)pattern);
else skip = strlen(pattern);
/* Look for the pattern */
while (0L <= tempos)
{
fseek(fp, tempos, SEEK_SET);
if (EOF == (ch = fgetc(fp)))
break;
if ((int)*pattern == ch)
{
if (size - 1 <= fread(sbuf, sizeof(char), size - 1, fp))
{
if (SUCCESS == memcmp(sbuf, &pattern[1], size - 1))
{
if (0 == --N)
{
pos = tempos;
goto RDONE;
}
}
}
tempos -= skip;
}
else --tempos;
}
/* Clean up and leave */
RDONE:
free(sbuf);
return pos;
}
#ifdef TEST
int main(int argc, char *argv[])
{
long pos;
int N = 1;
size_t size = strlen(argv[1]);
char buf[256], *fname = "SRCHFILE.C";
FILE *fp;
if (2 > argc)
{
puts("Usage: SRCHFILE string [N] [file]");
puts("where: N = find Nth occurance");
puts(" If file is specified, N must be given");
return EXIT_FAILURE;
}
if (2 < argc)
N = atoi(argv[2]);
if (3 < argc)
fname = strupr(argv[3]);
fp = fopen(fname, "r");
printf("ffsearch(%s, %s) returned %ld\n", fname, argv[1],
pos = ffsearch(fp, argv[1], size, N));
fseek(fp, pos, SEEK_SET);
fgets(buf, 256, fp);
printf("...which contains \"%s\"\n\n", buf);
fclose(fp);
fp = fopen(fname, "rb");
printf("rfsearch(%s, %s) returned %ld\n", fname, argv[1],
pos = rfsearch(fp, argv[1], size, N));
fseek(fp, pos, SEEK_SET);
fgets(buf, 256, fp);
printf("...which contains \"%s\"\n\n", buf);
fclose(fp);
return EXIT_SUCCESS;
}
#endif /* TEST */
|