New options -check_md5, -check_md5_r, find action check_md5, test -has_md5

This commit is contained in:
Thomas Schmitt 2009-08-11 19:55:08 +00:00
parent bc9eac552a
commit 3b05800e08
5 changed files with 269 additions and 753 deletions

View File

@ -2459,9 +2459,6 @@ int Linkitem_find(struct LinkiteM *stack, dev_t target_dev, ino_t target_ino,
}
#ifdef Xorriso_findjob_on_expR
/* ----------------------- Exprtest ----------------------- */
@ -3601,585 +3598,6 @@ int Findjob_set_action_found_path(struct FindjoB *o, int flag)
}
#else /* Xorriso_findjob_on_expR */
/* ------------------------------- FindjoB -------------------------------- */
struct FindjoB {
char *start_path;
char *name_expr;
regex_t name_re;
regmatch_t name_match;
/* b = blockdev
c = chardev
d = directory
p = fifo
f = reg
- = reg
s = socket
m = subordinate mountpoint (does never match find start directory)
X = other
0x0 = test inactive
*/
char file_type;
int start_lba;
int end_lba;
int damage_filter; /* -1=only undamaged , 0=all , 1=only damaged */
int commit_filter; /* bit0= test -pending_data : uncommitted regular files */
int acl_filter; /* -1=only without ACL , 0=all , 1=only with ACL */
int xattr_filter; /* -1=only without xattr , 0=all , 1=only with xattr */
int aaip_filter; /* -1=only without AA string , 0=all , 1=only with AA */
int filter_filter; /* -1=only unfiltered nodes , 0=all , 1=only filtered */
void *wanted_node; /* if not NULL, then only this node address matches */
/* 0= echo
1= rm (also rmdir)
2= rm_r
>>> 3= mv target
4= chown user
5= chgrp group
6= chmod mode_and mode_or
7= alter_date type date
8= lsdl
9= chown_r user
10= chgrp_r group
11= chmod_r mode_and mode_or
12= alter_date_r type date
13= find
14= compare disk_equivalent_of_start_path
15= in_iso iso_rr_equivalent_of_start_path
16= not_in_iso iso_rr_equiv
17= update disk_equiv
18= add_missing iso_rr_equiv
19= empty_iso_dir iso_rr_equiv
20= is_full_in_iso iso_rr_equiv
21= report_damage
22= report_lba
23= internal:memorize path of last matching node in found_path
24= getfacl
25= setfacl access_acl default_acl
26= getfattr
27= setfattr
28= set_filter name
29= show_stream
*/
int action;
/* action specific parameters */
char *target;
char *text_2;
uid_t user;
gid_t group;
mode_t mode_and, mode_or;
int type; /* see Xorriso_set_time flag */
time_t date;
char *found_path;
struct FindjoB *subjob;
};
int Findjob_new(struct FindjoB **o, char *start_path, int flag)
{
struct FindjoB *m;
m= *o= TSOB_FELD(struct FindjoB,1);
if(m==NULL)
return(-1);
m->start_path= NULL;
m->name_expr= NULL;
m->file_type= 0;
m->start_lba= 0;
m->end_lba= 0;
m->damage_filter= 0;
m->commit_filter= 0;
m->acl_filter= 0;
m->xattr_filter= 0;
m->aaip_filter= 0;
m->filter_filter= 0;
m->wanted_node= NULL;
m->action= 0; /* print */
m->target= NULL; /* a mere pointer, not managed memory */
m->text_2= NULL; /* a mere pointer, not managed memory */
m->user= 0;
m->group= 0;
m->type= 0;
m->date= 0;
m->start_path= strdup(start_path);
if(m->start_path==NULL)
goto failed;
m->found_path= NULL;
m->subjob= NULL;
return(1);
failed:;
Findjob_destroy(o, 0);
return(-1);
}
int Findjob_destroy(struct FindjoB **o, int flag)
{
struct FindjoB *m;
m= *o;
if(m==NULL)
return(0);
if(m->start_path!=NULL)
free(m->start_path);
if(m->name_expr!=NULL) {
regfree(&(m->name_re));
free(m->name_expr);
}
Findjob_destroy(&(m->subjob), 0);
free((char *) m);
*o= NULL;
return(1);
}
int Findjob_set_start_path(struct FindjoB *o, char *start_path, int flag)
{
if(o->start_path!=NULL)
free(o->start_path);
if(start_path!=NULL) {
o->start_path= strdup(start_path);
if(o->start_path==NULL)
return(-1);
} else
o->start_path= NULL;
return(1);
}
int Findjob_get_start_path(struct FindjoB *o, char **start_path, int flag)
{
*start_path= o->start_path;
return(1);
}
int Findjob_set_name_expr(struct FindjoB *o, char *name_expr, int flag)
{
char regexpr[2*SfileadrL+2];
if(o->name_expr!=NULL) {
regfree(&(o->name_re));
free(o->name_expr);
o->name_expr= NULL;
}
if(strlen(name_expr)>=SfileadrL)
return(0);
o->name_expr= strdup(name_expr);
if(o->name_expr==NULL)
return(-1);
Xorriso__bourne_to_reg(name_expr, regexpr, 0);
if(regcomp(&(o->name_re), regexpr, 0)!=0)
return(0);
return(1);
}
int Findjob_set_file_type(struct FindjoB *o, char file_type, int flag)
{
static char known[]= {"bcdpf-lsmeX"};
if(file_type!=0)
if(strchr(known, file_type)==NULL)
return(0);
o->file_type= file_type;
return(1);
}
int Findjob_set_lba_range(struct FindjoB *o, int start_lba, int count,
int flag)
{
o->start_lba= start_lba;
if(start_lba > 0)
o->end_lba= start_lba + count - 1;
else
o->end_lba= start_lba - count + 1;
return(1);
}
/* @param value -1= only undamaged files, 0= all files, 1= only damaged files
*/
int Findjob_set_damage_filter(struct FindjoB *o, int value, int flag)
{
if(value < 0)
o->damage_filter= -1;
else if(value > 0)
o->damage_filter= 1;
else
o->damage_filter= 0;
return(1);
}
int Findjob_get_lba_damage_filter(struct FindjoB *o, int *start_lba,
int *end_lba, int *damage_filter, int flag)
{
*start_lba= o->start_lba;
*end_lba= o->end_lba;
*damage_filter= o->damage_filter;
return(1);
}
int Findjob_set_commit_filter(struct FindjoB *o, int mask, int values,
int flag)
{
o->commit_filter&= ~mask;
o->commit_filter|= (mask & values);
return(1);
}
int Findjob_get_commit_filter(struct FindjoB *o, int *commit_filter, int flag)
{
*commit_filter= o->commit_filter;
return(1);
}
/* @param value -1= files without ACL, 0= all files, 1= only files with ACL
*/
int Findjob_set_acl_filter(struct FindjoB *o, int value, int flag)
{
if(value < 0)
o->acl_filter= -1;
else if(value > 0)
o->acl_filter= 1;
else
o->acl_filter= 0;
return(1);
}
/* @param value -1= files without xattr, 0= all files, 1= only files with xattr
*/
int Findjob_set_xattr_filter(struct FindjoB *o, int value, int flag)
{
if(value < 0)
o->xattr_filter= -1;
else if(value > 0)
o->xattr_filter= 1;
else
o->xattr_filter= 0;
return(1);
}
/* @param value -1= files without aaip, 0= all files, 1= only files with aaip
*/
int Findjob_set_aaip_filter(struct FindjoB *o, int value, int flag)
{
if(value < 0)
o->aaip_filter= -1;
else if(value > 0)
o->aaip_filter= 1;
else
o->aaip_filter= 0;
return(1);
}
int Findjob_get_acl_filter(struct FindjoB *o, int *acl_filter, int flag)
{
*acl_filter= o->acl_filter;
return(1);
}
int Findjob_get_xattr_filter(struct FindjoB *o, int *xattr_filter, int flag)
{
*xattr_filter= o->xattr_filter;
return(1);
}
int Findjob_get_aaip_filter(struct FindjoB *o, int *aaip_filter, int flag)
{
*aaip_filter= o->aaip_filter;
return(1);
}
/* @param value -1= files without filter, 0= all files, 1= files with filter
*/
int Findjob_set_filter_filter(struct FindjoB *o, int value, int flag)
{
if(value < 0)
o->filter_filter= -1;
else if(value > 0)
o->filter_filter= 1;
else
o->filter_filter= 0;
return(1);
}
int Findjob_get_filter_filter(struct FindjoB *o, int *value, int flag)
{
*value= o->filter_filter;
return(1);
}
int Findjob_set_wanted_node(struct FindjoB *o, void *wanted_node, int flag)
{
o->wanted_node= wanted_node;
return(1);
}
int Findjob_get_wanted_node(struct FindjoB *o, void **wanted_node, int flag)
{
*wanted_node= o->wanted_node;
return(1);
}
int Findjob_set_found_path(struct FindjoB *o, char *path, int flag)
{
if(o->found_path != NULL)
free(o->found_path);
if(path != NULL) {
o->found_path= strdup(path);
if(o->found_path == NULL)
return(-1);
} else
o->found_path= NULL;
return(1);
}
int Findjob_get_found_path(struct FindjoB *o, char **path, int flag)
{
*path= o->found_path;
return(1);
}
/* @flag bit0=recognize type "e" = El-Torito
@return 0=no match , 1=match , <0 = error
*/
int Findjob_test(struct FindjoB *o, char *name,
struct stat *boss_stbuf, struct stat *stbuf,
int depth, int flag)
{
int ret;
if(o->name_expr!=NULL) {
ret= regexec(&(o->name_re),name,1,&(o->name_match),0);
if(ret!=0)
return(0);
}
if(o->file_type!=0) {
if(S_ISBLK(stbuf->st_mode)) {
if(o->file_type!='b')
return(0);
} else if(S_ISCHR(stbuf->st_mode)) {
if(o->file_type!='c')
return(0);
} else if(S_ISDIR(stbuf->st_mode)) {
if(o->file_type=='m') {
if(boss_stbuf==NULL)
return(0);
if(boss_stbuf->st_dev == stbuf->st_dev)
return(0);
} else if(o->file_type!='d')
return(0);
} else if(S_ISFIFO(stbuf->st_mode)) {
if(o->file_type!='p')
return(0);
} else if(S_ISREG(stbuf->st_mode)) {
if(o->file_type!='f' && o->file_type!='-')
return(0);
} else if(((stbuf->st_mode)&S_IFMT)==S_IFLNK) {
if(o->file_type!='l')
return(0);
} else if(((stbuf->st_mode)&S_IFMT)==S_IFSOCK) {
if(o->file_type!='s')
return(0);
} else if((flag & 1) && ((stbuf->st_mode) & S_IFMT) == Xorriso_IFBOOT) {
if(o->file_type!='e')
return(0);
} else {
if(o->file_type!='X')
return(0);
}
}
/* ??? >>> more tests to come ?*/;
return(1);
}
int Findjob_get_action(struct FindjoB *o, int flag)
{
return(o->action);
}
/* @return <0 error, >=0 see above struct FindjoB.action
*/
int Findjob_get_action_parms(struct FindjoB *o, char **target, char **text_2,
uid_t *user, gid_t *group,
mode_t *mode_and, mode_t *mode_or,
int *type, time_t *date, struct FindjoB **subjob,
int flag)
{
*target= o->target;
*text_2= o->text_2;
*user= o->user;
*group= o->group;
*mode_and= o->mode_and;
*mode_or= o->mode_or;
*type= o->type;
*date= o->date;
*subjob= o->subjob;
return(o->action);
}
int Findjob_set_action_target(struct FindjoB *o, int action, char *target,
int flag)
{
o->action= action;
o->target= target;
return(1);
}
int Findjob_set_action_text_2(struct FindjoB *o, int action, char *target,
char* text_2, int flag)
{
o->action= action;
o->target= target;
o->text_2= text_2;
return(1);
}
/* @param flag bit0= recursive
*/
int Findjob_set_action_chown(struct FindjoB *o, uid_t user,int flag)
{
int ret;
if(flag&1) {
o->action= 0;
Findjob_destroy(&(o->subjob), 0);
ret= Findjob_new(&(o->subjob), "", 0);
if(ret<=0)
return(-1);
Findjob_set_action_chown(o->subjob, user, 0);
o->action= 9;
} else {
o->action= 4;
o->user= user;
}
return(1);
}
/* @param flag bit0= recursive
*/
int Findjob_set_action_chgrp(struct FindjoB *o, gid_t group, int flag)
{
int ret;
if(flag&1) {
o->action= 0;
Findjob_destroy(&(o->subjob), 0);
ret= Findjob_new(&(o->subjob), "", 0);
if(ret<=0)
return(-1);
Findjob_set_action_chgrp(o->subjob, group, 0);
o->action= 10;
} else {
o->action= 5;
o->group= group;
}
return(1);
}
/* @param flag bit0= recursive
*/
int Findjob_set_action_chmod(struct FindjoB *o,
mode_t mode_and, mode_t mode_or, int flag)
{
int ret;
if(flag&1) {
o->action= 0;
Findjob_destroy(&(o->subjob), 0);
ret= Findjob_new(&(o->subjob), "", 0);
if(ret<=0)
return(-1);
Findjob_set_action_chmod(o->subjob, mode_and, mode_or, 0);
o->action= 11;
} else {
o->action= 6;
o->mode_and= mode_and;
o->mode_or= mode_or;
}
return(1);
}
/* @param flag bit0= recursive
*/
int Findjob_set_action_ad(struct FindjoB *o, int type, time_t date, int flag)
{
int ret;
if(flag&1) {
o->action= 0;
Findjob_destroy(&(o->subjob), 0);
ret= Findjob_new(&(o->subjob), "", 0);
if(ret<=0)
return(-1);
Findjob_set_action_ad(o->subjob, type, date, 0);
o->action= 12;
} else {
o->action= 7;
o->type= type;
o->date= date;
}
return(1);
}
int Findjob_set_action_subjob(struct FindjoB *o, int action,
struct FindjoB *subjob, int flag)
{
o->action= action;
Findjob_destroy(&(o->subjob), 0);
o->subjob= subjob;
return(1);
}
int Findjob_set_action_found_path(struct FindjoB *o, int flag)
{
o->action= 23;
Findjob_set_found_path(o, NULL, 0);
return(1);
}
#endif /* ! Xorriso_findjob_on_expR */
/* ---------------------------- SplitparT ------------------------- */
@ -5411,6 +4829,7 @@ int Xorriso_new(struct XorrisO ** xorriso,char *progname, int flag)
m->start_time= 0.0;
m->last_update_time= 0.0;
m->find_compare_result= 1;
m->find_check_md5_result= 1;
m->node_counter= 0;
m->node_array_size= 0;
@ -8913,6 +8332,7 @@ int Xorriso_end_idx(struct XorrisO *xorriso,
bit4= ignore last argument
bit5= demand exactly one match
bit6= with bit5 allow 0 matches if pattern is a constant
bit7= silently tolerate empty argument list
bit8= free the eventually allocated sub_vector
*/
int Xorriso_opt_args(struct XorrisO *xorriso, char *cmd,
@ -8937,6 +8357,7 @@ int Xorriso_opt_args(struct XorrisO *xorriso, char *cmd,
*optc= 0;
*optv= NULL;
sprintf(xorriso->info_text, "%s : Not enough arguments given", cmd);
if(!(flag & 128))
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "SORRY", 0);
return(0);
}
@ -10472,19 +9893,8 @@ int Xorriso_findx(struct XorrisO *xorriso, struct FindjoB *job,
else
namept++;
#ifdef Xorriso_findjob_on_expR
ret= Findjob_test_2(xorriso, job, NULL, namept, dir_path, NULL, dir_stbuf,
0);
#else /* Xorriso_findjob_on_expR */
ret= Findjob_test(job, namept, NULL, dir_stbuf, depth, 0);
#endif /* ! Xorriso_findjob_on_expR */
if(ret<0)
goto ex;
if(ret>0) {
@ -10547,16 +9957,7 @@ int Xorriso_findx(struct XorrisO *xorriso, struct FindjoB *job,
no_dive= 1;
}
#ifdef Xorriso_findjob_on_expR
ret= Findjob_test_2(xorriso, job, NULL, name, path, dir_stbuf, &stbuf, 0);
#else /* Xorriso_findjob_on_expR */
ret= Findjob_test(job, name, dir_stbuf, &stbuf, depth, 0);
#endif /* ! Xorriso_findjob_on_expR */
if(ret<0)
goto ex;
if(ret>0) {
@ -13900,6 +13301,119 @@ int Xorriso_option_charset(struct XorrisO *xorriso, char *name, int flag)
}
/* Options -check_md5 and -check_md5_r
@param flag bit0= issue summary message
bit1= do not reset pacifier, no final pacifier message
bit2= do not issue pacifier messages at all
bit3= recursive: -check_md5_r
*/
int Xorriso_option_check_md5(struct XorrisO *xorriso,
int argc, char **argv, int *idx, int flag)
{
int ret, i, mem_pci, end_idx, fret, sev;
int optc= 0;
char **optv= NULL, *cpt, *severity;
struct FindjoB *job= NULL;
double mem_lut= 0.0;
if(!(flag&2)) {
Xorriso_pacifier_reset(xorriso, 0);
mem_lut= xorriso->last_update_time;
}
mem_pci= xorriso->pacifier_interval;
xorriso->pacifier_interval= 5.0;
/* Interpret argv[*idx] as severity */
if(argc <= *idx) {
sprintf(xorriso->info_text,
"-check_md5: No event severity given for case of mismatch");
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
return(0);
}
severity= argv[*idx];
ret= Xorriso__text_to_sev(severity, &sev, 0);
if(ret<=0) {
sprintf(xorriso->info_text, "-check_md5: Not a known severity name : ");
Text_shellsafe(severity, xorriso->info_text, 1);
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
return(ret);
}
ret= Xorriso_opt_args(xorriso, "-check_md5", argc, argv, (*idx) + 1,
&end_idx, &optc, &optv, 128);
if(ret<=0)
goto ex;
if(optc == 0) {
/* >>> check whole session */;
ret= 1;
return(ret);
}
xorriso->find_check_md5_result= 1;
for(i= 0; i < optc; i++) {
if(flag & 8) {
ret= Findjob_new(&job, optv[i], 0);
if(ret<=0) {
Xorriso_no_findjob(xorriso, "-check_md5_r", 0);
{ret= -1; goto ex;}
}
Findjob_set_action_target(job, 35, NULL, 0);
cpt= optv[i];
ret= Xorriso_findi_sorted(xorriso, job, (off_t) 0, 1, &cpt, 0);
Findjob_destroy(&job, 0);
if(ret > 0)
ret= xorriso->find_compare_result;
else {
ret= -1;
xorriso->find_check_md5_result= -1;
}
} else {
ret= Xorriso_check_md5(xorriso, NULL, optv[i], 4);
if(ret < xorriso->find_check_md5_result)
xorriso->find_check_md5_result= ret;
}
if(ret>0 && !xorriso->request_to_abort)
continue; /* regular bottom of loop */
fret= Xorriso_eval_problem_status(xorriso, ret, 1|2);
if(fret>=0)
continue;
ret= 0; goto report_outcome;
}
ret= 1;
xorriso->pacifier_interval= mem_pci;
if(mem_lut!=xorriso->last_update_time && !(flag&2))
Xorriso_pacifier_callback(xorriso, "content bytes read",
xorriso->pacifier_count, 0, "", 1);
report_outcome:;
if(xorriso->find_check_md5_result > 0) {
sprintf(xorriso->result_line,
"File contents and their MD5 checksums match.\n");
} else if(xorriso->find_check_md5_result == 0) {
sprintf(xorriso->result_line,
"Differences detected between file contents and MD5 checksums.\n");
} else {
sprintf(xorriso->result_line, "MD5 checking failed due to error.\n");
}
Xorriso_result(xorriso,0);
if(xorriso->find_check_md5_result <= 0 && strcmp(severity, "ALL") != 0) {
sprintf(xorriso->info_text, "Event triggered by MD5 comparison mismatch");
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, severity, 0);
}
ex:;
(*idx)= end_idx;
Xorriso_opt_args(xorriso, "-getfacl", argc, argv, *idx, &end_idx,
&optc, &optv, 256);
Findjob_destroy(&job, 0);
if(ret <= 0)
return(ret);
return(xorriso->find_check_md5_result > 0);
}
/* Option -check_media */
int Xorriso_option_check_media(struct XorrisO *xorriso,
int argc, char **argv, int *idx, int flag)
@ -15234,17 +14748,7 @@ not_enough_arguments:;
sscanf(argv[i], "%d", &count);
Findjob_set_lba_range(job, start_lba, count, 0);
} else if(strcmp(argv[i], "-pending_data")==0) {
#ifdef Xorriso_findjob_on_expR
Findjob_set_commit_filter_2(job, 0);
#else /* Xorriso_findjob_on_expR */
Findjob_set_commit_filter(job, 1, 1, 0);
#endif /* ! Xorriso_findjob_on_expR */
} else if(strcmp(argv[i], "-has_acl")==0) {
Findjob_set_acl_filter(job, 1, 0);
} else if(strcmp(argv[i], "-has_no_acl")==0) {
@ -15263,9 +14767,8 @@ not_enough_arguments:;
Findjob_set_filter_filter(job, 1, 0);
} else if(strcmp(argv[i], "-has_no_filter")==0) {
Findjob_set_filter_filter(job, -1, 0);
#ifdef Xorriso_findjob_on_expR
} else if(strcmp(argv[i], "-has_md5")==0) {
Findjob_set_prop_filter(job, 15, 1, 0);
} else if(strcmp(argv[i], "-true") == 0) {
ret= Findjob_set_false(job, -1, 0);
} else if(strcmp(argv[i], "-false") == 0) {
@ -15297,9 +14800,6 @@ not_enough_arguments:;
ret= Findjob_elseif(job, 0);
} else if(strcmp(argv[i], "-endif") == 0) {
ret= Findjob_endif(job, 0);
#endif /* Xorriso_findjob_on_expR */
} else if(strcmp(argv[i], "-sort_lba") == 0) {
flag|= 8;
/* If an operator is open: insert a -true test, else do nothing */
@ -15997,15 +15497,15 @@ int Xorriso_option_help(struct XorrisO *xorriso, int flag)
" the ISO image. Tests:",
" -name pattern, -wholename pattern, -type b|c|d|p|f|l|s|e,",
" -pending_data, -lba_range start count, -damaged,",
" -has_acl, -has_xattr, -has_aaip, -has_filter,",
" -prune, -decision yes|no, -true, -false",
" -has_acl, -has_xattr, -has_aaip, -has_filter, -has_md5",
" -has_any_xattr, -prune, -decision yes|no, -true, -false",
" Operators: -not, -or, -and, -sub, (, -subend, ),",
" -if, -then, -elseif, -else, -endif",
" Action may be one of: echo, chown, chown_r, chgrp, chgrp_r",
" chmod, chmod_r, alter_date, alter_date_r, lsdl, compare,",
" rm, rm_r, compare, update, report_damage, report_lba,",
" getfacl, setfacl, getfattr, setfattr, set_filter,",
" show_stream, find.",
" getfacl, setfacl, getfattr, setfattr, get_any_xattr,",
" get_md5, check_md5, set_filter, show_stream, find.",
" params are their arguments except iso_rr_path.",
" -mkdir iso_rr_path [...]",
" Create empty directories if they do not exist yet.",
@ -19066,7 +18566,7 @@ int Xorriso_count_args(struct XorrisO *xorriso, int argc, char **argv,
};
static char argn_commands[][40]= {
"add","alter_date","alter_date_r","as",
"check_media","check_media_defaults",
"check_md5","check_md5_r","check_media","check_media_defaults",
"chgrp","chgrpi","chgrp_r","chgrp_ri","chmod","chmodi",
"chmod_r","chmod_ri","chown","chowni","chown_r","chown_ri",
"compare_l","cpr","cpri","cp_rax","cp_rx","cpax","cpx",
@ -19263,6 +18763,12 @@ next_command:;
(*idx)++;
ret= Xorriso_option_charset(xorriso, arg1, 3);
} else if(strcmp(cmd,"check_md5")==0) {
ret= Xorriso_option_check_md5(xorriso, argc, argv, idx, 0);
} else if(strcmp(cmd,"check_md5_r")==0) {
ret= Xorriso_option_check_md5(xorriso, argc, argv, idx, 8);
} else if(strcmp(cmd,"check_media")==0) {
ret= Xorriso_option_check_media(xorriso, argc, argv, idx, 0);

View File

@ -497,6 +497,15 @@ int Xorriso_option_cdx(struct XorrisO *xorriso, char *disk_path, int flag);
*/
int Xorriso_option_charset(struct XorrisO *xorriso, char *name, int flag);
/* Options -check_md5 and -check_md5_r
@param flag bit0= issue summary message
bit1= do not reset pacifier, no final pacifier message
bit2= do not issue pacifier messages at all
bit3= recursive: -check_md5_r
*/
int Xorriso_option_check_md5(struct XorrisO *xorriso,
int argc, char **argv, int *idx, int flag);
/* Option -check_media */
int Xorriso_option_check_media(struct XorrisO *xorriso,
int argc, char **argv, int *idx, int flag);

View File

@ -395,6 +395,7 @@ struct XorrisO { /* the global context of xorriso */
void *pacifier_fifo;
int find_compare_result; /* 1=everything matches , 0=mismatch , -1=error */
int find_check_md5_result; /* 1=everything matches , 0=mismatch , -1=error */
/* Tree node collection and LBA sorting facility */
int node_counter;
@ -841,6 +842,7 @@ struct ExprtesT {
12= -prune
13= -wholename char *arg1 (regex_t in *arg2)
14= -has_any_xattr
15= -has_md5
*/
int test_type;
@ -944,6 +946,7 @@ struct FindjoB {
32= internal: widen_hardlinks disk_equiv: update nodes marked in di_do_widen
33= get_any_xattr
34= get_md5
35= check_md5
*/
int action;
int prune;

View File

@ -7594,12 +7594,18 @@ int Xorriso_findi_action(struct XorrisO *xorriso, struct FindjoB *job,
iso_prefix, target, 0);
if(ret==2)
deleted= 1;
} else if(action == 33) {
} else if(action == 33) { /* get_any_xattr */
ret= Xorriso_getfattr(xorriso, (void *) node, show_path, NULL, 8);
} else if(action == 34) {
} else if(action == 34) { /* get_md5 */
ret= Xorriso_get_md5(xorriso, (void *) node, show_path, md5, 0);
if(ret >= 0)
ret= 1;
} else if(action == 35) { /* check_md5 */
ret= Xorriso_check_md5(xorriso, (void *) node, show_path, 2);
if(ret < xorriso->find_check_md5_result)
xorriso->find_check_md5_result= ret;
if(ret >= 0)
ret= 1;
} else { /* includes : 15 in_iso */
sprintf(xorriso->result_line, "%s\n", Text_shellsafe(show_path, sfe, 0));
Xorriso_result(xorriso, 0);
@ -7615,8 +7621,6 @@ int Xorriso_findi_action(struct XorrisO *xorriso, struct FindjoB *job,
}
#ifdef Xorriso_findjob_on_expR
int Exprtest_match(struct XorrisO *xorriso, struct ExprtesT *ftest,
void *node_pt, char *name, char *path,
struct stat *boss_stbuf, struct stat *stbuf, int flag)
@ -7632,7 +7636,7 @@ return:
int value=0, ret, start_lba, end_lba;
int lba_count, *file_end_lbas= NULL, *file_start_lbas= NULL, i;
void *arg1, *arg2;
char ft, *decision;
char ft, *decision, md5[16];
regmatch_t name_match;
off_t damage_start, damage_end, size;
void *xinfo_dummy;
@ -7799,6 +7803,10 @@ return:
ret= regexec(arg2, path, 1, &name_match, 0);
value= !ret;
break; case 15: /* -has_md5 */
ret= Xorriso_get_md5(xorriso, node, path, md5, 1);
value= (ret > 0);
break; default:
/* >>> complain about unknown test type */;
@ -7833,126 +7841,6 @@ int Xorriso_findi_test(struct XorrisO *xorriso, struct FindjoB *job,
return(1);
}
#else /* Xorriso_findjob_on_expR */
int Xorriso_findi_test(struct XorrisO *xorriso, struct FindjoB *job,
IsoNode *node, char *name, char *path,
struct stat *boss_stbuf, struct stat *stbuf,
int depth, int flag)
{
int ret, start_lba, end_lba, damage_filter, commit_filter, lba, a_filter;
int is_filtered= 0;
off_t damage_start, damage_end, size;
int lba_count, *file_end_lbas= NULL, *file_start_lbas= NULL, i;
void *wanted_node;
IsoStream *stream;
ret= Findjob_test(job, name, boss_stbuf, stbuf, depth, 1);
if(ret<=0)
return(ret);
Findjob_get_lba_damage_filter(job, &start_lba, &end_lba, &damage_filter, 0);
if(damage_filter != 0) {
ret= Xorriso_file_eval_damage(xorriso, node, &damage_start, &damage_end, 0);
if(ret < 0)
return(ret);
if((damage_filter > 0) != (ret > 0))
return(0);
}
if(start_lba != 0) {
ret= Xorriso__start_end_lbas(node, &lba_count,
&file_start_lbas, &file_end_lbas, &size, 0);
if(ret <= 0) {
Xorriso_process_msg_queues(xorriso, 0);
if(start_lba > 0)
goto ex;
} else {
for(i= 0; i < lba_count; i++) {
if(start_lba > 0) {
if(file_end_lbas[i] < start_lba || file_start_lbas[i] > end_lba)
{ret= 0; goto ex;}
} else {
if(file_end_lbas[i] >= -start_lba && file_start_lbas[i] <= -end_lba)
{ret= 0; goto ex;}
}
}
}
}
Findjob_get_commit_filter(job, &commit_filter, 0);
if(commit_filter & 1) { /* -pending_data */
if(!LIBISO_ISREG(node))
{ret= 0; goto ex;}
ret= Xorriso__file_start_lba(node, &lba, 0);
if(ret > 0 && lba >= 0)
{ret= 0; goto ex;}
}
Findjob_get_acl_filter(job, &a_filter, 0);
if(a_filter) {
ret = Xorriso_getfacl(xorriso, (void *) node, "", NULL, 2);
if(ret <= 0) {
Xorriso_process_msg_queues(xorriso, 0);
goto ex;
}
if(a_filter < 0 && ret != 2)
{ret= 0; goto ex;}
if(a_filter > 0 && ret == 2)
{ret= 0; goto ex;}
}
Findjob_get_xattr_filter(job, &a_filter, 0);
if(a_filter) {
ret = Xorriso_getfattr(xorriso, (void *) node, "", NULL, 64);
if(ret < 0) {
Xorriso_process_msg_queues(xorriso, 0);
goto ex;
}
if(a_filter < 0 && ret > 0)
{ret= 0; goto ex;}
if(a_filter > 0 && ret == 0)
{ret= 0; goto ex;}
}
Findjob_get_aaip_filter(job, &a_filter, 0);
if(a_filter) {
{ void *xinfo_dummy;
ret= iso_node_get_xinfo(node, aaip_xinfo_func, &xinfo_dummy);
}
if(ret < 0) {
Xorriso_process_msg_queues(xorriso, 0);
goto ex;
}
if(a_filter < 0 && ret == 1)
{ret= 0; goto ex;}
if(a_filter > 0 && ret != 1)
{ret= 0; goto ex;}
}
Findjob_get_filter_filter(job, &a_filter, 0);
if(a_filter) {
is_filtered= 0;
if(LIBISO_ISREG(node)) {
stream= iso_file_get_stream((IsoFile *) node);
if(iso_stream_get_input_stream(stream, 0) != NULL)
is_filtered= 1;;
}
if(a_filter < 0 && is_filtered)
{ret= 0; goto ex;}
if(a_filter > 0 && !is_filtered)
{ret= 0; goto ex;}
}
Findjob_get_wanted_node(job, &wanted_node, 0);
if(wanted_node != NULL && ((IsoNode *) wanted_node) != node)
{ret= 0; goto ex;}
ret= 1;
ex:;
if(file_start_lbas != NULL)
free((char *) file_start_lbas);
if(file_end_lbas != NULL)
free((char *) file_end_lbas);
return(ret);
}
#endif /* ! Xorriso_findjob_on_expR */
/* @param flag bit0= recursion
bit1= do not count deleted files with rm and rm_r
@ -12160,7 +12048,7 @@ ex:;
/*
@param flag bit0= do not report to result but only retrieve md5 text
bit6= check for existence of md5, return 0 or 1
@return 1= ok, 0= no md5 available, <0= other error
*/
int Xorriso_get_md5(struct XorrisO *xorriso, void *in_node, char *path,
char md5[16], int flag)
@ -12185,7 +12073,6 @@ int Xorriso_get_md5(struct XorrisO *xorriso, void *in_node, char *path,
Xorriso_process_msg_queues(xorriso,0);
if(ret <= 0)
goto ex;
if(flag & 1)
{ret= 1; goto ex;}
@ -12203,3 +12090,111 @@ ex:;
}
/* @param node Opaque handle to IsoNode which is to be inquired instead of path if it is not NULL.
@param path is used as address if node is NULL.
@param flag bit0= do not report to result but only indicate outcome
by return value
bit1= silently ignore nodes without MD5
bit2= do not only report mismatches but also matches
@return 2= no MD5 attached to node
1= ok, MD5 compared and matching
0= not ok, MD5 mismatch
<0= other error
*/
int Xorriso_check_md5(struct XorrisO *xorriso, void *in_node, char *path,
int flag)
{
int i, ret, wanted, rret;
IsoImage *image;
IsoNode *node;
IsoFile *file;
char node_md5[16], data_md5[16], buffer[64 * 1024];
void *stream= NULL, *ctx= NULL;
off_t todo;
node= (IsoNode *) in_node;
if(node == NULL) {
ret= Xorriso_get_node_by_path(xorriso, path, NULL, &node, 0);
if(ret<=0)
goto ex;
}
if(!LIBISO_ISREG(node)) {
strcpy(xorriso->info_text, "-check_md5: Not a data file: ");
Text_shellsafe(path, xorriso->info_text, 1);
if(!(flag & 2))
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "NOTE", 0);
ret= 2; goto ex;
}
file= (IsoFile *) node;
/* obtain MD5 */
ret= Xorriso_get_volume(xorriso, &image, 0);
if(ret <= 0)
goto ex;
ret= iso_file_get_md5(image, file, node_md5, 0);
Xorriso_process_msg_queues(xorriso,0);
if(ret < 0)
{ret= -1; goto ex;}
if(ret == 0) {
strcpy(xorriso->info_text, "-check_md5: No MD5 recorded with file: ");
Text_shellsafe(path, xorriso->info_text, 1);
if(!(flag & 2))
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "NOTE", 0);
ret= 2; goto ex;
}
/* Read file and compute MD5 */;
ret= Xorriso_iso_file_open(xorriso, path, (void *) node, &stream, 1);
if(ret <= 0)
{ret= -1; goto ex;}
ret= iso_md5_start(&ctx);
if(ret < 0)
goto ex;
todo= iso_file_get_size(file);
while(todo > 0) {
if(todo < sizeof(buffer))
wanted= todo;
else
wanted= sizeof(buffer);
rret = Xorriso_iso_file_read(xorriso, stream, buffer, wanted, 0);
if(rret <= 0)
{ret= -1; goto ex;}
todo-= rret;
ret = iso_md5_compute(ctx, buffer, rret);
if(ret < 0)
goto ex;
xorriso->pacifier_count+= rret;
xorriso->pacifier_byte_count+= rret;
Xorriso_pacifier_callback(xorriso, "content bytes read",
xorriso->pacifier_count, 0, "", 0);
}
ret= iso_md5_end(&ctx, data_md5);
if(ret < 0)
goto ex;
/* Report outcome */
for(i= 0; i < 16; i++)
if(node_md5[i] != data_md5[i])
break;
if(i < 16 ) {
sprintf(xorriso->result_line, "MD5 MISMATCH: ");
Text_shellsafe(path, xorriso->result_line, 1);
strcat(xorriso->result_line, "\n");
if(!(flag & 1))
Xorriso_result(xorriso,0);
ret= 0;
} else {
sprintf(xorriso->result_line, "md5 match : ");
Text_shellsafe(path, xorriso->result_line, 1);
strcat(xorriso->result_line, "\n");
if(flag & 4)
Xorriso_result(xorriso,0);
ret= 1;
}
ex:;
Xorriso_iso_file_close(xorriso, &stream, 0);
if(ctx != NULL)
iso_md5_end(&ctx, data_md5);
return(ret);
}

View File

@ -321,6 +321,9 @@ int Xorriso_new_hln_array(struct XorrisO *xorriso, off_t mem_limit, int flag);
*/
int Xorriso_restore_node_array(struct XorrisO *xorriso, int flag);
int Xorriso_check_md5(struct XorrisO *xorriso, void *in_node, char *path,
int flag);
struct CheckmediajoB {
int use_dev; /* 0= use indev , 1= use outdev , 2= use sector map*/