Splitted xorriso.c and xorrisoburn.c into smaller source modules
This commit is contained in:
parent
a2b20e3ca2
commit
99e498057f
53
Makefile.am
53
Makefile.am
@ -50,8 +50,7 @@ bin_PROGRAMS = \
|
||||
# cat xorriso/xorriso_buildstamp.h
|
||||
|
||||
xorriso_xorriso_CPPFLAGS = -Ilibisoburn
|
||||
xorriso_xorriso_CFLAGS = -DXorriso_with_maiN \
|
||||
$(READLINE_DEF) $(LIBACL_DEF) $(XATTR_DEF) \
|
||||
xorriso_xorriso_CFLAGS = $(READLINE_DEF) $(LIBACL_DEF) $(XATTR_DEF) \
|
||||
$(EXTF_DEF) $(EXTF_SUID_DEF) $(ZLIB_DEF) \
|
||||
$(XORRISO_DVD_OBS_64K)
|
||||
|
||||
@ -61,9 +60,55 @@ xorriso_xorriso_LDADD = libisoburn/libisoburn.la -lisofs -lburn \
|
||||
xorriso_xorriso_SOURCES = \
|
||||
xorriso/xorriso.h \
|
||||
xorriso/xorriso_private.h \
|
||||
xorriso/xorriso.c \
|
||||
xorriso/xorriso_main.c \
|
||||
xorriso/sfile.h \
|
||||
xorriso/sfile.c \
|
||||
xorriso/aux_objects.h \
|
||||
xorriso/aux_objects.c \
|
||||
xorriso/findjob.h \
|
||||
xorriso/findjob.c \
|
||||
xorriso/check_media.h \
|
||||
xorriso/check_media.c \
|
||||
xorriso/misc_funct.h \
|
||||
xorriso/misc_funct.c \
|
||||
xorriso/text_io.h \
|
||||
xorriso/text_io.c \
|
||||
xorriso/match.h \
|
||||
xorriso/match.c \
|
||||
xorriso/emulators.h \
|
||||
xorriso/emulators.c \
|
||||
xorriso/disk_ops.h \
|
||||
xorriso/disk_ops.c \
|
||||
xorriso/cmp_update.h \
|
||||
xorriso/cmp_update.c \
|
||||
xorriso/parse_exec.h \
|
||||
xorriso/parse_exec.c \
|
||||
xorriso/opts_a_c.c \
|
||||
xorriso/opts_d_h.c \
|
||||
xorriso/opts_i_o.c \
|
||||
xorriso/opts_p_z.c \
|
||||
\
|
||||
xorriso/xorrisoburn.h \
|
||||
xorriso/xorrisoburn.c \
|
||||
xorriso/base_obj.h \
|
||||
xorriso/base_obj.c \
|
||||
xorriso/lib_mgt.h \
|
||||
xorriso/lib_mgt.c \
|
||||
xorriso/sort_cmp.h \
|
||||
xorriso/sort_cmp.c \
|
||||
xorriso/drive_mgt.h \
|
||||
xorriso/drive_mgt.c \
|
||||
xorriso/iso_img.h \
|
||||
xorriso/iso_img.c \
|
||||
xorriso/iso_tree.h \
|
||||
xorriso/iso_tree.c \
|
||||
xorriso/iso_manip.h \
|
||||
xorriso/iso_manip.c \
|
||||
xorriso/write_run.h \
|
||||
xorriso/write_run.c \
|
||||
xorriso/read_run.h \
|
||||
xorriso/read_run.c \
|
||||
xorriso/filters.h \
|
||||
xorriso/filters.c \
|
||||
xorriso/xorriso_timestamp.h \
|
||||
xorriso/xorriso_buildstamp.h
|
||||
|
||||
|
995
xorriso/aux_objects.c
Normal file
995
xorriso/aux_objects.c
Normal file
@ -0,0 +1,995 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains the implementations of classes:
|
||||
|
||||
- FindjoB, ExprnodE, ExprtesT which perform tree searches in
|
||||
libisofs or in POSIX filesystem
|
||||
|
||||
- DirseQ which crawls along a directory's content list.
|
||||
|
||||
- ExclusionS which manages the list of excluded file paths and
|
||||
leaf patterns.
|
||||
|
||||
- Xorriso_lsT which provides a generic double-linked list.
|
||||
|
||||
- LinkiteM, PermiteM which temporarily record relations and states.
|
||||
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <utime.h>
|
||||
#include <dirent.h>
|
||||
#include <errno.h>
|
||||
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
|
||||
|
||||
/* ---------------------------- SplitparT ------------------------- */
|
||||
|
||||
|
||||
struct SplitparT {
|
||||
char *name;
|
||||
int partno;
|
||||
int total_parts;
|
||||
off_t offset;
|
||||
off_t bytes;
|
||||
off_t total_bytes;
|
||||
};
|
||||
|
||||
static char Splitpart_wordS[][16]= {"part_", "_of_", "_at_", "_with_", "_of_"};
|
||||
|
||||
|
||||
int Splitparts_new(struct SplitparT **o, int count, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
(*o)= TSOB_FELD(struct SplitparT, count);
|
||||
if((*o)==NULL)
|
||||
return(-1);
|
||||
for(i= 0; i<count; i++) {
|
||||
(*o)[i].name= NULL;
|
||||
(*o)[i].partno= 0;
|
||||
(*o)[i].total_parts= 0;
|
||||
(*o)[i].offset= 0;
|
||||
(*o)[i].bytes= 0;
|
||||
(*o)[i].total_bytes= 0;
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitparts_destroy(struct SplitparT **o, int count, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if((*o)==NULL)
|
||||
return(0);
|
||||
for(i= 0; i<count; i++) {
|
||||
if((*o)[i].name!=NULL)
|
||||
free((*o)[i].name);
|
||||
}
|
||||
free(*o);
|
||||
*o= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitparts_set(struct SplitparT *o, int idx,
|
||||
char *name, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag)
|
||||
{
|
||||
if(o[idx].name!=NULL)
|
||||
free(o[idx].name);
|
||||
o[idx].name= strdup(name);
|
||||
if(o[idx].name==NULL)
|
||||
return(-1);
|
||||
o[idx].partno= partno;
|
||||
o[idx].total_parts= total_parts;
|
||||
o[idx].offset= offset;
|
||||
o[idx].bytes= bytes;
|
||||
o[idx].total_bytes= total_bytes;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitparts_get(struct SplitparT *o, int idx, char **name, int *partno,
|
||||
int *total_parts, off_t *offset, off_t *bytes,
|
||||
off_t *total_bytes, int flag)
|
||||
{
|
||||
*name= o[idx].name;
|
||||
*partno= o[idx].partno;
|
||||
*total_parts= o[idx].total_parts;
|
||||
*offset= o[idx].offset;
|
||||
*bytes= o[idx].bytes;
|
||||
*total_bytes= o[idx].total_bytes;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitpart__read_next_num(char *base_pt, char **next_pt, off_t *num,
|
||||
int flag)
|
||||
{
|
||||
char *cpt, *ept, scale[4];
|
||||
double sfak;
|
||||
|
||||
*num= 0;
|
||||
for(cpt= base_pt; *cpt!=0 && !isdigit(*cpt); cpt++);
|
||||
if(*cpt==0)
|
||||
return(0);
|
||||
for(ept= cpt; *ept!=0 && isdigit(*ept); ept++)
|
||||
*num= (*num)*10+(*ept)-'0';
|
||||
scale[0]= '1';
|
||||
scale[1]= *ept;
|
||||
scale[2]= 0;
|
||||
sfak= Scanf_io_size(scale, 0);
|
||||
*num *= (off_t) sfak;
|
||||
if(sfak > 1.0)
|
||||
ept++;
|
||||
*next_pt= ept;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitpart__parse(char *name, int *partno, int *total_parts,
|
||||
off_t *offset, off_t *bytes, off_t *total_bytes, int flag)
|
||||
|
||||
{
|
||||
int ret;
|
||||
off_t num;
|
||||
char *cpt, *ept;
|
||||
|
||||
cpt= name;
|
||||
if(strncmp(cpt, Splitpart_wordS[0], strlen(Splitpart_wordS[0])) != 0)
|
||||
return(0);
|
||||
ret= Splitpart__read_next_num(cpt, &ept, &num, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
*partno= num;
|
||||
cpt= ept;
|
||||
if(strncmp(cpt, Splitpart_wordS[1], strlen(Splitpart_wordS[1])) != 0)
|
||||
return(0);
|
||||
ret= Splitpart__read_next_num(cpt, &ept, &num, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
*total_parts= num;
|
||||
cpt= ept;
|
||||
if(strncmp(cpt, Splitpart_wordS[2], strlen(Splitpart_wordS[2])) != 0)
|
||||
return(0);
|
||||
ret= Splitpart__read_next_num(cpt, &ept, offset, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
cpt= ept;
|
||||
if(strncmp(cpt, Splitpart_wordS[3], strlen(Splitpart_wordS[3])) != 0)
|
||||
return(0);
|
||||
ret= Splitpart__read_next_num(cpt, &ept, bytes, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
cpt= ept;
|
||||
if(strncmp(cpt, Splitpart_wordS[4], strlen(Splitpart_wordS[4])) != 0)
|
||||
return(0);
|
||||
ret= Splitpart__read_next_num(cpt, &ept, total_bytes, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(*ept != 0)
|
||||
return(0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitpart__is_part_path(char *path, int flag)
|
||||
{
|
||||
int partno, total_parts, ret;
|
||||
off_t offset, bytes, total_bytes;
|
||||
char *name;
|
||||
|
||||
name= strrchr(path, '/');
|
||||
if(name == NULL)
|
||||
name= path;
|
||||
else
|
||||
name++;
|
||||
ret= Splitpart__parse(name, &partno, &total_parts, &offset, &bytes,
|
||||
&total_bytes, 0);
|
||||
return(ret > 0);
|
||||
}
|
||||
|
||||
|
||||
/* part_#_of_#_at_#_with_#_of_#
|
||||
*/
|
||||
int Splitpart__compose(char *adr, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag)
|
||||
{
|
||||
sprintf(adr, "%s%d%s%d%s", Splitpart_wordS[0], partno, Splitpart_wordS[1],
|
||||
total_parts, Splitpart_wordS[2]);
|
||||
if((offset % (1024*1024))==0 && offset>0) {
|
||||
Sfile_off_t_text(adr+strlen(adr), offset / (1024*1024), 0);
|
||||
strcat(adr, "m");
|
||||
} else
|
||||
Sfile_off_t_text(adr+strlen(adr), offset, 0);
|
||||
strcat(adr, Splitpart_wordS[3]);
|
||||
if((bytes % (1024*1024))==0) {
|
||||
Sfile_off_t_text(adr+strlen(adr), bytes / (1024*1024), 0);
|
||||
strcat(adr, "m");
|
||||
} else
|
||||
Sfile_off_t_text(adr+strlen(adr), bytes, 0);
|
||||
strcat(adr, Splitpart_wordS[4]);
|
||||
Sfile_off_t_text(adr+strlen(adr), total_bytes, 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Splitparts_cmp(const void *v1, const void *v2)
|
||||
{
|
||||
struct SplitparT *p1, *p2;
|
||||
|
||||
p1= (struct SplitparT *) v1;
|
||||
p2= (struct SplitparT *) v2;
|
||||
|
||||
if(p1->partno>p2->partno)
|
||||
return(1);
|
||||
if(p1->partno<p2->partno)
|
||||
return(-1);
|
||||
if(p1->offset>p2->offset)
|
||||
return(1);
|
||||
if(p1->offset<p2->offset)
|
||||
return(-1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Splitparts_sort(struct SplitparT *o, int count, int flag)
|
||||
{
|
||||
qsort(o, (size_t) count, sizeof(struct SplitparT), Splitparts_cmp);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* ---------------------------- End SplitparT ------------------------- */
|
||||
|
||||
|
||||
/* ------------------------------ DirseQ ------------------------------ */
|
||||
|
||||
|
||||
static int Dirseq_buffer_sizE= 100;
|
||||
|
||||
struct DirseQ {
|
||||
char adr[SfileadrL];
|
||||
DIR *dirpt;
|
||||
int count;
|
||||
char **buffer;
|
||||
int buffer_size;
|
||||
int buffer_fill;
|
||||
int buffer_rpt;
|
||||
|
||||
struct DirseQ *next;
|
||||
};
|
||||
|
||||
int Dirseq_destroy(struct DirseQ **o, int flag);
|
||||
int Dirseq_next_adrblock(struct DirseQ *o, char *replies[], int *reply_count,
|
||||
int max_replies, int flag);
|
||||
|
||||
|
||||
int Dirseq_new(struct DirseQ **o, char *adr, int flag)
|
||||
/*
|
||||
bit0= with non-fatal errors do not complain about failed opendir()
|
||||
*/
|
||||
{
|
||||
int ret,i,severe_error;
|
||||
struct DirseQ *m;
|
||||
|
||||
m= *o= TSOB_FELD(struct DirseQ,1);
|
||||
if(m==NULL)
|
||||
return(-1);
|
||||
m->adr[0]= 0;
|
||||
m->dirpt= NULL;
|
||||
m->count= 0;
|
||||
m->buffer= NULL;
|
||||
m->buffer_size= 0;
|
||||
m->buffer_fill= 0;
|
||||
m->buffer_rpt= 0;
|
||||
m->next= NULL;
|
||||
if(Sfile_str(m->adr, adr, 0)<=0)
|
||||
{ret= 0; goto failed;}
|
||||
m->buffer= TSOB_FELD(char *,Dirseq_buffer_sizE);
|
||||
if(m->buffer==NULL)
|
||||
{ret= -1; goto failed;}
|
||||
m->buffer_size= Dirseq_buffer_sizE;
|
||||
for(i= 0;i<m->buffer_size;i++)
|
||||
m->buffer[i]= NULL;
|
||||
if(adr[0]==0)
|
||||
m->dirpt= opendir(".");
|
||||
else
|
||||
m->dirpt= opendir(adr);
|
||||
if(m->dirpt==NULL) {
|
||||
severe_error= (errno && errno!=ENOENT && errno!=EACCES && errno!=ENOTDIR);
|
||||
if(severe_error || !(flag&1))
|
||||
fprintf(stderr,"opendir(%s) failed : %s\n",adr,strerror(errno));
|
||||
ret= -severe_error;
|
||||
goto failed;
|
||||
}
|
||||
return(1);
|
||||
failed:;
|
||||
Dirseq_destroy(o,0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_destroy(struct DirseQ **o, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(*o==NULL)
|
||||
return(0);
|
||||
if((*o)->dirpt!=NULL)
|
||||
closedir((*o)->dirpt);
|
||||
if((*o)->buffer!=NULL) {
|
||||
for(i=0;i<(*o)->buffer_size;i++)
|
||||
if((*o)->buffer[i]!=NULL)
|
||||
free((*o)->buffer[i]);
|
||||
free((char *) (*o)->buffer);
|
||||
}
|
||||
free((char *) *o);
|
||||
(*o)= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_set_next(struct DirseQ *o, struct DirseQ *next, int flag)
|
||||
{
|
||||
o->next= next;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_get_next(struct DirseQ *o, struct DirseQ **next, int flag)
|
||||
{
|
||||
*next= o->next;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_get_adr(struct DirseQ *o, char **adrpt, int flag)
|
||||
{
|
||||
*adrpt= o->adr;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_rewind(struct DirseQ *o, int flag)
|
||||
{
|
||||
rewinddir(o->dirpt);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_next_adr(struct DirseQ *o, char reply[SfileadrL], int flag)
|
||||
/*
|
||||
flag:
|
||||
bit0= permission to use buffer
|
||||
bit1= do not increment counter
|
||||
bit2= ignore buffer in any case
|
||||
bit3= do not exclude '.' and '..'
|
||||
bit4= sort buffer
|
||||
bit5= sort only incomplete last buffer
|
||||
return:
|
||||
<0 error
|
||||
0= no more entries available
|
||||
1= ok, reply is valid
|
||||
*/
|
||||
{
|
||||
int ret;
|
||||
struct dirent *entry;
|
||||
char *name;
|
||||
|
||||
static int override_flag_0= 0,override_flag_1= 32;
|
||||
flag= (flag&~override_flag_0)|override_flag_1;
|
||||
|
||||
if((flag&1) && o->buffer_rpt>=o->buffer_fill) {
|
||||
/* permission to buffer and buffer empty : load a buffer */
|
||||
ret= Dirseq_next_adrblock(o,o->buffer,&(o->buffer_fill),
|
||||
o->buffer_size,2|4|(flag&16));
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
o->buffer_rpt= 0;
|
||||
if((flag&32) && o->buffer_fill<o->buffer_size && o->buffer_fill>0)
|
||||
Sort_argv(o->buffer_fill,o->buffer,0);
|
||||
}
|
||||
if(o->buffer_rpt<o->buffer_fill && !(flag&4)) {
|
||||
ret= Sfile_str(reply,o->buffer[o->buffer_rpt],0);
|
||||
Sregex_string(&(o->buffer[o->buffer_rpt]),NULL,0);
|
||||
if(ret<=0)
|
||||
return(-1);
|
||||
(o->buffer_rpt)++;
|
||||
if(!(flag&2))
|
||||
o->count++;
|
||||
return(1);
|
||||
}
|
||||
do {
|
||||
entry= readdir(o->dirpt);
|
||||
if(entry==NULL) {
|
||||
/* >>> how to distinguish error from EOF , do i need a (FILE *) ? */
|
||||
return(0);
|
||||
}
|
||||
if(strlen(entry->d_name)>=SfileadrL) {
|
||||
fprintf(stderr,"--- oversized directory entry (number %d) :\n %s",
|
||||
o->count+1,entry->d_name);
|
||||
return(-1);
|
||||
}
|
||||
name= entry->d_name;
|
||||
if(flag&8)
|
||||
break;
|
||||
/* skip "." and ".." */
|
||||
} while(name[0]=='.' && ((name[1]=='.' && name[2]==0) || name[1]==0));
|
||||
if(Sfile_str(reply,name,0)<=0)
|
||||
return(-1);
|
||||
if(!(flag&2))
|
||||
o->count++;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Dirseq_next_adrblock(struct DirseQ *o, char *replies[], int *reply_count,
|
||||
int max_replies, int flag)
|
||||
/* @param replies A vector of Sregex_string pointers */
|
||||
/*
|
||||
flag:
|
||||
bit0= permission to use buffer
|
||||
bit1= do not increment counter
|
||||
bit2= ignore buffer in any case
|
||||
bit4= sort replies
|
||||
return:
|
||||
<0 error
|
||||
0= no more entries available
|
||||
1= ok, reply is valid
|
||||
*/
|
||||
{
|
||||
int i,ret;
|
||||
char reply[SfileadrL];
|
||||
|
||||
*reply_count= 0;
|
||||
for(i=0;i<max_replies;i++) {
|
||||
ret= Dirseq_next_adr(o,reply,flag&(1|2|4));
|
||||
if(ret<0)
|
||||
return(ret);
|
||||
if(ret==0)
|
||||
break;
|
||||
if(Sregex_string(&(replies[i]),reply,0)<=0)
|
||||
return(-1);
|
||||
(*reply_count)++;
|
||||
}
|
||||
if((*reply_count)==0)
|
||||
return(0);
|
||||
if(flag&16)
|
||||
Sort_argv(*reply_count,replies,0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* ---------------------------- End DirseQ ----------------------------- */
|
||||
|
||||
|
||||
/* ---------------------------- Xorriso_lsT ----------------------------- */
|
||||
|
||||
|
||||
/*
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= insert before link rather than after it
|
||||
bit1= do not copy data (e.g. because *data is invalid)
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
*/
|
||||
int Xorriso_lst_new_binary(struct Xorriso_lsT **lstring, char *data,
|
||||
int data_len, struct Xorriso_lsT *link, int flag)
|
||||
{
|
||||
int ret;
|
||||
struct Xorriso_lsT *s;
|
||||
|
||||
s= TSOB_FELD(struct Xorriso_lsT,1);
|
||||
if(s==NULL)
|
||||
return(-1);
|
||||
s->text= NULL;
|
||||
s->next= s->prev= NULL;
|
||||
|
||||
if(flag & 4) {
|
||||
s->text= data;
|
||||
} else {
|
||||
if(data_len<=0)
|
||||
{ret= -1; goto failed;}
|
||||
s->text= Smem_malloC(data_len);
|
||||
if(s->text==NULL)
|
||||
{ret= -1; goto failed;}
|
||||
if(!(flag&2))
|
||||
memcpy(s->text,data,data_len);
|
||||
}
|
||||
|
||||
if(link==NULL) {
|
||||
;
|
||||
} else if(flag&1) {
|
||||
s->next= link;
|
||||
s->prev= link->prev;
|
||||
if(link->prev!=NULL)
|
||||
link->prev->next= s;
|
||||
link->prev= s;
|
||||
} else {
|
||||
s->prev= link;
|
||||
s->next= link->next;
|
||||
if(link->next!=NULL)
|
||||
link->next->prev= s;
|
||||
link->next= s;
|
||||
}
|
||||
*lstring= s;
|
||||
return(1);
|
||||
failed:;
|
||||
*lstring= s;
|
||||
Xorriso_lst_destroy(lstring,0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param flag Bitfield for control purposes
|
||||
see Xorriso_lst_new_binary()
|
||||
*/
|
||||
int Xorriso_lst_new(struct Xorriso_lsT **lstring, char *text,
|
||||
struct Xorriso_lsT *link, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= Xorriso_lst_new_binary(lstring,text,strlen(text)+1,link,flag);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= do not set *lstring to NULL
|
||||
*/
|
||||
int Xorriso_lst_destroy(struct Xorriso_lsT **lstring, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *s;
|
||||
|
||||
s= *lstring;
|
||||
if(s==NULL)
|
||||
return(0);
|
||||
if(s->prev!=NULL)
|
||||
s->prev->next= s->next;
|
||||
if(s->next!=NULL)
|
||||
s->next->prev= s->prev;
|
||||
if(s->text!=NULL)
|
||||
Smem_freE(s->text);
|
||||
Smem_freE((char *) s);
|
||||
if(!(flag&1))
|
||||
*lstring= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_lst_destroy_all(struct Xorriso_lsT **lstring, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *s,*next;
|
||||
|
||||
if(lstring==NULL)
|
||||
return(-1);
|
||||
if((*lstring)==NULL)
|
||||
return(0);
|
||||
for(s= *lstring; s->prev!=NULL; s= s->prev);
|
||||
for(;s!=NULL;s= next){
|
||||
next= s->next;
|
||||
Xorriso_lst_destroy(&s,0);
|
||||
}
|
||||
*lstring= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_lst_append_binary(struct Xorriso_lsT **entry,
|
||||
char *data, int data_len, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *target= NULL,*newby;
|
||||
|
||||
if(*entry!=NULL)
|
||||
for(target= *entry; target->next!=NULL; target= target->next);
|
||||
if(Xorriso_lst_new_binary(&newby, data, data_len, target, flag & ~1)<=0)
|
||||
return(-1);
|
||||
if(*entry==NULL || (flag & 1))
|
||||
*entry= newby;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_next(struct Xorriso_lsT *entry, int flag)
|
||||
{
|
||||
return(entry->next);
|
||||
}
|
||||
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_prev(struct Xorriso_lsT *entry, int flag)
|
||||
{
|
||||
return(entry->prev);
|
||||
}
|
||||
|
||||
|
||||
char *Xorriso_lst_get_text(struct Xorriso_lsT *entry, int flag)
|
||||
{
|
||||
return(entry->text);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_lst_detach_text(struct Xorriso_lsT *entry, int flag)
|
||||
{
|
||||
entry->text= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* --------------------------- End Xorriso_lsT ---------------------------- */
|
||||
|
||||
|
||||
/* ------------------------------ ExclusionS ------------------------------ */
|
||||
|
||||
|
||||
struct ExclusionS {
|
||||
|
||||
/* Absolute input patterns which lead to not_paths */
|
||||
struct Xorriso_lsT *not_paths_descr;
|
||||
|
||||
/* Actually banned absolute paths */
|
||||
struct Xorriso_lsT *not_paths;
|
||||
|
||||
/* Input patterns which lead to not_leafs */
|
||||
struct Xorriso_lsT *not_leafs_descr;
|
||||
|
||||
/* Compiled not_leaf patterns. Caution: not char[] but regex_t */
|
||||
struct Xorriso_lsT *not_leafs;
|
||||
|
||||
};
|
||||
|
||||
|
||||
int Exclusions_new(struct ExclusionS **o, int flag)
|
||||
{
|
||||
struct ExclusionS *m;
|
||||
|
||||
m= *o= TSOB_FELD(struct ExclusionS, 1);
|
||||
if(m==NULL)
|
||||
return(-1);
|
||||
m->not_paths_descr= NULL;
|
||||
m->not_paths= NULL;
|
||||
m->not_leafs_descr= NULL;
|
||||
m->not_leafs= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Exclusions_destroy(struct ExclusionS **o, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *s,*next;
|
||||
|
||||
if((*o)==NULL)
|
||||
return(0);
|
||||
Xorriso_lst_destroy_all(&((*o)->not_paths_descr), 0);
|
||||
Xorriso_lst_destroy_all(&((*o)->not_paths), 0);
|
||||
Xorriso_lst_destroy_all(&((*o)->not_leafs_descr), 0);
|
||||
for(s= (*o)->not_leafs; s!=NULL; s= next){
|
||||
next= s->next;
|
||||
regfree((regex_t *) s->text);
|
||||
Xorriso_lst_destroy(&s, 0);
|
||||
}
|
||||
free((char *) *o);
|
||||
(*o)= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Exclusions_add_not_paths(struct ExclusionS *o, int descrc, char **descrs,
|
||||
int pathc, char **paths, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *s, *new_s;
|
||||
int i, ret;
|
||||
|
||||
s= NULL;
|
||||
if(o->not_paths_descr!=NULL)
|
||||
for(s= o->not_paths_descr; s->next!=NULL; s= s->next);
|
||||
for(i= 0; i<descrc; i++) {
|
||||
ret= Xorriso_lst_new(&new_s, descrs[i], s, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(o->not_paths_descr==NULL)
|
||||
o->not_paths_descr= new_s;
|
||||
s= new_s;
|
||||
}
|
||||
s= NULL;
|
||||
if(o->not_paths!=NULL)
|
||||
for(s= o->not_paths; s->next!=NULL; s= s->next);
|
||||
for(i= 0; i<pathc; i++) {
|
||||
ret= Xorriso_lst_new(&new_s, paths[i], s, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(o->not_paths==NULL)
|
||||
o->not_paths= new_s;
|
||||
s= new_s;
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @return -1=cannot store , 0=cannot compile regex , 1=ok
|
||||
*/
|
||||
int Exclusions_add_not_leafs(struct ExclusionS *o, char *not_leafs_descr,
|
||||
regex_t *re, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= Xorriso_lst_append_binary(&(o->not_leafs_descr),
|
||||
not_leafs_descr, strlen(not_leafs_descr)+1, 0);
|
||||
if(ret<=0)
|
||||
return(-1);
|
||||
ret= Xorriso_lst_append_binary(&(o->not_leafs), (char *) re, sizeof(regex_t), 0);
|
||||
if(ret<=0)
|
||||
return(-1);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= whole subtree is banned with -not_paths
|
||||
@return 0=no match , 1=not_paths , 2=not_leafs, <0=error
|
||||
*/
|
||||
int Exclusions_match(struct ExclusionS *o, char *abs_path, int flag)
|
||||
{
|
||||
struct Xorriso_lsT *s;
|
||||
char leaf[SfileadrL], *leaf_pt;
|
||||
regmatch_t match[1];
|
||||
int ret, was_non_slash, l;
|
||||
|
||||
/* test abs_paths */
|
||||
if(flag&1) {
|
||||
for(s= o->not_paths; s!=NULL; s= s->next) {
|
||||
l= strlen(s->text);
|
||||
if(strncmp(abs_path, s->text, l)==0)
|
||||
if(abs_path[l]=='/' || abs_path[l]==0)
|
||||
return(1);
|
||||
}
|
||||
} else {
|
||||
for(s= o->not_paths; s!=NULL; s= s->next)
|
||||
if(strcmp(abs_path, s->text)==0)
|
||||
return(1);
|
||||
}
|
||||
|
||||
/* determine leafname */
|
||||
was_non_slash= 0;
|
||||
for(leaf_pt= abs_path+strlen(abs_path); leaf_pt>abs_path; leaf_pt--) {
|
||||
if(*leaf_pt=='/') {
|
||||
if(was_non_slash) {
|
||||
leaf_pt++;
|
||||
break;
|
||||
}
|
||||
} else if(*leaf_pt!=0)
|
||||
was_non_slash= 1;
|
||||
}
|
||||
if(strlen(leaf_pt)>=SfileadrL)
|
||||
return(-1);
|
||||
strcpy(leaf, leaf_pt);
|
||||
leaf_pt= strchr(leaf, '/');
|
||||
if(leaf_pt!=NULL)
|
||||
*leaf_pt= 0;
|
||||
|
||||
/* test with leaf expressions */
|
||||
for(s= o->not_leafs; s!=NULL; s= s->next) {
|
||||
ret= regexec((regex_t *) s->text, leaf, 1, match, 0);
|
||||
if(ret==0)
|
||||
return(2);
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Exclusions_get_descrs(struct ExclusionS *o,
|
||||
struct Xorriso_lsT **not_paths_descr,
|
||||
struct Xorriso_lsT **not_leafs_descr, int flag)
|
||||
{
|
||||
*not_paths_descr= o->not_paths_descr;
|
||||
*not_leafs_descr= o->not_leafs_descr;
|
||||
return(1);
|
||||
}
|
||||
|
||||
/* ---------------------------- End ExclusionS ---------------------------- */
|
||||
|
||||
|
||||
/* ------------------------------ LinkiteM -------------------------------- */
|
||||
|
||||
struct LinkiteM {
|
||||
char *link_path;
|
||||
dev_t target_dev;
|
||||
ino_t target_ino;
|
||||
int link_count;
|
||||
struct LinkiteM *next;
|
||||
};
|
||||
|
||||
|
||||
int Linkitem_new(struct LinkiteM **o, char *link_path, dev_t target_dev,
|
||||
ino_t target_ino, struct LinkiteM *next, int flag)
|
||||
{
|
||||
struct LinkiteM *m;
|
||||
|
||||
m= *o= TSOB_FELD(struct LinkiteM,1);
|
||||
if(m==NULL)
|
||||
return(-1);
|
||||
m->target_dev= target_dev;
|
||||
m->target_ino= target_ino;
|
||||
m->next= next;
|
||||
m->link_count= 1;
|
||||
if(next!=NULL)
|
||||
m->link_count= m->next->link_count+1;
|
||||
m->link_path= strdup(link_path);
|
||||
if(m->link_path==NULL)
|
||||
goto failed;
|
||||
return(1);
|
||||
failed:;
|
||||
Linkitem_destroy(o, 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
int Linkitem_destroy(struct LinkiteM **o, int flag)
|
||||
{
|
||||
if((*o)==NULL)
|
||||
return(0);
|
||||
if((*o)->link_path!=NULL)
|
||||
free((*o)->link_path);
|
||||
free((char *) (*o));
|
||||
*o= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Linkitem_reset_stack(struct LinkiteM **o, struct LinkiteM *to, int flag)
|
||||
{
|
||||
struct LinkiteM *m, *m_next= NULL;
|
||||
|
||||
/* Prevent memory corruption */
|
||||
for(m= *o; m!=to; m= m->next)
|
||||
if(m==NULL) { /* this may actually not happen */
|
||||
*o= to;
|
||||
return(-1);
|
||||
}
|
||||
|
||||
for(m= *o; m!=to; m= m_next) {
|
||||
m_next= m->next;
|
||||
Linkitem_destroy(&m, 0);
|
||||
}
|
||||
*o= to;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Linkitem_find(struct LinkiteM *stack, dev_t target_dev, ino_t target_ino,
|
||||
struct LinkiteM **result, int flag)
|
||||
{
|
||||
struct LinkiteM *m;
|
||||
|
||||
for(m= stack; m!=NULL; m= m->next) {
|
||||
if(target_dev == m->target_dev && target_ino == m->target_ino) {
|
||||
*result= m;
|
||||
return(1);
|
||||
}
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Linkitem_get_link_count(struct LinkiteM *item, int flag)
|
||||
{
|
||||
return(item->link_count);
|
||||
}
|
||||
|
||||
|
||||
/* ------------------------------ PermstacK ------------------------------- */
|
||||
|
||||
|
||||
struct PermiteM {
|
||||
char *disk_path;
|
||||
struct stat stbuf;
|
||||
struct PermiteM *next;
|
||||
};
|
||||
|
||||
|
||||
int Permstack_push(struct PermiteM **o, char *disk_path, struct stat *stbuf,
|
||||
int flag)
|
||||
{
|
||||
struct PermiteM *m;
|
||||
|
||||
m= TSOB_FELD(struct PermiteM,1);
|
||||
if(m==NULL)
|
||||
return(-1);
|
||||
m->disk_path= NULL;
|
||||
memcpy(&(m->stbuf), stbuf, sizeof(struct stat));
|
||||
m->next= *o;
|
||||
|
||||
m->disk_path= strdup(disk_path);
|
||||
if(m->disk_path==NULL)
|
||||
goto failed;
|
||||
|
||||
*o= m;
|
||||
return(1);
|
||||
failed:;
|
||||
if(m->disk_path!=NULL)
|
||||
free(m->disk_path);
|
||||
free((char *) m);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= minimal transfer: access permissions only
|
||||
bit1= do not set timestamps
|
||||
*/
|
||||
int Permstack_pop(struct PermiteM **o, struct PermiteM *stopper,
|
||||
struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
char sfe[5*SfileadrL];
|
||||
struct utimbuf utime_buffer;
|
||||
struct PermiteM *m, *m_next;
|
||||
|
||||
if((*o)==stopper)
|
||||
return(1);
|
||||
for(m= *o; m!=NULL; m= m->next)
|
||||
if(m->next==stopper)
|
||||
break;
|
||||
if(m==NULL) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Program error: Permstack_pop() : cannot find stopper");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
for(m= *o; m!=stopper; m= m_next) {
|
||||
ret= chmod(m->disk_path, m->stbuf.st_mode);
|
||||
if(ret==-1) {
|
||||
if(xorriso!=NULL) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot change access permissions of disk directory: chmod %o %s",
|
||||
(unsigned int) (m->stbuf.st_mode & 07777),
|
||||
Text_shellsafe(m->disk_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE",
|
||||
0);
|
||||
}
|
||||
}
|
||||
if(!(flag&1)) {
|
||||
chown(m->disk_path, m->stbuf.st_uid, m->stbuf.st_gid);
|
||||
/* don't complain if it fails */
|
||||
if(!(flag&2)) {
|
||||
utime_buffer.actime= m->stbuf.st_atime;
|
||||
utime_buffer.modtime= m->stbuf.st_mtime;
|
||||
ret= utime(m->disk_path,&utime_buffer);
|
||||
if(ret==-1 && xorriso!=NULL) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot change timestamps of disk directory: %s",
|
||||
Text_shellsafe(m->disk_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE",
|
||||
0);
|
||||
}
|
||||
}
|
||||
}
|
||||
m_next= m->next;
|
||||
free(m->disk_path);
|
||||
free((char *) m);
|
||||
*o= m_next;
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* ---------------------------- End PermstacK ----------------------------- */
|
||||
|
182
xorriso/aux_objects.h
Normal file
182
xorriso/aux_objects.h
Normal file
@ -0,0 +1,182 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of classes:
|
||||
|
||||
- FindjoB, ExprnodE, ExprtesT which perform tree searches in
|
||||
libisofs or in POSIX filesystem
|
||||
|
||||
- DirseQ which crawls along a directory's content list.
|
||||
|
||||
- ExclusionS which manages the list of excluded file paths and
|
||||
leaf patterns.
|
||||
|
||||
- Xorriso_lsT which provides a generic double-linked list.
|
||||
|
||||
- LinkiteM, PermiteM which temporarily record relations and states.
|
||||
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_auxobj_includeD
|
||||
#define Xorriso_pvt_auxobj_includeD yes
|
||||
|
||||
struct SplitparT;
|
||||
|
||||
int Splitparts_new(struct SplitparT **o, int count, int flag);
|
||||
|
||||
int Splitparts_destroy(struct SplitparT **o, int count, int flag);
|
||||
|
||||
int Splitparts_set(struct SplitparT *o, int idx,
|
||||
char *name, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag);
|
||||
|
||||
int Splitparts_get(struct SplitparT *o, int idx, char **name, int *partno,
|
||||
int *total_parts, off_t *offset, off_t *bytes,
|
||||
off_t *total_bytes, int flag);
|
||||
|
||||
int Splitpart__parse(char *name, int *partno, int *total_parts,
|
||||
off_t *offset, off_t *bytes, off_t *total_bytes, int flag);
|
||||
|
||||
int Splitpart__is_part_path(char *path, int flag);
|
||||
|
||||
int Splitpart__compose(char *adr, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag);
|
||||
|
||||
int Splitpart__read_next_num(char *base_pt, char **next_pt, off_t *num,
|
||||
int flag);
|
||||
|
||||
int Splitparts_sort(struct SplitparT *o, int count, int flag);
|
||||
|
||||
|
||||
|
||||
struct DirseQ;
|
||||
|
||||
int Dirseq_new(struct DirseQ **o, char *adr, int flag);
|
||||
|
||||
int Dirseq_destroy(struct DirseQ **o, int flag);
|
||||
|
||||
int Dirseq_next_adr(struct DirseQ *o, char reply[SfileadrL], int flag);
|
||||
|
||||
int Dirseq_rewind(struct DirseQ *o, int flag);
|
||||
|
||||
|
||||
|
||||
struct Xorriso_lsT {
|
||||
char *text;
|
||||
struct Xorriso_lsT *prev,*next;
|
||||
};
|
||||
|
||||
/** Create a new list item with arbitrary byte content.
|
||||
@param lstring The newly created object or NULL on failure
|
||||
@param data An array of bytes to be copied into the new object
|
||||
@param data_len Number of bytes to be copied
|
||||
@param link Xorriso_lsT object to which the new object shall be linked
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= insert before link rather than after it
|
||||
bit1= do not copy data (e.g. because *data is invalid)
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_new_binary(struct Xorriso_lsT **lstring, char *data,
|
||||
int data_len, struct Xorriso_lsT *link, int flag);
|
||||
|
||||
|
||||
/** Create a new list item with a 0-terminated text as content.
|
||||
@param lstring The newly created object or NULL on failure
|
||||
@param text A 0-terminated array of bytes
|
||||
@param link Xorriso_lsT object to which the new object shall be linked
|
||||
@param flag see Xorriso_lst_new_binary
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_new(struct Xorriso_lsT **lstring, char *text,
|
||||
struct Xorriso_lsT *link, int flag);
|
||||
|
||||
|
||||
/** Create a new list item at the end of a given list.
|
||||
@param entry Contains as input a pointer to a pointer to any existing
|
||||
list item. As output this list item pointer may be
|
||||
changed to the address of the new list item:
|
||||
if ((*entry == 0) || (flag & 1))
|
||||
@param data An array of bytes to be copied into the new object
|
||||
@param data_len Number of bytes to be copied
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= Return new object address in *entry
|
||||
bit1= do not copy data (e.g. because *data is invalid)
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_append_binary(struct Xorriso_lsT **entry,
|
||||
char *data, int data_len, int flag);
|
||||
|
||||
|
||||
/** Destroy a single list item and connect its eventual list neighbors.
|
||||
@param lstring pointer to the pointer to be freed and set to NULL
|
||||
@param flag unused yet, submit 0
|
||||
@return 0= *lstring was alredy NULL, 1= ok
|
||||
*/
|
||||
int Xorriso_lst_destroy(struct Xorriso_lsT **lstring, int flag);
|
||||
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_next(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_prev(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
char *Xorriso_lst_get_text(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
int Xorriso_lst_detach_text(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
|
||||
|
||||
int Exclusions_new(struct ExclusionS **o, int flag);
|
||||
|
||||
int Exclusions_destroy(struct ExclusionS **o, int flag);
|
||||
|
||||
int Exclusions_get_descrs(struct ExclusionS *o,
|
||||
struct Xorriso_lsT **not_paths_descr,
|
||||
struct Xorriso_lsT **not_leafs_descr, int flag);
|
||||
|
||||
/* @param flag bit0= whole subtree is banned with -not_paths
|
||||
@return 0=no match , 1=not_paths , 2=not_leafs, <0=error
|
||||
*/
|
||||
int Exclusions_match(struct ExclusionS *o, char *abs_path, int flag);
|
||||
|
||||
int Exclusions_add_not_leafs(struct ExclusionS *o, char *not_leafs_descr,
|
||||
regex_t *re, int flag);
|
||||
|
||||
int Exclusions_add_not_paths(struct ExclusionS *o, int descrc, char **descrs,
|
||||
int pathc, char **paths, int flag);
|
||||
|
||||
|
||||
|
||||
struct LinkiteM; /* Trace of hops during symbolic link resolution */
|
||||
|
||||
int Linkitem_new(struct LinkiteM **o, char *link_path, dev_t target_dev,
|
||||
ino_t target_ino, struct LinkiteM *next, int flag);
|
||||
|
||||
int Linkitem_destroy(struct LinkiteM **o, int flag);
|
||||
|
||||
int Linkitem_reset_stack(struct LinkiteM **o, struct LinkiteM *to, int flag);
|
||||
|
||||
int Linkitem_find(struct LinkiteM *stack, dev_t target_dev, ino_t target_ino,
|
||||
struct LinkiteM **result, int flag);
|
||||
|
||||
int Linkitem_get_link_count(struct LinkiteM *item, int flag);
|
||||
|
||||
|
||||
struct PermiteM; /* Stack of temporarily altered access permissions */
|
||||
|
||||
int Permstack_push(struct PermiteM **o, char *disk_path, struct stat *stbuf,
|
||||
int flag);
|
||||
|
||||
int Permstack_pop(struct PermiteM **o, struct PermiteM *stopper,
|
||||
struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_auxobj_includeD */
|
||||
|
537
xorriso/base_obj.c
Normal file
537
xorriso/base_obj.c
Normal file
@ -0,0 +1,537 @@
|
||||
|
||||
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains functions which are needed to read data
|
||||
from ISO image.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
|
||||
#include "base_obj.h"
|
||||
#include "lib_mgt.h"
|
||||
|
||||
|
||||
|
||||
/* See Xorriso__preset_signal_behavior() */
|
||||
static int Xorriso_signal_behavioR= 1;
|
||||
|
||||
|
||||
char *Xorriso__get_version_text(int flag)
|
||||
{
|
||||
return(Xorriso_program_versioN);
|
||||
}
|
||||
|
||||
|
||||
char *Xorriso__get_patch_level_text(int flag)
|
||||
{
|
||||
return(Xorriso_program_patch_leveL);
|
||||
}
|
||||
|
||||
|
||||
/** The list of startup file names */
|
||||
#define Xorriso_rc_nuM 4
|
||||
|
||||
static char Xorriso_sys_rc_nameS[Xorriso_rc_nuM][80]= {
|
||||
"/etc/default/xorriso",
|
||||
"/etc/opt/xorriso/rc",
|
||||
"/etc/xorriso/xorriso.conf",
|
||||
"placeholder for $HOME/.xorrisorc"
|
||||
};
|
||||
|
||||
|
||||
int Xorriso_new(struct XorrisO ** xorriso,char *progname, int flag)
|
||||
{
|
||||
int i, ret;
|
||||
struct XorrisO *m;
|
||||
char leafname[SfileadrL];
|
||||
|
||||
*xorriso= m= TSOB_FELD(struct XorrisO,1);
|
||||
if(m==NULL)
|
||||
return(-1);
|
||||
m->libs_are_started= 0;
|
||||
strncpy(m->progname,progname,sizeof(m->progname)-1);
|
||||
m->progname[sizeof(m->progname)-1]= 0;
|
||||
if(getcwd(m->initial_wdx,sizeof(m->initial_wdx)-1)==NULL)
|
||||
m->initial_wdx[0]= 0;
|
||||
m->no_rc= 0;
|
||||
m->argument_emulation= 0;
|
||||
|
||||
m->rc_filename_count= Xorriso_rc_nuM;
|
||||
for(i=0;i<m->rc_filename_count-1;i++)
|
||||
strcpy(m->rc_filenames[i],Xorriso_sys_rc_nameS[i]);
|
||||
m->rc_filenames[m->rc_filename_count-1][0]= 0;
|
||||
|
||||
m->wdi[0]= 0;
|
||||
strcpy(m->wdx, m->initial_wdx);
|
||||
m->did_something_useful= 0;
|
||||
m->add_plainly= 0;
|
||||
m->split_size= 0;
|
||||
strcpy(m->list_delimiter, "--");
|
||||
m->ino_behavior= 7;
|
||||
m->do_joliet= 0;
|
||||
m->do_aaip= 0;
|
||||
m->do_md5= 0;
|
||||
m->scdbackup_tag_name[0]= 0;
|
||||
m->scdbackup_tag_time[0]= 0;
|
||||
m->scdbackup_tag_written[0]= 0;
|
||||
m->scdbackup_tag_listname[0]= 0;
|
||||
m->relax_compliance= 0;
|
||||
m->do_follow_pattern= 1;
|
||||
m->do_follow_param= 0;
|
||||
m->do_follow_links= 0;
|
||||
m->follow_link_limit= 100;
|
||||
m->do_follow_mount= 1;
|
||||
m->do_global_uid= 0;
|
||||
m->global_uid= 0;
|
||||
strcpy(m->volid, "ISOIMAGE");
|
||||
m->volid_default= 1;
|
||||
m->loaded_volid[0]= 0;
|
||||
m->assert_volid[0]= 0;
|
||||
m->assert_volid_sev[0]= 0;
|
||||
m->publisher[0]= 0;
|
||||
m->application_id[0]= 0;
|
||||
m->system_id[0]= 0;
|
||||
m->volset_id[0]= 0;
|
||||
m->session_logfile[0]= 0;
|
||||
m->session_lba= -1;
|
||||
m->session_blocks= 0;
|
||||
m->do_global_gid= 0;
|
||||
m->global_gid= 0;
|
||||
m->do_global_mode= 0;
|
||||
m->global_dir_mode= 0555;
|
||||
m->global_file_mode= 0444;
|
||||
m->filters= NULL;
|
||||
m->filter_list_closed= 0;
|
||||
m->zlib_level_default= m->zlib_level= 6;
|
||||
m->zisofs_block_size= m->zisofs_block_size_default= (1 << 15);
|
||||
m->zisofs_by_magic= 0;
|
||||
m->do_overwrite= 2;
|
||||
m->do_reassure= 0;
|
||||
m->drive_blacklist= NULL;
|
||||
m->drive_greylist= NULL;
|
||||
m->drive_whitelist= NULL;
|
||||
m->toc_emulation_flag= 0;
|
||||
m->image_start_mode= 0;
|
||||
m->image_start_value[0]= 0;
|
||||
m->drives_exclusive= 1;
|
||||
m->do_calm_drive= 1;
|
||||
m->indev[0]= 0;
|
||||
m->in_drive_handle= NULL;
|
||||
m->in_volset_handle= NULL;
|
||||
m->in_charset= NULL;
|
||||
m->isofs_st_out= time(0) - 1;
|
||||
m->indev_is_exclusive= 1;
|
||||
m->isofs_st_in= 0;
|
||||
m->volset_change_pending= 0;
|
||||
m->no_volset_present= 0;
|
||||
m->in_sector_map= NULL;
|
||||
m->check_media_default= NULL;
|
||||
m->check_media_bad_limit= Xorriso_read_quality_invaliD;
|
||||
m->outdev[0]= 0;
|
||||
m->out_drive_handle= NULL;
|
||||
m->out_charset= NULL;
|
||||
m->dev_fd_1= -1;
|
||||
m->outdev_is_exclusive= 1;
|
||||
m->grow_blindly_msc2= -1;
|
||||
m->ban_stdio_write= 0;
|
||||
m->do_dummy= 0;
|
||||
m->do_close= 0;
|
||||
m->speed= 0;
|
||||
m->fs= 4*512; /* 4 MiB */
|
||||
m->padding= 300*1024;
|
||||
m->alignment= 0;
|
||||
m->do_stream_recording= 0;
|
||||
m->dvd_obs= 0;
|
||||
m->stdio_sync= 0;
|
||||
m->keep_boot_image= 0;
|
||||
m->boot_image_cat_path[0]= 0;
|
||||
m->boot_count= 0;
|
||||
m->boot_platform_id= 0x00; /* El Torito Boot Catalog Platform ID: 0 = 80x86 */
|
||||
m->patch_isolinux_image= 0;
|
||||
m->boot_image_bin_path[0]= 0;
|
||||
m->boot_image_bin_form[0]= 0;
|
||||
m->boot_image_emul= 0;
|
||||
m->boot_image_load_size= 4 * 512; /* hearsay out of libisofs/demo/iso.c */
|
||||
memset(m->boot_id_string, 0, sizeof(m->boot_id_string));
|
||||
memset(m->boot_selection_crit, 0, sizeof(m->boot_selection_crit));
|
||||
|
||||
#ifdef Xorriso_with_isohybriD
|
||||
m->boot_image_isohybrid= 1;
|
||||
#else
|
||||
m->boot_image_isohybrid= 0;
|
||||
#endif
|
||||
|
||||
m->boot_efi_default= 0;
|
||||
m->system_area_disk_path[0]= 0;
|
||||
m->system_area_options= 0;
|
||||
m->patch_system_area= 0;
|
||||
m->vol_creation_time= 0;
|
||||
m->vol_modification_time= 0;
|
||||
m->vol_expiration_time= 0;
|
||||
m->vol_effective_time= 0;
|
||||
m->vol_uuid[0]= 0;
|
||||
m->loaded_boot_bin_lba= 0;
|
||||
m->loaded_boot_cat_path[0]= 0;
|
||||
m->allow_graft_points= 0;
|
||||
m->allow_restore= 0;
|
||||
m->do_concat_split= 1;
|
||||
m->do_auto_chmod= 0;
|
||||
m->do_restore_sort_lba= 0;
|
||||
m->dialog= 0;
|
||||
m->bsl_interpretation= 0;
|
||||
m->search_mode= 0;
|
||||
m->structured_search= 1;
|
||||
m->do_iso_rr_pattern= 1;
|
||||
m->do_disk_pattern= 2;
|
||||
m->temp_mem_limit= 16*1024*1024;
|
||||
m->file_size_limit= Xorriso_default_file_size_limiT;
|
||||
m->disk_exclusions= NULL;
|
||||
m->disk_excl_mode= 1;
|
||||
m->use_stdin= 0;
|
||||
m->result_page_length= 0;
|
||||
m->result_page_width= 80;
|
||||
m->mark_text[0]= 0;
|
||||
m->packet_output= 0;
|
||||
for(i=0; i<4; i++) {
|
||||
m->logfile[i][0]= 0;
|
||||
m->logfile_fp[i]= NULL;
|
||||
}
|
||||
m->pktlog_fp= NULL;
|
||||
for(i= 0; i < Xorriso_max_outlist_stacK; i++) {
|
||||
m->result_msglists[i]= NULL;
|
||||
m->info_msglists[i]= NULL;
|
||||
m->msglist_flags[i]= 0;
|
||||
}
|
||||
m->msglist_stackfill= 0;
|
||||
m->status_history_max= Xorriso_status_history_maX;
|
||||
m->scsi_log= 0;
|
||||
strcpy(m->report_about_text, "UPDATE");
|
||||
Xorriso__text_to_sev(m->report_about_text, &m->report_about_severity, 0);
|
||||
m->library_msg_direct_print= 0;
|
||||
strcpy(m->abort_on_text,"FATAL");
|
||||
Xorriso__text_to_sev(m->abort_on_text, &m->abort_on_severity, 0);
|
||||
m->problem_status= 0;
|
||||
m->problem_status_text[0]= 0;
|
||||
m->errfile_log[0]= 0;
|
||||
m->errfile_mode= 0;
|
||||
m->errfile_fp= NULL;
|
||||
|
||||
m->img_read_error_mode= 2; /* abort faulty image reading with FATAL */
|
||||
m->extract_error_mode= 1; /* keep extracted files after read error */
|
||||
strcpy(m->return_with_text, "SORRY");
|
||||
Xorriso__text_to_sev(m->return_with_text, &m->return_with_severity, 0);
|
||||
m->return_with_value= 32;
|
||||
m->eternal_problem_status= 0;
|
||||
m->eternal_problem_status_text[0]= 0;
|
||||
m->re= NULL;
|
||||
/* >>> ??? how to initialize m->match[0] ? */
|
||||
m->re_constants= NULL;
|
||||
m->re_count= 0;
|
||||
m->re_fill= 0;
|
||||
m->reg_expr[0]= 0;
|
||||
m->run_state= 0;
|
||||
m->is_dialog= 0;
|
||||
m->bar_is_fresh= 0;
|
||||
m->pending_option[0]= 0;
|
||||
m->request_to_abort= 0;
|
||||
m->request_not_to_ask= 0;
|
||||
m->idle_time= 0.0;
|
||||
m->re_failed_at= -1;
|
||||
m->prepended_wd= 0;
|
||||
m->insert_count= 0;
|
||||
m->insert_bytes= 0;
|
||||
m->error_count= 0;
|
||||
m->pacifier_style= 0;
|
||||
m->pacifier_interval= 1.0;
|
||||
m->pacifier_count= 0;
|
||||
m->pacifier_total= 0;
|
||||
m->pacifier_byte_count= 0;
|
||||
m->pacifier_fifo= NULL;
|
||||
m->start_time= 0.0;
|
||||
m->last_update_time= 0.0;
|
||||
m->find_compare_result= 1;
|
||||
m->find_check_md5_result= 0;
|
||||
|
||||
m->node_counter= 0;
|
||||
m->node_array_size= 0;
|
||||
m->node_array= NULL;
|
||||
m->node_disk_prefixes= NULL;
|
||||
m->node_img_prefixes= NULL;
|
||||
|
||||
m->hln_count= 0;
|
||||
m->hln_array= NULL;
|
||||
m->hln_targets= NULL;
|
||||
m->hln_change_pending= 0;
|
||||
m->di_do_widen= NULL;
|
||||
m->di_disk_paths= NULL;
|
||||
m->di_iso_paths= NULL;
|
||||
|
||||
m->node_targets_availmem= 0;
|
||||
|
||||
m->di_count= 0;
|
||||
m->di_array= NULL;
|
||||
|
||||
m->perm_stack= NULL;
|
||||
|
||||
m->result_line[0]= 0;
|
||||
m->result_line_counter= 0;
|
||||
m->result_page_counter= 0;
|
||||
m->result_open_line_len= 0;
|
||||
|
||||
m->info_text[0]= 0;
|
||||
|
||||
ret= Sfile_leafname(progname, leafname, 0);
|
||||
if(ret<=0)
|
||||
goto failure;
|
||||
if(strcmp(leafname, "osirrox")==0) {
|
||||
m->allow_restore= 1;
|
||||
m->drives_exclusive= 0;
|
||||
} else if(strcmp(leafname, "xorrisofs")==0 || strcmp(leafname, "genisofs")==0 ||
|
||||
strcmp(leafname, "mkisofs")==0 || strcmp(leafname, "genisoimage")==0) {
|
||||
m->argument_emulation= 1;
|
||||
m->pacifier_style= 1;
|
||||
Xorriso_protect_stdout(*xorriso, 0);
|
||||
} else if(strcmp(leafname, "xorrecord")==0 || strcmp(leafname, "wodim")==0 ||
|
||||
strcmp(leafname, "cdrecord")==0 || strcmp(leafname, "cdrskin")==0) {
|
||||
m->argument_emulation= 2;
|
||||
m->pacifier_style= 2;
|
||||
}
|
||||
ret= Exclusions_new(&(m->disk_exclusions), 0);
|
||||
if(ret<=0)
|
||||
goto failure;
|
||||
Xorriso_relax_compliance(m, "default", 0);
|
||||
ret= Xorriso_lst_new(&(m->drive_greylist), "/dev", m->drive_greylist, 1);
|
||||
if(ret <= 0)
|
||||
goto failure;
|
||||
|
||||
return(1);
|
||||
failure:;
|
||||
Xorriso_destroy(xorriso, 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_destroy_re(struct XorrisO *m, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(m->re!=NULL) {
|
||||
for(i=0;i<m->re_fill;i++) {
|
||||
if(m->re_constants!=NULL)
|
||||
if(m->re_constants[i]!=NULL)
|
||||
continue; /* ,->re[i] was never subject to regcomp() */
|
||||
regfree(&(m->re[i]));
|
||||
}
|
||||
free((char *) m->re);
|
||||
m->re= NULL;
|
||||
}
|
||||
|
||||
if(m->re_constants!=NULL) {
|
||||
for(i=0;i<m->re_fill;i++)
|
||||
if(m->re_constants[i]!=NULL)
|
||||
free(m->re_constants[i]);
|
||||
free((char *) m->re_constants);
|
||||
m->re_constants= NULL;
|
||||
}
|
||||
m->re_count= 0;
|
||||
m->re_fill= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= global shutdown of libraries */
|
||||
int Xorriso_destroy(struct XorrisO **xorriso, int flag)
|
||||
{
|
||||
struct XorrisO *m;
|
||||
|
||||
m= *xorriso;
|
||||
if(m==NULL)
|
||||
return(0);
|
||||
if(m->in_charset!=NULL)
|
||||
free(m->in_charset);
|
||||
if(m->out_charset!=NULL)
|
||||
free(m->out_charset);
|
||||
Xorriso_destroy_re(m,0);
|
||||
Exclusions_destroy(&(m->disk_exclusions), 0);
|
||||
Xorriso_destroy_all_extf(m, 0);
|
||||
Xorriso_lst_destroy_all(&(m->drive_blacklist), 0);
|
||||
Xorriso_lst_destroy_all(&(m->drive_greylist), 0);
|
||||
Xorriso_lst_destroy_all(&(m->drive_whitelist), 0);
|
||||
Xorriso_destroy_node_array(m, 0);
|
||||
Xorriso_destroy_hln_array(m, 0);
|
||||
Xorriso_destroy_di_array(m, 0);
|
||||
|
||||
Xorriso_detach_libraries(m, flag&1);
|
||||
|
||||
free((char *) m);
|
||||
*xorriso= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_destroy_node_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(xorriso->node_array != NULL) {
|
||||
for(i= 0; i < xorriso->node_counter; i++)
|
||||
iso_node_unref((IsoNode *) xorriso->node_array[i]);
|
||||
free(xorriso->node_array);
|
||||
}
|
||||
xorriso->node_array= NULL;
|
||||
xorriso->node_counter= xorriso->node_array_size= 0;
|
||||
Xorriso_lst_destroy_all(&(xorriso->node_disk_prefixes), 0);
|
||||
Xorriso_lst_destroy_all(&(xorriso->node_img_prefixes), 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not destroy hln_array but only hln_targets
|
||||
*/
|
||||
int Xorriso_destroy_hln_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
|
||||
if(xorriso->hln_array != NULL && !(flag & 1)) {
|
||||
for(i= 0; i < xorriso->hln_count; i++)
|
||||
iso_node_unref((IsoNode *) xorriso->hln_array[i]);
|
||||
free(xorriso->hln_array);
|
||||
xorriso->hln_array= NULL;
|
||||
xorriso->hln_count= 0;
|
||||
}
|
||||
if(xorriso->hln_targets != NULL) {
|
||||
for(i= 0; i < xorriso->hln_count; i++)
|
||||
if(xorriso->hln_targets[i] != NULL)
|
||||
free(xorriso->hln_targets[i]);
|
||||
free(xorriso->hln_targets);
|
||||
xorriso->hln_targets= NULL;
|
||||
}
|
||||
xorriso->node_targets_availmem= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_destroy_di_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(xorriso->di_array != NULL) {
|
||||
for(i= 0; i < xorriso->di_count; i++)
|
||||
if(xorriso->di_array[i] != NULL)
|
||||
iso_node_unref((IsoNode *) xorriso->di_array[i]);
|
||||
free(xorriso->di_array);
|
||||
xorriso->di_array= NULL;
|
||||
}
|
||||
if(xorriso->di_do_widen != NULL) {
|
||||
free(xorriso->di_do_widen);
|
||||
xorriso->di_do_widen= NULL;
|
||||
}
|
||||
Xorriso_lst_destroy_all(&(xorriso->di_disk_paths), 0);
|
||||
Xorriso_lst_destroy_all(&(xorriso->di_iso_paths), 0);
|
||||
xorriso->di_count= 0;
|
||||
|
||||
#ifdef NIX
|
||||
/* <<< */
|
||||
fprintf(stderr, "xorriso_DEBUG: get_di_count= %lu\n",
|
||||
Xorriso_get_di_counteR);
|
||||
#endif /* NIX */
|
||||
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_new_node_array(struct XorrisO *xorriso, off_t mem_limit,
|
||||
int addon_nodes, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(xorriso->node_counter <= 0)
|
||||
return(1);
|
||||
|
||||
xorriso->node_array= calloc(xorriso->node_counter + addon_nodes,
|
||||
sizeof(IsoNode *));
|
||||
if(xorriso->node_array == NULL) {
|
||||
Xorriso_no_malloc_memory(xorriso, NULL, 0);
|
||||
return(-1);
|
||||
}
|
||||
for(i= 0; i < xorriso->node_counter + addon_nodes; i++)
|
||||
xorriso->node_array[i]= NULL;
|
||||
xorriso->node_array_size= xorriso->node_counter + addon_nodes;
|
||||
xorriso->node_counter= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not allocate hln_array but only hln_targets
|
||||
*/
|
||||
int Xorriso_new_hln_array(struct XorrisO *xorriso, off_t mem_limit, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
Xorriso_destroy_hln_array(xorriso, flag & 1);
|
||||
if(xorriso->hln_count <= 0)
|
||||
return(1);
|
||||
|
||||
if(!(flag & 1)) {
|
||||
xorriso->hln_array= calloc(xorriso->hln_count, sizeof(char *));
|
||||
if(xorriso->hln_array == NULL) {
|
||||
Xorriso_no_malloc_memory(xorriso, NULL, 0);
|
||||
return(-1);
|
||||
}
|
||||
for(i= 0; i < xorriso->hln_count; i++)
|
||||
xorriso->hln_array[i]= NULL;
|
||||
}
|
||||
|
||||
xorriso->hln_targets= calloc(xorriso->hln_count, sizeof(char *));
|
||||
if(xorriso->hln_targets == NULL) {
|
||||
if(!(flag & 1)) {
|
||||
free(xorriso->hln_array);
|
||||
xorriso->hln_array= NULL;
|
||||
}
|
||||
Xorriso_no_malloc_memory(xorriso, NULL, 0);
|
||||
return(-1);
|
||||
}
|
||||
for(i= 0; i < xorriso->hln_count; i++)
|
||||
xorriso->hln_targets[i]= NULL;
|
||||
xorriso->node_targets_availmem= mem_limit
|
||||
- xorriso->hln_count * sizeof(void *)
|
||||
- xorriso->hln_count * sizeof(char *);
|
||||
if(xorriso->node_targets_availmem < 0)
|
||||
xorriso->node_targets_availmem= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__preset_signal_behavior(int behavior, int flag)
|
||||
{
|
||||
if(behavior < 0 || behavior > 1)
|
||||
return(0);
|
||||
Xorriso_signal_behavioR= behavior;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__get_signal_behavior(int flag)
|
||||
{
|
||||
return(Xorriso_signal_behavioR);
|
||||
}
|
||||
|
31
xorriso/base_obj.h
Normal file
31
xorriso/base_obj.h
Normal file
@ -0,0 +1,31 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which perform the
|
||||
fundamental operations of the XorrisO object.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_base_obj_includeD
|
||||
#define Xorriso_pvt_base_obj_includeD yes
|
||||
|
||||
|
||||
#ifdef NIX
|
||||
/* <<< */
|
||||
unsigned long Xorriso_get_di_counteR= 0;
|
||||
#endif /* NIX */
|
||||
|
||||
struct XorrisO;
|
||||
|
||||
|
||||
int Xorriso_destroy_re(struct XorrisO *m, int flag);
|
||||
|
||||
int Xorriso__get_signal_behavior(int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_base_obj_includeD */
|
||||
|
1102
xorriso/check_media.c
Normal file
1102
xorriso/check_media.c
Normal file
File diff suppressed because it is too large
Load Diff
181
xorriso/check_media.h
Normal file
181
xorriso/check_media.h
Normal file
@ -0,0 +1,181 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of classes SpotlistiteM, SpotlisT,
|
||||
SectorbitmaP, CheckmediajoB which represent media checks and their outcome.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_check_includeD
|
||||
#define Xorriso_pvt_check_includeD yes
|
||||
|
||||
struct SpotlisT; /* List of intervals with different read qualities */
|
||||
struct CheckmediajoB; /* Parameters for Xorriso_check_media() */
|
||||
|
||||
int Xorriso_check_media_setup_job(struct XorrisO *xorriso,
|
||||
struct CheckmediajoB *job,
|
||||
char **argv, int old_idx, int end_idx, int flag);
|
||||
|
||||
int Xorriso_sectormap_to_spotlist(struct XorrisO *xorriso,
|
||||
struct CheckmediajoB *job,
|
||||
struct SpotlisT **spotlist,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= mark untested areas as valid
|
||||
*/
|
||||
int Xorriso_spotlist_to_sectormap(struct XorrisO *xorriso,
|
||||
struct SpotlisT *spotlist,
|
||||
int read_chunk,
|
||||
struct SectorbitmaP **map,
|
||||
int flag);
|
||||
|
||||
/* Opens the -check_media data copy in for reading and writing
|
||||
*/
|
||||
int Xorriso_open_job_data_to(struct XorrisO *xorriso,
|
||||
struct CheckmediajoB *job, int flag);
|
||||
|
||||
/* @param report Buffer of at least 10*SfileadrL
|
||||
@param flag bit0= only report non-default settings
|
||||
@return <=0 error , 1 ok , 2 with bit0: every option is on default setting
|
||||
*/
|
||||
int Xorriso_check_media_list_job(struct XorrisO *xorriso,
|
||||
struct CheckmediajoB *job,
|
||||
char *report, int flag);
|
||||
|
||||
int Xorriso_update_in_sector_map(struct XorrisO *xorriso,
|
||||
struct SpotlisT *spotlist, int read_chunk,
|
||||
struct CheckmediajoB *job, int flag);
|
||||
|
||||
|
||||
/* Distiniction between valid and invalid sectors */
|
||||
struct SectorbitmaP {
|
||||
int sectors;
|
||||
int sector_size;
|
||||
unsigned char *map;
|
||||
int map_size;
|
||||
};
|
||||
|
||||
int Spotlist_new(struct SpotlisT **o, int flag);
|
||||
|
||||
int Spotlist_destroy(struct SpotlisT **o, int flag);
|
||||
|
||||
int Spotlist_add_item(struct SpotlisT *o, int start_lba, int blocks,
|
||||
int quality, int flag);
|
||||
|
||||
int Spotlist_count(struct SpotlisT *o, int flag);
|
||||
|
||||
int Spotlist_block_count(struct SpotlisT *o, int flag);
|
||||
|
||||
int Spotlist_sector_size(struct SpotlisT *o, int read_chunk, int flag);
|
||||
|
||||
int Spotlist_get_item(struct SpotlisT *o, int idx,
|
||||
int *start_lba, int *blocks, int *quality, int flag);
|
||||
|
||||
char *Spotlist__quality_name(int quality, char name[80], int bad_limit,
|
||||
int flag);
|
||||
|
||||
|
||||
#define Xorriso_read_quality_gooD 0x7fffffff
|
||||
#define Xorriso_read_quality_md5_matcH 0x70000000
|
||||
#define Xorriso_read_quality_sloW 0x60000000
|
||||
#define Xorriso_read_quality_partiaL 0x50000000
|
||||
#define Xorriso_read_quality_valiD 0x40000000
|
||||
#define Xorriso_read_quality_untesteD 0x3fffffff
|
||||
#define Xorriso_read_quality_invaliD 0x3ffffffe
|
||||
#define Xorriso_read_quality_tao_enD 0x28000000
|
||||
#define Xorriso_read_quality_off_tracK 0x20000000
|
||||
#define Xorriso_read_quality_md5_mismatcH 0x10000000
|
||||
#define Xorriso_read_quality_unreadablE 0x00000000
|
||||
|
||||
|
||||
struct CheckmediajoB {
|
||||
int use_dev; /* 0= use indev , 1= use outdev , 2= use sector map*/
|
||||
|
||||
int min_lba; /* if >=0 : begin checking at this address */
|
||||
int max_lba; /* if >=0 : read up to this address, else use mode */
|
||||
|
||||
int min_block_size; /* granularity desired by user
|
||||
*/
|
||||
int mode; /* 0= track by track
|
||||
1= single sweep over libisoburn media capacity
|
||||
>>> 2= single sweep over libburn media capacity
|
||||
*/
|
||||
time_t start_time;
|
||||
int time_limit; /* Number of seconds after which to abort */
|
||||
|
||||
int item_limit; /* Maximum number of media check list items as result */
|
||||
|
||||
char abort_file_path[SfileadrL];
|
||||
|
||||
char data_to_path[SfileadrL];
|
||||
int data_to_fd;
|
||||
off_t data_to_offset; /* usually 0 with image copy, negative with file copy */
|
||||
off_t data_to_limit; /* used with file copy */
|
||||
int patch_lba0;
|
||||
int patch_lba0_msc1;
|
||||
|
||||
char sector_map_path[SfileadrL];
|
||||
struct SectorbitmaP *sector_map;
|
||||
int map_with_volid; /* 0=add quick toc to map file,
|
||||
1=read ISO heads for toc
|
||||
*/
|
||||
|
||||
int retry; /* -1= only try full read_chunk, 1=retry with 2k blocks
|
||||
0= retry with CD, full chunk else
|
||||
*/
|
||||
|
||||
int report_mode; /* 0= print MCL items
|
||||
1= print damaged files
|
||||
*/
|
||||
|
||||
char event_severity[20]; /* If not "ALL": trigger event of given severity
|
||||
at the end of a check job if bad blocks were
|
||||
discovered.
|
||||
*/
|
||||
|
||||
double slow_threshold_seq; /* Time limit in seconds for the decision whether
|
||||
a read operation is considered slow. This does
|
||||
not apply to thr first read of an interval.
|
||||
*/
|
||||
|
||||
int untested_valid; /* 1= mark untested data blocks as valid when calling
|
||||
Xorriso_spotlist_to_sectormap()
|
||||
*/
|
||||
};
|
||||
|
||||
int Checkmediajob_new(struct CheckmediajoB **o, int flag);
|
||||
|
||||
int Checkmediajob_destroy(struct CheckmediajoB **o, int flag);
|
||||
|
||||
int Checkmediajob_copy(struct CheckmediajoB *from, struct CheckmediajoB *to,
|
||||
int flag);
|
||||
|
||||
int Sectorbitmap_new(struct SectorbitmaP **o, int sectors, int sector_size,
|
||||
int flag);
|
||||
int Sectorbitmap_destroy(struct SectorbitmaP **o, int flag);
|
||||
int Sectorbitmap_from_file(struct SectorbitmaP **o, char *path, char *msg,
|
||||
int *os_errno, int flag);
|
||||
int Sectorbitmap_to_file(struct SectorbitmaP *o, char *path, char *info,
|
||||
char *msg, int *os_errno, int flag);
|
||||
int Sectorbitmap_set(struct SectorbitmaP *o, int sector, int flag);
|
||||
int Sectorbitmap_set_range(struct SectorbitmaP *o,
|
||||
int start_sector, int sectors, int flag);
|
||||
int Sectorbitmap_is_set(struct SectorbitmaP *o, int sector, int flag);
|
||||
int Sectorbitmap_bytes_are_set(struct SectorbitmaP *o,
|
||||
off_t start_byte, off_t end_byte, int flag);
|
||||
|
||||
int Sectorbitmap_get_layout(struct SectorbitmaP *o,
|
||||
int *sectors, int *sector_size, int flag);
|
||||
|
||||
int Sectorbitmap_copy(struct SectorbitmaP *from, struct SectorbitmaP *to,
|
||||
int flag);
|
||||
|
||||
int Sectorbitmap_clone(struct SectorbitmaP *from, struct SectorbitmaP **clone,
|
||||
int flag);
|
||||
|
||||
#endif /* ! Xorriso_pvt_check_includeD */
|
||||
|
947
xorriso/cmp_update.c
Normal file
947
xorriso/cmp_update.c
Normal file
@ -0,0 +1,947 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains the implementation of actions which compare or update
|
||||
files between disk filesystem and ISO filesystem.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#include <pwd.h>
|
||||
#include <grp.h>
|
||||
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
|
||||
/*
|
||||
@param result Bitfield indicationg type of mismatch
|
||||
bit11= cannot open regular disk file
|
||||
bit12= cannot open iso file
|
||||
bit13= early eof of disk file
|
||||
bit14= early eof of iso file
|
||||
bit15= content bytes differ
|
||||
@param flag bit0= mtimes of both file objects are equal
|
||||
bit29= do not issue pacifier messages
|
||||
bit31= do not issue result messages
|
||||
@return >0 ok , <=0 error
|
||||
*/
|
||||
int Xorriso_compare_2_contents(struct XorrisO *xorriso, char *common_adr,
|
||||
char *disk_adr, off_t disk_size,
|
||||
off_t offset, off_t bytes,
|
||||
char *iso_adr, off_t iso_size,
|
||||
int *result, int flag)
|
||||
{
|
||||
int fd1= -1, ret, r1, r2, done, wanted, i, was_error= 0, use_md5= 0;
|
||||
void *stream2= NULL;
|
||||
off_t r1count= 0, r2count= 0, diffcount= 0, first_diff= -1;
|
||||
char *respt, buf1[32*1024], buf2[32*1024], offset_text[80];
|
||||
char disk_md5[16], iso_md5[16];
|
||||
void *ctx= NULL;
|
||||
|
||||
respt= xorriso->result_line;
|
||||
|
||||
fd1= open(disk_adr, O_RDONLY);
|
||||
if(fd1==-1) {
|
||||
sprintf(respt, "- %s (DISK) : cannot open() : %s\n",
|
||||
disk_adr, strerror(errno));
|
||||
cannot_address:;
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 2048;
|
||||
{ret= 0; goto ex;}
|
||||
}
|
||||
if(offset>0)
|
||||
if(lseek(fd1, offset, SEEK_SET)==-1) {
|
||||
sprintf(respt, "- %s (DISK) : cannot lseek(%.f) : %s\n",
|
||||
disk_adr, (double) offset, strerror(errno));
|
||||
close(fd1);
|
||||
goto cannot_address;
|
||||
}
|
||||
|
||||
if(xorriso->do_md5 & 16) {
|
||||
use_md5= 1;
|
||||
ret= Xorriso_is_plain_image_file(xorriso, NULL, iso_adr, 0);
|
||||
if(ret <= 0)
|
||||
ret= 0; /* (reverse) filtered files are likely not to match their MD5 */
|
||||
else
|
||||
ret= Xorriso_get_md5(xorriso, NULL, iso_adr, iso_md5, 1);
|
||||
if(ret <= 0)
|
||||
use_md5= 0;
|
||||
else {
|
||||
ret= Xorriso_md5_start(xorriso, &ctx, 0);
|
||||
if(ret <= 0)
|
||||
use_md5= 0;
|
||||
}
|
||||
}
|
||||
if (! use_md5) {
|
||||
ret= Xorriso_iso_file_open(xorriso, iso_adr, NULL, &stream2, 0);
|
||||
if(ret<=0) {
|
||||
sprintf(respt, "- %s (ISO) : cannot open() file in ISO image\n",iso_adr);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
close(fd1);
|
||||
(*result)|= 4096;
|
||||
{ret= 0; goto ex;}
|
||||
}
|
||||
}
|
||||
|
||||
done= 0;
|
||||
while(!done) {
|
||||
|
||||
wanted= sizeof(buf1);
|
||||
if(r1count+offset+wanted>disk_size)
|
||||
wanted= disk_size-r1count-offset;
|
||||
if(r1count+wanted>bytes)
|
||||
wanted= bytes-r1count;
|
||||
r1= 0;
|
||||
while(wanted>0) {
|
||||
ret= read(fd1, buf1, wanted);
|
||||
if(ret<=0)
|
||||
break;
|
||||
wanted-= ret;
|
||||
r1+= ret;
|
||||
}
|
||||
|
||||
wanted= sizeof(buf2);
|
||||
if(r2count+wanted>iso_size)
|
||||
wanted= iso_size-r2count;
|
||||
/*
|
||||
if(r2count+wanted>bytes)
|
||||
wanted= bytes-r2count;
|
||||
*/
|
||||
if(use_md5)
|
||||
r2= r1;
|
||||
else if(wanted>0)
|
||||
r2= Xorriso_iso_file_read(xorriso, stream2, buf2, wanted, 0);
|
||||
else
|
||||
r2= 0;
|
||||
|
||||
if(r1<0 || r2<0)
|
||||
was_error= 1;
|
||||
|
||||
if(r1<=0 && r2<=0)
|
||||
break;
|
||||
if(r1<=0) {
|
||||
if(r1<0)
|
||||
r1= 0;
|
||||
if(disk_size > r1count + r1 + offset) {
|
||||
sprintf(respt, "- %s (DISK) : early EOF after %.f bytes\n",
|
||||
disk_adr, (double) r1count);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 8196;
|
||||
}
|
||||
(*result)|= (1<<15);
|
||||
}
|
||||
r1count+= r1;
|
||||
if(r2<=0 || r2<r1) {
|
||||
if(r2<0)
|
||||
r2= 0;
|
||||
if(iso_size > r2count + r2) {
|
||||
sprintf(respt, "- %s (ISO) : early EOF after %.f bytes\n",
|
||||
iso_adr, (double) r2count);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= (1<<14);
|
||||
}
|
||||
(*result)|= (1<<15);
|
||||
done= 1;
|
||||
}
|
||||
if(r2>r1) {
|
||||
if(disk_size > r1count + r1 + offset) {
|
||||
sprintf(respt, "- %s (DISK) : early EOF after %.f bytes\n",
|
||||
disk_adr, (double) r1count);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 8196;
|
||||
}
|
||||
(*result)|= (1<<15);
|
||||
done= 1;
|
||||
}
|
||||
r2count+= r2;
|
||||
if(r1>r2)
|
||||
r1= r2;
|
||||
|
||||
if(use_md5) {
|
||||
Xorriso_md5_compute(xorriso, ctx, buf1, r1, 0);
|
||||
} else {
|
||||
for(i= 0; i<r1; i++) {
|
||||
if(buf1[i]!=buf2[i]) {
|
||||
if(first_diff<0)
|
||||
first_diff= r1count - r1 + i;
|
||||
diffcount++;
|
||||
}
|
||||
}
|
||||
}
|
||||
if(!(flag&(1<<29))) {
|
||||
xorriso->pacifier_count+= r1;
|
||||
xorriso->pacifier_byte_count+= r1;
|
||||
if(flag&(1<<31))
|
||||
Xorriso_pacifier_callback(xorriso, "content bytes read",
|
||||
xorriso->pacifier_count, 0, "", 0);
|
||||
else
|
||||
Xorriso_pacifier_callback(xorriso, "bytes", xorriso->pacifier_count, 0,
|
||||
"", 1<<6);
|
||||
}
|
||||
}
|
||||
|
||||
if(use_md5) {
|
||||
ret= Xorriso_md5_end(xorriso, &ctx, disk_md5, 0);
|
||||
if(ret <= 0) {
|
||||
*result |= (1 << 15);
|
||||
ret= -1; goto ex;
|
||||
}
|
||||
for(i= 0; i < 16; i++)
|
||||
if(iso_md5[i] != disk_md5[i])
|
||||
break;
|
||||
if(i < 16 ) {
|
||||
offset_text[0]= 0;
|
||||
if(offset>0)
|
||||
sprintf(offset_text, "%.f+", (double) offset);
|
||||
sprintf(respt, "%s %s : differs by MD5 sums.\n",
|
||||
common_adr, (flag&1 ? "CONTENT": "content"));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= (1<<15);
|
||||
}
|
||||
} else if(diffcount>0 || r1count!=r2count) {
|
||||
if(first_diff<0)
|
||||
first_diff= (r1count>r2count ? r2count : r1count);
|
||||
offset_text[0]= 0;
|
||||
if(offset>0)
|
||||
sprintf(offset_text, "%.f+", (double) offset);
|
||||
sprintf(respt, "%s %s : differs by at least %.f bytes. First at %s%.f\n",
|
||||
common_adr, (flag&1 ? "CONTENT": "content"),
|
||||
(double) (diffcount + abs(r1count-r2count)),
|
||||
offset_text, (double) first_diff);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= (1<<15);
|
||||
}
|
||||
if(fd1!=-1)
|
||||
close(fd1);
|
||||
if(! use_md5)
|
||||
Xorriso_iso_file_close(xorriso, &stream2, 0);
|
||||
if(was_error)
|
||||
{ret= -1; goto ex;}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(ctx != NULL)
|
||||
Xorriso_md5_end(xorriso, &ctx, disk_md5, 0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param result Bitfield indicationg type of mismatch
|
||||
bit0= disk_adr not existing
|
||||
bit1= iso_adr not existing
|
||||
bit2= access permissions
|
||||
bit3= file type
|
||||
bit4= user id
|
||||
bit5= group id
|
||||
bit6= minor, major with device file
|
||||
bit7= size
|
||||
bit8= mtime
|
||||
bit9= atime
|
||||
bit10= ctime
|
||||
bit11= cannot open regular disk file
|
||||
bit12= cannot open iso file
|
||||
bit13= early eof of disk file
|
||||
bit14= early eof of iso file
|
||||
bit15= content bytes differ
|
||||
bit16= symbolic link on disk pointing to dir, dir in iso
|
||||
bit17= file chunks detected and compared
|
||||
bit18= incomplete chunk collection encountered
|
||||
bit19= ACL differs (this condition sets also bit2)
|
||||
bit20= xattr differ
|
||||
bit21= mismatch of recorded dev,inode
|
||||
bit22= no recorded dev,inode found in node
|
||||
bit23= timestamps younger than xorriso->isofs_st_in
|
||||
bit24= hardlink split
|
||||
bit25= hardlink fusion
|
||||
@param flag bit0= compare atime
|
||||
bit1= compare ctime
|
||||
bit2= check only existence of both file objects
|
||||
count one or both missing as "difference"
|
||||
bit27= for Xorriso_path_is_excluded(): bit0
|
||||
bit28= examine eventual disk_path link target rather than link
|
||||
bit29= do not issue pacifier messages
|
||||
bit30= omit adr_common_tail in report messages
|
||||
bit31= do not issue result messages
|
||||
@return 1=files match properly , 0=difference detected , -1=error
|
||||
*/
|
||||
int Xorriso_compare_2_files(struct XorrisO *xorriso, char *disk_adr,
|
||||
char *iso_adr, char *adr_common_tail,
|
||||
int *result, int flag)
|
||||
{
|
||||
struct stat s1, s2, stbuf;
|
||||
int ret, missing= 0, is_split= 0, i, was_error= 0, diff_count= 0;
|
||||
int content_shortcut= 0;
|
||||
char *respt;
|
||||
char a[5*SfileadrL], sfe[5*SfileadrL];
|
||||
char ttx1[40], ttx2[40];
|
||||
char *a1_acl= NULL, *a2_acl= NULL, *d1_acl= NULL, *d2_acl= NULL;
|
||||
char *attrlist1= NULL, *attrlist2= NULL;
|
||||
struct SplitparT *split_parts= NULL;
|
||||
int split_count= 0;
|
||||
time_t stamp;
|
||||
|
||||
char part_path[SfileadrL], *part_name;
|
||||
int partno, total_parts= 0;
|
||||
off_t offset, bytes, total_bytes;
|
||||
|
||||
*result= 0;
|
||||
respt= xorriso->result_line;
|
||||
|
||||
if(!(xorriso->disk_excl_mode&8)) {
|
||||
ret= Xorriso_path_is_excluded(xorriso, disk_adr, 2 | !!(flag&(1<<27)));
|
||||
if(ret>0) {
|
||||
sprintf(respt , "? %s (DISK) : exluded by %s\n",
|
||||
Text_shellsafe(disk_adr, sfe, 0),
|
||||
(ret==1 ? "-not_paths" : "-not_leaf"));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
missing= 1;
|
||||
(*result)|= 1;
|
||||
}
|
||||
}
|
||||
if(!missing) {
|
||||
if(flag&(1<<28))
|
||||
ret= stat(disk_adr, &s1);
|
||||
else
|
||||
ret= lstat(disk_adr, &s1);
|
||||
if(ret==-1) {
|
||||
sprintf(respt , "? %s (DISK) : cannot lstat() : %s\n",
|
||||
Text_shellsafe(disk_adr, sfe, 0), strerror(errno));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
missing= 1;
|
||||
(*result)|= 1;
|
||||
}
|
||||
}
|
||||
if(missing)
|
||||
strcpy(a, "?");
|
||||
else
|
||||
strcpy(a, Ftypetxt(s1.st_mode, 1));
|
||||
strcat(a, " ");
|
||||
if(adr_common_tail[0])
|
||||
strcat(a, Text_shellsafe(adr_common_tail, sfe, 0));
|
||||
else {
|
||||
Text_shellsafe(disk_adr, a+strlen(a), 0);
|
||||
strcat(a, " (DISK)");
|
||||
/*
|
||||
strcat(a, "'.'");
|
||||
*/
|
||||
}
|
||||
strcat(a, " :");
|
||||
if(flag&(1<<30))
|
||||
a[0]= 0;
|
||||
|
||||
ret= Xorriso_iso_lstat(xorriso, iso_adr, &s2, 0);
|
||||
if(ret<0) {
|
||||
sprintf(respt, "? %s (ISO) : cannot find this file in ISO image\n",
|
||||
Text_shellsafe(iso_adr, sfe, 0));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
missing= 1;
|
||||
(*result)|= 2;
|
||||
}
|
||||
|
||||
if((flag&4)||missing)
|
||||
{ret= !missing; goto ex;}
|
||||
|
||||
|
||||
/* Splitfile parts */
|
||||
if((S_ISREG(s1.st_mode) || S_ISBLK(s1.st_mode)) && S_ISDIR(s2.st_mode)) {
|
||||
is_split= Xorriso_identify_split(xorriso, iso_adr, NULL, &split_parts,
|
||||
&split_count, &s2, 0);
|
||||
if(is_split>0)
|
||||
(*result)|= (1<<17);
|
||||
else
|
||||
is_split= 0;
|
||||
}
|
||||
|
||||
/* Attributes */
|
||||
if(s1.st_mode != s2.st_mode) {
|
||||
if((s1.st_mode&~S_IFMT)!=(s2.st_mode&~S_IFMT)) {
|
||||
sprintf(respt, "%s st_mode : %7.7o <> %7.7o\n",
|
||||
a, (unsigned int) (s1.st_mode & ~S_IFMT),
|
||||
(unsigned int) (s2.st_mode & ~S_IFMT));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 4;
|
||||
}
|
||||
|
||||
if((s1.st_mode&S_IFMT)!=(s2.st_mode&S_IFMT)) {
|
||||
sprintf(respt, "%s type : %s <> %s\n",
|
||||
a, Ftypetxt(s1.st_mode, 0), Ftypetxt(s2.st_mode, 0));
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 8;
|
||||
if((s1.st_mode&S_IFMT) == S_IFLNK) {
|
||||
/* check whether link target type matches */
|
||||
ret= stat(disk_adr, &stbuf);
|
||||
if(ret!=-1)
|
||||
if(S_ISDIR(stbuf.st_mode) && S_ISDIR(s2.st_mode))
|
||||
(*result)|= (1<<16);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* ACL */
|
||||
if(xorriso->do_aaip & 3) {
|
||||
Xorriso_local_getfacl(xorriso, disk_adr, &a1_acl,
|
||||
16 | ((flag & (1 << 28)) >> 23));
|
||||
if(S_ISDIR(s1.st_mode))
|
||||
Xorriso_local_getfacl(xorriso, disk_adr, &d1_acl, 1);
|
||||
ret= Xorriso_getfacl(xorriso, NULL, iso_adr, &a2_acl, 1 | 4 | 16);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(S_ISDIR(s1.st_mode)) {
|
||||
ret= Xorriso_getfacl(xorriso, NULL, iso_adr, &d2_acl, 1 | 8);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
}
|
||||
ret= Compare_text_lines(a1_acl, a2_acl, &diff_count, 0);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(ret == 0)
|
||||
(*result)|= 4 | (1 << 19);
|
||||
ret= Compare_text_lines(d1_acl, d2_acl, &diff_count, 1);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(ret == 0)
|
||||
(*result)|= 4 | (1 << 19);
|
||||
if((*result) & (1 << 19)) {
|
||||
sprintf(respt, "%s ACL : %d difference%s\n",
|
||||
a, diff_count, diff_count == 1 ? "" : "s");
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
}
|
||||
|
||||
/* xattr */
|
||||
if(xorriso->do_aaip & 12) {
|
||||
ret= Xorriso_getfattr(xorriso, NULL, disk_adr, &attrlist1,
|
||||
1 | 2 | ((flag & (1 << 28)) >> 23));
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
ret= Xorriso_getfattr(xorriso, NULL, iso_adr, &attrlist2, 1);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
ret= Compare_text_lines(attrlist1, attrlist2, &diff_count, 0);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(ret == 0) {
|
||||
(*result)|= (1 << 20);
|
||||
sprintf(respt, "%s xattr : %d difference%s\n",
|
||||
a, diff_count, diff_count == 1 ? "" : "s");
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
}
|
||||
|
||||
if(s1.st_uid != s2.st_uid) {
|
||||
sprintf(respt, "%s st_uid : %lu <> %lu\n", a,
|
||||
(unsigned long) s1.st_uid, (unsigned long) s2.st_uid);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 16;
|
||||
}
|
||||
if(s1.st_gid != s2.st_gid) {
|
||||
sprintf(respt, "%s st_gid : %lu <> %lu\n", a,
|
||||
(unsigned long) s1.st_gid, (unsigned long) s2.st_gid);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 32;
|
||||
}
|
||||
if((S_ISCHR(s1.st_mode) && S_ISCHR(s2.st_mode)) ||
|
||||
(S_ISBLK(s1.st_mode) && S_ISBLK(s2.st_mode))) {
|
||||
if(s1.st_rdev != s2.st_rdev) {
|
||||
sprintf(respt, "%s %s st_rdev : %lu <> %lu\n", a,
|
||||
(S_ISCHR(s1.st_mode) ? "S_IFCHR" : "S_IFBLK"),
|
||||
(unsigned long) s1.st_rdev, (unsigned long) s1.st_rdev);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 64;
|
||||
}
|
||||
}
|
||||
if((!(xorriso->do_aaip & 32)) &&
|
||||
S_ISREG(s2.st_mode) && s1.st_size != s2.st_size) {
|
||||
sprintf(respt, "%s st_size : %.f <> %.f diff= %.f\n",
|
||||
a, (double) s1.st_size, (double) s2.st_size,
|
||||
((double) s1.st_size) - (double) s2.st_size);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 128;
|
||||
}
|
||||
if(s1.st_mtime != s2.st_mtime) {
|
||||
sprintf(respt, "%s st_mtime : %s <> %s diff= %.f s\n",
|
||||
a, Ftimetxt(s1.st_mtime, ttx1, 0),
|
||||
Ftimetxt(s2.st_mtime, ttx2, 0),
|
||||
((double) s1.st_mtime) - (double) s2.st_mtime);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 256;
|
||||
}
|
||||
if(flag&1) {
|
||||
if(s1.st_atime != s2.st_atime) {
|
||||
sprintf(respt, "%s st_atime : %s <> %s diff= %.f s\n",
|
||||
a, Ftimetxt(s1.st_atime, ttx1, 0),
|
||||
Ftimetxt(s2.st_atime, ttx2, 0),
|
||||
((double) s1.st_atime) - (double) s2.st_atime);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 512;
|
||||
}
|
||||
}
|
||||
if(flag&2) {
|
||||
if(s1.st_ctime != s2.st_ctime) {
|
||||
sprintf(respt, "%s st_ctime : %s <> %s diff= %.f s\n",
|
||||
a, Ftimetxt(s1.st_ctime, ttx1, 0),
|
||||
Ftimetxt(s2.st_ctime, ttx2, 0),
|
||||
((double) s1.st_ctime) - (double) s2.st_ctime);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= 1024;
|
||||
}
|
||||
}
|
||||
if(xorriso->isofs_st_in > 0 &&
|
||||
(xorriso->isofs_st_in <= s2.st_mtime ||
|
||||
((flag & 1) && xorriso->isofs_st_in <= s2.st_atime) ||
|
||||
((flag & 2) && xorriso->isofs_st_in <= s2.st_ctime)))
|
||||
(*result)|= 1 << 23;
|
||||
|
||||
if((xorriso->do_aaip & 32) || !(xorriso->ino_behavior & 2)) {
|
||||
/* dev,inode comparison.
|
||||
For skipping content comparison or for hardlink detection.
|
||||
*/
|
||||
ret= Xorriso_record_dev_inode(xorriso, "", s1.st_dev, s1.st_ino, NULL,
|
||||
iso_adr, 1 | 2 | ((flag & (1 << 28)) >> 23) | (xorriso->do_aaip & 128));
|
||||
if(ret < 0) {
|
||||
ret= -1; goto ex;
|
||||
} else if(ret == 0) { /* match */
|
||||
if((xorriso->do_aaip & 64) && S_ISREG(s1.st_mode) && S_ISREG(s2.st_mode)){
|
||||
if(xorriso->do_aaip & 32)
|
||||
content_shortcut= 1;
|
||||
if((*result) & (8 | 128 | 256 | 512 | 1024 | (1 << 23))) {
|
||||
(*result)|= (1 << 15); /* content bytes differ */
|
||||
if(((*result) & (1 << 23)) &&
|
||||
!((*result) & (8 | 128 | 256 | 512 | 1024))) {
|
||||
sprintf(respt,
|
||||
"%s content : node timestamp younger than image timestamp\n", a);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
stamp= s2.st_mtime;
|
||||
if((flag & 1) && s2.st_atime >= stamp)
|
||||
stamp= s2.st_atime;
|
||||
if((flag & 2) && s2.st_ctime >= stamp)
|
||||
stamp= s2.st_ctime;
|
||||
sprintf(respt, "%s content : %s > %s diff= %.f s\n",
|
||||
a, Ftimetxt(stamp, ttx1, 3 << 1),
|
||||
Ftimetxt(xorriso->isofs_st_in, ttx2, 3 << 1),
|
||||
((double) stamp) - (double) xorriso->isofs_st_in);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
sprintf(respt,
|
||||
"%s content : assuming inequality due to size or timestamps\n", a);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
}
|
||||
} else if(ret == 1) { /* mismatch */
|
||||
(*result)|= (1 << 21);
|
||||
sprintf(respt, "%s dev_ino : differing\n", a);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
|
||||
if((xorriso->do_aaip & 64) && S_ISREG(s1.st_mode) && S_ISREG(s2.st_mode)){
|
||||
if(xorriso->do_aaip & 32)
|
||||
content_shortcut= 1;
|
||||
(*result)|= (1 << 15); /* content bytes differ */
|
||||
sprintf(respt,
|
||||
"%s content : assuming inequality after dev_ino mismatch\n", a);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
} else {
|
||||
sprintf(respt, "%s dev_ino : no dev_ino stored with image node\n", a);
|
||||
if((xorriso->do_aaip & 32) && !(flag&(1<<31)))
|
||||
Xorriso_result(xorriso,0);
|
||||
(*result)|= (1 << 22);
|
||||
}
|
||||
}
|
||||
|
||||
if(S_ISREG(s1.st_mode) && S_ISREG(s2.st_mode) && !content_shortcut) {
|
||||
/* Content */
|
||||
if(is_split) {
|
||||
for(i= 0; i<split_count; i++) {
|
||||
Splitparts_get(split_parts, i, &part_name, &partno, &total_parts,
|
||||
&offset, &bytes, &total_bytes, 0);
|
||||
strcpy(part_path, iso_adr);
|
||||
if(Sfile_add_to_path(part_path, part_name, 0)<=0) {
|
||||
Xorriso_much_too_long(xorriso, strlen(iso_adr)+strlen(part_name)+1,
|
||||
2);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
ret= Xorriso_iso_lstat(xorriso, part_path, &stbuf, 0);
|
||||
if(ret<0)
|
||||
continue;
|
||||
ret= Xorriso_compare_2_contents(xorriso, a, disk_adr, s1.st_size,
|
||||
offset, bytes,
|
||||
part_path, stbuf.st_size, result,
|
||||
(s1.st_mtime==s2.st_mtime) | (flag&((1<<29)|(1<<31))));
|
||||
if(ret<0)
|
||||
was_error= 1;
|
||||
}
|
||||
if(total_parts>0 && split_count!=total_parts) {
|
||||
sprintf(xorriso->info_text,
|
||||
"- %s/* (ISO) : Not all split parts present (%d of %d)\n",
|
||||
iso_adr, split_count, total_parts);
|
||||
if(!(flag&(1<<31)))
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "NOTE", 1);
|
||||
(*result)|= 1<<18;
|
||||
}
|
||||
} else {
|
||||
ret= Xorriso_compare_2_contents(xorriso, a, disk_adr, s1.st_size,
|
||||
(off_t) 0, s1.st_size,
|
||||
iso_adr, s2.st_size, result,
|
||||
(s1.st_mtime==s2.st_mtime) | (flag&((1<<29)|(1<<31))));
|
||||
if(ret<0)
|
||||
was_error= 1;
|
||||
}
|
||||
|
||||
}
|
||||
if(was_error)
|
||||
ret= -1;
|
||||
else
|
||||
ret= (((*result) & ~((1 << 17) | (1 << 18) | (1 << 23)))==0);
|
||||
ex:;
|
||||
if(split_parts!=NULL)
|
||||
Splitparts_destroy(&split_parts, split_count, 0);
|
||||
Xorriso_local_getfacl(xorriso, disk_adr, &a1_acl, 1 << 15);
|
||||
Xorriso_local_getfacl(xorriso, disk_adr, &d1_acl, 1 << 15);
|
||||
if(a2_acl != NULL)
|
||||
free(a2_acl);
|
||||
if(d2_acl != NULL)
|
||||
free(d2_acl);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_pfx_disk_path(struct XorrisO *xorriso, char *iso_path,
|
||||
char *iso_prefix, char *disk_prefix,
|
||||
char disk_path[SfileadrL], int flag)
|
||||
{
|
||||
int ret;
|
||||
char adrc[SfileadrL];
|
||||
|
||||
if(strncmp(iso_path, iso_prefix, strlen(iso_prefix))!=0)
|
||||
return(-1);
|
||||
if(strlen(disk_prefix) + strlen(iso_path) - strlen(iso_prefix)+1 >= SfileadrL)
|
||||
return(-1);
|
||||
if(iso_path[strlen(iso_prefix)] == '/')
|
||||
strcpy(adrc, iso_path + strlen(iso_prefix) + 1);
|
||||
else
|
||||
strcpy(adrc, iso_path + strlen(iso_prefix));
|
||||
ret= Xorriso_make_abs_adr(xorriso, disk_prefix, adrc, disk_path, 4 | 8);
|
||||
if(ret <= 0)
|
||||
return(ret);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
@param flag bit0= update rather than compare
|
||||
bit1= find[ix] is in recursion
|
||||
@return <=0 error, 1= ok , 2= iso_path was deleted
|
||||
3=ok, do not dive into directory (e.g. because it is a split file)
|
||||
*/
|
||||
int Xorriso_find_compare(struct XorrisO *xorriso, void *boss_iter,
|
||||
char *iso_path, char *iso_prefix, char *disk_prefix,
|
||||
int flag)
|
||||
{
|
||||
int ret, result, uret, follow_links, deleted= 0;
|
||||
char disk_path[SfileadrL];
|
||||
|
||||
ret= Xorriso_pfx_disk_path(xorriso, iso_path, iso_prefix, disk_prefix,
|
||||
disk_path, 0);
|
||||
if(ret <= 0)
|
||||
return(ret);
|
||||
|
||||
/* compare exclusions against disk_path resp. leaf name */
|
||||
if(xorriso->disk_excl_mode&8)
|
||||
ret= Xorriso_path_is_excluded(xorriso, disk_path, !(flag&2));
|
||||
else
|
||||
ret= 0;
|
||||
if(ret<0)
|
||||
return(ret);
|
||||
if(ret>0)
|
||||
return(3);
|
||||
|
||||
follow_links= (xorriso->do_follow_links ||
|
||||
(xorriso->do_follow_param && !(flag&2))) <<28;
|
||||
ret= Xorriso_compare_2_files(xorriso, disk_path, iso_path, "", &result,
|
||||
2 | follow_links | ((!(flag&2))<<27) | ((flag&1)<<31));
|
||||
/* was once: | ((!(flag&1))<<29) */
|
||||
if(ret<xorriso->find_compare_result)
|
||||
xorriso->find_compare_result= ret;
|
||||
if(flag&1) {
|
||||
if(ret<=0) {
|
||||
if(ret<0)
|
||||
if(Xorriso_eval_problem_status(xorriso, ret, 1|2)<0)
|
||||
return(ret);
|
||||
uret= Xorriso_update_interpreter(xorriso, boss_iter, result,
|
||||
disk_path, iso_path, (flag&2)<<1);
|
||||
if(uret<=0)
|
||||
ret= 0;
|
||||
if(uret==2)
|
||||
deleted= 1;
|
||||
}
|
||||
}
|
||||
if(ret<0)
|
||||
return(ret);
|
||||
if(deleted)
|
||||
return(2);
|
||||
if(result&(1<<17))
|
||||
return(3);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
@param flag bit0= widen hardlink sibling:
|
||||
Do not call Xorriso_hardlink_update()
|
||||
Overwrite exactly if normal mode would not,
|
||||
else do nothing
|
||||
bit2= -follow: this is not a command parameter
|
||||
@return <=0 error, 1= ok , 2= iso_rr_path node object has been deleted ,
|
||||
3= no action taken
|
||||
*/
|
||||
int Xorriso_update_interpreter(struct XorrisO *xorriso, void *boss_iter,
|
||||
int compare_result, char *disk_path,
|
||||
char *iso_rr_path, int flag)
|
||||
{
|
||||
int ret, deleted= 0, is_split= 0, i, loop_count, late_hardlink_update= 0;
|
||||
char sfe[5*SfileadrL];
|
||||
struct stat stbuf;
|
||||
struct SplitparT *split_parts= NULL;
|
||||
int split_count= 0;
|
||||
char part_path[SfileadrL], *part_name;
|
||||
int partno, total_parts, new_total_parts;
|
||||
off_t offset, bytes, total_bytes, disk_size, first_bytes;
|
||||
|
||||
if((compare_result&3)==3) {
|
||||
sprintf(xorriso->info_text, "Missing on disk and in ISO: disk_path %s",
|
||||
Text_shellsafe(disk_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "SORRY", 1);
|
||||
xorriso->find_compare_result= -1;
|
||||
ret= 3; goto ex;
|
||||
}
|
||||
|
||||
if(compare_result&((1<<11)|(1<<13))) {
|
||||
if(flag & 1)
|
||||
{ret= 3; goto ex;}
|
||||
/* cannot open regular disk file, early eof of disk file */
|
||||
sprintf(xorriso->info_text, "Problems with reading disk file %s",
|
||||
Text_shellsafe(disk_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 1);
|
||||
xorriso->find_compare_result= -1;
|
||||
ret= 1; goto ex;
|
||||
}
|
||||
xorriso->info_text[0]= 0;
|
||||
is_split= !!(compare_result & (1<<17));
|
||||
|
||||
if((!(xorriso->ino_behavior & 2)) && (compare_result & (2 | (3 << 21))) &&
|
||||
!(flag & 1)) {
|
||||
if(compare_result & 2) {
|
||||
/* File is not yet in image */
|
||||
late_hardlink_update= 1;
|
||||
} else {
|
||||
/* Hard link relation has changed resp. was not recorded. */
|
||||
ret= Xorriso_hardlink_update(xorriso, &compare_result,
|
||||
disk_path, iso_rr_path, flag & 4);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(ret == 2)
|
||||
{ret= 1; goto ex;}
|
||||
}
|
||||
}
|
||||
|
||||
if(compare_result&(8|64)) {
|
||||
/* file type, minor+major with device file */
|
||||
if(flag & 1)
|
||||
{ret= 3; goto ex;}
|
||||
ret= Xorriso_rmi(xorriso, boss_iter, (off_t) 0, iso_rr_path, 1); /* rm_r */
|
||||
if(ret>0) {
|
||||
deleted= 1;
|
||||
ret= Xorriso_graft_in(xorriso, boss_iter, disk_path, iso_rr_path,
|
||||
(off_t) 0, (off_t) 0, 2|(flag&4));
|
||||
}
|
||||
sprintf(xorriso->info_text, "Deleted and re-added ");
|
||||
|
||||
} else if(compare_result&(1)) {
|
||||
delete:;
|
||||
/* disk_adr not existing */
|
||||
ret= Xorriso_rmi(xorriso, boss_iter, (off_t) 0, iso_rr_path, 1);
|
||||
deleted= 1;
|
||||
sprintf(xorriso->info_text, "Deleted ");
|
||||
|
||||
} else if(compare_result&(2|128|(1<<12)|(1<<14)|(1<<15))) {
|
||||
/* iso_adr not existing, size, cannot open iso file, early eof of iso file
|
||||
content bytes differ */
|
||||
|
||||
if(flag & 1)
|
||||
{ret= 3; goto ex;}
|
||||
overwrite:;
|
||||
if(is_split) {
|
||||
ret= Xorriso_identify_split(xorriso, iso_rr_path, NULL,
|
||||
&split_parts, &split_count, &stbuf, 0);
|
||||
if(ret<=0)
|
||||
{ret= -1; goto ex;} /* (should not happen) */
|
||||
ret= lstat(disk_path, &stbuf);
|
||||
if(ret==-1)
|
||||
goto delete;
|
||||
disk_size= stbuf.st_size;
|
||||
Splitparts_get(split_parts, 0, &part_name, &partno, &total_parts,
|
||||
&offset, &first_bytes, &total_bytes, 0);
|
||||
new_total_parts= disk_size/first_bytes;
|
||||
if(disk_size % first_bytes)
|
||||
new_total_parts++;
|
||||
|
||||
loop_count= split_count;
|
||||
/* If disk file grew over part limit and all parts are present:
|
||||
add new parts */
|
||||
if(new_total_parts > total_parts && split_count == total_parts)
|
||||
loop_count= new_total_parts;
|
||||
|
||||
for(i= 0; i<loop_count; i++) {
|
||||
if(i<split_count) {
|
||||
/* Delete old part */
|
||||
Splitparts_get(split_parts, i, &part_name, &partno, &total_parts,
|
||||
&offset, &bytes, &total_bytes, 0);
|
||||
strcpy(part_path, iso_rr_path);
|
||||
if(Sfile_add_to_path(part_path, part_name, 0)<=0) {
|
||||
Xorriso_much_too_long(xorriso,
|
||||
strlen(iso_rr_path)+strlen(part_path)+1, 2);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
ret= Xorriso_rmi(xorriso, NULL, (off_t) 0, part_path, 1);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
deleted= 1;
|
||||
} else {
|
||||
partno= i+1;
|
||||
offset= i*first_bytes;
|
||||
bytes= first_bytes;
|
||||
}
|
||||
if(disk_size<=offset)
|
||||
continue;
|
||||
/* Insert new part */
|
||||
if(strlen(part_path)+160>SfileadrL) {
|
||||
Xorriso_much_too_long(xorriso, strlen(part_path)+160, 2);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
Splitpart__compose(part_path+strlen(iso_rr_path)+1, partno,
|
||||
new_total_parts, offset, first_bytes, disk_size, 0);
|
||||
ret= Xorriso_graft_in(xorriso, boss_iter, disk_path, part_path,
|
||||
offset, bytes, 2|(flag&4)|8|128);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
}
|
||||
/* Copy file attributes to iso_rr_path, augment r-perms by x-perms */
|
||||
ret= Xorriso_copy_properties(xorriso, disk_path, iso_rr_path, 2 | 4);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
} else {
|
||||
ret= Xorriso_graft_in(xorriso, boss_iter, disk_path, iso_rr_path,
|
||||
(off_t) 0, (off_t) 0, 2|(flag&4));
|
||||
if(ret>0 && !(compare_result&2))
|
||||
deleted= 1;
|
||||
}
|
||||
if(late_hardlink_update) {
|
||||
/* Handle eventual hardlink siblings of newly created file */
|
||||
ret= Xorriso_hardlink_update(xorriso, &compare_result,
|
||||
disk_path, iso_rr_path, 1 | (flag & 4));
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
}
|
||||
if(flag & 1)
|
||||
sprintf(xorriso->info_text, "Widened hard link ");
|
||||
else
|
||||
sprintf(xorriso->info_text, "Added/overwrote ");
|
||||
|
||||
} else if(compare_result&(4|16|32|256|512|1024|(1<<19)|(1<<20)|(1<<22))) {
|
||||
/* access permissions, user id, group id, mtime, atime, ctime, ACL, xattr,
|
||||
dev_ino missing */
|
||||
|
||||
if(flag & 1)
|
||||
goto overwrite;
|
||||
|
||||
if(is_split) {
|
||||
ret= Xorriso_identify_split(xorriso, iso_rr_path, NULL,
|
||||
&split_parts, &split_count, &stbuf, 0);
|
||||
if(ret<=0)
|
||||
{ret= -1; goto ex;} /* (should not happen) */
|
||||
for(i= 0; i<split_count; i++) {
|
||||
Splitparts_get(split_parts, i, &part_name, &partno, &total_parts,
|
||||
&offset, &bytes, &total_bytes, 0);
|
||||
strcpy(part_path, iso_rr_path);
|
||||
if(Sfile_add_to_path(part_path, part_name, 0)<=0) {
|
||||
Xorriso_much_too_long(xorriso,
|
||||
strlen(iso_rr_path)+strlen(part_path)+1, 2);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
ret= Xorriso_copy_properties(xorriso, disk_path, part_path,
|
||||
4 * !(compare_result & (1<<21)));
|
||||
/* do not update eventually mismatching dev_ino */
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
}
|
||||
/* Copy file attributes to iso_rr_path, augment r-perms by x-perms */
|
||||
ret= Xorriso_copy_properties(xorriso, disk_path, iso_rr_path, 2 | 4);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
} else
|
||||
ret= Xorriso_copy_properties(xorriso, disk_path, iso_rr_path, 4);
|
||||
sprintf(xorriso->info_text, "Adjusted attributes of ");
|
||||
|
||||
} else if(flag & 1) {
|
||||
goto overwrite;
|
||||
} else
|
||||
ret= 1;
|
||||
if(ret>0 && xorriso->info_text[0]) {
|
||||
strcat(xorriso->info_text, Text_shellsafe(iso_rr_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "UPDATE", 0);
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(split_parts!=NULL)
|
||||
Splitparts_destroy(&split_parts, split_count, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(deleted)
|
||||
return(2);
|
||||
return(ret);
|
||||
}
|
||||
|
40
xorriso/cmp_update.h
Normal file
40
xorriso/cmp_update.h
Normal file
@ -0,0 +1,40 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of class DirseQ which
|
||||
crawls along a directory's content list.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_cmp_includeD
|
||||
#define Xorriso_pvt_cmp_includeD yes
|
||||
|
||||
int Xorriso_compare_2_files(struct XorrisO *xorriso, char *disk_adr,
|
||||
char *iso_adr, char *adr_common_tail,
|
||||
int *result, int flag);
|
||||
|
||||
int Xorriso_pfx_disk_path(struct XorrisO *xorriso, char *iso_path,
|
||||
char *iso_prefix, char *disk_prefix,
|
||||
char disk_path[SfileadrL], int flag);
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
@param flag bit0= update rather than compare
|
||||
*/
|
||||
int Xorriso_find_compare(struct XorrisO *xorriso, void *boss_iter,
|
||||
char *iso_path, char *iso_prefix, char *disk_prefix,
|
||||
int flag);
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
*/
|
||||
int Xorriso_update_interpreter(struct XorrisO *xorriso, void *boss_iter,
|
||||
int compare_result, char *disk_path,
|
||||
char *iso_rr_path, int flag);
|
||||
|
||||
#endif /* ! Xorriso_pvt_cmp_includeD */
|
||||
|
@ -117,9 +117,33 @@ cc -I. -DXorriso_with_maiN $def_libreadline \
|
||||
\
|
||||
-o "$xorr"/xorriso \
|
||||
\
|
||||
"$xorr"/xorriso.c \
|
||||
"$xorr"/xorriso_main.c \
|
||||
"$xorr"/sfile.c \
|
||||
"$xorr"/aux_objects.c \
|
||||
"$xorr"/findjob.c \
|
||||
"$xorr"/check_media.c \
|
||||
"$xorr"/misc_funct.c \
|
||||
"$xorr"/text_io.c \
|
||||
"$xorr"/match.c \
|
||||
"$xorr"/emulators.c \
|
||||
"$xorr"/disk_ops.c \
|
||||
"$xorr"/cmp_update.c \
|
||||
"$xorr"/parse_exec.c \
|
||||
"$xorr"/opts_a_c.c \
|
||||
"$xorr"/opts_d_h.c \
|
||||
"$xorr"/opts_i_o.c \
|
||||
"$xorr"/opts_p_z.c \
|
||||
\
|
||||
"$xorr"/xorrisoburn.c \
|
||||
"$xorr"/base_obj.c \
|
||||
"$xorr"/lib_mgt.c \
|
||||
"$xorr"/sort_cmp.c \
|
||||
"$xorr"/drive_mgt.c \
|
||||
"$xorr"/iso_img.c \
|
||||
"$xorr"/iso_tree.c \
|
||||
"$xorr"/iso_manip.c \
|
||||
"$xorr"/write_run.c \
|
||||
"$xorr"/read_run.c \
|
||||
"$xorr"/filters.c \
|
||||
\
|
||||
"$burn"/async.o \
|
||||
"$burn"/debug.o \
|
||||
|
1838
xorriso/disk_ops.c
Normal file
1838
xorriso/disk_ops.c
Normal file
File diff suppressed because it is too large
Load Diff
116
xorriso/disk_ops.h
Normal file
116
xorriso/disk_ops.h
Normal file
@ -0,0 +1,116 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of class DirseQ which
|
||||
crawls along a directory's content list.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_diskop_includeD
|
||||
#define Xorriso_pvt_diskop_includeD yes
|
||||
|
||||
|
||||
/* @param flag bit0= simple readlink(): no normalization, no multi-hop
|
||||
*/
|
||||
int Xorriso_resolve_link(struct XorrisO *xorriso,
|
||||
char *link_path, char result_path[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_convert_gidstring(struct XorrisO *xorriso, char *gid_string,
|
||||
gid_t *gid, int flag);
|
||||
|
||||
int Xorriso_convert_modstring(struct XorrisO *xorriso, char *cmd, char *mode,
|
||||
mode_t *mode_and, mode_t *mode_or, int flag);
|
||||
|
||||
int Xorriso_convert_uidstring(struct XorrisO *xorriso, char *uid_string,
|
||||
uid_t *uid, int flag);
|
||||
|
||||
/* @param flag bit0= for Xorriso_msgs_submit: use pager
|
||||
*/
|
||||
int Xorriso_hop_link(struct XorrisO *xorriso, char *link_path,
|
||||
struct LinkiteM **link_stack, struct stat *stbuf, int flag);
|
||||
|
||||
int Xorriso__mode_to_perms(mode_t st_mode, char perms[11], int flag);
|
||||
|
||||
int Xorriso_format_ls_l(struct XorrisO *xorriso, struct stat *stbuf, int flag);
|
||||
|
||||
/* @param flag bit0= long format
|
||||
bit1= do not print count of nodes
|
||||
bit2= du format
|
||||
bit3= print directories as themselves (ls -d)
|
||||
*/
|
||||
int Xorriso_lsx_filev(struct XorrisO *xorriso, char *wd,
|
||||
int filec, char **filev, off_t boss_mem, int flag);
|
||||
|
||||
/*
|
||||
@param flag >>> bit0= remove whole sub tree: rm -r
|
||||
bit1= remove empty directory: rmdir
|
||||
bit2= recursion: do not reassure in mode 2 "tree"
|
||||
bit3= this is for overwriting and not for plain removal
|
||||
bit4= count deleted files in xorriso->pacifier_count
|
||||
bit5= with bit0 only remove directory content, not the directory
|
||||
@return <=0 = error
|
||||
1 = removed leaf file object
|
||||
2 = removed directory or tree
|
||||
3 = did not remove on user revocation
|
||||
*/
|
||||
int Xorriso_rmx(struct XorrisO *xorriso, off_t boss_mem, char *path, int flag);
|
||||
|
||||
int Xorriso_findx(struct XorrisO *xorriso, struct FindjoB *job,
|
||||
char *abs_dir_parm, char *dir_path,
|
||||
struct stat *dir_stbuf, int depth,
|
||||
struct LinkiteM *link_stack, int flag);
|
||||
|
||||
/* @param flag bit0= no hardlink reconstruction
|
||||
bit1= do not set xorriso->node_*_prefixes
|
||||
bit5= -extract_single: eventually do not insert directory tree
|
||||
*/
|
||||
int Xorriso_restore_sorted(struct XorrisO *xorriso, int count,
|
||||
char **src_array, char **tgt_array, int flag);
|
||||
|
||||
/* @param flag bit0= path is a directory
|
||||
bit2= recursion: do not reassure in mode 2 "tree"
|
||||
bit3= this is for overwriting and not for plain removal
|
||||
*/
|
||||
int Xorriso_reassure_restore(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
/* @param flag bit7= return 4 if restore fails from denied permission
|
||||
do not issue error message
|
||||
@return <=0 failure , 1 success ,
|
||||
4 with bit7: permission to create file was denied
|
||||
*/
|
||||
int Xorriso_make_tmp_path(struct XorrisO *xorriso, char *orig_path,
|
||||
char *tmp_path, int *fd, int flag);
|
||||
|
||||
/* @param flag bit0= change regardless of xorriso->do_auto_chmod
|
||||
bit1= desired is only rx
|
||||
*/
|
||||
int Xorriso_auto_chmod(struct XorrisO *xorriso, char *disk_path, int flag);
|
||||
|
||||
int Xorriso_make_accessible(struct XorrisO *xorriso, char *disk_path,int flag);
|
||||
|
||||
/* @param flag bit0= prefer to find a match after *img_prefixes
|
||||
(but deliver img_prefixes if no other can be found)
|
||||
*/
|
||||
int Xorriso_make_restore_path(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT **img_prefixes, struct Xorriso_lsT **disk_prefixes,
|
||||
char img_path[SfileadrL], char disk_path[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_restore_make_hl(struct XorrisO *xorriso,
|
||||
char *old_path, char *new_path, int flag);
|
||||
|
||||
int Xorriso_afile_fopen(struct XorrisO *xorriso,
|
||||
char *filename, char *mode, FILE **ret_fp, int flag);
|
||||
|
||||
int Xorriso_make_mount_cmd(struct XorrisO *xorriso, char *cmd,
|
||||
int lba, int track, int session, char *volid,
|
||||
char *devadr, char result[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_append_scdbackup_record(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_diskop_includeD */
|
||||
|
2242
xorriso/drive_mgt.c
Normal file
2242
xorriso/drive_mgt.c
Normal file
File diff suppressed because it is too large
Load Diff
37
xorriso/drive_mgt.h
Normal file
37
xorriso/drive_mgt.h
Normal file
@ -0,0 +1,37 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which operate on drives
|
||||
and media.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_drive_mgt_includeD
|
||||
#define Xorriso_pvt_drive_mgt_includeD yes
|
||||
|
||||
|
||||
int Xorriso_may_burn(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_toc_line(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_media_product(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_check_md5_range(struct XorrisO *xorriso, off_t start_lba,
|
||||
off_t end_lba, char md5[16], int flag);
|
||||
|
||||
int Xorriso_check_interval(struct XorrisO *xorriso, struct SpotlisT *spotlist,
|
||||
struct CheckmediajoB *job,
|
||||
int from_lba, int block_count, int read_chunk,
|
||||
int md5_start, int flag);
|
||||
|
||||
int Xorriso_get_drive_handles(struct XorrisO *xorriso,
|
||||
struct burn_drive_info **dinfo,
|
||||
struct burn_drive **drive,
|
||||
char *attempt, int flag);
|
||||
|
||||
#endif /* ! Xorriso_pvt_drive_mgt_includeD */
|
||||
|
1248
xorriso/emulators.c
Normal file
1248
xorriso/emulators.c
Normal file
File diff suppressed because it is too large
Load Diff
34
xorriso/emulators.h
Normal file
34
xorriso/emulators.h
Normal file
@ -0,0 +1,34 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of emulators for mkisofs and cdrecord.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_emul_includeD
|
||||
#define Xorriso_pvt_emul_includeD yes
|
||||
|
||||
/* micro version of cdrskin */
|
||||
int Xorriso_cdrskin(struct XorrisO *xorriso, char *whom, int argc, char **argv,
|
||||
int flag);
|
||||
|
||||
int Xorriso_cdrskin_help(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_as_cdrskin(struct XorrisO *xorriso, int argc, char **argv,
|
||||
int *idx, int flag);
|
||||
|
||||
/* micro emulation of mkisofs */
|
||||
int Xorriso_genisofs(struct XorrisO *xorriso, char *whom,
|
||||
int argc, char **argv, int flag);
|
||||
|
||||
int Xorriso_genisofs_help(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_as_genisofs(struct XorrisO *xorriso, int argc, char **argv,
|
||||
int *idx, int flag);
|
||||
|
||||
#endif /* ! Xorriso_pvt_emul_includeD */
|
||||
|
694
xorriso/filters.c
Normal file
694
xorriso/filters.c
Normal file
@ -0,0 +1,694 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains functions which operate on data filter objects.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "lib_mgt.h"
|
||||
#include "iso_tree.h"
|
||||
|
||||
/*
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
#include "iso_img.h"
|
||||
#include "iso_manip.h"
|
||||
#include "sort_cmp.h"
|
||||
|
||||
*/
|
||||
|
||||
|
||||
struct Xorriso_extF {
|
||||
|
||||
int flag; /* unused yet */
|
||||
|
||||
IsoExternalFilterCommand *cmd;
|
||||
|
||||
};
|
||||
|
||||
int Xorriso_extf_destroy(struct XorrisO *xorriso, struct Xorriso_extF **filter,
|
||||
int flag);
|
||||
|
||||
|
||||
/* @param flag see struct Xorriso_extF.flag */
|
||||
int Xorriso_extf_new(struct XorrisO *xorriso, struct Xorriso_extF **filter,
|
||||
char *path, int argc, char **argv, int behavior,
|
||||
char *suffix, char *name, int flag)
|
||||
{
|
||||
int i;
|
||||
struct Xorriso_extF *o= NULL;
|
||||
IsoExternalFilterCommand *cmd;
|
||||
|
||||
*filter= o= calloc(sizeof(struct Xorriso_extF), 1);
|
||||
if(o == NULL)
|
||||
goto failure;
|
||||
o->flag= flag;
|
||||
o->cmd= NULL;
|
||||
o->cmd= cmd= calloc(sizeof(IsoExternalFilterCommand), 1);
|
||||
if(cmd == NULL)
|
||||
goto failure;
|
||||
cmd->version= 0;
|
||||
cmd->refcount= 0;
|
||||
cmd->name= NULL;
|
||||
cmd->path= NULL;
|
||||
cmd->argv= NULL;
|
||||
cmd->argc= argc + 1;
|
||||
cmd->behavior= behavior;
|
||||
cmd->suffix= NULL;
|
||||
cmd->suffix= strdup(suffix);
|
||||
if(cmd->suffix == NULL)
|
||||
goto failure;
|
||||
|
||||
cmd->path= strdup(path);
|
||||
if(cmd->path == NULL)
|
||||
goto failure;
|
||||
cmd->argv= calloc(sizeof(char *), argc + 2);
|
||||
if(cmd->argv == NULL)
|
||||
goto failure;
|
||||
for(i= 0; i < argc + 2; i++)
|
||||
cmd->argv[i]= NULL;
|
||||
cmd->argv[0]= strdup(path);
|
||||
if(cmd->argv[0] == NULL)
|
||||
goto failure;
|
||||
for(i= 0; i < argc; i++) {
|
||||
cmd->argv[i + 1]= strdup(argv[i]);
|
||||
if(cmd->argv[i] == NULL)
|
||||
goto failure;
|
||||
}
|
||||
cmd->name= strdup(name);
|
||||
if(cmd->name == NULL)
|
||||
goto failure;
|
||||
return(1);
|
||||
failure:;
|
||||
Xorriso_extf_destroy(xorriso, filter, 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_extf_destroy(struct XorrisO *xorriso, struct Xorriso_extF **filter,
|
||||
int flag)
|
||||
{
|
||||
int i;
|
||||
IsoExternalFilterCommand *cmd;
|
||||
|
||||
if(*filter == NULL)
|
||||
return(0);
|
||||
cmd= (*filter)->cmd;
|
||||
if(cmd != NULL) {
|
||||
if(cmd->refcount > 0)
|
||||
return(0);
|
||||
if(cmd->suffix != NULL)
|
||||
free(cmd->suffix);
|
||||
if(cmd->argv != NULL) {
|
||||
for(i= 0; i < cmd->argc; i++)
|
||||
if(cmd->argv[i] != NULL)
|
||||
free(cmd->argv[i]);
|
||||
free((char *) cmd->argv);
|
||||
}
|
||||
if(cmd->name != NULL)
|
||||
free(cmd->name);
|
||||
}
|
||||
free((char *) *filter);
|
||||
*filter= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_lookup_extf(struct XorrisO *xorriso, char *name,
|
||||
struct Xorriso_lsT **found_lst, int flag)
|
||||
{
|
||||
struct Xorriso_extF *filter;
|
||||
struct Xorriso_lsT *lst;
|
||||
|
||||
for(lst= xorriso->filters; lst != NULL; lst= Xorriso_lst_get_next(lst, 0)) {
|
||||
filter= (struct Xorriso_extF *) Xorriso_lst_get_text(lst, 0);
|
||||
if(strcmp(filter->cmd->name, name) == 0) {
|
||||
*found_lst= lst;
|
||||
return(1);
|
||||
}
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_destroy_all_extf(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
struct Xorriso_extF *filter;
|
||||
struct Xorriso_lsT *lst, *next_lst;
|
||||
|
||||
for(lst= xorriso->filters; lst != NULL; lst= next_lst) {
|
||||
filter= (struct Xorriso_extF *) Xorriso_lst_get_text(lst, 0);
|
||||
Xorriso_lst_detach_text(lst, 0);
|
||||
next_lst= Xorriso_lst_get_next(lst, 0);
|
||||
Xorriso_lst_destroy(&lst, 0);
|
||||
Xorriso_extf_destroy(xorriso, &filter, 0);
|
||||
}
|
||||
xorriso->filters= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param flag bit0= return 2 if renaming is not possible by libisofs
|
||||
(always: if demanded strip suffix is missing
|
||||
or if suffix makes name length > 255)
|
||||
bit1= strip suffix rather than appending it
|
||||
*/
|
||||
int Xorriso_rename_suffix(struct XorrisO *xorriso, IsoNode *node, char *suffix,
|
||||
char *show_path, char new_name[], int flag)
|
||||
{
|
||||
int ret, lo= 0, ls= 0, strip_suffix;
|
||||
char *old_name= NULL, *show_name;
|
||||
|
||||
strip_suffix= !!(flag & 2);
|
||||
|
||||
old_name= strdup((char *) iso_node_get_name(node));
|
||||
show_name= old_name;
|
||||
if(show_path != NULL)
|
||||
if(show_path[0] != 0)
|
||||
show_name= show_path;
|
||||
lo= strlen(old_name);
|
||||
ls= strlen(suffix);
|
||||
if(strip_suffix) {
|
||||
if(lo <= ls) {
|
||||
/* refuse gracefully */
|
||||
ret= 2; goto ex;
|
||||
}
|
||||
if(strcmp(old_name + lo - ls, suffix) != 0) {
|
||||
ret= 2; goto ex;
|
||||
}
|
||||
if(lo >= SfileadrL)
|
||||
goto cannot_remove_suffix;
|
||||
strcpy(new_name, old_name);
|
||||
new_name[lo - ls]= 0;
|
||||
ret = iso_node_set_name(node, new_name);
|
||||
if (ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if (!(flag & 1))
|
||||
Xorriso_report_iso_error(xorriso, "", ret,
|
||||
"Error when renaming ISO node", 0, "FAILURE", 1);
|
||||
cannot_remove_suffix:;
|
||||
strcpy(xorriso->info_text, "-set_filter: Cannot remove suffix from ");
|
||||
Text_shellsafe(show_name, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
(flag & 1) ? "WARNING" : "FAILURE", 0);
|
||||
ret= 2 * (flag & 1); goto ex;
|
||||
}
|
||||
} else {
|
||||
/* check whether suffix already present */
|
||||
if(lo >= ls)
|
||||
if(strcmp(old_name + lo - ls, suffix) == 0) {
|
||||
/* refuse gracefully */
|
||||
ret= 2; goto ex;
|
||||
}
|
||||
if(lo + ls > 255) {
|
||||
cannot_append_suffix:;
|
||||
strcpy(xorriso->info_text, "-set_filter: Cannot append suffix to ");
|
||||
Text_shellsafe(show_name, xorriso->info_text, 1);
|
||||
strcat(xorriso->info_text, ". Left unfiltered.");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
(flag & 1) ? "WARNING" : "FAILURE", 0);
|
||||
ret= 2 * (flag & 1); goto ex;
|
||||
}
|
||||
sprintf(new_name, "%s%s", old_name, suffix);
|
||||
ret = iso_node_set_name(node, new_name);
|
||||
if (ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if (!(flag & 1))
|
||||
Xorriso_report_iso_error(xorriso, "", ret,
|
||||
"Error when renaming ISO node", 0, "FAILURE", 1);
|
||||
goto cannot_append_suffix;
|
||||
}
|
||||
}
|
||||
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(old_name != NULL)
|
||||
free(old_name);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param flag bit0= return 2 if renaming is not possible
|
||||
bit1= print pacifier messages
|
||||
*/
|
||||
int Xorriso_set_filter(struct XorrisO *xorriso, void *in_node,
|
||||
char *path, char *filter_name, int flag)
|
||||
{
|
||||
int ret, strip_suffix= 0, strip_filter= 0, filter_ret= 0;
|
||||
int explicit_suffix= 0, internal_filter= 0;
|
||||
IsoNode *node;
|
||||
IsoFile *file;
|
||||
struct Xorriso_lsT *found_lst;
|
||||
struct Xorriso_extF *found_filter;
|
||||
IsoExternalFilterCommand *cmd = NULL;
|
||||
char *old_name= NULL, new_name[SfileadrL], *suffix= "";
|
||||
IsoStream *stream;
|
||||
int is_renamed= 0;
|
||||
|
||||
new_name[0]= 0;
|
||||
|
||||
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, "-set_filter: Not a regular data file node ");
|
||||
Text_shellsafe(path, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "SORRY", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
file= (IsoFile *) node;
|
||||
|
||||
if(strncmp(filter_name, "--remove-all-filters", 20) == 0) {
|
||||
strip_filter= 1;
|
||||
strip_suffix= 1;
|
||||
if(strlen(filter_name) > 21) {
|
||||
strip_suffix= (filter_name[20] != '+');
|
||||
suffix= filter_name + 21;
|
||||
explicit_suffix= 1;
|
||||
}
|
||||
} else if(strcmp(filter_name, "--zisofs") == 0) {
|
||||
internal_filter= 1;
|
||||
} else if(strcmp(filter_name, "--zisofs-decode") == 0) {
|
||||
internal_filter= 2;
|
||||
} else if(strcmp(filter_name, "--gzip") == 0) {
|
||||
internal_filter= 3;
|
||||
suffix= ".gz";
|
||||
strip_suffix= 0;
|
||||
explicit_suffix= 1;
|
||||
} else if(strcmp(filter_name, "--gunzip") == 0 ||
|
||||
strcmp(filter_name, "--gzip-decode") == 0) {
|
||||
internal_filter= 4;
|
||||
suffix= ".gz";
|
||||
strip_suffix= 1;
|
||||
explicit_suffix= 1;
|
||||
} else {
|
||||
ret= Xorriso_lookup_extf(xorriso, filter_name, &found_lst, 0);
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
if(ret == 0) {
|
||||
strcpy(xorriso->info_text, "-set_filter: Not a registered filter name ");
|
||||
Text_shellsafe(filter_name, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
found_filter= (struct Xorriso_extF *) Xorriso_lst_get_text(found_lst, 0);
|
||||
cmd= found_filter->cmd;
|
||||
suffix= cmd->suffix;
|
||||
strip_suffix= cmd->behavior & 8;
|
||||
}
|
||||
|
||||
if(suffix[0]) {
|
||||
|
||||
/* >>> would need full iso_rr_path of node for showing */;
|
||||
|
||||
old_name= strdup((char *) iso_node_get_name(node));
|
||||
ret= Xorriso_rename_suffix(xorriso, node, suffix, path, new_name,
|
||||
(flag & 1) | (strip_suffix ? 2 : 0));
|
||||
if(ret <= 0 || ret == 2)
|
||||
goto ex;
|
||||
is_renamed= 1;
|
||||
}
|
||||
|
||||
if(strip_filter) {
|
||||
while(1) {
|
||||
if(!explicit_suffix) {
|
||||
stream= iso_file_get_stream(file);
|
||||
|
||||
if(strncmp(stream->class->type, "gzip", 4) == 0) {
|
||||
suffix= ".gz";
|
||||
strip_suffix= 1;
|
||||
} else if(strncmp(stream->class->type, "pizg", 4) == 0) {
|
||||
suffix= ".gz";
|
||||
strip_suffix= 0;
|
||||
} else {
|
||||
ret= iso_stream_get_external_filter(stream, &cmd, 0);
|
||||
if(ret > 0) {
|
||||
suffix= cmd->suffix;
|
||||
strip_suffix= !(cmd->behavior & 8);
|
||||
}
|
||||
}
|
||||
if(suffix[0]) {
|
||||
|
||||
/* >>> would need the current renaming state of path */;
|
||||
|
||||
ret= Xorriso_rename_suffix(xorriso, node, suffix, NULL, new_name,
|
||||
(flag & 1) | (strip_suffix << 1));
|
||||
if(ret <= 0 || ret == 2)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
ret= iso_file_remove_filter(file, 0);
|
||||
if(ret != 1)
|
||||
break;
|
||||
}
|
||||
filter_ret= 1;
|
||||
} else if (internal_filter == 1 || internal_filter == 2) {
|
||||
filter_ret = iso_file_add_zisofs_filter(file, 1 | (internal_filter & 2));
|
||||
if(filter_ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(!(internal_filter == 2 && filter_ret == ISO_ZISOFS_WRONG_INPUT))
|
||||
Xorriso_report_iso_error(xorriso, "", filter_ret,
|
||||
"Error when setting filter to ISO node", 0, "FAILURE", 1);
|
||||
}
|
||||
} else if (internal_filter == 3 || internal_filter == 4) {
|
||||
filter_ret = iso_file_add_gzip_filter(file,
|
||||
1 | ((internal_filter == 4) << 1));
|
||||
if(filter_ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
Xorriso_report_iso_error(xorriso, "", filter_ret,
|
||||
"Error when setting filter to ISO node", 0, "FAILURE", 1);
|
||||
}
|
||||
} else {
|
||||
|
||||
#ifndef Xorriso_allow_extf_suiD
|
||||
/* This is a final safety precaution before iso_file_add_external_filter()
|
||||
performs fork() and executes the alleged filter program.
|
||||
*/
|
||||
if(getuid() != geteuid()) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-set_filter: UID and EUID differ. Will not run external programs.");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(0);
|
||||
}
|
||||
#endif /* ! Xorriso_allow_extf_suiD */
|
||||
|
||||
filter_ret = iso_file_add_external_filter(file, cmd, 0);
|
||||
if(filter_ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
Xorriso_report_iso_error(xorriso, "", filter_ret,
|
||||
"Error when setting filter to ISO node", 0, "FAILURE", 1);
|
||||
}
|
||||
}
|
||||
if(filter_ret != 1 && new_name[0] && old_name != NULL) {
|
||||
ret = iso_node_set_name(node, old_name);
|
||||
if (ret < 0) {
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if (!(flag & 1))
|
||||
Xorriso_report_iso_error(xorriso, "", ret,
|
||||
"Error when renaming ISO node", 0, "FAILURE", 1);
|
||||
}
|
||||
}
|
||||
if(flag & 2) {
|
||||
xorriso->pacifier_count++;
|
||||
Xorriso_pacifier_callback(xorriso, "file filters processed",
|
||||
xorriso->pacifier_count, xorriso->pacifier_total, "", 0);
|
||||
}
|
||||
if(filter_ret < 0) {
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
|
||||
ret= filter_ret;
|
||||
ex:;
|
||||
if(old_name != NULL)
|
||||
free(old_name);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= delete filter with the given name
|
||||
*/
|
||||
int Xorriso_external_filter(struct XorrisO *xorriso,
|
||||
char *name, char *options, char *path,
|
||||
int argc, char **argv, int flag)
|
||||
{
|
||||
int ret, delete= 0, behavior= 0, extf_flag= 0, is_banned= 0;
|
||||
char *what, *what_next, *suffix= "";
|
||||
struct Xorriso_lsT *lst;
|
||||
struct Xorriso_extF *found_filter, *new_filter= NULL;
|
||||
|
||||
#ifndef Xorriso_allow_external_filterS
|
||||
/* To be controlled by: configure --enable-external-filters */
|
||||
|
||||
sprintf(xorriso->info_text, "%s : Banned at compile time.",
|
||||
flag & 1 ? "-unregister_filter" : "-external_filter");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
sprintf(xorriso->info_text,
|
||||
"This may be changed at compile time by ./configure option --enable-external-filters");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "HINT", 0);
|
||||
is_banned= 1;
|
||||
|
||||
#endif /* ! Xorriso_allow_external_filterS */
|
||||
|
||||
#ifndef Xorriso_allow_extf_suiD
|
||||
/* To be controlled by: configure --enable-external-filters-setuid */
|
||||
|
||||
if(getuid() != geteuid()) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-set_filter: UID and EUID differ. Will not run external programs.");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
sprintf(xorriso->info_text,
|
||||
"This may be changed at compile time by ./configure option --enable-external-filters-setuid");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "HINT", 0);
|
||||
is_banned= 1;
|
||||
}
|
||||
#endif /* ! Xorriso_allow_extf_suiD */
|
||||
|
||||
if(is_banned)
|
||||
return(0);
|
||||
|
||||
if(xorriso->filter_list_closed) {
|
||||
sprintf(xorriso->info_text,
|
||||
"%s : Banned by previous command -close_filter_list",
|
||||
flag & 1 ? "-unregister_filter" : "-external_filter");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
return(0);
|
||||
}
|
||||
if((!(flag & 1)) && path[0] != '/') {
|
||||
sprintf(xorriso->info_text,
|
||||
"-external_filter : Given command path does not begin by '/' : ");
|
||||
Text_shellsafe(path, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
delete= flag & 1;
|
||||
ret= Xorriso_lookup_extf(xorriso, name, &lst, 0);
|
||||
if(ret < 0)
|
||||
return(ret);
|
||||
if(ret > 0) {
|
||||
if(delete) {
|
||||
found_filter= (struct Xorriso_extF *) Xorriso_lst_get_text(lst, 0);
|
||||
if(found_filter->cmd->refcount > 0) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-external_filter: Cannot remove filter because it is in use by %.f nodes : ",
|
||||
(double) found_filter->cmd->refcount);
|
||||
Text_shellsafe(name, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
Xorriso_lst_detach_text(lst, 0);
|
||||
if(xorriso->filters == lst)
|
||||
xorriso->filters= Xorriso_lst_get_next(lst, 0);
|
||||
Xorriso_lst_destroy(&lst, 0);
|
||||
Xorriso_extf_destroy(xorriso, &found_filter, 0);
|
||||
ret= 1; goto ex;
|
||||
}
|
||||
strcpy(xorriso->info_text,
|
||||
"-external_filter: filter with given name already existing: ");
|
||||
Text_shellsafe(name, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
if(delete) {
|
||||
strcpy(xorriso->info_text,
|
||||
"-external_filter: filter with given name does not exist: ");
|
||||
Text_shellsafe(name, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
|
||||
for(what= options; what!=NULL; what= what_next) {
|
||||
what_next= strchr(what, ':');
|
||||
if(what_next!=NULL) {
|
||||
*what_next= 0;
|
||||
what_next++;
|
||||
}
|
||||
if(strncmp(what, "default", 7) == 0) {
|
||||
suffix= "";
|
||||
behavior= 0;
|
||||
} else if(strncmp(what, "suffix=", 7) == 0) {
|
||||
suffix= what + 7;
|
||||
} else if(strcmp(what, "remove_suffix") == 0) {
|
||||
behavior|= 8;
|
||||
} else if(strcmp(what, "if_nonempty") == 0) {
|
||||
behavior|= 1;
|
||||
} else if(strcmp(what, "if_reduction") == 0) {
|
||||
behavior|= 2;
|
||||
} else if(strcmp(what, "if_block_reduction") == 0) {
|
||||
behavior|= 4;
|
||||
} else if(strncmp(what, "used=", 5) == 0) {
|
||||
; /* this is informational output from -status */
|
||||
} else if(what[0]) {
|
||||
strcpy(xorriso->info_text,
|
||||
"-external_filter: unknown option ");
|
||||
Text_shellsafe(what, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
}
|
||||
|
||||
ret= Xorriso_extf_new(xorriso, &new_filter, path, argc, argv, behavior,
|
||||
suffix, name, extf_flag);
|
||||
if(ret <= 0) {
|
||||
could_not_create:;
|
||||
strcpy(xorriso->info_text,
|
||||
"-external_filter: Could not create filter object");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
goto ex;
|
||||
}
|
||||
ret= Xorriso_lst_append_binary(&(xorriso->filters), (char *) new_filter,0, 4);
|
||||
if(ret <= 0)
|
||||
goto could_not_create;
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(ret <= 0) {
|
||||
if(new_filter != NULL)
|
||||
Xorriso_extf_destroy(xorriso, &new_filter, 0);
|
||||
}
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_status_extf(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
int flag)
|
||||
/*
|
||||
bit1= do only report to fp
|
||||
*/
|
||||
{
|
||||
int i, maxl= 4 * SfileadrL;
|
||||
struct Xorriso_extF *extf;
|
||||
struct Xorriso_lsT *lst;
|
||||
char *line;
|
||||
|
||||
line= xorriso->result_line;
|
||||
for(lst= xorriso->filters; lst != NULL; lst= Xorriso_lst_get_next(lst, 0)) {
|
||||
extf= (struct Xorriso_extF *) Xorriso_lst_get_text(lst, 0);
|
||||
|
||||
strcpy(xorriso->result_line, "-external_filter ");
|
||||
Text_shellsafe(extf->cmd->name, line, 1);
|
||||
if(strlen(line) > maxl)
|
||||
continue;
|
||||
strcat(line, " ");
|
||||
if(extf->cmd->suffix[0]) {
|
||||
strcat(line, "suffix=");
|
||||
Text_shellsafe(extf->cmd->suffix, line, 1);
|
||||
if(strlen(line) > maxl)
|
||||
continue;
|
||||
strcat(line, ":");
|
||||
}
|
||||
if(extf->cmd->behavior & 8)
|
||||
strcat(line, "remove_suffix:");
|
||||
if(extf->cmd->behavior & 1)
|
||||
strcat(line, "if_nonempty:");
|
||||
if(extf->cmd->behavior & 2)
|
||||
strcat(line, "if_reduction:");
|
||||
if(extf->cmd->behavior & 4)
|
||||
strcat(line, "if_block_reduction:");
|
||||
sprintf(line + strlen(line), "used=%.f ", (double) extf->cmd->refcount);
|
||||
if(strlen(line) > maxl)
|
||||
continue;
|
||||
Text_shellsafe(extf->cmd->path, line, 1);
|
||||
if(strlen(line) > maxl)
|
||||
continue;
|
||||
for(i= 1; i < extf->cmd->argc; i++) {
|
||||
strcat(line, " ");
|
||||
Text_shellsafe(extf->cmd->argv[i], line, 1);
|
||||
if(strlen(line) > maxl)
|
||||
break;
|
||||
}
|
||||
if(i < extf->cmd->argc)
|
||||
continue;
|
||||
strcat(line, " --\n");
|
||||
Xorriso_status_result(xorriso, filter, fp, flag&2);
|
||||
}
|
||||
if(xorriso->filter_list_closed) {
|
||||
strcpy(line, "-close_filter_list\n");
|
||||
Xorriso_status_result(xorriso, filter, fp, flag&2);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_set_zisofs_params(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
struct iso_zisofs_ctrl ctrl;
|
||||
|
||||
ctrl.version= 0;
|
||||
ctrl.compression_level= xorriso->zlib_level;
|
||||
if(xorriso->zisofs_block_size == (1 << 16))
|
||||
ctrl.block_size_log2= 16;
|
||||
else if(xorriso->zisofs_block_size == (1 << 17))
|
||||
ctrl.block_size_log2= 17;
|
||||
else
|
||||
ctrl.block_size_log2= 15;
|
||||
ret= iso_zisofs_set_params(&ctrl, 0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret < 0) {
|
||||
Xorriso_report_iso_error(xorriso, "", ret,
|
||||
"Error when setting zisofs parameters", 0, "FAILURE", 1);
|
||||
return(0);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_status_zisofs(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
int flag)
|
||||
/*
|
||||
bit0= do only report non-default settings
|
||||
bit1= do only report to fp
|
||||
*/
|
||||
{
|
||||
off_t ziso_count= 0, osiz_count= 0;
|
||||
off_t gzip_count= 0, gunzip_count= 0;
|
||||
|
||||
iso_zisofs_get_refcounts(&ziso_count, &osiz_count, 0);
|
||||
iso_gzip_get_refcounts(&gzip_count, &gunzip_count, 0);
|
||||
if((flag & 1) && xorriso->zlib_level == xorriso->zlib_level_default &&
|
||||
xorriso->zisofs_block_size == xorriso->zisofs_block_size_default &&
|
||||
xorriso->zisofs_by_magic == 0 &&
|
||||
ziso_count == 0 && osiz_count == 0 &&
|
||||
gzip_count == 0 && gunzip_count == 0) {
|
||||
if(filter == NULL)
|
||||
return(2);
|
||||
if(filter[0] == 0)
|
||||
return 2;
|
||||
}
|
||||
sprintf(xorriso->result_line,
|
||||
"-zisofs level=%d:block_size=%dk:by_magic=%s:ziso_used=%.f:osiz_used=%.f",
|
||||
xorriso->zlib_level, xorriso->zisofs_block_size / 1024,
|
||||
xorriso->zisofs_by_magic ? "on" : "off",
|
||||
(double) ziso_count, (double) osiz_count);
|
||||
sprintf(xorriso->result_line + strlen(xorriso->result_line),
|
||||
":gzip_used=%.f:gunzip_used=%.f\n",
|
||||
(double) gzip_count, (double) gunzip_count);
|
||||
Xorriso_status_result(xorriso, filter, fp, flag&2);
|
||||
return(1);
|
||||
}
|
||||
|
31
xorriso/filters.h
Normal file
31
xorriso/filters.h
Normal file
@ -0,0 +1,31 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which operate on
|
||||
data filter objects.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_filters_includeD
|
||||
#define Xorriso_pvt_filters_includeD yes
|
||||
|
||||
int Xorriso_extf_new(struct XorrisO *xorriso, struct Xorriso_extF **filter,
|
||||
char *path, int argc, char **argv, int behavior,
|
||||
char *suffix, char *name, int flag);
|
||||
|
||||
int Xorriso_extf_destroy(struct XorrisO *xorriso, struct Xorriso_extF **filter,
|
||||
int flag);
|
||||
|
||||
int Xorriso_lookup_extf(struct XorrisO *xorriso, char *name,
|
||||
struct Xorriso_lsT **found_lst, int flag);
|
||||
|
||||
int Xorriso_rename_suffix(struct XorrisO *xorriso, IsoNode *node, char *suffix,
|
||||
char *show_path, char new_name[], int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_filters_includeD */
|
||||
|
1178
xorriso/findjob.c
Normal file
1178
xorriso/findjob.c
Normal file
File diff suppressed because it is too large
Load Diff
400
xorriso/findjob.h
Normal file
400
xorriso/findjob.h
Normal file
@ -0,0 +1,400 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of classes FindjoB, ExprnodE, ExprtesT
|
||||
which perform tree searches in libisofs or in POSIX filesystem.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_findjob_includeD
|
||||
#define Xorriso_pvt_findjob_includeD yes
|
||||
|
||||
|
||||
#define Xorriso_findjob_on_expR yes
|
||||
|
||||
#ifdef Xorriso_findjob_on_expR
|
||||
|
||||
/*
|
||||
A single Testnode.
|
||||
*/
|
||||
struct ExprtesT {
|
||||
|
||||
struct FindjoB *boss;
|
||||
|
||||
int invert; /* 0=normal 1=invert result */
|
||||
|
||||
/*
|
||||
0= -false (with invert : -true)
|
||||
1= -name char *arg1 (regex_t in *arg2)
|
||||
2= -type char *arg1
|
||||
3= -damaged
|
||||
4= -lba_range int *arg1 int *arg2
|
||||
5= -has_acl
|
||||
6= -has_xattr
|
||||
7= -has_aaip
|
||||
8= -has_filter
|
||||
9= -wanted_node IsoNode *arg1 (for internal use, arg1 not allocated)
|
||||
10= -pending_data
|
||||
11= -decision char *arg1 ("yes", "no")
|
||||
12= -prune
|
||||
13= -wholename char *arg1 (regex_t in *arg2)
|
||||
14= -has_any_xattr
|
||||
15= -has_md5
|
||||
*/
|
||||
int test_type;
|
||||
|
||||
void *arg1;
|
||||
void *arg2;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
A computational node.
|
||||
A tree of these nodes forms the expression.
|
||||
Sequences of AND/OR operations form branches, brackets spawn new branches,
|
||||
NOT inverts node's test resp. subtree result.
|
||||
*/
|
||||
struct ExprnodE {
|
||||
|
||||
struct ExprnodE *up;
|
||||
|
||||
char origin[8];
|
||||
|
||||
/* Operators */
|
||||
int invert; /* 0=normal 1=invert own result (subtree or test, but not op) */
|
||||
|
||||
int assoc; /*
|
||||
0= left : compute own value, combine with left value,
|
||||
compute right value, combine with current value
|
||||
1= right: compute own value, compute right value,
|
||||
combine own and right, combine with left value
|
||||
*/
|
||||
|
||||
int use_shortcuts; /* 0= evaluate all tests of -and and -or,
|
||||
1= evaluate only until the combined result is known
|
||||
*/
|
||||
|
||||
struct ExprnodE *left;
|
||||
int left_op; /* 0=OR , 1=AND */
|
||||
|
||||
struct ExprnodE *right;
|
||||
int right_op; /* see left_op */
|
||||
|
||||
/* Brackets : a pointer to the first node in a subchain */
|
||||
struct ExprnodE *sub;
|
||||
|
||||
int is_if_then_else;
|
||||
struct ExprnodE *true_branch;
|
||||
struct ExprnodE *false_branch;
|
||||
|
||||
/* elementary test : if sub!=NULL , test is ignored */
|
||||
struct ExprtesT *test;
|
||||
|
||||
/* Result */
|
||||
int own_value;
|
||||
int composed_value;
|
||||
|
||||
};
|
||||
|
||||
|
||||
struct FindjoB {
|
||||
|
||||
char *start_path;
|
||||
|
||||
struct ExprnodE *test_tree;
|
||||
|
||||
struct ExprnodE *cursor;
|
||||
int invert; /* 0=normal 1=set invert-property for next new test node */
|
||||
int use_shortcuts;
|
||||
|
||||
/* 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
|
||||
30= internal: count by xorriso->node_counter
|
||||
31= internal: register in xorriso->node_array
|
||||
32= internal: widen_hardlinks disk_equiv: update nodes marked in di_do_widen
|
||||
33= get_any_xattr
|
||||
34= get_md5
|
||||
35= check_md5
|
||||
36= make_md5
|
||||
37= mkisofs_r
|
||||
38= sort_weight number
|
||||
*/
|
||||
int action;
|
||||
int prune;
|
||||
|
||||
/* 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, also used as weight */
|
||||
time_t date;
|
||||
char *found_path;
|
||||
struct FindjoB *subjob;
|
||||
|
||||
/* Errors */
|
||||
char errmsg[4096];
|
||||
int errn; /*
|
||||
>0 = UNIX errno
|
||||
-1 = close_bracket: no bracket open
|
||||
-2 = binary operator or closing bracket expected
|
||||
-3 = unexpected binary operator or closing bracket
|
||||
-4 = unsupported command
|
||||
-5 = -then -elseif -else -endif without -if or at wrong place
|
||||
*/
|
||||
};
|
||||
|
||||
|
||||
int Exprnode_destroy(struct ExprnodE **fnode, int flag);
|
||||
|
||||
int Exprnode_tree_value(struct XorrisO *xorriso, struct ExprnodE *fnode,
|
||||
int left_value, void *node, char *name, char *path,
|
||||
struct stat *boss_stbuf, struct stat *stbuf, int flag);
|
||||
|
||||
|
||||
int Findjob_new(struct FindjoB **o, char *start_path, int flag);
|
||||
|
||||
int Findjob_destroy(struct FindjoB **o, int flag);
|
||||
|
||||
int Findjob_set_start_path(struct FindjoB *o, char *start_path, int flag);
|
||||
|
||||
int Findjob_get_start_path(struct FindjoB *o, char **start_path, int flag);
|
||||
|
||||
int Findjob_set_commit_filter_2(struct FindjoB *o, int flag);
|
||||
|
||||
int Findjob_set_lba_range(struct FindjoB *o, int start_lba, int count,
|
||||
int flag);
|
||||
|
||||
int Findjob_set_wanted_node(struct FindjoB *o, void *wanted_node, int flag);
|
||||
|
||||
/* @param value -1= only undamaged files, 1= only damaged files
|
||||
*/
|
||||
int Findjob_set_damage_filter(struct FindjoB *o, int value, int flag);
|
||||
|
||||
|
||||
int Findjob_set_decision(struct FindjoB *o, char *decision, int flag);
|
||||
|
||||
int Findjob_open_bracket(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_close_bracket(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_not(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_and(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_or(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_if(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_then(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_else(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_elseif(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_endif(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_test_2(struct XorrisO *xorriso, struct FindjoB *o,
|
||||
void *node, char *name, char *path,
|
||||
struct stat *boss_stbuf, struct stat *stbuf, int flag);
|
||||
|
||||
int Findjob_set_action_found_path(struct FindjoB *o, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_target(struct FindjoB *o, int action, char *target,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_ad(struct FindjoB *o, int type, time_t date, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chgrp(struct FindjoB *o, gid_t group, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chmod(struct FindjoB *o,
|
||||
mode_t mode_and, mode_t mode_or, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chown(struct FindjoB *o, uid_t user,int flag);
|
||||
|
||||
/* @param flag bit0= -wholename rather than -name
|
||||
*/
|
||||
int Findjob_set_name_expr(struct FindjoB *o, char *name_expr, int flag);
|
||||
|
||||
int Findjob_set_file_type(struct FindjoB *o, char file_type, int flag);
|
||||
|
||||
/* @param value -1= files without ACL, 1= only files with ACL
|
||||
*/
|
||||
int Findjob_set_acl_filter(struct FindjoB *o, int value, int flag);
|
||||
|
||||
/* @param value -1= files without xattr, 1= only files with xattr
|
||||
@param flag bit0=-has_any_xattr rather than -has_xattr
|
||||
*/
|
||||
int Findjob_set_xattr_filter(struct FindjoB *o, int value, int flag);
|
||||
|
||||
/* @param value -1= files without aaip, 1= only files with aaip
|
||||
*/
|
||||
int Findjob_set_aaip_filter(struct FindjoB *o, int value, int flag);
|
||||
|
||||
/* @param value -1= files without filter, 1= files with filter
|
||||
*/
|
||||
int Findjob_set_filter_filter(struct FindjoB *o, int value, int flag);
|
||||
|
||||
/* @param value -1= only without property, 1= only with property
|
||||
@param flag bit0= pseudo-test:
|
||||
if no operator is open, do nothing and return 2
|
||||
*/
|
||||
int Findjob_set_prop_filter(struct FindjoB *o, int test_type, int value,
|
||||
int flag);
|
||||
|
||||
/* @param value -1= true, 1= false
|
||||
@param flag bit0= pseudo-test:
|
||||
if no operator is open, do nothing and return 2
|
||||
*/
|
||||
int Findjob_set_false(struct FindjoB *o, int value, int flag);
|
||||
|
||||
int Findjob_set_prune(struct FindjoB *o, int flag);
|
||||
|
||||
|
||||
int Findjob_set_action_subjob(struct FindjoB *o, int action,
|
||||
struct FindjoB *subjob, int flag);
|
||||
|
||||
int Findjob_set_action_text_2(struct FindjoB *o, int action, char *target,
|
||||
char* text_2, int flag);
|
||||
|
||||
int Findjob_set_action_type(struct FindjoB *o, int action, int type, int flag);
|
||||
|
||||
|
||||
int Findjob_get_action(struct FindjoB *o, int flag);
|
||||
|
||||
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);
|
||||
|
||||
int Findjob_set_found_path(struct FindjoB *o, char *path, int flag);
|
||||
|
||||
int Findjob_get_found_path(struct FindjoB *o, char **path, int flag);
|
||||
|
||||
#else /* Xorriso_findjob_on_expR */
|
||||
|
||||
|
||||
struct FindjoB;
|
||||
|
||||
|
||||
int Findjob_new(struct FindjoB **o, char *start_path, int flag);
|
||||
|
||||
int Findjob_destroy(struct FindjoB **job, int flag);
|
||||
|
||||
|
||||
/* @return 0=no match , 1=match , <0 = error
|
||||
*/
|
||||
int Findjob_test(struct FindjoB *job, char *name,
|
||||
struct stat *boss_stbuf, struct stat *stbuf,
|
||||
int depth, int flag);
|
||||
|
||||
/* @return <0 error, >=0 see xorriso.c struct FindjoB.action
|
||||
*/
|
||||
int Findjob_get_action(struct FindjoB *o, int flag);
|
||||
|
||||
/* @return <0 error, >=0 see xorriso.c 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);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_target(struct FindjoB *o, int action, char *target,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chgrp(struct FindjoB *o, gid_t group, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chmod(struct FindjoB *o,
|
||||
mode_t mode_and, mode_t mode_or, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_ad(struct FindjoB *o, int type, time_t date, int flag);
|
||||
|
||||
int Findjob_set_start_path(struct FindjoB *o, char *start_path, int flag);
|
||||
|
||||
int Findjob_set_action_found_path(struct FindjoB *o, int flag);
|
||||
|
||||
int Findjob_get_start_path(struct FindjoB *o, char **start_path, int flag);
|
||||
|
||||
int Findjob_set_lba_range(struct FindjoB *o, int start_lba, int count,
|
||||
int flag);
|
||||
|
||||
int Findjob_get_lba_damage_filter(struct FindjoB *o, int *start_lba,
|
||||
int *end_lba, int *damage_filter, int flag);
|
||||
|
||||
int Findjob_get_commit_filter(struct FindjoB *o, int *commit_filter, int flag);
|
||||
|
||||
int Findjob_get_acl_filter(struct FindjoB *o, int *acl_filter, int flag);
|
||||
|
||||
int Findjob_get_xattr_filter(struct FindjoB *o, int *xattr_filter, int flag);
|
||||
|
||||
int Findjob_get_aaip_filter(struct FindjoB *o, int *aaip_filter, int flag);
|
||||
|
||||
int Findjob_get_filter_filter(struct FindjoB *o, int *value, int flag);
|
||||
|
||||
int Findjob_set_wanted_node(struct FindjoB *o, void *wanted_node, int flag);
|
||||
|
||||
int Findjob_get_wanted_node(struct FindjoB *o, void **wanted_node, int flag);
|
||||
|
||||
int Findjob_set_found_path(struct FindjoB *o, char *path, int flag);
|
||||
|
||||
int Findjob_get_found_path(struct FindjoB *o, char **path, int flag);
|
||||
|
||||
#endif /* ! Xorriso_findjob_on_expR */
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_findjob_includeD */
|
||||
|
950
xorriso/iso_img.c
Normal file
950
xorriso/iso_img.c
Normal file
@ -0,0 +1,950 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains functions which operate on ISO images and their
|
||||
global properties.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include <sys/wait.h>
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
#include "lib_mgt.h"
|
||||
#include "iso_img.h"
|
||||
#include "iso_tree.h"
|
||||
#include "drive_mgt.h"
|
||||
|
||||
|
||||
int Xorriso_set_ignore_aclea(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, hflag;
|
||||
IsoImage *volume;
|
||||
|
||||
ret= Xorriso_get_volume(xorriso, &volume, 1);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
hflag= (~xorriso->do_aaip) & 1;
|
||||
if((xorriso->ino_behavior & (1 | 2)) && !(xorriso->do_aaip & (4 | 16)))
|
||||
hflag|= 2;
|
||||
iso_image_set_ignore_aclea(volume, hflag);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_update_volid(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int gret, sret= 1;
|
||||
|
||||
gret= Xorriso_get_volid(xorriso, xorriso->loaded_volid, 0);
|
||||
if(gret<=0 || (!xorriso->volid_default) || xorriso->loaded_volid[0]==0)
|
||||
sret= Xorriso_set_volid(xorriso, xorriso->volid, 1);
|
||||
return(gret>0 && sret>0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_create_empty_iso(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
IsoImage *volset;
|
||||
struct isoburn_read_opts *ropts;
|
||||
struct burn_drive_info *dinfo= NULL;
|
||||
struct burn_drive *drive= NULL;
|
||||
|
||||
if(xorriso->out_drive_handle != NULL) {
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to attach volset to drive", 2);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
}
|
||||
if(xorriso->in_volset_handle!=NULL) {
|
||||
iso_image_unref((IsoImage *) xorriso->in_volset_handle);
|
||||
xorriso->in_volset_handle= NULL;
|
||||
Sectorbitmap_destroy(&(xorriso->in_sector_map), 0);
|
||||
Xorriso_destroy_di_array(xorriso, 0);
|
||||
Xorriso_destroy_hln_array(xorriso, 0);
|
||||
xorriso->loaded_volid[0]= 0;
|
||||
xorriso->volset_change_pending= 0;
|
||||
xorriso->no_volset_present= 0;
|
||||
}
|
||||
|
||||
ret= isoburn_ropt_new(&ropts, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
/* Note: no return before isoburn_ropt_destroy() */
|
||||
isoburn_ropt_set_extensions(ropts, isoburn_ropt_pretend_blank);
|
||||
isoburn_ropt_set_input_charset(ropts, xorriso->in_charset);
|
||||
isoburn_set_read_pacifier(drive, NULL, NULL);
|
||||
ret= isoburn_read_image(drive, ropts, &volset);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
isoburn_ropt_destroy(&ropts, 0);
|
||||
if(ret<=0) {
|
||||
sprintf(xorriso->info_text, "Failed to create new empty ISO image object");
|
||||
Xorriso_report_iso_error(xorriso, "", ret, xorriso->info_text, 0, "FATAL",
|
||||
0);
|
||||
return(-1);
|
||||
}
|
||||
xorriso->in_volset_handle= (void *) volset;
|
||||
xorriso->in_sector_map= NULL;
|
||||
Xorriso_update_volid(xorriso, 0);
|
||||
xorriso->volset_change_pending= 0;
|
||||
xorriso->no_volset_present= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_record_boot_info(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
struct burn_drive_info *dinfo;
|
||||
struct burn_drive *drive;
|
||||
IsoImage *image;
|
||||
ElToritoBootImage *bootimg;
|
||||
IsoFile *bootimg_node;
|
||||
IsoBoot *bootcat_node;
|
||||
|
||||
xorriso->loaded_boot_bin_lba= -1;
|
||||
xorriso->loaded_boot_cat_path[0]= 0;
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to record boot LBAs", 0);
|
||||
if(ret<=0)
|
||||
return(0);
|
||||
image= isoburn_get_attached_image(drive);
|
||||
if(image == NULL)
|
||||
return(0);
|
||||
ret= iso_image_get_boot_image(image, &bootimg,
|
||||
&bootimg_node, &bootcat_node);
|
||||
iso_image_unref(image); /* release obtained reference */
|
||||
if(ret != 1)
|
||||
return(0);
|
||||
if(bootimg_node != NULL)
|
||||
Xorriso__file_start_lba((IsoNode *) bootimg_node,
|
||||
&(xorriso->loaded_boot_bin_lba), 0);
|
||||
if(bootcat_node != NULL)
|
||||
Xorriso_path_from_lba(xorriso, (IsoNode *) bootcat_node, 0,
|
||||
xorriso->loaded_boot_cat_path, 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_assert_volid(struct XorrisO *xorriso, int msc1, int flag)
|
||||
{
|
||||
int ret, image_blocks;
|
||||
char volid[33];
|
||||
struct burn_drive_info *dinfo;
|
||||
struct burn_drive *drive;
|
||||
|
||||
if(xorriso->assert_volid[0] == 0)
|
||||
return(1);
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to perform -assert_volid", 0);
|
||||
if(ret<=0)
|
||||
return(0);
|
||||
ret= isoburn_read_iso_head(drive, msc1, &image_blocks, volid, 1);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret <= 0) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-assert_volid: Cannot determine Volume Id at LBA %d.", msc1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
xorriso->assert_volid_sev, 0);
|
||||
return(0);
|
||||
}
|
||||
ret= Sregex_match(xorriso->assert_volid, volid, 0);
|
||||
if(ret < 0)
|
||||
return(2);
|
||||
if(ret == 0) {
|
||||
strcpy(xorriso->info_text,
|
||||
"-assert_volid: Volume id does not match pattern: ");
|
||||
Text_shellsafe(xorriso->assert_volid, xorriso->info_text, 1);
|
||||
strcat(xorriso->info_text, " <> ");
|
||||
Text_shellsafe(volid, xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
xorriso->assert_volid_sev, 0);
|
||||
return(0);
|
||||
}
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @return <0 yes , 0 no , <0 error */
|
||||
int Xorriso_is_isohybrid(struct XorrisO *xorriso, IsoFile *bootimg_node,
|
||||
int flag)
|
||||
{
|
||||
int ret;
|
||||
unsigned char buf[68];
|
||||
void *data_stream= NULL;
|
||||
|
||||
ret= Xorriso_iso_file_open(xorriso, "", (void *) bootimg_node,
|
||||
&data_stream, 1);
|
||||
if(ret <= 0)
|
||||
return(-1);
|
||||
ret= Xorriso_iso_file_read(xorriso, data_stream, (char *) buf, 68, 0);
|
||||
Xorriso_iso_file_close(xorriso, &data_stream, 0);
|
||||
if(ret <= 0)
|
||||
return(0);
|
||||
if(buf[64] == 0xfb && buf[65] == 0xc0 && buf[66] == 0x78 && buf[67] == 0x70)
|
||||
return(1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_image_has_md5(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
IsoImage *image;
|
||||
uint32_t start_lba, end_lba;
|
||||
char md5[16];
|
||||
|
||||
ret= Xorriso_get_volume(xorriso, &image, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
ret= iso_image_get_session_md5(image, &start_lba, &end_lba, md5, 0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret <= 0)
|
||||
return(0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
static const char *un0(const char *text)
|
||||
{
|
||||
if(text == NULL)
|
||||
return("");
|
||||
return(text);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_pvd_info(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, msc1= -1, msc2, i;
|
||||
IsoImage *image;
|
||||
struct burn_drive_info *dinfo;
|
||||
struct burn_drive *drive;
|
||||
char *msg, block_head[8];
|
||||
off_t head_count;
|
||||
|
||||
msg= xorriso->result_line;
|
||||
ret= Xorriso_get_volume(xorriso, &image, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive, "", 16);
|
||||
if(ret > 0) {
|
||||
ret= Xorriso_msinfo(xorriso, &msc1, &msc2, 1 | 4);
|
||||
if(ret<0)
|
||||
return(ret);
|
||||
Xorriso_toc(xorriso, 128);
|
||||
if(msc1 >= 0) {
|
||||
for(i = msc1 + 16; i < msc1 + 32; i++) {
|
||||
ret= burn_read_data(drive, (off_t) i * (off_t) 2048, block_head,
|
||||
(off_t) sizeof(block_head), &head_count, 2);
|
||||
if(ret <= 0) {
|
||||
i= msc1 + 32;
|
||||
break;
|
||||
}
|
||||
if(block_head[0] == 1 && strncmp(block_head + 1, "CD001", 5) == 0)
|
||||
break;
|
||||
}
|
||||
if(i < msc1 + 32) {
|
||||
sprintf(msg, "PVD address : %ds\n", i);
|
||||
Xorriso_result(xorriso,0);
|
||||
}
|
||||
}
|
||||
}
|
||||
sprintf(msg, "Volume Id : %s\n", un0(iso_image_get_volume_id(image)));
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Volume Set Id: %s\n", xorriso->volset_id);
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Publisher Id : %s\n", xorriso->publisher);
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Preparer Id : %s\n",
|
||||
un0(iso_image_get_data_preparer_id(image)));
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "App Id : %s\n", xorriso->application_id);
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "System Id : %s\n", xorriso->system_id);
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Copyright Id : %s\n",
|
||||
un0(iso_image_get_copyright_file_id(image)));
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Abstract Id : %s\n",
|
||||
un0(iso_image_get_abstract_file_id(image)));
|
||||
Xorriso_result(xorriso,0);
|
||||
sprintf(msg, "Biblio Id : %s\n", un0(iso_image_get_biblio_file_id(image)));
|
||||
Xorriso_result(xorriso,0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not mark image as changed */
|
||||
int Xorriso_set_volid(struct XorrisO *xorriso, char *volid, int flag)
|
||||
{
|
||||
int ret;
|
||||
IsoImage *volume;
|
||||
|
||||
if(xorriso->in_volset_handle == NULL)
|
||||
return(2);
|
||||
ret= Xorriso_get_volume(xorriso, &volume, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
iso_image_set_volume_id(volume, volid);
|
||||
if(!(flag&1))
|
||||
Xorriso_set_change_pending(xorriso, 1);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
sprintf(xorriso->info_text,"Volume ID: '%s'",iso_image_get_volume_id(volume));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "DEBUG", 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_get_volid(struct XorrisO *xorriso, char volid[33], int flag)
|
||||
{
|
||||
int ret;
|
||||
IsoImage *volume;
|
||||
|
||||
ret= Xorriso_get_volume(xorriso, &volume, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
strncpy(volid, iso_image_get_volume_id(volume), 32);
|
||||
volid[32]= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
bit0= do only report non-default settings
|
||||
bit1= do only report to fp
|
||||
bit2= is_default
|
||||
bit3= append -boot_image any next
|
||||
bit4= eventually concentrate boot options
|
||||
*/
|
||||
int Xorriso_boot_item_status(struct XorrisO *xorriso, char *cat_path,
|
||||
char *bin_path, int platform_id,
|
||||
int patch_isolinux, int emul, off_t load_size,
|
||||
unsigned char *id_string,
|
||||
unsigned char *selection_crit, char *form,
|
||||
char *filter, FILE *fp, int flag)
|
||||
{
|
||||
int is_default, no_defaults, i, is_default_id= 0, ret;
|
||||
char *line, bspec[SfileadrL + 80], zeros[28];
|
||||
off_t file_size;
|
||||
struct stat stbuf;
|
||||
|
||||
no_defaults= flag & 1;
|
||||
line= xorriso->result_line;
|
||||
|
||||
if(flag & 16) {
|
||||
/* Allow to concentrate boot options. */
|
||||
memset(zeros, 0, 28);
|
||||
if(memcmp(id_string, zeros, 28) == 0 &&
|
||||
memcmp(selection_crit, zeros, 20) == 0)
|
||||
is_default_id= 1;
|
||||
|
||||
/* -boot_image isolinux dir= ... */
|
||||
bspec[0]= 0;
|
||||
if(strcmp(form, "isolinux") != 0 && strcmp(form, "any") != 0)
|
||||
;
|
||||
else if(strcmp(bin_path, "/isolinux.bin") == 0 &&
|
||||
strcmp(cat_path, "/boot.cat") == 0)
|
||||
strcpy(bspec, "dir=/");
|
||||
else if(strcmp(bin_path, "/isolinux/isolinux.bin") == 0 &&
|
||||
strcmp(cat_path, "/isolinux/boot.cat") == 0)
|
||||
strcpy(bspec, "dir=/isolinux");
|
||||
else if(strcmp(xorriso->boot_image_bin_path,
|
||||
"/boot/isolinux/isolinux.bin") == 0
|
||||
&& strcmp(xorriso->boot_image_cat_path,
|
||||
"/boot/isolinux/boot.cat") == 0)
|
||||
strcpy(bspec, "dir=/boot/isolinux");
|
||||
memset(zeros, 0, 28);
|
||||
if(bspec[0] && platform_id == 0 && patch_isolinux &&
|
||||
load_size == 2048 && is_default_id) {
|
||||
sprintf(line, "-boot_image isolinux %s\n", bspec);
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
return(1);
|
||||
}
|
||||
|
||||
file_size= 0;
|
||||
ret= Xorriso_iso_lstat(xorriso, bin_path, &stbuf, 2 | 4);
|
||||
if(ret == 0)
|
||||
file_size= ((stbuf.st_size / (off_t) 512) +
|
||||
!!(stbuf.st_size % (off_t) 512)) * 512;
|
||||
if(platform_id == 0xef && !patch_isolinux &&
|
||||
load_size == file_size && is_default_id) {
|
||||
sprintf(line, "-boot_image any efi_path=");
|
||||
Text_shellsafe(bin_path, line, 1);
|
||||
strcat(line, "\n");
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
return(1);
|
||||
}
|
||||
}
|
||||
|
||||
is_default= (bin_path[0] == 0) || (flag & 4);
|
||||
sprintf(line, "-boot_image %s bin_path=", form);
|
||||
Text_shellsafe(bin_path, line, 1);
|
||||
strcat(line, "\n");
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
is_default= (platform_id == 0 || (flag & 4));
|
||||
sprintf(line, "-boot_image %s platform_id=0x%-2.2x\n", form, platform_id);
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
is_default= ((patch_isolinux & 1) == 0 || bin_path[0] == 0 || (flag & 4));
|
||||
sprintf(line, "-boot_image %s boot_info_table=%s\n",
|
||||
(patch_isolinux & 2) ? "grub" : form, patch_isolinux ? "on" : "off");
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
is_default= (load_size == 2048 || (flag & 4));
|
||||
sprintf(line, "-boot_image %s load_size=%lu\n",
|
||||
form, (unsigned long) load_size);
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
is_default= 1;
|
||||
if(!(flag & 4))
|
||||
for(i= 0; i < 20; i++)
|
||||
if(selection_crit[i])
|
||||
is_default= 0;
|
||||
sprintf(line, "-boot_image %s sel_crit=", form);
|
||||
for(i= 0; i < 20; i++)
|
||||
sprintf(line + strlen(line), "%-2.2X", (unsigned int) selection_crit[i]);
|
||||
strcat(line, "\n");
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
is_default= 1;
|
||||
if(!(flag & 4))
|
||||
for(i= 0; i < 28; i++)
|
||||
if(id_string[i])
|
||||
is_default= 0;
|
||||
sprintf(line, "-boot_image %s id_string=", form);
|
||||
for(i= 0; i < 28; i++)
|
||||
sprintf(line + strlen(line), "%-2.2X", (unsigned int) id_string[i]);
|
||||
strcat(line, "\n");
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
bit0= do only report non-default settings
|
||||
bit1= do only report to fp
|
||||
*/
|
||||
int Xorriso_boot_image_status(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
int flag)
|
||||
{
|
||||
int ret, i, num_boots, hflag;
|
||||
int bin_path_in_use= 0, is_default, no_defaults;
|
||||
char sfe[5*SfileadrL], path[SfileadrL], *form= "any", *line;
|
||||
struct burn_drive_info *dinfo;
|
||||
struct burn_drive *drive;
|
||||
IsoImage *image= NULL;
|
||||
ElToritoBootImage **boots = NULL;
|
||||
IsoFile **bootnodes = NULL;
|
||||
int platform_id, patch, load_size;
|
||||
enum eltorito_boot_media_type media_type;
|
||||
unsigned char id_string[29], sel_crit[21];
|
||||
|
||||
line= xorriso->result_line;
|
||||
no_defaults= flag & 1;
|
||||
|
||||
if(xorriso->boot_count == 0 && xorriso->boot_image_bin_path[0] == 0) {
|
||||
if(xorriso->patch_isolinux_image & 1) {
|
||||
sprintf(line, "-boot_image %s patch\n",
|
||||
xorriso->patch_isolinux_image & 2 ? "grub" : form);
|
||||
is_default= 0;
|
||||
} else if(xorriso->keep_boot_image) {
|
||||
sprintf(line, "-boot_image %s keep\n", form);
|
||||
is_default= 0;
|
||||
} else {
|
||||
sprintf(line, "-boot_image %s discard\n", form);
|
||||
is_default= 1;
|
||||
}
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
ret= 1; goto ex;
|
||||
}
|
||||
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to print boot info", 16);
|
||||
if(ret<=0)
|
||||
{ret= 0; goto ex;}
|
||||
image= isoburn_get_attached_image(drive);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(image == NULL)
|
||||
{ret= 0; goto ex;}
|
||||
|
||||
if(xorriso->boot_image_bin_path[0] || xorriso->boot_count > 0)
|
||||
bin_path_in_use= 1;
|
||||
if(xorriso->boot_image_cat_path[0] && bin_path_in_use) {
|
||||
is_default= 0;
|
||||
sprintf(line,"-boot_image %s cat_path=%s\n",
|
||||
form, Text_shellsafe(xorriso->boot_image_cat_path, sfe, 0));
|
||||
if(!(is_default && no_defaults))
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
}
|
||||
|
||||
if(xorriso->boot_count > 0) {
|
||||
|
||||
/* show attached boot image info */;
|
||||
|
||||
ret= iso_image_get_all_boot_imgs(image, &num_boots, &boots, &bootnodes, 0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret == 1 && num_boots > 0) {
|
||||
for(i= 0; i < num_boots; i++) {
|
||||
ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootnodes[i], path, 0);
|
||||
if(ret <= 0)
|
||||
continue;
|
||||
platform_id= el_torito_get_boot_platform_id(boots[i]);
|
||||
patch= el_torito_get_isolinux_options(boots[i], 0);
|
||||
el_torito_get_boot_media_type(boots[i], &media_type);
|
||||
load_size= el_torito_get_load_size(boots[i]) * 512;
|
||||
el_torito_get_id_string(boots[i], id_string);
|
||||
el_torito_get_selection_crit(boots[i], sel_crit);
|
||||
ret= Xorriso_boot_item_status(xorriso, xorriso->boot_image_cat_path,
|
||||
path, platform_id, patch & 1, media_type,
|
||||
load_size, id_string, sel_crit, "any",
|
||||
filter, fp, 16 | (flag & 3));
|
||||
if(ret <= 0)
|
||||
continue;
|
||||
sprintf(line,"-boot_image %s next\n", form);
|
||||
Xorriso_status_result(xorriso,filter,fp,flag&2);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Show pending boot image info */
|
||||
if(strcmp(xorriso->boot_image_bin_form, "isolinux") == 0 ||
|
||||
strcmp(xorriso->boot_image_bin_form, "grub") == 0)
|
||||
form= xorriso->boot_image_bin_form;
|
||||
|
||||
if(xorriso->boot_count > 0 &&
|
||||
xorriso->boot_platform_id == 0 &&
|
||||
xorriso->patch_isolinux_image == 0 &&
|
||||
xorriso->boot_image_bin_path[0] == 0 &&
|
||||
xorriso->boot_image_emul == 0 &&
|
||||
xorriso->boot_image_load_size == 4 * 512) {
|
||||
for(i= 0; i < 20; i++)
|
||||
if(xorriso->boot_selection_crit[i])
|
||||
break;
|
||||
if(i >= 20)
|
||||
for(i= 0; i < 28; i++)
|
||||
if(xorriso->boot_id_string[i])
|
||||
break;
|
||||
if(i >= 28)
|
||||
{ret= 1; goto ex;} /* Images registered, pending is still default */
|
||||
}
|
||||
|
||||
hflag= 16;
|
||||
if(xorriso->boot_platform_id == 0xef && !xorriso->boot_efi_default)
|
||||
hflag= 0;
|
||||
ret= Xorriso_boot_item_status(xorriso, xorriso->boot_image_cat_path,
|
||||
xorriso->boot_image_bin_path, xorriso->boot_platform_id,
|
||||
xorriso->patch_isolinux_image, xorriso->boot_image_emul,
|
||||
xorriso->boot_image_load_size, xorriso->boot_id_string,
|
||||
xorriso->boot_selection_crit, form,
|
||||
filter, fp, hflag | (flag & 3));
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
|
||||
ret= 1;
|
||||
ex:
|
||||
if(boots != NULL)
|
||||
free(boots);
|
||||
if(bootnodes != NULL)
|
||||
free(bootnodes);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__append_boot_params(char *line, ElToritoBootImage *bootimg,
|
||||
int flag)
|
||||
{
|
||||
unsigned int platform_id;
|
||||
|
||||
platform_id= el_torito_get_boot_platform_id(bootimg);
|
||||
if(platform_id != 0)
|
||||
sprintf(line + strlen(line),
|
||||
" , platform_id=0x%-2.2X ", (unsigned int) platform_id);
|
||||
if(el_torito_seems_boot_info_table(bootimg, 0))
|
||||
sprintf(line + strlen(line), " , boot_info_table=on");
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= no output if no boot record was found
|
||||
bit1= short form
|
||||
bit3= report to info channel (else to result channel)
|
||||
*/
|
||||
int Xorriso_show_boot_info(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, bin_path_valid= 0,has_isolinux_mbr= 0, i, num_boots;
|
||||
unsigned int mbr_lba= 0;
|
||||
off_t lb0_count;
|
||||
char *respt, sfe[5*SfileadrL], path[SfileadrL];
|
||||
unsigned char lb0[2048];
|
||||
struct burn_drive_info *dinfo;
|
||||
struct burn_drive *drive;
|
||||
IsoImage *image= NULL;
|
||||
ElToritoBootImage *bootimg, **boots = NULL;
|
||||
IsoFile *bootimg_node, **bootnodes = NULL;
|
||||
IsoBoot *bootcat_node;
|
||||
|
||||
respt= xorriso->result_line;
|
||||
|
||||
if(xorriso->boot_count > 0) {
|
||||
if(!(flag & 1)) {
|
||||
sprintf(respt, "Boot record : overridden by -boot_image any next\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
}
|
||||
ret= 1; goto ex;
|
||||
}
|
||||
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to print boot info", 16);
|
||||
if(ret<=0)
|
||||
goto no_boot;
|
||||
image= isoburn_get_attached_image(drive);
|
||||
if(image == NULL) {
|
||||
ret= 0;
|
||||
no_boot:;
|
||||
if(!(flag & 1)) {
|
||||
sprintf(respt, "Boot record : none\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
}
|
||||
goto ex;
|
||||
}
|
||||
|
||||
/* Using the nodes with extreme care . They might be deleted meanwhile. */
|
||||
ret= iso_image_get_boot_image(image, &bootimg, &bootimg_node, &bootcat_node);
|
||||
if(ret != 1)
|
||||
goto no_boot;
|
||||
|
||||
ret= Xorriso_path_from_lba(xorriso, NULL, xorriso->loaded_boot_bin_lba,
|
||||
path, 1);
|
||||
if(ret > 0)
|
||||
bin_path_valid= 1;
|
||||
sprintf(respt, "Boot record : El Torito");
|
||||
if(bin_path_valid)
|
||||
ret= Xorriso_is_isohybrid(xorriso, bootimg_node, 0);
|
||||
else
|
||||
ret= 0;
|
||||
if(ret > 0) {
|
||||
/* Load and examine potential MBR */
|
||||
ret= burn_read_data(drive, (off_t) 0, (char *) lb0, (off_t) 2048,
|
||||
&lb0_count, 2);
|
||||
if(ret > 0) {
|
||||
has_isolinux_mbr= 1;
|
||||
if(lb0[510] != 0x55 || lb0[511] != 0xaa)
|
||||
has_isolinux_mbr= 0;
|
||||
mbr_lba= lb0[432] | (lb0[433] << 8) | (lb0[434] << 16) | (lb0[435] << 24);
|
||||
mbr_lba/= 4;
|
||||
if(mbr_lba != xorriso->loaded_boot_bin_lba)
|
||||
has_isolinux_mbr= 0;
|
||||
if(has_isolinux_mbr) {
|
||||
for(i= 0; i < 426; i++)
|
||||
if(strncmp((char *) (lb0 + i), "isolinux", 8) == 0)
|
||||
break;
|
||||
if(i >= 426)
|
||||
has_isolinux_mbr= 0;
|
||||
}
|
||||
for(i= 462; i < 510; i++)
|
||||
if(lb0[i])
|
||||
break;
|
||||
if(i < 510)
|
||||
has_isolinux_mbr= 0;
|
||||
}
|
||||
if(has_isolinux_mbr)
|
||||
strcat(respt, " , ISOLINUX isohybrid MBR pointing to boot image");
|
||||
else
|
||||
strcat(respt, " , ISOLINUX boot image capable of isohybrid");
|
||||
}
|
||||
strcat(respt, "\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
if(flag & 2)
|
||||
{ret= 1; goto ex;}
|
||||
|
||||
if(xorriso->loaded_boot_cat_path[0])
|
||||
sprintf(respt, "Boot catalog : %s\n",
|
||||
Text_shellsafe(xorriso->loaded_boot_cat_path, sfe, 0));
|
||||
else
|
||||
sprintf(respt, "Boot catalog : -not-found-at-load-time-\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
|
||||
if(bin_path_valid)
|
||||
sprintf(respt, "Boot image : %s", Text_shellsafe(path, sfe, 0));
|
||||
else if(xorriso->loaded_boot_bin_lba <= 0)
|
||||
sprintf(respt, "Boot image : -not-found-at-load-time-");
|
||||
else
|
||||
sprintf(respt, "Boot image : -not-found-any-more-by-lba=%d",
|
||||
xorriso->loaded_boot_bin_lba);
|
||||
Xorriso__append_boot_params(respt, bootimg, 0);
|
||||
strcat(respt, "\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
|
||||
ret= iso_image_get_all_boot_imgs(image, &num_boots, &boots, &bootnodes, 0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret == 1 && num_boots > 1) {
|
||||
for(i= 1; i < num_boots; i++) {
|
||||
ret= Xorriso_path_from_node(xorriso, (IsoNode *) bootnodes[i], path, 0);
|
||||
if(ret > 0)
|
||||
sprintf(respt, "Boot image : %s", Text_shellsafe(path, sfe, 0));
|
||||
else
|
||||
sprintf(respt, "Boot image : -not-found-any-more-");
|
||||
Xorriso__append_boot_params(respt, boots[i], 0);
|
||||
strcat(respt, "\n");
|
||||
Xorriso_toc_line(xorriso, flag & 8);
|
||||
}
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(boots != NULL)
|
||||
free(boots);
|
||||
if(bootnodes != NULL);
|
||||
free(bootnodes);
|
||||
if(image != NULL)
|
||||
iso_image_unref(image); /* release obtained reference */
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0=silently return 0 if no volume/image is present
|
||||
*/
|
||||
int Xorriso_get_volume(struct XorrisO *xorriso, IsoImage **volume,
|
||||
int flag)
|
||||
{
|
||||
if(xorriso->in_volset_handle==NULL) {
|
||||
if(flag & 1)
|
||||
return(0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
sprintf(xorriso->info_text,"No ISO image present.");
|
||||
if(xorriso->indev[0]==0 && xorriso->outdev[0]==0)
|
||||
sprintf(xorriso->info_text+strlen(xorriso->info_text),
|
||||
" No -dev, -indev, or -outdev selected.");
|
||||
else
|
||||
sprintf(xorriso->info_text+strlen(xorriso->info_text),
|
||||
" Possible program error with drive '%s'.", xorriso->indev);
|
||||
|
||||
if(!xorriso->no_volset_present)
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
xorriso->no_volset_present= 1;
|
||||
return(0);
|
||||
}
|
||||
*volume= (IsoImage *) xorriso->in_volset_handle;
|
||||
xorriso->no_volset_present= 0;
|
||||
return(*volume != NULL);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_change_is_pending(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
return(!!xorriso->volset_change_pending);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not set hln_change_pending */
|
||||
int Xorriso_set_change_pending(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
IsoImage *image;
|
||||
|
||||
ret= Xorriso_get_volume(xorriso, &image, 1);
|
||||
if(ret <= 0)
|
||||
return ret;
|
||||
xorriso->volset_change_pending= 1;
|
||||
if(!(flag & 1))
|
||||
xorriso->hln_change_pending= 1;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
@param flag bit0= print mount command to result channel rather than
|
||||
performing it
|
||||
bit1= do not allow prefixes with cmd
|
||||
bit2= interpret unprefixed cmd as shell:
|
||||
*/
|
||||
int Xorriso_mount(struct XorrisO *xorriso, char *dev, int adr_mode,
|
||||
char *adr_value, char *cmd, int flag)
|
||||
{
|
||||
int ret, lba, track, session, params_flag= 0, is_safe= 0, is_extra_drive= 0;
|
||||
int give_up= 0, mount_chardev= 0, status;
|
||||
char volid[33], *devadr, mount_command[SfileadrL], adr_data[163], *adr_pt;
|
||||
char *dev_path, libburn_adr[BURN_DRIVE_ADR_LEN + SfileadrL];
|
||||
char sfe[5 * SfileadrL], *dpt, *sysname= "";
|
||||
struct stat stbuf;
|
||||
struct burn_drive_info *dinfo= NULL;
|
||||
struct burn_drive *drive= NULL;
|
||||
|
||||
devadr= dev;
|
||||
adr_pt= adr_value;
|
||||
if(strcmp(dev, "indev") == 0) {
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to perform -mount \"indev\"", 0);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
dev_path= devadr= xorriso->indev;
|
||||
if(strncmp(dev_path, "stdio:", 6) == 0)
|
||||
dev_path+= 6;
|
||||
if(xorriso->in_drive_handle == xorriso->out_drive_handle)
|
||||
give_up= 3;
|
||||
else
|
||||
give_up= 1;
|
||||
} else if(strcmp(dev, "outdev") == 0) {
|
||||
ret= Xorriso_get_drive_handles(xorriso, &dinfo, &drive,
|
||||
"on attempt to perform -mount \"outdev\"",
|
||||
2);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
dev_path= devadr= xorriso->outdev;
|
||||
if(strncmp(dev_path, "stdio:", 6) == 0)
|
||||
dev_path+= 6;
|
||||
if(xorriso->in_drive_handle == xorriso->out_drive_handle)
|
||||
give_up= 3;
|
||||
else
|
||||
give_up= 2;
|
||||
} else {
|
||||
is_extra_drive= 1;
|
||||
dev_path= dev;
|
||||
if(strncmp(dev_path, "stdio:", 6) == 0)
|
||||
dev_path+= 6;
|
||||
|
||||
/* do only accept regular files and block devices */
|
||||
ret= stat(dev_path, &stbuf);
|
||||
if(ret == -1) {
|
||||
sprintf(xorriso->info_text, "Cannot determine properties of file %s",
|
||||
Text_shellsafe(dev_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
ret= System_uname(&sysname, NULL, NULL, NULL, 0);
|
||||
if(ret > 0 && strcmp(sysname, "FreeBSD") == 0)
|
||||
mount_chardev= 1;
|
||||
if(!(S_ISREG(stbuf.st_mode) || (S_ISBLK(stbuf.st_mode) && !mount_chardev)
|
||||
|| (S_ISCHR(stbuf.st_mode) && !mount_chardev))) {
|
||||
sprintf(xorriso->info_text,
|
||||
"File object is not suitable as mount device: %s",
|
||||
Text_shellsafe(dev_path, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
|
||||
/* Aquire drive as direct libburn address or via stdio: prefix */
|
||||
ret= burn_drive_convert_fs_adr(dev, libburn_adr);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret < 0)
|
||||
{ret= -1; goto ex;}
|
||||
if(ret == 0 && strncmp(dev, "stdio:", 6) != 0)
|
||||
sprintf(libburn_adr, "stdio:%s", dev);
|
||||
burn_preset_device_open(xorriso->drives_exclusive, 0, 0);
|
||||
ret= isoburn_drive_aquire(&dinfo, libburn_adr, 1);
|
||||
burn_preset_device_open(1, 0, 0);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret <= 0)
|
||||
{ret= 0; goto ex;}
|
||||
drive= dinfo[0].drive;
|
||||
}
|
||||
|
||||
if(adr_mode == 4 && strlen(adr_pt) <= 80) {
|
||||
ret= Xorriso__bourne_to_reg(adr_pt, adr_data, 0);
|
||||
if(ret == 1) {
|
||||
params_flag|= 4;
|
||||
adr_pt= adr_data;
|
||||
}
|
||||
}
|
||||
ret= isoburn_get_mount_params(drive, adr_mode, adr_pt, &lba, &track,
|
||||
&session, volid, params_flag);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
if(session <= 0 || track <= 0 || ret == 2) {
|
||||
Xorriso_msgs_submit(xorriso, 0,
|
||||
"-mount : Given address does not point to an ISO 9660 session",
|
||||
0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
if(strstr(devadr, "stdio:") == devadr)
|
||||
devadr+= 6;
|
||||
ret= Xorriso_make_mount_cmd(xorriso, cmd, lba, track, session, volid, devadr,
|
||||
mount_command, flag & (2 | 4));
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
if(ret == 2)
|
||||
is_safe= 1;
|
||||
|
||||
if(is_extra_drive) {
|
||||
isoburn_drive_release(drive, 0);
|
||||
burn_drive_info_free(dinfo);
|
||||
drive= NULL;
|
||||
} else if(give_up > 0 && !((flag & 1) || (xorriso->mount_opts_flag & 1))) {
|
||||
Xorriso_give_up_drive(xorriso, give_up);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
|
||||
sprintf(xorriso->info_text, "Volume id : %s\n",
|
||||
Text_shellsafe(volid, sfe, 0));
|
||||
Xorriso_info(xorriso, 0);
|
||||
if(flag & 1) {
|
||||
sprintf(xorriso->result_line, "%s\n", mount_command);
|
||||
Xorriso_result(xorriso,0);
|
||||
} else {
|
||||
sprintf(xorriso->info_text, "Mount command: %s\n", mount_command);
|
||||
Xorriso_info(xorriso, 0);
|
||||
if(!is_safe) {
|
||||
Xorriso_msgs_submit(xorriso, 0,
|
||||
"-mount : Will not perform mount command which stems from command template.",
|
||||
0, "SORRY", 0);
|
||||
sprintf(xorriso->result_line, "%s\n", mount_command);
|
||||
Xorriso_result(xorriso,0);
|
||||
} else {
|
||||
ret= Xorriso_execv(xorriso, mount_command, "/bin:/sbin", &status, 1);
|
||||
if(WIFEXITED(status) && WEXITSTATUS(status) != 0) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-mount : mount command failed with exit value %d",
|
||||
(int) WEXITSTATUS(ret));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
sprintf(xorriso->info_text, "\nMounted session %d of device %s",
|
||||
session, Text_shellsafe(dev_path, sfe, 0));
|
||||
dpt= strchr(cmd, ':');
|
||||
if(dpt == NULL)
|
||||
dpt= cmd ;
|
||||
else
|
||||
dpt++;
|
||||
sprintf(xorriso->info_text + strlen(xorriso->info_text),
|
||||
" as directory %s\n", Text_shellsafe(dpt, sfe, 0));
|
||||
Xorriso_info(xorriso, 0);
|
||||
}
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(is_extra_drive && drive != NULL) {
|
||||
isoburn_drive_release(drive, 0);
|
||||
burn_drive_info_free(dinfo);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
}
|
||||
return(ret);
|
||||
}
|
||||
|
44
xorriso/iso_img.h
Normal file
44
xorriso/iso_img.h
Normal file
@ -0,0 +1,44 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which operate on ISO images
|
||||
and their global properties.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_iso_img_includeD
|
||||
#define Xorriso_pvt_iso_img_includeD yes
|
||||
|
||||
|
||||
int Xorriso_update_volid(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_record_boot_info(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_assert_volid(struct XorrisO *xorriso, int msc1, int flag);
|
||||
|
||||
int Xorriso_is_isohybrid(struct XorrisO *xorriso, IsoFile *bootimg_node,
|
||||
int flag);
|
||||
|
||||
int Xorriso_boot_item_status(struct XorrisO *xorriso, char *cat_path,
|
||||
char *bin_path, int platform_id,
|
||||
int patch_isolinux, int emul, off_t load_size,
|
||||
unsigned char *id_string,
|
||||
unsigned char *selection_crit, char *form,
|
||||
char *filter, FILE *fp, int flag);
|
||||
|
||||
int Xorriso__append_boot_params(char *line, ElToritoBootImage *bootimg,
|
||||
int flag);
|
||||
|
||||
int Xorriso_get_volume(struct XorrisO *xorriso, IsoImage **volume,
|
||||
int flag);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_iso_img_includeD */
|
||||
|
2637
xorriso/iso_manip.c
Normal file
2637
xorriso/iso_manip.c
Normal file
File diff suppressed because it is too large
Load Diff
72
xorriso/iso_manip.h
Normal file
72
xorriso/iso_manip.h
Normal file
@ -0,0 +1,72 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which manipulate the
|
||||
libisofs tree model.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_iso_manip_includeD
|
||||
#define Xorriso_pvt_iso_manip_includeD yes
|
||||
|
||||
|
||||
int Xorriso_transfer_properties(struct XorrisO *xorriso, struct stat *stbuf,
|
||||
char *disk_path, IsoNode *node, int flag);
|
||||
|
||||
int Xorriso_graft_split(struct XorrisO *xorriso, IsoImage *volume,
|
||||
IsoDir *dir, char *disk_path, char *img_name,
|
||||
char *nominal_source, char *nominal_target,
|
||||
off_t size, IsoNode **node, int flag);
|
||||
|
||||
int Xorriso_tree_graft_node(struct XorrisO *xorriso, IsoImage *volume,
|
||||
IsoDir *dir, char *disk_path, char *img_name,
|
||||
char *nominal_source, char *nominal_target,
|
||||
off_t offset, off_t cut_size,
|
||||
IsoNode **node, int flag);
|
||||
|
||||
int Xorriso_add_tree(struct XorrisO *xorriso, IsoDir *dir,
|
||||
char *img_dir_path, char *disk_dir_path,
|
||||
struct LinkiteM *link_stack, int flag);
|
||||
|
||||
int Xorriso_copy_implicit_properties(struct XorrisO *xorriso, IsoDir *dir,
|
||||
char *full_img_path, char *img_path, char *full_disk_path, int flag);
|
||||
|
||||
int Xorriso_mkisofs_lower_r(struct XorrisO *xorriso, IsoNode *node, int flag);
|
||||
|
||||
int Xorriso_widen_hardlink(struct XorrisO *xorriso, void * boss_iter,
|
||||
IsoNode *node,
|
||||
char *abs_path, char *iso_prefix, char *disk_prefix,
|
||||
int flag);
|
||||
|
||||
|
||||
int Xorriso_cannot_create_iter(struct XorrisO *xorriso, int iso_error,
|
||||
int flag);
|
||||
|
||||
int Xorriso_findi_iter(struct XorrisO *xorriso, IsoDir *dir_node, off_t *mem,
|
||||
IsoDirIter **iter,
|
||||
IsoNode ***node_array, int *node_count, int *node_idx,
|
||||
IsoNode **iterated_node, int flag);
|
||||
|
||||
int Xorriso_findi_action(struct XorrisO *xorriso, struct FindjoB *job,
|
||||
IsoDirIter *boss_iter, off_t boss_mem,
|
||||
char *abs_path, char *show_path,
|
||||
IsoNode *node, int depth, int flag);
|
||||
|
||||
int Xorriso_findi_headline(struct XorrisO *xorriso, struct FindjoB *job,
|
||||
int flag);
|
||||
|
||||
int Xorriso_findi_sorted(struct XorrisO *xorriso, struct FindjoB *job,
|
||||
off_t boss_mem, int filec, char **filev, int flag);
|
||||
|
||||
int Xorriso_all_node_array(struct XorrisO *xorriso, int addon_nodes, int flag);
|
||||
|
||||
|
||||
int Xorriso__file_start_lba(IsoNode *node, int *lba, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_iso_manip_includeD */
|
||||
|
2146
xorriso/iso_tree.c
Normal file
2146
xorriso/iso_tree.c
Normal file
File diff suppressed because it is too large
Load Diff
92
xorriso/iso_tree.h
Normal file
92
xorriso/iso_tree.h
Normal file
@ -0,0 +1,92 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which access nodes of the
|
||||
libisofs tree model.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_iso_tree_includeD
|
||||
#define Xorriso_pvt_iso_tree_includeD yes
|
||||
|
||||
|
||||
#define LIBISO_ISDIR(node) (iso_node_get_type(node) == LIBISO_DIR)
|
||||
#define LIBISO_ISREG(node) (iso_node_get_type(node) == LIBISO_FILE)
|
||||
#define LIBISO_ISLNK(node) (iso_node_get_type(node) == LIBISO_SYMLINK)
|
||||
#define LIBISO_ISCHR(node) (iso_node_get_type(node) == LIBISO_SPECIAL && \
|
||||
S_ISCHR(iso_node_get_mode(node)))
|
||||
#define LIBISO_ISBLK(node) (iso_node_get_type(node) == LIBISO_SPECIAL && \
|
||||
S_ISBLK(iso_node_get_mode(node)))
|
||||
#define LIBISO_ISFIFO(node) (iso_node_get_type(node) == LIBISO_SPECIAL && \
|
||||
S_ISFIFO(iso_node_get_mode(node)))
|
||||
#define LIBISO_ISSOCK(node) (iso_node_get_type(node) == LIBISO_SPECIAL && \
|
||||
S_ISSOCK(iso_node_get_mode(node)))
|
||||
#define LIBISO_ISBOOT(node) (iso_node_get_type(node) == LIBISO_BOOT)
|
||||
|
||||
|
||||
int Xorriso_node_from_path(struct XorrisO *xorriso, IsoImage *volume,
|
||||
char *path, IsoNode **node, int flag);
|
||||
|
||||
int Xorriso_get_node_by_path(struct XorrisO *xorriso,
|
||||
char *in_path, char *eff_path,
|
||||
IsoNode **node, int flag);
|
||||
|
||||
int Xorriso_node_get_dev(struct XorrisO *xorriso, IsoNode *node,
|
||||
char *path, dev_t *dev, int flag);
|
||||
|
||||
int Xorriso_fake_stbuf(struct XorrisO *xorriso, char *path, struct stat *stbuf,
|
||||
IsoNode **node, int flag);
|
||||
|
||||
int Xorriso_node_is_valid(struct XorrisO *xorriso, IsoNode *in_node, int flag);
|
||||
|
||||
int Xorriso_path_from_node(struct XorrisO *xorriso, IsoNode *in_node,
|
||||
char path[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_path_from_lba(struct XorrisO *xorriso, IsoNode *node, int lba,
|
||||
char path[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_get_attr_value(struct XorrisO *xorriso, void *in_node, char *path,
|
||||
char *name, size_t *value_length, char **value, int flag);
|
||||
|
||||
int Xorriso_stream_type(struct XorrisO *xorriso, IsoNode *node,
|
||||
IsoStream *stream, char type_text[], int flag);
|
||||
|
||||
|
||||
int Xorriso_show_du_subs(struct XorrisO *xorriso, IsoDir *dir_node,
|
||||
char *abs_path, char *rel_path, off_t *size,
|
||||
off_t boss_mem, int flag);
|
||||
|
||||
int Xorriso_sorted_dir_i(struct XorrisO *xorriso, IsoDir *dir_node,
|
||||
int *filec, char ***filev, off_t boss_mem, int flag);
|
||||
|
||||
int Xorriso_obtain_pattern_files_i(
|
||||
struct XorrisO *xorriso, char *wd, IsoDir *dir,
|
||||
int *filec, char **filev, int count_limit, off_t *mem,
|
||||
int *dive_count, int flag);
|
||||
|
||||
int Xorriso__start_end_lbas(IsoNode *node,
|
||||
int *lba_count, int **start_lbas, int **end_lbas,
|
||||
off_t *size, int flag);
|
||||
|
||||
int Xorriso__file_start_lba(IsoNode *node,
|
||||
int *lba, int flag);
|
||||
|
||||
int Xorriso_file_eval_damage(struct XorrisO *xorriso, IsoNode *node,
|
||||
off_t *damage_start, off_t *damage_end,
|
||||
int flag);
|
||||
|
||||
int Xorriso_report_lba(struct XorrisO *xorriso, char *show_path,
|
||||
IsoNode *node, int flag);
|
||||
|
||||
int Xorriso_report_damage(struct XorrisO *xorriso, char *show_path,
|
||||
IsoNode *node, int flag);
|
||||
|
||||
int Xorriso_getfname(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_iso_tree_includeD */
|
||||
|
483
xorriso/lib_mgt.c
Normal file
483
xorriso/lib_mgt.c
Normal file
@ -0,0 +1,483 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains functions which manage the relation between xorriso
|
||||
and the libraries: libburn, libisofs, libisoburn.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
|
||||
/* for -charset */
|
||||
#include <iconv.h>
|
||||
#include <langinfo.h>
|
||||
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
#include "lib_mgt.h"
|
||||
|
||||
|
||||
int Xorriso_abort(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= burn_abort(4440, burn_abort_pacifier, "xorriso : ");
|
||||
if(ret<=0) {
|
||||
fprintf(stderr,
|
||||
"\nxorriso : ABORT : Cannot cancel burn session and release drive.\n");
|
||||
return(0);
|
||||
}
|
||||
fprintf(stderr,
|
||||
"xorriso : ABORT : Drive is released and library is shut down now.\n");
|
||||
fprintf(stderr,
|
||||
"xorriso : ABORT : Program done. Even if you do not see a shell prompt.\n");
|
||||
fprintf(stderr, "\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= asynchronous handling (else catch thread, wait, and exit)
|
||||
*/
|
||||
int Xorriso_set_signal_handling(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
char *handler_prefix= NULL;
|
||||
|
||||
if(Xorriso__get_signal_behavior(0) != 1)
|
||||
return(2);
|
||||
handler_prefix= calloc(strlen(xorriso->progname)+3+1, 1);
|
||||
if(handler_prefix==NULL) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot allocate memory for for setting signal handler");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(-1);
|
||||
}
|
||||
sprintf(handler_prefix, "%s : ", xorriso->progname);
|
||||
burn_set_signal_handling(handler_prefix, NULL, (flag & 1) * 0x30);
|
||||
free(handler_prefix);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_startup_libraries(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, major, minor, micro;
|
||||
char *queue_sev, *print_sev, reason[1024];
|
||||
struct iso_zisofs_ctrl zisofs_ctrl= {0, 6, 15};
|
||||
|
||||
|
||||
/* First an ugly compile time check for header version compatibility.
|
||||
If everthing matches, then no C code is produced. In case of mismatch,
|
||||
intentionally faulty C code will be inserted.
|
||||
*/
|
||||
|
||||
/* The minimum requirement of xorriso towards the libisoburn header
|
||||
at compile time is defined in xorriso/xorrisoburn.h
|
||||
xorriso_libisoburn_req_major
|
||||
xorriso_libisoburn_req_minor
|
||||
xorriso_libisoburn_req_micro
|
||||
It gets compared against the version macros in libburn/libburn.h :
|
||||
isoburn_header_version_major
|
||||
isoburn_header_version_minor
|
||||
isoburn_header_version_micro
|
||||
If the header is too old then the following code shall cause failure of
|
||||
cdrskin compilation rather than to allow production of a program with
|
||||
unpredictable bugs or memory corruption.
|
||||
The compiler messages supposed to appear in this case are:
|
||||
error: 'LIBISOBURN_MISCONFIGURATION' undeclared (first use in this function)
|
||||
error: 'INTENTIONAL_ABORT_OF_COMPILATION__HEADERFILE_libisoburn_dot_h_TOO_OLD__SEE_xorrisoburn_dot_c' undeclared (first use in this function)
|
||||
error: 'LIBISOBURN_MISCONFIGURATION_' undeclared (first use in this function)
|
||||
*/
|
||||
/* The indendation is an advise of man gcc to help old compilers ignoring */
|
||||
#if xorriso_libisoburn_req_major > isoburn_header_version_major
|
||||
#define Isoburn_libisoburn_dot_h_too_olD 1
|
||||
#endif
|
||||
#if xorriso_libisoburn_req_major == isoburn_header_version_major && xorriso_libisoburn_req_minor > isoburn_header_version_minor
|
||||
#define Isoburn_libisoburn_dot_h_too_olD 1
|
||||
#endif
|
||||
#if xorriso_libisoburn_req_minor == isoburn_header_version_minor && xorriso_libisoburn_req_micro > isoburn_header_version_micro
|
||||
#define Isoburn_libisoburn_dot_h_too_olD 1
|
||||
#endif
|
||||
|
||||
#ifdef Isoburn_libisoburn_dot_h_too_olD
|
||||
LIBISOBURN_MISCONFIGURATION = 0;
|
||||
INTENTIONAL_ABORT_OF_COMPILATION__HEADERFILE_libisoburn_dot_h_TOO_OLD__SEE_xorrisoburn_dot_c = 0;
|
||||
LIBISOBURN_MISCONFIGURATION_ = 0;
|
||||
#endif
|
||||
|
||||
/* End of ugly compile time test (scroll up for explanation) */
|
||||
|
||||
reason[0]= 0;
|
||||
ret= isoburn_initialize(reason, 0);
|
||||
if(ret==0) {
|
||||
sprintf(xorriso->info_text, "Cannot initialize libraries");
|
||||
if(reason[0])
|
||||
sprintf(xorriso->info_text+strlen(xorriso->info_text),
|
||||
". Reason given:\n%s", reason);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(0);
|
||||
}
|
||||
ret= isoburn_is_compatible(isoburn_header_version_major,
|
||||
isoburn_header_version_minor,
|
||||
isoburn_header_version_micro, 0);
|
||||
if(ret<=0) {
|
||||
isoburn_version(&major, &minor, µ);
|
||||
sprintf(xorriso->info_text,
|
||||
"libisoburn version too old: %d.%d.%d . Need at least: %d.%d.%d .\n",
|
||||
major, minor, micro,
|
||||
isoburn_header_version_major, isoburn_header_version_minor,
|
||||
isoburn_header_version_micro);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
xorriso->libs_are_started= 1;
|
||||
|
||||
queue_sev= "ALL";
|
||||
if(xorriso->library_msg_direct_print) {
|
||||
|
||||
/* >>> need option for controlling this in XorrisO.
|
||||
See also Xorriso_msgs_submit */;
|
||||
|
||||
print_sev= xorriso->report_about_text;
|
||||
} else
|
||||
print_sev= "NEVER";
|
||||
|
||||
iso_set_msgs_severities(queue_sev, print_sev, "libsofs : ");
|
||||
burn_msgs_set_severities(queue_sev, print_sev, "libburn : ");
|
||||
|
||||
/* ??? >>> do we want united queues ? */
|
||||
/* burn_set_messenger(iso_get_messenger()); */
|
||||
|
||||
isoburn_set_msgs_submit(Xorriso_msgs_submit_void, (void *) xorriso,
|
||||
(3<<2) | 128 , 0);
|
||||
|
||||
ret= Xorriso_set_signal_handling(xorriso, 0);
|
||||
if(ret <= 0)
|
||||
return(ret);
|
||||
|
||||
ret = iso_zisofs_get_params(&zisofs_ctrl, 0);
|
||||
if (ret == 1) {
|
||||
xorriso->zisofs_block_size= xorriso->zisofs_block_size_default=
|
||||
(1 << zisofs_ctrl.block_size_log2);
|
||||
xorriso->zlib_level= xorriso->zlib_level_default=
|
||||
zisofs_ctrl.compression_level;
|
||||
}
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(reason[0]) {
|
||||
sprintf(xorriso->info_text, "%s", reason);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "DEBUG", 0);
|
||||
}
|
||||
strcpy(xorriso->info_text, "Using ");
|
||||
strncat(xorriso->info_text, burn_scsi_transport_id(0), 1024);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "DEBUG", 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= global shutdown of libraries */
|
||||
int Xorriso_detach_libraries(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
Xorriso_give_up_drive(xorriso, 3);
|
||||
if(xorriso->in_volset_handle!=NULL) { /* standalone image */
|
||||
iso_image_unref((IsoImage *) xorriso->in_volset_handle);
|
||||
xorriso->in_volset_handle= NULL;
|
||||
Sectorbitmap_destroy(&(xorriso->in_sector_map), 0);
|
||||
Xorriso_destroy_di_array(xorriso, 0);
|
||||
Xorriso_destroy_hln_array(xorriso, 0);
|
||||
}
|
||||
if(flag&1) {
|
||||
if(xorriso->libs_are_started==0)
|
||||
return(0);
|
||||
isoburn_finish();
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= suppress messages below UPDATE
|
||||
bit1= suppress messages below FAILURE
|
||||
*/
|
||||
int Xorriso_set_image_severities(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
char *queue_sev, *print_sev;
|
||||
|
||||
if(flag&2)
|
||||
queue_sev= "FAILURE";
|
||||
else if(flag&1)
|
||||
queue_sev= "UPDATE";
|
||||
else
|
||||
queue_sev= "ALL";
|
||||
if(xorriso->library_msg_direct_print)
|
||||
print_sev= xorriso->report_about_text;
|
||||
else
|
||||
print_sev= "NEVER";
|
||||
iso_set_msgs_severities(queue_sev, print_sev, "libisofs : ");
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0=prepare for a burn run */
|
||||
int Xorriso_set_abort_severity(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, abort_on_number;
|
||||
char *sev_text;
|
||||
static int note_number= -1, failure_number= -1;
|
||||
|
||||
if(note_number==-1)
|
||||
Xorriso__text_to_sev("NOTE", ¬e_number, 0);
|
||||
if(failure_number==-1)
|
||||
Xorriso__text_to_sev("FAILURE", &failure_number, 0);
|
||||
sev_text= xorriso->abort_on_text;
|
||||
ret= Xorriso__text_to_sev(xorriso->abort_on_text, &abort_on_number, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(abort_on_number<note_number)
|
||||
sev_text= "NOTE";
|
||||
else if(abort_on_number>failure_number)
|
||||
sev_text= "FAILURE";
|
||||
ret= iso_set_abort_severity(sev_text);
|
||||
return(ret>=0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_report_lib_versions(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int major, minor, micro;
|
||||
int req_major, req_minor, req_micro;
|
||||
|
||||
iso_lib_version(&major, &minor, µ);
|
||||
isoburn_libisofs_req(&req_major, &req_minor, &req_micro);
|
||||
sprintf(xorriso->result_line,
|
||||
"libisofs in use : %d.%d.%d (min. %d.%d.%d)\n",
|
||||
major, minor, micro, req_major, req_minor, req_micro);
|
||||
Xorriso_result(xorriso, 0);
|
||||
burn_version(&major, &minor, µ);
|
||||
isoburn_libburn_req(&req_major, &req_minor, &req_micro);
|
||||
sprintf(xorriso->result_line,
|
||||
"libburn in use : %d.%d.%d (min. %d.%d.%d)\n",
|
||||
major, minor, micro, req_major, req_minor, req_micro);
|
||||
Xorriso_result(xorriso, 0);
|
||||
strcpy(xorriso->result_line, "libburn OS adapter: ");
|
||||
strncat(xorriso->result_line, burn_scsi_transport_id(0), 1024);
|
||||
strcat(xorriso->result_line, "\n");
|
||||
Xorriso_result(xorriso, 0);
|
||||
isoburn_version(&major, &minor, µ);
|
||||
sprintf(xorriso->result_line,
|
||||
"libisoburn in use : %d.%d.%d (min. %d.%d.%d)\n",
|
||||
major, minor, micro,
|
||||
isoburn_header_version_major, isoburn_header_version_minor,
|
||||
isoburn_header_version_micro);
|
||||
Xorriso_result(xorriso, 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__sev_to_text(int severity, char **severity_name,
|
||||
int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= iso_sev_to_text(severity, severity_name);
|
||||
if(ret>0)
|
||||
return(ret);
|
||||
ret= burn_sev_to_text(severity, severity_name, 0);
|
||||
if(ret>0)
|
||||
return(ret);
|
||||
*severity_name= "";
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__text_to_sev(char *severity_name, int *severity_number, int flag)
|
||||
{
|
||||
int ret= 1;
|
||||
|
||||
ret= iso_text_to_sev(severity_name, severity_number);
|
||||
if(ret>0)
|
||||
return(ret);
|
||||
ret= burn_text_to_sev(severity_name, severity_number, 0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= report libisofs error text
|
||||
bit1= victim is disk_path
|
||||
bit2= do not inquire libisofs, report msg_text and min_severity
|
||||
*/
|
||||
int Xorriso_report_iso_error(struct XorrisO *xorriso, char *victim,
|
||||
int iso_error_code, char msg_text[], int os_errno,
|
||||
char min_severity[], int flag)
|
||||
{
|
||||
int error_code, iso_sev, min_sev, ret;
|
||||
char *sev_text_pt, *msg_text_pt= NULL;
|
||||
char sfe[6*SfileadrL];
|
||||
static int sorry_sev= -1;
|
||||
|
||||
if(sorry_sev<0)
|
||||
Xorriso__text_to_sev("SORRY", &sorry_sev, 0);
|
||||
|
||||
if(flag&4) {
|
||||
error_code= 0x00050000;
|
||||
Xorriso__text_to_sev(min_severity, &iso_sev, 0);
|
||||
} else {
|
||||
error_code= iso_error_get_code(iso_error_code);
|
||||
if(error_code < 0x00030000 || error_code >= 0x00040000)
|
||||
error_code= (error_code & 0xffff) | 0x00050000;
|
||||
if(flag&1)
|
||||
msg_text_pt= (char *) iso_error_to_msg(iso_error_code);
|
||||
iso_sev= iso_error_get_severity(iso_error_code);
|
||||
}
|
||||
if(msg_text_pt==NULL)
|
||||
msg_text_pt= msg_text;
|
||||
|
||||
if(iso_sev >= sorry_sev && (flag & 2) && victim[0])
|
||||
Xorriso_msgs_submit(xorriso, 0, victim, 0, "ERRFILE", 0);
|
||||
sev_text_pt= min_severity;
|
||||
Xorriso__text_to_sev(min_severity, &min_sev, 0);
|
||||
if(min_sev < iso_sev && !(flag&4))
|
||||
Xorriso__sev_to_text(iso_sev, &sev_text_pt, 0);
|
||||
strcpy(sfe, msg_text_pt);
|
||||
if(victim[0]) {
|
||||
strcat(sfe, ": ");
|
||||
Text_shellsafe(victim, sfe+strlen(sfe), 0);
|
||||
}
|
||||
ret= Xorriso_msgs_submit(xorriso, error_code, sfe, os_errno, sev_text_pt, 4);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_get_local_charset(struct XorrisO *xorriso, char **name, int flag)
|
||||
{
|
||||
(*name)= iso_get_local_charset(0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_set_local_charset(struct XorrisO *xorriso, char *name, int flag)
|
||||
{
|
||||
int ret;
|
||||
char *nl_charset, sfe[5 * SfileadrL];
|
||||
iconv_t iconv_ret= (iconv_t) -1;
|
||||
|
||||
nl_charset= nl_langinfo(CODESET);
|
||||
if(name == NULL)
|
||||
name= nl_charset;
|
||||
|
||||
if(name != NULL) {
|
||||
iconv_ret= iconv_open(nl_charset, name);
|
||||
if(iconv_ret == (iconv_t) -1)
|
||||
goto cannot;
|
||||
else
|
||||
iconv_close(iconv_ret);
|
||||
}
|
||||
ret= iso_set_local_charset(name, 0);
|
||||
if(ret <= 0) {
|
||||
cannot:;
|
||||
sprintf(xorriso->info_text,
|
||||
"-local_charset: Cannot assume as local character set: %s",
|
||||
Text_shellsafe(name, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "NOTE", 0);
|
||||
return(0);
|
||||
}
|
||||
sprintf(xorriso->info_text, "Local character set is now assumed as: %s",
|
||||
Text_shellsafe(name, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "NOTE", 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_process_msg_queues(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, error_code= 0, os_errno= 0, count= 0, pass, imgid, tunneled;
|
||||
char severity[80];
|
||||
|
||||
if(!xorriso->libs_are_started)
|
||||
return(1);
|
||||
for(pass= 0; pass< 2; pass++) {
|
||||
while(1) {
|
||||
tunneled= 0;
|
||||
if(pass==0)
|
||||
ret= iso_obtain_msgs("ALL", &error_code, &imgid,
|
||||
xorriso->info_text, severity);
|
||||
else {
|
||||
ret= burn_msgs_obtain("ALL", &error_code, xorriso->info_text, &os_errno,
|
||||
severity);
|
||||
if((error_code>=0x00030000 && error_code<0x00040000) ||
|
||||
(error_code>=0x00050000 && error_code<0x00060000))
|
||||
tunneled= -1; /* "libisofs:" */
|
||||
else if(error_code>=0x00060000 && error_code<0x00070000)
|
||||
tunneled= 1; /* "libisoburn:" */
|
||||
}
|
||||
if(ret<=0)
|
||||
break;
|
||||
|
||||
/* <<< tunneled MISHAP from libisoburn through libburn
|
||||
or well known error codes of MISHAP events
|
||||
With libburn-0.4.4 this is not necessary */
|
||||
if(error_code==0x5ff73 || error_code==0x3ff73 ||
|
||||
error_code==0x3feb9 || error_code==0x3feb2)
|
||||
strcpy(severity, "MISHAP");
|
||||
else if(error_code==0x51001)
|
||||
strcpy(severity, "ERRFILE");
|
||||
|
||||
Xorriso_msgs_submit(xorriso, error_code, xorriso->info_text, os_errno,
|
||||
severity, ((pass+tunneled)+1)<<2);
|
||||
count++;
|
||||
}
|
||||
}
|
||||
if(xorriso->library_msg_direct_print && count>0) {
|
||||
sprintf(xorriso->info_text," (%d library messages repeated by xorriso)\n",
|
||||
count);
|
||||
Xorriso_info(xorriso, 0);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_md5_start(struct XorrisO *xorriso, void **ctx, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= iso_md5_start(ctx);
|
||||
if(ret == 1)
|
||||
return(1);
|
||||
Xorriso_no_malloc_memory(xorriso, NULL, 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_md5_compute(struct XorrisO *xorriso, void *ctx,
|
||||
char *data, int datalen, int flag)
|
||||
{
|
||||
iso_md5_compute(ctx, data, datalen);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_md5_end(struct XorrisO *xorriso, void **ctx, char md5[16],
|
||||
int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= iso_md5_end(ctx, md5);
|
||||
Xorriso_process_msg_queues(xorriso,0);
|
||||
if(ret <= 0)
|
||||
return(0);
|
||||
return(1);
|
||||
}
|
||||
|
78
xorriso/lib_mgt.h
Normal file
78
xorriso/lib_mgt.h
Normal file
@ -0,0 +1,78 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which manage the relation
|
||||
between xorriso and the libraries: libburn, libisofs, and libisoburn.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_x_includeD
|
||||
#define Xorriso_pvt_x_includeD yes
|
||||
|
||||
|
||||
#ifndef Xorriso_standalonE
|
||||
|
||||
/* The library which does the ISO 9660 / RockRidge manipulations */
|
||||
#include <libisofs/libisofs.h>
|
||||
|
||||
/* The library which does MMC optical drive operations */
|
||||
#include <libburn/libburn.h>
|
||||
|
||||
/* The library which enhances overwriteable media with ISO 9660 multi-session
|
||||
capabilities via the method invented by Andy Polyakov for growisofs */
|
||||
#include <libisoburn/libisoburn.h>
|
||||
|
||||
/* The official xorriso options API. "No shortcuts" */
|
||||
#include "xorriso.h"
|
||||
|
||||
/* The inner description of XorrisO */
|
||||
#include "xorriso_private.h"
|
||||
|
||||
/* The inner isofs- and burn-library interface */
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
#else /* ! Xorriso_standalonE */
|
||||
|
||||
#include "../libisofs/libisofs.h"
|
||||
#include "../libburn/libburn.h"
|
||||
#include "../libisoburn/libisoburn.h"
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
#endif /* Xorriso_standalonE */
|
||||
|
||||
|
||||
int Xorriso_abort(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
|
||||
/* @param flag bit0= asynchronous handling (else catch thread, wait, and exit)
|
||||
*/
|
||||
int Xorriso_set_signal_handling(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* @param flag bit0= suppress messages below UPDATE
|
||||
bit1= suppress messages below FAILURE
|
||||
*/
|
||||
int Xorriso_set_image_severities(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso__sev_to_text(int severity, char **severity_name,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= report libisofs error text
|
||||
bit1= victim is disk_path
|
||||
bit2= do not inquire libisofs, report msg_text and min_severity
|
||||
*/
|
||||
int Xorriso_report_iso_error(struct XorrisO *xorriso, char *victim,
|
||||
int iso_error_code, char msg_text[], int os_errno,
|
||||
char min_severity[], int flag);
|
||||
|
||||
int Xorriso_process_msg_queues(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_x_includeD */
|
||||
|
@ -134,10 +134,58 @@ xorriso/convert_man_to_html.sh
|
||||
|
||||
create_dir "$lone_dir"/xorriso
|
||||
copy_files \
|
||||
xorriso/xorrisoburn.[ch] \
|
||||
xorriso/xorriso.[ch] \
|
||||
xorriso/xorriso.h \
|
||||
xorriso/xorriso_private.h \
|
||||
xorriso/sfile.h \
|
||||
xorriso/sfile.c \
|
||||
xorriso/aux_objects.h \
|
||||
xorriso/aux_objects.c \
|
||||
xorriso/findjob.h \
|
||||
xorriso/findjob.c \
|
||||
xorriso/check_media.h \
|
||||
xorriso/check_media.c \
|
||||
xorriso/misc_funct.h \
|
||||
xorriso/misc_funct.c \
|
||||
xorriso/text_io.h \
|
||||
xorriso/text_io.c \
|
||||
xorriso/match.h \
|
||||
xorriso/match.c \
|
||||
xorriso/emulators.h \
|
||||
xorriso/emulators.c \
|
||||
xorriso/disk_ops.h \
|
||||
xorriso/disk_ops.c \
|
||||
xorriso/cmp_update.h \
|
||||
xorriso/cmp_update.c \
|
||||
xorriso/parse_exec.h \
|
||||
xorriso/parse_exec.c \
|
||||
xorriso/opts_a_c.c \
|
||||
xorriso/opts_d_h.c \
|
||||
xorriso/opts_i_o.c \
|
||||
xorriso/opts_p_z.c \
|
||||
\
|
||||
xorriso/xorrisoburn.h \
|
||||
xorriso/base_obj.h \
|
||||
xorriso/base_obj.c \
|
||||
xorriso/lib_mgt.h \
|
||||
xorriso/lib_mgt.c \
|
||||
xorriso/sort_cmp.h \
|
||||
xorriso/sort_cmp.c \
|
||||
xorriso/drive_mgt.h \
|
||||
xorriso/drive_mgt.c \
|
||||
xorriso/iso_img.h \
|
||||
xorriso/iso_img.c \
|
||||
xorriso/iso_tree.h \
|
||||
xorriso/iso_tree.c \
|
||||
xorriso/iso_manip.h \
|
||||
xorriso/iso_manip.c \
|
||||
xorriso/write_run.h \
|
||||
xorriso/write_run.c \
|
||||
xorriso/read_run.h \
|
||||
xorriso/read_run.c \
|
||||
xorriso/filters.h \
|
||||
xorriso/filters.c \
|
||||
\
|
||||
xorriso/xorriso_main.c \
|
||||
xorriso/xorriso_timestamp.h \
|
||||
\
|
||||
xorriso/changelog.txt \
|
||||
@ -237,7 +285,7 @@ then
|
||||
# patch xorriso/xorriso.c to be GNU xorriso
|
||||
sed -e's/define Xorriso_libburnia_xorrisO/define Xorriso_GNU_xorrisO/' \
|
||||
-e's/This may be changed to Xorriso_GNU_xorrisO in order to c/C/' \
|
||||
<xorriso/xorriso.c >"$lone_dir"/xorriso/xorriso.c
|
||||
<xorriso/xorriso_main.c >"$lone_dir"/xorriso/xorriso_main.c
|
||||
|
||||
else
|
||||
|
||||
|
755
xorriso/match.c
Normal file
755
xorriso/match.c
Normal file
@ -0,0 +1,755 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains the implementation of functions for pattern matching.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "xorriso.h"
|
||||
#include "xorriso_private.h"
|
||||
#include "xorrisoburn.h"
|
||||
|
||||
|
||||
/* @param flag bit0= do not augment relative structured search by xorriso->wdi
|
||||
bit1= return 2 if bonked at start point by ..
|
||||
(caller then aborts or retries without bit0)
|
||||
bit2= eventually prepend wdx rather than wdi
|
||||
@return <=0 error, 1= ok, 2= with bit1: relative pattern exceeds start point
|
||||
*/
|
||||
int Xorriso_prepare_regex(struct XorrisO *xorriso, char *adr, int flag)
|
||||
{
|
||||
int l,ret,i,count,bonked= 0,is_constant,is_still_relative= 0;
|
||||
char *cpt,*npt,adr_part[2*SfileadrL],absolute_adr[2*SfileadrL],*adr_start,*wd;
|
||||
|
||||
if(flag&4)
|
||||
wd= xorriso->wdx;
|
||||
else
|
||||
wd= xorriso->wdi;
|
||||
|
||||
if(xorriso->search_mode>=2 && xorriso->search_mode<=4) {
|
||||
if(xorriso->search_mode==3 || xorriso->search_mode==4) {
|
||||
l= strlen(adr)+strlen(wd)+1;
|
||||
if(l*2+2>sizeof(xorriso->reg_expr) || l*2+2>sizeof(adr_part)) {
|
||||
sprintf(xorriso->info_text,"Search pattern too long");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
return(0);
|
||||
}
|
||||
}
|
||||
Xorriso_destroy_re(xorriso,0);
|
||||
if(xorriso->structured_search && xorriso->search_mode==3) {
|
||||
if(adr[0]!='/')
|
||||
is_still_relative= 1;
|
||||
if(is_still_relative && !(flag&1)) {
|
||||
/* relative expression : prepend working directory */
|
||||
sprintf(absolute_adr,"%s/%s",wd,adr);
|
||||
adr_start= absolute_adr;
|
||||
xorriso->prepended_wd= 1;
|
||||
is_still_relative= 0;
|
||||
} else
|
||||
adr_start= adr;
|
||||
/* count slashes */;
|
||||
cpt= adr_start;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
for(i= 0;1;i++) {
|
||||
cpt= strchr(cpt,'/');
|
||||
if(cpt==NULL)
|
||||
break;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
}
|
||||
count= i+1;
|
||||
xorriso->re= TSOB_FELD(regex_t,count);
|
||||
if(xorriso->re==NULL)
|
||||
return(-1);
|
||||
xorriso->re_constants= TSOB_FELD(char *,count);
|
||||
if(xorriso->re_constants==NULL)
|
||||
return(-1);
|
||||
for(i= 0;i<count;i++)
|
||||
xorriso->re_constants[i]= NULL;
|
||||
xorriso->re_count= count;
|
||||
xorriso->re_fill= 0;
|
||||
|
||||
/* loop over slash chunks*/;
|
||||
cpt= adr_start;
|
||||
xorriso->re_fill= 0;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
for(i= 0;i<count;i++) {
|
||||
npt= strchr(cpt,'/');
|
||||
if(npt==NULL) {
|
||||
if(strlen(cpt)>=sizeof(adr_part))
|
||||
return(-1);
|
||||
strcpy(adr_part,cpt);
|
||||
} else {
|
||||
if(npt-cpt>=sizeof(adr_part))
|
||||
return(-1);
|
||||
strncpy(adr_part,cpt,npt-cpt);
|
||||
adr_part[npt-cpt]= 0;
|
||||
}
|
||||
|
||||
if(adr_part[0]==0)
|
||||
goto next_adr_part;
|
||||
if(adr_part[0]=='.' && adr_part[1]==0 &&
|
||||
(xorriso->re_fill>0 || i<count-1))
|
||||
goto next_adr_part;
|
||||
if(adr_part[0]=='.' && adr_part[1]=='.' && adr_part[2]==0) {
|
||||
/* delete previous part */
|
||||
if(xorriso->re_fill <= 0) {
|
||||
bonked= 1;
|
||||
goto next_adr_part;
|
||||
}
|
||||
if(xorriso->re_constants[xorriso->re_fill-1]!=NULL) {
|
||||
free(xorriso->re_constants[xorriso->re_fill-1]);
|
||||
xorriso->re_constants[xorriso->re_fill-1]= NULL;
|
||||
} else
|
||||
regfree(&(xorriso->re[xorriso->re_fill-1]));
|
||||
(xorriso->re_fill)--;
|
||||
goto next_adr_part;
|
||||
}
|
||||
if(strcmp(adr_part,"*")==0) {
|
||||
adr_part[0]= 0;
|
||||
ret= 2;
|
||||
} else
|
||||
ret= Xorriso__bourne_to_reg(adr_part,xorriso->reg_expr,0);
|
||||
if(ret==2) {
|
||||
if(Sregex_string(&(xorriso->re_constants[xorriso->re_fill]),adr_part,0)
|
||||
<=0)
|
||||
return(-1);
|
||||
} else {
|
||||
if(regcomp(&(xorriso->re[xorriso->re_fill]),xorriso->reg_expr,0)!=0)
|
||||
goto cannot_compile;
|
||||
}
|
||||
xorriso->re_fill++;
|
||||
next_adr_part:;
|
||||
if(i==count-1)
|
||||
break;
|
||||
cpt= npt+1;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
}
|
||||
if(bonked) {
|
||||
if(flag&2)
|
||||
return(2);
|
||||
sprintf(xorriso->info_text, "Your '..' bonked at the %s directory.",
|
||||
is_still_relative ? "working" : "root");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE",0);
|
||||
return(0);
|
||||
}
|
||||
|
||||
Xorriso__bourne_to_reg(adr_start,xorriso->reg_expr,0); /* just for show */
|
||||
|
||||
} else {
|
||||
is_constant= 0;
|
||||
if(strcmp(adr,"*")==0 || adr[0]==0) {
|
||||
is_constant= 1;
|
||||
} else if(xorriso->search_mode==3 || xorriso->search_mode==4) {
|
||||
ret= Xorriso__bourne_to_reg(adr,xorriso->reg_expr,0);
|
||||
is_constant= (ret==2);
|
||||
} else {
|
||||
if(strlen(adr)>=sizeof(xorriso->reg_expr))
|
||||
return(-1);
|
||||
strcpy(xorriso->reg_expr,adr);
|
||||
}
|
||||
xorriso->re_count= 0; /* tells matcher that this is not structured */
|
||||
xorriso->re_constants= TSOB_FELD(char *,1);
|
||||
if(xorriso->re_constants==NULL)
|
||||
return(-1);
|
||||
xorriso->re_constants[0]= NULL;
|
||||
if(is_constant) {
|
||||
if(strcmp(adr,"*")==0) {
|
||||
if(Sregex_string(&(xorriso->re_constants[0]),"",0)<=0)
|
||||
return(-1);
|
||||
} else {
|
||||
if(Sregex_string(&(xorriso->re_constants[0]),adr,0)<=0)
|
||||
return(-1);
|
||||
}
|
||||
xorriso->re_fill= 1;
|
||||
} else {
|
||||
xorriso->re= TSOB_FELD(regex_t,1);
|
||||
if(xorriso->re==NULL)
|
||||
return(-1);
|
||||
if(regcomp(&(xorriso->re[0]),xorriso->reg_expr,0)!=0) {
|
||||
cannot_compile:;
|
||||
sprintf(xorriso->info_text, "Cannot compile regular expression : %s",
|
||||
xorriso->reg_expr);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE",0);
|
||||
return(0);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not shortcut last component of to_match
|
||||
bit1= consider match if regex matches parent of path
|
||||
bit2= retry beginning at failed last component
|
||||
|
||||
@return 0=match , else no match
|
||||
*/
|
||||
int Xorriso_regexec(struct XorrisO *xorriso, char *to_match, int *failed_at,
|
||||
int flag)
|
||||
{
|
||||
int ret,i,re_start= 0,reg_nomatch= -1;
|
||||
char *cpt,*npt,adr_part[SfileadrL],*mpt;
|
||||
|
||||
reg_nomatch= REG_NOMATCH;
|
||||
|
||||
*failed_at= 0;
|
||||
if(!(xorriso->structured_search && xorriso->re_count>0)) {
|
||||
if(xorriso->re_constants!=NULL)
|
||||
if(xorriso->re_constants[0]!=NULL) {
|
||||
if(xorriso->re_constants[0][0]==0)
|
||||
return(0);
|
||||
if(strcmp(xorriso->re_constants[0],to_match)!=0)
|
||||
return(reg_nomatch);
|
||||
return(0);
|
||||
}
|
||||
ret= regexec(&(xorriso->re[0]),to_match,1,xorriso->match,0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
cpt= to_match;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
if(flag&4)
|
||||
re_start= xorriso->re_failed_at;
|
||||
if(re_start<0)
|
||||
re_start= 0;
|
||||
for(i= re_start;i<xorriso->re_fill;i++) {
|
||||
*failed_at= i;
|
||||
npt= strchr(cpt,'/');
|
||||
if(npt==NULL) {
|
||||
if(i<xorriso->re_fill-1 && !(flag&1))
|
||||
return(reg_nomatch); /* this must be the last expression part */
|
||||
mpt= cpt;
|
||||
} else {
|
||||
strncpy(adr_part,cpt,npt-cpt);
|
||||
adr_part[npt-cpt]= 0;
|
||||
mpt= adr_part;
|
||||
}
|
||||
if(xorriso->re_constants[i]!=NULL) {
|
||||
if(xorriso->re_constants[i][0]!=0) /* empty constant matches anything */
|
||||
if(strcmp(xorriso->re_constants[i],mpt)!=0)
|
||||
return(reg_nomatch);
|
||||
} else {
|
||||
ret= regexec(&(xorriso->re[i]),mpt,1,xorriso->match,0);
|
||||
if(ret!=0)
|
||||
return(ret);
|
||||
}
|
||||
if(npt==NULL) {
|
||||
if(i>=xorriso->re_fill-1)
|
||||
return(0); /* MATCH */
|
||||
*failed_at= i+1;
|
||||
return(reg_nomatch);
|
||||
}
|
||||
cpt= npt+1;
|
||||
while(*cpt=='/')
|
||||
cpt++;
|
||||
}
|
||||
*failed_at= xorriso->re_fill;
|
||||
if(flag & 2)
|
||||
return(0); /* MATCH */
|
||||
return(reg_nomatch);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_is_in_patternlist(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, char *path,
|
||||
int flag)
|
||||
{
|
||||
int ret, failed_at, i= 0;
|
||||
struct Xorriso_lsT *s;
|
||||
|
||||
xorriso->search_mode= 3;
|
||||
xorriso->structured_search= 1;
|
||||
|
||||
for(s= patternlist; s != NULL; s= Xorriso_lst_get_next(s, 0)) {
|
||||
ret= Xorriso_prepare_regex(xorriso, Xorriso_lst_get_text(s, 0), 0);
|
||||
if(ret <= 0)
|
||||
return(-1);
|
||||
/* Match path or parent of path */
|
||||
ret= Xorriso_regexec(xorriso, path, &failed_at, 2);
|
||||
if(ret == 0)
|
||||
return(i + 1);
|
||||
i++;
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
char *Xorriso_get_pattern(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, int index, int flag)
|
||||
{
|
||||
int i= 0;
|
||||
struct Xorriso_lsT *s;
|
||||
|
||||
for(s= patternlist; s != NULL; s= Xorriso_lst_get_next(s, 0)) {
|
||||
if(i == index)
|
||||
return(Xorriso_lst_get_text(s, 0));
|
||||
i++;
|
||||
}
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* @param flag bit2= this is a disk_pattern
|
||||
@return <=0 failure , 1 pattern ok , 2 pattern needed prepended wd */
|
||||
int Xorriso_prepare_expansion_pattern(struct XorrisO *xorriso, char *pattern,
|
||||
int flag)
|
||||
{
|
||||
int ret, prepwd= 0;
|
||||
|
||||
ret= Xorriso_prepare_regex(xorriso, pattern, 1|2|(flag&4));
|
||||
if(ret==2) {
|
||||
ret= Xorriso_prepare_regex(xorriso, pattern, flag&4);
|
||||
prepwd= 1;
|
||||
}
|
||||
if(ret<=0) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot compile pattern to regular expression: %s", pattern);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
return(0);
|
||||
}
|
||||
return(1+prepwd);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= count results rather than storing them
|
||||
bit1= unexpected change of number is a FATAL event
|
||||
@return <=0 error , 1 is root (end processing) ,
|
||||
2 is not root (go on processing)
|
||||
*/
|
||||
int Xorriso_check_for_root_pattern(struct XorrisO *xorriso,
|
||||
int *filec, char **filev, int count_limit, off_t *mem, int flag)
|
||||
{
|
||||
if(xorriso->re_fill!=0)
|
||||
return(2);
|
||||
/* This is the empty pattern representing root */
|
||||
if(flag&1) {
|
||||
(*filec)++;
|
||||
(*mem)+= 8;
|
||||
} else {
|
||||
if(*filec >= count_limit) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Number of matching files changed unexpectedly (> %d)",
|
||||
count_limit);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
(flag&2 ? "FATAL" : "WARNING"), 0);
|
||||
return(flag&2 ? -1 : 0);
|
||||
}
|
||||
filev[*filec]= strdup("/");
|
||||
if(filev[*filec]==NULL) {
|
||||
Xorriso_no_pattern_memory(xorriso, (off_t) 2, 0);
|
||||
return(-1);
|
||||
}
|
||||
(*filec)++;
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= count result rather than storing it
|
||||
bit1= unexpected change of number is a FATAL event
|
||||
*/
|
||||
int Xorriso_register_matched_adr(struct XorrisO *xorriso,
|
||||
char *adr, int count_limit,
|
||||
int *filec, char **filev, off_t *mem, int flag)
|
||||
{
|
||||
int l;
|
||||
|
||||
if(flag&1) {
|
||||
(*filec)++;
|
||||
l= strlen(adr)+1;
|
||||
(*mem)+= sizeof(char *)+l;
|
||||
if(l % sizeof(char *))
|
||||
(*mem)+= sizeof(char *)-(l % sizeof(char *));
|
||||
} else {
|
||||
if(*filec >= count_limit) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Number of matching files changed unexpectedly (> %d)",
|
||||
count_limit);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
(flag&2 ? "FATAL" : "WARNING"), 0);
|
||||
return(flag&2 ? -1 : 0);
|
||||
}
|
||||
filev[*filec]= strdup(adr);
|
||||
if(filev[*filec]==NULL) {
|
||||
Xorriso_no_pattern_memory(xorriso, (off_t) (strlen(adr)+1), 0);
|
||||
return(-1);
|
||||
}
|
||||
(*filec)++;
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= count results rather than storing them
|
||||
bit1= this is a recursion
|
||||
bit2= prepend wd (automatically done if wd[0]!=0)
|
||||
@return <=0 error , 1 ok , 2 could not open directory
|
||||
*/
|
||||
int Xorriso_obtain_pattern_files_x(
|
||||
struct XorrisO *xorriso, char *wd, char *dir_adr,
|
||||
int *filec, char **filev, int count_limit, off_t *mem,
|
||||
int *dive_count, int flag)
|
||||
{
|
||||
int ret, failed_at, follow_mount, follow_links;
|
||||
struct DirseQ *dirseq= NULL;
|
||||
struct stat stbuf;
|
||||
dev_t dir_dev;
|
||||
char *path;
|
||||
char *adr= NULL, *name= NULL, *path_data= NULL;
|
||||
|
||||
adr= malloc(SfileadrL);
|
||||
name= malloc(SfileadrL);
|
||||
path_data= malloc(SfileadrL);
|
||||
if(adr==NULL || name==NULL || path_data==NULL) {
|
||||
Xorriso_no_malloc_memory(xorriso, &adr, 0);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
follow_mount= (xorriso->do_follow_mount || xorriso->do_follow_pattern);
|
||||
follow_links= (xorriso->do_follow_links || xorriso->do_follow_pattern);
|
||||
if(!(flag&2))
|
||||
*dive_count= 0;
|
||||
else
|
||||
(*dive_count)++;
|
||||
|
||||
ret= Xorriso_check_for_root_pattern(xorriso, filec, filev, count_limit,
|
||||
mem, flag&1);
|
||||
if(ret!=2)
|
||||
goto ex;
|
||||
|
||||
if(lstat(dir_adr, &stbuf)==-1)
|
||||
{ret= 2; goto ex;}
|
||||
dir_dev= stbuf.st_dev;
|
||||
if(S_ISLNK(stbuf.st_mode)) {
|
||||
if(stat(dir_adr, &stbuf)==-1)
|
||||
{ret= 2; goto ex;}
|
||||
if(dir_dev != stbuf.st_dev && !follow_mount)
|
||||
{ret= 2; goto ex;}
|
||||
}
|
||||
ret= Dirseq_new(&dirseq, dir_adr, 1);
|
||||
if(ret<0) {
|
||||
sprintf(xorriso->info_text, "Cannot obtain disk directory iterator");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
if(ret==0)
|
||||
{ret= 2; goto ex;}
|
||||
|
||||
while(1) {
|
||||
ret= Dirseq_next_adr(dirseq,name,0);
|
||||
if(ret==0)
|
||||
break;
|
||||
if(ret<0) {
|
||||
sprintf(xorriso->info_text,"Failed to obtain next directory entry");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
|
||||
ret= Xorriso_make_abs_adr(xorriso, wd, name, adr, flag&4);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
|
||||
ret= Xorriso_regexec(xorriso, adr, &failed_at, 1);
|
||||
if(ret>0) { /* no match */
|
||||
if(failed_at <= *dive_count) /* no hope for a match */
|
||||
continue;
|
||||
path= adr;
|
||||
if(adr[0]!='/') {
|
||||
path= path_data;
|
||||
ret= Xorriso_make_abs_adr(xorriso, xorriso->wdx, adr, path, 1|4);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
}
|
||||
|
||||
if(follow_links)
|
||||
ret= stat(path,&stbuf);
|
||||
else
|
||||
ret= lstat(path,&stbuf);
|
||||
if(ret==-1)
|
||||
continue;
|
||||
if(!S_ISDIR(stbuf.st_mode))
|
||||
continue;
|
||||
if(dir_dev != stbuf.st_dev && !follow_mount)
|
||||
continue;
|
||||
|
||||
/* dive deeper */
|
||||
ret= Xorriso_obtain_pattern_files_x(xorriso, adr, path,
|
||||
filec, filev, count_limit, mem, dive_count, flag|2);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
} else {
|
||||
ret= Xorriso_register_matched_adr(xorriso, adr, count_limit,
|
||||
filec, filev, mem, flag&1);
|
||||
if(ret<0)
|
||||
goto ex;
|
||||
if(ret==0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(adr!=NULL)
|
||||
free(adr);
|
||||
if(name!=NULL)
|
||||
free(name);
|
||||
if(path_data!=NULL)
|
||||
free(path_data);
|
||||
Dirseq_destroy(&dirseq,0);
|
||||
if(flag&2)
|
||||
(*dive_count)--;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_eval_nonmatch(struct XorrisO *xorriso, char *pattern,
|
||||
int *nonconst_mismatches, off_t *mem, int flag)
|
||||
{
|
||||
int k,l;
|
||||
|
||||
/* Is this a constant pattern ? */
|
||||
for(k= 0; k<xorriso->re_fill; k++) {
|
||||
if(xorriso->re_constants[k]==NULL)
|
||||
break;
|
||||
if(xorriso->re_constants[k][0]==0)
|
||||
break;
|
||||
}
|
||||
if(k<xorriso->re_fill)
|
||||
(*nonconst_mismatches)++; /* it is not */
|
||||
|
||||
l= strlen(pattern)+1;
|
||||
(*mem)+= sizeof(char *)+l;
|
||||
if(l % sizeof(char *))
|
||||
(*mem)+= sizeof(char *)-(l % sizeof(char *));
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= a match count !=1 is a SORRY event
|
||||
bit1= a match count !=1 is a FAILURE event
|
||||
*/
|
||||
int Xorriso_check_matchcount(struct XorrisO *xorriso,
|
||||
int count, int nonconst_mismatches, int num_patterns,
|
||||
char **patterns, int flag)
|
||||
{
|
||||
char sfe[5*SfileadrL];
|
||||
|
||||
if((flag&1) && (count!=1 || nonconst_mismatches)){
|
||||
if(count-nonconst_mismatches>0)
|
||||
sprintf(xorriso->info_text,
|
||||
"Pattern match with more than one file object");
|
||||
else
|
||||
sprintf(xorriso->info_text, "No pattern match with any file object");
|
||||
if(num_patterns==1)
|
||||
sprintf(xorriso->info_text+strlen(xorriso->info_text), ": %s",
|
||||
Text_shellsafe(patterns[0], sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0,
|
||||
(flag&2 ? "FAILURE" : "SORRY"), 0);
|
||||
return(0);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_no_pattern_memory(struct XorrisO *xorriso, off_t mem, int flag)
|
||||
{
|
||||
char mem_text[80];
|
||||
|
||||
Sfile_scale((double) mem, mem_text,5,1e4,1);
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot allocate enough memory (%s) for pattern expansion",
|
||||
mem_text);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_alloc_pattern_mem(struct XorrisO *xorriso, off_t mem,
|
||||
int count, char ***filev, int flag)
|
||||
{
|
||||
char mem_text[80], limit_text[80];
|
||||
|
||||
Sfile_scale((double) mem, mem_text,5,1e4,0);
|
||||
sprintf(xorriso->info_text,
|
||||
"Temporary memory needed for pattern expansion : %s", mem_text);
|
||||
if(!(flag&1))
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "DEBUG", 0);
|
||||
if(mem > xorriso->temp_mem_limit) {
|
||||
Sfile_scale((double) xorriso->temp_mem_limit, limit_text,5,1e4,1);
|
||||
sprintf(xorriso->info_text,
|
||||
"List of matching file addresses exceeds -temp_mem_limit (%s > %s)",
|
||||
mem_text, limit_text);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
return(0);
|
||||
}
|
||||
|
||||
(*filev)= (char **) calloc(count, sizeof(char *));
|
||||
if(*filev==NULL) {
|
||||
Xorriso_no_pattern_memory(xorriso, mem, 0);
|
||||
return(-1);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= a match count !=1 is a FAILURE event
|
||||
bit1= with bit0 tolerate 0 matches if pattern is a constant
|
||||
*/
|
||||
int Xorriso_expand_disk_pattern(struct XorrisO *xorriso,
|
||||
int num_patterns, char **patterns, int extra_filec,
|
||||
int *filec, char ***filev, off_t *mem, int flag)
|
||||
{
|
||||
int ret, count= 0, abs_adr= 0, i, was_count, was_filec;
|
||||
int nonconst_mismatches= 0, dive_count= 0;
|
||||
char sfe[5*SfileadrL], dir_adr[SfileadrL];
|
||||
|
||||
*filec= 0;
|
||||
*filev= NULL;
|
||||
|
||||
xorriso->search_mode= 3;
|
||||
xorriso->structured_search= 1;
|
||||
|
||||
for(i= 0; i<num_patterns; i++) {
|
||||
|
||||
ret= Xorriso_prepare_expansion_pattern(xorriso, patterns[i], 4);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(ret==2)
|
||||
abs_adr= 4;
|
||||
|
||||
if(patterns[i][0]=='/' || abs_adr) {
|
||||
strcpy(dir_adr, "/");
|
||||
abs_adr= 4;
|
||||
} else {
|
||||
strcpy(dir_adr, xorriso->wdx);
|
||||
if(dir_adr[0]==0)
|
||||
strcpy(dir_adr, "/");
|
||||
ret= Sfile_type(dir_adr, 1|4);
|
||||
if(ret!=2) {
|
||||
Xorriso_msgs_submit(xorriso, 0, dir_adr, 0, "ERRFILE", 0);
|
||||
sprintf(xorriso->info_text,
|
||||
"Address set by -cdx is not a directory: %s",
|
||||
Text_shellsafe(dir_adr, sfe, 0));
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
}
|
||||
|
||||
/* count the matches */
|
||||
was_count= count;
|
||||
ret= Xorriso_obtain_pattern_files_x(xorriso, "", dir_adr, &count, NULL, 0,
|
||||
mem, &dive_count, 1 | abs_adr);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
if(was_count==count && strcmp(patterns[i],"*")!=0 && (flag&3)!=1) {
|
||||
count++;
|
||||
ret= Xorriso_eval_nonmatch(xorriso, patterns[i],
|
||||
&nonconst_mismatches, mem, 0);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
|
||||
ret= Xorriso_check_matchcount(xorriso, count, nonconst_mismatches,
|
||||
num_patterns, patterns, (flag&1)|2);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
|
||||
count+= extra_filec;
|
||||
mem+= extra_filec*sizeof(char *);
|
||||
|
||||
if(count<=0)
|
||||
{ret= 0; goto ex;}
|
||||
|
||||
ret= Xorriso_alloc_pattern_mem(xorriso, *mem, count, filev, 0);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
|
||||
/* now store addresses */
|
||||
for(i= 0; i<num_patterns; i++) {
|
||||
|
||||
ret= Xorriso_prepare_expansion_pattern(xorriso, patterns[i], 4);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
|
||||
if(patterns[i][0]=='/' || abs_adr) {
|
||||
strcpy(dir_adr, "/");
|
||||
abs_adr= 4;
|
||||
} else {
|
||||
strcpy(dir_adr, xorriso->wdx);
|
||||
if(dir_adr[0]==0)
|
||||
strcpy(dir_adr, "/");
|
||||
}
|
||||
|
||||
was_filec= *filec;
|
||||
ret= Xorriso_obtain_pattern_files_x(xorriso, "", dir_adr, filec, *filev,
|
||||
count, mem, &dive_count, abs_adr);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
|
||||
if(was_filec == *filec && strcmp(patterns[i],"*")!=0) {
|
||||
(*filev)[*filec]= strdup(patterns[i]);
|
||||
if((*filev)[*filec]==NULL) {
|
||||
(*mem)= strlen(patterns[i])+1;
|
||||
Xorriso_no_pattern_memory(xorriso, *mem, 0);
|
||||
ret= -1; goto ex;
|
||||
}
|
||||
(*filec)++;
|
||||
}
|
||||
}
|
||||
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(ret<=0) {
|
||||
if(filev!=NULL)
|
||||
Sfile_destroy_argv(&count, filev, 0);
|
||||
*filec= 0;
|
||||
}
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= command without pattern capability
|
||||
bit1= disk_pattern rather than iso_rr_pattern
|
||||
*/
|
||||
int Xorriso_warn_of_wildcards(struct XorrisO *xorriso, char *path, int flag)
|
||||
{
|
||||
if(strchr(path,'*')!=NULL || strchr(path,'?')!=NULL ||
|
||||
strchr(path,'[')!=NULL) {
|
||||
if(flag&1) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Pattern expansion of wildcards \"*?[\" does not apply to this command");
|
||||
} else {
|
||||
sprintf(xorriso->info_text,
|
||||
"Pattern expansion of wildcards \"*?[\" is disabled by command %s",
|
||||
(flag&2) ? "-disk_pattern or -pathspecs" : "-iso_rr_pattern");
|
||||
}
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "WARNING", 0);
|
||||
sprintf(xorriso->info_text,"Pattern seen: %s\n", path);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "WARNING", 0);
|
||||
return(1);
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
74
xorriso/match.h
Normal file
74
xorriso/match.h
Normal file
@ -0,0 +1,74 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains the implementation of functions for pattern matching.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_match_includeD
|
||||
#define Xorriso_pvt_match_includeD yes
|
||||
|
||||
|
||||
int Xorriso_prepare_regex(struct XorrisO *xorriso, char *adr, int flag);
|
||||
|
||||
/* @return 0=match , else no match
|
||||
*/
|
||||
int Xorriso_regexec(struct XorrisO *xorriso, char *to_match, int *failed_at,
|
||||
int flag);
|
||||
|
||||
int Xorriso_is_in_patternlist(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, char *path, int flag);
|
||||
|
||||
char *Xorriso_get_pattern(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, int index, int flag);
|
||||
|
||||
int Xorriso_prepare_expansion_pattern(struct XorrisO *xorriso, char *pattern,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= count results rather than storing them
|
||||
@return <=0 error , 1 is root (end processing) ,
|
||||
2 is not root (go on processing)
|
||||
*/
|
||||
int Xorriso_check_for_root_pattern(struct XorrisO *xorriso,
|
||||
int *filec, char **filev, int count_limit, off_t *mem, int flag);
|
||||
|
||||
/* @param flag bit0= count result rather than storing it
|
||||
bit1= unexpected change of number is a FATAL event
|
||||
*/
|
||||
int Xorriso_register_matched_adr(struct XorrisO *xorriso,
|
||||
char *adr, int count_limit,
|
||||
int *filec, char **filev, off_t *mem, int flag);
|
||||
|
||||
int Xorriso_eval_nonmatch(struct XorrisO *xorriso, char *pattern,
|
||||
int *nonconst_mismatches, off_t *mem, int flag);
|
||||
|
||||
/* @param flag bit0= a match count !=1 is a SORRY event
|
||||
*/
|
||||
int Xorriso_check_matchcount(struct XorrisO *xorriso,
|
||||
int count, int nonconst_mismatches, int num_patterns,
|
||||
char **patterns, int flag);
|
||||
|
||||
int Xorriso_no_pattern_memory(struct XorrisO *xorriso, off_t mem, int flag);
|
||||
|
||||
int Xorriso_alloc_pattern_mem(struct XorrisO *xorriso, off_t mem,
|
||||
int count, char ***filev, int flag);
|
||||
|
||||
/* @param flag bit0= command without pattern capability
|
||||
bit1= disk_pattern rather than iso_rr_pattern
|
||||
*/
|
||||
int Xorriso_warn_of_wildcards(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
/* @param flag bit0= a match count !=1 is a FAILURE event
|
||||
bit1= with bit0 tolerate 0 matches if pattern is a constant
|
||||
*/
|
||||
int Xorriso_expand_disk_pattern(struct XorrisO *xorriso,
|
||||
int num_patterns, char **patterns, int extra_filec,
|
||||
int *filec, char ***filev, off_t *mem, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_match_includeD */
|
||||
|
1177
xorriso/misc_funct.c
Normal file
1177
xorriso/misc_funct.c
Normal file
File diff suppressed because it is too large
Load Diff
89
xorriso/misc_funct.h
Normal file
89
xorriso/misc_funct.h
Normal file
@ -0,0 +1,89 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of cellaneous helper functions of xorriso.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_misc_includeD
|
||||
#define Xorriso_pvt_misc_includeD yes
|
||||
|
||||
#include <regex.h>
|
||||
|
||||
|
||||
char *Text_shellsafe(char *in_text, char *out_text, int flag);
|
||||
|
||||
int Sort_argv(int argc, char **argv, int flag);
|
||||
|
||||
/* @param flag bit0= single letters */
|
||||
char *Ftypetxt(mode_t st_mode, int flag);
|
||||
|
||||
/* @param flag bit0=with year and seconds
|
||||
bit1=timestamp format YYYY.MM.DD.hhmmss
|
||||
*/
|
||||
char *Ftimetxt(time_t t, char timetext[40], int flag);
|
||||
|
||||
int System_uname(char **sysname, char **release, char **version,
|
||||
char **machine, int flag);
|
||||
|
||||
/** Convert a text into a number of type double and multiply it by unit code
|
||||
[kmgtpe] (2^10 to 2^60) or [s] (2048). (Also accepts capital letters.)
|
||||
@param text Input like "42", "2k", "3.14m" or "-1g"
|
||||
@param flag Bitfield for control purposes:
|
||||
bit0= return -1 rathern than 0 on failure
|
||||
@return The derived double value
|
||||
*/
|
||||
double Scanf_io_size(char *text, int flag);
|
||||
|
||||
/*
|
||||
@flag bit0= do not initialize *diff_count
|
||||
@return <0 error , 0 = mismatch , 1 = match
|
||||
*/
|
||||
int Compare_text_lines(char *text1, char *text2, int *diff_count, int flag);
|
||||
|
||||
time_t Decode_timestring(char *code, time_t *date, int flag);
|
||||
|
||||
int Decode_ecma119_format(struct tm *erg, char *text, int flag);
|
||||
|
||||
int Wait_for_input(int fd, int microsec, int flag);
|
||||
|
||||
int Fileliste__target_source_limit(char *line, char sep, char **limit_pt,
|
||||
int flag);
|
||||
|
||||
int Hex_to_bin(char *hex,
|
||||
int bin_size, int *bin_count, unsigned char *bin_data, int flag);
|
||||
|
||||
|
||||
/* bit0= append (text!=NULL) */
|
||||
int Sregex_string(char **handle, char *text, int flag);
|
||||
|
||||
/* @param flag bit0= only test expression whether compilable
|
||||
*/
|
||||
int Sregex_match(char *pattern, char *text, int flag);
|
||||
|
||||
/*
|
||||
vars[][0] points to the variable names, vars[][1] to their contents.
|
||||
start marks the begin of variable names. It must be non-empty. esc before
|
||||
start disables this meaning. start and esc may be equal but else they must
|
||||
have disjoint character sets.
|
||||
end marks the end of a variable name. It may be empty but if non-empty it
|
||||
must not appear in vars[][0].
|
||||
@param flag bit0= Substitute unknown variables by empty text
|
||||
(else copy start,name,end unaltered to result).
|
||||
Parameter end must be non-empty for that.
|
||||
*/
|
||||
int Sregex_resolve_var(char *form, char *vars[][2], int num_vars,
|
||||
char *start, char *end, char *esc,
|
||||
char *result, int result_size, int flag);
|
||||
|
||||
/* reg_expr should be twice as large as bourne_expr ( + 2 to be exact) */
|
||||
/* return: 2= bourne_expr is surely a constant */
|
||||
int Xorriso__bourne_to_reg(char bourne_expr[], char reg_expr[], int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_misc_includeD */
|
||||
|
1901
xorriso/opts_a_c.c
Normal file
1901
xorriso/opts_a_c.c
Normal file
File diff suppressed because it is too large
Load Diff
1823
xorriso/opts_d_h.c
Normal file
1823
xorriso/opts_d_h.c
Normal file
File diff suppressed because it is too large
Load Diff
1179
xorriso/opts_i_o.c
Normal file
1179
xorriso/opts_i_o.c
Normal file
File diff suppressed because it is too large
Load Diff
1764
xorriso/opts_p_z.c
Normal file
1764
xorriso/opts_p_z.c
Normal file
File diff suppressed because it is too large
Load Diff
2051
xorriso/parse_exec.c
Normal file
2051
xorriso/parse_exec.c
Normal file
File diff suppressed because it is too large
Load Diff
88
xorriso/parse_exec.h
Normal file
88
xorriso/parse_exec.h
Normal file
@ -0,0 +1,88 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which deal with parsing
|
||||
and interpretation of command input.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_cmd_includeD
|
||||
#define Xorriso_pvt_cmd_includeD yes
|
||||
|
||||
|
||||
/* @param flag bit0= do not warn of wildcards
|
||||
bit1= these are disk_paths
|
||||
*/
|
||||
int Xorriso_end_idx(struct XorrisO *xorriso,
|
||||
int argc, char **argv, int idx, int flag);
|
||||
|
||||
int Xorriso_opt_args(struct XorrisO *xorriso, char *cmd,
|
||||
int argc, char **argv, int idx,
|
||||
int *end_idx, int *optc, char ***optv, int flag);
|
||||
|
||||
int Xorriso_get_problem_status(struct XorrisO *xorriso, char severity[80],
|
||||
int flag);
|
||||
|
||||
int Xorriso_set_problem_status(struct XorrisO *xorriso, char *severity,
|
||||
int flag);
|
||||
|
||||
/**
|
||||
@param flag bit0= do not issue own event messages
|
||||
bit1= take xorriso->request_to_abort as reason for abort
|
||||
@return Gives the advice:
|
||||
2= pardon was given, go on
|
||||
1= no problem, go on
|
||||
0= function failed but xorriso would not abort, go on
|
||||
<0= do abort
|
||||
-1 = due to problem_status
|
||||
-2 = due to xorriso->request_to_abort
|
||||
*/
|
||||
int Xorriso_eval_problem_status(struct XorrisO *xorriso, int ret, int flag);
|
||||
|
||||
int Xorriso_cpmv_args(struct XorrisO *xorriso, char *cmd,
|
||||
int argc, char **argv, int *idx,
|
||||
int *optc, char ***optv, char eff_dest[SfileadrL],
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= with adr_mode sbsector: adr_value is possibly 16 too high
|
||||
*/
|
||||
int Xorriso_decode_load_adr(struct XorrisO *xorriso, char *cmd,
|
||||
char *adr_mode, char *adr_value,
|
||||
int *entity_code, char entity_id[81],
|
||||
int flag);
|
||||
|
||||
int Xorriso_check_name_len(struct XorrisO *xorriso, char *name, int size,
|
||||
char *cmd, int flag);
|
||||
|
||||
/* @param flag bit0= prepend wd only if name does not begin by '/'
|
||||
bit2= prepend wd (automatically done if wd[0]!=0)
|
||||
*/
|
||||
int Xorriso_make_abs_adr(struct XorrisO *xorriso, char *wd, char *name,
|
||||
char adr[], int flag);
|
||||
|
||||
/* @param flag bit0= do not complain in case of error, but set info_text */
|
||||
int Xorriso_convert_datestring(struct XorrisO *xorriso, char *cmd,
|
||||
char *time_type, char *timestring,
|
||||
int *t_type, time_t *t, int flag);
|
||||
|
||||
int Xorriso_check_temp_mem_limit(struct XorrisO *xorriso, off_t mem, int flag);
|
||||
|
||||
/* @param flag bit0= use env_path to find the desired program
|
||||
*/
|
||||
int Xorriso_execv(struct XorrisO *xorriso, char *cmd, char *env_path,
|
||||
int *status, int flag);
|
||||
|
||||
int Xorriso_path_is_excluded(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
/* Normalize ACL and sort apart "access" ACL from "default" ACL.
|
||||
*/
|
||||
int Xorriso_normalize_acl_text(struct XorrisO *xorriso, char *in_text,
|
||||
char **access_acl_text, char **default_acl_text, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_cmd_includeD */
|
||||
|
2011
xorriso/read_run.c
Normal file
2011
xorriso/read_run.c
Normal file
File diff suppressed because it is too large
Load Diff
70
xorriso/read_run.h
Normal file
70
xorriso/read_run.h
Normal file
@ -0,0 +1,70 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_read_run_includeD
|
||||
#define Xorriso_pvt_read_run_includeD yes
|
||||
|
||||
|
||||
int Xorriso__read_pacifier(IsoImage *image, IsoFileSource *filesource);
|
||||
|
||||
int Xorriso_restore_properties(struct XorrisO *xorriso, char *disk_path,
|
||||
IsoNode *node, int flag);
|
||||
|
||||
int Xorriso_restore_implicit_properties(struct XorrisO *xorriso,
|
||||
char *full_disk_path, char *disk_path, char *full_img_path, int flag);
|
||||
|
||||
int Xorriso_tree_restore_node(struct XorrisO *xorriso, IsoNode *node,
|
||||
char *img_path, off_t img_offset,
|
||||
char *disk_path, off_t disk_offset, off_t bytes,
|
||||
int flag);
|
||||
|
||||
int Xorriso_restore_overwrite(struct XorrisO *xorriso,
|
||||
IsoNode *node, char *img_path,
|
||||
char *path, char *nominal_path,
|
||||
struct stat *stbuf, int flag);
|
||||
|
||||
int Xorriso_restore_target_hl(struct XorrisO *xorriso, IsoNode *node,
|
||||
char *disk_path, int *node_idx, int flag);
|
||||
|
||||
int Xorriso_restore_prefix_hl(struct XorrisO *xorriso, IsoNode *node,
|
||||
char *disk_path, int node_idx, int flag);
|
||||
|
||||
int Xorriso_register_node_target(struct XorrisO *xorriso, int node_idx,
|
||||
char *disk_path, int flag);
|
||||
|
||||
int Xorriso_restore_disk_object(struct XorrisO *xorriso,
|
||||
char *img_path, IsoNode *node,
|
||||
char *disk_path,
|
||||
off_t offset, off_t bytes, int flag);
|
||||
|
||||
int Xorriso_handle_collision(struct XorrisO *xorriso,
|
||||
IsoNode *node, char *img_path,
|
||||
char *disk_path, char *nominal_disk_path,
|
||||
int *stbuf_ret, int flag);
|
||||
|
||||
int Xorriso_restore_tree(struct XorrisO *xorriso, IsoDir *dir,
|
||||
char *img_dir_path, char *disk_dir_path,
|
||||
off_t boss_mem,
|
||||
struct LinkiteM *link_stack, int flag);
|
||||
|
||||
int Xorriso_read_file_data(struct XorrisO *xorriso, IsoNode *node,
|
||||
char *img_path, char *disk_path,
|
||||
off_t img_offset, off_t disk_offset,
|
||||
off_t bytes, int flag);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_read_run_includeD */
|
||||
|
877
xorriso/sfile.c
Normal file
877
xorriso/sfile.c
Normal file
@ -0,0 +1,877 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains the implementation of functions around files and strings.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <pwd.h>
|
||||
#include <grp.h>
|
||||
|
||||
|
||||
#include "sfile.h"
|
||||
|
||||
|
||||
/* @param flag bit0= do not clip of carriage return at line end
|
||||
*/
|
||||
char *Sfile_fgets_n(char *line, int maxl, FILE *fp, int flag)
|
||||
{
|
||||
int l;
|
||||
char *ret;
|
||||
|
||||
ret= fgets(line,maxl,fp);
|
||||
if(ret==NULL)
|
||||
return(NULL);
|
||||
l= strlen(line);
|
||||
if(l > 0 && !(flag & 1)) if(line[l-1] == '\r') line[--l]= 0;
|
||||
if(l > 0) if(line[l-1] == '\n') line[--l]= 0;
|
||||
if(l > 0 && !(flag & 1)) if(line[l-1] == '\r') line[--l]= 0;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_count_components(char *path, int flag)
|
||||
/*
|
||||
bit0= do not ignore trailing slash
|
||||
bit1= do not ignore empty components (other than the empty root name)
|
||||
*/
|
||||
{
|
||||
int l,count= 0;
|
||||
char *cpt;
|
||||
|
||||
l= strlen(path);
|
||||
if(l==0)
|
||||
return(0);
|
||||
count= 1;
|
||||
for(cpt= path+l-1;cpt>=path;cpt--) {
|
||||
if(*cpt=='/') {
|
||||
if(*(cpt+1)==0 && !(flag&1))
|
||||
continue;
|
||||
if(*(cpt+1)=='/' && !(flag&2))
|
||||
continue;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
return(count);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_component_pointer(char *path, char **sourcept, int idx, int flag)
|
||||
/*
|
||||
bit0= do not ignore trailing slash
|
||||
bit1= do not ignore empty components (other than the empty root name)
|
||||
bit2= accept 0 as '/'
|
||||
*/
|
||||
{
|
||||
int count= 0;
|
||||
char *spt;
|
||||
|
||||
for(spt= path;*spt!=0 || (flag&4);spt++) {
|
||||
if(count>=idx) {
|
||||
*sourcept= spt;
|
||||
return(1);
|
||||
}
|
||||
if(*spt=='/' || *spt==0) {
|
||||
if(*(spt+1)=='/' && !(flag&2))
|
||||
continue;
|
||||
if(*(spt+1)==0 && !(flag&1))
|
||||
continue;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
if((flag&1) && count>=idx)
|
||||
return(1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_leafname(char *path, char leafname[SfileadrL], int flag)
|
||||
{
|
||||
int count, ret;
|
||||
char *lpt;
|
||||
|
||||
leafname[0]= 0;
|
||||
count= Sfile_count_components(path, 0);
|
||||
if(count==0)
|
||||
return(0);
|
||||
ret= Sfile_component_pointer(path, &lpt, count-1, 0);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
if(Sfile_str(leafname, lpt, 0)<=0)
|
||||
return(0);
|
||||
lpt= strchr(leafname, '/');
|
||||
if(lpt!=NULL)
|
||||
*lpt= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_add_to_path(char path[SfileadrL], char *addon, int flag)
|
||||
{
|
||||
int l;
|
||||
|
||||
l= strlen(path);
|
||||
if(l+1>=SfileadrL)
|
||||
return(0);
|
||||
if(l==0) {
|
||||
strcpy(path,"/");
|
||||
l= 1;
|
||||
} else if(path[l-1]!='/') {
|
||||
path[l++]= '/';
|
||||
path[l]= 0;
|
||||
}
|
||||
if(l+strlen(addon)>=SfileadrL)
|
||||
return(0);
|
||||
if(addon[0]=='/')
|
||||
strcpy(path+l,addon+1);
|
||||
else
|
||||
strcpy(path+l,addon);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_prepend_path(char *prefix, char path[SfileadrL], int flag)
|
||||
{
|
||||
int l, i;
|
||||
|
||||
l= strlen(path)+strlen(prefix)+1;
|
||||
if(l>=SfileadrL) {
|
||||
|
||||
#ifdef Not_yeT
|
||||
/* >>> ??? how to transport messages to xorriso ? */
|
||||
sprintf(xorriso->info_text,
|
||||
"Combination of wd and relative address too long (%d > %d)",
|
||||
l,SfileadrL-1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
#endif
|
||||
|
||||
return(-1);
|
||||
}
|
||||
l-= strlen(path);
|
||||
for(i= strlen(path)+1; i>=0; i--)
|
||||
path[i+l]= path[i];
|
||||
strcpy(path,prefix);
|
||||
path[l-1]= '/';
|
||||
return(1);
|
||||
}
|
||||
|
||||
int Sfile_being_group_member(struct stat *stbuf, int flag)
|
||||
{
|
||||
int i, suppl_groups;
|
||||
gid_t *suppl_glist;
|
||||
|
||||
if (getegid()==stbuf->st_gid)
|
||||
return(1);
|
||||
suppl_groups= getgroups(0, NULL);
|
||||
suppl_glist= (gid_t *) malloc((suppl_groups + 1) * sizeof(gid_t));
|
||||
if (suppl_glist==NULL)
|
||||
return(-1);
|
||||
suppl_groups= getgroups(suppl_groups+1,suppl_glist);
|
||||
for (i= 0; i<suppl_groups; i++) {
|
||||
if (suppl_glist[i]==stbuf->st_gid) {
|
||||
free((char *) suppl_glist);
|
||||
return(1);
|
||||
}
|
||||
}
|
||||
free((char *) suppl_glist);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_type(char *filename, int flag)
|
||||
/*
|
||||
bit0= return -1 if file is missing
|
||||
bit1= return a hardlink with siblings as type 5
|
||||
bit2= evaluate eventual link target rather than the link object itself
|
||||
bit3= return a socket or a char device as types 7 or 8 rather than 0
|
||||
*/
|
||||
/*
|
||||
return:
|
||||
0=unknown
|
||||
1=regular
|
||||
2=directory
|
||||
3=symbolic link
|
||||
4=named pipe
|
||||
5=multiple hardlink (with bit1)
|
||||
6=block device
|
||||
7=socket (with bit3)
|
||||
8=character device (with bit3)
|
||||
*/
|
||||
{
|
||||
struct stat stbuf;
|
||||
if(flag&4) {
|
||||
if(stat(filename,&stbuf)==-1) {
|
||||
if(flag&1) return(-1);
|
||||
else return(0);
|
||||
}
|
||||
} else {
|
||||
if(lstat(filename,&stbuf)==-1) {
|
||||
if(flag&1) return(-1);
|
||||
else return(0);
|
||||
}
|
||||
}
|
||||
if(S_ISREG(stbuf.st_mode)) {
|
||||
if(flag&2)
|
||||
if(stbuf.st_nlink>1)
|
||||
return(5);
|
||||
return(1);
|
||||
}
|
||||
if(S_ISDIR(stbuf.st_mode))
|
||||
return(2);
|
||||
if((stbuf.st_mode&S_IFMT)==S_IFLNK)
|
||||
return(3);
|
||||
if(S_ISFIFO(stbuf.st_mode))
|
||||
return(4);
|
||||
if(S_ISBLK(stbuf.st_mode))
|
||||
return(6);
|
||||
if(flag&8)
|
||||
if((stbuf.st_mode&S_IFMT)==S_IFSOCK)
|
||||
return(7);
|
||||
if(flag&8)
|
||||
if(S_ISCHR(stbuf.st_mode))
|
||||
return(8);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
char *Sfile_datestr(time_t tim, short int flag)
|
||||
/*
|
||||
bit0=with hours+minutes
|
||||
bit1=with seconds
|
||||
|
||||
bit8= local time rather than UTC
|
||||
*/
|
||||
{
|
||||
static char zeitcode[80]={"000000"};
|
||||
char puff[80];
|
||||
struct tm *azt;
|
||||
|
||||
if(flag&256)
|
||||
azt = localtime(&tim);
|
||||
else
|
||||
azt = gmtime(&tim);
|
||||
|
||||
if(azt->tm_year>99)
|
||||
sprintf(zeitcode,"%c%1.1d%2.2d%2.2d",
|
||||
'A'+(azt->tm_year-100)/10,azt->tm_year%10,
|
||||
azt->tm_mon+1,azt->tm_mday);
|
||||
else
|
||||
sprintf(zeitcode,"%2.2d%2.2d%2.2d",
|
||||
azt->tm_year,azt->tm_mon+1,azt->tm_mday);
|
||||
if(flag&1){
|
||||
sprintf(puff,".%2.2d%2.2d",azt->tm_hour,azt->tm_min);
|
||||
strcat(zeitcode,puff);
|
||||
}
|
||||
if(flag&2){
|
||||
sprintf(puff,"%2.2d",azt->tm_sec);
|
||||
strcat(zeitcode,puff);
|
||||
}
|
||||
|
||||
return(zeitcode);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_scale(double value, char *result, int siz, double thresh, int flag)
|
||||
/*
|
||||
bit0= eventually ommit 'b'
|
||||
bit1= make text as short as possible
|
||||
bit2= no fraction (if it would fit at all)
|
||||
*/
|
||||
{
|
||||
char scale_c,scales[7],form[80], *negpt= NULL, *cpt;
|
||||
int i,dec_siz= 0,avail_siz= 1;
|
||||
|
||||
if(value<0) {
|
||||
value= -value;
|
||||
siz--;
|
||||
result[0]= '-';
|
||||
negpt= result;
|
||||
result++;
|
||||
}
|
||||
strcpy(scales,"bkmgtp");
|
||||
scale_c= scales[0];
|
||||
for(i=1;scales[i]!=0;i++) {
|
||||
if(value<thresh-0.5)
|
||||
break;
|
||||
value/= 1024.0;
|
||||
scale_c= scales[i];
|
||||
}
|
||||
if(scale_c!='b' && !(flag&4)) { /* is there room for fractional part ? */
|
||||
avail_siz= siz-1;
|
||||
sprintf(form,"%%.f");
|
||||
sprintf(result,"%.f",value);
|
||||
if(strlen(result)<=avail_siz-2)
|
||||
dec_siz= 1; /* we are very modest */
|
||||
}
|
||||
if(scale_c=='b' && (flag&1)) {
|
||||
if(flag&2)
|
||||
sprintf(form,"%%.f");
|
||||
else
|
||||
sprintf(form,"%%%d.f",siz);
|
||||
sprintf(result,form,value);
|
||||
} else {
|
||||
if(flag&2)
|
||||
sprintf(form,"%%.f%%c");
|
||||
else if(dec_siz>0)
|
||||
sprintf(form,"%%%d.%df%%c",avail_siz,dec_siz);
|
||||
else
|
||||
sprintf(form,"%%%d.f%%c",siz-1);
|
||||
sprintf(result,form,value,scale_c);
|
||||
}
|
||||
if(negpt != NULL) {
|
||||
for(cpt= result; *cpt==' '; cpt++);
|
||||
if(cpt > result) {
|
||||
*negpt= ' ';
|
||||
*(cpt - 1)= '-';
|
||||
}
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_off_t_text(char text[80], off_t num, int flag)
|
||||
{
|
||||
char *tpt;
|
||||
off_t hnum, scale= 1;
|
||||
int digits= 0, d, i;
|
||||
|
||||
tpt= text;
|
||||
hnum= num;
|
||||
if(hnum<0) {
|
||||
*(tpt++)= '-';
|
||||
hnum= -num;
|
||||
}
|
||||
if(hnum<0) { /* it can stay nastily persistent */
|
||||
strcpy(text, "_overflow_");
|
||||
return(0);
|
||||
}
|
||||
for(i= 0; i<23; i++) { /* good for up to 70 bit = 10 exp 21.07... */
|
||||
if(hnum==0)
|
||||
break;
|
||||
hnum/= 10;
|
||||
if(hnum)
|
||||
scale*= 10;
|
||||
}
|
||||
if(i==0) {
|
||||
strcpy(text, "0");
|
||||
return(1);
|
||||
}
|
||||
if(i==23) {
|
||||
strcpy(text, "_overflow_");
|
||||
return(0);
|
||||
}
|
||||
digits= i;
|
||||
hnum= num;
|
||||
for(; i>0; i--) {
|
||||
d= hnum/scale;
|
||||
tpt[digits-i]= '0'+d;
|
||||
hnum= hnum%scale;
|
||||
scale/= 10;
|
||||
}
|
||||
tpt[digits]= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* Converts backslash codes into single characters:
|
||||
\a BEL 7 , \b BS 8 , \e ESC 27 , \f FF 12 , \n LF 10 , \r CR 13 ,
|
||||
\t HT 9 , \v VT 11 , \\ \ 92
|
||||
\[0-9][0-9][0-9] octal code , \x[0-9a-f][0-9a-f] hex code ,
|
||||
\cX control-x (ascii(X)-64)
|
||||
@param upto maximum number of characters to examine for backslash.
|
||||
The scope of a backslash (0 to 3 characters) is not affected.
|
||||
@param eaten returns the difference in length between input and output
|
||||
@param flag bit0= only determine *eaten, do not convert
|
||||
bit1= allow to convert \000 to binary 0
|
||||
*/
|
||||
int Sfile_bsl_interpreter(char *text, int upto, int *eaten, int flag)
|
||||
{
|
||||
char *rpt, *wpt, num_text[8], wdummy[8];
|
||||
unsigned int num= 0;
|
||||
|
||||
*eaten= 0;
|
||||
wpt= text;
|
||||
for(rpt= text; *rpt != 0 && rpt - text < upto; rpt++) {
|
||||
if(flag & 1)
|
||||
wpt= wdummy;
|
||||
if(*rpt == '\\') {
|
||||
rpt++;
|
||||
(*eaten)++;
|
||||
if(*rpt == 'a') {
|
||||
*(wpt++)= 7;
|
||||
} else if(*rpt == 'b') {
|
||||
*(wpt++)= 8;
|
||||
} else if(*rpt == 'e') {
|
||||
*(wpt++)= 27;
|
||||
} else if(*rpt == 'f') {
|
||||
*(wpt++)= 12;
|
||||
} else if(*rpt == 'n') {
|
||||
*(wpt++)= 10;
|
||||
} else if(*rpt == 'r') {
|
||||
*(wpt++)= 13;
|
||||
} else if(*rpt == 't') {
|
||||
*(wpt++)= 9;
|
||||
} else if(*rpt == 'v') {
|
||||
*(wpt++)= 11;
|
||||
} else if(*rpt == '\\') {
|
||||
*(wpt++)= '\\';
|
||||
} else if(rpt[0] >= '0' && rpt[0] <= '7' &&
|
||||
rpt[1] >= '0' && rpt[1] <= '7' &&
|
||||
rpt[2] >= '0' && rpt[2] <= '7') {
|
||||
num_text[0]= '0';
|
||||
num_text[1]= *(rpt + 0);
|
||||
num_text[2]= *(rpt + 1);
|
||||
num_text[3]= *(rpt + 2);
|
||||
num_text[4]= 0;
|
||||
sscanf(num_text, "%o", &num);
|
||||
if((num > 0 || (flag & 2)) && num <= 255) {
|
||||
rpt+= 2;
|
||||
(*eaten)+= 2;
|
||||
*(wpt++)= num;
|
||||
} else
|
||||
goto not_a_code;
|
||||
} else if(rpt[0] == 'x' &&
|
||||
((rpt[1] >= '0' && rpt[1] <= '9') ||
|
||||
(rpt[1] >= 'A' && rpt[1] <= 'F') ||
|
||||
(rpt[1] >= 'a' && rpt[1] <= 'f'))
|
||||
&&
|
||||
((rpt[2] >= '0' && rpt[2] <= '9') ||
|
||||
(rpt[2] >= 'A' && rpt[2] <= 'F') ||
|
||||
(rpt[2] >= 'a' && rpt[2] <= 'f'))
|
||||
) {
|
||||
num_text[0]= *(rpt + 1);
|
||||
num_text[1]= *(rpt + 2);
|
||||
num_text[2]= 0;
|
||||
sscanf(num_text, "%x", &num);
|
||||
if(num > 0 && num <= 255) {
|
||||
rpt+= 2;
|
||||
(*eaten)+= 2;
|
||||
*(wpt++)= num;
|
||||
} else
|
||||
goto not_a_code;
|
||||
} else if(*rpt == 'c') {
|
||||
if(rpt[1] > 64 && rpt[1] < 96) {
|
||||
*(wpt++)= rpt[1] - 64;
|
||||
rpt++;
|
||||
(*eaten)++;
|
||||
} else
|
||||
goto not_a_code;
|
||||
} else {
|
||||
not_a_code:;
|
||||
*(wpt++)= '\\';
|
||||
rpt--;
|
||||
(*eaten)--;
|
||||
}
|
||||
} else
|
||||
*(wpt++)= *rpt;
|
||||
}
|
||||
*wpt= *rpt;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_argv_bsl(int argc, char ***argv, int flag)
|
||||
{
|
||||
int i, ret, eaten;
|
||||
char **new_argv= NULL;
|
||||
|
||||
if(argc <= 0)
|
||||
return(0);
|
||||
new_argv= (char **) Smem_malloC(argc * sizeof(char *));
|
||||
if(new_argv == NULL)
|
||||
return(-1);
|
||||
for(i= 0; i < argc; i++) {
|
||||
new_argv[i]= strdup((*argv)[i]);
|
||||
if(new_argv[i] == NULL)
|
||||
{ret= -1; goto ex;}
|
||||
ret= Sfile_bsl_interpreter(new_argv[i], strlen(new_argv[i]), &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(ret <= 0) {
|
||||
if(new_argv != NULL)
|
||||
free((char *) new_argv);
|
||||
} else
|
||||
*argv= new_argv;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= only encode inside quotes
|
||||
bit1= encode < 32 outside quotes except 7, 8, 9, 10, 12, 13
|
||||
bit2= encode in any case above 126
|
||||
bit3= encode in any case shellsafe and name-value-safe:
|
||||
<=42 , 59, 60, 61, 62, 63, 92, 94, 96, >=123
|
||||
*/
|
||||
int Sfile_bsl_encoder(char **result, char *text, size_t text_len, int flag)
|
||||
{
|
||||
char *rpt, *wpt;
|
||||
int count, sq_open= 0, dq_open= 0;
|
||||
|
||||
count= 0;
|
||||
for(rpt= text; rpt - text < text_len; rpt++) {
|
||||
count++;
|
||||
if(flag & 8) {
|
||||
if(!(*rpt <= 42 || (*rpt >= 59 && *rpt <= 63) ||
|
||||
*rpt == 92 || *rpt == 94 || *rpt == 96 || *rpt >= 123))
|
||||
continue;
|
||||
} else if(*rpt >= 32 && *rpt <= 126 && *rpt != '\\')
|
||||
continue;
|
||||
if(((*rpt >= 7 && *rpt <= 13) || *rpt == 27 || *rpt == '\\') && !(flag & 8))
|
||||
count++;
|
||||
else
|
||||
count+= 3;
|
||||
}
|
||||
(*result)= wpt= calloc(count + 1, 1);
|
||||
if(wpt == NULL)
|
||||
return(-1);
|
||||
for(rpt= text; rpt - text < text_len; rpt++) {
|
||||
if(*rpt == '\'')
|
||||
sq_open= !(sq_open || dq_open);
|
||||
if(*rpt == '"')
|
||||
dq_open= !(sq_open || dq_open);
|
||||
|
||||
if(flag & 8) {
|
||||
if(!(*rpt <= 42 || (*rpt >= 59 && *rpt <= 63) ||
|
||||
*rpt == 92 || *rpt == 94 || *rpt == 96 || *rpt >= 123)) {
|
||||
*(wpt++)= *rpt;
|
||||
continue;
|
||||
}
|
||||
} else if(*rpt >= 32 && *rpt <= 126 && *rpt != '\\') {
|
||||
*(wpt++)= *rpt;
|
||||
continue;
|
||||
} else if( ((flag & 1) && !(sq_open || dq_open)) &&
|
||||
!((flag & 2) && (*rpt >= 1 && * rpt <= 31 &&
|
||||
!(*rpt == 7 || *rpt == 8 || *rpt == 9 || *rpt == 10 ||
|
||||
*rpt == 12 || *rpt == 13))) &&
|
||||
!((flag & 4) && (*rpt > 126 || *rpt < 0)) &&
|
||||
!((flag & 6) && *rpt == '\\')) {
|
||||
*(wpt++)= *rpt;
|
||||
continue;
|
||||
}
|
||||
*(wpt++)= '\\';
|
||||
if(((*rpt >= 7 && *rpt <= 13) || *rpt == 27 || *rpt == '\\') && !(flag&8)) {
|
||||
if(*rpt == 7)
|
||||
*(wpt++)= 'a';
|
||||
else if(*rpt == 8)
|
||||
*(wpt++)= 'b';
|
||||
else if(*rpt == 9)
|
||||
*(wpt++)= 't';
|
||||
else if(*rpt == 10) {
|
||||
*(wpt++)= 'n';
|
||||
} else if(*rpt == 11)
|
||||
*(wpt++)= 'v';
|
||||
else if(*rpt == 12)
|
||||
*(wpt++)= 'f';
|
||||
else if(*rpt == 13)
|
||||
*(wpt++)= 'c';
|
||||
else if(*rpt == 27)
|
||||
*(wpt++)= 'e';
|
||||
else if(*rpt == '\\')
|
||||
*(wpt++)= '\\';
|
||||
} else {
|
||||
sprintf(wpt, "%-3.3o", (unsigned int) *((unsigned char *) rpt));
|
||||
wpt+= 3;
|
||||
}
|
||||
}
|
||||
*wpt= 0;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_destroy_argv(int *argc, char ***argv, int flag)
|
||||
{
|
||||
int i;
|
||||
|
||||
if(*argc>0 && *argv!=NULL){
|
||||
for(i=0;i<*argc;i++){
|
||||
if((*argv)[i]!=NULL)
|
||||
Smem_freE((*argv)[i]);
|
||||
}
|
||||
Smem_freE((char *) *argv);
|
||||
}
|
||||
*argc= 0;
|
||||
*argv= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Sfile_make_argv(char *progname, char *line, int *argc, char ***argv,
|
||||
int flag)
|
||||
/*
|
||||
bit0= read progname as first argument from line
|
||||
bit1= just release argument list argv and return
|
||||
bit2= abort with return(0) if incomplete quotes are found
|
||||
bit3= eventually prepend missing '-' to first argument read from line
|
||||
bit4= like bit2 but only check quote completeness, do not allocate memory
|
||||
bit5+6= interpretation of backslashes:
|
||||
0= no interpretation, leave unchanged
|
||||
1= only inside double quotes
|
||||
2= outside single quotes
|
||||
3= everywhere
|
||||
bit7= append a NULL element to argv
|
||||
*/
|
||||
{
|
||||
int i,pass,maxl=0,l,argzaehl=0,bufl,line_start_argc, bsl_mode, ret= 0, eaten;
|
||||
char *cpt,*start;
|
||||
char *buf= NULL;
|
||||
|
||||
Sfile_destroy_argv(argc,argv,0);
|
||||
if(flag&2)
|
||||
{ret= 1; goto ex;}
|
||||
|
||||
if(flag & 16)
|
||||
flag|= 4;
|
||||
bsl_mode= (flag >> 5) & 3;
|
||||
|
||||
buf= calloc(strlen(line) + SfileadrL, 1);
|
||||
if(buf == NULL)
|
||||
{ret= -1; goto ex;}
|
||||
for(pass=0;pass<2;pass++) {
|
||||
cpt= line-1;
|
||||
if(!(flag&1)){
|
||||
argzaehl= line_start_argc= 1;
|
||||
if(pass==0)
|
||||
maxl= strlen(progname);
|
||||
else
|
||||
strcpy((*argv)[0],progname);
|
||||
} else {
|
||||
argzaehl= line_start_argc= 0;
|
||||
if(pass==0) maxl= 0;
|
||||
}
|
||||
while(*(++cpt)!=0){
|
||||
if(isspace(*cpt)) continue;
|
||||
start= cpt;
|
||||
buf[0]= 0;
|
||||
cpt--;
|
||||
while(*(++cpt)!=0) {
|
||||
if(isspace(*cpt)) break;
|
||||
if(*cpt=='"'){
|
||||
l= cpt-start; bufl= strlen(buf);
|
||||
if(l>0) {
|
||||
strncpy(buf + bufl, start, l); buf[bufl + l]= 0;
|
||||
if(bsl_mode >= 3) {
|
||||
ret= Sfile_bsl_interpreter(buf, l, &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
l= strlen(buf);
|
||||
start= cpt+1;
|
||||
while(*(++cpt)!=0) if(*cpt=='"') break;
|
||||
if((flag&4) && *cpt==0)
|
||||
{ret= 0; goto ex;}
|
||||
l= cpt-start; bufl= strlen(buf);
|
||||
if(l>0) {
|
||||
strncpy(buf + bufl, start, l);
|
||||
buf[bufl + l]= 0;
|
||||
if(bsl_mode >= 1) {
|
||||
ret= Sfile_bsl_interpreter(buf + bufl, l, &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
start= cpt+1;
|
||||
}else if(*cpt=='\''){
|
||||
l= cpt-start; bufl= strlen(buf);
|
||||
if(l>0) {
|
||||
strncpy(buf + bufl, start, l); buf[bufl + l]= 0;
|
||||
if(bsl_mode >= 3) {
|
||||
ret= Sfile_bsl_interpreter(buf, l, &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
l= strlen(buf);
|
||||
start= cpt+1;
|
||||
while(*(++cpt)!=0) if(*cpt=='\'') break;
|
||||
if((flag&4) && *cpt==0)
|
||||
{ret= 0; goto ex;}
|
||||
l= cpt-start; bufl= strlen(buf);
|
||||
if(l>0) {
|
||||
strncat(buf,start,l);buf[bufl+l]= 0;
|
||||
if(bsl_mode >= 2) {
|
||||
ret= Sfile_bsl_interpreter(buf + bufl, l, &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
start= cpt+1;
|
||||
}
|
||||
if(*cpt==0) break;
|
||||
}
|
||||
l= cpt-start;
|
||||
bufl= strlen(buf);
|
||||
if(l>0) {
|
||||
strncpy(buf + bufl, start, l); buf[bufl + l]= 0;
|
||||
if(bsl_mode >= 3) {
|
||||
ret= Sfile_bsl_interpreter(buf, l, &eaten, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
}
|
||||
l= strlen(buf);
|
||||
if(pass==0){
|
||||
if(argzaehl==line_start_argc && (flag&8))
|
||||
if(buf[0]!='-' && buf[0]!=0 && buf[0]!='#')
|
||||
l++;
|
||||
if(l>maxl) maxl= l;
|
||||
}else{
|
||||
strcpy((*argv)[argzaehl],buf);
|
||||
if(argzaehl==line_start_argc && (flag&8))
|
||||
if(buf[0]!='-' && buf[0]!=0 && buf[0]!='#')
|
||||
sprintf((*argv)[argzaehl],"-%s", buf);
|
||||
}
|
||||
argzaehl++;
|
||||
if(*cpt==0) break;
|
||||
}
|
||||
if(pass==0){
|
||||
if(flag & 16)
|
||||
{ret= 1; goto ex;}
|
||||
*argc= argzaehl;
|
||||
if(argzaehl>0 || (flag & 128)) {
|
||||
*argv= (char **) Smem_malloC((argzaehl + !!(flag & 128))
|
||||
* sizeof(char *));
|
||||
if(*argv==NULL)
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
for(i=0;i<*argc;i++) {
|
||||
(*argv)[i]= (char *) Smem_malloC((maxl+1));
|
||||
if((*argv)[i]==NULL)
|
||||
{ret= -1; goto ex;}
|
||||
}
|
||||
if(flag & 128)
|
||||
(*argv)[*argc]= NULL;
|
||||
}
|
||||
}
|
||||
ret= 1;
|
||||
ex:
|
||||
if(buf != NULL)
|
||||
free(buf);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= append */
|
||||
int Sfile_str(char target[SfileadrL], char *source, int flag)
|
||||
{
|
||||
int l;
|
||||
|
||||
l= strlen(source);
|
||||
if(flag&1)
|
||||
l+= strlen(target);
|
||||
if(l>=SfileadrL) {
|
||||
fprintf(stderr, "--- Path string overflow (%d > %d). Malicious input ?\n",
|
||||
l,SfileadrL-1);
|
||||
return(0);
|
||||
}
|
||||
if(flag&1)
|
||||
strcat(target, source);
|
||||
else
|
||||
strcpy(target, source);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/** Combine environment variable HOME with given filename
|
||||
@param filename Address relative to $HOME
|
||||
@param fileadr Resulting combined address
|
||||
@param fa_size Size of array fileadr
|
||||
@param flag Unused yet
|
||||
@return 1=ok , 0=no HOME variable , -1=result address too long
|
||||
*/
|
||||
int Sfile_home_adr_s(char *filename, char *fileadr, int fa_size, int flag)
|
||||
{
|
||||
char *home;
|
||||
|
||||
strcpy(fileadr,filename);
|
||||
home= getenv("HOME");
|
||||
if(home==NULL)
|
||||
return(0);
|
||||
if(strlen(home)+strlen(filename)+1>=fa_size)
|
||||
return(-1);
|
||||
strcpy(fileadr,home);
|
||||
if(filename[0]!=0){
|
||||
strcat(fileadr,"/");
|
||||
strcat(fileadr,filename);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/** Return a double representing seconds and microseconds since 1 Jan 1970 */
|
||||
double Sfile_microtime(int flag)
|
||||
{
|
||||
struct timeval tv;
|
||||
struct timezone tz;
|
||||
gettimeofday(&tv,&tz);
|
||||
return((double) (tv.tv_sec+1.0e-6*tv.tv_usec));
|
||||
}
|
||||
|
||||
|
||||
int Sfile_decode_datestr(struct tm *reply, char *text, int flag)
|
||||
/* YYMMDD[.hhmm[ss]] */
|
||||
{
|
||||
int i,l;
|
||||
time_t current_time;
|
||||
struct tm *now;
|
||||
|
||||
current_time= time(0);
|
||||
now= localtime(¤t_time);
|
||||
for(i=0;i<sizeof(struct tm);i++)
|
||||
((char *) reply)[i]= ((char *) now)[i];
|
||||
|
||||
if(text[0]<'0'|| (text[0]>'9' && text[0]<'A') || text[0]>'Z')
|
||||
return(0);
|
||||
l= strlen(text);
|
||||
for(i=1;i<l;i++)
|
||||
if(text[i]<'0'||text[i]>'9')
|
||||
break;
|
||||
if(i!=6)
|
||||
return(0);
|
||||
if(text[i]==0)
|
||||
goto decode;
|
||||
if(text[i]!='.' || (l!=11 && l!=13))
|
||||
return(0);
|
||||
for(i++;i<l;i++)
|
||||
if(text[i]<'0'||text[i]>'9')
|
||||
break;
|
||||
if(i!=l)
|
||||
return(0);
|
||||
|
||||
decode:;
|
||||
reply->tm_hour= 0;
|
||||
reply->tm_min= 0;
|
||||
reply->tm_sec= 0;
|
||||
i= 0;
|
||||
if(text[0]>='A')
|
||||
reply->tm_year= 100+(text[i]-'A')*10+text[1]-'0';
|
||||
else
|
||||
reply->tm_year= 10*(text[0]-'0')+text[1]-'0';
|
||||
reply->tm_mon= 10*(text[2]-'0')+text[3]-'0'-1;
|
||||
reply->tm_mday= 10*(text[4]-'0')+text[5]-'0';
|
||||
if(l==6)
|
||||
return(1);
|
||||
reply->tm_hour= 10*(text[7]-'0')+text[8]-'0';
|
||||
reply->tm_min= 10*(text[9]-'0')+text[10]-'0';
|
||||
if(l==11)
|
||||
return(1);
|
||||
reply->tm_sec= 10*(text[11]-'0')+text[12]-'0';
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
121
xorriso/sfile.h
Normal file
121
xorriso/sfile.h
Normal file
@ -0,0 +1,121 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions around files and strings.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_sfile_includeD
|
||||
#define Xorriso_pvt_sfile_includeD yes
|
||||
|
||||
#define TSOB_FELD(typ,anz) (typ *) calloc(1, (anz)*sizeof(typ));
|
||||
#define Smem_malloC malloc
|
||||
#define Smem_freE free
|
||||
|
||||
#define SfileadrL 4096
|
||||
|
||||
|
||||
int Sfile_str(char target[SfileadrL], char *source, int flag);
|
||||
|
||||
double Sfile_microtime(int flag);
|
||||
|
||||
int Sfile_add_to_path(char path[SfileadrL], char *addon, int flag);
|
||||
|
||||
int Sfile_scale(double value, char *result, int siz, double thresh, int flag);
|
||||
|
||||
int Sfile_destroy_argv(int *argc, char ***argv, int flag);
|
||||
|
||||
/*
|
||||
bit0= do not ignore trailing slash
|
||||
bit1= do not ignore empty components (other than the empty root name)
|
||||
*/
|
||||
int Sfile_count_components(char *path, int flag);
|
||||
|
||||
/*
|
||||
@param flag
|
||||
bit0= return -1 if file is missing
|
||||
bit1= return a hardlink with siblings as type 5
|
||||
bit2= evaluate eventual link target rather than the link object itself
|
||||
bit3= return a socket or a char device as types 7 or 8 rather than 0
|
||||
@return
|
||||
0=unknown
|
||||
1=regular
|
||||
2=directory
|
||||
3=symbolic link
|
||||
4=named pipe
|
||||
5=multiple hardlink (with bit1)
|
||||
6=block device
|
||||
7=socket (with bit3)
|
||||
8=character device (with bit3)
|
||||
*/
|
||||
int Sfile_type(char *filename, int flag);
|
||||
|
||||
/* @param flag bit0= only encode inside quotes
|
||||
bit1= encode < 32 outside quotes except 7, 8, 9, 10, 12, 13
|
||||
bit2= encode in any case above 126
|
||||
bit3= encode in any case shellsafe:
|
||||
<=42 , 59, 60, 62, 63, 92, 94, 96, >=123
|
||||
*/
|
||||
int Sfile_bsl_encoder(char **result, char *text, size_t text_len, int flag);
|
||||
|
||||
int Sfile_argv_bsl(int argc, char ***argv, int flag);
|
||||
|
||||
/*
|
||||
bit0= read progname as first argument from line
|
||||
bit1= just release argument list argv and return
|
||||
bit2= abort with return(0) if incomplete quotes are found
|
||||
bit3= eventually prepend missing '-' to first argument read from line
|
||||
bit4= like bit2 but only check quote completeness, do not allocate memory
|
||||
bit5+6= interpretation of backslashes:
|
||||
0= no interpretation, leave unchanged
|
||||
1= only inside double quotes
|
||||
2= outside single quotes
|
||||
3= everywhere
|
||||
bit7= append a NULL element to argv
|
||||
*/
|
||||
int Sfile_make_argv(char *progname, char *line, int *argc, char ***argv,
|
||||
int flag);
|
||||
|
||||
/* YYMMDD[.hhmm[ss]] */
|
||||
int Sfile_decode_datestr(struct tm *reply, char *text, int flag);
|
||||
|
||||
int Sfile_off_t_text(char text[80], off_t num, int flag);
|
||||
|
||||
int Sfile_leafname(char *path, char leafname[SfileadrL], int flag);
|
||||
|
||||
/* @param flag bit0= do not clip of carriage return at line end
|
||||
*/
|
||||
char *Sfile_fgets_n(char *line, int maxl, FILE *fp, int flag);
|
||||
|
||||
/*
|
||||
bit0=with hours+minutes
|
||||
bit1=with seconds
|
||||
|
||||
bit8= local time rather than UTC
|
||||
*/
|
||||
char *Sfile_datestr(time_t tim, short int flag);
|
||||
|
||||
/* Converts backslash codes into single characters:
|
||||
\a BEL 7 , \b BS 8 , \e ESC 27 , \f FF 12 , \n LF 10 , \r CR 13 ,
|
||||
\t HT 9 , \v VT 11 , \\ \ 92
|
||||
\[0-9][0-9][0-9] octal code , \x[0-9a-f][0-9a-f] hex code ,
|
||||
\cX control-x (ascii(X)-64)
|
||||
@param upto maximum number of characters to examine for backslash.
|
||||
The scope of a backslash (0 to 3 characters) is not affected.
|
||||
@param eaten returns the difference in length between input and output
|
||||
@param flag bit0= only determine *eaten, do not convert
|
||||
bit1= allow to convert \000 to binary 0
|
||||
*/
|
||||
int Sfile_bsl_interpreter(char *text, int upto, int *eaten, int flag);
|
||||
|
||||
int Sfile_prepend_path(char *prefix, char path[SfileadrL], int flag);
|
||||
|
||||
int Sfile_home_adr_s(char *filename, char *fileadr, int fa_size, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_sfile_includeD */
|
||||
|
710
xorriso/sort_cmp.c
Normal file
710
xorriso/sort_cmp.c
Normal file
@ -0,0 +1,710 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains functions which sort and compare tree nodes.
|
||||
*/
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <time.h>
|
||||
#include <errno.h>
|
||||
|
||||
|
||||
#include "base_obj.h"
|
||||
#include "lib_mgt.h"
|
||||
#include "sort_cmp.h"
|
||||
#include "iso_tree.h"
|
||||
#include "iso_manip.h"
|
||||
|
||||
|
||||
int Xorriso__findi_sorted_ino_cmp(const void *p1, const void *p2)
|
||||
{
|
||||
int ret;
|
||||
IsoNode *n1, *n2;
|
||||
|
||||
n1= *((IsoNode **) p1);
|
||||
n2= *((IsoNode **) p2);
|
||||
|
||||
ret= Xorriso__node_lba_cmp(&n1, &n2);
|
||||
if(ret)
|
||||
return (ret > 0 ? 1 : -1);
|
||||
ret= iso_node_cmp_ino(n1, n2, 0);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* Not suitable for qsort() but for cross-array comparisons.
|
||||
p1 and p2 are actually IsoNode *p1, IsoNode *p2
|
||||
*/
|
||||
int Xorriso__hln_cmp(const void *p1, const void *p2)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= Xorriso__findi_sorted_ino_cmp(&p1, &p2);
|
||||
if(ret)
|
||||
return (ret > 0 ? 1 : -1);
|
||||
if(p1 != p2)
|
||||
return(p1 < p2 ? -1 : 1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
p1 and p2 are actually IsoNode **p1, IsoNode **p2
|
||||
*/
|
||||
int Xorriso__findi_sorted_cmp(const void *p1, const void *p2)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret= Xorriso__findi_sorted_ino_cmp(p1, p2);
|
||||
if(ret)
|
||||
return (ret > 0 ? 1 : -1);
|
||||
if(p1 != p2)
|
||||
return(p1 < p2 ? -1 : 1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_sort_node_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
if(xorriso->node_counter <= 0)
|
||||
return(0);
|
||||
qsort(xorriso->node_array, xorriso->node_counter, sizeof(IsoNode *),
|
||||
Xorriso__findi_sorted_cmp);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__search_node(void *node_array[], int n,
|
||||
int (*cmp)(const void *p1, const void *p2),
|
||||
void *node, int *idx, int flag)
|
||||
{
|
||||
int ret, l, r, p, pos;
|
||||
|
||||
if(n == 0)
|
||||
return(0);
|
||||
l= 0;
|
||||
r= n + 1;
|
||||
while(1) {
|
||||
p= (r - l) / 2;
|
||||
if(p == 0)
|
||||
break;
|
||||
p+= l;
|
||||
|
||||
/* NULL elements may indicate invalid nodes. Their first valid right neigbor
|
||||
will serve as proxy. If none exists, then the test pushes leftwards.
|
||||
*/
|
||||
for(pos= p - 1; pos < n; pos++)
|
||||
if(node_array[pos] != NULL)
|
||||
break;
|
||||
if(pos < n)
|
||||
ret= (*cmp)(&(node_array[pos]), &node);
|
||||
else
|
||||
ret= 1;
|
||||
|
||||
if(ret < 0)
|
||||
l= p;
|
||||
else if(ret > 0)
|
||||
r= p;
|
||||
else {
|
||||
*idx= pos;
|
||||
return(1);
|
||||
}
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_search_in_hln_array(struct XorrisO *xorriso,
|
||||
void *node, int *idx, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if(xorriso->hln_array == NULL || xorriso->hln_count <= 0)
|
||||
return(0);
|
||||
ret= Xorriso__search_node(xorriso->hln_array, xorriso->hln_count,
|
||||
Xorriso__findi_sorted_ino_cmp, node, idx, 0);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__get_di(IsoNode *node, dev_t *dev, ino_t *ino, int flag)
|
||||
{
|
||||
int ret, i, i_end, imgid, error_code;
|
||||
size_t value_length= 0;
|
||||
char *value= NULL, msg[ISO_MSGS_MESSAGE_LEN], severity[80];
|
||||
unsigned char *vpt;
|
||||
static char *name= "isofs.di";
|
||||
|
||||
#ifdef NIX
|
||||
/* <<< */
|
||||
Xorriso_get_di_counteR++;
|
||||
#endif /* NIX */
|
||||
|
||||
*dev= 0;
|
||||
*ino= 0;
|
||||
ret= iso_node_lookup_attr(node, name, &value_length, &value, 0);
|
||||
if(ret <= 0) {
|
||||
/* Drop any pending messages because there is no xorriso to take them */
|
||||
iso_obtain_msgs("NEVER", &error_code, &imgid, msg, severity);
|
||||
return(ret);
|
||||
}
|
||||
vpt= (unsigned char *) value;
|
||||
for(i= 1; i <= vpt[0] && i < value_length; i++)
|
||||
*dev= ((*dev) << 8) | vpt[i];
|
||||
i_end= i + vpt[i] + 1;
|
||||
for(i++; i < i_end && i < value_length; i++)
|
||||
*ino= ((*ino) << 8) | vpt[i];
|
||||
free(value);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__di_ino_cmp(const void *p1, const void *p2)
|
||||
{
|
||||
int ret;
|
||||
IsoNode *n1, *n2;
|
||||
dev_t d1, d2;
|
||||
ino_t i1, i2;
|
||||
|
||||
n1= *((IsoNode **) p1);
|
||||
n2= *((IsoNode **) p2);
|
||||
|
||||
ret= Xorriso__get_di(n1, &d1, &i1, 0);
|
||||
if(ret <= 0)
|
||||
{d1= 0; i1= 0;}
|
||||
ret= Xorriso__get_di(n2, &d2, &i2, 0);
|
||||
if(ret <= 0)
|
||||
{d2= 0; i2= 0;}
|
||||
|
||||
if(d1 < d2)
|
||||
return(-1);
|
||||
if(d1 > d2)
|
||||
return(1);
|
||||
if(i1 < i2)
|
||||
return(-1);
|
||||
if(i1 > i2)
|
||||
return(1);
|
||||
if(d1 == 0 && i1 == 0 && n1 != n2)
|
||||
return(n1 < n2 ? -1 : 1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__di_cmp(const void *p1, const void *p2)
|
||||
{
|
||||
int ret;
|
||||
IsoNode *n1, *n2;
|
||||
|
||||
ret= Xorriso__di_ino_cmp(p1, p2);
|
||||
if(ret)
|
||||
return(ret);
|
||||
n1= *((IsoNode **) p1);
|
||||
n2= *((IsoNode **) p2);
|
||||
if(n1 != n2)
|
||||
return(n1 < n2 ? -1 : 1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__sort_di(void *node_array[], int count, int flag)
|
||||
{
|
||||
if(count <= 0)
|
||||
return(0);
|
||||
qsort(node_array, count, sizeof(IsoNode *), Xorriso__di_cmp);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_invalidate_di_item(struct XorrisO *xorriso, IsoNode *node,
|
||||
int flag)
|
||||
{
|
||||
int ret, idx;
|
||||
|
||||
if(xorriso->di_array == NULL)
|
||||
return(1);
|
||||
ret= Xorriso__search_node(xorriso->di_array, xorriso->di_count,
|
||||
Xorriso__di_cmp, node, &idx, 0);
|
||||
if(ret <= 0)
|
||||
return(ret == 0);
|
||||
if(xorriso->di_array[idx] != NULL)
|
||||
iso_node_unref(xorriso->di_array[idx]);
|
||||
xorriso->di_array[idx]= NULL;
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= return 1 even if matching nodes were found but node is
|
||||
not among them
|
||||
bit1= use Xorriso__di_cmp() rather than Xorriso__di_ino_cmp()
|
||||
*/
|
||||
int Xorriso_search_di_range(struct XorrisO *xorriso, IsoNode *node,
|
||||
int *idx, int *low, int *high, int flag)
|
||||
{
|
||||
int ret, i, found;
|
||||
int (*cmp)(const void *p1, const void *p2)= Xorriso__di_ino_cmp;
|
||||
|
||||
if(flag & 2)
|
||||
cmp= Xorriso__di_cmp;
|
||||
|
||||
*high= *low= *idx= -1;
|
||||
ret= Xorriso__search_node(xorriso->di_array, xorriso->di_count,
|
||||
cmp, node, &found, 0);
|
||||
if(ret <= 0)
|
||||
return(0);
|
||||
*low= *high= found;
|
||||
for(i= found + 1; i < xorriso->di_count; i++)
|
||||
if(xorriso->di_array[i] != NULL) {
|
||||
if((*cmp)(&node, &(xorriso->di_array[i])) != 0)
|
||||
break;
|
||||
*high= i;
|
||||
}
|
||||
for(i= found - 1; i >= 0; i--)
|
||||
if(xorriso->di_array[i] != NULL) {
|
||||
if((*cmp)(&node, &(xorriso->di_array[i])) != 0)
|
||||
break;
|
||||
*low= i;
|
||||
}
|
||||
for(i= *low; i <= *high; i++)
|
||||
if(xorriso->di_array[i] == node) {
|
||||
*idx= i;
|
||||
break;
|
||||
}
|
||||
return(*idx >= 0 || (flag & 1));
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__node_lba_cmp(const void *node1, const void *node2)
|
||||
{
|
||||
int ret;
|
||||
int lba1= 0, lba2= 0;
|
||||
|
||||
ret= Xorriso__file_start_lba(*((IsoNode **) node1), &lba1, 0);
|
||||
if(ret!=1)
|
||||
lba1= 0;
|
||||
ret= Xorriso__file_start_lba(*((IsoNode **) node2), &lba2, 0);
|
||||
if(ret!=1)
|
||||
lba2= 0;
|
||||
return(lba1-lba2);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso__node_name_cmp(const void *node1, const void *node2)
|
||||
{
|
||||
char *name1, *name2;
|
||||
|
||||
name1= (char *) iso_node_get_name(*((IsoNode **) node1));
|
||||
name2= (char *) iso_node_get_name(*((IsoNode **) node2));
|
||||
return(strcmp(name1,name2));
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= only accept directory nodes
|
||||
bit1= do not report memory usage as DEBUG
|
||||
bit2= do not apply search pattern but accept any node
|
||||
*/
|
||||
int Xorriso_sorted_node_array(struct XorrisO *xorriso,
|
||||
IsoDir *dir_node,
|
||||
int *nodec, IsoNode ***node_array,
|
||||
off_t boss_mem, int flag)
|
||||
{
|
||||
int i, ret, failed_at;
|
||||
char *npt;
|
||||
IsoDirIter *iter= NULL;
|
||||
IsoNode *node;
|
||||
off_t mem;
|
||||
|
||||
mem= ((*nodec)+1)*sizeof(IsoNode *);
|
||||
ret= Xorriso_check_temp_mem_limit(xorriso, mem+boss_mem, flag&2);
|
||||
if(ret<=0)
|
||||
return(ret);
|
||||
|
||||
*node_array= calloc(sizeof(IsoNode *), (*nodec)+1);
|
||||
if(*node_array==NULL) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Cannot allocate memory for %d directory entries", *nodec);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
ret= iso_dir_get_children(dir_node, &iter);
|
||||
if(ret<0) {
|
||||
Xorriso_cannot_create_iter(xorriso, ret, 0);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
for(i= 0; iso_dir_iter_next(iter, &node) == 1 && i<*nodec; ) {
|
||||
npt= (char *) iso_node_get_name(node);
|
||||
if(!(flag&4)) {
|
||||
ret= Xorriso_regexec(xorriso, npt, &failed_at, 0);
|
||||
if(ret)
|
||||
continue; /* no match */
|
||||
}
|
||||
if(flag&1)
|
||||
if(!LIBISO_ISDIR(node))
|
||||
continue;
|
||||
(*node_array)[i++]= node;
|
||||
}
|
||||
iso_dir_iter_free(iter);
|
||||
*nodec= i;
|
||||
if(*nodec<=0)
|
||||
return(1);
|
||||
qsort(*node_array, *nodec, sizeof(IsoNode *), Xorriso__node_name_cmp);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
int Xorriso_remake_hln_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, addon_nodes= 0, i, old_count, old_pt, new_pt;
|
||||
IsoNode **old_nodes;
|
||||
char **old_targets;
|
||||
|
||||
/* Count hln_targets of which the node has been deleted meanwhile */
|
||||
for(i= 0; i < xorriso->hln_count; i++) {
|
||||
if(xorriso->hln_targets[i] == NULL)
|
||||
continue;
|
||||
if(Xorriso_node_is_valid(xorriso, xorriso->hln_array[i], 0))
|
||||
continue;
|
||||
addon_nodes++;
|
||||
}
|
||||
ret= Xorriso_all_node_array(xorriso, addon_nodes, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
if(addon_nodes > 0) {
|
||||
/* Transfer delete nodes with hln_target to node array */
|
||||
for(i= 0; i < xorriso->hln_count; i++) {
|
||||
if(xorriso->hln_targets[i] == NULL)
|
||||
continue;
|
||||
if(Xorriso_node_is_valid(xorriso, xorriso->hln_array[i], 0))
|
||||
continue;
|
||||
if(xorriso->node_counter < xorriso->node_array_size) {
|
||||
xorriso->node_array[xorriso->node_counter++]= xorriso->hln_array[i];
|
||||
iso_node_ref(xorriso->node_array[xorriso->node_counter - 1]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Xorriso_sort_node_array(xorriso, 0);
|
||||
old_nodes= (IsoNode **) xorriso->hln_array;
|
||||
old_targets= (char **) xorriso->hln_targets;
|
||||
old_count= xorriso->hln_count;
|
||||
xorriso->hln_array= 0;
|
||||
xorriso->hln_targets= NULL;
|
||||
|
||||
/* Transfer node_array to di_array without unrefering nodes */
|
||||
xorriso->hln_count= xorriso->node_counter;
|
||||
xorriso->hln_array= xorriso->node_array;
|
||||
xorriso->node_counter= 0;
|
||||
xorriso->node_array_size= 0;
|
||||
xorriso->node_array= NULL;
|
||||
|
||||
/* Allocate hln_targets */
|
||||
ret= Xorriso_new_hln_array(xorriso, xorriso->temp_mem_limit, 1);
|
||||
if(ret<=0)
|
||||
goto ex;
|
||||
xorriso->node_targets_availmem= xorriso->temp_mem_limit;
|
||||
if(old_targets != NULL) {
|
||||
/* Transfer targets from old target array */;
|
||||
new_pt= old_pt= 0;
|
||||
while(new_pt < xorriso->hln_count && old_pt < old_count) {
|
||||
ret= Xorriso__hln_cmp(xorriso->hln_array[new_pt], old_nodes[old_pt]);
|
||||
if(ret < 0) {
|
||||
new_pt++;
|
||||
} else if(ret > 0) {
|
||||
old_pt++;
|
||||
} else {
|
||||
xorriso->hln_targets[new_pt]= old_targets[old_pt];
|
||||
if(old_targets[old_pt] != NULL)
|
||||
xorriso->temp_mem_limit-= strlen(old_targets[old_pt]) + 1;
|
||||
old_targets[old_pt]= NULL;
|
||||
new_pt++;
|
||||
old_pt++;
|
||||
}
|
||||
}
|
||||
for(old_pt= 0; old_pt < old_count; old_pt++)
|
||||
if(old_targets[old_pt] != NULL) /* (should not happen) */
|
||||
free(old_targets[old_pt]);
|
||||
free((char *) old_targets);
|
||||
}
|
||||
if(old_nodes != NULL) {
|
||||
for(old_pt= 0; old_pt < old_count; old_pt++)
|
||||
if(old_nodes[old_pt] != NULL)
|
||||
iso_node_unref(old_nodes[old_pt]);
|
||||
free((char *) old_nodes);
|
||||
}
|
||||
xorriso->hln_change_pending= 0;
|
||||
ret= 1;
|
||||
ex:;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= overwrite existing hln_array (else return 2)
|
||||
*/
|
||||
int Xorriso_make_hln_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if(xorriso->hln_array != NULL && !(flag & 1)) {
|
||||
/* If no fresh image manipulations occured: keep old array */
|
||||
if(!xorriso->hln_change_pending)
|
||||
return(2);
|
||||
ret= Xorriso_remake_hln_array(xorriso, 0);
|
||||
return(ret);
|
||||
}
|
||||
Xorriso_destroy_hln_array(xorriso, 0);
|
||||
|
||||
ret= Xorriso_all_node_array(xorriso, 0, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
Xorriso_sort_node_array(xorriso, 0);
|
||||
|
||||
/* Transfer node_array to di_array without unrefering nodes */
|
||||
xorriso->hln_count= xorriso->node_counter;
|
||||
xorriso->hln_array= xorriso->node_array;
|
||||
xorriso->node_counter= 0;
|
||||
xorriso->node_array_size= 0;
|
||||
xorriso->node_array= NULL;
|
||||
|
||||
/* Allocate hln_targets */
|
||||
ret= Xorriso_new_hln_array(xorriso, xorriso->temp_mem_limit, 1);
|
||||
if(ret<=0) {
|
||||
Xorriso_destroy_hln_array(xorriso, 0);
|
||||
goto ex;
|
||||
}
|
||||
xorriso->node_targets_availmem= xorriso->temp_mem_limit;
|
||||
xorriso->hln_change_pending= 0;
|
||||
ret= 1;
|
||||
ex:;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= overwrite existing di_array (else return 2)
|
||||
bit1= make di_array despite xorriso->ino_behavior bit 3
|
||||
*/
|
||||
int Xorriso_make_di_array(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, bytes;
|
||||
|
||||
#ifdef NIX
|
||||
/* <<< */
|
||||
unsigned long old_gdic;
|
||||
old_gdic= Xorriso_get_di_counteR;
|
||||
#endif /* NIX */
|
||||
|
||||
if((xorriso->ino_behavior & 8 ) && !(flag & 2))
|
||||
return(2);
|
||||
if(xorriso->di_array != NULL && !(flag & 1))
|
||||
return(2);
|
||||
Xorriso_finish_hl_update(xorriso, 0);
|
||||
|
||||
ret= Xorriso_all_node_array(xorriso, 0, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
bytes= xorriso->node_array_size / 8 + 1;
|
||||
xorriso->di_do_widen= calloc(bytes, 1);
|
||||
if(xorriso->di_do_widen == NULL) {
|
||||
Xorriso_no_malloc_memory(xorriso, NULL, 0);
|
||||
ret= -1; goto ex;
|
||||
}
|
||||
|
||||
/* Transfer node_array to di_array without unrefering nodes */
|
||||
xorriso->di_count= xorriso->node_counter;
|
||||
xorriso->di_array= xorriso->node_array;
|
||||
xorriso->node_counter= 0;
|
||||
xorriso->node_array_size= 0;
|
||||
xorriso->node_array= NULL;
|
||||
|
||||
Xorriso__sort_di((void *) xorriso->di_array, xorriso->di_count, 0);
|
||||
|
||||
ret= 1;
|
||||
ex:;
|
||||
|
||||
#ifdef NIX
|
||||
/* <<< */
|
||||
fprintf(stderr, "xorriso_DEBUG: sort_count= %lu\n",
|
||||
Xorriso_get_di_counteR - old_gdic);
|
||||
#endif /* NIX */
|
||||
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
@param flag bit0= iso_rr_path is freshly added and up to date
|
||||
bit2= -follow: this is not a command parameter
|
||||
@return -1= severe error
|
||||
0= not applicable for hard links
|
||||
1= go on with processing
|
||||
2= iso_rr_path is fully updated
|
||||
*/
|
||||
int Xorriso_hardlink_update(struct XorrisO *xorriso, int *compare_result,
|
||||
char *disk_path, char *iso_rr_path, int flag)
|
||||
{
|
||||
int ret, hret, idx, low, high, i, do_overwrite= 0, did_fake_di= 0;
|
||||
int follow_links, old_idx= -1;
|
||||
IsoNode *node;
|
||||
struct stat stbuf;
|
||||
dev_t old_dev;
|
||||
ino_t old_ino;
|
||||
|
||||
if(xorriso->di_array == NULL)
|
||||
return(1);
|
||||
follow_links= xorriso->do_follow_links ||
|
||||
(xorriso->do_follow_param && !(flag & 4));
|
||||
ret= Xorriso_node_from_path(xorriso, NULL, iso_rr_path, &node, 0);
|
||||
if(ret <= 0)
|
||||
return(ret);
|
||||
if(LIBISO_ISDIR(node))
|
||||
return(1);
|
||||
|
||||
/* Handle eventual hardlink split : */
|
||||
/* This is achieved by setting the content change bit. Reason:
|
||||
The node needs to be removed from di_array because its di is
|
||||
not matching its array index any more. So it becomes invisible for
|
||||
the join check of eventual later hardlink siblings. Therefore
|
||||
it must be updated now, even if it has currently no siblings
|
||||
which it leaves or which it joins.
|
||||
*/
|
||||
if(!(flag & 1))
|
||||
do_overwrite= 1;
|
||||
|
||||
Xorriso__get_di(node, &old_dev, &old_ino, 0);
|
||||
ret= Xorriso__search_node(xorriso->di_array, xorriso->di_count,
|
||||
Xorriso__di_cmp, node, &idx, 0);
|
||||
if(ret < 0)
|
||||
{ret= 0; goto ex;}
|
||||
if(ret > 0)
|
||||
old_idx= idx;
|
||||
|
||||
/* Handle eventual hardlink joining : */
|
||||
|
||||
if(follow_links)
|
||||
ret= stat(disk_path, &stbuf);
|
||||
else
|
||||
ret= lstat(disk_path, &stbuf);
|
||||
if(ret==-1)
|
||||
{ret= 0; goto ex;}
|
||||
|
||||
/* Are there new dev-ino-siblings in the image ? */
|
||||
/* Fake isofs.di */
|
||||
if(!(flag & 1)) {
|
||||
ret= Xorriso_record_dev_inode(xorriso, disk_path, stbuf.st_dev,
|
||||
stbuf.st_ino, node, iso_rr_path, 1);
|
||||
if(ret <= 0)
|
||||
{ret= -1; goto ex;}
|
||||
did_fake_di= 1;
|
||||
/* temporarily remove node from di_array so it does not disturb
|
||||
search by its fake di info */;
|
||||
if(old_idx >= 0)
|
||||
xorriso->di_array[old_idx]= NULL;
|
||||
}
|
||||
ret= Xorriso_search_di_range(xorriso, node, &idx, &low, &high, 1);
|
||||
if(did_fake_di) {
|
||||
/* Revoke fake of isofs.di */
|
||||
hret= Xorriso_record_dev_inode(xorriso, disk_path, old_dev, old_ino,
|
||||
node, iso_rr_path, 1);
|
||||
if(hret <= 0)
|
||||
{ret= -1; goto ex;}
|
||||
if(old_idx >= 0)
|
||||
xorriso->di_array[old_idx]= node;
|
||||
}
|
||||
if(ret == 0)
|
||||
{ret= 1; goto ex;}
|
||||
if(ret < 0)
|
||||
{ret= 0; goto ex;}
|
||||
|
||||
|
||||
#ifdef Xorriso_hardlink_update_debuG
|
||||
/* <<< */
|
||||
if(low < high || idx < 0) {
|
||||
fprintf(stderr,
|
||||
"xorriso_DEBUG: old_idx= %d , low= %d , high= %d , iso= '%s' , disk='%s'\n",
|
||||
old_idx, low, high, iso_rr_path, disk_path);
|
||||
fprintf(stderr,
|
||||
"xorriso_DEBUG: old_dev= %lu , old_ino= %lu , dev= %lu , ino= %lu\n",
|
||||
(unsigned long) old_dev, (unsigned long) old_ino,
|
||||
(unsigned long) stbuf.st_dev, (unsigned long) stbuf.st_ino);
|
||||
|
||||
if(idx >= 0 && idx != old_idx)
|
||||
fprintf(stderr, "xorriso_DEBUG: idx= %d , old_idx = %d\n", idx, old_idx);
|
||||
}
|
||||
#endif /* Xorriso_hardlink_update_debuG */
|
||||
|
||||
/* Overwrite all valid siblings : */
|
||||
for(i= low; i <= high; i++) {
|
||||
if(i == idx || xorriso->di_array[i] == NULL)
|
||||
continue;
|
||||
|
||||
#ifdef Xorriso_hardlink_update_debuG
|
||||
/* <<< */
|
||||
{
|
||||
ino_t ino;
|
||||
dev_t dev;
|
||||
|
||||
Xorriso__get_di(xorriso->di_array[i], &dev, &ino, 0);
|
||||
fprintf(stderr, "xorriso_DEBUG: iso_sibling= '%s' , dev= %lu , ino= %lu\n",
|
||||
node_path, (unsigned long) dev, (unsigned long) ino);
|
||||
}
|
||||
#endif /* Xorriso_hardlink_update_debuG */
|
||||
|
||||
xorriso->di_do_widen[i / 8]|= 1 << (i % 8);
|
||||
}
|
||||
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(do_overwrite)
|
||||
*compare_result|= (1<<15);
|
||||
if(old_idx >= 0 && (*compare_result & (3 << 21))) {
|
||||
/* The old di info is obsolete */
|
||||
if(xorriso->di_array[old_idx] != NULL)
|
||||
iso_node_unref(xorriso->di_array[old_idx]);
|
||||
xorriso->di_array[old_idx]= NULL;
|
||||
}
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/* @param flag bit0= do not destroy di_array
|
||||
*/
|
||||
int Xorriso_finish_hl_update(struct XorrisO *xorriso, int flag)
|
||||
{
|
||||
int ret, zero= 0;
|
||||
char *argv[4];
|
||||
struct Xorriso_lsT *disk_lst, *iso_lst;
|
||||
|
||||
if(xorriso->di_array == NULL)
|
||||
{ret= 1; goto ex;}
|
||||
disk_lst= xorriso->di_disk_paths;
|
||||
iso_lst= xorriso->di_iso_paths;
|
||||
while(disk_lst != NULL && iso_lst != NULL) {
|
||||
argv[0]= Xorriso_lst_get_text(iso_lst, 0);
|
||||
argv[1]= "-exec";
|
||||
argv[2]= "widen_hardlinks";
|
||||
argv[3]= Xorriso_lst_get_text(disk_lst, 0);
|
||||
zero= 0;
|
||||
ret= Xorriso_option_find(xorriso, 4, argv, &zero, 0); /* -findi */
|
||||
if(ret < 0)
|
||||
goto ex;
|
||||
disk_lst= Xorriso_lst_get_next(disk_lst, 0);
|
||||
iso_lst= Xorriso_lst_get_next(iso_lst, 0);
|
||||
}
|
||||
ret= 1;
|
||||
ex:;
|
||||
if(!(flag & 1))
|
||||
Xorriso_destroy_di_array(xorriso, 0);
|
||||
return(ret);
|
||||
}
|
||||
|
62
xorriso/sort_cmp.h
Normal file
62
xorriso/sort_cmp.h
Normal file
@ -0,0 +1,62 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which sort and compare
|
||||
tree nodes.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_sort_cmp_includeD
|
||||
#define Xorriso_pvt_sort_cmp_includeD yes
|
||||
|
||||
|
||||
int Xorriso__findi_sorted_ino_cmp(const void *p1, const void *p2);
|
||||
|
||||
int Xorriso__hln_cmp(const void *p1, const void *p2);
|
||||
|
||||
int Xorriso__findi_sorted_cmp(const void *p1, const void *p2);
|
||||
|
||||
int Xorriso__search_node(void *node_array[], int n,
|
||||
int (*cmp)(const void *p1, const void *p2),
|
||||
void *node, int *idx, int flag);
|
||||
|
||||
int Xorriso_search_in_hln_array(struct XorrisO *xorriso,
|
||||
void *node, int *idx, int flag);
|
||||
|
||||
int Xorriso__get_di(IsoNode *node, dev_t *dev, ino_t *ino, int flag);
|
||||
|
||||
int Xorriso__di_ino_cmp(const void *p1, const void *p2);
|
||||
|
||||
int Xorriso__di_cmp(const void *p1, const void *p2);
|
||||
|
||||
int Xorriso__sort_di(void *node_array[], int count, int flag);
|
||||
|
||||
int Xorriso_invalidate_di_item(struct XorrisO *xorriso, IsoNode *node,
|
||||
int flag);
|
||||
|
||||
int Xorriso_search_di_range(struct XorrisO *xorriso, IsoNode *node,
|
||||
int *idx, int *low, int *high, int flag);
|
||||
|
||||
int Xorriso__node_lba_cmp(const void *node1, const void *node2);
|
||||
|
||||
int Xorriso__node_name_cmp(const void *node1, const void *node2);
|
||||
|
||||
int Xorriso_sorted_node_array(struct XorrisO *xorriso,
|
||||
IsoDir *dir_node,
|
||||
int *nodec, IsoNode ***node_array,
|
||||
off_t boss_mem, int flag);
|
||||
|
||||
int Xorriso_remake_hln_array(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_make_di_array(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_search_hardlinks(struct XorrisO *xorriso, IsoNode *node,
|
||||
int *node_idx, int *min_hl, int *max_hl, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_sort_cmp_includeD */
|
||||
|
1990
xorriso/text_io.c
Normal file
1990
xorriso/text_io.c
Normal file
File diff suppressed because it is too large
Load Diff
90
xorriso/text_io.h
Normal file
90
xorriso/text_io.h
Normal file
@ -0,0 +1,90 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of text i/o functions.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_textio_includeD
|
||||
#define Xorriso_pvt_textio_includeD yes
|
||||
|
||||
|
||||
int Xorriso_dialog_input(struct XorrisO *xorriso, char line[], int linesize,
|
||||
int flag);
|
||||
|
||||
/** @return -1= abort , 0= no , 1= yes
|
||||
*/
|
||||
int Xorriso_reassure(struct XorrisO *xorriso, char *cmd, char *which_will,
|
||||
int flag);
|
||||
|
||||
int Xorriso_request_confirmation(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* @param flag bit0= quoted multiline mode
|
||||
bit1= release allocated memory and return 1
|
||||
bit2= with bit0: warn of empty text arguments
|
||||
bit3= deliver as single quoted text including all whitespace
|
||||
and without any backslash interpretation
|
||||
@return -1=out of memory , 0=line format error , 1=ok, go on , 2=done
|
||||
*/
|
||||
int Xorriso_read_lines(struct XorrisO *xorriso, FILE *fp, int *linecount,
|
||||
int *argc, char ***argv, int flag);
|
||||
|
||||
int Xorriso_write_to_channel(struct XorrisO *xorriso,
|
||||
char *in_text, int channel_no, int flag);
|
||||
|
||||
int Xorriso_result(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_restxt(struct XorrisO *xorriso, char *text);
|
||||
|
||||
int Xorriso_info(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_mark(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
int Xorriso_write_session_log(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
int Xorriso_status_result(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
int flag);
|
||||
|
||||
int Xorriso_status(struct XorrisO *xorriso, char *filter, FILE *fp, int flag);
|
||||
|
||||
int Xorriso_pacifier_reset(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* This call is to be issued by long running workers in short intervals.
|
||||
It will check whether enough time has elapsed since the last pacifier
|
||||
message and eventually issue an update message.
|
||||
@param what_done A sparse description of the action, preferrably in past
|
||||
tense. E.g. "done" , "files added".
|
||||
@param count The number of objects processed so far.
|
||||
Is ignored if <=0.
|
||||
@param todo The number of objects to be done in total.
|
||||
Is ignored if <=0.
|
||||
@param current_object A string telling the object currently processed.
|
||||
Ignored if "".
|
||||
@param flag bit0= report unconditionally, no time check
|
||||
*/
|
||||
int Xorriso_pacifier_callback(struct XorrisO *xorriso, char *what_done,
|
||||
off_t count, off_t todo, char *current_object,
|
||||
int flag);
|
||||
|
||||
int Xorriso_reset_counters(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_no_malloc_memory(struct XorrisO *xorriso, char **to_free,
|
||||
int flag);
|
||||
|
||||
int Xorriso_much_too_long(struct XorrisO *xorriso, int len, int flag);
|
||||
|
||||
int Xorriso_no_findjob(struct XorrisO *xorriso, char *cmd, int flag);
|
||||
|
||||
int Xorriso_report_md5_outcome(struct XorrisO *xorriso, char *severity,
|
||||
int flag);
|
||||
|
||||
int Xorriso_protect_stdout(struct XorrisO *xorriso, int flag);
|
||||
|
||||
#endif /* ! Xorriso_pvt_textio_includeD */
|
||||
|
2106
xorriso/write_run.c
Normal file
2106
xorriso/write_run.c
Normal file
File diff suppressed because it is too large
Load Diff
53
xorriso/write_run.h
Normal file
53
xorriso/write_run.h
Normal file
@ -0,0 +1,53 @@
|
||||
|
||||
/* xorriso - creates, loads, manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Provided under GPL version 2 or later.
|
||||
|
||||
This file contains declarations of functions which are needed to write
|
||||
sessions.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef Xorriso_pvt_write_run_includeD
|
||||
#define Xorriso_pvt_write_run_includeD yes
|
||||
|
||||
|
||||
/* CD specs say one shall not write tracks < 600 kiB */
|
||||
#define Xorriso_cd_min_track_sizE 300
|
||||
|
||||
|
||||
/* Default setting for -compliance */
|
||||
#define Xorriso_relax_compliance_defaulT \
|
||||
(isoburn_igopt_allow_deep_paths | isoburn_igopt_allow_longer_paths | \
|
||||
isoburn_igopt_always_gmt | \
|
||||
isoburn_igopt_rrip_version_1_10 | isoburn_igopt_aaip_susp_1_10 | \
|
||||
isoburn_igopt_only_iso_versions | isoburn_igopt_no_j_force_dots)
|
||||
|
||||
|
||||
int Xorriso_make_write_options(
|
||||
struct XorrisO *xorriso, struct burn_drive *drive,
|
||||
struct burn_write_opts **burn_options, int flag);
|
||||
|
||||
int Xorriso_sanitize_image_size(struct XorrisO *xorriso,
|
||||
struct burn_drive *drive, struct burn_disc *disc,
|
||||
struct burn_write_opts *burn_options, int flag);
|
||||
|
||||
int Xorriso_auto_format(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_set_system_area(struct XorrisO *xorriso, struct burn_drive *drive,
|
||||
IsoImage *img, struct isoburn_imgen_opts *sopts,
|
||||
int flag);
|
||||
|
||||
int Xorriso_check_burn_abort(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_pacifier_loop(struct XorrisO *xorriso, struct burn_drive *drive,
|
||||
int flag);
|
||||
|
||||
int Xorriso_set_isolinux_options(struct XorrisO *xorriso,
|
||||
IsoImage *image, int flag);
|
||||
|
||||
|
||||
#endif /* ! Xorriso_pvt_write_run_includeD */
|
||||
|
21301
xorriso/xorriso.c
21301
xorriso/xorriso.c
File diff suppressed because it is too large
Load Diff
@ -574,6 +574,9 @@ int Xorriso_option_chowni(struct XorrisO *xorriso, char *uid,
|
||||
/* Option -close "on"|"off" */
|
||||
int Xorriso_option_close(struct XorrisO *xorriso, char *mode, int flag);
|
||||
|
||||
/* Option -close_filter_list */
|
||||
int Xorriso_option_close_filter_list(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* Option -commit */
|
||||
/* @param flag bit0= leave indrive and outdrive aquired as they were,
|
||||
i.e. do not aquire outdrive as new in-out-drive
|
||||
@ -596,6 +599,9 @@ int Xorriso_option_commit_eject(struct XorrisO *xorriso, char *which, int flag);
|
||||
int Xorriso_option_compare(struct XorrisO *xorriso, char *disk_path,
|
||||
char *iso_path, int flag);
|
||||
|
||||
/* Option -compliance */
|
||||
int Xorriso_option_compliance(struct XorrisO *xorriso, char *mode, int flag);
|
||||
|
||||
/* Option -cpr alias -cpri */
|
||||
int Xorriso_option_cpri( struct XorrisO *xorriso, int argc, char **argv,
|
||||
int *idx, int flag);
|
||||
@ -676,8 +682,10 @@ int Xorriso_option_extract(struct XorrisO *xorriso, char *disk_path,
|
||||
int Xorriso_option_extract_cut(struct XorrisO *xorriso, char *iso_rr_path,
|
||||
char *start, char *count, char *disk_path, int flag);
|
||||
|
||||
/* Option -follow */
|
||||
int Xorriso_option_follow(struct XorrisO *xorriso, char *mode, int flag);
|
||||
/* Option -file_size_limit */
|
||||
int Xorriso_option_file_size_limit(struct XorrisO *xorriso,
|
||||
int argc, char **argv, int *idx, int flag);
|
||||
|
||||
|
||||
/* Option -find alias -findi, and -findx */
|
||||
/* @param flag bit0= -findx rather than -findi
|
||||
@ -687,6 +695,9 @@ int Xorriso_option_follow(struct XorrisO *xorriso, char *mode, int flag);
|
||||
int Xorriso_option_find(struct XorrisO *xorriso, int argc, char **argv,
|
||||
int *idx, int flag);
|
||||
|
||||
/* Option -follow */
|
||||
int Xorriso_option_follow(struct XorrisO *xorriso, char *mode, int flag);
|
||||
|
||||
/* Option -fs */
|
||||
int Xorriso_option_fs(struct XorrisO *xorriso, char *size, int flag);
|
||||
|
||||
@ -811,6 +822,9 @@ int Xorriso_option_not_leaf(struct XorrisO *xorriso, char *pattern, int flag);
|
||||
/* @param flag bit0= -quoted_not_list */
|
||||
int Xorriso_option_not_list(struct XorrisO *xorriso, char *adr, int flag);
|
||||
|
||||
/* Option -not_mgt */
|
||||
int Xorriso_option_not_mgt(struct XorrisO *xorriso, char *setting, int flag);
|
||||
|
||||
/* Option -not_paths */
|
||||
int Xorriso_option_not_paths(struct XorrisO *xorriso, int argc, char **argv,
|
||||
int *idx, int flag);
|
||||
@ -860,6 +874,9 @@ int Xorriso_option_print_size(struct XorrisO *xorriso, int flag);
|
||||
/* Option -prog */
|
||||
int Xorriso_option_prog(struct XorrisO *xorriso, char *name, int flag);
|
||||
|
||||
/* Option -prompt */
|
||||
int Xorriso_option_prompt(struct XorrisO *xorriso, char *text, int flag);
|
||||
|
||||
/* Option -prog_help */
|
||||
int Xorriso_option_prog_help(struct XorrisO *xorriso, char *name, int flag);
|
||||
|
||||
|
229
xorriso/xorriso_main.c
Normal file
229
xorriso/xorriso_main.c
Normal file
@ -0,0 +1,229 @@
|
||||
|
||||
/*
|
||||
|
||||
( cd .. ; libisoburn-develop/xorriso/compile_xorriso.sh -g )
|
||||
|
||||
*/
|
||||
|
||||
/* Command line oriented batch and dialog tool which creates, loads,
|
||||
manipulates and burns ISO 9660 filesystem images.
|
||||
|
||||
Copyright 2007-2010 Thomas Schmitt, <scdbackup@gmx.net>
|
||||
|
||||
Initial code of this program was derived from program src/askme.c out
|
||||
of scdbackup-0.8.8, Copyright 2007 Thomas Schmitt, BSD-License.
|
||||
|
||||
Provided under GPL version 2 or later, with the announcement that this
|
||||
might get changed in future. I would prefer BSD or LGPL as soon as the
|
||||
license situation of the library code allows that.
|
||||
(This announcement affects only future releases of xorriso and it will
|
||||
always be possible to derive a GPLv2+ from the future license.)
|
||||
|
||||
There is a derived package "GNU xorriso" under GPLv3+ which combines the
|
||||
libburnia libraries and program xorriso to a statically linked binary.
|
||||
|
||||
|
||||
Overview of xorriso architecture:
|
||||
|
||||
libburn provides the ability to read and write data.
|
||||
|
||||
libisofs interprets and manipulates ISO 9660 directory trees. It generates
|
||||
the output stream which is handed over to libburn.
|
||||
|
||||
libisoburn encapsulates the connectivity issues between libburn and
|
||||
libisofs. It also enables multi-session emulation on overwritable media
|
||||
and random access file objects.
|
||||
xorriso is intended as reference application of libisoburn.
|
||||
|
||||
xorriso.h exposes the public functions of xorriso which are intended
|
||||
to be used by programs which link with xorriso.o. These functions are
|
||||
direct equivalents of the xorriso interpreter commands.
|
||||
There is also the API for handling event messages.
|
||||
|
||||
The source is divided in two groups:
|
||||
|
||||
A set of source modules interacts with the libraries:
|
||||
base_obj.[ch] fundamental operations of the XorrisO object
|
||||
lib_mgt.[ch] manages the relation between xorriso and the libraries
|
||||
drive_mgt.[ch] operates on drives and media
|
||||
iso_img.[ch] operates on ISO images and their global properties
|
||||
iso_tree.[ch] access nodes of the libisofs tree model
|
||||
iso_manip.[ch] manipulates the libisofs tree model
|
||||
sort_cmp.[ch] sorts and compare tree nodes
|
||||
write_run.[ch] functions to write sessions
|
||||
read_run.[ch] functions to read data from ISO image
|
||||
filters.[ch] operates on data filter objects
|
||||
xorrisoburn.h declarations needed by the non-library modules
|
||||
|
||||
Another set is independent of the liburnia libraries:
|
||||
parse_exec.c deals with parsing and interpretation of command input
|
||||
sfile.c functions around files and strings
|
||||
aux_objects.c various helper classes
|
||||
misc_funct.c miscellaneous helper functions
|
||||
findjob.c performs tree searches in libisofs or in POSIX filesystem
|
||||
check_media.c perform verifying runs on media resp. images
|
||||
text_io.c text i/o functions
|
||||
match.c functions for pattern matching
|
||||
emulators.c emulators for mkisofs and cdrecord
|
||||
disk_ops.c actions on onjects of disk filesystems
|
||||
cmp_update.c compare or update files between disk filesystem and
|
||||
ISO filesystem
|
||||
opts_a_c.c options -a* to -c*
|
||||
opts_d_h.c options -d* to -h*
|
||||
opts_i_o.c options -i* to -o*
|
||||
opts_p_z.c options -p* to -z*
|
||||
|
||||
xorriso_main.c the main program
|
||||
|
||||
xorriso_private.h contains the definition of struct Xorriso and for
|
||||
convenience includes the .h files of the non-library group.
|
||||
|
||||
*/
|
||||
|
||||
/* This may be changed to Xorriso_GNU_xorrisO in order to create GNU xorriso */
|
||||
#define Xorriso_libburnia_xorrisO yes
|
||||
|
||||
|
||||
|
||||
#include <ctype.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <locale.h>
|
||||
|
||||
/* The official xorriso options API. "No shortcuts" */
|
||||
#include "xorriso.h"
|
||||
|
||||
|
||||
|
||||
#ifdef Xorriso_without_subS
|
||||
|
||||
/* xorriso consists only of a main() stub which has an own version to match
|
||||
the version of libxorriso header and runtime code.
|
||||
*/
|
||||
#define Xorriso_main_program_versioN "0.5.7"
|
||||
|
||||
#else /* Xorriso_without_subS */
|
||||
|
||||
/* Make sure that both version tests always match. */
|
||||
#define Xorriso_main_program_versioN Xorriso_program_versioN
|
||||
|
||||
#endif /* ! Xorriso_without_subS */
|
||||
|
||||
|
||||
static void yell_xorriso()
|
||||
{
|
||||
fprintf(stderr,
|
||||
"%sxorriso %s%s : RockRidge filesystem manipulator, libburnia project.\n\n",
|
||||
#ifdef Xorriso_GNU_xorrisO
|
||||
"GNU ",
|
||||
#else
|
||||
"",
|
||||
#endif
|
||||
Xorriso_main_program_versioN, Xorriso_program_patch_leveL);
|
||||
}
|
||||
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int ret, i;
|
||||
struct XorrisO *xorriso= NULL;
|
||||
char **orig_argv= NULL;
|
||||
|
||||
if(strcmp(Xorriso_main_program_versioN, Xorriso_program_versioN)) {
|
||||
yell_xorriso();
|
||||
fprintf(stderr,
|
||||
"xorriso : FATAL : libxorriso compile time version mismatch. Found %s\n\n",
|
||||
Xorriso_program_versioN);
|
||||
exit(4);
|
||||
}
|
||||
if(strcmp(Xorriso_program_versioN, Xorriso__get_version_text(0))) {
|
||||
yell_xorriso();
|
||||
fprintf(stderr,
|
||||
"xorriso : FATAL : libxorriso runtime version mismatch. Found %s\n\n",
|
||||
Xorriso__get_version_text(0));
|
||||
exit(4);
|
||||
}
|
||||
|
||||
if(argc < 2) {
|
||||
yell_xorriso();
|
||||
fprintf(stderr,"usage : %s [options]\n", argv[0]);
|
||||
fprintf(stderr, " More is told by option -help\n");
|
||||
exit(2);
|
||||
}
|
||||
setlocale(LC_CTYPE, "");
|
||||
ret= Xorriso_new(&xorriso, argv[0], 0);
|
||||
if(ret <= 0) {
|
||||
fprintf(stderr,"Creation of XorrisO object failed. (not enough memory ?)\n");
|
||||
exit(3);
|
||||
}
|
||||
|
||||
/* The prescan of arguments performs actions which have to happen before
|
||||
the normal processing of startup files and arguments.
|
||||
*/
|
||||
ret= Xorriso_prescan_args(xorriso,argc,argv,0);
|
||||
if(ret == 0)
|
||||
goto end_sucessfully;
|
||||
if(ret < 0)
|
||||
exit(5);
|
||||
|
||||
yell_xorriso();
|
||||
|
||||
/* The following functions are allowed only after this initialization */
|
||||
ret= Xorriso_startup_libraries(xorriso, 0);
|
||||
if(ret <= 0)
|
||||
{ret= 4; goto emergency_exit;}
|
||||
Xorriso_process_msg_queues(xorriso, 0);
|
||||
|
||||
/* Interpret startup files */
|
||||
ret= Xorriso_read_rc(xorriso, 0);
|
||||
if(ret == 3)
|
||||
goto end_sucessfully;
|
||||
if(ret <= 0)
|
||||
{ret= 5; goto emergency_exit;}
|
||||
|
||||
/* Interpret program arguments */
|
||||
orig_argv= argv;
|
||||
ret= Xorriso_program_arg_bsl(xorriso, argc, &argv, 0);
|
||||
if(ret <= 0)
|
||||
{ret= 5; goto emergency_exit;}
|
||||
i= 1;
|
||||
ret= Xorriso_interpreter(xorriso, argc, argv, &i, 2);
|
||||
if(ret == 3)
|
||||
goto end_sucessfully;
|
||||
if(ret <= 0)
|
||||
{ret= 5; goto emergency_exit;}
|
||||
|
||||
/* Enter dialog mode if it has been activated meanwhile */
|
||||
ret= Xorriso_dialog(xorriso, 0);
|
||||
if(ret <= 0)
|
||||
{ret= 6; goto emergency_exit;}
|
||||
|
||||
end_sucessfully:; /* normal shutdown, including eventual -commit */
|
||||
Xorriso_process_msg_queues(xorriso, 0);
|
||||
if(Xorriso_change_is_pending(xorriso, 0))
|
||||
Xorriso_option_end(xorriso, 2);
|
||||
Xorriso_process_msg_queues(xorriso, 0);
|
||||
ret= Xorriso_make_return_value(xorriso, 0);
|
||||
Xorriso_process_errfile(xorriso, 0, "xorriso end", 0, 1);
|
||||
Xorriso_destroy(&xorriso, 1);
|
||||
if(orig_argv != argv && orig_argv != NULL) {
|
||||
for(i= 0; i < argc; i++)
|
||||
if(argv[i] != NULL)
|
||||
free(argv[i]);
|
||||
free(argv);
|
||||
}
|
||||
exit(ret);
|
||||
|
||||
emergency_exit:;
|
||||
if(xorriso != NULL) { /* minimal shutdown */
|
||||
Xorriso_process_msg_queues(xorriso, 0);
|
||||
Xorriso_destroy(&xorriso, 1);
|
||||
}
|
||||
exit(ret);
|
||||
}
|
||||
|
||||
|
@ -23,7 +23,7 @@ xorriso_xorriso_CPPFLAGS = -I./libburn -I./libisofs -I./libisoburn -I./xorriso
|
||||
|
||||
# No readline in the vanilla version because the necessary headers
|
||||
# are in a separate readline-development package.
|
||||
xorriso_xorriso_CFLAGS = -DXorriso_standalonE -DXorriso_with_maiN \
|
||||
xorriso_xorriso_CFLAGS = -DXorriso_standalonE \
|
||||
$(READLINE_DEF) $(LIBACL_DEF) $(XATTR_DEF) \
|
||||
$(EXTF_DEF) $(EXTF_SUID_DEF) $(ZLIB_DEF) \
|
||||
$(LIBCDIO_DEF) \
|
||||
@ -48,9 +48,56 @@ xorriso_xorriso_SOURCES = \
|
||||
\
|
||||
xorriso/xorriso.h \
|
||||
xorriso/xorriso_private.h \
|
||||
xorriso/xorriso.c \
|
||||
xorriso/xorriso_main.c \
|
||||
xorriso/sfile.h \
|
||||
xorriso/sfile.c \
|
||||
xorriso/aux_objects.h \
|
||||
xorriso/aux_objects.c \
|
||||
xorriso/findjob.h \
|
||||
xorriso/findjob.c \
|
||||
xorriso/check_media.h \
|
||||
xorriso/check_media.c \
|
||||
xorriso/misc_funct.h \
|
||||
xorriso/misc_funct.c \
|
||||
xorriso/text_io.h \
|
||||
xorriso/text_io.c \
|
||||
xorriso/match.h \
|
||||
xorriso/match.c \
|
||||
xorriso/emulators.h \
|
||||
xorriso/emulators.c \
|
||||
xorriso/disk_ops.h \
|
||||
xorriso/disk_ops.c \
|
||||
xorriso/cmp_update.h \
|
||||
xorriso/cmp_update.c \
|
||||
xorriso/parse_exec.h \
|
||||
xorriso/parse_exec.c \
|
||||
xorriso/opts_a_c.c \
|
||||
xorriso/opts_d_h.c \
|
||||
xorriso/opts_i_o.c \
|
||||
xorriso/opts_p_z.c \
|
||||
\
|
||||
xorriso/xorrisoburn.h \
|
||||
xorriso/xorrisoburn.c \
|
||||
xorriso/base_obj.h \
|
||||
xorriso/base_obj.c \
|
||||
xorriso/lib_mgt.h \
|
||||
xorriso/lib_mgt.c \
|
||||
xorriso/sort_cmp.h \
|
||||
xorriso/sort_cmp.c \
|
||||
xorriso/drive_mgt.h \
|
||||
xorriso/drive_mgt.c \
|
||||
xorriso/iso_img.h \
|
||||
xorriso/iso_img.c \
|
||||
xorriso/iso_tree.h \
|
||||
xorriso/iso_tree.c \
|
||||
xorriso/iso_manip.h \
|
||||
xorriso/iso_manip.c \
|
||||
xorriso/write_run.h \
|
||||
xorriso/write_run.c \
|
||||
xorriso/read_run.h \
|
||||
xorriso/read_run.c \
|
||||
xorriso/filters.h \
|
||||
xorriso/filters.c \
|
||||
\
|
||||
xorriso/xorriso_timestamp.h \
|
||||
xorriso/xorriso_buildstamp.h \
|
||||
\
|
||||
|
@ -33,19 +33,16 @@
|
||||
#define Xorriso_build_timestamP "-none-given-"
|
||||
#endif
|
||||
|
||||
#include <regex.h>
|
||||
|
||||
#include "sfile.h"
|
||||
#include "misc_funct.h"
|
||||
|
||||
|
||||
#define Smem_malloC malloc
|
||||
#define Smem_freE free
|
||||
#define SfileadrL 4096
|
||||
|
||||
struct LinkiteM; /* Trace of hops during symbolic link resolution */
|
||||
struct ExclusionS; /* List of -not_* conditions */
|
||||
struct PermiteM; /* Stack of temporarily altered access permissions */
|
||||
struct SpotlisT; /* List of intervals with different read qualities */
|
||||
struct CheckmediajoB; /* Parameters for Xorriso_check_media() */
|
||||
struct SectorbitmaP; /* Distiniction between valid and invalid sectors */
|
||||
struct FindjoB; /* Program and status of a find run */
|
||||
|
||||
|
||||
/* maximum number of history lines to be reported with -status:long_history */
|
||||
@ -502,860 +499,18 @@ struct XorrisO { /* the global context of xorriso */
|
||||
};
|
||||
|
||||
|
||||
int Xorriso__get_signal_behavior(int flag);
|
||||
#include "base_obj.h"
|
||||
#include "aux_objects.h"
|
||||
#include "findjob.h"
|
||||
#include "check_media.h"
|
||||
#include "misc_funct.h"
|
||||
#include "text_io.h"
|
||||
#include "match.h"
|
||||
#include "emulators.h"
|
||||
#include "disk_ops.h"
|
||||
#include "cmp_update.h"
|
||||
#include "parse_exec.h"
|
||||
|
||||
int Xorriso_prepare_regex(struct XorrisO *xorriso, char *adr, int flag);
|
||||
|
||||
int Xorriso_result(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_info(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_request_confirmation(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* @return 0=match , else no match
|
||||
*/
|
||||
int Xorriso_regexec(struct XorrisO *xorriso, char *to_match, int *failed_at,
|
||||
int flag);
|
||||
|
||||
int Xorriso_prepare_expansion_pattern(struct XorrisO *xorriso, char *pattern,
|
||||
int flag);
|
||||
|
||||
int Xorriso__mode_to_perms(mode_t st_mode, char perms[11], int flag);
|
||||
|
||||
int Xorriso_much_too_long(struct XorrisO *xorriso, int len, int flag);
|
||||
|
||||
int Xorriso_check_temp_mem_limit(struct XorrisO *xorriso, off_t mem, int flag);
|
||||
|
||||
int Xorriso_eval_nonmatch(struct XorrisO *xorriso, char *pattern,
|
||||
int *nonconst_mismatches, off_t *mem, int flag);
|
||||
|
||||
/* @param flag bit0= a match count !=1 is a SORRY event
|
||||
*/
|
||||
int Xorriso_check_matchcount(struct XorrisO *xorriso,
|
||||
int count, int nonconst_mismatches, int num_patterns,
|
||||
char **patterns, int flag);
|
||||
|
||||
int Xorriso_no_pattern_memory(struct XorrisO *xorriso, off_t mem, int flag);
|
||||
|
||||
int Xorriso_alloc_pattern_mem(struct XorrisO *xorriso, off_t mem,
|
||||
int count, char ***filev, int flag);
|
||||
|
||||
/* @param flag bit0= count results rather than storing them
|
||||
@return <=0 error , 1 is root (end processing) ,
|
||||
2 is not root (go on processing)
|
||||
*/
|
||||
int Xorriso_check_for_root_pattern(struct XorrisO *xorriso,
|
||||
int *filec, char **filev, int count_limit, off_t *mem, int flag);
|
||||
|
||||
/* @param flag bit0= prepend wd only if name does not begin by '/'
|
||||
bit2= prepend wd (automatically done if wd[0]!=0)
|
||||
*/
|
||||
int Xorriso_make_abs_adr(struct XorrisO *xorriso, char *wd, char *name,
|
||||
char adr[], int flag);
|
||||
|
||||
/* @param flag bit0= count result rather than storing it
|
||||
bit1= unexpected change of number is a FATAL event
|
||||
*/
|
||||
int Xorriso_register_matched_adr(struct XorrisO *xorriso,
|
||||
char *adr, int count_limit,
|
||||
int *filec, char **filev, off_t *mem, int flag);
|
||||
|
||||
int Xorriso_format_ls_l(struct XorrisO *xorriso, struct stat *stbuf, int flag);
|
||||
|
||||
/* @param flag bit0= simple readlink(): no normalization, no multi-hop
|
||||
*/
|
||||
int Xorriso_resolve_link(struct XorrisO *xorriso,
|
||||
char *link_path, char result_path[SfileadrL], int flag);
|
||||
|
||||
/* @param flag bit0= for Xorriso_msgs_submit: use pager
|
||||
*/
|
||||
int Xorriso_hop_link(struct XorrisO *xorriso, char *link_path,
|
||||
struct LinkiteM **link_stack, struct stat *stbuf, int flag);
|
||||
|
||||
/* reg_expr should be twice as large as bourne_expr ( + 2 to be exact) */
|
||||
/* return: 2= bourne_expr is surely a constant */
|
||||
int Xorriso__bourne_to_reg(char bourne_expr[], char reg_expr[], int flag);
|
||||
|
||||
int Xorriso_no_malloc_memory(struct XorrisO *xorriso, char **to_free,
|
||||
int flag);
|
||||
|
||||
int Xorriso_pacifier_reset(struct XorrisO *xorriso, int flag);
|
||||
|
||||
/* This call is to be issued by long running workers in short intervals.
|
||||
It will check whether enough time has elapsed since the last pacifier
|
||||
message and eventually issue an update message.
|
||||
@param what_done A sparse description of the action, preferrably in past
|
||||
tense. E.g. "done" , "files added".
|
||||
@param count The number of objects processed so far.
|
||||
Is ignored if <=0.
|
||||
@param todo The number of objects to be done in total.
|
||||
Is ignored if <=0.
|
||||
@param current_object A string telling the object currently processed.
|
||||
Ignored if "".
|
||||
@param flag bit0= report unconditionally, no time check
|
||||
*/
|
||||
int Xorriso_pacifier_callback(struct XorrisO *xorriso, char *what_done,
|
||||
off_t count, off_t todo, char *current_object,
|
||||
int flag);
|
||||
|
||||
int Xorriso_pfx_disk_path(struct XorrisO *xorriso, char *iso_path,
|
||||
char *iso_prefix, char *disk_prefix,
|
||||
char disk_path[SfileadrL], int flag);
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
@param flag bit0= update rather than compare
|
||||
*/
|
||||
int Xorriso_find_compare(struct XorrisO *xorriso, void *boss_iter,
|
||||
char *iso_path, char *iso_prefix, char *disk_prefix,
|
||||
int flag);
|
||||
|
||||
/* @param boss_iter Opaque handle to be forwarded to actions in ISO image
|
||||
Set to NULL if calling this function from outside ISO world
|
||||
*/
|
||||
int Xorriso_update_interpreter(struct XorrisO *xorriso, void *boss_iter,
|
||||
int compare_result, char *disk_path,
|
||||
char *iso_rr_path, int flag);
|
||||
|
||||
int Xorriso_path_is_excluded(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
/* @param flag bit0= long format
|
||||
bit1= do not print count of nodes
|
||||
bit2= du format
|
||||
bit3= print directories as themselves (ls -d)
|
||||
*/
|
||||
int Xorriso_lsx_filev(struct XorrisO *xorriso, char *wd,
|
||||
int filec, char **filev, off_t boss_mem, int flag);
|
||||
|
||||
/*
|
||||
@param flag >>> bit0= remove whole sub tree: rm -r
|
||||
bit1= remove empty directory: rmdir
|
||||
bit2= recursion: do not reassure in mode 2 "tree"
|
||||
bit3= this is for overwriting and not for plain removal
|
||||
bit4= count deleted files in xorriso->pacifier_count
|
||||
bit5= with bit0 only remove directory content, not the directory
|
||||
@return <=0 = error
|
||||
1 = removed leaf file object
|
||||
2 = removed directory or tree
|
||||
3 = did not remove on user revocation
|
||||
*/
|
||||
int Xorriso_rmx(struct XorrisO *xorriso, off_t boss_mem, char *path, int flag);
|
||||
|
||||
|
||||
/* @param flag bit7= return 4 if restore fails from denied permission
|
||||
do not issue error message
|
||||
@return <=0 failure , 1 success ,
|
||||
4 with bit7: permission to create file was denied
|
||||
*/
|
||||
int Xorriso_make_tmp_path(struct XorrisO *xorriso, char *orig_path,
|
||||
char *tmp_path, int *fd, int flag);
|
||||
|
||||
/* @param flag bit0= path is a directory
|
||||
bit2= recursion: do not reassure in mode 2 "tree"
|
||||
bit3= this is for overwriting and not for plain removal
|
||||
*/
|
||||
int Xorriso_reassure_restore(struct XorrisO *xorriso, char *path, int flag);
|
||||
|
||||
|
||||
/* @param flag bit0= change regardless of xorriso->do_auto_chmod
|
||||
bit1= desired is only rx
|
||||
*/
|
||||
int Xorriso_auto_chmod(struct XorrisO *xorriso, char *disk_path, int flag);
|
||||
|
||||
int Xorriso_make_accessible(struct XorrisO *xorriso, char *disk_path,int flag);
|
||||
|
||||
/* @param flag bit0= prefer to find a match after *img_prefixes
|
||||
(but deliver img_prefixes if no other can be found)
|
||||
*/
|
||||
int Xorriso_make_restore_path(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT **img_prefixes, struct Xorriso_lsT **disk_prefixes,
|
||||
char img_path[SfileadrL], char disk_path[SfileadrL], int flag);
|
||||
|
||||
int Xorriso_restore_make_hl(struct XorrisO *xorriso,
|
||||
char *old_path, char *new_path, int flag);
|
||||
|
||||
|
||||
int Xorriso_protect_stdout(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
/* @param flag bit0= mark untested areas as valid
|
||||
*/
|
||||
int Xorriso_spotlist_to_sectormap(struct XorrisO *xorriso,
|
||||
struct SpotlisT *spotlist,
|
||||
int read_chunk,
|
||||
struct SectorbitmaP **map,
|
||||
int flag);
|
||||
|
||||
int Xorriso_toc_to_string(struct XorrisO *xorriso, char **toc_text, int flag);
|
||||
|
||||
|
||||
/* @param flag bit0+1= what to aquire after giving up outdev
|
||||
0=none, 1=indev, 2=outdev, 3=both
|
||||
*/
|
||||
int Xorriso_reaquire_outdev(struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
/* Opens the -check_media data copy in for reading and writing
|
||||
*/
|
||||
int Xorriso_open_job_data_to(struct XorrisO *xorriso,
|
||||
struct CheckmediajoB *job, int flag);
|
||||
|
||||
int Xorriso_no_findjob(struct XorrisO *xorriso, char *cmd, int flag);
|
||||
|
||||
|
||||
int Xorriso_make_mount_cmd(struct XorrisO *xorriso, char *cmd,
|
||||
int lba, int track, int session, char *volid,
|
||||
char *devadr, char result[SfileadrL], int flag);
|
||||
|
||||
|
||||
/* @param flag bit0= use env_path to find the desired program
|
||||
*/
|
||||
int Xorriso_execv(struct XorrisO *xorriso, char *cmd, char *env_path,
|
||||
int *status, int flag);
|
||||
|
||||
int Xorriso_is_in_patternlist(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, char *path, int flag);
|
||||
|
||||
char *Xorriso_get_pattern(struct XorrisO *xorriso,
|
||||
struct Xorriso_lsT *patternlist, int index, int flag);
|
||||
|
||||
|
||||
/* Normalize ACL and sort apart "access" ACL from "default" ACL.
|
||||
*/
|
||||
int Xorriso_normalize_acl_text(struct XorrisO *xorriso, char *in_text,
|
||||
char **access_acl_text, char **default_acl_text, int flag);
|
||||
|
||||
int Xorriso_path_setfattr(struct XorrisO *xorriso, void *in_node, char *path,
|
||||
char *name, size_t value_length, char *value, int flag);
|
||||
|
||||
int Xorriso_status_result(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
int flag);
|
||||
|
||||
int Xorriso_compare_2_files(struct XorrisO *xorriso, char *disk_adr,
|
||||
char *iso_adr, char *adr_common_tail,
|
||||
int *result, int flag);
|
||||
|
||||
int Xorriso_report_md5_outcome(struct XorrisO *xorriso, char *severity,
|
||||
int flag);
|
||||
|
||||
int Xorriso_append_scdbackup_record(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_may_burn(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_afile_fopen(struct XorrisO *xorriso,
|
||||
char *filename, char *mode, FILE **ret_fp, int flag);
|
||||
|
||||
|
||||
int Sfile_str(char target[SfileadrL], char *source, int flag);
|
||||
|
||||
double Sfile_microtime(int flag);
|
||||
|
||||
int Sfile_add_to_path(char path[SfileadrL], char *addon, int flag);
|
||||
|
||||
int Sfile_scale(double value, char *result, int siz, double thresh, int flag);
|
||||
|
||||
int Sfile_destroy_argv(int *argc, char ***argv, int flag);
|
||||
|
||||
/*
|
||||
bit0= do not ignore trailing slash
|
||||
bit1= do not ignore empty components (other than the empty root name)
|
||||
*/
|
||||
int Sfile_count_components(char *path, int flag);
|
||||
|
||||
/*
|
||||
@param flag
|
||||
bit0= return -1 if file is missing
|
||||
bit1= return a hardlink with siblings as type 5
|
||||
bit2= evaluate eventual link target rather than the link object itself
|
||||
bit3= return a socket or a char device as types 7 or 8 rather than 0
|
||||
@return
|
||||
0=unknown
|
||||
1=regular
|
||||
2=directory
|
||||
3=symbolic link
|
||||
4=named pipe
|
||||
5=multiple hardlink (with bit1)
|
||||
6=block device
|
||||
7=socket (with bit3)
|
||||
8=character device (with bit3)
|
||||
*/
|
||||
int Sfile_type(char *filename, int flag);
|
||||
|
||||
/* @param flag bit0= only encode inside quotes
|
||||
bit1= encode < 32 outside quotes except 7, 8, 9, 10, 12, 13
|
||||
bit2= encode in any case above 126
|
||||
bit3= encode in any case shellsafe:
|
||||
<=42 , 59, 60, 62, 63, 92, 94, 96, >=123
|
||||
*/
|
||||
int Sfile_bsl_encoder(char **result, char *text, size_t text_len, int flag);
|
||||
|
||||
int Sfile_argv_bsl(int argc, char ***argv, int flag);
|
||||
|
||||
|
||||
struct Xorriso_lsT {
|
||||
char *text;
|
||||
struct Xorriso_lsT *prev,*next;
|
||||
};
|
||||
|
||||
/** Create a new list item with arbitrary byte content.
|
||||
@param lstring The newly created object or NULL on failure
|
||||
@param data An array of bytes to be copied into the new object
|
||||
@param data_len Number of bytes to be copied
|
||||
@param link Xorriso_lsT object to which the new object shall be linked
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= insert before link rather than after it
|
||||
bit1= do not copy data (e.g. because *data is invalid)
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_new_binary(struct Xorriso_lsT **lstring, char *data,
|
||||
int data_len, struct Xorriso_lsT *link, int flag);
|
||||
|
||||
|
||||
/** Create a new list item with a 0-terminated text as content.
|
||||
@param lstring The newly created object or NULL on failure
|
||||
@param text A 0-terminated array of bytes
|
||||
@param link Xorriso_lsT object to which the new object shall be linked
|
||||
@param flag see Xorriso_lst_new_binary
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_new(struct Xorriso_lsT **lstring, char *text,
|
||||
struct Xorriso_lsT *link, int flag);
|
||||
|
||||
|
||||
/** Create a new list item at the end of a given list.
|
||||
@param entry Contains as input a pointer to a pointer to any existing
|
||||
list item. As output this list item pointer may be
|
||||
changed to the address of the new list item:
|
||||
if ((*entry == 0) || (flag & 1))
|
||||
@param data An array of bytes to be copied into the new object
|
||||
@param data_len Number of bytes to be copied
|
||||
@param flag Bitfield for control purposes
|
||||
bit0= Return new object address in *entry
|
||||
bit1= do not copy data (e.g. because *data is invalid)
|
||||
bit2= attach data directly by pointer rather than by copying
|
||||
@return <=0 error, 1 ok
|
||||
*/
|
||||
int Xorriso_lst_append_binary(struct Xorriso_lsT **entry,
|
||||
char *data, int data_len, int flag);
|
||||
|
||||
|
||||
/** Destroy a single list item and connect its eventual list neighbors.
|
||||
@param lstring pointer to the pointer to be freed and set to NULL
|
||||
@param flag unused yet, submit 0
|
||||
@return 0= *lstring was alredy NULL, 1= ok
|
||||
*/
|
||||
int Xorriso_lst_destroy(struct Xorriso_lsT **lstring, int flag);
|
||||
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_next(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
struct Xorriso_lsT *Xorriso_lst_get_prev(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
char *Xorriso_lst_get_text(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
int Xorriso_lst_detach_text(struct Xorriso_lsT *entry, int flag);
|
||||
|
||||
|
||||
char *Text_shellsafe(char *in_text, char *out_text, int flag);
|
||||
|
||||
int Sort_argv(int argc, char **argv, int flag);
|
||||
|
||||
/* @param flag bit0= single letters */
|
||||
char *Ftypetxt(mode_t st_mode, int flag);
|
||||
|
||||
/* @param flag bit0=with year and seconds
|
||||
bit1=timestamp format YYYY.MM.DD.hhmmss
|
||||
*/
|
||||
char *Ftimetxt(time_t t, char timetext[40], int flag);
|
||||
|
||||
int System_uname(char **sysname, char **release, char **version,
|
||||
char **machine, int flag);
|
||||
|
||||
|
||||
struct DirseQ;
|
||||
|
||||
int Dirseq_new(struct DirseQ **o, char *adr, int flag);
|
||||
|
||||
int Dirseq_destroy(struct DirseQ **o, int flag);
|
||||
|
||||
int Dirseq_next_adr(struct DirseQ *o, char reply[SfileadrL], int flag);
|
||||
|
||||
|
||||
int Linkitem_reset_stack(struct LinkiteM **o, struct LinkiteM *to, int flag);
|
||||
|
||||
|
||||
|
||||
|
||||
#define Xorriso_findjob_on_expR yes
|
||||
|
||||
#ifdef Xorriso_findjob_on_expR
|
||||
|
||||
/*
|
||||
A single Testnode.
|
||||
*/
|
||||
struct ExprtesT {
|
||||
|
||||
struct FindjoB *boss;
|
||||
|
||||
int invert; /* 0=normal 1=invert result */
|
||||
|
||||
/*
|
||||
0= -false (with invert : -true)
|
||||
1= -name char *arg1 (regex_t in *arg2)
|
||||
2= -type char *arg1
|
||||
3= -damaged
|
||||
4= -lba_range int *arg1 int *arg2
|
||||
5= -has_acl
|
||||
6= -has_xattr
|
||||
7= -has_aaip
|
||||
8= -has_filter
|
||||
9= -wanted_node IsoNode *arg1 (for internal use, arg1 not allocated)
|
||||
10= -pending_data
|
||||
11= -decision char *arg1 ("yes", "no")
|
||||
12= -prune
|
||||
13= -wholename char *arg1 (regex_t in *arg2)
|
||||
14= -has_any_xattr
|
||||
15= -has_md5
|
||||
*/
|
||||
int test_type;
|
||||
|
||||
void *arg1;
|
||||
void *arg2;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
A computational node.
|
||||
A tree of these nodes forms the expression.
|
||||
Sequences of AND/OR operations form branches, brackets spawn new branches,
|
||||
NOT inverts node's test resp. subtree result.
|
||||
*/
|
||||
struct ExprnodE {
|
||||
|
||||
struct ExprnodE *up;
|
||||
|
||||
char origin[8];
|
||||
|
||||
/* Operators */
|
||||
int invert; /* 0=normal 1=invert own result (subtree or test, but not op) */
|
||||
|
||||
int assoc; /*
|
||||
0= left : compute own value, combine with left value,
|
||||
compute right value, combine with current value
|
||||
1= right: compute own value, compute right value,
|
||||
combine own and right, combine with left value
|
||||
*/
|
||||
|
||||
int use_shortcuts; /* 0= evaluate all tests of -and and -or,
|
||||
1= evaluate only until the combined result is known
|
||||
*/
|
||||
|
||||
struct ExprnodE *left;
|
||||
int left_op; /* 0=OR , 1=AND */
|
||||
|
||||
struct ExprnodE *right;
|
||||
int right_op; /* see left_op */
|
||||
|
||||
/* Brackets : a pointer to the first node in a subchain */
|
||||
struct ExprnodE *sub;
|
||||
|
||||
int is_if_then_else;
|
||||
struct ExprnodE *true_branch;
|
||||
struct ExprnodE *false_branch;
|
||||
|
||||
/* elementary test : if sub!=NULL , test is ignored */
|
||||
struct ExprtesT *test;
|
||||
|
||||
/* Result */
|
||||
int own_value;
|
||||
int composed_value;
|
||||
|
||||
};
|
||||
|
||||
|
||||
struct FindjoB {
|
||||
|
||||
char *start_path;
|
||||
|
||||
struct ExprnodE *test_tree;
|
||||
|
||||
struct ExprnodE *cursor;
|
||||
int invert; /* 0=normal 1=set invert-property for next new test node */
|
||||
int use_shortcuts;
|
||||
|
||||
/* 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
|
||||
30= internal: count by xorriso->node_counter
|
||||
31= internal: register in xorriso->node_array
|
||||
32= internal: widen_hardlinks disk_equiv: update nodes marked in di_do_widen
|
||||
33= get_any_xattr
|
||||
34= get_md5
|
||||
35= check_md5
|
||||
36= make_md5
|
||||
37= mkisofs_r
|
||||
38= sort_weight number
|
||||
*/
|
||||
int action;
|
||||
int prune;
|
||||
|
||||
/* 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, also used as weight */
|
||||
time_t date;
|
||||
char *found_path;
|
||||
struct FindjoB *subjob;
|
||||
|
||||
/* Errors */
|
||||
char errmsg[4096];
|
||||
int errn; /*
|
||||
>0 = UNIX errno
|
||||
-1 = close_bracket: no bracket open
|
||||
-2 = binary operator or closing bracket expected
|
||||
-3 = unexpected binary operator or closing bracket
|
||||
-4 = unsupported command
|
||||
-5 = -then -elseif -else -endif without -if or at wrong place
|
||||
*/
|
||||
};
|
||||
|
||||
|
||||
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);
|
||||
|
||||
|
||||
int Exprnode_destroy(struct ExprnodE **fnode, int flag);
|
||||
|
||||
int Exprnode_tree_value(struct XorrisO *xorriso, struct ExprnodE *fnode,
|
||||
int left_value, void *node, char *name, char *path,
|
||||
struct stat *boss_stbuf, struct stat *stbuf, int flag);
|
||||
|
||||
|
||||
int Findjob_new(struct FindjoB **o, char *start_path, int flag);
|
||||
|
||||
int Findjob_destroy(struct FindjoB **o, int flag);
|
||||
|
||||
int Findjob_set_start_path(struct FindjoB *o, char *start_path, int flag);
|
||||
|
||||
int Findjob_get_start_path(struct FindjoB *o, char **start_path, int flag);
|
||||
|
||||
int Findjob_set_commit_filter_2(struct FindjoB *o, int flag);
|
||||
|
||||
int Findjob_set_lba_range(struct FindjoB *o, int start_lba, int count,
|
||||
int flag);
|
||||
|
||||
int Findjob_set_wanted_node(struct FindjoB *o, void *wanted_node, int flag);
|
||||
|
||||
int Findjob_set_decision(struct FindjoB *o, char *decision, int flag);
|
||||
|
||||
int Findjob_open_bracket(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_close_bracket(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_not(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_and(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_or(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_if(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_then(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_else(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_elseif(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_endif(struct FindjoB *job, int flag);
|
||||
|
||||
int Findjob_test_2(struct XorrisO *xorriso, struct FindjoB *o,
|
||||
void *node, char *name, char *path,
|
||||
struct stat *boss_stbuf, struct stat *stbuf, int flag);
|
||||
|
||||
int Findjob_set_action_found_path(struct FindjoB *o, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_target(struct FindjoB *o, int action, char *target,
|
||||
int flag);
|
||||
int Findjob_get_action(struct FindjoB *o, int flag);
|
||||
|
||||
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);
|
||||
|
||||
int Findjob_set_found_path(struct FindjoB *o, char *path, int flag);
|
||||
|
||||
int Findjob_get_found_path(struct FindjoB *o, char **path, int flag);
|
||||
|
||||
#else /* Xorriso_findjob_on_expR */
|
||||
|
||||
|
||||
struct FindjoB;
|
||||
|
||||
|
||||
int Findjob_new(struct FindjoB **o, char *start_path, int flag);
|
||||
|
||||
int Findjob_destroy(struct FindjoB **job, int flag);
|
||||
|
||||
|
||||
/* @return 0=no match , 1=match , <0 = error
|
||||
*/
|
||||
int Findjob_test(struct FindjoB *job, char *name,
|
||||
struct stat *boss_stbuf, struct stat *stbuf,
|
||||
int depth, int flag);
|
||||
|
||||
/* @return <0 error, >=0 see xorriso.c struct FindjoB.action
|
||||
*/
|
||||
int Findjob_get_action(struct FindjoB *o, int flag);
|
||||
|
||||
/* @return <0 error, >=0 see xorriso.c 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);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_target(struct FindjoB *o, int action, char *target,
|
||||
int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chgrp(struct FindjoB *o, gid_t group, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_chmod(struct FindjoB *o,
|
||||
mode_t mode_and, mode_t mode_or, int flag);
|
||||
|
||||
/* @param flag bit0= recursive
|
||||
*/
|
||||
int Findjob_set_action_ad(struct FindjoB *o, int type, time_t date, int flag);
|
||||
|
||||
int Findjob_set_start_path(struct FindjoB *o, char *start_path, int flag);
|
||||
|
||||
int Findjob_set_action_found_path(struct FindjoB *o, int flag);
|
||||
|
||||
int Findjob_get_start_path(struct FindjoB *o, char **start_path, int flag);
|
||||
|
||||
int Findjob_set_lba_range(struct FindjoB *o, int start_lba, int count,
|
||||
int flag);
|
||||
|
||||
int Findjob_get_lba_damage_filter(struct FindjoB *o, int *start_lba,
|
||||
int *end_lba, int *damage_filter, int flag);
|
||||
|
||||
int Findjob_get_commit_filter(struct FindjoB *o, int *commit_filter, int flag);
|
||||
|
||||
int Findjob_get_acl_filter(struct FindjoB *o, int *acl_filter, int flag);
|
||||
|
||||
int Findjob_get_xattr_filter(struct FindjoB *o, int *xattr_filter, int flag);
|
||||
|
||||
int Findjob_get_aaip_filter(struct FindjoB *o, int *aaip_filter, int flag);
|
||||
|
||||
int Findjob_get_filter_filter(struct FindjoB *o, int *value, int flag);
|
||||
|
||||
int Findjob_set_wanted_node(struct FindjoB *o, void *wanted_node, int flag);
|
||||
|
||||
int Findjob_get_wanted_node(struct FindjoB *o, void **wanted_node, int flag);
|
||||
|
||||
int Findjob_set_found_path(struct FindjoB *o, char *path, int flag);
|
||||
|
||||
int Findjob_get_found_path(struct FindjoB *o, char **path, int flag);
|
||||
|
||||
#endif /* ! Xorriso_findjob_on_expR */
|
||||
|
||||
|
||||
struct SplitparT;
|
||||
|
||||
int Splitparts_new(struct SplitparT **o, int count, int flag);
|
||||
|
||||
int Splitparts_destroy(struct SplitparT **o, int count, int flag);
|
||||
|
||||
int Splitparts_set(struct SplitparT *o, int idx,
|
||||
char *name, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag);
|
||||
|
||||
int Splitparts_get(struct SplitparT *o, int idx, char **name, int *partno,
|
||||
int *total_parts, off_t *offset, off_t *bytes,
|
||||
off_t *total_bytes, int flag);
|
||||
|
||||
int Splitpart__parse(char *name, int *partno, int *total_parts,
|
||||
off_t *offset, off_t *bytes, off_t *total_bytes, int flag);
|
||||
|
||||
int Splitpart__is_part_path(char *path, int flag);
|
||||
|
||||
int Splitpart__compose(char *adr, int partno, int total_parts,
|
||||
off_t offset, off_t bytes, off_t total_bytes, int flag);
|
||||
|
||||
int Splitparts_sort(struct SplitparT *o, int count, int flag);
|
||||
|
||||
|
||||
int Permstack_push(struct PermiteM **o, char *disk_path, struct stat *stbuf,
|
||||
int flag);
|
||||
|
||||
int Permstack_pop(struct PermiteM **o, struct PermiteM *stopper,
|
||||
struct XorrisO *xorriso, int flag);
|
||||
|
||||
|
||||
int Spotlist_new(struct SpotlisT **o, int flag);
|
||||
|
||||
int Spotlist_destroy(struct SpotlisT **o, int flag);
|
||||
|
||||
int Spotlist_add_item(struct SpotlisT *o, int start_lba, int blocks,
|
||||
int quality, int flag);
|
||||
|
||||
int Spotlist_count(struct SpotlisT *o, int flag);
|
||||
|
||||
int Spotlist_block_count(struct SpotlisT *o, int flag);
|
||||
|
||||
int Spotlist_sector_size(struct SpotlisT *o, int read_chunk, int flag);
|
||||
|
||||
int Spotlist_get_item(struct SpotlisT *o, int idx,
|
||||
int *start_lba, int *blocks, int *quality, int flag);
|
||||
|
||||
char *Spotlist__quality_name(int quality, char name[80], int bad_limit,
|
||||
int flag);
|
||||
|
||||
|
||||
#define Xorriso_read_quality_gooD 0x7fffffff
|
||||
#define Xorriso_read_quality_md5_matcH 0x70000000
|
||||
#define Xorriso_read_quality_sloW 0x60000000
|
||||
#define Xorriso_read_quality_partiaL 0x50000000
|
||||
#define Xorriso_read_quality_valiD 0x40000000
|
||||
#define Xorriso_read_quality_untesteD 0x3fffffff
|
||||
#define Xorriso_read_quality_invaliD 0x3ffffffe
|
||||
#define Xorriso_read_quality_tao_enD 0x28000000
|
||||
#define Xorriso_read_quality_off_tracK 0x20000000
|
||||
#define Xorriso_read_quality_md5_mismatcH 0x10000000
|
||||
#define Xorriso_read_quality_unreadablE 0x00000000
|
||||
|
||||
|
||||
struct CheckmediajoB {
|
||||
int use_dev; /* 0= use indev , 1= use outdev , 2= use sector map*/
|
||||
|
||||
int min_lba; /* if >=0 : begin checking at this address */
|
||||
int max_lba; /* if >=0 : read up to this address, else use mode */
|
||||
|
||||
int min_block_size; /* granularity desired by user
|
||||
*/
|
||||
int mode; /* 0= track by track
|
||||
1= single sweep over libisoburn media capacity
|
||||
>>> 2= single sweep over libburn media capacity
|
||||
*/
|
||||
time_t start_time;
|
||||
int time_limit; /* Number of seconds after which to abort */
|
||||
|
||||
int item_limit; /* Maximum number of media check list items as result */
|
||||
|
||||
char abort_file_path[SfileadrL];
|
||||
|
||||
char data_to_path[SfileadrL];
|
||||
int data_to_fd;
|
||||
off_t data_to_offset; /* usually 0 with image copy, negative with file copy */
|
||||
off_t data_to_limit; /* used with file copy */
|
||||
int patch_lba0;
|
||||
int patch_lba0_msc1;
|
||||
|
||||
char sector_map_path[SfileadrL];
|
||||
struct SectorbitmaP *sector_map;
|
||||
int map_with_volid; /* 0=add quick toc to map file,
|
||||
1=read ISO heads for toc
|
||||
*/
|
||||
|
||||
int retry; /* -1= only try full read_chunk, 1=retry with 2k blocks
|
||||
0= retry with CD, full chunk else
|
||||
*/
|
||||
|
||||
int report_mode; /* 0= print MCL items
|
||||
1= print damaged files
|
||||
*/
|
||||
|
||||
char event_severity[20]; /* If not "ALL": trigger event of given severity
|
||||
at the end of a check job if bad blocks were
|
||||
discovered.
|
||||
*/
|
||||
|
||||
double slow_threshold_seq; /* Time limit in seconds for the decision whether
|
||||
a read operation is considered slow. This does
|
||||
not apply to thr first read of an interval.
|
||||
*/
|
||||
|
||||
int untested_valid; /* 1= mark untested data blocks as valid when calling
|
||||
Xorriso_spotlist_to_sectormap()
|
||||
*/
|
||||
};
|
||||
|
||||
int Checkmediajob_new(struct CheckmediajoB **o, int flag);
|
||||
|
||||
int Checkmediajob_destroy(struct CheckmediajoB **o, int flag);
|
||||
|
||||
int Checkmediajob_copy(struct CheckmediajoB *from, struct CheckmediajoB *to,
|
||||
int flag);
|
||||
|
||||
int Sectorbitmap_new(struct SectorbitmaP **o, int sectors, int sector_size,
|
||||
int flag);
|
||||
int Sectorbitmap_destroy(struct SectorbitmaP **o, int flag);
|
||||
int Sectorbitmap_from_file(struct SectorbitmaP **o, char *path, char *msg,
|
||||
int *os_errno, int flag);
|
||||
int Sectorbitmap_to_file(struct SectorbitmaP *o, char *path, char *info,
|
||||
char *msg, int *os_errno, int flag);
|
||||
int Sectorbitmap_set(struct SectorbitmaP *o, int sector, int flag);
|
||||
int Sectorbitmap_set_range(struct SectorbitmaP *o,
|
||||
int start_sector, int sectors, int flag);
|
||||
int Sectorbitmap_is_set(struct SectorbitmaP *o, int sector, int flag);
|
||||
int Sectorbitmap_bytes_are_set(struct SectorbitmaP *o,
|
||||
off_t start_byte, off_t end_byte, int flag);
|
||||
|
||||
int Sectorbitmap_get_layout(struct SectorbitmaP *o,
|
||||
int *sectors, int *sector_size, int flag);
|
||||
|
||||
int Sectorbitmap_copy(struct SectorbitmaP *from, struct SectorbitmaP *to,
|
||||
int flag);
|
||||
|
||||
/* bit0= append (text!=NULL) */
|
||||
int Sregex_string(char **handle, char *text, int flag);
|
||||
|
||||
/* @param flag bit0= only test expression whether compilable
|
||||
*/
|
||||
int Sregex_match(char *pattern, char *text, int flag);
|
||||
|
||||
#endif /* Xorriso_private_includeD */
|
||||
|
||||
|
@ -1 +1 @@
|
||||
#define Xorriso_timestamP "2010.05.05.194248"
|
||||
#define Xorriso_timestamP "2010.05.15.184604"
|
||||
|
13703
xorriso/xorrisoburn.c
13703
xorriso/xorrisoburn.c
File diff suppressed because it is too large
Load Diff
@ -412,6 +412,15 @@ int Xorriso_setfattr(struct XorrisO *xorriso, void *in_node, char *path,
|
||||
size_t num_attrs, char **names,
|
||||
size_t *value_lengths, char **values, int flag);
|
||||
|
||||
int Xorriso_perform_attr_from_list(struct XorrisO *xorriso, char *path,
|
||||
struct Xorriso_lsT *lst_start, int flag);
|
||||
|
||||
int Xorriso_path_setfattr(struct XorrisO *xorriso, void *in_node, char *path,
|
||||
char *name, size_t value_length, char *value, int flag);
|
||||
|
||||
int Xorriso_perform_acl_from_list(struct XorrisO *xorriso, char *file_path,
|
||||
char *uid, char *gid, char *acl, int flag);
|
||||
|
||||
int Xorriso_record_dev_inode(struct XorrisO *xorriso, char *disk_path,
|
||||
dev_t dev, ino_t ino,
|
||||
void *in_node, char *iso_path, int flag);
|
||||
@ -509,5 +518,18 @@ int Xorriso_boot_image_status(struct XorrisO *xorriso, char *filter, FILE *fp,
|
||||
#define Xorriso_IFBOOT S_IFMT
|
||||
|
||||
|
||||
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);
|
||||
|
||||
|
||||
int Xorriso_toc_to_string(struct XorrisO *xorriso, char **toc_text, int flag);
|
||||
|
||||
|
||||
int Xorriso_reaquire_outdev(struct XorrisO *xorriso, int flag);
|
||||
|
||||
int Xorriso_set_system_area_path(struct XorrisO *xorriso, char *path,
|
||||
int flag);
|
||||
|
||||
#endif /* Xorrisoburn_includeD */
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user