mirror of
https://github.com/edeproject/ede.git
synced 2023-08-10 21:13:03 +03:00
505 lines
14 KiB
C
505 lines
14 KiB
C
|
|
||
|
/* glob.c file filter for grep.*/
|
||
|
/*
|
||
|
Copyright 2000 Edscott Wilson Garcia
|
||
|
|
||
|
This program is free software; you can redistribute it and/or modify
|
||
|
it under the terms of the GNU General Public License as published by
|
||
|
the Free Software Foundation; either version 2, or (at your option)
|
||
|
any later version.
|
||
|
|
||
|
This program is distributed in the hope that it will be useful,
|
||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||
|
GNU General Public License for more details.
|
||
|
|
||
|
You should have received a copy of the GNU General Public License
|
||
|
along with this program; if not, write to the Free Software
|
||
|
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||
|
02111-1307, USA. */
|
||
|
|
||
|
/*****************************************************************/
|
||
|
|
||
|
#include "globber.h"
|
||
|
#include <stdio.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <unistd.h>
|
||
|
#include <string.h>
|
||
|
#include <signal.h>
|
||
|
#include <stdarg.h>
|
||
|
#include <sys/stat.h>
|
||
|
#include <sys/wait.h>
|
||
|
#include <time.h>
|
||
|
|
||
|
#ifdef HAVE_CONFIG_H
|
||
|
# include <config.h>
|
||
|
#endif
|
||
|
|
||
|
#ifdef HAVE_SNPRINTF
|
||
|
# include "snprintf.h"
|
||
|
#endif
|
||
|
|
||
|
#ifdef DMALLOC
|
||
|
# include "dmalloc.h"
|
||
|
#endif
|
||
|
|
||
|
/** tripas */
|
||
|
#define VERSION_NAME "\nglob 0.5.0\n\nCopyright 2000-2001 Edscott Wilson Garcia\n\
|
||
|
This is free software; see the source for copying conditions. There is NO\n\
|
||
|
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n"
|
||
|
|
||
|
#define GREP "grep"
|
||
|
|
||
|
static void *object=NULL;
|
||
|
static int initial;
|
||
|
static int terminated = 0;
|
||
|
static char *token;
|
||
|
static int options=0,type=0;
|
||
|
static long size=0;
|
||
|
static long month_t=0;
|
||
|
static long unsigned day_t=0;
|
||
|
static long unsigned hour_t=0;
|
||
|
static long unsigned min_t=0;
|
||
|
|
||
|
#define GLOBRUN_PID 0x01
|
||
|
#define GLOBRUN_COUNT 0x02
|
||
|
#define GLOBRUN_FILTERED 0x04
|
||
|
#define GLOBRUN_IGNORE_CASE 0x08
|
||
|
#define GLOBRUN_REG_EXP 0x10
|
||
|
#define GLOBRUN_INVERT 0x20
|
||
|
/*#define GLOBRUN_WHATEVER 0x40*/
|
||
|
#define GLOBRUN_WORDS_ONLY 0x80
|
||
|
#define GLOBRUN_LINES_ONLY 0x100
|
||
|
#define GLOBRUN_ZERO_BYTE 0x200
|
||
|
#define GLOBRUN_NOBINARIES 0x400
|
||
|
#define GLOBRUN_RECURSIVE 0x800
|
||
|
#define GLOBRUN_VERBOSE 0x1000
|
||
|
#define GLOBRUN_XDEV 0x2000
|
||
|
|
||
|
#define MAX_ARG 25
|
||
|
|
||
|
static int display (char *input)
|
||
|
{
|
||
|
if (terminated) return terminated; /* die quietly and quickly */
|
||
|
printf ("%s\n", input);
|
||
|
if (time (NULL) - initial > 3) {
|
||
|
fflush (NULL);
|
||
|
initial = time (NULL);
|
||
|
}
|
||
|
return terminated;
|
||
|
}
|
||
|
|
||
|
static int grep (char *file)
|
||
|
{
|
||
|
static char *arguments[MAX_ARG];
|
||
|
int status = 0;
|
||
|
if (terminated) return terminated; /* die quietly and quickly */
|
||
|
|
||
|
arguments[status++] = "grep";
|
||
|
arguments[status++] = "-d";
|
||
|
arguments[status++] = "skip";
|
||
|
arguments[status++] = "-H";
|
||
|
if (options & GLOBRUN_NOBINARIES)
|
||
|
arguments[status++] = "-I";
|
||
|
if (options & GLOBRUN_IGNORE_CASE)
|
||
|
arguments[status++] = "-i";
|
||
|
if (options & GLOBRUN_WORDS_ONLY)
|
||
|
arguments[status++] = "-w";
|
||
|
if (options & GLOBRUN_LINES_ONLY)
|
||
|
arguments[status++] = "-x";
|
||
|
if (options & GLOBRUN_ZERO_BYTE)
|
||
|
arguments[status++] = "-Z";
|
||
|
|
||
|
if ((options & GLOBRUN_COUNT) && (options & GLOBRUN_INVERT))
|
||
|
{
|
||
|
arguments[status++] = "-c";
|
||
|
arguments[status++] = "-v";
|
||
|
}
|
||
|
if ((options & GLOBRUN_COUNT) && !(options & GLOBRUN_INVERT))
|
||
|
{
|
||
|
arguments[status++] = "-c";
|
||
|
}
|
||
|
if (!(options & GLOBRUN_COUNT) && (options & GLOBRUN_INVERT))
|
||
|
{
|
||
|
arguments[status++] = "-L";
|
||
|
}
|
||
|
if (!(options & GLOBRUN_COUNT) && !(options & GLOBRUN_INVERT))
|
||
|
{
|
||
|
arguments[status++] = "-l";
|
||
|
}
|
||
|
|
||
|
if (options & GLOBRUN_REG_EXP)
|
||
|
arguments[status++] = "-E";
|
||
|
else
|
||
|
arguments[status++] = "-e";
|
||
|
arguments[status++] = token;
|
||
|
|
||
|
arguments[status++] = file;
|
||
|
arguments[status++] = (char *) 0;
|
||
|
if (options & GLOBRUN_VERBOSE)
|
||
|
{
|
||
|
int i;
|
||
|
for (i = 0; i < status; i++)
|
||
|
printf ("%s ", arguments[i]);
|
||
|
printf ("\n");
|
||
|
}
|
||
|
|
||
|
if (fork () == 0){
|
||
|
execvp (GREP, arguments);
|
||
|
fprintf(stderr,"%s not found in path!\n",GREP);
|
||
|
exit(1);
|
||
|
}
|
||
|
wait (&status);
|
||
|
|
||
|
/*fflush(NULL); */
|
||
|
return terminated;
|
||
|
}
|
||
|
|
||
|
|
||
|
static char *message[] = {
|
||
|
" [-vVPrMACaiIyLcwxZ] [-fpotkhsmudgeE (option)] path \n\n",
|
||
|
"options: \n"
|
||
|
" [-r] [-v] [-d ddd] [-m mmm] [-f filter] [-s (+/-)size]\n",
|
||
|
" [-t type] [-p perm] [grep options...] \n",
|
||
|
"-v = verbose\n",
|
||
|
"-V = print version number information\n",
|
||
|
"-a = stay on a single filesystem.\n",
|
||
|
"-P = print process id (capital P)\n",
|
||
|
"-f filter = file filter (enclosed in quotes if regexp *,? or\n",
|
||
|
" [] is used)\n",
|
||
|
"-r = recursive\n",
|
||
|
"-s +kbytes = size greater than kbytes KBYTES\n",
|
||
|
"-s -kbytes = size less than kbytes KBYTES\n",
|
||
|
"-p perm = perm is either suid | exe\n",
|
||
|
"-o octal_mode = octal mode is the file mode in octal notation\n",
|
||
|
"-t type = any | reg | dir | sym | sock | blk | chr | fifo\n",
|
||
|
" (any, regular, directory, symlink, socket, blk_dev,\n",
|
||
|
" chr_dev, fifo: any is the default.)\n",
|
||
|
" * Time options must be used with either -M, -C, or -A.\n"
|
||
|
"-k min = file time in the previous (int) min minutes (either -M -C -A)\n",
|
||
|
"-h hhh = file time in the previous (int) hh hours (either -M -C -A)\n",
|
||
|
"-d ddd = file time in the previous (int) dd days (either -M -C -A)\n",
|
||
|
"-m mmm = file time in the previous (int) mm months (either -M -C -A)\n",
|
||
|
"-M = use mtime for file (modification time: mknod, truncate,\n",
|
||
|
" utime,write \n",
|
||
|
"-A = use atime for file (access time: exec, mknod, pipe,\n",
|
||
|
" utime, read) \n",
|
||
|
"-C = use ctime for file (change time: setting inode information\n",
|
||
|
" i.e., owner, group, link count, mode, etc.) \n",
|
||
|
"-u user-id = only files matching numeric user-id\n",
|
||
|
"-g group-id = only files matching numeric group-id\n",
|
||
|
"-Z = Output a zero byte (the ASCII NUL character)\n",
|
||
|
" instead of the character that normally follows a\n",
|
||
|
" file name (never tested option, if you do, email me)\n",
|
||
|
"\n",
|
||
|
"**specifying these option will be used in content search (grep):\n",
|
||
|
"-e string = containing string (if *,? or [], use quotes)\n",
|
||
|
"-E regexp = containing regexp: (use quotes amigo). \n",
|
||
|
"-i = ignore case (for search string -c)\n",
|
||
|
"-I = do not search into binary files\n",
|
||
|
"-y = same as -i (obsolete)\n",
|
||
|
"-L = print the name of each input file from which *no*\n",
|
||
|
" output would normally have been printed.\n",
|
||
|
"-c = only print a count of matching lines for each input\n",
|
||
|
" file.\n",
|
||
|
"-w = Select only those lines containing matches that\n",
|
||
|
" form whole words. Word-constituent characters are\n",
|
||
|
" letters, digits, and the underscore.\n",
|
||
|
"-x = Select only those matches that exactly match the\n",
|
||
|
" whole line.\n",
|
||
|
"\n",
|
||
|
NULL
|
||
|
};
|
||
|
|
||
|
void
|
||
|
finish (int sig)
|
||
|
{
|
||
|
/*printf("\n****\nglob terminated by signal\n****\n"); */
|
||
|
terminated = 1;
|
||
|
fflush (NULL);
|
||
|
}
|
||
|
|
||
|
void
|
||
|
halt (int sig)
|
||
|
{
|
||
|
fflush (NULL);
|
||
|
globber_destroy(object);
|
||
|
exit (1);
|
||
|
}
|
||
|
|
||
|
|
||
|
#define CHECK_ARG if (argc <= i) goto error;
|
||
|
int
|
||
|
main (int argc, char **argv)
|
||
|
{
|
||
|
int i,timetype=0;
|
||
|
char *filter = NULL, globbered = 0;
|
||
|
int (*operate) (char *) = display;
|
||
|
initial = time (NULL);
|
||
|
|
||
|
/* initializations */
|
||
|
signal (SIGHUP, halt);
|
||
|
signal (SIGSEGV, finish);
|
||
|
signal (SIGKILL, finish);
|
||
|
signal (SIGTERM, finish);
|
||
|
|
||
|
|
||
|
if (argc < 2)
|
||
|
{
|
||
|
error:
|
||
|
fprintf (stdout, "use: %s ", argv[0]);
|
||
|
i = 0;
|
||
|
while (message[i])
|
||
|
fprintf (stdout,"%s", message[i++]);
|
||
|
exit (1);
|
||
|
}
|
||
|
object=globber_create();
|
||
|
for (i = 1; i < argc; i++)
|
||
|
{
|
||
|
if (argv[i][0] == '-')
|
||
|
{
|
||
|
/* options for the globber : *****************/
|
||
|
if (strstr (argv[i], "M") != NULL)
|
||
|
{
|
||
|
timetype=1;
|
||
|
glob_set_options(object,GLOBBER_MTIME);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "A") != NULL)
|
||
|
{
|
||
|
timetype=1;
|
||
|
glob_set_options(object,GLOBBER_ATIME);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "C") != NULL)
|
||
|
{
|
||
|
timetype=1;
|
||
|
glob_set_options(object,GLOBBER_CTIME);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "a") != NULL)
|
||
|
{
|
||
|
glob_set_options(object,GLOBBER_XDEV);
|
||
|
options |= GLOBRUN_XDEV;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "v") != NULL)
|
||
|
{
|
||
|
glob_set_options(object,GLOBBER_VERBOSE);
|
||
|
options |= GLOBRUN_VERBOSE;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "r") != NULL)
|
||
|
{
|
||
|
glob_set_options(object,GLOBBER_RECURSIVE);
|
||
|
options |= GLOBRUN_RECURSIVE;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "u") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
glob_set_user(object,atol(argv[i]));
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "g") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
glob_set_group(object,atol(argv[i]));
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
|
||
|
if (strstr (argv[i], "t") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
type &= 07777;
|
||
|
CHECK_ARG;
|
||
|
/*if (strcmp (argv[i], "any") == 0) type &= 07777;*/
|
||
|
if (strcmp (argv[i], "reg") == 0) type |= S_IFREG;
|
||
|
if (strcmp (argv[i], "dir") == 0) type |= S_IFDIR;
|
||
|
if (strcmp (argv[i], "sym") == 0) type |= S_IFLNK;
|
||
|
if (strcmp (argv[i], "sock") == 0)type |= S_IFSOCK;
|
||
|
if (strcmp (argv[i], "blk") == 0) type |= S_IFBLK;
|
||
|
if (strcmp (argv[i], "chr") == 0) type |= S_IFCHR;
|
||
|
if (strcmp (argv[i], "fifo") == 0)type |= S_IFIFO;
|
||
|
if (strcmp (argv[i], "any") != 0) {
|
||
|
glob_set_options(object,GLOBBER_TYPE);
|
||
|
glob_set_type(object,type);
|
||
|
}
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "p") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
/*type &= S_IFMT;*/
|
||
|
CHECK_ARG;
|
||
|
if (strcmp (argv[i], "suid") == 0)
|
||
|
type |= S_ISUID;
|
||
|
if (strcmp (argv[i], "exe") == 0)
|
||
|
type |= S_IXUSR;
|
||
|
glob_set_options(object,GLOBBER_PERM);
|
||
|
glob_set_type(object,type);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "o") != NULL)
|
||
|
{
|
||
|
int valor;
|
||
|
i++;
|
||
|
type &= S_IFMT;
|
||
|
CHECK_ARG;
|
||
|
sscanf(argv[i],"%o",&valor);
|
||
|
type |= (07777&valor);
|
||
|
glob_set_options(object,GLOBBER_PERM);
|
||
|
glob_set_type(object,type);
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
if (strstr (argv[i], "s") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
size = atol (argv[i]);
|
||
|
if (size < 0) glob_set_sizeL(object,-size*1024);
|
||
|
else glob_set_sizeG(object,size*1024);
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
if (strstr (argv[i], "k") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
min_t = atol (argv[i]);
|
||
|
glob_set_time(object,month_t,day_t,hour_t,min_t);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "h") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
hour_t = atol (argv[i]);
|
||
|
glob_set_time(object,month_t,day_t,hour_t,min_t);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "d") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
day_t = atol (argv[i]);
|
||
|
glob_set_time(object,month_t,day_t,hour_t,min_t);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "m") != NULL)
|
||
|
{
|
||
|
CHECK_ARG;
|
||
|
month_t = atol (argv[i]);
|
||
|
glob_set_time(object,month_t,day_t,hour_t,min_t);
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
|
||
|
if (strstr (argv[i], "f") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_FILTERED;
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
filter = argv[i];
|
||
|
if (options & GLOBRUN_VERBOSE)
|
||
|
fprintf (stderr, "filtering %s\n", filter);
|
||
|
continue;
|
||
|
}
|
||
|
/* options for grep : *******************/
|
||
|
if (strstr (argv[i], "I") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_NOBINARIES;
|
||
|
continue;
|
||
|
}
|
||
|
if ((strstr (argv[i], "i") != NULL)||(strstr (argv[i], "y") != NULL))
|
||
|
{
|
||
|
options |= GLOBRUN_IGNORE_CASE;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "L") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_INVERT;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "c") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_COUNT;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "w") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_WORDS_ONLY;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "x") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_LINES_ONLY;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "Z") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_ZERO_BYTE;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "P") != NULL)
|
||
|
{
|
||
|
options |= GLOBRUN_PID;
|
||
|
printf ("PID=%d\n", (int) getpid ());
|
||
|
fflush (NULL);
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "E") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
token = argv[i];
|
||
|
operate = grep;
|
||
|
options |= GLOBRUN_REG_EXP;
|
||
|
continue;
|
||
|
}
|
||
|
if (strstr (argv[i], "e") != NULL)
|
||
|
{
|
||
|
i++;
|
||
|
CHECK_ARG;
|
||
|
token = argv[i];
|
||
|
operate = grep;
|
||
|
options |= GLOBRUN_REG_EXP;
|
||
|
options ^= GLOBRUN_REG_EXP; /* turn off extended regexp */
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
if (strstr (argv[i], "V") != NULL)
|
||
|
{
|
||
|
printf ("%s", VERSION_NAME);
|
||
|
return 0;
|
||
|
}
|
||
|
fprintf(stdout,"unknown argument: %s\nuse -h for help.\n",argv[i]);
|
||
|
exit(1);
|
||
|
}
|
||
|
if (((min_t)||(hour_t)||(day_t)||(month_t))&& !timetype)
|
||
|
glob_set_options(object,GLOBBER_MTIME);
|
||
|
terminated = globber (object,argv[i], operate, filter);
|
||
|
globbered = 1;
|
||
|
} /* end of argument processing */
|
||
|
|
||
|
|
||
|
if (!globbered)
|
||
|
{
|
||
|
fprintf (stderr, "must specify path\n");
|
||
|
goto error;
|
||
|
}
|
||
|
/* if (terminated) printf("glob run was terminated.\n");*/
|
||
|
if (!terminated)
|
||
|
{ /* die quietly and quickly */
|
||
|
if (options & GLOBRUN_PID)
|
||
|
printf ("GLOB DONE=%d\n", (int) getpid ());
|
||
|
}
|
||
|
fflush (NULL);
|
||
|
globber_destroy(object);
|
||
|
exit (0);
|
||
|
}
|