}
}
-static void generate_shredlist(const int argc, const char *argv[])
+static void generate_shredlist(int argc, char *argv[])
/* generate an in-core list of sorthash structures */
{
int i, file_count;
extern char *optarg; /* set by getopt */
extern int optind; /* set by getopt */
- int status, file_only;
+ int status, file_only, exec_direct;
- file_only = 0;
- while ((status = getopt(argc, argv, "cd:fhs:w")) != EOF)
+ exec_direct = file_only = 0;
+ while ((status = getopt(argc, argv, "cd:efhs:w")) != EOF)
{
switch (status)
{
c_only = 1;
break;
- case 'f':
- file_only = 1;
- break;
-
case 'd':
chdir(optarg);
break;
+ case 'e':
+ exec_direct = 1;
+ break;
+
+ case 'f':
+ file_only = 1;
+ break;
+
case 's':
shredsize = atoi(optarg);
break;
fprintf(stderr,"usage: shredtree [-c] [-d dir ] [-s shredsize] [-w] [-x] path\n");
fprintf(stderr," -c = check .c, .h, and .txt files only.\n");
fprintf(stderr," -d dir = change directory before digesting.\n");
+ fprintf(stderr," -e = pass structures in core\n");
fprintf(stderr," -h = help (display this message).\n");
fprintf(stderr," -s size = set shred size (default %d)\n",
shredsize);
if (file_only)
generate_shredfile(argv[optind], stdout);
+ else if (exec_direct)
+ {
+ report_time(NULL);
+ generate_shredlist(argc-optind, argv+optind);
+ report_time("Hash merge done, %d entries", sort_count);
+ sort_hashes(sort_buffer, sort_count);
+ report_time("Sort done");
+ emit_report(sort_buffer, sort_count);
+ }
else
{
int hashcount;
};
static struct shif_t *shiflist;
-static struct sorthash_t *obarray, *np;
-static int hashcount;
-
struct range_t
{
char *file;
dummy_match;
static struct match_t *reduced = &dummy_match;
-static void init_intern(const int count)
-/* prepare an alllocation area of a given size */
-{
- np=obarray=(struct sorthash_t *)calloc(sizeof(struct sorthash_t),count);
- if (!np)
- {
- fprintf(stderr, "shredcompare: insufficient memory\n");
- }
-}
-
static void file_intern(const char *file)
/* stash the name of a file */
{
void hash_intern(const struct hash_t *chunk)
/* enter a has into the in-core array */
{
- np->file = head->file;
- np->hash = *chunk;
- np++;
}
struct sorthash_t *merge_hashes(int argc, char *argv[], int *count)
struct shif_t *sp;
struct stat sb;
long total;
+ struct sorthash_t *obarray;
+ int hashcount;
/* set up metadata blocks for the hash files */
shiflist = (struct shif_t *)calloc(sizeof(struct shif_t), argc);
stat(sp->name, &sb);
total += sb.st_size - ftell(sp->fp);
}
- init_intern(total/sizeof(struct hash_t)); /* real work done here */
+
+ obarray=(struct sorthash_t *)calloc(sizeof(struct sorthash_t),
+ total/sizeof(struct hash_t));
+ if (!obarray)
+ {
+ fprintf(stderr, "shredcompare: insufficient memory\n");
+ exit(1);
+ }
/* read in all hashes */
hashcount = 0;
fread(&this, sizeof(struct hash_t), 1, sp->fp);
this.start = FROMNET(this.start);
this.end = FROMNET(this.end);
- hash_intern(&this); /* real work done here */
+ obarray[hashcount].file = head->file;
+ obarray[hashcount].hash = this;
hashcount++;
sp->hashcount++;
if (hashcount % 10000 == 0)
return (sn == tn) && !strncmp(s, t, sn);
}
-struct match_t *reduce_matches(void)
+struct match_t *reduce_matches(struct sorthash_t *obarray, int hashcount)
/* assemble list of duplicated hashes */
{
static struct match_t dummy;
struct match_t *reduced = &dummy, *sp, *tp;
unsigned int retry, nonuniques;
+ struct sorthash_t *np;
/* build list of hashes with more than one range associated with */
nonuniques = 0;
np->file, np->hash.start, np->hash.end);
#endif /* ODEBUG */
- hitlist = reduce_matches();
+ hitlist = reduce_matches(obarray, hashcount);
report_time("Reduction done");
puts("#SHIF-B 1.0");