dos_compilers/Microsoft C v4/WILD.C

208 lines
4.0 KiB
C++
Raw Permalink Normal View History

2024-07-01 19:35:17 +02:00
/*
** wild.c
** wildcard expander
**
** handles '*' (none or more of any char), '?' (exactly one char), and
** '[string]' (chars which match string chars or between n1 and n2 if 'n1-n2'
** in string inclusive)
**
*/
#include <stdio.h>
#include <register.h>
#include <ctype.h>
/*
** these are the data structures
**
** [_psp]:81
** Raw command line.
**
** __argv
** ------- ------
** | |---->| |---->"arg0"
** ------- ------
** | |---->"arg1"
** ------
** ....
** ------
** | |---->"argn"
** ------
** |NULL|
** ------
*/
#define SLASHCHAR '\\'
#define FWDSLASHCHAR '/'
#define SLASH "\\"
#define FWDSLASH "/"
char *_hfind();
extern int __argc;
extern int __argl;
extern char **__argv;
static int _add(int, char ***, char far *, char far *, int );
static int _match(char far *, char ***, char far *, int );
static _sort (char **);
static _hmmcpy( a, b, n )
char *a, far *b;
int n;
{ REG1 int i;
for ( i = 0; i < n; i++ )
*( a + i ) = *( b + i );
}
char **
_cwild ( argv, pass, arg )
char **argv;
int pass;
char far *arg;
{
char savechar;
char far *wchar;
char far *arghead = arg;
int ptr, sptr, arglen;
_setdta();
while ( *arg && ( *arg != ' ' ) && ( *arg != '\t' )
&& ( *arg != '\15' ))
arg++;
savechar = *arg; /* save this character, since it is in psp */
*arg = '\0';
for ( wchar = arghead; wchar && ( *wchar != '*' ) && ( *wchar != '?' );
wchar++ );
_match( wchar, &argv, arghead, pass );
*arg = savechar; /* restore this character */
return( argv );
}
static int
_match ( ptr, argv, arg, pass)
char far *ptr;
char ***argv;
char far *arg;
int pass;
{
char *new;
int length;
char **oldargv = *argv;
int gotone = 0;
if ( pass == 1 )
--__argc;
while (ptr != arg && *ptr != SLASHCHAR && *ptr != FWDSLASHCHAR
&& *ptr != ':')
/* find first slash or ':' before wildcard */
ptr--;
if (*ptr == ':' && ptr != arg+1) /* weird name, just add it as is */
return( _add( 0, argv, arg, (char far *)NULL, pass ) );
if (*ptr == SLASHCHAR || *ptr == FWDSLASHCHAR
|| *ptr == ':') /* pathname */
length = ptr - arg + 1; /* length of dir prefix */
if (new = _hfind(arg)) { /* get the first file name */
do { /* got a file name */
if (strcmp(new, ".")
&& strcmp(new, "..")) {
if (*ptr != SLASHCHAR && *ptr != ':'
&& *ptr != FWDSLASHCHAR ) {
/* current directory; don't need path */
if ( _add( 0, argv, (char far *)new,
(char far *)NULL, pass ) )
return(-1);
}
else /* add full pathname */
if ( _add( length, argv,
(char far *)new, arg, pass) )
return(-1);
gotone++;
}
} while (new = _hfind(NULL)); /* get following files */
if (gotone) {
if ( pass == 2 )
{
new = **argv;
**argv = NULL;
_sort(oldargv);
**argv = new;
}
return(0);
}
}
return( _add( 0, argv, arg, (char far *)NULL, pass) ); /* no match */
}
static int
_add(length, argv, arg, prfxstr, pass )
int length;
char ***argv;
char far *arg;
char far *prfxstr;
{
int argln = 1, prfln = 0;
char far *argcnt = arg, far *prfcnt = prfxstr;
while ( *argcnt )
{
argln++;
argcnt++;
}
while ( *prfcnt )
{
prfln++;
prfcnt++;
}
if ( pass == 1 )
{
__argc++;
__argl += argln + length;
}
else /* pass 2 actually build the arg */
{
if ( length )
_hmmcpy( (char *)**argv, (char far *)prfxstr, prfln );
_hmmcpy( (char *)**argv + length, arg, argln );
(*argv)++;
**argv = (char *)(*(*argv - 1) + argln + length);
}
return(0);
}
static
_sort (first)
char **first;
{
char *temp, **last;
if (!*first)
return;
while (*first) {
last = first;
while (*++last) {
if (strcmp(*last, *first) < 0) {
temp = *first;
*first = *last;
*last = temp;
}
}
++first;
}
}