mirror of
https://github.com/ultimatepp/ultimatepp.git
synced 2026-05-15 14:16:07 -06:00
plugin/jpg: Updated to version 10, Core: INITCHECK improved to show initializers
This commit is contained in:
parent
4f47d02b39
commit
4bf79098bc
43 changed files with 2109 additions and 3269 deletions
|
|
@ -206,6 +206,7 @@ initial: 9b
|
|||
2019-03-22: 9c
|
||||
2020-09-03: 9d
|
||||
2024-05-19: 9f
|
||||
2026-01-28: 10
|
||||
-------------------------------------------------------------------
|
||||
plugin/tif
|
||||
|
||||
|
|
|
|||
|
|
@ -75,15 +75,15 @@ inline void LOGNOP__() {}
|
|||
#endif
|
||||
|
||||
#ifdef flagCHECKINIT
|
||||
void InitBlockBegin__(const char *fn, int line);
|
||||
void InitBlockEnd__(const char *fn, int line);
|
||||
void InitBlockBegin__(const char *fn, int line, const char *kind);
|
||||
void InitBlockEnd__(const char *fn, int line, const char *kind);
|
||||
#else
|
||||
inline void InitBlockBegin__(const char *, int) {}
|
||||
inline void InitBlockEnd__(const char *, int) {}
|
||||
#endif
|
||||
|
||||
struct Callinit {
|
||||
Callinit(void (*fn)(), const char *cpp, int line) { InitBlockBegin__(cpp, line); fn(); InitBlockEnd__(cpp, line); }
|
||||
Callinit(void (*fn)(), const char *cpp, int line) { InitBlockBegin__(cpp, line, "INITBLOCK"); fn(); InitBlockEnd__(cpp, line, "INITBLOCK"); }
|
||||
Callinit(void (*fn)()) { fn(); }
|
||||
};
|
||||
|
||||
|
|
@ -118,7 +118,9 @@ void x##__initializer_fn(); \
|
|||
void x##__initializer() \
|
||||
{ \
|
||||
ONCELOCK { \
|
||||
InitBlockBegin__(__FILE__, __LINE__, "INITIALIZER(" #x ")"); \
|
||||
x##__initializer_fn(); \
|
||||
InitBlockEnd__(__FILE__, __LINE__, "INITIALIZER(" #x ")"); \
|
||||
} \
|
||||
} \
|
||||
void x##__initializer_fn()
|
||||
|
|
|
|||
|
|
@ -318,8 +318,8 @@ void LogStream::_Put(const void *data, dword size)
|
|||
|
||||
#ifdef flagCHECKINIT // Adds heap check and additional logging INITBLOCKs
|
||||
|
||||
void InitBlockBegin__(const char *fn, int line) {
|
||||
RLOG(fn << " " << line << " init block");
|
||||
void InitBlockBegin__(const char *fn, int line, const char *kind) {
|
||||
RLOG(fn << " " << line << " " << kind << " started");
|
||||
#ifdef HEAPDBG
|
||||
MemoryCheckDebug();
|
||||
#else
|
||||
|
|
@ -327,8 +327,8 @@ void InitBlockBegin__(const char *fn, int line) {
|
|||
#endif
|
||||
}
|
||||
|
||||
void InitBlockEnd__(const char *fn, int line) {
|
||||
RLOG(fn << " " << line << " init block finished");
|
||||
void InitBlockEnd__(const char *fn, int line, const char *kind) {
|
||||
RLOG(fn << " " << line << " " << kind << " finished");
|
||||
#ifdef HEAPDBG
|
||||
MemoryCheckDebug();
|
||||
#else
|
||||
|
|
|
|||
|
|
@ -11,35 +11,12 @@ protected:
|
|||
Vector<WString>& coreCmdLine__();
|
||||
Vector<WString> SplitCmdLine__(const char *cmd);
|
||||
|
||||
#ifdef PLATFORM_WINCE
|
||||
|
||||
#define GUI_APP_MAIN \
|
||||
void GuiMainFn_();\
|
||||
\
|
||||
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE, LPTSTR lpCmdLine, int nCmdShow) \
|
||||
{ \
|
||||
UPP::coreCmdLine__() = UPP::SplitCmdLine__(UPP::FromSystemCharset(lpCmdLine)); \
|
||||
UPP::AppInitEnvironment__(); \
|
||||
UPP::Ctrl::InitWin32(hInstance); \
|
||||
try { \
|
||||
GuiMainFn_(); \
|
||||
} \
|
||||
UPP::Ctrl::ExitWin32(); \
|
||||
UPP::Ctrl::ShutdownThreads(); \
|
||||
UPP::AppExit__(); \
|
||||
return UPP::GetExitCode(); \
|
||||
} \
|
||||
\
|
||||
void GuiMainFn_()
|
||||
|
||||
#else
|
||||
|
||||
#define GUI_APP_MAIN \
|
||||
void GuiMainFn_();\
|
||||
\
|
||||
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR lpCmdLine, int nCmdShow) \
|
||||
{ \
|
||||
UPP::AppInitEnvironment__(); \
|
||||
DLOG("WinMain"); UPP::AppInitEnvironment__(); \
|
||||
GUI_APP_MAIN_HOOK \
|
||||
UPP::Ctrl::InitWin32(hInstance); \
|
||||
UPP::AppExecute__(GuiMainFn_); \
|
||||
|
|
@ -71,10 +48,6 @@ BOOL WINAPI DllMain(HINSTANCE hinstDll, DWORD fdwReason, LPVOID lpReserved) \
|
|||
\
|
||||
void _DllMainAppInit()
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef PLATFORM_WINCE
|
||||
|
||||
class DHCtrl : public Ctrl {
|
||||
public:
|
||||
virtual void State(int reason);
|
||||
|
|
@ -109,6 +82,3 @@ public:
|
|||
DHCtrl();
|
||||
~DHCtrl();
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ with respect to this software, its quality, accuracy, merchantability, or
|
|||
fitness for a particular purpose. This software is provided "AS IS", and you,
|
||||
its user, assume the entire risk as to its quality and accuracy.
|
||||
|
||||
This software is copyright (C) 1991-2024, Thomas G. Lane, Guido Vollbeding.
|
||||
This software is copyright (C) 1991-2026, Thomas G. Lane, Guido Vollbeding.
|
||||
All Rights Reserved except as specified below.
|
||||
|
||||
Permission is hereby granted to use, copy, modify, and distribute this
|
||||
|
|
|
|||
|
|
@ -11,19 +11,7 @@ file
|
|||
jpgreg.icpp,
|
||||
src.tpp,
|
||||
lib readonly separator,
|
||||
lib\jconfig.h,
|
||||
lib\README,
|
||||
lib\cderror.h,
|
||||
lib\cdjpeg.h,
|
||||
lib\jdct.h,
|
||||
lib\jerror.h,
|
||||
lib\jinclude.h,
|
||||
lib\jmemsys.h,
|
||||
lib\jmorecfg.h,
|
||||
lib\jpegint.h,
|
||||
lib\jpeglib.h,
|
||||
lib\jversion.h,
|
||||
lib\transupp.h,
|
||||
lib\jaricom.c,
|
||||
lib\jcapimin.c,
|
||||
lib\jcapistd.c,
|
||||
|
|
@ -83,6 +71,18 @@ file
|
|||
lib\wrppm.c,
|
||||
lib\wrrle.c,
|
||||
lib\wrtarga.c,
|
||||
lib\cderror.h,
|
||||
lib\cdjpeg.h,
|
||||
lib\jconfig.h,
|
||||
lib\jdct.h,
|
||||
lib\jerror.h,
|
||||
lib\jinclude.h,
|
||||
lib\jmemsys.h,
|
||||
lib\jmorecfg.h,
|
||||
lib\jpegint.h,
|
||||
lib\jpeglib.h,
|
||||
lib\jversion.h,
|
||||
lib\transupp.h,
|
||||
end readonly separator,
|
||||
Copying;
|
||||
|
||||
|
|
|
|||
374
uppsrc/plugin/jpg/lib/README
Normal file
374
uppsrc/plugin/jpg/lib/README
Normal file
|
|
@ -0,0 +1,374 @@
|
|||
The Independent JPEG Group's JPEG software
|
||||
==========================================
|
||||
|
||||
README for release 10 of 25-Jan-2026
|
||||
====================================
|
||||
|
||||
This distribution contains the ninth public release of the Independent JPEG
|
||||
Group's free JPEG software. You are welcome to redistribute this software and
|
||||
to use it for any purpose, subject to the conditions under LEGAL ISSUES, below.
|
||||
|
||||
This software is the work of Tom Lane, Guido Vollbeding, Philip Gladstone,
|
||||
Bill Allombert, Jim Boucher, Lee Crocker, Bob Friesenhahn, Ben Jackson,
|
||||
John Korejwa, Julian Minguillon, Luis Ortiz, George Phillips, Davide Rossi,
|
||||
Ge' Weijers, and other members of the Independent JPEG Group.
|
||||
|
||||
IJG is not affiliated with the ISO/IEC JTC1/SC29/WG1 standards committee
|
||||
(previously known as JPEG, together with ITU-T SG16).
|
||||
|
||||
|
||||
DOCUMENTATION ROADMAP
|
||||
=====================
|
||||
|
||||
This file contains the following sections:
|
||||
|
||||
OVERVIEW General description of JPEG and the IJG software.
|
||||
LEGAL ISSUES Copyright, lack of warranty, terms of distribution.
|
||||
REFERENCES Where to learn more about JPEG.
|
||||
ARCHIVE LOCATIONS Where to find newer versions of this software.
|
||||
ACKNOWLEDGMENTS Special thanks.
|
||||
FILE FORMAT WARS Software *not* to get.
|
||||
TO DO Plans for future IJG releases.
|
||||
|
||||
Other documentation files in the distribution are:
|
||||
|
||||
User documentation:
|
||||
install.txt How to configure and install the IJG software.
|
||||
usage.txt Usage instructions for cjpeg, djpeg, jpegtran,
|
||||
rdjpgcom, and wrjpgcom.
|
||||
*.1 Unix-style man pages for programs (same info as usage.txt).
|
||||
wizard.txt Advanced usage instructions for JPEG wizards only.
|
||||
cdaltui.txt Description of alternate user interface for cjpeg/djpeg.
|
||||
change.log Version-to-version change highlights.
|
||||
Programmer and internal documentation:
|
||||
libjpeg.txt How to use the JPEG library in your own programs.
|
||||
example.c Sample code for calling the JPEG library.
|
||||
structure.txt Overview of the JPEG library's internal structure.
|
||||
filelist.txt Road map of IJG files.
|
||||
coderules.txt Coding style rules --- please read if you contribute code.
|
||||
|
||||
Please read at least the files install.txt and usage.txt. Some information
|
||||
can also be found in the JPEG FAQ (Frequently Asked Questions) article. See
|
||||
ARCHIVE LOCATIONS below to find out where to obtain the FAQ article.
|
||||
|
||||
If you want to understand how the JPEG code works, we suggest reading one or
|
||||
more of the REFERENCES, then looking at the documentation files (in roughly
|
||||
the order listed) before diving into the code.
|
||||
|
||||
|
||||
OVERVIEW
|
||||
========
|
||||
|
||||
This package contains C software to implement JPEG image encoding, decoding,
|
||||
and transcoding. JPEG (pronounced "jay-peg") is a standardized compression
|
||||
method for full-color and grayscale images.
|
||||
|
||||
This software implements JPEG baseline, extended-sequential, and progressive
|
||||
compression processes. Provision is made for supporting all variants of these
|
||||
processes, although some uncommon parameter settings aren't implemented yet.
|
||||
We have made no provision for supporting the hierarchical or lossless
|
||||
processes defined in the standard.
|
||||
|
||||
We provide a set of library routines for reading and writing JPEG image files,
|
||||
plus two sample applications "cjpeg" and "djpeg", which use the library to
|
||||
perform conversion between JPEG and some other popular image file formats.
|
||||
The library is intended to be reused in other applications.
|
||||
|
||||
In order to support file conversion and viewing software, we have included
|
||||
considerable functionality beyond the bare JPEG coding/decoding capability;
|
||||
for example, the color quantization modules are not strictly part of JPEG
|
||||
decoding, but they are essential for output to colormapped file formats or
|
||||
colormapped displays. These extra functions can be compiled out of the
|
||||
library if not required for a particular application.
|
||||
|
||||
We have also included "jpegtran", a utility for lossless transcoding between
|
||||
different JPEG processes, and "rdjpgcom" and "wrjpgcom", two simple
|
||||
applications for inserting and extracting textual comments in JFIF files.
|
||||
|
||||
The emphasis in designing this software has been on achieving portability and
|
||||
flexibility, while also making it fast enough to be useful. In particular,
|
||||
the software is not intended to be read as a tutorial on JPEG. (See the
|
||||
REFERENCES section for introductory material.) Rather, it is intended to
|
||||
be reliable, portable, industrial-strength code. We do not claim to have
|
||||
achieved that goal in every aspect of the software, but we strive for it.
|
||||
|
||||
We welcome the use of this software as a component of commercial products.
|
||||
No royalty is required, but we do ask for an acknowledgement in product
|
||||
documentation, as described under LEGAL ISSUES.
|
||||
|
||||
|
||||
LEGAL ISSUES
|
||||
============
|
||||
|
||||
In plain English:
|
||||
|
||||
1. We don't promise that this software works. (But if you find any bugs,
|
||||
please let us know!)
|
||||
2. You can use this software for whatever you want. You don't have to pay us.
|
||||
3. You may not pretend that you wrote this software. If you use it in a
|
||||
program, you must acknowledge somewhere in your documentation that
|
||||
you've used the IJG code.
|
||||
|
||||
In legalese:
|
||||
|
||||
The authors make NO WARRANTY or representation, either express or implied,
|
||||
with respect to this software, its quality, accuracy, merchantability, or
|
||||
fitness for a particular purpose. This software is provided "AS IS", and you,
|
||||
its user, assume the entire risk as to its quality and accuracy.
|
||||
|
||||
This software is copyright (C) 1991-2026, Thomas G. Lane, Guido Vollbeding.
|
||||
All Rights Reserved except as specified below.
|
||||
|
||||
Permission is hereby granted to use, copy, modify, and distribute this
|
||||
software (or portions thereof) for any purpose, without fee, subject to these
|
||||
conditions:
|
||||
(1) If any part of the source code for this software is distributed, then this
|
||||
README file must be included, with this copyright and no-warranty notice
|
||||
unaltered; and any additions, deletions, or changes to the original files
|
||||
must be clearly indicated in accompanying documentation.
|
||||
(2) If only executable code is distributed, then the accompanying
|
||||
documentation must state that "this software is based in part on the work of
|
||||
the Independent JPEG Group".
|
||||
(3) Permission for use of this software is granted only if the user accepts
|
||||
full responsibility for any undesirable consequences; the authors accept
|
||||
NO LIABILITY for damages of any kind.
|
||||
|
||||
These conditions apply to any software derived from or based on the IJG code,
|
||||
not just to the unmodified library. If you use our work, you ought to
|
||||
acknowledge us.
|
||||
|
||||
Permission is NOT granted for the use of any IJG author's name or company name
|
||||
in advertising or publicity relating to this software or products derived from
|
||||
it. This software may be referred to only as "the Independent JPEG Group's
|
||||
software".
|
||||
|
||||
We specifically permit and encourage the use of this software as the basis of
|
||||
commercial products, provided that all warranty or liability claims are
|
||||
assumed by the product vendor.
|
||||
|
||||
|
||||
The Unix configuration script "configure" was produced with GNU Autoconf.
|
||||
It is copyright by the Free Software Foundation but is freely distributable.
|
||||
The same holds for its supporting scripts (config.guess, config.sub,
|
||||
ltmain.sh). Another support script, install-sh, is copyright by X Consortium
|
||||
but is also freely distributable.
|
||||
|
||||
|
||||
REFERENCES
|
||||
==========
|
||||
|
||||
We recommend reading one or more of these references before trying to
|
||||
understand the innards of the JPEG software.
|
||||
|
||||
The best short technical introduction to the JPEG compression algorithm is
|
||||
Wallace, Gregory K. "The JPEG Still Picture Compression Standard",
|
||||
Communications of the ACM, April 1991 (vol. 34 no. 4), pp. 30-44.
|
||||
(Adjacent articles in that issue discuss MPEG motion picture compression,
|
||||
applications of JPEG, and related topics.) If you don't have the CACM issue
|
||||
handy, a PDF file containing a revised version of Wallace's article is
|
||||
available at https://www.ijg.org/files/Wallace.JPEG.pdf. The file (actually
|
||||
a preprint for an article that appeared in IEEE Trans. Consumer Electronics)
|
||||
omits the sample images that appeared in CACM, but it includes corrections
|
||||
and some added material. Note: the Wallace article is copyright ACM and IEEE,
|
||||
and it may not be used for commercial purposes.
|
||||
|
||||
A somewhat less technical, more leisurely introduction to JPEG can be found in
|
||||
"The Data Compression Book" by Mark Nelson and Jean-loup Gailly, published by
|
||||
M&T Books (New York), 2nd ed. 1996, ISBN 1-55851-434-1. This book provides
|
||||
good explanations and example C code for a multitude of compression methods
|
||||
including JPEG. It is an excellent source if you are comfortable reading C
|
||||
code but don't know much about data compression in general. The book's JPEG
|
||||
sample code is far from industrial-strength, but when you are ready to look
|
||||
at a full implementation, you've got one here...
|
||||
|
||||
The best currently available description of JPEG is the textbook "JPEG Still
|
||||
Image Data Compression Standard" by William B. Pennebaker and Joan L.
|
||||
Mitchell, published by Van Nostrand Reinhold, 1993, ISBN 0-442-01272-1.
|
||||
Price US$59.95, 638 pp. The book includes the complete text of the ISO JPEG
|
||||
standards (DIS 10918-1 and draft DIS 10918-2).
|
||||
Although this is by far the most detailed and comprehensive exposition of
|
||||
JPEG publicly available, we point out that it is still missing an explanation
|
||||
of the most essential properties and algorithms of the underlying DCT
|
||||
technology.
|
||||
If you think that you know about DCT-based JPEG after reading this book,
|
||||
then you are in delusion. The real fundamentals and corresponding potential
|
||||
of DCT-based JPEG are not publicly known so far, and that is the reason for
|
||||
all the mistaken developments taking place in the image coding domain.
|
||||
|
||||
The original JPEG standard is divided into two parts, Part 1 being the actual
|
||||
specification, while Part 2 covers compliance testing methods. Part 1 is
|
||||
titled "Digital Compression and Coding of Continuous-tone Still Images,
|
||||
Part 1: Requirements and guidelines" and has document numbers ISO/IEC IS
|
||||
10918-1, ITU-T T.81. Part 2 is titled "Digital Compression and Coding of
|
||||
Continuous-tone Still Images, Part 2: Compliance testing" and has document
|
||||
numbers ISO/IEC IS 10918-2, ITU-T T.83.
|
||||
IJG JPEG 8 introduced an implementation of the JPEG SmartScale extension
|
||||
which is specified in two documents: A contributed document at ITU and ISO
|
||||
with title "ITU-T JPEG-Plus Proposal for Extending ITU-T T.81 for Advanced
|
||||
Image Coding", April 2006, Geneva, Switzerland. The latest version of this
|
||||
document is Revision 3. And a contributed document ISO/IEC JTC1/SC29/WG1 N
|
||||
5799 with title "Evolution of JPEG", June/July 2011, Berlin, Germany.
|
||||
IJG JPEG 9 introduces a reversible color transform for improved lossless
|
||||
compression which is described in a contributed document ISO/IEC JTC1/SC29/
|
||||
WG1 N 6080 with title "JPEG 9 Lossless Coding", June/July 2012, Paris, France.
|
||||
|
||||
The JPEG standard does not specify all details of an interchangeable file
|
||||
format. For the omitted details we follow the "JFIF" conventions, version 2.
|
||||
JFIF version 1 has been adopted as Recommendation ITU-T T.871 (05/2011) :
|
||||
Information technology - Digital compression and coding of continuous-tone
|
||||
still images: JPEG File Interchange Format (JFIF). It is available as a
|
||||
free download in PDF file format from https://www.itu.int/rec/T-REC-T.871.
|
||||
A PDF file of the older JFIF document is available at
|
||||
https://www.w3.org/Graphics/JPEG/jfif3.pdf.
|
||||
|
||||
The TIFF 6.0 file format specification can be obtained by FTP from
|
||||
ftp://ftp.sgi.com/graphics/tiff/TIFF6.ps.gz. The JPEG incorporation scheme
|
||||
found in the TIFF 6.0 spec of 3-June-92 has a number of serious problems.
|
||||
IJG does not recommend use of the TIFF 6.0 design (TIFF Compression tag 6).
|
||||
Instead, we recommend the JPEG design proposed by TIFF Technical Note #2
|
||||
(Compression tag 7). Copies of this Note can be obtained from
|
||||
https://www.ijg.org/files/. It is expected that the next revision
|
||||
of the TIFF spec will replace the 6.0 JPEG design with the Note's design.
|
||||
Although IJG's own code does not support TIFF/JPEG, the free libtiff library
|
||||
uses our library to implement TIFF/JPEG per the Note.
|
||||
|
||||
|
||||
ARCHIVE LOCATIONS
|
||||
=================
|
||||
|
||||
The "official" archive site for this software is www.ijg.org.
|
||||
The most recent released version can always be found there in
|
||||
directory "files". This particular version will be archived
|
||||
in Windows-compatible "zip" archive format as
|
||||
https://www.ijg.org/files/jpegsr10.zip, and
|
||||
in Unix-compatible "tar.gz" archive format as
|
||||
https://www.ijg.org/files/jpegsrc.v10.tar.gz.
|
||||
|
||||
The JPEG FAQ (Frequently Asked Questions) article is a source of some
|
||||
general information about JPEG.
|
||||
It is available on the World Wide Web at http://www.faqs.org/faqs/jpeg-faq/
|
||||
and other news.answers archive sites, including the official news.answers
|
||||
archive at rtfm.mit.edu: ftp://rtfm.mit.edu/pub/usenet/news.answers/jpeg-faq/.
|
||||
If you don't have Web or FTP access, send e-mail to mail-server@rtfm.mit.edu
|
||||
with body
|
||||
send usenet/news.answers/jpeg-faq/part1
|
||||
send usenet/news.answers/jpeg-faq/part2
|
||||
|
||||
|
||||
ACKNOWLEDGMENTS
|
||||
===============
|
||||
|
||||
Thank to Juergen Bruder for providing me with a copy of the common DCT
|
||||
algorithm article, only to find out that I had come to the same result
|
||||
in a more direct and comprehensible way with a more generative approach.
|
||||
|
||||
Thank to Istvan Sebestyen and Joan L. Mitchell for inviting me to the
|
||||
ITU JPEG (Study Group 16) meeting in Geneva, Switzerland.
|
||||
|
||||
Thank to Thomas Wiegand and Gary Sullivan for inviting me to the
|
||||
Joint Video Team (MPEG & ITU) meeting in Geneva, Switzerland.
|
||||
|
||||
Thank to Thomas Richter and Daniel Lee for inviting me to the
|
||||
ISO/IEC JTC1/SC29/WG1 (previously known as JPEG, together with ITU-T SG16)
|
||||
meeting in Berlin, Germany.
|
||||
|
||||
Thank to John Korejwa and Massimo Ballerini for inviting me to
|
||||
fruitful consultations in Boston, MA and Milan, Italy.
|
||||
|
||||
Thank to Hendrik Elstner, Roland Fassauer, Simone Zuck, Guenther
|
||||
Maier-Gerber, Walter Stoeber, Fred Schmitz, and Norbert Braunagel
|
||||
for corresponding business development.
|
||||
|
||||
Thank to Nico Zschach and Dirk Stelling of the technical support team
|
||||
at the Digital Images company in Halle for providing me with extra
|
||||
equipment for configuration tests.
|
||||
|
||||
Thank to Richard F. Lyon (then of Foveon Inc.) for fruitful
|
||||
communication about JPEG configuration in Sigma Photo Pro software.
|
||||
|
||||
Thank to Andrew Finkenstadt for hosting the ijg.org site.
|
||||
|
||||
Thank to Thomas G. Lane for the original design and development
|
||||
of this singular software package.
|
||||
|
||||
Thank to Lars Goehler, Andreas Heinecke, Sebastian Fuss,
|
||||
Yvonne Roebert, Andrej Werner, Ulf-Dietrich Braumann,
|
||||
and Nina Ssymank for support and public relations.
|
||||
|
||||
|
||||
FILE FORMAT WARS
|
||||
================
|
||||
|
||||
The ISO/IEC JTC1/SC29/WG1 standards committee (previously known as JPEG,
|
||||
together with ITU-T SG16) currently promotes different formats containing
|
||||
the name "JPEG" which is misleading because these formats are incompatible
|
||||
with original DCT-based JPEG and are based on faulty technologies.
|
||||
IJG therefore does not and will not support such momentary mistakes
|
||||
(see REFERENCES).
|
||||
There exist also distributions under the name "OpenJPEG" promoting such
|
||||
kind of formats which is misleading because they don't support original
|
||||
JPEG images.
|
||||
We have no sympathy for the promotion of inferior formats. Indeed, one of
|
||||
the original reasons for developing this free software was to help force
|
||||
convergence on common, interoperable format standards for JPEG files.
|
||||
Don't use an incompatible file format!
|
||||
(In any case, our decoder will remain capable of reading existing JPEG
|
||||
image files indefinitely.)
|
||||
|
||||
The ISO committee pretends to be "responsible for the popular JPEG" in their
|
||||
public reports which is not true because they don't respond to actual
|
||||
requirements for the maintenance of the original JPEG specification.
|
||||
Furthermore, the ISO committee pretends to "ensure interoperability" with
|
||||
their standards which is not true because their "standards" support only
|
||||
application-specific and proprietary use cases and contain mathematically
|
||||
incorrect code.
|
||||
|
||||
There are currently different distributions in circulation containing the
|
||||
name "libjpeg" which is misleading because they don't have the features and
|
||||
are incompatible with formats supported by actual IJG libjpeg distributions.
|
||||
One of those fakes is released by members of the ISO committee and just uses
|
||||
the name of libjpeg for misdirection of people, similar to the abuse of the
|
||||
name JPEG as described above, while having nothing in common with actual IJG
|
||||
libjpeg distributions and containing mathematically incorrect code.
|
||||
The other one claims to be a "derivative" or "fork" of the original libjpeg,
|
||||
but violates the license conditions as described under LEGAL ISSUES above
|
||||
and violates basic C programming properties.
|
||||
We have no sympathy for the release of misleading, incorrect and illegal
|
||||
distributions derived from obsolete code bases.
|
||||
Don't use an obsolete code base!
|
||||
|
||||
According to the UCC (Uniform Commercial Code) law, IJG has the lawful and
|
||||
legal right to foreclose on certain standardization bodies and other
|
||||
institutions or corporations that knowingly perform substantial and
|
||||
systematic deceptive acts and practices, fraud, theft, and damaging of the
|
||||
value of the people of this planet without their knowing, willing and
|
||||
intentional consent.
|
||||
The titles, ownership, and rights of these institutions and all their assets
|
||||
are now duly secured and held in trust for the free people of this planet.
|
||||
People of the planet, on every country, may have a financial interest in
|
||||
the assets of these former principals, agents, and beneficiaries of the
|
||||
foreclosed institutions and corporations.
|
||||
IJG asserts what is: that each man, woman, and child has unalienable value
|
||||
and rights granted and deposited in them by the Creator and not any one of
|
||||
the people is subordinate to any artificial principality, corporate fiction
|
||||
or the special interest of another without their appropriate knowing,
|
||||
willing and intentional consent made by contract or accommodation agreement.
|
||||
IJG expresses that which already was.
|
||||
The people have already determined and demanded that public administration
|
||||
entities, national governments, and their supporting judicial systems must
|
||||
be fully transparent, accountable, and liable.
|
||||
IJG has secured the value for all concerned free people of the planet.
|
||||
|
||||
A partial list of foreclosed institutions and corporations ("Hall of Shame")
|
||||
is currently prepared and will be published later.
|
||||
|
||||
|
||||
TO DO
|
||||
=====
|
||||
|
||||
Version 10 is the third release of a new generation JPEG standard
|
||||
to overcome the limitations of the original JPEG specification,
|
||||
and is a true source reference JPEG codec.
|
||||
More features are being prepared for coming releases...
|
||||
|
||||
Please send bug reports, offers of help, etc. to jpeg-info@ijg.org.
|
||||
|
|
@ -1,664 +0,0 @@
|
|||
/*
|
||||
* cjpeg.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2003-2013 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
* This file contains a command-line user interface for the JPEG compressor.
|
||||
* It should work on any system with Unix- or MS-DOS-style command lines.
|
||||
*
|
||||
* Two different command line styles are permitted, depending on the
|
||||
* compile-time switch TWO_FILE_COMMANDLINE:
|
||||
* cjpeg [options] inputfile outputfile
|
||||
* cjpeg [options] [inputfile]
|
||||
* In the second style, output is always to standard output, which you'd
|
||||
* normally redirect to a file or pipe to some other program. Input is
|
||||
* either from a named file or from standard input (typically redirected).
|
||||
* The second style is convenient on Unix but is unhelpful on systems that
|
||||
* don't support pipes. Also, you MUST use the first style if your system
|
||||
* doesn't do binary I/O to stdin/stdout.
|
||||
* To simplify script writing, the "-outfile" switch is provided. The syntax
|
||||
* cjpeg [options] -outfile outputfile inputfile
|
||||
* works regardless of which command line style is used.
|
||||
*/
|
||||
|
||||
#include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */
|
||||
#include "jversion.h" /* for version message */
|
||||
|
||||
#ifdef USE_CCOMMAND /* command-line reader for Macintosh */
|
||||
#ifdef __MWERKS__
|
||||
#include <SIOUX.h> /* Metrowerks needs this */
|
||||
#include <console.h> /* ... and this */
|
||||
#endif
|
||||
#ifdef THINK_C
|
||||
#include <console.h> /* Think declares it here */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
/* Create the add-on message string table. */
|
||||
|
||||
#define JMESSAGE(code,string) string ,
|
||||
|
||||
static const char * const cdjpeg_message_table[] = {
|
||||
#include "cderror.h"
|
||||
NULL
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* This routine determines what format the input file is,
|
||||
* and selects the appropriate input-reading module.
|
||||
*
|
||||
* To determine which family of input formats the file belongs to,
|
||||
* we may look only at the first byte of the file, since C does not
|
||||
* guarantee that more than one character can be pushed back with ungetc.
|
||||
* Looking at additional bytes would require one of these approaches:
|
||||
* 1) assume we can fseek() the input file (fails for piped input);
|
||||
* 2) assume we can push back more than one character (works in
|
||||
* some C implementations, but unportable);
|
||||
* 3) provide our own buffering (breaks input readers that want to use
|
||||
* stdio directly, such as the RLE library);
|
||||
* or 4) don't put back the data, and modify the input_init methods to assume
|
||||
* they start reading after the start of file (also breaks RLE library).
|
||||
* #1 is attractive for MS-DOS but is untenable on Unix.
|
||||
*
|
||||
* The most portable solution for file types that can't be identified by their
|
||||
* first byte is to make the user tell us what they are. This is also the
|
||||
* only approach for "raw" file types that contain only arbitrary values.
|
||||
* We presently apply this method for Targa files. Most of the time Targa
|
||||
* files start with 0x00, so we recognize that case. Potentially, however,
|
||||
* a Targa file could start with any byte value (byte 0 is the length of the
|
||||
* seldom-used ID field), so we provide a switch to force Targa input mode.
|
||||
*/
|
||||
|
||||
static boolean is_targa; /* records user -targa switch */
|
||||
|
||||
|
||||
LOCAL(cjpeg_source_ptr)
|
||||
select_file_type (j_compress_ptr cinfo, FILE * infile)
|
||||
{
|
||||
int c;
|
||||
|
||||
if (is_targa) {
|
||||
#ifdef TARGA_SUPPORTED
|
||||
return jinit_read_targa(cinfo);
|
||||
#else
|
||||
ERREXIT(cinfo, JERR_TGA_NOTCOMP);
|
||||
#endif
|
||||
}
|
||||
|
||||
if ((c = getc(infile)) == EOF)
|
||||
ERREXIT(cinfo, JERR_INPUT_EMPTY);
|
||||
if (ungetc(c, infile) == EOF)
|
||||
ERREXIT(cinfo, JERR_UNGETC_FAILED);
|
||||
|
||||
switch (c) {
|
||||
#ifdef BMP_SUPPORTED
|
||||
case 'B':
|
||||
return jinit_read_bmp(cinfo);
|
||||
#endif
|
||||
#ifdef GIF_SUPPORTED
|
||||
case 'G':
|
||||
return jinit_read_gif(cinfo);
|
||||
#endif
|
||||
#ifdef PPM_SUPPORTED
|
||||
case 'P':
|
||||
return jinit_read_ppm(cinfo);
|
||||
#endif
|
||||
#ifdef RLE_SUPPORTED
|
||||
case 'R':
|
||||
return jinit_read_rle(cinfo);
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
case 0x00:
|
||||
return jinit_read_targa(cinfo);
|
||||
#endif
|
||||
default:
|
||||
ERREXIT(cinfo, JERR_UNKNOWN_FORMAT);
|
||||
break;
|
||||
}
|
||||
|
||||
return NULL; /* suppress compiler warnings */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Argument-parsing code.
|
||||
* The switch parser is designed to be useful with DOS-style command line
|
||||
* syntax, ie, intermixed switches and file names, where only the switches
|
||||
* to the left of a given file name affect processing of that file.
|
||||
* The main program in this file doesn't actually use this capability...
|
||||
*/
|
||||
|
||||
|
||||
static const char * progname; /* program name for error messages */
|
||||
static char * outfilename; /* for -outfile switch */
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
usage (void)
|
||||
/* complain about bad command line */
|
||||
{
|
||||
fprintf(stderr, "usage: %s [switches] ", progname);
|
||||
#ifdef TWO_FILE_COMMANDLINE
|
||||
fprintf(stderr, "inputfile outputfile\n");
|
||||
#else
|
||||
fprintf(stderr, "[inputfile]\n");
|
||||
#endif
|
||||
|
||||
fprintf(stderr, "Switches (names may be abbreviated):\n");
|
||||
fprintf(stderr, " -quality N[,...] Compression quality (0..100; 5-95 is useful range)\n");
|
||||
fprintf(stderr, " -grayscale Create monochrome JPEG file\n");
|
||||
fprintf(stderr, " -rgb Create RGB JPEG file\n");
|
||||
#ifdef ENTROPY_OPT_SUPPORTED
|
||||
fprintf(stderr, " -optimize Optimize Huffman table (smaller file, but slow compression)\n");
|
||||
#endif
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
fprintf(stderr, " -progressive Create progressive JPEG file\n");
|
||||
#endif
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
fprintf(stderr, " -scale M/N Scale image by fraction M/N, eg, 1/2\n");
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
fprintf(stderr, " -targa Input file is Targa format (usually not needed)\n");
|
||||
#endif
|
||||
fprintf(stderr, "Switches for advanced users:\n");
|
||||
#ifdef C_ARITH_CODING_SUPPORTED
|
||||
fprintf(stderr, " -arithmetic Use arithmetic coding\n");
|
||||
#endif
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
fprintf(stderr, " -block N DCT block size (1..16; default is 8)\n");
|
||||
#endif
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9
|
||||
fprintf(stderr, " -rgb1 Create RGB JPEG file with reversible color transform\n");
|
||||
fprintf(stderr, " -bgycc Create big gamut YCC JPEG file\n");
|
||||
#endif
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
fprintf(stderr, " -dct int Use integer DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_ISLOW ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_IFAST_SUPPORTED
|
||||
fprintf(stderr, " -dct fast Use fast integer DCT (less accurate)%s\n",
|
||||
(JDCT_DEFAULT == JDCT_IFAST ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_FLOAT_SUPPORTED
|
||||
fprintf(stderr, " -dct float Use floating-point DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_FLOAT ? " (default)" : ""));
|
||||
#endif
|
||||
fprintf(stderr, " -nosmooth Don't use high-quality downsampling\n");
|
||||
fprintf(stderr, " -restart N Set restart interval in rows, or in blocks with B\n");
|
||||
#ifdef INPUT_SMOOTHING_SUPPORTED
|
||||
fprintf(stderr, " -smooth N Smooth dithered input (N=1..100 is strength)\n");
|
||||
#endif
|
||||
fprintf(stderr, " -maxmemory N Maximum memory to use (in kbytes)\n");
|
||||
fprintf(stderr, " -outfile name Specify name for output file\n");
|
||||
fprintf(stderr, " -verbose or -debug Emit debug output\n");
|
||||
fprintf(stderr, "Switches for wizards:\n");
|
||||
fprintf(stderr, " -baseline Force baseline quantization tables\n");
|
||||
fprintf(stderr, " -qtables file Use quantization tables given in file\n");
|
||||
fprintf(stderr, " -qslots N[,...] Set component quantization tables\n");
|
||||
fprintf(stderr, " -sample HxV[,...] Set component sampling factors\n");
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
fprintf(stderr, " -scans file Create multi-scan JPEG per script file\n");
|
||||
#endif
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
||||
LOCAL(int)
|
||||
parse_switches (j_compress_ptr cinfo, int argc, char **argv,
|
||||
int last_file_arg_seen, boolean for_real)
|
||||
/* Parse optional switches.
|
||||
* Returns argv[] index of first file-name argument (== argc if none).
|
||||
* Any file names with indexes <= last_file_arg_seen are ignored;
|
||||
* they have presumably been processed in a previous iteration.
|
||||
* (Pass 0 for last_file_arg_seen on the first or only iteration.)
|
||||
* for_real is FALSE on the first (dummy) pass; we may skip any expensive
|
||||
* processing.
|
||||
*/
|
||||
{
|
||||
int argn;
|
||||
char * arg;
|
||||
boolean force_baseline;
|
||||
boolean simple_progressive;
|
||||
char * qualityarg = NULL; /* saves -quality parm if any */
|
||||
char * qtablefile = NULL; /* saves -qtables filename if any */
|
||||
char * qslotsarg = NULL; /* saves -qslots parm if any */
|
||||
char * samplearg = NULL; /* saves -sample parm if any */
|
||||
char * scansarg = NULL; /* saves -scans parm if any */
|
||||
|
||||
/* Set up default JPEG parameters. */
|
||||
|
||||
force_baseline = FALSE; /* by default, allow 16-bit quantizers */
|
||||
simple_progressive = FALSE;
|
||||
is_targa = FALSE;
|
||||
outfilename = NULL;
|
||||
cinfo->err->trace_level = 0;
|
||||
|
||||
/* Scan command line options, adjust parameters */
|
||||
|
||||
for (argn = 1; argn < argc; argn++) {
|
||||
arg = argv[argn];
|
||||
if (*arg != '-') {
|
||||
/* Not a switch, must be a file name argument */
|
||||
if (argn <= last_file_arg_seen) {
|
||||
outfilename = NULL; /* -outfile applies to just one input file */
|
||||
continue; /* ignore this name if previously processed */
|
||||
}
|
||||
break; /* else done parsing switches */
|
||||
}
|
||||
arg++; /* advance past switch marker character */
|
||||
|
||||
if (keymatch(arg, "arithmetic", 1)) {
|
||||
/* Use arithmetic coding. */
|
||||
#ifdef C_ARITH_CODING_SUPPORTED
|
||||
cinfo->arith_code = TRUE;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, arithmetic coding not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "baseline", 2)) {
|
||||
/* Force baseline-compatible output (8-bit quantizer values). */
|
||||
force_baseline = TRUE;
|
||||
|
||||
} else if (keymatch(arg, "block", 2)) {
|
||||
/* Set DCT block size. */
|
||||
#if defined DCT_SCALING_SUPPORTED && JPEG_LIB_VERSION_MAJOR >= 8 && \
|
||||
(JPEG_LIB_VERSION_MAJOR > 8 || JPEG_LIB_VERSION_MINOR >= 3)
|
||||
int val;
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d", &val) != 1)
|
||||
usage();
|
||||
if (val < 1 || val > 16)
|
||||
usage();
|
||||
cinfo->block_size = val;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, block size setting not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "dct", 2)) {
|
||||
/* Select DCT algorithm. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (keymatch(argv[argn], "int", 1)) {
|
||||
cinfo->dct_method = JDCT_ISLOW;
|
||||
} else if (keymatch(argv[argn], "fast", 2)) {
|
||||
cinfo->dct_method = JDCT_IFAST;
|
||||
} else if (keymatch(argv[argn], "float", 2)) {
|
||||
cinfo->dct_method = JDCT_FLOAT;
|
||||
} else
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
|
||||
/* Enable debug printouts. */
|
||||
/* On first -d, print version identification */
|
||||
static boolean printed_version = FALSE;
|
||||
|
||||
if (! printed_version) {
|
||||
fprintf(stderr, "Independent JPEG Group's CJPEG, version %s\n%s\n",
|
||||
JVERSION, JCOPYRIGHT);
|
||||
printed_version = TRUE;
|
||||
}
|
||||
cinfo->err->trace_level++;
|
||||
|
||||
} else if (keymatch(arg, "grayscale", 2) || keymatch(arg, "greyscale",2)) {
|
||||
/* Force a monochrome JPEG file to be generated. */
|
||||
jpeg_set_colorspace(cinfo, JCS_GRAYSCALE);
|
||||
|
||||
} else if (keymatch(arg, "rgb", 3) || keymatch(arg, "rgb1", 4)) {
|
||||
/* Force an RGB JPEG file to be generated. */
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9
|
||||
/* Note: Entropy table assignment in jpeg_set_colorspace depends
|
||||
* on color_transform.
|
||||
*/
|
||||
cinfo->color_transform = arg[3] ? JCT_SUBTRACT_GREEN : JCT_NONE;
|
||||
#endif
|
||||
jpeg_set_colorspace(cinfo, JCS_RGB);
|
||||
|
||||
} else if (keymatch(arg, "bgycc", 5)) {
|
||||
/* Force a big gamut YCC JPEG file to be generated. */
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9 && \
|
||||
(JPEG_LIB_VERSION_MAJOR > 9 || JPEG_LIB_VERSION_MINOR >= 1)
|
||||
jpeg_set_colorspace(cinfo, JCS_BG_YCC);
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, BG_YCC colorspace not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "maxmemory", 3)) {
|
||||
/* Maximum memory in Kb (or Mb with 'm'). */
|
||||
long lval;
|
||||
char ch = 'x';
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
|
||||
usage();
|
||||
if (ch == 'm' || ch == 'M')
|
||||
lval *= 1000L;
|
||||
cinfo->mem->max_memory_to_use = lval * 1000L;
|
||||
|
||||
} else if (keymatch(arg, "nosmooth", 3)) {
|
||||
/* Suppress fancy downsampling. */
|
||||
cinfo->do_fancy_downsampling = FALSE;
|
||||
|
||||
} else if (keymatch(arg, "optimize", 1) || keymatch(arg, "optimise", 1)) {
|
||||
/* Enable entropy parm optimization. */
|
||||
#ifdef ENTROPY_OPT_SUPPORTED
|
||||
cinfo->optimize_coding = TRUE;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, entropy optimization was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "outfile", 4)) {
|
||||
/* Set output file name. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
outfilename = argv[argn]; /* save it away for later use */
|
||||
|
||||
} else if (keymatch(arg, "progressive", 1)) {
|
||||
/* Select simple progressive mode. */
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
simple_progressive = TRUE;
|
||||
/* We must postpone execution until num_components is known. */
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, progressive output was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "quality", 1)) {
|
||||
/* Quality ratings (quantization table scaling factors). */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qualityarg = argv[argn];
|
||||
|
||||
} else if (keymatch(arg, "qslots", 2)) {
|
||||
/* Quantization table slot numbers. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qslotsarg = argv[argn];
|
||||
/* Must delay setting qslots until after we have processed any
|
||||
* colorspace-determining switches, since jpeg_set_colorspace sets
|
||||
* default quant table numbers.
|
||||
*/
|
||||
|
||||
} else if (keymatch(arg, "qtables", 2)) {
|
||||
/* Quantization tables fetched from file. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qtablefile = argv[argn];
|
||||
/* We postpone actually reading the file in case -quality comes later. */
|
||||
|
||||
} else if (keymatch(arg, "restart", 1)) {
|
||||
/* Restart interval in MCU rows (or in MCUs with 'b'). */
|
||||
long lval;
|
||||
char ch = 'x';
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
|
||||
usage();
|
||||
if (lval < 0 || lval > 65535L)
|
||||
usage();
|
||||
if (ch == 'b' || ch == 'B') {
|
||||
cinfo->restart_interval = (unsigned int) lval;
|
||||
cinfo->restart_in_rows = 0; /* else prior '-restart n' overrides me */
|
||||
} else {
|
||||
cinfo->restart_in_rows = (int) lval;
|
||||
/* restart_interval will be computed during startup */
|
||||
}
|
||||
|
||||
} else if (keymatch(arg, "sample", 2)) {
|
||||
/* Set sampling factors. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
samplearg = argv[argn];
|
||||
/* Must delay setting sample factors until after we have processed any
|
||||
* colorspace-determining switches, since jpeg_set_colorspace sets
|
||||
* default sampling factors.
|
||||
*/
|
||||
|
||||
} else if (keymatch(arg, "scale", 4)) {
|
||||
/* Scale the image by a fraction M/N. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%u/%u",
|
||||
&cinfo->scale_num, &cinfo->scale_denom) != 2)
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "scans", 4)) {
|
||||
/* Set scan script. */
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
scansarg = argv[argn];
|
||||
/* We must postpone reading the file in case -progressive appears. */
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, multi-scan output was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "smooth", 2)) {
|
||||
/* Set input smoothing factor. */
|
||||
int val;
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d", &val) != 1)
|
||||
usage();
|
||||
if (val < 0 || val > 100)
|
||||
usage();
|
||||
cinfo->smoothing_factor = val;
|
||||
|
||||
} else if (keymatch(arg, "targa", 1)) {
|
||||
/* Input file is Targa format. */
|
||||
is_targa = TRUE;
|
||||
|
||||
} else {
|
||||
usage(); /* bogus switch */
|
||||
}
|
||||
}
|
||||
|
||||
/* Post-switch-scanning cleanup */
|
||||
|
||||
if (for_real) {
|
||||
|
||||
/* Set quantization tables for selected quality. */
|
||||
/* Some or all may be overridden if -qtables is present. */
|
||||
if (qualityarg != NULL) /* process -quality if it was present */
|
||||
if (! set_quality_ratings(cinfo, qualityarg, force_baseline))
|
||||
usage();
|
||||
|
||||
if (qtablefile != NULL) /* process -qtables if it was present */
|
||||
if (! read_quant_tables(cinfo, qtablefile, force_baseline))
|
||||
usage();
|
||||
|
||||
if (qslotsarg != NULL) /* process -qslots if it was present */
|
||||
if (! set_quant_slots(cinfo, qslotsarg))
|
||||
usage();
|
||||
|
||||
if (samplearg != NULL) /* process -sample if it was present */
|
||||
if (! set_sample_factors(cinfo, samplearg))
|
||||
usage();
|
||||
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
if (simple_progressive) /* process -progressive; -scans can override */
|
||||
jpeg_simple_progression(cinfo);
|
||||
#endif
|
||||
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
if (scansarg != NULL) /* process -scans if it was present */
|
||||
if (! read_scan_script(cinfo, scansarg))
|
||||
usage();
|
||||
#endif
|
||||
}
|
||||
|
||||
return argn; /* return index of next arg (file name) */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* The main program.
|
||||
*/
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
struct jpeg_compress_struct cinfo;
|
||||
struct jpeg_error_mgr jerr;
|
||||
#ifdef PROGRESS_REPORT
|
||||
struct cdjpeg_progress_mgr progress;
|
||||
#endif
|
||||
int file_index;
|
||||
cjpeg_source_ptr src_mgr;
|
||||
FILE * input_file;
|
||||
FILE * output_file;
|
||||
JDIMENSION num_scanlines;
|
||||
|
||||
/* On Mac, fetch a command line. */
|
||||
#ifdef USE_CCOMMAND
|
||||
argc = ccommand(&argv);
|
||||
#endif
|
||||
|
||||
progname = argv[0];
|
||||
if (progname == NULL || progname[0] == 0)
|
||||
progname = "cjpeg"; /* in case C library doesn't provide it */
|
||||
|
||||
/* Initialize the JPEG compression object with default error handling. */
|
||||
cinfo.err = jpeg_std_error(&jerr);
|
||||
jpeg_create_compress(&cinfo);
|
||||
/* Add some application-specific error messages (from cderror.h) */
|
||||
jerr.addon_message_table = cdjpeg_message_table;
|
||||
jerr.first_addon_message = JMSG_FIRSTADDONCODE;
|
||||
jerr.last_addon_message = JMSG_LASTADDONCODE;
|
||||
|
||||
/* Now safe to enable signal catcher. */
|
||||
#ifdef NEED_SIGNAL_CATCHER
|
||||
enable_signal_catcher((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* Initialize JPEG parameters.
|
||||
* Much of this may be overridden later.
|
||||
* In particular, we don't yet know the input file's color space,
|
||||
* but we need to provide some value for jpeg_set_defaults() to work.
|
||||
*/
|
||||
|
||||
cinfo.in_color_space = JCS_RGB; /* arbitrary guess */
|
||||
jpeg_set_defaults(&cinfo);
|
||||
|
||||
/* Scan command line to find file names.
|
||||
* It is convenient to use just one switch-parsing routine, but the switch
|
||||
* values read here are ignored; we will rescan the switches after opening
|
||||
* the input file.
|
||||
*/
|
||||
|
||||
file_index = parse_switches(&cinfo, argc, argv, 0, FALSE);
|
||||
|
||||
#ifdef TWO_FILE_COMMANDLINE
|
||||
/* Must have either -outfile switch or explicit output file name */
|
||||
if (outfilename == NULL) {
|
||||
if (file_index != argc-2) {
|
||||
fprintf(stderr, "%s: must name one input and one output file\n",
|
||||
progname);
|
||||
usage();
|
||||
}
|
||||
outfilename = argv[file_index+1];
|
||||
} else {
|
||||
if (file_index != argc-1) {
|
||||
fprintf(stderr, "%s: must name one input and one output file\n",
|
||||
progname);
|
||||
usage();
|
||||
}
|
||||
}
|
||||
#else
|
||||
/* Unix style: expect zero or one file name */
|
||||
if (file_index < argc-1) {
|
||||
fprintf(stderr, "%s: only one input file\n", progname);
|
||||
usage();
|
||||
}
|
||||
#endif /* TWO_FILE_COMMANDLINE */
|
||||
|
||||
/* Open the input file. */
|
||||
if (file_index < argc) {
|
||||
if ((input_file = fopen(argv[file_index], READ_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't open %s\n", progname, argv[file_index]);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
} else {
|
||||
/* default input file is stdin */
|
||||
input_file = read_stdin();
|
||||
}
|
||||
|
||||
/* Open the output file. */
|
||||
if (outfilename != NULL) {
|
||||
if ((output_file = fopen(outfilename, WRITE_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't open %s\n", progname, outfilename);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
} else {
|
||||
/* default output file is stdout */
|
||||
output_file = write_stdout();
|
||||
}
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
start_progress_monitor((j_common_ptr) &cinfo, &progress);
|
||||
#endif
|
||||
|
||||
/* Figure out the input file format, and set up to read it. */
|
||||
src_mgr = select_file_type(&cinfo, input_file);
|
||||
src_mgr->input_file = input_file;
|
||||
|
||||
/* Read the input file header to obtain file size & colorspace. */
|
||||
(*src_mgr->start_input) (&cinfo, src_mgr);
|
||||
|
||||
/* Now that we know input colorspace, fix colorspace-dependent defaults */
|
||||
jpeg_default_colorspace(&cinfo);
|
||||
|
||||
/* Adjust default compression parameters by re-parsing the options */
|
||||
file_index = parse_switches(&cinfo, argc, argv, 0, TRUE);
|
||||
|
||||
/* Specify data destination for compression */
|
||||
jpeg_stdio_dest(&cinfo, output_file);
|
||||
|
||||
/* Start compressor */
|
||||
jpeg_start_compress(&cinfo, TRUE);
|
||||
|
||||
/* Process data */
|
||||
while (cinfo.next_scanline < cinfo.image_height) {
|
||||
num_scanlines = (*src_mgr->get_pixel_rows) (&cinfo, src_mgr);
|
||||
(void) jpeg_write_scanlines(&cinfo, src_mgr->buffer, num_scanlines);
|
||||
}
|
||||
|
||||
/* Finish compression and release memory */
|
||||
(*src_mgr->finish_input) (&cinfo, src_mgr);
|
||||
jpeg_finish_compress(&cinfo);
|
||||
jpeg_destroy_compress(&cinfo);
|
||||
|
||||
/* Close files, if we opened them */
|
||||
if (input_file != stdin)
|
||||
fclose(input_file);
|
||||
if (output_file != stdout)
|
||||
fclose(output_file);
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
end_progress_monitor((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* All done. */
|
||||
exit(jerr.num_warnings ? EXIT_WARNING : EXIT_SUCCESS);
|
||||
return 0; /* suppress no-return-value warnings */
|
||||
}
|
||||
|
|
@ -1,791 +0,0 @@
|
|||
/*
|
||||
* alternate cjpeg.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2009-2023 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
* This file contains an alternate user interface for the JPEG compressor.
|
||||
* One or more input files are named on the command line, and output file
|
||||
* names are created by substituting ".jpg" for the input file's extension.
|
||||
*/
|
||||
|
||||
#include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */
|
||||
#include "jversion.h" /* for version message */
|
||||
|
||||
#ifdef USE_CCOMMAND /* command-line reader for Macintosh */
|
||||
#ifdef __MWERKS__
|
||||
#include <SIOUX.h> /* Metrowerks needs this */
|
||||
#include <console.h> /* ... and this */
|
||||
#endif
|
||||
#ifdef THINK_C
|
||||
#include <console.h> /* Think declares it here */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef PATH_MAX /* ANSI maximum-pathname-length constant */
|
||||
#define PATH_MAX 256
|
||||
#endif
|
||||
|
||||
|
||||
/* Create the add-on message string table. */
|
||||
|
||||
#define JMESSAGE(code,string) string ,
|
||||
|
||||
static const char * const cdjpeg_message_table[] = {
|
||||
#include "cderror.h"
|
||||
NULL
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Automatic determination of available memory.
|
||||
*/
|
||||
|
||||
static long default_maxmem; /* saves value determined at startup, or 0 */
|
||||
|
||||
#ifndef FREE_MEM_ESTIMATE /* may be defined from command line */
|
||||
|
||||
#ifdef MSDOS /* For MS-DOS (unless flat-memory model) */
|
||||
|
||||
#include <dos.h> /* for access to intdos() call */
|
||||
|
||||
LOCAL(long)
|
||||
unused_dos_memory (void)
|
||||
/* Obtain total amount of unallocated DOS memory */
|
||||
{
|
||||
union REGS regs;
|
||||
long nparas;
|
||||
|
||||
regs.h.ah = 0x48; /* DOS function Allocate Memory Block */
|
||||
regs.x.bx = 0xFFFF; /* Ask for more memory than DOS can have */
|
||||
(void) intdos(®s, ®s);
|
||||
/* DOS will fail and return # of paragraphs actually available in BX. */
|
||||
nparas = (unsigned int) regs.x.bx;
|
||||
/* Times 16 to convert to bytes. */
|
||||
return nparas << 4;
|
||||
}
|
||||
|
||||
/* The default memory setting is 95% of the available space. */
|
||||
#define FREE_MEM_ESTIMATE ((unused_dos_memory() * 95L) / 100L)
|
||||
|
||||
#endif /* MSDOS */
|
||||
|
||||
#ifdef ATARI /* For Atari ST/Mega/STE/TT/Falcon, Pure C or Turbo C */
|
||||
|
||||
#include <ext.h>
|
||||
|
||||
/* The default memory setting is 90% of the available space. */
|
||||
#define FREE_MEM_ESTIMATE (((long) coreleft() * 90L) / 100L)
|
||||
|
||||
#endif /* ATARI */
|
||||
|
||||
/* Add memory-estimation procedures for other operating systems here,
|
||||
* with appropriate #ifdef's around them.
|
||||
*/
|
||||
|
||||
#endif /* !FREE_MEM_ESTIMATE */
|
||||
|
||||
|
||||
/*
|
||||
* This routine determines what format the input file is,
|
||||
* and selects the appropriate input-reading module.
|
||||
*
|
||||
* To determine which family of input formats the file belongs to,
|
||||
* we may look only at the first byte of the file, since C does not
|
||||
* guarantee that more than one character can be pushed back with ungetc.
|
||||
* Looking at additional bytes would require one of these approaches:
|
||||
* 1) assume we can fseek() the input file (fails for piped input);
|
||||
* 2) assume we can push back more than one character (works in
|
||||
* some C implementations, but unportable);
|
||||
* 3) provide our own buffering (breaks input readers that want to use
|
||||
* stdio directly, such as the RLE library);
|
||||
* or 4) don't put back the data, and modify the input_init methods to assume
|
||||
* they start reading after the start of file (also breaks RLE library).
|
||||
* #1 is attractive for MS-DOS but is untenable on Unix.
|
||||
*
|
||||
* The most portable solution for file types that can't be identified by their
|
||||
* first byte is to make the user tell us what they are. This is also the
|
||||
* only approach for "raw" file types that contain only arbitrary values.
|
||||
* We presently apply this method for Targa files. Most of the time Targa
|
||||
* files start with 0x00, so we recognize that case. Potentially, however,
|
||||
* a Targa file could start with any byte value (byte 0 is the length of the
|
||||
* seldom-used ID field), so we provide a switch to force Targa input mode.
|
||||
*/
|
||||
|
||||
static boolean is_targa; /* records user -targa switch */
|
||||
|
||||
|
||||
LOCAL(cjpeg_source_ptr)
|
||||
select_file_type (j_compress_ptr cinfo, FILE * infile)
|
||||
{
|
||||
int c;
|
||||
|
||||
if (is_targa) {
|
||||
#ifdef TARGA_SUPPORTED
|
||||
return jinit_read_targa(cinfo);
|
||||
#else
|
||||
ERREXIT(cinfo, JERR_TGA_NOTCOMP);
|
||||
#endif
|
||||
}
|
||||
|
||||
if ((c = getc(infile)) == EOF)
|
||||
ERREXIT(cinfo, JERR_INPUT_EMPTY);
|
||||
if (ungetc(c, infile) == EOF)
|
||||
ERREXIT(cinfo, JERR_UNGETC_FAILED);
|
||||
|
||||
switch (c) {
|
||||
#ifdef BMP_SUPPORTED
|
||||
case 'B':
|
||||
return jinit_read_bmp(cinfo);
|
||||
#endif
|
||||
#ifdef GIF_SUPPORTED
|
||||
case 'G':
|
||||
return jinit_read_gif(cinfo);
|
||||
#endif
|
||||
#ifdef PPM_SUPPORTED
|
||||
case 'P':
|
||||
return jinit_read_ppm(cinfo);
|
||||
#endif
|
||||
#ifdef RLE_SUPPORTED
|
||||
case 'R':
|
||||
return jinit_read_rle(cinfo);
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
case 0x00:
|
||||
return jinit_read_targa(cinfo);
|
||||
#endif
|
||||
default:
|
||||
ERREXIT(cinfo, JERR_UNKNOWN_FORMAT);
|
||||
break;
|
||||
}
|
||||
|
||||
return NULL; /* suppress compiler warnings */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Argument-parsing code.
|
||||
* The switch parser is designed to be useful with DOS-style command line
|
||||
* syntax, ie, intermixed switches and file names, where only the switches
|
||||
* to the left of a given file name affect processing of that file.
|
||||
*/
|
||||
|
||||
|
||||
static const char * progname; /* program name for error messages */
|
||||
static char * outfilename; /* for -outfile switch */
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
usage (void)
|
||||
/* complain about bad command line */
|
||||
{
|
||||
fprintf(stderr, "usage: %s [switches] inputfile(s)\n", progname);
|
||||
fprintf(stderr, "List of input files may use wildcards (* and ?)\n");
|
||||
fprintf(stderr, "Output filename is same as input filename, but extension .jpg\n");
|
||||
|
||||
fprintf(stderr, "Switches (names may be abbreviated):\n");
|
||||
fprintf(stderr, " -quality N[,...] Compression quality (0..100; 5-95 is useful range)\n");
|
||||
fprintf(stderr, " -grayscale Create monochrome JPEG file\n");
|
||||
fprintf(stderr, " -rgb Create RGB JPEG file\n");
|
||||
#ifdef ENTROPY_OPT_SUPPORTED
|
||||
fprintf(stderr, " -optimize Optimize Huffman table (smaller file, but slow compression)\n");
|
||||
#endif
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
fprintf(stderr, " -progressive Create progressive JPEG file\n");
|
||||
#endif
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
fprintf(stderr, " -scale M/N Scale image by fraction M/N, eg, 1/2\n");
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
fprintf(stderr, " -targa Input file is Targa format (usually not needed)\n");
|
||||
#endif
|
||||
fprintf(stderr, "Switches for advanced users:\n");
|
||||
#ifdef C_ARITH_CODING_SUPPORTED
|
||||
fprintf(stderr, " -arithmetic Use arithmetic coding\n");
|
||||
#endif
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
fprintf(stderr, " -block N DCT block size (1..16; default is 8)\n");
|
||||
#endif
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9
|
||||
fprintf(stderr, " -rgb1 Create RGB JPEG file with reversible color transform\n");
|
||||
fprintf(stderr, " -bgycc Create big gamut YCC JPEG file\n");
|
||||
#endif
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
fprintf(stderr, " -dct int Use integer DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_ISLOW ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_IFAST_SUPPORTED
|
||||
fprintf(stderr, " -dct fast Use fast integer DCT (less accurate)%s\n",
|
||||
(JDCT_DEFAULT == JDCT_IFAST ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_FLOAT_SUPPORTED
|
||||
fprintf(stderr, " -dct float Use floating-point DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_FLOAT ? " (default)" : ""));
|
||||
#endif
|
||||
fprintf(stderr, " -nosmooth Don't use high-quality downsampling\n");
|
||||
fprintf(stderr, " -restart N Set restart interval in rows, or in blocks with B\n");
|
||||
#ifdef INPUT_SMOOTHING_SUPPORTED
|
||||
fprintf(stderr, " -smooth N Smooth dithered input (N=1..100 is strength)\n");
|
||||
#endif
|
||||
#ifndef FREE_MEM_ESTIMATE
|
||||
fprintf(stderr, " -maxmemory N Maximum memory to use (in kbytes)\n");
|
||||
#endif
|
||||
fprintf(stderr, " -outfile name Specify name for output file\n");
|
||||
fprintf(stderr, " -verbose or -debug Emit debug output\n");
|
||||
fprintf(stderr, "Switches for wizards:\n");
|
||||
fprintf(stderr, " -baseline Force baseline quantization tables\n");
|
||||
fprintf(stderr, " -qtables file Use quantization tables given in file\n");
|
||||
fprintf(stderr, " -qslots N[,...] Set component quantization tables\n");
|
||||
fprintf(stderr, " -sample HxV[,...] Set component sampling factors\n");
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
fprintf(stderr, " -scans file Create multi-scan JPEG per script file\n");
|
||||
#endif
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
||||
LOCAL(int)
|
||||
parse_switches (j_compress_ptr cinfo, int argc, char **argv,
|
||||
int last_file_arg_seen, boolean for_real)
|
||||
/* Parse optional switches.
|
||||
* Returns argv[] index of first file-name argument (== argc if none).
|
||||
* Any file names with indexes <= last_file_arg_seen are ignored;
|
||||
* they have presumably been processed in a previous iteration.
|
||||
* (Pass 0 for last_file_arg_seen on the first or only iteration.)
|
||||
* for_real is FALSE on the first (dummy) pass; we may skip any expensive
|
||||
* processing.
|
||||
*/
|
||||
{
|
||||
int argn;
|
||||
char * arg;
|
||||
boolean force_baseline;
|
||||
boolean simple_progressive;
|
||||
char * qualityarg = NULL; /* saves -quality parm if any */
|
||||
char * qtablefile = NULL; /* saves -qtables filename if any */
|
||||
char * qslotsarg = NULL; /* saves -qslots parm if any */
|
||||
char * samplearg = NULL; /* saves -sample parm if any */
|
||||
char * scansarg = NULL; /* saves -scans parm if any */
|
||||
|
||||
/* Set up default JPEG parameters. */
|
||||
|
||||
force_baseline = FALSE; /* by default, allow 16-bit quantizers */
|
||||
simple_progressive = FALSE;
|
||||
is_targa = FALSE;
|
||||
outfilename = NULL;
|
||||
cinfo->err->trace_level = 0;
|
||||
if (default_maxmem > 0) /* override library's default value */
|
||||
cinfo->mem->max_memory_to_use = default_maxmem;
|
||||
|
||||
/* Scan command line options, adjust parameters */
|
||||
|
||||
for (argn = 1; argn < argc; argn++) {
|
||||
arg = argv[argn];
|
||||
if (*arg != '-') {
|
||||
/* Not a switch, must be a file name argument */
|
||||
if (argn <= last_file_arg_seen) {
|
||||
outfilename = NULL; /* -outfile applies to just one input file */
|
||||
continue; /* ignore this name if previously processed */
|
||||
}
|
||||
break; /* else done parsing switches */
|
||||
}
|
||||
arg++; /* advance past switch marker character */
|
||||
|
||||
if (keymatch(arg, "arithmetic", 1)) {
|
||||
/* Use arithmetic coding. */
|
||||
#ifdef C_ARITH_CODING_SUPPORTED
|
||||
cinfo->arith_code = TRUE;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, arithmetic coding not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "baseline", 2)) {
|
||||
/* Force baseline-compatible output (8-bit quantizer values). */
|
||||
force_baseline = TRUE;
|
||||
|
||||
} else if (keymatch(arg, "block", 2)) {
|
||||
/* Set DCT block size. */
|
||||
#if defined DCT_SCALING_SUPPORTED && JPEG_LIB_VERSION_MAJOR >= 8 && \
|
||||
(JPEG_LIB_VERSION_MAJOR > 8 || JPEG_LIB_VERSION_MINOR >= 3)
|
||||
int val;
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d", &val) != 1)
|
||||
usage();
|
||||
if (val < 1 || val > 16)
|
||||
usage();
|
||||
cinfo->block_size = val;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, block size setting not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "dct", 2)) {
|
||||
/* Select DCT algorithm. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (keymatch(argv[argn], "int", 1)) {
|
||||
cinfo->dct_method = JDCT_ISLOW;
|
||||
} else if (keymatch(argv[argn], "fast", 2)) {
|
||||
cinfo->dct_method = JDCT_IFAST;
|
||||
} else if (keymatch(argv[argn], "float", 2)) {
|
||||
cinfo->dct_method = JDCT_FLOAT;
|
||||
} else
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
|
||||
/* Enable debug printouts. */
|
||||
/* On first -d, print version identification */
|
||||
static boolean printed_version = FALSE;
|
||||
|
||||
if (! printed_version) {
|
||||
fprintf(stderr, "Independent JPEG Group's CJPEG, version %s\n%s\n",
|
||||
JVERSION, JCOPYRIGHT);
|
||||
printed_version = TRUE;
|
||||
}
|
||||
cinfo->err->trace_level++;
|
||||
|
||||
} else if (keymatch(arg, "grayscale", 2) || keymatch(arg, "greyscale",2)) {
|
||||
/* Force a monochrome JPEG file to be generated. */
|
||||
jpeg_set_colorspace(cinfo, JCS_GRAYSCALE);
|
||||
|
||||
} else if (keymatch(arg, "rgb", 3) || keymatch(arg, "rgb1", 4)) {
|
||||
/* Force an RGB JPEG file to be generated. */
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9
|
||||
/* Note: Entropy table assignment in jpeg_set_colorspace depends
|
||||
* on color_transform.
|
||||
*/
|
||||
cinfo->color_transform = arg[3] ? JCT_SUBTRACT_GREEN : JCT_NONE;
|
||||
#endif
|
||||
jpeg_set_colorspace(cinfo, JCS_RGB);
|
||||
|
||||
} else if (keymatch(arg, "bgycc", 5)) {
|
||||
/* Force a big gamut YCC JPEG file to be generated. */
|
||||
#if JPEG_LIB_VERSION_MAJOR >= 9 && \
|
||||
(JPEG_LIB_VERSION_MAJOR > 9 || JPEG_LIB_VERSION_MINOR >= 1)
|
||||
jpeg_set_colorspace(cinfo, JCS_BG_YCC);
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, BG_YCC colorspace not supported\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "maxmemory", 3)) {
|
||||
/* Maximum memory in Kb (or Mb with 'm'). */
|
||||
long lval;
|
||||
char ch = 'x';
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
|
||||
usage();
|
||||
if (ch == 'm' || ch == 'M')
|
||||
lval *= 1000L;
|
||||
cinfo->mem->max_memory_to_use = lval * 1000L;
|
||||
|
||||
} else if (keymatch(arg, "nosmooth", 3)) {
|
||||
/* Suppress fancy downsampling. */
|
||||
cinfo->do_fancy_downsampling = FALSE;
|
||||
|
||||
} else if (keymatch(arg, "optimize", 1) || keymatch(arg, "optimise", 1)) {
|
||||
/* Enable entropy parm optimization. */
|
||||
#ifdef ENTROPY_OPT_SUPPORTED
|
||||
cinfo->optimize_coding = TRUE;
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, entropy optimization was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "outfile", 4)) {
|
||||
/* Set output file name. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
outfilename = argv[argn]; /* save it away for later use */
|
||||
|
||||
} else if (keymatch(arg, "progressive", 1)) {
|
||||
/* Select simple progressive mode. */
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
simple_progressive = TRUE;
|
||||
/* We must postpone execution until num_components is known. */
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, progressive output was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "quality", 1)) {
|
||||
/* Quality ratings (quantization table scaling factors). */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qualityarg = argv[argn];
|
||||
|
||||
} else if (keymatch(arg, "qslots", 2)) {
|
||||
/* Quantization table slot numbers. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qslotsarg = argv[argn];
|
||||
/* Must delay setting qslots until after we have processed any
|
||||
* colorspace-determining switches, since jpeg_set_colorspace sets
|
||||
* default quant table numbers.
|
||||
*/
|
||||
|
||||
} else if (keymatch(arg, "qtables", 2)) {
|
||||
/* Quantization tables fetched from file. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
qtablefile = argv[argn];
|
||||
/* We postpone actually reading the file in case -quality comes later. */
|
||||
|
||||
} else if (keymatch(arg, "restart", 1)) {
|
||||
/* Restart interval in MCU rows (or in MCUs with 'b'). */
|
||||
long lval;
|
||||
char ch = 'x';
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
|
||||
usage();
|
||||
if (lval < 0 || lval > 65535L)
|
||||
usage();
|
||||
if (ch == 'b' || ch == 'B') {
|
||||
cinfo->restart_interval = (unsigned int) lval;
|
||||
cinfo->restart_in_rows = 0; /* else prior '-restart n' overrides me */
|
||||
} else {
|
||||
cinfo->restart_in_rows = (int) lval;
|
||||
/* restart_interval will be computed during startup */
|
||||
}
|
||||
|
||||
} else if (keymatch(arg, "sample", 2)) {
|
||||
/* Set sampling factors. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
samplearg = argv[argn];
|
||||
/* Must delay setting sample factors until after we have processed any
|
||||
* colorspace-determining switches, since jpeg_set_colorspace sets
|
||||
* default sampling factors.
|
||||
*/
|
||||
|
||||
} else if (keymatch(arg, "scale", 4)) {
|
||||
/* Scale the image by a fraction M/N. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d/%d",
|
||||
&cinfo->scale_num, &cinfo->scale_denom) != 2)
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "scans", 4)) {
|
||||
/* Set scan script. */
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
scansarg = argv[argn];
|
||||
/* We must postpone reading the file in case -progressive appears. */
|
||||
#else
|
||||
fprintf(stderr, "%s: sorry, multi-scan output was not compiled\n",
|
||||
progname);
|
||||
exit(EXIT_FAILURE);
|
||||
#endif
|
||||
|
||||
} else if (keymatch(arg, "smooth", 2)) {
|
||||
/* Set input smoothing factor. */
|
||||
int val;
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d", &val) != 1)
|
||||
usage();
|
||||
if (val < 0 || val > 100)
|
||||
usage();
|
||||
cinfo->smoothing_factor = val;
|
||||
|
||||
} else if (keymatch(arg, "targa", 1)) {
|
||||
/* Input file is Targa format. */
|
||||
is_targa = TRUE;
|
||||
|
||||
} else {
|
||||
usage(); /* bogus switch */
|
||||
}
|
||||
}
|
||||
|
||||
/* Post-switch-scanning cleanup */
|
||||
|
||||
if (for_real) {
|
||||
|
||||
/* Set quantization tables for selected quality. */
|
||||
/* Some or all may be overridden if -qtables is present. */
|
||||
if (qualityarg != NULL) /* process -quality if it was present */
|
||||
if (! set_quality_ratings(cinfo, qualityarg, force_baseline))
|
||||
usage();
|
||||
|
||||
if (qtablefile != NULL) /* process -qtables if it was present */
|
||||
if (! read_quant_tables(cinfo, qtablefile, force_baseline))
|
||||
usage();
|
||||
|
||||
if (qslotsarg != NULL) /* process -qslots if it was present */
|
||||
if (! set_quant_slots(cinfo, qslotsarg))
|
||||
usage();
|
||||
|
||||
if (samplearg != NULL) /* process -sample if it was present */
|
||||
if (! set_sample_factors(cinfo, samplearg))
|
||||
usage();
|
||||
|
||||
#ifdef C_PROGRESSIVE_SUPPORTED
|
||||
if (simple_progressive) /* process -progressive; -scans can override */
|
||||
jpeg_simple_progression(cinfo);
|
||||
#endif
|
||||
|
||||
#ifdef C_MULTISCAN_FILES_SUPPORTED
|
||||
if (scansarg != NULL) /* process -scans if it was present */
|
||||
if (! read_scan_script(cinfo, scansarg))
|
||||
usage();
|
||||
#endif
|
||||
}
|
||||
|
||||
return argn; /* return index of next arg (file name) */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Check for overwrite of an existing file; clear it with user
|
||||
*/
|
||||
|
||||
#ifndef NO_OVERWRITE_CHECK
|
||||
|
||||
LOCAL(boolean)
|
||||
is_write_ok (char * outfname)
|
||||
{
|
||||
FILE * ofile;
|
||||
int ch;
|
||||
|
||||
ofile = fopen(outfname, READ_BINARY);
|
||||
if (ofile == NULL)
|
||||
return TRUE; /* not present */
|
||||
fclose(ofile); /* oops, it is present */
|
||||
|
||||
for (;;) {
|
||||
fprintf(stderr, "%s already exists, overwrite it? [y/n] ",
|
||||
outfname);
|
||||
fflush(stderr);
|
||||
ch = getc(stdin);
|
||||
if (ch != '\n') /* flush rest of line */
|
||||
while (getc(stdin) != '\n')
|
||||
/* nothing */;
|
||||
|
||||
switch (ch) {
|
||||
case 'Y':
|
||||
case 'y':
|
||||
return TRUE;
|
||||
case 'N':
|
||||
case 'n':
|
||||
return FALSE;
|
||||
/* otherwise, ask again */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Process a single input file name, and return its index in argv[].
|
||||
* File names at or to left of old_file_index have been processed already.
|
||||
*/
|
||||
|
||||
LOCAL(int)
|
||||
process_one_file (int argc, char **argv, int old_file_index)
|
||||
{
|
||||
struct jpeg_compress_struct cinfo;
|
||||
struct jpeg_error_mgr jerr;
|
||||
char *infilename;
|
||||
char workfilename[PATH_MAX];
|
||||
#ifdef PROGRESS_REPORT
|
||||
struct cdjpeg_progress_mgr progress;
|
||||
#endif
|
||||
int file_index;
|
||||
cjpeg_source_ptr src_mgr;
|
||||
FILE * input_file = NULL;
|
||||
FILE * output_file = NULL;
|
||||
JDIMENSION num_scanlines;
|
||||
|
||||
/* Initialize the JPEG compression object with default error handling. */
|
||||
cinfo.err = jpeg_std_error(&jerr);
|
||||
jpeg_create_compress(&cinfo);
|
||||
/* Add some application-specific error messages (from cderror.h) */
|
||||
jerr.addon_message_table = cdjpeg_message_table;
|
||||
jerr.first_addon_message = JMSG_FIRSTADDONCODE;
|
||||
jerr.last_addon_message = JMSG_LASTADDONCODE;
|
||||
|
||||
/* Now safe to enable signal catcher. */
|
||||
#ifdef NEED_SIGNAL_CATCHER
|
||||
enable_signal_catcher((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* Initialize JPEG parameters.
|
||||
* Much of this may be overridden later.
|
||||
* In particular, we don't yet know the input file's color space,
|
||||
* but we need to provide some value for jpeg_set_defaults() to work.
|
||||
*/
|
||||
|
||||
cinfo.in_color_space = JCS_RGB; /* arbitrary guess */
|
||||
jpeg_set_defaults(&cinfo);
|
||||
|
||||
/* Scan command line to find next file name.
|
||||
* It is convenient to use just one switch-parsing routine, but the switch
|
||||
* values read here are ignored; we will rescan the switches after opening
|
||||
* the input file.
|
||||
*/
|
||||
|
||||
file_index = parse_switches(&cinfo, argc, argv, old_file_index, FALSE);
|
||||
if (file_index >= argc) {
|
||||
fprintf(stderr, "%s: missing input file name\n", progname);
|
||||
usage();
|
||||
}
|
||||
|
||||
/* Open the input file. */
|
||||
infilename = argv[file_index];
|
||||
if ((input_file = fopen(infilename, READ_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't open %s\n", progname, infilename);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
start_progress_monitor((j_common_ptr) &cinfo, &progress);
|
||||
#endif
|
||||
|
||||
/* Figure out the input file format, and set up to read it. */
|
||||
src_mgr = select_file_type(&cinfo, input_file);
|
||||
src_mgr->input_file = input_file;
|
||||
|
||||
/* Read the input file header to obtain file size & colorspace. */
|
||||
(*src_mgr->start_input) (&cinfo, src_mgr);
|
||||
|
||||
/* Now that we know input colorspace, fix colorspace-dependent defaults */
|
||||
jpeg_default_colorspace(&cinfo);
|
||||
|
||||
/* Adjust default compression parameters by re-parsing the options */
|
||||
file_index = parse_switches(&cinfo, argc, argv, old_file_index, TRUE);
|
||||
|
||||
/* If user didn't supply -outfile switch, select output file name. */
|
||||
if (outfilename == NULL) {
|
||||
int i;
|
||||
|
||||
outfilename = workfilename;
|
||||
/* Make outfilename be infilename with .jpg substituted for extension */
|
||||
strcpy(outfilename, infilename);
|
||||
for (i = (int)strlen(outfilename)-1; i >= 0; i--) {
|
||||
switch (outfilename[i]) {
|
||||
case ':':
|
||||
case '/':
|
||||
case '\\':
|
||||
i = 0; /* stop scanning */
|
||||
break;
|
||||
case '.':
|
||||
outfilename[i] = '\0'; /* lop off existing extension */
|
||||
i = 0; /* stop scanning */
|
||||
break;
|
||||
default:
|
||||
break; /* keep scanning */
|
||||
}
|
||||
}
|
||||
strcat(outfilename, ".jpg");
|
||||
}
|
||||
|
||||
fprintf(stderr, "Compressing %s => %s\n", infilename, outfilename);
|
||||
#ifndef NO_OVERWRITE_CHECK
|
||||
if (! is_write_ok(outfilename))
|
||||
goto fail;
|
||||
#endif
|
||||
|
||||
/* Open the output file. */
|
||||
if ((output_file = fopen(outfilename, WRITE_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't create %s\n", progname, outfilename);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/* Specify data destination for compression */
|
||||
jpeg_stdio_dest(&cinfo, output_file);
|
||||
|
||||
/* Start compressor */
|
||||
jpeg_start_compress(&cinfo, TRUE);
|
||||
|
||||
/* Process data */
|
||||
while (cinfo.next_scanline < cinfo.image_height) {
|
||||
num_scanlines = (*src_mgr->get_pixel_rows) (&cinfo, src_mgr);
|
||||
(void) jpeg_write_scanlines(&cinfo, src_mgr->buffer, num_scanlines);
|
||||
}
|
||||
|
||||
/* Finish compression and release memory */
|
||||
(*src_mgr->finish_input) (&cinfo, src_mgr);
|
||||
jpeg_finish_compress(&cinfo);
|
||||
|
||||
/* Clean up and exit */
|
||||
fail:
|
||||
jpeg_destroy_compress(&cinfo);
|
||||
|
||||
if (input_file != NULL) fclose(input_file);
|
||||
if (output_file != NULL) fclose(output_file);
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
end_progress_monitor((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* Disable signal catcher. */
|
||||
#ifdef NEED_SIGNAL_CATCHER
|
||||
enable_signal_catcher((j_common_ptr) NULL);
|
||||
#endif
|
||||
|
||||
return file_index;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* The main program.
|
||||
*/
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
int file_index;
|
||||
|
||||
/* On Mac, fetch a command line. */
|
||||
#ifdef USE_CCOMMAND
|
||||
argc = ccommand(&argv);
|
||||
#endif
|
||||
|
||||
#ifdef MSDOS
|
||||
progname = "cjpeg"; /* DOS tends to be too verbose about argv[0] */
|
||||
#else
|
||||
progname = argv[0];
|
||||
if (progname == NULL || progname[0] == 0)
|
||||
progname = "cjpeg"; /* in case C library doesn't provide it */
|
||||
#endif
|
||||
|
||||
/* The default maxmem must be computed only once at program startup,
|
||||
* since releasing memory with free() won't give it back to the OS.
|
||||
*/
|
||||
#ifdef FREE_MEM_ESTIMATE
|
||||
default_maxmem = FREE_MEM_ESTIMATE;
|
||||
#else
|
||||
default_maxmem = 0;
|
||||
#endif
|
||||
|
||||
/* Scan command line, parse switches and locate input file names */
|
||||
|
||||
if (argc < 2)
|
||||
usage(); /* nothing on the command line?? */
|
||||
|
||||
file_index = 0;
|
||||
|
||||
while (file_index < argc-1)
|
||||
file_index = process_one_file(argc, argv, file_index);
|
||||
|
||||
/* All done. */
|
||||
exit(EXIT_SUCCESS);
|
||||
return 0; /* suppress no-return-value warnings */
|
||||
}
|
||||
|
|
@ -1,766 +0,0 @@
|
|||
/*
|
||||
* alternate djpeg.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2009-2023 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
* This file contains an alternate user interface for the JPEG decompressor.
|
||||
* One or more input files are named on the command line, and output file
|
||||
* names are created by substituting an appropriate extension.
|
||||
*/
|
||||
|
||||
#include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */
|
||||
#include "jversion.h" /* for version message */
|
||||
|
||||
#include <ctype.h> /* to declare isprint() */
|
||||
|
||||
#ifdef USE_CCOMMAND /* command-line reader for Macintosh */
|
||||
#ifdef __MWERKS__
|
||||
#include <SIOUX.h> /* Metrowerks needs this */
|
||||
#include <console.h> /* ... and this */
|
||||
#endif
|
||||
#ifdef THINK_C
|
||||
#include <console.h> /* Think declares it here */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef PATH_MAX /* ANSI maximum-pathname-length constant */
|
||||
#define PATH_MAX 256
|
||||
#endif
|
||||
|
||||
|
||||
/* Create the add-on message string table. */
|
||||
|
||||
#define JMESSAGE(code,string) string ,
|
||||
|
||||
static const char * const cdjpeg_message_table[] = {
|
||||
#include "cderror.h"
|
||||
NULL
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Automatic determination of available memory.
|
||||
*/
|
||||
|
||||
static long default_maxmem; /* saves value determined at startup, or 0 */
|
||||
|
||||
#ifndef FREE_MEM_ESTIMATE /* may be defined from command line */
|
||||
|
||||
#ifdef MSDOS /* For MS-DOS (unless flat-memory model) */
|
||||
|
||||
#include <dos.h> /* for access to intdos() call */
|
||||
|
||||
LOCAL(long)
|
||||
unused_dos_memory (void)
|
||||
/* Obtain total amount of unallocated DOS memory */
|
||||
{
|
||||
union REGS regs;
|
||||
long nparas;
|
||||
|
||||
regs.h.ah = 0x48; /* DOS function Allocate Memory Block */
|
||||
regs.x.bx = 0xFFFF; /* Ask for more memory than DOS can have */
|
||||
(void) intdos(®s, ®s);
|
||||
/* DOS will fail and return # of paragraphs actually available in BX. */
|
||||
nparas = (unsigned int) regs.x.bx;
|
||||
/* Times 16 to convert to bytes. */
|
||||
return nparas << 4;
|
||||
}
|
||||
|
||||
/* The default memory setting is 95% of the available space. */
|
||||
#define FREE_MEM_ESTIMATE ((unused_dos_memory() * 95L) / 100L)
|
||||
|
||||
#endif /* MSDOS */
|
||||
|
||||
#ifdef ATARI /* For Atari ST/Mega/STE/TT/Falcon, Pure C or Turbo C */
|
||||
|
||||
#include <ext.h>
|
||||
|
||||
/* The default memory setting is 90% of the available space. */
|
||||
#define FREE_MEM_ESTIMATE (((long) coreleft() * 90L) / 100L)
|
||||
|
||||
#endif /* ATARI */
|
||||
|
||||
/* Add memory-estimation procedures for other operating systems here,
|
||||
* with appropriate #ifdef's around them.
|
||||
*/
|
||||
|
||||
#endif /* !FREE_MEM_ESTIMATE */
|
||||
|
||||
|
||||
/*
|
||||
* This list defines the known output image formats
|
||||
* (not all of which need be supported by a given version).
|
||||
* You can change the default output format by defining DEFAULT_FMT;
|
||||
* indeed, you had better do so if you undefine PPM_SUPPORTED.
|
||||
*/
|
||||
|
||||
typedef enum {
|
||||
FMT_BMP, /* BMP format (Windows flavor) */
|
||||
FMT_GIF, /* GIF format (LZW compressed) */
|
||||
FMT_GIF0, /* GIF format (uncompressed) */
|
||||
FMT_OS2, /* BMP format (OS/2 flavor) */
|
||||
FMT_PPM, /* PPM/PGM (PBMPLUS formats) */
|
||||
FMT_RLE, /* RLE format */
|
||||
FMT_TARGA, /* Targa format */
|
||||
FMT_TIFF /* TIFF format */
|
||||
} IMAGE_FORMATS;
|
||||
|
||||
#ifndef DEFAULT_FMT /* so can override from CFLAGS in Makefile */
|
||||
#define DEFAULT_FMT FMT_BMP
|
||||
#endif
|
||||
|
||||
static IMAGE_FORMATS requested_fmt;
|
||||
|
||||
|
||||
/*
|
||||
* Argument-parsing code.
|
||||
* The switch parser is designed to be useful with DOS-style command line
|
||||
* syntax, ie, intermixed switches and file names, where only the switches
|
||||
* to the left of a given file name affect processing of that file.
|
||||
*/
|
||||
|
||||
|
||||
static const char * progname; /* program name for error messages */
|
||||
static char * outfilename; /* for -outfile switch */
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
usage (void)
|
||||
/* complain about bad command line */
|
||||
{
|
||||
fprintf(stderr, "usage: %s [switches] inputfile(s)\n", progname);
|
||||
fprintf(stderr, "List of input files may use wildcards (* and ?)\n");
|
||||
fprintf(stderr, "Output filename is same as input filename except for extension\n");
|
||||
|
||||
fprintf(stderr, "Switches (names may be abbreviated):\n");
|
||||
fprintf(stderr, " -colors N Reduce image to no more than N colors\n");
|
||||
fprintf(stderr, " -fast Fast, low-quality processing\n");
|
||||
fprintf(stderr, " -grayscale Force grayscale output\n");
|
||||
fprintf(stderr, " -rgb Force RGB output\n");
|
||||
#ifdef IDCT_SCALING_SUPPORTED
|
||||
fprintf(stderr, " -scale M/N Scale output image by fraction M/N, eg, 1/8\n");
|
||||
#endif
|
||||
#ifdef BMP_SUPPORTED
|
||||
fprintf(stderr, " -bmp Select BMP output format (Windows style)%s\n",
|
||||
(DEFAULT_FMT == FMT_BMP ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef GIF_SUPPORTED
|
||||
fprintf(stderr, " -gif Select GIF output format (LZW compressed)%s\n",
|
||||
(DEFAULT_FMT == FMT_GIF ? " (default)" : ""));
|
||||
fprintf(stderr, " -gif0 Select GIF output format (uncompressed)%s\n",
|
||||
(DEFAULT_FMT == FMT_GIF0 ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef BMP_SUPPORTED
|
||||
fprintf(stderr, " -os2 Select BMP output format (OS/2 style)%s\n",
|
||||
(DEFAULT_FMT == FMT_OS2 ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef PPM_SUPPORTED
|
||||
fprintf(stderr, " -pnm Select PBMPLUS (PPM/PGM) output format%s\n",
|
||||
(DEFAULT_FMT == FMT_PPM ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef RLE_SUPPORTED
|
||||
fprintf(stderr, " -rle Select Utah RLE output format%s\n",
|
||||
(DEFAULT_FMT == FMT_RLE ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
fprintf(stderr, " -targa Select Targa output format%s\n",
|
||||
(DEFAULT_FMT == FMT_TARGA ? " (default)" : ""));
|
||||
#endif
|
||||
fprintf(stderr, "Switches for advanced users:\n");
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
fprintf(stderr, " -dct int Use integer DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_ISLOW ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_IFAST_SUPPORTED
|
||||
fprintf(stderr, " -dct fast Use fast integer DCT (less accurate)%s\n",
|
||||
(JDCT_DEFAULT == JDCT_IFAST ? " (default)" : ""));
|
||||
#endif
|
||||
#ifdef DCT_FLOAT_SUPPORTED
|
||||
fprintf(stderr, " -dct float Use floating-point DCT method%s\n",
|
||||
(JDCT_DEFAULT == JDCT_FLOAT ? " (default)" : ""));
|
||||
#endif
|
||||
fprintf(stderr, " -dither fs Use F-S dithering (default)\n");
|
||||
fprintf(stderr, " -dither none Don't use dithering in quantization\n");
|
||||
fprintf(stderr, " -dither ordered Use ordered dither (medium speed, quality)\n");
|
||||
#ifdef QUANT_2PASS_SUPPORTED
|
||||
fprintf(stderr, " -map FILE Map to colors used in named image file\n");
|
||||
#endif
|
||||
fprintf(stderr, " -nosmooth Don't use high-quality upsampling\n");
|
||||
#ifdef QUANT_1PASS_SUPPORTED
|
||||
fprintf(stderr, " -onepass Use 1-pass quantization (fast, low quality)\n");
|
||||
#endif
|
||||
#ifndef FREE_MEM_ESTIMATE
|
||||
fprintf(stderr, " -maxmemory N Maximum memory to use (in kbytes)\n");
|
||||
#endif
|
||||
fprintf(stderr, " -outfile name Specify name for output file\n");
|
||||
fprintf(stderr, " -verbose or -debug Emit debug output\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
|
||||
LOCAL(int)
|
||||
parse_switches (j_decompress_ptr cinfo, int argc, char **argv,
|
||||
int last_file_arg_seen, boolean for_real)
|
||||
/* Parse optional switches.
|
||||
* Returns argv[] index of first file-name argument (== argc if none).
|
||||
* Any file names with indexes <= last_file_arg_seen are ignored;
|
||||
* they have presumably been processed in a previous iteration.
|
||||
* (Pass 0 for last_file_arg_seen on the first or only iteration.)
|
||||
* for_real is FALSE on the first (dummy) pass; we may skip any expensive
|
||||
* processing.
|
||||
*/
|
||||
{
|
||||
int argn;
|
||||
char * arg;
|
||||
|
||||
/* Set up default JPEG parameters. */
|
||||
requested_fmt = DEFAULT_FMT; /* set default output file format */
|
||||
outfilename = NULL;
|
||||
cinfo->err->trace_level = 0;
|
||||
if (default_maxmem > 0) /* override library's default value */
|
||||
cinfo->mem->max_memory_to_use = default_maxmem;
|
||||
|
||||
/* Scan command line options, adjust parameters */
|
||||
|
||||
for (argn = 1; argn < argc; argn++) {
|
||||
arg = argv[argn];
|
||||
if (*arg != '-') {
|
||||
/* Not a switch, must be a file name argument */
|
||||
if (argn <= last_file_arg_seen) {
|
||||
outfilename = NULL; /* -outfile applies to just one input file */
|
||||
continue; /* ignore this name if previously processed */
|
||||
}
|
||||
break; /* else done parsing switches */
|
||||
}
|
||||
arg++; /* advance past switch marker character */
|
||||
|
||||
if (keymatch(arg, "bmp", 1)) {
|
||||
/* BMP output format (Windows flavor). */
|
||||
requested_fmt = FMT_BMP;
|
||||
|
||||
} else if (keymatch(arg, "colors", 1) || keymatch(arg, "colours", 1) ||
|
||||
keymatch(arg, "quantize", 1) || keymatch(arg, "quantise", 1)) {
|
||||
/* Do color quantization. */
|
||||
int val;
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%d", &val) != 1)
|
||||
usage();
|
||||
cinfo->desired_number_of_colors = val;
|
||||
cinfo->quantize_colors = TRUE;
|
||||
|
||||
} else if (keymatch(arg, "dct", 2)) {
|
||||
/* Select IDCT algorithm. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (keymatch(argv[argn], "int", 1)) {
|
||||
cinfo->dct_method = JDCT_ISLOW;
|
||||
} else if (keymatch(argv[argn], "fast", 2)) {
|
||||
cinfo->dct_method = JDCT_IFAST;
|
||||
} else if (keymatch(argv[argn], "float", 2)) {
|
||||
cinfo->dct_method = JDCT_FLOAT;
|
||||
} else
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "dither", 2)) {
|
||||
/* Select dithering algorithm. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (keymatch(argv[argn], "fs", 2)) {
|
||||
cinfo->dither_mode = JDITHER_FS;
|
||||
} else if (keymatch(argv[argn], "none", 2)) {
|
||||
cinfo->dither_mode = JDITHER_NONE;
|
||||
} else if (keymatch(argv[argn], "ordered", 2)) {
|
||||
cinfo->dither_mode = JDITHER_ORDERED;
|
||||
} else
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "debug", 1) || keymatch(arg, "verbose", 1)) {
|
||||
/* Enable debug printouts. */
|
||||
/* On first -d, print version identification */
|
||||
static boolean printed_version = FALSE;
|
||||
|
||||
if (! printed_version) {
|
||||
fprintf(stderr, "Independent JPEG Group's DJPEG, version %s\n%s\n",
|
||||
JVERSION, JCOPYRIGHT);
|
||||
printed_version = TRUE;
|
||||
}
|
||||
cinfo->err->trace_level++;
|
||||
|
||||
} else if (keymatch(arg, "fast", 1)) {
|
||||
/* Select recommended processing options for quick-and-dirty output. */
|
||||
cinfo->two_pass_quantize = FALSE;
|
||||
cinfo->dither_mode = JDITHER_ORDERED;
|
||||
if (! cinfo->quantize_colors) /* don't override an earlier -colors */
|
||||
cinfo->desired_number_of_colors = 216;
|
||||
cinfo->dct_method = JDCT_FASTEST;
|
||||
cinfo->do_fancy_upsampling = FALSE;
|
||||
|
||||
} else if (keymatch(arg, "gif", 1)) {
|
||||
/* GIF output format (LZW compressed). */
|
||||
requested_fmt = FMT_GIF;
|
||||
|
||||
} else if (keymatch(arg, "gif0", 4)) {
|
||||
/* GIF output format (uncompressed). */
|
||||
requested_fmt = FMT_GIF0;
|
||||
|
||||
} else if (keymatch(arg, "grayscale", 2) || keymatch(arg, "greyscale",2)) {
|
||||
/* Force monochrome output. */
|
||||
cinfo->out_color_space = JCS_GRAYSCALE;
|
||||
|
||||
} else if (keymatch(arg, "rgb", 3)) {
|
||||
/* Force RGB output. */
|
||||
cinfo->out_color_space = JCS_RGB;
|
||||
|
||||
} else if (keymatch(arg, "map", 3)) {
|
||||
/* Quantize to a color map taken from an input file. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (for_real) { /* too expensive to do twice! */
|
||||
#ifdef QUANT_2PASS_SUPPORTED /* otherwise can't quantize to supplied map */
|
||||
FILE * mapfile;
|
||||
|
||||
if ((mapfile = fopen(argv[argn], READ_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't open %s\n", progname, argv[argn]);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
read_color_map(cinfo, mapfile);
|
||||
fclose(mapfile);
|
||||
cinfo->quantize_colors = TRUE;
|
||||
#else
|
||||
ERREXIT(cinfo, JERR_NOT_COMPILED);
|
||||
#endif
|
||||
}
|
||||
|
||||
} else if (keymatch(arg, "maxmemory", 3)) {
|
||||
/* Maximum memory in Kb (or Mb with 'm'). */
|
||||
long lval;
|
||||
char ch = 'x';
|
||||
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%ld%c", &lval, &ch) < 1)
|
||||
usage();
|
||||
if (ch == 'm' || ch == 'M')
|
||||
lval *= 1000L;
|
||||
cinfo->mem->max_memory_to_use = lval * 1000L;
|
||||
|
||||
} else if (keymatch(arg, "nosmooth", 3)) {
|
||||
/* Suppress fancy upsampling. */
|
||||
cinfo->do_fancy_upsampling = FALSE;
|
||||
|
||||
} else if (keymatch(arg, "onepass", 3)) {
|
||||
/* Use fast one-pass quantization. */
|
||||
cinfo->two_pass_quantize = FALSE;
|
||||
|
||||
} else if (keymatch(arg, "os2", 3)) {
|
||||
/* BMP output format (OS/2 flavor). */
|
||||
requested_fmt = FMT_OS2;
|
||||
|
||||
} else if (keymatch(arg, "outfile", 4)) {
|
||||
/* Set output file name. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
outfilename = argv[argn]; /* save it away for later use */
|
||||
|
||||
} else if (keymatch(arg, "pnm", 1) || keymatch(arg, "ppm", 1)) {
|
||||
/* PPM/PGM output format. */
|
||||
requested_fmt = FMT_PPM;
|
||||
|
||||
} else if (keymatch(arg, "rle", 1)) {
|
||||
/* RLE output format. */
|
||||
requested_fmt = FMT_RLE;
|
||||
|
||||
} else if (keymatch(arg, "scale", 1)) {
|
||||
/* Scale the output image by a fraction M/N. */
|
||||
if (++argn >= argc) /* advance to next argument */
|
||||
usage();
|
||||
if (sscanf(argv[argn], "%u/%u",
|
||||
&cinfo->scale_num, &cinfo->scale_denom) < 1)
|
||||
usage();
|
||||
|
||||
} else if (keymatch(arg, "targa", 1)) {
|
||||
/* Targa output format. */
|
||||
requested_fmt = FMT_TARGA;
|
||||
|
||||
} else {
|
||||
usage(); /* bogus switch */
|
||||
}
|
||||
}
|
||||
|
||||
return argn; /* return index of next arg (file name) */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Marker processor for COM and interesting APPn markers.
|
||||
* This replaces the library's built-in processor, which just skips the marker.
|
||||
* We want to print out the marker as text, to the extent possible.
|
||||
* Note this code relies on a non-suspending data source.
|
||||
*/
|
||||
|
||||
LOCAL(unsigned int)
|
||||
jpeg_getc (j_decompress_ptr cinfo)
|
||||
/* Read next byte */
|
||||
{
|
||||
struct jpeg_source_mgr * datasrc = cinfo->src;
|
||||
|
||||
if (datasrc->bytes_in_buffer == 0) {
|
||||
if (! (*datasrc->fill_input_buffer) (cinfo))
|
||||
ERREXIT(cinfo, JERR_CANT_SUSPEND);
|
||||
}
|
||||
datasrc->bytes_in_buffer--;
|
||||
return GETJOCTET(*datasrc->next_input_byte++);
|
||||
}
|
||||
|
||||
|
||||
METHODDEF(boolean)
|
||||
print_text_marker (j_decompress_ptr cinfo)
|
||||
{
|
||||
boolean traceit = (cinfo->err->trace_level >= 1);
|
||||
INT32 length;
|
||||
unsigned int ch;
|
||||
unsigned int lastch = 0;
|
||||
|
||||
length = jpeg_getc(cinfo) << 8;
|
||||
length += jpeg_getc(cinfo);
|
||||
length -= 2; /* discount the length word itself */
|
||||
|
||||
if (traceit) {
|
||||
if (cinfo->unread_marker == JPEG_COM)
|
||||
fprintf(stderr, "Comment, length %ld:\n", (long) length);
|
||||
else /* assume it is an APPn otherwise */
|
||||
fprintf(stderr, "APP%d, length %ld:\n",
|
||||
cinfo->unread_marker - JPEG_APP0, (long) length);
|
||||
}
|
||||
|
||||
while (--length >= 0) {
|
||||
ch = jpeg_getc(cinfo);
|
||||
if (traceit) {
|
||||
/* Emit the character in a readable form.
|
||||
* Nonprintables are converted to \nnn form,
|
||||
* while \ is converted to \\.
|
||||
* Newlines in CR, CR/LF, or LF form will be printed as one newline.
|
||||
*/
|
||||
if (ch == '\r') {
|
||||
fprintf(stderr, "\n");
|
||||
} else if (ch == '\n') {
|
||||
if (lastch != '\r')
|
||||
fprintf(stderr, "\n");
|
||||
} else if (ch == '\\') {
|
||||
fprintf(stderr, "\\\\");
|
||||
} else if (isprint(ch)) {
|
||||
putc(ch, stderr);
|
||||
} else {
|
||||
fprintf(stderr, "\\%03o", ch);
|
||||
}
|
||||
lastch = ch;
|
||||
}
|
||||
}
|
||||
|
||||
if (traceit)
|
||||
fprintf(stderr, "\n");
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Check for overwrite of an existing file; clear it with user
|
||||
*/
|
||||
|
||||
#ifndef NO_OVERWRITE_CHECK
|
||||
|
||||
LOCAL(boolean)
|
||||
is_write_ok (char * outfname)
|
||||
{
|
||||
FILE * ofile;
|
||||
int ch;
|
||||
|
||||
ofile = fopen(outfname, READ_BINARY);
|
||||
if (ofile == NULL)
|
||||
return TRUE; /* not present */
|
||||
fclose(ofile); /* oops, it is present */
|
||||
|
||||
for (;;) {
|
||||
fprintf(stderr, "%s already exists, overwrite it? [y/n] ",
|
||||
outfname);
|
||||
fflush(stderr);
|
||||
ch = getc(stdin);
|
||||
if (ch != '\n') /* flush rest of line */
|
||||
while (getc(stdin) != '\n')
|
||||
/* nothing */;
|
||||
|
||||
switch (ch) {
|
||||
case 'Y':
|
||||
case 'y':
|
||||
return TRUE;
|
||||
case 'N':
|
||||
case 'n':
|
||||
return FALSE;
|
||||
/* otherwise, ask again */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Process a single input file name, and return its index in argv[].
|
||||
* File names at or to left of old_file_index have been processed already.
|
||||
*/
|
||||
|
||||
LOCAL(int)
|
||||
process_one_file (int argc, char **argv, int old_file_index)
|
||||
{
|
||||
struct jpeg_decompress_struct cinfo;
|
||||
struct jpeg_error_mgr jerr;
|
||||
char *infilename;
|
||||
char workfilename[PATH_MAX];
|
||||
const char *default_extension = NULL;
|
||||
#ifdef PROGRESS_REPORT
|
||||
struct cdjpeg_progress_mgr progress;
|
||||
#endif
|
||||
int file_index;
|
||||
djpeg_dest_ptr dest_mgr = NULL;
|
||||
FILE * input_file = NULL;
|
||||
FILE * output_file = NULL;
|
||||
JDIMENSION num_scanlines;
|
||||
|
||||
/* Initialize the JPEG decompression object with default error handling. */
|
||||
cinfo.err = jpeg_std_error(&jerr);
|
||||
jpeg_create_decompress(&cinfo);
|
||||
/* Add some application-specific error messages (from cderror.h) */
|
||||
jerr.addon_message_table = cdjpeg_message_table;
|
||||
jerr.first_addon_message = JMSG_FIRSTADDONCODE;
|
||||
jerr.last_addon_message = JMSG_LASTADDONCODE;
|
||||
|
||||
/* Insert custom marker processor for COM and APP12.
|
||||
* APP12 is used by some digital camera makers for textual info,
|
||||
* so we provide the ability to display it as text.
|
||||
* If you like, additional APPn marker types can be selected for display,
|
||||
* but don't try to override APP0 or APP14 this way (see libjpeg.txt).
|
||||
*/
|
||||
jpeg_set_marker_processor(&cinfo, JPEG_COM, print_text_marker);
|
||||
jpeg_set_marker_processor(&cinfo, JPEG_APP0+12, print_text_marker);
|
||||
|
||||
/* Now safe to enable signal catcher. */
|
||||
#ifdef NEED_SIGNAL_CATCHER
|
||||
enable_signal_catcher((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* Scan command line to find next file name.
|
||||
* It is convenient to use just one switch-parsing routine, but the switch
|
||||
* values read here are ignored; we will rescan the switches after opening
|
||||
* the input file.
|
||||
* (Exception: tracing level set here controls verbosity for COM markers
|
||||
* found during jpeg_read_header...)
|
||||
*/
|
||||
|
||||
file_index = parse_switches(&cinfo, argc, argv, old_file_index, FALSE);
|
||||
if (file_index >= argc) {
|
||||
fprintf(stderr, "%s: missing input file name\n", progname);
|
||||
usage();
|
||||
}
|
||||
|
||||
/* Open the input file. */
|
||||
infilename = argv[file_index];
|
||||
if ((input_file = fopen(infilename, READ_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't open %s\n", progname, infilename);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
start_progress_monitor((j_common_ptr) &cinfo, &progress);
|
||||
#endif
|
||||
|
||||
/* Specify data source for decompression */
|
||||
jpeg_stdio_src(&cinfo, input_file);
|
||||
|
||||
/* Read file header, set default decompression parameters */
|
||||
(void) jpeg_read_header(&cinfo, TRUE);
|
||||
|
||||
/* Adjust default decompression parameters by re-parsing the options */
|
||||
file_index = parse_switches(&cinfo, argc, argv, old_file_index, TRUE);
|
||||
|
||||
/* Initialize the output module now to let it override any crucial
|
||||
* option settings (for instance, GIF wants to force color quantization).
|
||||
*/
|
||||
switch (requested_fmt) {
|
||||
#ifdef BMP_SUPPORTED
|
||||
case FMT_BMP:
|
||||
dest_mgr = jinit_write_bmp(&cinfo, FALSE);
|
||||
default_extension = ".bmp";
|
||||
break;
|
||||
case FMT_OS2:
|
||||
dest_mgr = jinit_write_bmp(&cinfo, TRUE);
|
||||
default_extension = ".bmp";
|
||||
break;
|
||||
#endif
|
||||
#ifdef GIF_SUPPORTED
|
||||
case FMT_GIF:
|
||||
dest_mgr = jinit_write_gif(&cinfo, TRUE);
|
||||
default_extension = ".gif";
|
||||
break;
|
||||
case FMT_GIF0:
|
||||
dest_mgr = jinit_write_gif(&cinfo, FALSE);
|
||||
default_extension = ".gif";
|
||||
break;
|
||||
#endif
|
||||
#ifdef PPM_SUPPORTED
|
||||
case FMT_PPM:
|
||||
dest_mgr = jinit_write_ppm(&cinfo);
|
||||
default_extension = ".ppm";
|
||||
break;
|
||||
#endif
|
||||
#ifdef RLE_SUPPORTED
|
||||
case FMT_RLE:
|
||||
dest_mgr = jinit_write_rle(&cinfo);
|
||||
default_extension = ".rle";
|
||||
break;
|
||||
#endif
|
||||
#ifdef TARGA_SUPPORTED
|
||||
case FMT_TARGA:
|
||||
dest_mgr = jinit_write_targa(&cinfo);
|
||||
default_extension = ".tga";
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
ERREXIT(&cinfo, JERR_UNSUPPORTED_FORMAT);
|
||||
}
|
||||
|
||||
/* If user didn't supply -outfile switch, select output file name. */
|
||||
if (outfilename == NULL) {
|
||||
int i;
|
||||
|
||||
outfilename = workfilename;
|
||||
/* Make outfilename be infilename with appropriate extension */
|
||||
strcpy(outfilename, infilename);
|
||||
for (i = (int)strlen(outfilename)-1; i >= 0; i--) {
|
||||
switch (outfilename[i]) {
|
||||
case ':':
|
||||
case '/':
|
||||
case '\\':
|
||||
i = 0; /* stop scanning */
|
||||
break;
|
||||
case '.':
|
||||
outfilename[i] = '\0'; /* lop off existing extension */
|
||||
i = 0; /* stop scanning */
|
||||
break;
|
||||
default:
|
||||
break; /* keep scanning */
|
||||
}
|
||||
}
|
||||
strcat(outfilename, default_extension);
|
||||
}
|
||||
|
||||
fprintf(stderr, "Decompressing %s => %s\n", infilename, outfilename);
|
||||
#ifndef NO_OVERWRITE_CHECK
|
||||
if (! is_write_ok(outfilename))
|
||||
goto fail;
|
||||
#endif
|
||||
|
||||
/* Open the output file. */
|
||||
if ((output_file = fopen(outfilename, WRITE_BINARY)) == NULL) {
|
||||
fprintf(stderr, "%s: can't create %s\n", progname, outfilename);
|
||||
goto fail;
|
||||
}
|
||||
dest_mgr->output_file = output_file;
|
||||
|
||||
/* Start decompressor */
|
||||
(void) jpeg_start_decompress(&cinfo);
|
||||
|
||||
/* Write output file header */
|
||||
(*dest_mgr->start_output) (&cinfo, dest_mgr);
|
||||
|
||||
/* Process data */
|
||||
while (cinfo.output_scanline < cinfo.output_height) {
|
||||
num_scanlines = jpeg_read_scanlines(&cinfo, dest_mgr->buffer,
|
||||
dest_mgr->buffer_height);
|
||||
(*dest_mgr->put_pixel_rows) (&cinfo, dest_mgr, num_scanlines);
|
||||
}
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
/* Hack: count final pass as done in case finish_output does an extra pass.
|
||||
* The library won't have updated completed_passes.
|
||||
*/
|
||||
progress.pub.completed_passes = progress.pub.total_passes;
|
||||
#endif
|
||||
|
||||
/* Finish decompression and release memory.
|
||||
* I must do it in this order because output module has allocated memory
|
||||
* of lifespan JPOOL_IMAGE; it needs to finish before releasing memory.
|
||||
*/
|
||||
(*dest_mgr->finish_output) (&cinfo, dest_mgr);
|
||||
(void) jpeg_finish_decompress(&cinfo);
|
||||
|
||||
/* Clean up and exit */
|
||||
fail:
|
||||
jpeg_destroy_decompress(&cinfo);
|
||||
|
||||
if (input_file != NULL) fclose(input_file);
|
||||
if (output_file != NULL) fclose(output_file);
|
||||
|
||||
#ifdef PROGRESS_REPORT
|
||||
end_progress_monitor((j_common_ptr) &cinfo);
|
||||
#endif
|
||||
|
||||
/* Disable signal catcher. */
|
||||
#ifdef NEED_SIGNAL_CATCHER
|
||||
enable_signal_catcher((j_common_ptr) NULL);
|
||||
#endif
|
||||
|
||||
return file_index;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* The main program.
|
||||
*/
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
int file_index;
|
||||
|
||||
/* On Mac, fetch a command line. */
|
||||
#ifdef USE_CCOMMAND
|
||||
argc = ccommand(&argv);
|
||||
#endif
|
||||
|
||||
#ifdef MSDOS
|
||||
progname = "djpeg"; /* DOS tends to be too verbose about argv[0] */
|
||||
#else
|
||||
progname = argv[0];
|
||||
if (progname == NULL || progname[0] == 0)
|
||||
progname = "djpeg"; /* in case C library doesn't provide it */
|
||||
#endif
|
||||
|
||||
/* The default maxmem must be computed only once at program startup,
|
||||
* since releasing memory with free() won't give it back to the OS.
|
||||
*/
|
||||
#ifdef FREE_MEM_ESTIMATE
|
||||
default_maxmem = FREE_MEM_ESTIMATE;
|
||||
#else
|
||||
default_maxmem = 0;
|
||||
#endif
|
||||
|
||||
/* Scan command line, parse switches and locate input file names */
|
||||
|
||||
if (argc < 2)
|
||||
usage(); /* nothing on the command line?? */
|
||||
|
||||
file_index = 0;
|
||||
|
||||
while (file_index < argc-1)
|
||||
file_index = process_one_file(argc, argv, file_index);
|
||||
|
||||
/* All done. */
|
||||
exit(EXIT_SUCCESS);
|
||||
return 0; /* suppress no-return-value warnings */
|
||||
}
|
||||
|
|
@ -2,7 +2,7 @@
|
|||
* jccolor.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2011-2023 by Guido Vollbeding.
|
||||
* Modified 2011-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -476,8 +476,9 @@ jinit_color_converter (j_compress_ptr cinfo)
|
|||
|
||||
/* Support color transform only for RGB colorspaces */
|
||||
if (cinfo->color_transform &&
|
||||
cinfo->jpeg_color_space != JCS_RGB &&
|
||||
cinfo->jpeg_color_space != JCS_BG_RGB)
|
||||
(cinfo->LSE_maxtrans != MAXJSAMPLE ||
|
||||
(cinfo->jpeg_color_space != JCS_RGB &&
|
||||
cinfo->jpeg_color_space != JCS_BG_RGB)))
|
||||
ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
||||
|
||||
/* Check num_components, set conversion method based on requested space */
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jcdctmgr.c
|
||||
*
|
||||
* Copyright (C) 1994-1996, Thomas G. Lane.
|
||||
* Modified 2003-2020 by Guido Vollbeding.
|
||||
* Modified 2003-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -50,18 +50,6 @@ typedef union {
|
|||
} divisor_table;
|
||||
|
||||
|
||||
/* The current scaled-DCT routines require ISLOW-style divisor tables,
|
||||
* so be sure to compile that code if either ISLOW or SCALING is requested.
|
||||
*/
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#else
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Perform forward DCT on one or more blocks of a component.
|
||||
*
|
||||
|
|
@ -102,9 +90,9 @@ forward_DCT (j_compress_ptr cinfo, jpeg_component_info * compptr,
|
|||
* In most files, at least half of the output values will be zero
|
||||
* (at default quantization settings, more like three-quarters...)
|
||||
* so we should ensure that this case is fast. On many machines,
|
||||
* a comparison is enough cheaper than a divide to make a special test
|
||||
* a win. Since both inputs will be nonnegative, we need only test
|
||||
* for a < b to discover whether a/b is 0.
|
||||
* a comparison is enough cheaper than a divide to make a special
|
||||
* test a win. Since both inputs will be nonnegative, we need
|
||||
* only test for a < b to discover whether a/b is 0.
|
||||
* If your machine's division is fast enough, define FAST_DIVIDE.
|
||||
*/
|
||||
#ifdef FAST_DIVIDE
|
||||
|
|
@ -185,7 +173,7 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
my_fdct_ptr fdct = (my_fdct_ptr) cinfo->fdct;
|
||||
int ci, qtblno, i;
|
||||
jpeg_component_info *compptr;
|
||||
int method = 0;
|
||||
J_DCT_METHOD method = JDCT_DEFAULT;
|
||||
JQUANT_TBL * qtbl;
|
||||
DCTELEM * dtbl;
|
||||
|
||||
|
|
@ -194,6 +182,13 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
/* Select the proper DCT routine for this component's scaling */
|
||||
switch ((compptr->DCT_h_scaled_size << 8) + compptr->DCT_v_scaled_size) {
|
||||
#ifdef DCT_SCALING_SUPPORTED
|
||||
/*
|
||||
* The current scaled-DCT routines require ISLOW-style divisor tables,
|
||||
* so be sure to compile that code if either ISLOW or SCALING is requested.
|
||||
*/
|
||||
#ifndef PROVIDE_ISLOW_TABLES
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
case ((1 << 8) + 1):
|
||||
fdct->do_dct[ci] = jpeg_fdct_1x1;
|
||||
method = JDCT_ISLOW; /* jfdctint uses islow-style table */
|
||||
|
|
@ -323,14 +318,34 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
switch (cinfo->dct_method) {
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
case JDCT_ISLOW:
|
||||
#ifndef PROVIDE_ISLOW_TABLES
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
fdct->do_dct[ci] = jpeg_fdct_islow;
|
||||
method = JDCT_ISLOW;
|
||||
break;
|
||||
#endif
|
||||
#ifdef DCT_IFAST_SUPPORTED
|
||||
case JDCT_IFAST:
|
||||
#if BITS_IN_JSAMPLE < JPEG_DATA_PRECISION || \
|
||||
BITS_IN_JSAMPLE > JPEG_DATA_PRECISION + 8
|
||||
/*
|
||||
* Adjustment of divisor tables in JDCT_IFAST
|
||||
* below doesn't work well in this condition.
|
||||
* Use JDCT_ISLOW instead.
|
||||
*/
|
||||
#ifndef PROVIDE_ISLOW_TABLES
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
fdct->do_dct[ci] = jpeg_fdct_islow;
|
||||
method = JDCT_ISLOW;
|
||||
#else
|
||||
#ifndef PROVIDE_IFAST_TABLES
|
||||
#define PROVIDE_IFAST_TABLES
|
||||
#endif
|
||||
fdct->do_dct[ci] = jpeg_fdct_ifast;
|
||||
method = JDCT_IFAST;
|
||||
#endif
|
||||
break;
|
||||
#endif
|
||||
#ifdef DCT_FLOAT_SUPPORTED
|
||||
|
|
@ -357,7 +372,7 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
switch (method) {
|
||||
#ifdef PROVIDE_ISLOW_TABLES
|
||||
case JDCT_ISLOW:
|
||||
/* For LL&M IDCT method, divisors are equal to raw quantization
|
||||
/* For LL&M FDCT method, divisors are equal to raw quantization
|
||||
* coefficients multiplied by 8 (to counteract scaling).
|
||||
*/
|
||||
dtbl = (DCTELEM *) compptr->dct_table;
|
||||
|
|
@ -368,14 +383,15 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
fdct->pub.forward_DCT[ci] = forward_DCT;
|
||||
break;
|
||||
#endif
|
||||
#ifdef DCT_IFAST_SUPPORTED
|
||||
#ifdef PROVIDE_IFAST_TABLES
|
||||
case JDCT_IFAST:
|
||||
{
|
||||
/* For AA&N IDCT method, divisors are equal to quantization
|
||||
/* For AA&N FDCT method, divisors are equal to quantization
|
||||
* coefficients scaled by scalefactor[row]*scalefactor[col], where
|
||||
* scalefactor[0] = 1
|
||||
* scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
|
||||
* We apply a further scale factor of 8.
|
||||
* We apply a further scale factor of 8
|
||||
* with adjustment if necessary.
|
||||
*/
|
||||
#define CONST_BITS 14
|
||||
static const INT16 aanscales[DCTSIZE2] = {
|
||||
|
|
@ -392,11 +408,20 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
SHIFT_TEMPS
|
||||
|
||||
dtbl = (DCTELEM *) compptr->dct_table;
|
||||
for (i = 0; i < DCTSIZE2; i++) {
|
||||
dtbl[i] = (DCTELEM)
|
||||
DESCALE(MULTIPLY16V16((INT32) qtbl->quantval[i],
|
||||
(INT32) aanscales[i]),
|
||||
compptr->component_needed ? CONST_BITS-4 : CONST_BITS-3);
|
||||
if (compptr->component_needed) {
|
||||
for (i = 0; i < DCTSIZE2; i++) {
|
||||
dtbl[i] = (DCTELEM)
|
||||
DESCALE(MULTIPLY16V16((INT32) qtbl->quantval[i],
|
||||
(INT32) aanscales[i]),
|
||||
CONST_BITS+JPEG_DATA_PRECISION-BITS_IN_JSAMPLE-4);
|
||||
}
|
||||
} else {
|
||||
for (i = 0; i < DCTSIZE2; i++) {
|
||||
dtbl[i] = (DCTELEM)
|
||||
DESCALE(MULTIPLY16V16((INT32) qtbl->quantval[i],
|
||||
(INT32) aanscales[i]),
|
||||
CONST_BITS+JPEG_DATA_PRECISION-BITS_IN_JSAMPLE-3);
|
||||
}
|
||||
}
|
||||
}
|
||||
fdct->pub.forward_DCT[ci] = forward_DCT;
|
||||
|
|
@ -405,11 +430,12 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
#ifdef DCT_FLOAT_SUPPORTED
|
||||
case JDCT_FLOAT:
|
||||
{
|
||||
/* For float AA&N IDCT method, divisors are equal to quantization
|
||||
/* For float AA&N FDCT method, divisors are equal to quantization
|
||||
* coefficients scaled by scalefactor[row]*scalefactor[col], where
|
||||
* scalefactor[0] = 1
|
||||
* scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
|
||||
* We apply a further scale factor of 8.
|
||||
* We apply a further scale factor of 8
|
||||
* with adjustment if necessary.
|
||||
* What's actually stored is 1/divisor so that the inner loop can
|
||||
* use a multiplication rather than a division.
|
||||
*/
|
||||
|
|
@ -419,6 +445,7 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
1.0, 1.387039845, 1.306562965, 1.175875602,
|
||||
1.0, 0.785694958, 0.541196100, 0.275899379
|
||||
};
|
||||
#if BITS_IN_JSAMPLE == JPEG_DATA_PRECISION
|
||||
|
||||
i = 0;
|
||||
for (row = 0; row < DCTSIZE; row++) {
|
||||
|
|
@ -427,6 +454,26 @@ start_pass_fdctmgr (j_compress_ptr cinfo)
|
|||
(1.0 / ((double) qtbl->quantval[i] *
|
||||
aanscalefactor[row] * aanscalefactor[col] *
|
||||
(compptr->component_needed ? 16.0 : 8.0)));
|
||||
#else
|
||||
double extrafactor = compptr->component_needed ? 16.0 : 8.0;
|
||||
|
||||
/* Adjust extra factor */
|
||||
#if BITS_IN_JSAMPLE < JPEG_DATA_PRECISION
|
||||
i = JPEG_DATA_PRECISION - BITS_IN_JSAMPLE;
|
||||
do { extrafactor *= 0.5; } while (--i);
|
||||
#else
|
||||
i = BITS_IN_JSAMPLE - JPEG_DATA_PRECISION;
|
||||
do { extrafactor *= 2.0; } while (--i);
|
||||
#endif
|
||||
|
||||
i = 0;
|
||||
for (row = 0; row < DCTSIZE; row++) {
|
||||
for (col = 0; col < DCTSIZE; col++) {
|
||||
fdtbl[i] = (FAST_FLOAT)
|
||||
(1.0 / ((double) qtbl->quantval[i] *
|
||||
aanscalefactor[row] * aanscalefactor[col] *
|
||||
extrafactor));
|
||||
#endif
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jchuff.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2006-2023 by Guido Vollbeding.
|
||||
* Modified 2006-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -26,9 +26,9 @@
|
|||
|
||||
|
||||
/* The legal range of a DCT coefficient is
|
||||
* -1024 .. +1023 for 8-bit sample data precision;
|
||||
* -16384 .. +16383 for 12-bit sample data precision.
|
||||
* Hence the magnitude should always fit in sample data precision + 2 bits.
|
||||
* -1024 .. +1023 for 8-bit JPEG data precision;
|
||||
* -16384 .. +16383 for 12-bit JPEG data precision.
|
||||
* Hence the magnitude should always fit in JPEG data precision + 2 bits.
|
||||
*/
|
||||
|
||||
/* Derived data constructed for each Huffman table */
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jcinit.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2003-2017 by Guido Vollbeding.
|
||||
* Modified 2003-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -196,7 +196,7 @@ jinit_compress_master (j_compress_ptr cinfo)
|
|||
JDIMENSION jd_samplesperrow;
|
||||
|
||||
/* For now, precision must match compiled-in value... */
|
||||
if (cinfo->data_precision != BITS_IN_JSAMPLE)
|
||||
if (cinfo->data_precision != JPEG_DATA_PRECISION)
|
||||
ERREXIT1(cinfo, JERR_BAD_PRECISION, cinfo->data_precision);
|
||||
|
||||
/* Sanity check on input image dimensions */
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jcmarker.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2003-2019 by Guido Vollbeding.
|
||||
* Modified 2003-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -296,7 +296,7 @@ emit_lse_ict (j_compress_ptr cinfo)
|
|||
emit_2bytes(cinfo, 24); /* fixed length */
|
||||
|
||||
emit_byte(cinfo, 0x0D); /* ID inverse transform specification */
|
||||
emit_2bytes(cinfo, MAXJSAMPLE); /* MAXTRANS */
|
||||
emit_2bytes(cinfo, (int) cinfo->LSE_maxtrans); /* MAXTRANS */
|
||||
emit_byte(cinfo, 3); /* Nt=3 */
|
||||
emit_byte(cinfo, cinfo->comp_info[1].component_id);
|
||||
emit_byte(cinfo, cinfo->comp_info[0].component_id);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
/* jconfig.vc --- jconfig.h for Microsoft Visual C++ on Windows 9x or NT.
|
||||
* This file also works for Borland/Embarcadero C++ for Win32 or Win64
|
||||
* (CLI: bcc32, bcc32c, bcc32x, bcc64; GUI IDE: C++Builder/RAD Studio).
|
||||
* (CLI: bcc32, bcc32c, bcc32x, bcc64, bcc64x;
|
||||
* GUI IDE: C++Builder/RAD Studio).
|
||||
* See jconfig.txt for explanations.
|
||||
*/
|
||||
|
||||
|
|
@ -22,7 +23,9 @@
|
|||
#ifdef boolean
|
||||
#undef boolean
|
||||
#endif
|
||||
#define boolean int
|
||||
#ifndef __RPCNDR_H__ /* don't conflict if rpcndr.h already read */
|
||||
typedef unsigned char boolean;
|
||||
#endif
|
||||
#ifndef FALSE /* in case these macros already exist */
|
||||
#define FALSE 0 /* values of boolean */
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jcparam.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2003-2022 by Guido Vollbeding.
|
||||
* Modified 2003-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -215,7 +215,7 @@ jpeg_set_defaults (j_compress_ptr cinfo)
|
|||
|
||||
cinfo->scale_num = 1; /* 1:1 scaling */
|
||||
cinfo->scale_denom = 1;
|
||||
cinfo->data_precision = BITS_IN_JSAMPLE;
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
/* Set up two quantization tables using default quality of 75 */
|
||||
jpeg_set_quality(cinfo, 75, TRUE);
|
||||
/* Reset standard Huffman tables */
|
||||
|
|
@ -283,6 +283,7 @@ jpeg_set_defaults (j_compress_ptr cinfo)
|
|||
|
||||
/* No color transform */
|
||||
cinfo->color_transform = JCT_NONE;
|
||||
cinfo->LSE_maxtrans = MAXJSAMPLE; /* Default LSE MAXTRANS value */
|
||||
|
||||
/* Choose JPEG colorspace based on input space, set defaults accordingly */
|
||||
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jctrans.c
|
||||
*
|
||||
* Copyright (C) 1995-1998, Thomas G. Lane.
|
||||
* Modified 2000-2020 by Guido Vollbeding.
|
||||
* Modified 2000-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -91,6 +91,7 @@ jpeg_copy_critical_parameters (j_decompress_ptr srcinfo,
|
|||
* entropy coding mode dependent on image data precision.
|
||||
*/
|
||||
dstinfo->color_transform = srcinfo->color_transform;
|
||||
dstinfo->LSE_maxtrans = srcinfo->LSE_maxtrans;
|
||||
jpeg_set_colorspace(dstinfo, srcinfo->jpeg_color_space);
|
||||
dstinfo->data_precision = srcinfo->data_precision;
|
||||
dstinfo->arith_code = srcinfo->data_precision > 8 ? TRUE : FALSE;
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jdcolor.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2011-2023 by Guido Vollbeding.
|
||||
* Modified 2011-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -640,8 +640,9 @@ jinit_color_deconverter (j_decompress_ptr cinfo)
|
|||
|
||||
/* Support color transform only for RGB colorspaces */
|
||||
if (cinfo->color_transform &&
|
||||
cinfo->jpeg_color_space != JCS_RGB &&
|
||||
cinfo->jpeg_color_space != JCS_BG_RGB)
|
||||
(cinfo->LSE_maxtrans != MAXJSAMPLE ||
|
||||
(cinfo->jpeg_color_space != JCS_RGB &&
|
||||
cinfo->jpeg_color_space != JCS_BG_RGB)))
|
||||
ERREXIT(cinfo, JERR_CONVERSION_NOTIMPL);
|
||||
|
||||
/* Set out_color_components and conversion method based on requested space.
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jdct.h
|
||||
*
|
||||
* Copyright (C) 1994-1996, Thomas G. Lane.
|
||||
* Modified 2002-2023 by Guido Vollbeding.
|
||||
* Modified 2002-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -17,9 +17,9 @@
|
|||
/*
|
||||
* A forward DCT routine is given a pointer to an input sample array and
|
||||
* a pointer to a work area of type DCTELEM[]; the DCT is to be performed
|
||||
* in-place in that buffer. Type DCTELEM is int for 8-bit samples, INT32
|
||||
* for 12-bit samples. (NOTE: Floating-point DCT implementations use an
|
||||
* array of type FAST_FLOAT, instead.)
|
||||
* in-place in that buffer. Type DCTELEM is int or INT32, depending on
|
||||
* bit depth parameters. (NOTE: Floating-point DCT implementations use
|
||||
* an array of type FAST_FLOAT, instead.)
|
||||
* The input data is to be fetched from the sample array starting at a
|
||||
* specified column. (Any row offset needed will be applied to the array
|
||||
* pointer before it is passed to the FDCT code.)
|
||||
|
|
@ -32,7 +32,20 @@
|
|||
* Quantization of the output coefficients is done by jcdctmgr.c.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
/* Condition for FDCT:
|
||||
* BITS_IN_JSAMPLE <= 10 && JPEG_DATA_PRECISION <= 10
|
||||
* Condition for int IDCT where DCTELEM is used (2x2, 1x1, 2x1, 1x2):
|
||||
* JPEG_DATA_PRECISION + RANGE_BITS <= 12
|
||||
* [BITS_IN_JSAMPLE - 1 + RANGE_BITS +
|
||||
* 3 - (BITS_IN_JSAMPLE - JPEG_DATA_PRECISION) <= 14]
|
||||
* {3 - (BITS_IN_JSAMPLE - JPEG_DATA_PRECISION) = PASS2_BITS - PASS1_BITS}
|
||||
* Condition for fast IDCT where DCTELEM is used:
|
||||
* JPEG_DATA_PRECISION <= 10 && BITS_IN_JSAMPLE <= 13 && RANGE_BITS <= 2
|
||||
* [BITS_IN_JSAMPLE - 1 + RANGE_BITS + PASS2BITS <= 14]
|
||||
* Combined for all:
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE <= 10 && JPEG_DATA_PRECISION <= 10 && RANGE_BITS <= 2
|
||||
typedef int DCTELEM; /* 16 or 32 bits is fine */
|
||||
#else
|
||||
typedef INT32 DCTELEM; /* must have 32 bits */
|
||||
|
|
@ -64,9 +77,10 @@ typedef JMETHOD(void, float_DCT_method_ptr, (FAST_FLOAT * data,
|
|||
*/
|
||||
|
||||
typedef MULTIPLIER ISLOW_MULT_TYPE; /* short or int, whichever is faster */
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
#if JPEG_DATA_PRECISION <= 10 && BITS_IN_JSAMPLE <= 13
|
||||
typedef MULTIPLIER IFAST_MULT_TYPE; /* 16 bits is OK, use short if faster */
|
||||
#define IFAST_SCALE_BITS 2 /* fractional bits in scale factors */
|
||||
#define IFAST_SCALE_BITS (10 - JPEG_DATA_PRECISION)
|
||||
/* fractional bits in scale factors */
|
||||
#else
|
||||
typedef INT32 IFAST_MULT_TYPE; /* need 32 bits for scaled quantizers */
|
||||
#define IFAST_SCALE_BITS 13 /* fractional bits in scale factors */
|
||||
|
|
@ -394,7 +408,7 @@ EXTERN(void) jpeg_idct_1x2
|
|||
|
||||
#ifdef RIGHT_SHIFT_IS_UNSIGNED
|
||||
#define ISHIFT_TEMPS DCTELEM ishift_temp;
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
#if BITS_IN_JSAMPLE <= 10 && JPEG_DATA_PRECISION <= 10 && RANGE_BITS <= 2
|
||||
#define DCTELEMBITS 16 /* DCTELEM may be 16 or 32 bits */
|
||||
#else
|
||||
#define DCTELEMBITS 32 /* DCTELEM must be 32 bits */
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jddctmgr.c
|
||||
*
|
||||
* Copyright (C) 1994-1996, Thomas G. Lane.
|
||||
* Modified 2002-2013 by Guido Vollbeding.
|
||||
* Modified 2002-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -46,8 +46,8 @@ typedef struct {
|
|||
|
||||
/* This array contains the IDCT method code that each multiplier table
|
||||
* is currently set up for, or -1 if it's not yet set up.
|
||||
* The actual multiplier tables are pointed to by dct_table in the
|
||||
* per-component comp_info structures.
|
||||
* The actual multiplier tables are pointed to by dct_table
|
||||
* in the per-component comp_info structures.
|
||||
*/
|
||||
int cur_method[MAX_COMPONENTS];
|
||||
} my_idct_controller;
|
||||
|
|
@ -68,18 +68,6 @@ typedef union {
|
|||
} multiplier_table;
|
||||
|
||||
|
||||
/* The current scaled-IDCT routines require ISLOW-style multiplier tables,
|
||||
* so be sure to compile that code if either ISLOW or SCALING is requested.
|
||||
*/
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#else
|
||||
#ifdef IDCT_SCALING_SUPPORTED
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Prepare for an output pass.
|
||||
* Here we select the proper IDCT routine for each component and build
|
||||
|
|
@ -101,6 +89,13 @@ start_pass (j_decompress_ptr cinfo)
|
|||
/* Select the proper IDCT routine for this component's scaling */
|
||||
switch ((compptr->DCT_h_scaled_size << 8) + compptr->DCT_v_scaled_size) {
|
||||
#ifdef IDCT_SCALING_SUPPORTED
|
||||
/*
|
||||
* The current scaled-IDCT routines require ISLOW-style multiplier tables,
|
||||
* so be sure to compile that code if either ISLOW or SCALING is requested.
|
||||
*/
|
||||
#ifndef PROVIDE_ISLOW_TABLES
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
case ((1 << 8) + 1):
|
||||
method_ptr = jpeg_idct_1x1;
|
||||
method = JDCT_ISLOW; /* jidctint uses islow-style table */
|
||||
|
|
@ -230,6 +225,9 @@ start_pass (j_decompress_ptr cinfo)
|
|||
switch (cinfo->dct_method) {
|
||||
#ifdef DCT_ISLOW_SUPPORTED
|
||||
case JDCT_ISLOW:
|
||||
#ifndef PROVIDE_ISLOW_TABLES
|
||||
#define PROVIDE_ISLOW_TABLES
|
||||
#endif
|
||||
method_ptr = jpeg_idct_islow;
|
||||
method = JDCT_ISLOW;
|
||||
break;
|
||||
|
|
@ -248,21 +246,19 @@ start_pass (j_decompress_ptr cinfo)
|
|||
#endif
|
||||
default:
|
||||
ERREXIT(cinfo, JERR_NOT_COMPILED);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ERREXIT2(cinfo, JERR_BAD_DCTSIZE,
|
||||
compptr->DCT_h_scaled_size, compptr->DCT_v_scaled_size);
|
||||
break;
|
||||
}
|
||||
idct->pub.inverse_DCT[ci] = method_ptr;
|
||||
/* Create multiplier table from quant table.
|
||||
* However, we can skip this if the component is uninteresting
|
||||
* or if we already built the table. Also, if no quant table
|
||||
* has yet been saved for the component, we leave the
|
||||
* multiplier table all-zero; we'll be reading zeroes from the
|
||||
* coefficient controller's buffer anyway.
|
||||
* multiplier table all-zero; we'll be reading zeroes
|
||||
* from the coefficient controller's buffer anyway.
|
||||
*/
|
||||
if (! compptr->component_needed || idct->cur_method[ci] == method)
|
||||
continue;
|
||||
|
|
@ -325,7 +321,8 @@ start_pass (j_decompress_ptr cinfo)
|
|||
* coefficients scaled by scalefactor[row]*scalefactor[col], where
|
||||
* scalefactor[0] = 1
|
||||
* scalefactor[k] = cos(k*PI/16) * sqrt(2) for k=1..7
|
||||
* We apply a further scale factor of 1/8.
|
||||
* We apply a further scale factor of 1/8
|
||||
* with adjustment if necessary.
|
||||
*/
|
||||
FLOAT_MULT_TYPE * fmtbl = (FLOAT_MULT_TYPE *) compptr->dct_table;
|
||||
int row, col;
|
||||
|
|
@ -333,13 +330,31 @@ start_pass (j_decompress_ptr cinfo)
|
|||
1.0, 1.387039845, 1.306562965, 1.175875602,
|
||||
1.0, 0.785694958, 0.541196100, 0.275899379
|
||||
};
|
||||
#if JPEG_DATA_PRECISION == BITS_IN_JSAMPLE
|
||||
|
||||
i = 0;
|
||||
for (row = 0; row < DCTSIZE; row++) {
|
||||
for (col = 0; col < DCTSIZE; col++) {
|
||||
fmtbl[i] = (FLOAT_MULT_TYPE)
|
||||
((double) qtbl->quantval[i] *
|
||||
aanscalefactor[row] * aanscalefactor[col] * 0.125);
|
||||
fmtbl[i] = (FLOAT_MULT_TYPE) ((double) qtbl->quantval[i] *
|
||||
aanscalefactor[row] * aanscalefactor[col] * 0.125);
|
||||
#else
|
||||
double extrafactor = 0.125;
|
||||
|
||||
/* Adjust extra factor */
|
||||
#if JPEG_DATA_PRECISION < BITS_IN_JSAMPLE
|
||||
i = BITS_IN_JSAMPLE - JPEG_DATA_PRECISION;
|
||||
do { extrafactor *= 2.0; } while (--i);
|
||||
#else
|
||||
i = JPEG_DATA_PRECISION - BITS_IN_JSAMPLE;
|
||||
do { extrafactor *= 0.5; } while (--i);
|
||||
#endif
|
||||
|
||||
i = 0;
|
||||
for (row = 0; row < DCTSIZE; row++) {
|
||||
for (col = 0; col < DCTSIZE; col++) {
|
||||
fmtbl[i] = (FLOAT_MULT_TYPE) ((double) qtbl->quantval[i] *
|
||||
aanscalefactor[row] * aanscalefactor[col] * extrafactor);
|
||||
#endif
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
|
@ -348,7 +363,6 @@ start_pass (j_decompress_ptr cinfo)
|
|||
#endif
|
||||
default:
|
||||
ERREXIT(cinfo, JERR_NOT_COMPILED);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -365,18 +379,16 @@ jinit_inverse_dct (j_decompress_ptr cinfo)
|
|||
int ci;
|
||||
jpeg_component_info *compptr;
|
||||
|
||||
idct = (my_idct_ptr)
|
||||
(*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE,
|
||||
SIZEOF(my_idct_controller));
|
||||
idct = (my_idct_ptr) (*cinfo->mem->alloc_small)
|
||||
((j_common_ptr) cinfo, JPOOL_IMAGE, SIZEOF(my_idct_controller));
|
||||
cinfo->idct = &idct->pub;
|
||||
idct->pub.start_pass = start_pass;
|
||||
|
||||
for (ci = 0, compptr = cinfo->comp_info; ci < cinfo->num_components;
|
||||
ci++, compptr++) {
|
||||
/* Allocate and pre-zero a multiplier table for each component */
|
||||
compptr->dct_table =
|
||||
(*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE,
|
||||
SIZEOF(multiplier_table));
|
||||
compptr->dct_table = (*cinfo->mem->alloc_small)
|
||||
((j_common_ptr) cinfo, JPOOL_IMAGE, SIZEOF(multiplier_table));
|
||||
MEMZERO(compptr->dct_table, SIZEOF(multiplier_table));
|
||||
/* Mark multiplier table not yet set up for any method */
|
||||
idct->cur_method[ci] = -1;
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jdmarker.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2009-2019 by Guido Vollbeding.
|
||||
* Modified 2009-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -664,7 +664,7 @@ get_lse (j_decompress_ptr cinfo)
|
|||
if (tmp != 0x0D) /* ID inverse transform specification */
|
||||
ERREXIT1(cinfo, JERR_UNKNOWN_MARKER, cinfo->unread_marker);
|
||||
INPUT_2BYTES(cinfo, tmp, return FALSE);
|
||||
if (tmp != MAXJSAMPLE) goto bad; /* MAXTRANS */
|
||||
cinfo->LSE_maxtrans = (UINT16) tmp; /* MAXTRANS */
|
||||
INPUT_BYTE(cinfo, tmp, return FALSE);
|
||||
if (tmp != 3) goto bad; /* Nt=3 */
|
||||
INPUT_BYTE(cinfo, cid, return FALSE);
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jdmaster.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2002-2020 by Guido Vollbeding.
|
||||
* Modified 2002-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -267,7 +267,7 @@ master_selection (j_decompress_ptr cinfo)
|
|||
JDIMENSION jd_samplesperrow;
|
||||
|
||||
/* For now, precision must match compiled-in value... */
|
||||
if (cinfo->data_precision != BITS_IN_JSAMPLE)
|
||||
if (cinfo->data_precision != JPEG_DATA_PRECISION)
|
||||
ERREXIT1(cinfo, JERR_BAD_PRECISION, cinfo->data_precision);
|
||||
|
||||
/* Initialize dimensions and other stuff */
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jerror.c
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2012-2015 by Guido Vollbeding.
|
||||
* Modified 2012-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -237,9 +237,18 @@ jpeg_std_error (struct jpeg_error_mgr * err)
|
|||
err->format_message = format_message;
|
||||
err->reset_error_mgr = reset_error_mgr;
|
||||
|
||||
err->msg_code = 0; /* may be useful as a flag for "no error" */
|
||||
err->msg_parm.i[0] = 0; /* initialize 8 int message parameters */
|
||||
err->msg_parm.i[1] = 0;
|
||||
err->msg_parm.i[2] = 0;
|
||||
err->msg_parm.i[3] = 0;
|
||||
err->msg_parm.i[4] = 0;
|
||||
err->msg_parm.i[5] = 0;
|
||||
err->msg_parm.i[6] = 0;
|
||||
err->msg_parm.i[7] = 0;
|
||||
|
||||
err->trace_level = 0; /* default = no tracing */
|
||||
err->num_warnings = 0; /* no warnings emitted yet */
|
||||
err->msg_code = 0; /* may be useful as a flag for "no error" */
|
||||
|
||||
/* Initialize message table pointers */
|
||||
err->jpeg_message_table = jpeg_std_message_table;
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jerror.h
|
||||
*
|
||||
* Copyright (C) 1994-1997, Thomas G. Lane.
|
||||
* Modified 1997-2018 by Guido Vollbeding.
|
||||
* Modified 1997-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -130,7 +130,7 @@ JMESSAGE(JTRC_ADOBE,
|
|||
"Adobe APP14 marker: version %d, flags 0x%04x 0x%04x, transform %d")
|
||||
JMESSAGE(JTRC_APP0, "Unknown APP0 marker (not JFIF), length %u")
|
||||
JMESSAGE(JTRC_APP14, "Unknown APP14 marker (not Adobe), length %u")
|
||||
JMESSAGE(JTRC_DAC, "Define Arithmetic Table 0x%02x: 0x%02x")
|
||||
JMESSAGE(JTRC_DAC, "Define Arithmetic Conditioning 0x%02x: 0x%02x")
|
||||
JMESSAGE(JTRC_DHT, "Define Huffman Table 0x%02x")
|
||||
JMESSAGE(JTRC_DQT, "Define Quantization Table %d precision %d")
|
||||
JMESSAGE(JTRC_DRI, "Define Restart Interval %u")
|
||||
|
|
@ -156,7 +156,7 @@ JMESSAGE(JTRC_SMOOTH_NOTIMPL,
|
|||
"Smoothing not supported with nonstandard sampling ratios")
|
||||
JMESSAGE(JTRC_SOF, "Start Of Frame 0x%02x: width=%u, height=%u, components=%d")
|
||||
JMESSAGE(JTRC_SOF_COMPONENT, " Component %d: %dhx%dv q=%d")
|
||||
JMESSAGE(JTRC_SOI, "Start of Image")
|
||||
JMESSAGE(JTRC_SOI, "Start Of Image")
|
||||
JMESSAGE(JTRC_SOS, "Start Of Scan: %d components")
|
||||
JMESSAGE(JTRC_SOS_COMPONENT, " Component %d: dc=%d ac=%d")
|
||||
JMESSAGE(JTRC_SOS_PARAMS, " Ss=%d, Se=%d, Ah=%d, Al=%d")
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -2,7 +2,7 @@
|
|||
* jidctfst.c
|
||||
*
|
||||
* Copyright (C) 1994-1998, Thomas G. Lane.
|
||||
* Modified 2015-2017 by Guido Vollbeding.
|
||||
* Modified 2015-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -15,11 +15,11 @@
|
|||
* a time). Direct algorithms are also available, but they are much more
|
||||
* complex and seem not to be any faster when reduced to code.
|
||||
*
|
||||
* This implementation is based on Arai, Agui, and Nakajima's algorithm for
|
||||
* scaled DCT. Their original paper (Trans. IEICE E-71(11):1095) is in
|
||||
* Japanese, but the algorithm is described in the Pennebaker & Mitchell
|
||||
* JPEG textbook (see REFERENCES section in file README). The following code
|
||||
* is based directly on figure 4-8 in P&M.
|
||||
* This implementation is based on Arai, Agui, and Nakajima's algorithm
|
||||
* for scaled DCT. Their original paper (Trans. IEICE E-71(11):1095) is
|
||||
* in Japanese, but the algorithm is described in the Pennebaker & Mitchell
|
||||
* JPEG textbook (see REFERENCES section in file README). The following
|
||||
* code is based directly on figure 4-8 in P&M.
|
||||
* While an 8-point DCT cannot be done in less than 11 multiplies, it is
|
||||
* possible to arrange the computation so that many of the multiplies are
|
||||
* simple scalings of the final outputs. These multiplies can then be
|
||||
|
|
@ -28,9 +28,9 @@
|
|||
* to be done in the DCT itself.
|
||||
* The primary disadvantage of this method is that with fixed-point math,
|
||||
* accuracy is lost due to imprecise representation of the scaled
|
||||
* quantization values. The smaller the quantization table entry, the less
|
||||
* precise the scaled value, so this implementation does worse with high-
|
||||
* quality-setting files than with low-quality ones.
|
||||
* quantization values. The smaller the quantization table entry,
|
||||
* the less precise the scaled value, so this implementation does
|
||||
* worse with high-quality-setting files than with low-quality ones.
|
||||
*/
|
||||
|
||||
#define JPEG_INTERNALS
|
||||
|
|
@ -55,17 +55,17 @@
|
|||
* (right shift) multiplication products as soon as they are formed,
|
||||
* rather than carrying additional fractional bits into subsequent additions.
|
||||
* This compromises accuracy slightly, but it lets us save a few shifts.
|
||||
* More importantly, 16-bit arithmetic is then adequate (for 8-bit samples)
|
||||
* everywhere except in the multiplications proper; this saves a good deal
|
||||
* of work on 16-bit-int machines.
|
||||
* More importantly, 16-bit arithmetic is then adequate (for up to 10-bit
|
||||
* data) everywhere except in the multiplications proper;
|
||||
* this saves a good deal of work on 16-bit-int machines.
|
||||
*
|
||||
* The dequantized coefficients are not integers because the AA&N scaling
|
||||
* factors have been incorporated. We represent them scaled up by PASS1_BITS,
|
||||
* so that the first and second IDCT rounds have the same input scaling.
|
||||
* For 8-bit JSAMPLEs, we choose IFAST_SCALE_BITS = PASS1_BITS so as to
|
||||
* For up to 10-bit data, we choose IFAST_SCALE_BITS = PASS1_BITS so as to
|
||||
* avoid a descaling shift; this compromises accuracy rather drastically
|
||||
* for small quantization table entries, but it saves a lot of shifts.
|
||||
* For 12-bit JSAMPLEs, there's no hope of using 16x16 multiplies anyway,
|
||||
* For higher bit depths, there's no hope of using 16x16 multiplies anyway,
|
||||
* so we use a much larger scaling factor to preserve accuracy.
|
||||
*
|
||||
* A final compromise is to represent the multiplicative constants to only
|
||||
|
|
@ -74,16 +74,20 @@
|
|||
* are fewer one-bits in the constants).
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
#if JPEG_DATA_PRECISION <= 10 && BITS_IN_JSAMPLE <= 13
|
||||
#define CONST_BITS 8
|
||||
#define PASS1_BITS 2
|
||||
#define PASS1_BITS (10 - JPEG_DATA_PRECISION)
|
||||
#define PASS2_BITS (13 - BITS_IN_JSAMPLE)
|
||||
#else
|
||||
#if JPEG_DATA_PRECISION <= 13 && BITS_IN_JSAMPLE <= 16
|
||||
#define CONST_BITS 8
|
||||
#define PASS1_BITS 1 /* lose a little precision to avoid overflow */
|
||||
#define PASS1_BITS (13 - JPEG_DATA_PRECISION)
|
||||
#define PASS2_BITS (16 - BITS_IN_JSAMPLE)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* Some C compilers fail to reduce "FIX(constant)" at compile time, thus
|
||||
* causing a lot of useless floating-point operations at run time.
|
||||
/* Some C compilers fail to reduce "FIX(constant)" at compile time,
|
||||
* thus causing a lot of useless floating-point operations at run time.
|
||||
* To get around this we use the following pre-calculated constants.
|
||||
* If you change CONST_BITS you may want to add appropriate values.
|
||||
* (With a reasonable C compiler, you can just rely on the FIX() macro...)
|
||||
|
|
@ -102,9 +106,9 @@
|
|||
#endif
|
||||
|
||||
|
||||
/* We can gain a little more speed, with a further compromise in accuracy,
|
||||
* by omitting the addition in a descaling shift. This yields an incorrectly
|
||||
* rounded result half the time...
|
||||
/* We can gain a little more speed, with a further compromise
|
||||
* in accuracy, by omitting the addition in a descaling shift.
|
||||
* This yields an incorrectly rounded result half the time...
|
||||
*/
|
||||
|
||||
#ifndef USE_ACCURATE_ROUNDING
|
||||
|
|
@ -113,20 +117,20 @@
|
|||
#endif
|
||||
|
||||
|
||||
/* Multiply a DCTELEM variable by an INT32 constant, and immediately
|
||||
* descale to yield a DCTELEM result.
|
||||
/* Multiply a DCTELEM variable by an INT32 constant,
|
||||
* and immediately descale to yield a DCTELEM result.
|
||||
*/
|
||||
|
||||
#define MULTIPLY(var,const) ((DCTELEM) DESCALE((var) * (const), CONST_BITS))
|
||||
|
||||
|
||||
/* Dequantize a coefficient by multiplying it by the multiplier-table
|
||||
* entry; produce a DCTELEM result. For 8-bit data a 16x16->16
|
||||
* multiplication will do. For 12-bit data, the multiplier table is
|
||||
* declared INT32, so a 32-bit multiply will be used.
|
||||
* entry; produce a DCTELEM result. For up to 10-bit data a 16x16->16
|
||||
* multiplication will do. For higher bit depths, the multiplier table
|
||||
* is declared INT32, so a 32-bit multiply will be used.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
#if JPEG_DATA_PRECISION <= 10 && BITS_IN_JSAMPLE <= 13
|
||||
#define DEQUANTIZE(coef,quantval) (((IFAST_MULT_TYPE) (coef)) * (quantval))
|
||||
#else
|
||||
#define DEQUANTIZE(coef,quantval) \
|
||||
|
|
@ -134,6 +138,16 @@
|
|||
#endif
|
||||
|
||||
|
||||
/* Final output conversion: scale down and range-limit. */
|
||||
|
||||
#if PASS2_BITS > 0
|
||||
#define FINAL_OUTPUT(x) \
|
||||
range_limit[(int) IRIGHT_SHIFT(x, PASS2_BITS) & RANGE_MASK]
|
||||
#else
|
||||
#define FINAL_OUTPUT(x) range_limit[(int) (x) & RANGE_MASK]
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Perform dequantization and inverse DCT on one block of coefficients.
|
||||
*
|
||||
|
|
@ -172,7 +186,7 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
* With typical images and quantization tables, half or more of the
|
||||
* column DCT calculations can be simplified this way.
|
||||
*/
|
||||
|
||||
|
||||
if (inptr[DCTSIZE*1] == 0 && inptr[DCTSIZE*2] == 0 &&
|
||||
inptr[DCTSIZE*3] == 0 && inptr[DCTSIZE*4] == 0 &&
|
||||
inptr[DCTSIZE*5] == 0 && inptr[DCTSIZE*6] == 0 &&
|
||||
|
|
@ -188,13 +202,13 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
wsptr[DCTSIZE*5] = dcval;
|
||||
wsptr[DCTSIZE*6] = dcval;
|
||||
wsptr[DCTSIZE*7] = dcval;
|
||||
|
||||
|
||||
inptr++; /* advance pointers to next column */
|
||||
quantptr++;
|
||||
wsptr++;
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
/* Even part */
|
||||
|
||||
tmp0 = DEQUANTIZE(inptr[DCTSIZE*0], quantptr[DCTSIZE*0]);
|
||||
|
|
@ -212,7 +226,7 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
tmp3 = tmp10 - tmp13;
|
||||
tmp1 = tmp11 + tmp12;
|
||||
tmp2 = tmp11 - tmp12;
|
||||
|
||||
|
||||
/* Odd part */
|
||||
|
||||
tmp4 = DEQUANTIZE(inptr[DCTSIZE*1], quantptr[DCTSIZE*1]);
|
||||
|
|
@ -249,10 +263,10 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
quantptr++;
|
||||
wsptr++;
|
||||
}
|
||||
|
||||
|
||||
/* Pass 2: process rows from work array, store into output array.
|
||||
* Note that we must descale the results by a factor of 8 == 2**3,
|
||||
* and also undo the PASS1_BITS scaling.
|
||||
* which is folded into the PASS2_BITS value.
|
||||
*/
|
||||
|
||||
wsptr = workspace;
|
||||
|
|
@ -260,9 +274,16 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
outptr = output_buf[ctr] + output_col;
|
||||
|
||||
/* Add range center and fudge factor for final descale and range-limit. */
|
||||
#if PASS2_BITS > 1
|
||||
z5 = (DCTELEM) wsptr[0] +
|
||||
((((DCTELEM) RANGE_CENTER) << (PASS1_BITS+3)) +
|
||||
(1 << (PASS1_BITS+2)));
|
||||
((((DCTELEM) RANGE_CENTER) << PASS2_BITS) + (1 << (PASS2_BITS-1)));
|
||||
#else
|
||||
#if PASS2_BITS > 0
|
||||
z5 = (DCTELEM) wsptr[0] + ((((DCTELEM) RANGE_CENTER) << 1) + 1);
|
||||
#else
|
||||
z5 = (DCTELEM) wsptr[0] + (DCTELEM) RANGE_CENTER;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* Rows of zeroes can be exploited in the same way as we did with columns.
|
||||
* However, the column calculation has created many nonzero AC terms, so
|
||||
|
|
@ -271,14 +292,13 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
* test takes more time than it's worth. In that case this section
|
||||
* may be commented out.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef NO_ZERO_ROW_TEST
|
||||
if (wsptr[1] == 0 && wsptr[2] == 0 && wsptr[3] == 0 && wsptr[4] == 0 &&
|
||||
wsptr[5] == 0 && wsptr[6] == 0 && wsptr[7] == 0) {
|
||||
/* AC terms all zero */
|
||||
JSAMPLE dcval = range_limit[(int) IRIGHT_SHIFT(z5, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
|
||||
JSAMPLE dcval = FINAL_OUTPUT(z5);
|
||||
|
||||
outptr[0] = dcval;
|
||||
outptr[1] = dcval;
|
||||
outptr[2] = dcval;
|
||||
|
|
@ -292,7 +312,7 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* Even part */
|
||||
|
||||
tmp10 = z5 + (DCTELEM) wsptr[4];
|
||||
|
|
@ -325,24 +345,16 @@ jpeg_idct_ifast (j_decompress_ptr cinfo, jpeg_component_info * compptr,
|
|||
tmp5 = tmp11 - tmp6;
|
||||
tmp4 = tmp10 - tmp5;
|
||||
|
||||
/* Final output stage: scale down by a factor of 8 and range-limit */
|
||||
/* Final output stage: scale down and range-limit */
|
||||
|
||||
outptr[0] = range_limit[(int) IRIGHT_SHIFT(tmp0 + tmp7, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[7] = range_limit[(int) IRIGHT_SHIFT(tmp0 - tmp7, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[1] = range_limit[(int) IRIGHT_SHIFT(tmp1 + tmp6, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[6] = range_limit[(int) IRIGHT_SHIFT(tmp1 - tmp6, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[2] = range_limit[(int) IRIGHT_SHIFT(tmp2 + tmp5, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[5] = range_limit[(int) IRIGHT_SHIFT(tmp2 - tmp5, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[3] = range_limit[(int) IRIGHT_SHIFT(tmp3 + tmp4, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[4] = range_limit[(int) IRIGHT_SHIFT(tmp3 - tmp4, PASS1_BITS+3)
|
||||
& RANGE_MASK];
|
||||
outptr[0] = FINAL_OUTPUT(tmp0 + tmp7);
|
||||
outptr[7] = FINAL_OUTPUT(tmp0 - tmp7);
|
||||
outptr[1] = FINAL_OUTPUT(tmp1 + tmp6);
|
||||
outptr[6] = FINAL_OUTPUT(tmp1 - tmp6);
|
||||
outptr[2] = FINAL_OUTPUT(tmp2 + tmp5);
|
||||
outptr[5] = FINAL_OUTPUT(tmp2 - tmp5);
|
||||
outptr[3] = FINAL_OUTPUT(tmp3 + tmp4);
|
||||
outptr[4] = FINAL_OUTPUT(tmp3 - tmp4);
|
||||
|
||||
wsptr += DCTSIZE; /* advance pointer to next row */
|
||||
}
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -2,7 +2,7 @@
|
|||
* jmorecfg.h
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 1997-2022 by Guido Vollbeding.
|
||||
* Modified 1997-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -12,26 +12,62 @@
|
|||
*/
|
||||
|
||||
|
||||
#define JPEG_DATA_PRECISION 8 /* see table below */
|
||||
#define BITS_IN_JSAMPLE JPEG_DATA_PRECISION /* see table below */
|
||||
/*
|
||||
* Define BITS_IN_JSAMPLE as either
|
||||
* 8 for 8-bit sample values (the usual setting)
|
||||
* 9 for 9-bit sample values
|
||||
* 10 for 10-bit sample values
|
||||
* 11 for 11-bit sample values
|
||||
* 12 for 12-bit sample values
|
||||
* Only 8, 9, 10, 11, and 12 bits sample data precision are supported for
|
||||
* full-feature DCT processing. Further depths up to 16-bit may be added
|
||||
* later for the lossless modes of operation.
|
||||
* Run-time selection and conversion of data precision will be added later
|
||||
* and are currently not supported, sorry.
|
||||
* Most useful alternative for "HDR" (High Dynamic Range) application
|
||||
* with backward compatibility for file interchange (see table below;
|
||||
* move comment marks for selection):
|
||||
#define BITS_IN_JSAMPLE 10
|
||||
*/
|
||||
/* For still higher demands (see table below):
|
||||
#define BITS_IN_JSAMPLE 11
|
||||
*/
|
||||
/* or
|
||||
#define BITS_IN_JSAMPLE 12
|
||||
*/
|
||||
|
||||
/* | BITS_IN_JSAMPLE
|
||||
* JPEG_DATA_PRECISION | read / write with full DCT up to lossless operation
|
||||
* | exceptions see below
|
||||
* -------------------------------------------------------------------------------
|
||||
* {[_8_]} | _8_ <9> <10> <11>* <12>~
|
||||
* [_9_] | <8> _9_ <10> <11> <12>*
|
||||
* [_10_] | <8> <9> _10_ <11> <12> 13 *
|
||||
* _11_ | <8> <9> <10> _11_ <12> 13 14 *
|
||||
* _12_ | <8> <9> <10> <11> _12_ 13 14 15 *
|
||||
* 13 | 8 9 10 11 12 13 14 15 16 *
|
||||
*
|
||||
* _x_ currently and previously implemented - default configuration
|
||||
* <x> newly implemented
|
||||
* {x} current standard for file interchange - backward compatible
|
||||
* [x] next standard for file interchange - common DCT implementation category
|
||||
* * does not support GCC lossless (GCbCr lossless - requires 1 extra bit)
|
||||
* ~ 1 bit precision loss - effective 11 bits precision (lossy)
|
||||
*
|
||||
* Since the DCT coefficients are 3 bits larger than sample values with normal DCT
|
||||
* processing, it is possible to support sample values with up to 3 more bits than
|
||||
* the nominal JPEG data precision parameter by adapted DCT processing with up to
|
||||
* lossless operation. The generated JPEG files are fully interchangeable for the
|
||||
* same JPEG data precision parameter. Another BITS_IN_JSAMPLE setting will just
|
||||
* reconstruct an image with corresponding precision.
|
||||
*
|
||||
* A special case for JPEG data precision 8 with 12-bit sample size (4 more bits)
|
||||
* is provided so that all previously available sample formats are now supported
|
||||
* for file interchange with backward compatibility.
|
||||
* If full-feature DCT up to lossless operation with up to 12-bit sample size is
|
||||
* required, it is recommended to select JPEG data precision 10, because it falls
|
||||
* in the same DCT implementation category with 8 and 9 which may be commonly
|
||||
* supported at run-time as the next standard for file interchange.
|
||||
*
|
||||
* Remaining bit depths and variability at run-time may be added later and
|
||||
* are currently not supported, sorry.
|
||||
* Exception: The transcoding part (jpegtran) supports all settings in a
|
||||
* single instance, since it operates on the level of DCT coefficients and
|
||||
* not sample values. The DCT coefficients are of the same type (16 bits)
|
||||
* in all cases (see below).
|
||||
*/
|
||||
|
||||
#define BITS_IN_JSAMPLE 8 /* use 8, 9, 10, 11, or 12 */
|
||||
|
||||
|
||||
/*
|
||||
* Maximum number of components (color channels) allowed in JPEG image.
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* jpeglib.h
|
||||
*
|
||||
* Copyright (C) 1991-1998, Thomas G. Lane.
|
||||
* Modified 2002-2022 by Guido Vollbeding.
|
||||
* Modified 2002-2025 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -34,12 +34,12 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
/* Version IDs for the JPEG library.
|
||||
* Might be useful for tests like "#if JPEG_LIB_VERSION >= 90".
|
||||
* Might be useful for tests like "#if JPEG_LIB_VERSION >= 100".
|
||||
*/
|
||||
|
||||
#define JPEG_LIB_VERSION 90 /* Compatibility version 9.0 */
|
||||
#define JPEG_LIB_VERSION_MAJOR 9
|
||||
#define JPEG_LIB_VERSION_MINOR 6
|
||||
#define JPEG_LIB_VERSION 100 /* Compatibility version 10.0 */
|
||||
#define JPEG_LIB_VERSION_MAJOR 10
|
||||
#define JPEG_LIB_VERSION_MINOR 0
|
||||
|
||||
|
||||
/* Various constants determining the sizes of things.
|
||||
|
|
@ -384,8 +384,9 @@ struct jpeg_compress_struct {
|
|||
UINT16 Y_density; /* Vertical pixel density */
|
||||
boolean write_Adobe_marker; /* should an Adobe marker be written? */
|
||||
|
||||
J_COLOR_TRANSFORM color_transform;
|
||||
/* Color transform identifier, writes LSE marker if nonzero */
|
||||
J_COLOR_TRANSFORM color_transform;
|
||||
UINT16 LSE_maxtrans; /* LSE MAXTRANS value, usually = MAXJSAMPLE */
|
||||
|
||||
/* State variable: index of next scanline to be written to
|
||||
* jpeg_write_scanlines(). Application may use this to control its
|
||||
|
|
@ -606,8 +607,9 @@ struct jpeg_decompress_struct {
|
|||
boolean saw_Adobe_marker; /* TRUE iff an Adobe APP14 marker was found */
|
||||
UINT8 Adobe_transform; /* Color transform code from Adobe marker */
|
||||
|
||||
J_COLOR_TRANSFORM color_transform;
|
||||
/* Color transform identifier derived from LSE marker, otherwise zero */
|
||||
J_COLOR_TRANSFORM color_transform;
|
||||
UINT16 LSE_maxtrans; /* LSE MAXTRANS value, usually = MAXJSAMPLE */
|
||||
|
||||
boolean CCIR601_sampling; /* TRUE=first samples are cosited */
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* jversion.h
|
||||
*
|
||||
* Copyright (C) 1991-2024, Thomas G. Lane, Guido Vollbeding.
|
||||
* Copyright (C) 1991-2026, Thomas G. Lane, Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -9,6 +9,6 @@
|
|||
*/
|
||||
|
||||
|
||||
#define JVERSION "9f 14-Jan-2024"
|
||||
#define JVERSION "10 25-Jan-2026"
|
||||
|
||||
#define JCOPYRIGHT "Copyright (C) 2024, Thomas G. Lane, Guido Vollbeding"
|
||||
#define JCOPYRIGHT "Copyright (C) 2026, Thomas G. Lane, Guido Vollbeding"
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* rdbmp.c
|
||||
*
|
||||
* Copyright (C) 1994-1996, Thomas G. Lane.
|
||||
* Modified 2009-2019 by Guido Vollbeding.
|
||||
* Modified 2009-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -27,6 +27,11 @@
|
|||
#ifdef BMP_SUPPORTED
|
||||
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
Sorry, this code only copes with 8-bit JSAMPLEs. /* deliberate syntax err */
|
||||
#endif
|
||||
|
||||
|
||||
/* Macros to deal with unsigned chars as efficiently as compiler allows */
|
||||
|
||||
#ifdef HAVE_UNSIGNED_CHAR
|
||||
|
|
@ -429,7 +434,7 @@ start_input_bmp (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
|
||||
cinfo->in_color_space = JCS_RGB;
|
||||
cinfo->input_components = 3;
|
||||
cinfo->data_precision = 8;
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
cinfo->image_width = (JDIMENSION) biWidth;
|
||||
cinfo->image_height = (JDIMENSION) biHeight;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* rdgif.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2019-2020 by Guido Vollbeding.
|
||||
* Modified 2019-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -522,7 +522,7 @@ start_input_gif (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
/* Return info about the image. */
|
||||
cinfo->in_color_space = JCS_RGB;
|
||||
cinfo->input_components = NUMCOLORS;
|
||||
cinfo->data_precision = BITS_IN_JSAMPLE; /* we always rescale data to this */
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
cinfo->image_width = width;
|
||||
cinfo->image_height = height;
|
||||
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* rdppm.c
|
||||
*
|
||||
* Copyright (C) 1991-1997, Thomas G. Lane.
|
||||
* Modified 2009-2020 by Bill Allombert, Guido Vollbeding.
|
||||
* Modified 2009-2026 by Bill Allombert, Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -371,7 +371,7 @@ start_input_ppm (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
((long) maxval >> 16)) /* support max 16-bit (2-byte) sample values */
|
||||
ERREXIT(cinfo, JERR_PPM_OUTOFRANGE);
|
||||
|
||||
cinfo->data_precision = BITS_IN_JSAMPLE; /* we always rescale data to this */
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
cinfo->image_width = (JDIMENSION) w;
|
||||
cinfo->image_height = (JDIMENSION) h;
|
||||
source->maxval = maxval;
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* rdrle.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2019 by Guido Vollbeding.
|
||||
* Modified 2019-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -30,7 +30,8 @@
|
|||
|
||||
/*
|
||||
* We assume that JSAMPLE has the same representation as rle_pixel,
|
||||
* to wit, "unsigned char". Hence we can't cope with 12- or 16-bit samples.
|
||||
* to wit, "unsigned char".
|
||||
* Hence we can't cope with larger than 8-bit samples.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
|
|
@ -107,15 +108,15 @@ start_input_rle (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
}
|
||||
|
||||
/* Figure out what we have, set private vars and return values accordingly */
|
||||
|
||||
|
||||
width = source->header.xmax - source->header.xmin + 1;
|
||||
height = source->header.ymax - source->header.ymin + 1;
|
||||
source->header.xmin = 0; /* realign horizontally */
|
||||
source->header.xmax = width-1;
|
||||
|
||||
cinfo->image_width = width;
|
||||
cinfo->image_height = height;
|
||||
cinfo->data_precision = 8; /* we can only handle 8 bit data */
|
||||
cinfo->image_width = width;
|
||||
cinfo->image_height = height;
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
|
||||
if (source->header.ncolors == 1 && source->header.ncmap == 0) {
|
||||
source->visual = GRAYSCALE;
|
||||
|
|
@ -137,7 +138,7 @@ start_input_rle (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
TRACEMS2(cinfo, 1, JTRC_RLE, width, height);
|
||||
} else
|
||||
ERREXIT(cinfo, JERR_RLE_UNSUPPORTED);
|
||||
|
||||
|
||||
if (source->visual == GRAYSCALE || source->visual == MAPPEDGRAY) {
|
||||
cinfo->in_color_space = JCS_GRAYSCALE;
|
||||
cinfo->input_components = 1;
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* rdtarga.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2017-2019 by Guido Vollbeding.
|
||||
* Modified 2017-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -23,6 +23,11 @@
|
|||
#ifdef TARGA_SUPPORTED
|
||||
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
Sorry, this code only copes with 8-bit JSAMPLEs. /* deliberate syntax err */
|
||||
#endif
|
||||
|
||||
|
||||
/* Macros to deal with unsigned chars as efficiently as compiler allows */
|
||||
|
||||
#ifdef HAVE_UNSIGNED_CHAR
|
||||
|
|
@ -460,7 +465,7 @@ start_input_tga (j_compress_ptr cinfo, cjpeg_source_ptr sinfo)
|
|||
}
|
||||
|
||||
cinfo->input_components = components;
|
||||
cinfo->data_precision = 8;
|
||||
cinfo->data_precision = JPEG_DATA_PRECISION;
|
||||
cinfo->image_width = width;
|
||||
cinfo->image_height = height;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* transupp.c
|
||||
*
|
||||
* Copyright (C) 1997-2023, Thomas G. Lane, Guido Vollbeding.
|
||||
* Copyright (C) 1997-2025, Thomas G. Lane, Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -268,10 +268,16 @@ adjust_quant(j_decompress_ptr srcinfo, jvirt_barray_ptr *src_coef_arrays,
|
|||
|
||||
for (ci = 0; ci < dstinfo->num_components &&
|
||||
ci < dropinfo->num_components; ci++) {
|
||||
compptr1 = srcinfo->comp_info + ci;
|
||||
compptr2 = dropinfo->comp_info + ci;
|
||||
qtblptr1 = compptr1->quant_table;
|
||||
qtblptr2 = compptr2->quant_table;
|
||||
if (qtblptr2 == NULL) continue;
|
||||
compptr1 = srcinfo->comp_info + ci;
|
||||
qtblptr1 = compptr1->quant_table;
|
||||
if (qtblptr1 == NULL) {
|
||||
MEMCOPY(dstinfo->quant_tbl_ptrs[compptr1->quant_tbl_no],
|
||||
qtblptr2, SIZEOF(JQUANT_TBL));
|
||||
continue;
|
||||
}
|
||||
for (k = 0; k < DCTSIZE2; k++) {
|
||||
if (qtblptr1->quantval[k] != qtblptr2->quantval[k]) {
|
||||
if (trim)
|
||||
|
|
@ -799,6 +805,92 @@ do_reflect (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
}
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
do_negate_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
||||
JDIMENSION x_crop_offset,
|
||||
jvirt_barray_ptr *src_coef_arrays)
|
||||
/* Negation; done in-place, so no separate dest array is required.
|
||||
* NB: this only works when y_crop_offset is zero.
|
||||
*/
|
||||
{
|
||||
JDIMENSION blk_x, blk_y, x_crop_blocks;
|
||||
int ci, k, offset_y;
|
||||
JBLOCKARRAY buffer;
|
||||
JBLOCKROW src_row_ptr, dst_row_ptr;
|
||||
JCOEFPTR src_ptr, dst_ptr;
|
||||
jpeg_component_info *compptr;
|
||||
|
||||
for (ci = 0; ci < dstinfo->num_components; ci++) {
|
||||
compptr = dstinfo->comp_info + ci;
|
||||
x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
|
||||
for (blk_y = 0; blk_y < compptr->height_in_blocks;
|
||||
blk_y += compptr->v_samp_factor) {
|
||||
buffer = (*srcinfo->mem->access_virt_barray)
|
||||
((j_common_ptr) srcinfo, src_coef_arrays[ci], blk_y,
|
||||
(JDIMENSION) compptr->v_samp_factor, TRUE);
|
||||
for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
|
||||
dst_row_ptr = buffer[offset_y];
|
||||
src_row_ptr = dst_row_ptr + x_crop_blocks;
|
||||
for (blk_x = 0; blk_x < compptr->width_in_blocks; blk_x++) {
|
||||
dst_ptr = dst_row_ptr[blk_x];
|
||||
src_ptr = src_row_ptr[blk_x];
|
||||
for (k = 0; k < DCTSIZE2; k++) {
|
||||
*dst_ptr++ = - *src_ptr++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
do_negate (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
||||
JDIMENSION x_crop_offset, JDIMENSION y_crop_offset,
|
||||
jvirt_barray_ptr *src_coef_arrays,
|
||||
jvirt_barray_ptr *dst_coef_arrays)
|
||||
/* Negation in general cropping case */
|
||||
{
|
||||
JDIMENSION dst_blk_x, dst_blk_y, x_crop_blocks, y_crop_blocks;
|
||||
int ci, k, offset_y;
|
||||
JBLOCKARRAY src_buffer, dst_buffer;
|
||||
JBLOCKROW src_row_ptr, dst_row_ptr;
|
||||
JCOEFPTR src_ptr, dst_ptr;
|
||||
jpeg_component_info *compptr;
|
||||
|
||||
/* Here we must output into a separate array because we can't
|
||||
* touch different rows of a single virtual array simultaneously.
|
||||
* Otherwise, this is essentially the same as the routine above.
|
||||
*/
|
||||
for (ci = 0; ci < dstinfo->num_components; ci++) {
|
||||
compptr = dstinfo->comp_info + ci;
|
||||
x_crop_blocks = x_crop_offset * compptr->h_samp_factor;
|
||||
y_crop_blocks = y_crop_offset * compptr->v_samp_factor;
|
||||
for (dst_blk_y = 0; dst_blk_y < compptr->height_in_blocks;
|
||||
dst_blk_y += compptr->v_samp_factor) {
|
||||
dst_buffer = (*srcinfo->mem->access_virt_barray)
|
||||
((j_common_ptr) srcinfo, dst_coef_arrays[ci], dst_blk_y,
|
||||
(JDIMENSION) compptr->v_samp_factor, TRUE);
|
||||
src_buffer = (*srcinfo->mem->access_virt_barray)
|
||||
((j_common_ptr) srcinfo, src_coef_arrays[ci],
|
||||
dst_blk_y + y_crop_blocks,
|
||||
(JDIMENSION) compptr->v_samp_factor, FALSE);
|
||||
for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
|
||||
dst_row_ptr = dst_buffer[offset_y];
|
||||
src_row_ptr = src_buffer[offset_y] + x_crop_blocks;
|
||||
for (dst_blk_x = 0; dst_blk_x < compptr->width_in_blocks; dst_blk_x++) {
|
||||
dst_ptr = dst_row_ptr[dst_blk_x];
|
||||
src_ptr = src_row_ptr[dst_blk_x];
|
||||
for (k = 0; k < DCTSIZE2; k++) {
|
||||
*dst_ptr++ = - *src_ptr++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
LOCAL(void)
|
||||
do_flip_h_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
||||
JDIMENSION x_crop_offset,
|
||||
|
|
@ -810,6 +902,7 @@ do_flip_h_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
JDIMENSION MCU_cols, comp_width, blk_x, blk_y, x_crop_blocks;
|
||||
int ci, k, offset_y;
|
||||
JBLOCKARRAY buffer;
|
||||
JBLOCKROW src_row_ptr, dst_row_ptr;
|
||||
JCOEFPTR ptr1, ptr2;
|
||||
JCOEF temp1, temp2;
|
||||
jpeg_component_info *compptr;
|
||||
|
|
@ -832,10 +925,11 @@ do_flip_h_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
((j_common_ptr) srcinfo, src_coef_arrays[ci], blk_y,
|
||||
(JDIMENSION) compptr->v_samp_factor, TRUE);
|
||||
for (offset_y = 0; offset_y < compptr->v_samp_factor; offset_y++) {
|
||||
dst_row_ptr = buffer[offset_y];
|
||||
/* Do the mirroring */
|
||||
for (blk_x = 0; blk_x * 2 < comp_width; blk_x++) {
|
||||
ptr1 = buffer[offset_y][blk_x];
|
||||
ptr2 = buffer[offset_y][comp_width - blk_x - 1];
|
||||
ptr1 = dst_row_ptr[blk_x];
|
||||
ptr2 = dst_row_ptr[comp_width - blk_x - 1];
|
||||
/* this unrolled loop doesn't need to know which row it's on... */
|
||||
for (k = 0; k < DCTSIZE2; k += 2) {
|
||||
temp1 = *ptr1; /* swap even column */
|
||||
|
|
@ -854,9 +948,10 @@ do_flip_h_no_crop (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
* depends on memcpy(), whose behavior is unspecified for overlapping
|
||||
* source and destination areas. Sigh.
|
||||
*/
|
||||
src_row_ptr = dst_row_ptr + x_crop_blocks;
|
||||
for (blk_x = 0; blk_x < compptr->width_in_blocks; blk_x++) {
|
||||
jcopy_block_row(buffer[offset_y] + blk_x + x_crop_blocks,
|
||||
buffer[offset_y] + blk_x,
|
||||
jcopy_block_row(src_row_ptr + blk_x,
|
||||
dst_row_ptr + blk_x,
|
||||
(JDIMENSION) 1);
|
||||
}
|
||||
}
|
||||
|
|
@ -881,9 +976,9 @@ do_flip_h (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
JCOEFPTR src_ptr, dst_ptr;
|
||||
jpeg_component_info *compptr;
|
||||
|
||||
/* Here we must output into a separate array because we can't touch
|
||||
* different rows of a single virtual array simultaneously. Otherwise,
|
||||
* this is essentially the same as the routine above.
|
||||
/* Here we must output into a separate array because we can't
|
||||
* touch different rows of a single virtual array simultaneously.
|
||||
* Otherwise, this is essentially the same as the routine above.
|
||||
*/
|
||||
MCU_cols = srcinfo->output_width /
|
||||
(dstinfo->max_h_samp_factor * dstinfo->min_DCT_h_scaled_size);
|
||||
|
|
@ -944,10 +1039,10 @@ do_flip_v (j_decompress_ptr srcinfo, j_compress_ptr dstinfo,
|
|||
jpeg_component_info *compptr;
|
||||
|
||||
/* We output into a separate array because we can't touch different
|
||||
* rows of the source virtual array simultaneously. Otherwise, this
|
||||
* is a pretty straightforward analog of horizontal flip.
|
||||
* Within a DCT block, vertical mirroring is done by changing the signs
|
||||
* of odd-numbered rows.
|
||||
* rows of the source virtual array simultaneously. Otherwise,
|
||||
* this is a pretty straightforward analog of horizontal flip.
|
||||
* Within a DCT block, vertical mirroring is done by changing
|
||||
* the signs of odd-numbered rows.
|
||||
* Partial iMCUs at the bottom edge are copied verbatim.
|
||||
*/
|
||||
MCU_rows = srcinfo->output_height /
|
||||
|
|
@ -1858,6 +1953,11 @@ jtransform_request_workspace (j_decompress_ptr srcinfo,
|
|||
drop_request_from_src(info->drop_ptr, srcinfo);
|
||||
#endif
|
||||
break;
|
||||
case JXFORM_NEGATE:
|
||||
if (info->y_crop_offset != 0)
|
||||
need_workspace = TRUE;
|
||||
/* do_negate_no_crop doesn't need a workspace array */
|
||||
break;
|
||||
}
|
||||
|
||||
/* Allocate workspace if needed.
|
||||
|
|
@ -2299,6 +2399,14 @@ jtransform_execute_transform (j_decompress_ptr srcinfo,
|
|||
src_coef_arrays, info->drop_ptr, info->drop_coef_arrays,
|
||||
info->drop_width, info->drop_height);
|
||||
break;
|
||||
case JXFORM_NEGATE:
|
||||
if (info->y_crop_offset != 0)
|
||||
do_negate(srcinfo, dstinfo, info->x_crop_offset, info->y_crop_offset,
|
||||
src_coef_arrays, dst_coef_arrays);
|
||||
else
|
||||
do_negate_no_crop(srcinfo, dstinfo, info->x_crop_offset,
|
||||
src_coef_arrays);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* transupp.h
|
||||
*
|
||||
* Copyright (C) 1997-2019, Thomas G. Lane, Guido Vollbeding.
|
||||
* Copyright (C) 1997-2025, Thomas G. Lane, Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -67,6 +67,9 @@
|
|||
* otherwise quantization adaption occurs. The trim option can be used with
|
||||
* the drop option to requantize the drop file to the source file.
|
||||
*
|
||||
* A lossless negation function can be used in case an image file contains
|
||||
* inverted component data.
|
||||
*
|
||||
* We also provide a lossless-resize option, which is kind of a lossless-crop
|
||||
* operation in the DCT coefficient block domain - it discards higher-order
|
||||
* coefficients and losslessly preserves lower-order coefficients of a
|
||||
|
|
@ -112,7 +115,8 @@ typedef enum {
|
|||
JXFORM_ROT_180, /* 180-degree rotation */
|
||||
JXFORM_ROT_270, /* 270-degree clockwise (or 90 ccw) */
|
||||
JXFORM_WIPE, /* wipe */
|
||||
JXFORM_DROP /* drop */
|
||||
JXFORM_DROP, /* drop */
|
||||
JXFORM_NEGATE /* negate */
|
||||
} JXFORM_CODE;
|
||||
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* wrbmp.c
|
||||
*
|
||||
* Copyright (C) 1994-1996, Thomas G. Lane.
|
||||
* Modified 2017-2019 by Guido Vollbeding.
|
||||
* Modified 2017-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -24,8 +24,8 @@
|
|||
|
||||
|
||||
/*
|
||||
* To support 12-bit JPEG data, we'd have to scale output down to 8 bits.
|
||||
* This is not yet implemented.
|
||||
* To support larger than 8-bit sample data, we'd have to scale output
|
||||
* down to 8 bits. This is not yet implemented.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* wrgif.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2015-2019 by Guido Vollbeding.
|
||||
* Modified 2015-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -527,8 +527,8 @@ jinit_write_gif (j_decompress_ptr cinfo, boolean is_lzw)
|
|||
cinfo->out_color_space != JCS_RGB)
|
||||
ERREXIT(cinfo, JERR_GIF_COLORSPACE);
|
||||
|
||||
/* Force quantization if color or if > 8 bits input */
|
||||
if (cinfo->out_color_space != JCS_GRAYSCALE || cinfo->data_precision > 8) {
|
||||
/* Force quantization if larger than 8-bit samples or if color */
|
||||
if (BITS_IN_JSAMPLE > 8 || cinfo->out_color_space != JCS_GRAYSCALE) {
|
||||
/* Force quantization to at most 256 colors */
|
||||
cinfo->quantize_colors = TRUE;
|
||||
if (cinfo->desired_number_of_colors > 256)
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* wrppm.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2009-2020 by Guido Vollbeding.
|
||||
* Modified 2009-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -22,13 +22,13 @@
|
|||
|
||||
|
||||
/*
|
||||
* For 12-bit JPEG data, we either downscale the values to 8 bits
|
||||
* (to write standard byte-per-sample PPM/PGM files), or output
|
||||
* nonstandard word-per-sample PPM/PGM files. Downscaling is done
|
||||
* if PPM_NORAWWORD is defined (this can be done in the Makefile
|
||||
* or in jconfig.h).
|
||||
* (When the core library supports data precision reduction, a cleaner
|
||||
* implementation will be to ask for that instead.)
|
||||
* For larger than 8-bit sample data, we either downscale the values
|
||||
* to 8 bits (to write standard byte-per-sample PPM/PGM files),
|
||||
* or output nonstandard word-per-sample PPM/PGM files.
|
||||
* Downscaling is done if PPM_NORAWWORD is defined (this can be done
|
||||
* in the Makefile or in jconfig.h).
|
||||
* (When the core library supports data precision reduction,
|
||||
* a cleaner implementation will be to ask for that instead.)
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE == 8
|
||||
|
|
@ -98,8 +98,9 @@ put_pixel_rows (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo,
|
|||
|
||||
|
||||
/*
|
||||
* This code is used when we have to copy the data and apply a pixel
|
||||
* format translation. Typically this only happens in 12-bit mode.
|
||||
* This code is used when we have to copy the data and apply
|
||||
* a pixel format translation.
|
||||
* Typically this only happens in larger than 8-bit mode.
|
||||
*/
|
||||
|
||||
METHODDEF(void)
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* wrrle.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2017-2019 by Guido Vollbeding.
|
||||
* Modified 2017-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -27,7 +27,8 @@
|
|||
|
||||
/*
|
||||
* We assume that JSAMPLE has the same representation as rle_pixel,
|
||||
* to wit, "unsigned char". Hence we can't cope with 12- or 16-bit samples.
|
||||
* to wit, "unsigned char".
|
||||
* Hence we can't cope with larger than 8-bit samples.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
* wrtarga.c
|
||||
*
|
||||
* Copyright (C) 1991-1996, Thomas G. Lane.
|
||||
* Modified 2015-2019 by Guido Vollbeding.
|
||||
* Modified 2015-2026 by Guido Vollbeding.
|
||||
* This file is part of the Independent JPEG Group's software.
|
||||
* For conditions of distribution and use, see the accompanying README file.
|
||||
*
|
||||
|
|
@ -21,8 +21,8 @@
|
|||
|
||||
|
||||
/*
|
||||
* To support 12-bit JPEG data, we'd have to scale output down to 8 bits.
|
||||
* This is not yet implemented.
|
||||
* To support larger than 8-bit sample data, we'd have to scale output
|
||||
* down to 8 bits. This is not yet implemented.
|
||||
*/
|
||||
|
||||
#if BITS_IN_JSAMPLE != 8
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue