| Refactor jpg2ff - farbfeld - suckless image format with conversion tools | |
| git clone git://git.suckless.org/farbfeld | |
| Log | |
| Files | |
| Refs | |
| README | |
| LICENSE | |
| --- | |
| commit ff5bbfae5214d8291c8eb93670233909ded5b722 | |
| parent 98dbe21bcb83fead026c295329ad2a55d8eff1b5 | |
| Author: FRIGN <[email protected]> | |
| Date: Wed, 6 Jan 2016 12:30:17 +0100 | |
| Refactor jpg2ff | |
| Remove some kitchen sink comments (the jpg boilerplate is already | |
| horrible enough) and flush the output buffer manually to detect write | |
| errors. | |
| Also improve error reporting. | |
| Diffstat: | |
| M jpg2ff.c | 74 +++++++++++++++--------------… | |
| 1 file changed, 36 insertions(+), 38 deletions(-) | |
| --- | |
| diff --git a/jpg2ff.c b/jpg2ff.c | |
| @@ -1,34 +1,22 @@ | |
| /* See LICENSE file for copyright and license details. */ | |
| #include <arpa/inet.h> | |
| + | |
| #include <errno.h> | |
| #include <stdint.h> | |
| #include <stdio.h> | |
| #include <stdlib.h> | |
| #include <string.h> | |
| - | |
| #include <setjmp.h> | |
| -#include <jpeglib.h> | |
| -char *argv0; | |
| - | |
| -static jmp_buf setjmp_buffer; | |
| +#include <jpeglib.h> | |
| -static void | |
| -usage(void) | |
| -{ | |
| - fprintf(stderr, "usage: %s\n", argv0); | |
| - exit(1); | |
| -} | |
| +static jmp_buf error_jump; | |
| METHODDEF(void) | |
| -if_jpeg_error(j_common_ptr cinfo) | |
| +jpeg_error(j_common_ptr cinfo) | |
| { | |
| - /* Always display the message. */ | |
| - /* We could postpone this until after returning, if we chose. */ | |
| - (*cinfo->err->output_message) (cinfo); | |
| - | |
| - /* Return control to the setjmp point */ | |
| - longjmp(setjmp_buffer, 1); | |
| + (*cinfo->err->output_message)(cinfo); | |
| + longjmp(error_jump, 1); | |
| } | |
| int | |
| @@ -42,18 +30,16 @@ main(int argc, char *argv[]) | |
| int ret = 1; | |
| JSAMPARRAY buffer; /* output row buffer */ | |
| - argv0 = argv[0]; | |
| - if (argc > 1) | |
| - usage(); | |
| + if (argc > 1) { | |
| + fprintf(stderr, "usage: %s\n", argv[0]); | |
| + return 1; | |
| + } | |
| - /* load jpeg */ | |
| + /* load jpg */ | |
| cinfo.err = jpeg_std_error(&jerr); | |
| - jerr.error_exit = if_jpeg_error; | |
| - /* Establish the setjmp return context for my_error_exit to use. */ | |
| - if (setjmp(setjmp_buffer)) { | |
| - /* If we get here, the JPEG code has signaled an error. | |
| - * We need to clean up the JPEG object, close the input file, a… | |
| + jerr.error_exit = jpeg_error; | |
| + if (setjmp(error_jump)) { | |
| goto cleanup; | |
| } | |
| @@ -64,23 +50,23 @@ main(int argc, char *argv[]) | |
| width = cinfo.image_width; | |
| height = cinfo.image_height; | |
| - /* change output for farbfeld */ | |
| - cinfo.output_components = 3; /* # of color components per pixel */ | |
| - cinfo.out_color_space = JCS_RGB; /* colorspace of input image */ | |
| + /* set output format */ | |
| + cinfo.output_components = 3; /* color components per pixel */ | |
| + cinfo.out_color_space = JCS_RGB; /* input color space */ | |
| jpeg_start_decompress(&cinfo); | |
| jpeg_row_len = width * cinfo.output_components; | |
| - /* Make a one-row-high sample array that will go away when done with i… | |
| - buffer = (*cinfo.mem->alloc_sarray) | |
| - ((j_common_ptr) &cinfo, JPOOL_IMAGE, jpeg_row_len, 1); | |
| - ff_row_len = strlen("RRGGBBAA") * width; | |
| + /* create output buffers */ | |
| + buffer = (*cinfo.mem->alloc_sarray)((j_common_ptr)&cinfo, | |
| + JPOOL_IMAGE, jpeg_row_len, 1); | |
| + ff_row_len = strlen("RGBA") * sizeof(uint16_t) * width; | |
| if(!(ff_row = malloc(ff_row_len))) { | |
| - fprintf(stderr, "Can't malloc\n"); | |
| + fprintf(stderr, "%s: malloc: out of memory\n", argv[0]); | |
| return 1; | |
| } | |
| - /* write header with big endian width and height-values */ | |
| + /* write header */ | |
| fprintf(stdout, "farbfeld"); | |
| val_be = htonl(width); | |
| fwrite(&val_be, sizeof(uint32_t), 1, stdout); | |
| @@ -91,7 +77,7 @@ main(int argc, char *argv[]) | |
| /* jpeg_read_scanlines expects an array of pointers to scanlin… | |
| * Here the array is only one element long, but you could ask … | |
| * more than one scanline at a time if that's more convenient.… | |
| - (void)jpeg_read_scanlines(&cinfo, buffer, 1); | |
| + jpeg_read_scanlines(&cinfo, buffer, 1); | |
| for(i = 0, dx = 0, sx = 0; i < width; i++, sx += 3, dx += 4) { | |
| ff_row[dx] = htons(buffer[0][sx] * 257); | |
| @@ -102,13 +88,25 @@ main(int argc, char *argv[]) | |
| /* write data */ | |
| if (fwrite(ff_row, 1, ff_row_len, stdout) != ff_row_len) { | |
| - fprintf(stderr, "fwrite() failed\n"); | |
| + fprintf(stderr, "%s: fwrite: "); | |
| + perror(NULL); | |
| goto cleanup; | |
| } | |
| } | |
| jpeg_finish_decompress(&cinfo); | |
| ret = 0; | |
| + /* flush output */ | |
| + if (fflush(stdout)) { | |
| + fprintf(stderr, "%s: fflush stdout: ", argv[0]); | |
| + perror(NULL); | |
| + ret = 1; | |
| + } | |
| + if (fclose(stdout) && !ret) { | |
| + fprintf(stderr, "%s: fclose stdout: ", argv[0]); | |
| + perror(NULL); | |
| + ret = 1; | |
| + } | |
| cleanup: | |
| free(ff_row); | |
| jpeg_destroy_decompress(&cinfo); |