pngminus: Delete the incomplete output files upon premature termination

Defer the program termination on error until all files are closed and
(if applicable) all incompletely-written output files are deleted.

In addition, perform the following maintenance tasks:
 * Rename and document the internal helpers used by the functions
   `png2pnm` and `pnm2png`.
 * Unset the executable permission bits for the *.bat test programs.
This commit is contained in:
Cosmin Truta 2024-01-09 18:54:02 +02:00
parent 6beae586d6
commit b3521c60af
5 changed files with 49 additions and 32 deletions

View File

@ -11,4 +11,4 @@ version 1.0 - 1999.10.15 - First version.
1.5 - 2018.08.05 - Fix buffer overflow in tokenizer (Cosmin Truta) 1.5 - 2018.08.05 - Fix buffer overflow in tokenizer (Cosmin Truta)
1.6 - 2018.08.05 - Improve portability and fix style (Cosmin Truta) 1.6 - 2018.08.05 - Improve portability and fix style (Cosmin Truta)
1.7 - 2019.01.22 - Change license to MIT (Willem van Schaik) 1.7 - 2019.01.22 - Change license to MIT (Willem van Schaik)
1.8 - 2024.01.08 - Fix, improve, modernize (Cosmin Truta) 1.8 - 2024.01.09 - Fix, improve, modernize (Cosmin Truta)

View File

@ -28,9 +28,9 @@ int main (int argc, char *argv[]);
void usage (); void usage ();
BOOL png2pnm (FILE *png_file, FILE *pnm_file, FILE *alpha_file, BOOL png2pnm (FILE *png_file, FILE *pnm_file, FILE *alpha_file,
BOOL raw, BOOL alpha); BOOL raw, BOOL alpha);
BOOL png2pnm_internal (png_struct *png_ptr, png_info *info_ptr, BOOL do_png2pnm (png_struct *png_ptr, png_info *info_ptr,
FILE *pnm_file, FILE *alpha_file, FILE *pnm_file, FILE *alpha_file,
BOOL raw, BOOL alpha); BOOL raw, BOOL alpha);
/* /*
* main * main
@ -41,9 +41,12 @@ int main (int argc, char *argv[])
FILE *fp_rd = stdin; FILE *fp_rd = stdin;
FILE *fp_wr = stdout; FILE *fp_wr = stdout;
FILE *fp_al = NULL; FILE *fp_al = NULL;
const char *fname_wr = NULL;
const char *fname_al = NULL;
BOOL raw = TRUE; BOOL raw = TRUE;
BOOL alpha = FALSE; BOOL alpha = FALSE;
int argi; int argi;
int ret;
for (argi = 1; argi < argc; argi++) for (argi = 1; argi < argc; argi++)
{ {
@ -62,6 +65,7 @@ int main (int argc, char *argv[])
argi++; argi++;
if ((fp_al = fopen (argv[argi], "wb")) == NULL) if ((fp_al = fopen (argv[argi], "wb")) == NULL)
{ {
fname_al = argv[argi];
fprintf (stderr, "PNM2PNG\n"); fprintf (stderr, "PNM2PNG\n");
fprintf (stderr, "Error: cannot create alpha-channel file %s\n", fprintf (stderr, "Error: cannot create alpha-channel file %s\n",
argv[argi]); argv[argi]);
@ -92,6 +96,7 @@ int main (int argc, char *argv[])
} }
else if (fp_wr == stdout) else if (fp_wr == stdout)
{ {
fname_wr = argv[argi];
if ((fp_wr = fopen (argv[argi], "wb")) == NULL) if ((fp_wr = fopen (argv[argi], "wb")) == NULL)
{ {
fprintf (stderr, "PNG2PNM\n"); fprintf (stderr, "PNG2PNM\n");
@ -117,12 +122,7 @@ int main (int argc, char *argv[])
#endif #endif
/* call the conversion program itself */ /* call the conversion program itself */
if (png2pnm (fp_rd, fp_wr, fp_al, raw, alpha) == FALSE) ret = png2pnm (fp_rd, fp_wr, fp_al, raw, alpha);
{
fprintf (stderr, "PNG2PNM\n");
fprintf (stderr, "Error: unsuccessful conversion of PNG-image\n");
exit (1);
}
/* close input file */ /* close input file */
fclose (fp_rd); fclose (fp_rd);
@ -132,6 +132,17 @@ int main (int argc, char *argv[])
if (alpha) if (alpha)
fclose (fp_al); fclose (fp_al);
if (!ret)
{
fprintf (stderr, "PNG2PNM\n");
fprintf (stderr, "Error: unsuccessful conversion of PNG-image\n");
if (fname_wr)
remove (fname_wr); /* no broken output file shall remain behind */
if (fname_al)
remove (fname_al); /* ditto */
exit (1);
}
return 0; return 0;
} }
@ -165,7 +176,7 @@ BOOL png2pnm (FILE *png_file, FILE *pnm_file, FILE *alpha_file,
png_info *info_ptr; png_info *info_ptr;
BOOL ret; BOOL ret;
/* initialize the libpng structures for reading from png_file */ /* initialize the libpng context for reading from png_file */
png_ptr = png_create_read_struct (png_get_libpng_ver(NULL), png_ptr = png_create_read_struct (png_get_libpng_ver(NULL),
NULL, NULL, NULL); NULL, NULL, NULL);
@ -188,7 +199,7 @@ BOOL png2pnm (FILE *png_file, FILE *pnm_file, FILE *alpha_file,
png_init_io (png_ptr, png_file); png_init_io (png_ptr, png_file);
/* do the actual conversion */ /* do the actual conversion */
ret = png2pnm_internal (png_ptr, info_ptr, pnm_file, alpha_file, raw, alpha); ret = do_png2pnm (png_ptr, info_ptr, pnm_file, alpha_file, raw, alpha);
/* clean up the libpng structures and their internally-managed data */ /* clean up the libpng structures and their internally-managed data */
png_destroy_read_struct (&png_ptr, &info_ptr, NULL); png_destroy_read_struct (&png_ptr, &info_ptr, NULL);
@ -197,12 +208,12 @@ BOOL png2pnm (FILE *png_file, FILE *pnm_file, FILE *alpha_file,
} }
/* /*
* png2pnm_internal * do_png2pnm - does the conversion in a fully-initialized libpng context
*/ */
BOOL png2pnm_internal (png_struct *png_ptr, png_info *info_ptr, BOOL do_png2pnm (png_struct *png_ptr, png_info *info_ptr,
FILE *pnm_file, FILE *alpha_file, FILE *pnm_file, FILE *alpha_file,
BOOL raw, BOOL alpha) BOOL raw, BOOL alpha)
{ {
png_byte **row_pointers; png_byte **row_pointers;
png_byte *pix_ptr; png_byte *pix_ptr;

View File

@ -29,9 +29,9 @@ int main (int argc, char *argv[]);
void usage (); void usage ();
BOOL pnm2png (FILE *pnm_file, FILE *png_file, FILE *alpha_file, BOOL pnm2png (FILE *pnm_file, FILE *png_file, FILE *alpha_file,
BOOL interlace, BOOL alpha); BOOL interlace, BOOL alpha);
BOOL pnm2png_internal (png_struct *png_ptr, png_info *info_ptr, BOOL do_pnm2png (png_struct *png_ptr, png_info *info_ptr,
FILE *pnm_file, FILE *alpha_file, FILE *pnm_file, FILE *alpha_file,
BOOL interlace, BOOL alpha); BOOL interlace, BOOL alpha);
int fscan_pnm_magic (FILE *pnm_file, char *magic_buf, size_t magic_buf_size); int fscan_pnm_magic (FILE *pnm_file, char *magic_buf, size_t magic_buf_size);
int fscan_pnm_token (FILE *pnm_file, char *token_buf, size_t token_buf_size); int fscan_pnm_token (FILE *pnm_file, char *token_buf, size_t token_buf_size);
int fscan_pnm_uint_32 (FILE *pnm_file, png_uint_32 *num_ptr); int fscan_pnm_uint_32 (FILE *pnm_file, png_uint_32 *num_ptr);
@ -47,9 +47,11 @@ int main (int argc, char *argv[])
FILE *fp_rd = stdin; FILE *fp_rd = stdin;
FILE *fp_al = NULL; FILE *fp_al = NULL;
FILE *fp_wr = stdout; FILE *fp_wr = stdout;
const char *fname_wr = NULL;
BOOL interlace = FALSE; BOOL interlace = FALSE;
BOOL alpha = FALSE; BOOL alpha = FALSE;
int argi; int argi;
int ret;
for (argi = 1; argi < argc; argi++) for (argi = 1; argi < argc; argi++)
{ {
@ -95,6 +97,7 @@ int main (int argc, char *argv[])
} }
else if (fp_wr == stdout) else if (fp_wr == stdout)
{ {
fname_wr = argv[argi];
if ((fp_wr = fopen (argv[argi], "wb")) == NULL) if ((fp_wr = fopen (argv[argi], "wb")) == NULL)
{ {
fprintf (stderr, "PNM2PNG\n"); fprintf (stderr, "PNM2PNG\n");
@ -122,12 +125,7 @@ int main (int argc, char *argv[])
#endif #endif
/* call the conversion program itself */ /* call the conversion program itself */
if (pnm2png (fp_rd, fp_wr, fp_al, interlace, alpha) == FALSE) ret = pnm2png (fp_rd, fp_wr, fp_al, interlace, alpha);
{
fprintf (stderr, "PNM2PNG\n");
fprintf (stderr, "Error: unsuccessful converting to PNG-image\n");
exit (1);
}
/* close input file */ /* close input file */
fclose (fp_rd); fclose (fp_rd);
@ -137,6 +135,15 @@ int main (int argc, char *argv[])
if (alpha) if (alpha)
fclose (fp_al); fclose (fp_al);
if (!ret)
{
fprintf (stderr, "PNM2PNG\n");
fprintf (stderr, "Error: unsuccessful converting to PNG-image\n");
if (fname_wr)
remove (fname_wr); /* no broken output file shall remain behind */
exit (1);
}
return 0; return 0;
} }
@ -168,7 +175,7 @@ BOOL pnm2png (FILE *pnm_file, FILE *png_file, FILE *alpha_file,
png_info *info_ptr; png_info *info_ptr;
BOOL ret; BOOL ret;
/* initialize the libpng structures for writing to png_file */ /* initialize the libpng context for writing to png_file */
png_ptr = png_create_write_struct (png_get_libpng_ver(NULL), png_ptr = png_create_write_struct (png_get_libpng_ver(NULL),
NULL, NULL, NULL); NULL, NULL, NULL);
@ -191,8 +198,7 @@ BOOL pnm2png (FILE *pnm_file, FILE *png_file, FILE *alpha_file,
png_init_io (png_ptr, png_file); png_init_io (png_ptr, png_file);
/* do the actual conversion */ /* do the actual conversion */
ret = pnm2png_internal (png_ptr, info_ptr, ret = do_pnm2png (png_ptr, info_ptr, pnm_file, alpha_file, interlace, alpha);
pnm_file, alpha_file, interlace, alpha);
/* clean up the libpng structures and their internally-managed data */ /* clean up the libpng structures and their internally-managed data */
png_destroy_write_struct (&png_ptr, &info_ptr); png_destroy_write_struct (&png_ptr, &info_ptr);
@ -201,12 +207,12 @@ BOOL pnm2png (FILE *pnm_file, FILE *png_file, FILE *alpha_file,
} }
/* /*
* pnm2png_internal * do_pnm2png - does the conversion in a fully-initialized libpng context
*/ */
BOOL pnm2png_internal (png_struct *png_ptr, png_info *info_ptr, BOOL do_pnm2png (png_struct *png_ptr, png_info *info_ptr,
FILE *pnm_file, FILE *alpha_file, FILE *pnm_file, FILE *alpha_file,
BOOL interlace, BOOL alpha) BOOL interlace, BOOL alpha)
{ {
png_byte **row_pointers; png_byte **row_pointers;
png_byte *pix_ptr; png_byte *pix_ptr;

0
contrib/pngminus/test_png2pnm.bat Executable file → Normal file
View File

0
contrib/pngminus/test_pnm2png.bat Executable file → Normal file
View File