home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 10 Tools
/
10-Tools.zip
/
cidsam.zip
/
FINDFILE.C
< prev
next >
Wrap
C/C++ Source or Header
|
1993-06-28
|
10KB
|
178 lines
/*********************************/
/* NOTE */
/* */
/* This sample code has been */
/* provided by IBM. It is not */
/* warranted for any particular */
/* use or purpose. */
/* */
/* IBM releases this code into */
/* the public domain. You may */
/* use it, modify it, or */
/* incorporate it into other */
/* products without restriction. */
/*********************************/
/*********************************************************************/
/* */
/* MODULE NAME: findfile.c */
/* */
/* DESCRIPTIVE NAME: Contains routine CID_findfile() */
/* */
/* LINKAGE: This is a linkable subroutine. It requires no other */
/* linkages. */
/* */
/*********************************************************************/
#pragma page (1)
/**************************************************************************
* Given a file spec, find the first file that satisfies it. *
* *
* The algorithem is: look on the current directory. *
* If it's not there, and the filespec was fully qualified, return *
* file-not-found. *
* If it's not there but the filespec was relative, look up the DPATH *
* concatenate the file with each directory listed there, and search *
* for the resultant fully qualified name. *
* If it's still not found, look up the PATH and search on each *
* directory listed there. *
* *
* The file spec can be ambiguous. Only the first file that satisfies *
* the spec will be returned. *
* *
* Returns a pointer to the fully-qualified file name if successful, *
* or NULL if the file was not found. The reason the file was not *
* found is not returned. It could be because the file does not exist *
* or because an I/O error prevented access. It could also be that *
* there is not enough memory left to store the file name. *
* *
* THIS CODE IS FINE FOR PORTABILITY, BUT SHOULD BE REPLACED BY CALLS *
* TO DosSearchPath() IN THE OS/2 ENVIRONMENT. IT WILL BE, PRETTY *
* QUICK. *
**************************************************************************/
/*************************************************************************/
/* Modification history: */
/* */
/* Marker PTR Who When Why */
/* U1 grb 09/27/91 mallocing 1 byte too few in ff_make_fqname*/
/* R1 grb 09/30/91 Incorporated comments from code review */
/* U2 grb 10/30/91 Algorithem failed for roots of drives */
/* A2 grb 05/06/93 Port to 32-bit IBM C++ compiler */
/*************************************************************************/
#pragma page (1)
#define INCL_BASE
#include <os2.h>
#include <stdlib.h>
#include <string.h>
#include "findfile.h"
char *CID_findfile(char *filespec)
{
char *fqname, *sname, *p, *q, *ep;
int fslen, rc, epi; /*@R1c*/
#define ENVPATHS 2
char *envlist[ENVPATHS] = { "DPATH", "PATH"};
HDIR handle;
#ifdef I16 /*@A2a*/
FILEFINDBUF ffb;
USHORT count; /*@R1a*/
#else /*@A2a*/ /*@A2a*/
FILEFINDBUF3 ffb; /*@A2a*/
ULONG count; /*@R1a*/
#endif /*@A2a*/
fqname = (char *)NULL;
fslen = strlen(filespec);
/* STEP 1: look on current working directory */
count = 1;
handle = 1;
#ifdef I16 /*@A2a*/
if ( (rc = DosFindFirst((PSZ)filespec, &handle, /*@R1c*/
FILE_SYSTEM | FILE_HIDDEN,
&ffb, sizeof(FILEFINDBUF), &count, 0l)) == NO_ERROR)
#else
if ( (rc = DosFindFirst((PSZ)filespec, &handle, /*@R1c*/
FILE_SYSTEM | FILE_HIDDEN,
&ffb, sizeof(FILEFINDBUF3), &count, 1l)) == NO_ERROR)
#endif
/* FIle was found on the current directory */
fqname = ff_make_fqname(filespec, ffb.achName);
else /* file is not on current DIRECTORY */
{ /* if it's fully qualified, we're out of here */
if (*filespec != PATH_SEPC && *(filespec + CHARSIZE) != DRIVE_SEPC)
/* STEP 2: look on DPATH and PATH */
/* for each path variable */
for (epi = 0; epi < ENVPATHS && !fqname; epi++)
{
ep = getenv(envlist[epi]); /* get envir variable */
if (ep)
while (*ep) /* for each path element */
{ /* find end of path element */ for (p = ep; *p && *p != ';'; p++);
if (!(p = strchr(ep, ENVPATH_SEPC)) )
p = ep + strlen(ep);
/* make space for it */
sname = (char *)malloc(p - ep + fslen + CHARLENT2);
if (sname)
{ /* copy it */
for (q = sname; ep != p; *q++ = *ep++);
if (*ep) /* point to start of next path */
ep += CHARSIZE;
if (*(q-1) != PATH_SEPC) /*@U2a*/
{ /*@U2a*/
strcpy(q,PATH_SEPS); /* put in the path seperator */
q += strlen(PATH_SEPS);
} /*@U2a*/
strcpy(q, filespec); /* put in the file spec */
/* Is the file on this path? */
count = 1;
handle = 1;
if ( (rc = DosFindFirst((PSZ)sname, &handle,/*@R1c*/
FILE_SYSTEM | FILE_HIDDEN,
&ffb, sizeof(FILEFINDBUF), &count, 0l))
== NO_ERROR)
{ /* seperate the path from the file name */
fqname = ff_make_fqname(sname, ffb.achName);
break; /* get out of the WHILE loop */
}
else /* No, it's not */
{
fqname = (char *)NULL;
}
free(sname);
} /* end IF memory was available */
} /* end WHILE more paths in this variable */
} /* end FOR all variables */
} /* end IF file was not local */
return(fqname);
}
#pragma page (1)
/**************************************************************************
* Strip the file name (possibly ambiguous) off a file specification, *
* and append in its place a resolved file name *
**************************************************************************/
char *ff_make_fqname(char *ambig_name, char *resolv_name)
{
char *p, *q1, *q2, *fqname;
if (!(p = strrchr(ambig_name, PATH_SEPC)) )
if (!(p = strrchr(ambig_name, DRIVE_SEPC)) )
p = ambig_name; /* seperate the path from the file name */
fqname = (char *)malloc(p - ambig_name + strlen(resolv_name) + 2);/*U1c*/
if (fqname)
{
for (q1 = ambig_name, q2 = fqname; q1 != p; *q2++ = *q1++);
if (*p == DRIVE_SEPC) /* @A1a2 */
*q2++ = *p;
*q2 = '\0'; /* null terminate the path portion of the fq name */
if (*p == '\\')
strcat(fqname, PATH_SEPS);
strcat(fqname, resolv_name);
}
return(fqname);
}