dj(1): more refactor (get rid of ep pun)

This commit is contained in:
dtb 2024-06-26 13:41:24 -06:00
parent b70b356ce5
commit e65f6b650d
Signed by: trinity
GPG Key ID: 34C0543BBB6AF81B

101
src/dj.c
View File

@ -156,6 +156,9 @@ Io_fdseek(struct Io *io){
|| (!fdisstd(io->fd) && lseek(io->fd, io->seek, SEEK_SET) != -1)) || (!fdisstd(io->fd) && lseek(io->fd, io->seek, SEEK_SET) != -1))
return; return;
if(io->fl == write_flags)
memset(io->buf, '\0', io->bs);
if(io->fl == write_flags){ if(io->fl == write_flags){
memset(io->buf, '\0', io->bs); memset(io->buf, '\0', io->bs);
/* We're going to cheat and use bufuse as the retval for write(2), /* We're going to cheat and use bufuse as the retval for write(2),
@ -273,7 +276,7 @@ usage(void){
int main(int argc, char *argv[]){ int main(int argc, char *argv[]){
int align; /* low 8b used, negative if no alignment is being done */ int align; /* low 8b used, negative if no alignment is being done */
int count; /* 0 if dj(1) runs until no more reads are possible */ int count; /* 0 if dj(1) runs until no more reads are possible */
struct Io ep[2]; /* "engineered pipe"; also "extended play", for the DJ */ struct Io io[2];
char *fmt_output; /* fmt_asv (default) or fmt_human (-H) */ char *fmt_output; /* fmt_asv (default) or fmt_human (-H) */
char noerror; /* 0=exits (default) 1=retries on partial reads or writes */ char noerror; /* 0=exits (default) 1=retries on partial reads or writes */
int c; int c;
@ -284,10 +287,10 @@ int main(int argc, char *argv[]){
count = 0; count = 0;
fmt_output = fmt_asv; fmt_output = fmt_asv;
noerror = 0; noerror = 0;
ep[0].fl = read_flags; io[0].fl = read_flags;
Io_setdefaults(&ep[0]); Io_setdefaults(&io[0]);
ep[1].fl = write_flags; io[1].fl = write_flags;
Io_setdefaults(&ep[1]); Io_setdefaults(&io[1]);
if(argc > 0){ if(argc > 0){
program_name = argv[0]; program_name = argv[0];
@ -296,12 +299,12 @@ int main(int argc, char *argv[]){
case 'i': case 'o': case 'i': case 'o':
i = (c == 'o'); i = (c == 'o');
if(optarg[0] == '-' && optarg[1] == '\0'){ /* optarg == "-" */ if(optarg[0] == '-' && optarg[1] == '\0'){ /* optarg == "-" */
ep[i].fd = (i == 0) ? STDIN_FILENO : STDOUT_FILENO; io[i].fd = (i == 0) ? STDIN_FILENO : STDOUT_FILENO;
ep[i].fn = (i == 0) ? stdin_name : stdout_name; io[i].fn = (i == 0) ? stdin_name : stdout_name;
break; break;
}else if(Io_fdopen(&ep[i], optarg) != -1) }else if(Io_fdopen(&io[i], optarg) != -1)
break; break;
terminate(ep); terminate(io);
return oserr(optarg); return oserr(optarg);
case 'A': align = '\0'; break; case 'A': align = '\0'; break;
case 'n': noerror = 1; break; case 'n': noerror = 1; break;
@ -317,82 +320,82 @@ int main(int argc, char *argv[]){
break; break;
i = isupper(c); i = isupper(c);
c = tolower(c); c = tolower(c);
if((c == 'b' && (ep[i].bs = parse(optarg)) > 0) if((c == 'b' && (io[i].bs = parse(optarg)) > 0)
|| (c == 's' && (ep[i].seek = parse(optarg)) >= 0)) || (c == 's' && (io[i].seek = parse(optarg)) >= 0))
break; break;
/* FALLTHROUGH */ /* FALLTHROUGH */
default: default:
terminate(ep); terminate(io);
return usage(); return usage();
} }
} }
if(argc > optind){ if(argc > optind){
terminate(ep); terminate(io);
return usage(); return usage();
} }
for(i = 0; i <= 1; ++i){ for(i = 0; i < 2; ++i){
if(Io_bufalloc(&ep[i]) == NULL){ if(Io_bufalloc(&io[i]) == NULL){
fprintf(stderr, "%s: Failed to allocate %d bytes\n", fprintf(stderr, "%s: Failed to allocate %d bytes\n",
program_name, ep[i].bs); program_name, io[i].bs);
terminate(ep); terminate(io);
return EX_OSERR; return EX_OSERR;
}else if(ep[i].seek > 0) }else if(io[i].seek > 0)
Io_fdseek(&ep[i]); Io_fdseek(&io[i]);
if(ep[i].seek > 0){ if(io[i].seek > 0){
terminate(ep); terminate(io);
return oserr(ep[i].fn); return oserr(io[i].fn);
} }
} }
do{ /* read */ do{ /* read */
Io_read(&ep[0]); Io_read(&io[0]);
if(!noerror && ep[0].bufuse == 0) if(!noerror && io[0].bufuse == 0)
Io_read(&ep[0]); /* second chance */ Io_read(&io[0]); /* second chance */
if(ep[0].bufuse == 0) /* that's all she wrote */ if(io[0].bufuse == 0) /* that's all she wrote */
break; break;
else if(ep[0].bufuse < ep[0].bs){ else if(io[0].bufuse < io[0].bs){
++ep[0].prec; ++io[0].prec;
fprintf(stderr, "%s: Partial read:\n\t", program_name); fprintf(stderr, "%s: Partial read:\n\t", program_name);
output(ep, fmt_output); output(io, fmt_output);
if(!noerror) if(!noerror)
count = 1; count = 1;
if(align >= 0) if(align >= 0)
Io_bufrpad(&ep[0], align); Io_bufrpad(&io[0], align);
}else }else
++ep[0].rec; ++io[0].rec;
/* write */ /* write */
do{ if(ep[1].bs > ep[0].bs){ /* io[1].bs > io[0].bs */ do{ if(io[1].bs > io[0].bs){ /* io[1].bs > io[0].bs */
Io_bufxapp(&ep[1], &ep[0]); Io_bufxapp(&io[1], &io[0]);
if(ep[0].bs + ep[1].bufuse <= ep[1].bs && count != 1) if(io[0].bs + io[1].bufuse <= io[1].bs && count != 1)
continue; /* we could write more */ continue; /* we could write more */
}else }else
Io_bufxfer(&ep[1], &ep[0], MIN(ep[0].bufuse, ep[1].bs)); Io_bufxfer(&io[1], &io[0], MIN(io[0].bufuse, io[1].bs));
c = ep[1].bufuse; c = io[1].bufuse;
Io_write(&ep[1]); Io_write(&io[1]);
if(!noerror && ep[1].bufuse == c) if(!noerror && io[1].bufuse == c)
Io_write(&ep[1]); /* second chance */ Io_write(&io[1]); /* second chance */
if(c == ep[1].bufuse){ /* no more love */ if(c == io[1].bufuse){ /* no more love */
count = 1; count = 1;
break; break;
}else if(c > ep[1].bufuse && ep[1].bufuse > 0){ }else if(c > io[1].bufuse && io[1].bufuse > 0){
ep[1].prec += 1; io[1].prec += 1;
fprintf(stderr, "%s: Partial write:\n\t", program_name); fprintf(stderr, "%s: Partial write:\n\t", program_name);
output(ep, fmt_output); output(io, fmt_output);
if(!noerror) if(!noerror)
count = 1; count = 1;
}else if(ep[1].bufuse == 0 && c < ep[1].bs) }else if(io[1].bufuse == 0 && c < io[1].bs)
++ep[1].prec; ++io[1].prec;
else else
++ep[1].rec; ++io[1].rec;
}while(ep[0].bufuse > 0); }while(io[0].bufuse > 0);
}while(count == 0 || --count > 0); }while(count == 0 || --count > 0);
output(ep, fmt_output); output(io, fmt_output);
terminate(ep); terminate(io);
return EX_OK; return EX_OK;
} }