2 |
- |
1 |
/*
|
|
|
2 |
* cdjpeg.c
|
|
|
3 |
*
|
|
|
4 |
* Copyright (C) 1991-1997, Thomas G. Lane.
|
|
|
5 |
* This file is part of the Independent JPEG Group's software.
|
|
|
6 |
* For conditions of distribution and use, see the accompanying README file.
|
|
|
7 |
*
|
|
|
8 |
* This file contains common support routines used by the IJG application
|
|
|
9 |
* programs (cjpeg, djpeg, jpegtran).
|
|
|
10 |
*/
|
|
|
11 |
|
|
|
12 |
#include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */
|
|
|
13 |
#include <ctype.h> /* to declare isupper(), tolower() */
|
|
|
14 |
#ifdef NEED_SIGNAL_CATCHER
|
|
|
15 |
#include <signal.h> /* to declare signal() */
|
|
|
16 |
#endif
|
|
|
17 |
#ifdef USE_SETMODE
|
|
|
18 |
#include <fcntl.h> /* to declare setmode()'s parameter macros */
|
|
|
19 |
/* If you have setmode() but not <io.h>, just delete this line: */
|
|
|
20 |
#include <io.h> /* to declare setmode() */
|
|
|
21 |
#endif
|
|
|
22 |
|
|
|
23 |
|
|
|
24 |
/*
|
|
|
25 |
* Signal catcher to ensure that temporary files are removed before aborting.
|
|
|
26 |
* NB: for Amiga Manx C this is actually a global routine named _abort();
|
|
|
27 |
* we put "#define signal_catcher _abort" in jconfig.h. Talk about bogus...
|
|
|
28 |
*/
|
|
|
29 |
|
|
|
30 |
#ifdef NEED_SIGNAL_CATCHER
|
|
|
31 |
|
|
|
32 |
static j_common_ptr sig_cinfo;
|
|
|
33 |
|
|
|
34 |
void /* must be global for Manx C */
|
|
|
35 |
signal_catcher (int signum)
|
|
|
36 |
{
|
|
|
37 |
if (sig_cinfo != NULL) {
|
|
|
38 |
if (sig_cinfo->err != NULL) /* turn off trace output */
|
|
|
39 |
sig_cinfo->err->trace_level = 0;
|
|
|
40 |
jpeg_destroy(sig_cinfo); /* clean up memory allocation & temp files */
|
|
|
41 |
}
|
|
|
42 |
exit(EXIT_FAILURE);
|
|
|
43 |
}
|
|
|
44 |
|
|
|
45 |
|
|
|
46 |
GLOBAL(void)
|
|
|
47 |
enable_signal_catcher (j_common_ptr cinfo)
|
|
|
48 |
{
|
|
|
49 |
sig_cinfo = cinfo;
|
|
|
50 |
#ifdef SIGINT /* not all systems have SIGINT */
|
|
|
51 |
signal(SIGINT, signal_catcher);
|
|
|
52 |
#endif
|
|
|
53 |
#ifdef SIGTERM /* not all systems have SIGTERM */
|
|
|
54 |
signal(SIGTERM, signal_catcher);
|
|
|
55 |
#endif
|
|
|
56 |
}
|
|
|
57 |
|
|
|
58 |
#endif
|
|
|
59 |
|
|
|
60 |
|
|
|
61 |
/*
|
|
|
62 |
* Optional progress monitor: display a percent-done figure on stderr.
|
|
|
63 |
*/
|
|
|
64 |
|
|
|
65 |
#ifdef PROGRESS_REPORT
|
|
|
66 |
|
|
|
67 |
METHODDEF(void)
|
|
|
68 |
progress_monitor (j_common_ptr cinfo)
|
|
|
69 |
{
|
|
|
70 |
cd_progress_ptr prog = (cd_progress_ptr) cinfo->progress;
|
|
|
71 |
int total_passes = prog->pub.total_passes + prog->total_extra_passes;
|
|
|
72 |
int percent_done = (int) (prog->pub.pass_counter*100L/prog->pub.pass_limit);
|
|
|
73 |
|
|
|
74 |
if (percent_done != prog->percent_done) {
|
|
|
75 |
prog->percent_done = percent_done;
|
|
|
76 |
if (total_passes > 1) {
|
|
|
77 |
fprintf(stderr, "\rPass %d/%d: %3d%% ",
|
|
|
78 |
prog->pub.completed_passes + prog->completed_extra_passes + 1,
|
|
|
79 |
total_passes, percent_done);
|
|
|
80 |
} else {
|
|
|
81 |
fprintf(stderr, "\r %3d%% ", percent_done);
|
|
|
82 |
}
|
|
|
83 |
fflush(stderr);
|
|
|
84 |
}
|
|
|
85 |
}
|
|
|
86 |
|
|
|
87 |
|
|
|
88 |
GLOBAL(void)
|
|
|
89 |
start_progress_monitor (j_common_ptr cinfo, cd_progress_ptr progress)
|
|
|
90 |
{
|
|
|
91 |
/* Enable progress display, unless trace output is on */
|
|
|
92 |
if (cinfo->err->trace_level == 0) {
|
|
|
93 |
progress->pub.progress_monitor = progress_monitor;
|
|
|
94 |
progress->completed_extra_passes = 0;
|
|
|
95 |
progress->total_extra_passes = 0;
|
|
|
96 |
progress->percent_done = -1;
|
|
|
97 |
cinfo->progress = &progress->pub;
|
|
|
98 |
}
|
|
|
99 |
}
|
|
|
100 |
|
|
|
101 |
|
|
|
102 |
GLOBAL(void)
|
|
|
103 |
end_progress_monitor (j_common_ptr cinfo)
|
|
|
104 |
{
|
|
|
105 |
/* Clear away progress display */
|
|
|
106 |
if (cinfo->err->trace_level == 0) {
|
|
|
107 |
fprintf(stderr, "\r \r");
|
|
|
108 |
fflush(stderr);
|
|
|
109 |
}
|
|
|
110 |
}
|
|
|
111 |
|
|
|
112 |
#endif
|
|
|
113 |
|
|
|
114 |
|
|
|
115 |
/*
|
|
|
116 |
* Case-insensitive matching of possibly-abbreviated keyword switches.
|
|
|
117 |
* keyword is the constant keyword (must be lower case already),
|
|
|
118 |
* minchars is length of minimum legal abbreviation.
|
|
|
119 |
*/
|
|
|
120 |
|
|
|
121 |
GLOBAL(boolean)
|
|
|
122 |
keymatch (char * arg, const char * keyword, int minchars)
|
|
|
123 |
{
|
|
|
124 |
register int ca, ck;
|
|
|
125 |
register int nmatched = 0;
|
|
|
126 |
|
|
|
127 |
while ((ca = *arg++) != '\0') {
|
|
|
128 |
if ((ck = *keyword++) == '\0')
|
|
|
129 |
return FALSE; /* arg longer than keyword, no good */
|
|
|
130 |
if (isupper(ca)) /* force arg to lcase (assume ck is already) */
|
|
|
131 |
ca = tolower(ca);
|
|
|
132 |
if (ca != ck)
|
|
|
133 |
return FALSE; /* no good */
|
|
|
134 |
nmatched++; /* count matched characters */
|
|
|
135 |
}
|
|
|
136 |
/* reached end of argument; fail if it's too short for unique abbrev */
|
|
|
137 |
if (nmatched < minchars)
|
|
|
138 |
return FALSE;
|
|
|
139 |
return TRUE; /* A-OK */
|
|
|
140 |
}
|
|
|
141 |
|
|
|
142 |
|
|
|
143 |
/*
|
|
|
144 |
* Routines to establish binary I/O mode for stdin and stdout.
|
|
|
145 |
* Non-Unix systems often require some hacking to get out of text mode.
|
|
|
146 |
*/
|
|
|
147 |
|
|
|
148 |
GLOBAL(FILE *)
|
|
|
149 |
read_stdin (void)
|
|
|
150 |
{
|
|
|
151 |
FILE * input_file = stdin;
|
|
|
152 |
|
|
|
153 |
#ifdef USE_SETMODE /* need to hack file mode? */
|
|
|
154 |
setmode(fileno(stdin), O_BINARY);
|
|
|
155 |
#endif
|
|
|
156 |
#ifdef USE_FDOPEN /* need to re-open in binary mode? */
|
|
|
157 |
if ((input_file = fdopen(fileno(stdin), READ_BINARY)) == NULL) {
|
|
|
158 |
fprintf(stderr, "Cannot reopen stdin\n");
|
|
|
159 |
exit(EXIT_FAILURE);
|
|
|
160 |
}
|
|
|
161 |
#endif
|
|
|
162 |
return input_file;
|
|
|
163 |
}
|
|
|
164 |
|
|
|
165 |
|
|
|
166 |
GLOBAL(FILE *)
|
|
|
167 |
write_stdout (void)
|
|
|
168 |
{
|
|
|
169 |
FILE * output_file = stdout;
|
|
|
170 |
|
|
|
171 |
#ifdef USE_SETMODE /* need to hack file mode? */
|
|
|
172 |
setmode(fileno(stdout), O_BINARY);
|
|
|
173 |
#endif
|
|
|
174 |
#ifdef USE_FDOPEN /* need to re-open in binary mode? */
|
|
|
175 |
if ((output_file = fdopen(fileno(stdout), WRITE_BINARY)) == NULL) {
|
|
|
176 |
fprintf(stderr, "Cannot reopen stdout\n");
|
|
|
177 |
exit(EXIT_FAILURE);
|
|
|
178 |
}
|
|
|
179 |
#endif
|
|
|
180 |
return output_file;
|
|
|
181 |
}
|