提交 6547cb86 编写于 作者: X xdono

Merge

......@@ -339,8 +339,7 @@ ifeq ($(PLATFORM), windows)
FONTCONFIGS_SRC = $(PLATFORM_SRC)/classes/sun/awt/windows
_FONTCONFIGS = \
fontconfig.properties \
fontconfig.98.properties
fontconfig.properties
FONTCONFIGS_SRC_PREFIX =
......
......@@ -304,12 +304,14 @@ SUNWprivate_1.1 {
Java_java_awt_FileDialog_initIDs;
Java_sun_awt_X11_XWindow_initIDs;
Java_sun_java2d_opengl_OGLContext_getOGLIdString;
Java_sun_java2d_opengl_OGLMaskFill_maskFill;
Java_sun_java2d_opengl_OGLRenderer_drawPoly;
Java_sun_java2d_opengl_OGLRenderQueue_flushBuffer;
Java_sun_java2d_opengl_OGLSurfaceData_initTexture;
Java_sun_java2d_opengl_OGLSurfaceData_initFBObject;
Java_sun_java2d_opengl_OGLSurfaceData_initFlipBackbuffer;
Java_sun_java2d_opengl_OGLSurfaceData_getTextureID;
Java_sun_java2d_opengl_OGLSurfaceData_getTextureTarget;
Java_sun_java2d_opengl_OGLTextRenderer_drawGlyphList;
Java_sun_java2d_opengl_GLXGraphicsConfig_getGLXConfigInfo;
......
......@@ -153,7 +153,7 @@ public class GIFImageMetadata extends GIFMetadata {
node.setAttribute("imageWidth", Integer.toString(imageWidth));
node.setAttribute("imageHeight", Integer.toString(imageHeight));
node.setAttribute("interlaceFlag",
interlaceFlag ? "true" : "false");
interlaceFlag ? "TRUE" : "FALSE");
root.appendChild(node);
// Local color table
......@@ -185,9 +185,9 @@ public class GIFImageMetadata extends GIFMetadata {
node.setAttribute("disposalMethod",
disposalMethodNames[disposalMethod]);
node.setAttribute("userInputFlag",
userInputFlag ? "true" : "false");
userInputFlag ? "TRUE" : "FALSE");
node.setAttribute("transparentColorFlag",
transparentColorFlag ? "true" : "false");
transparentColorFlag ? "TRUE" : "FALSE");
node.setAttribute("delayTime",
Integer.toString(delayTime));
node.setAttribute("transparentColorIndex",
......
......@@ -55,6 +55,7 @@ import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import com.sun.imageio.plugins.common.LZWCompressor;
import com.sun.imageio.plugins.common.PaletteBuilder;
import sun.awt.image.ByteComponentRaster;
public class GIFImageWriter extends ImageWriter {
private static final boolean DEBUG = false; // XXX false for release!
......@@ -905,10 +906,18 @@ public class GIFImageWriter extends ImageWriter {
LZWCompressor compressor =
new LZWCompressor(stream, initCodeSize, false);
/* At this moment we know that input image is indexed image.
* We can directly copy data iff:
* - no subsampling required (periodX = 1, periodY = 0)
* - we can access data directly (image is non-tiled,
* i.e. image data are in single block)
* - we can calculate offset in data buffer (next 3 lines)
*/
boolean isOptimizedCase =
periodX == 1 && periodY == 1 &&
sampleModel instanceof ComponentSampleModel &&
image.getNumXTiles() == 1 && image.getNumYTiles() == 1 &&
sampleModel instanceof ComponentSampleModel &&
image.getTile(0, 0) instanceof ByteComponentRaster &&
image.getTile(0, 0).getDataBuffer() instanceof DataBufferByte;
int numRowsWritten = 0;
......@@ -921,11 +930,14 @@ public class GIFImageWriter extends ImageWriter {
if (DEBUG) System.out.println("Writing interlaced");
if (isOptimizedCase) {
Raster tile = image.getTile(0, 0);
ByteComponentRaster tile =
(ByteComponentRaster)image.getTile(0, 0);
byte[] data = ((DataBufferByte)tile.getDataBuffer()).getData();
ComponentSampleModel csm =
(ComponentSampleModel)tile.getSampleModel();
int offset = csm.getOffset(sourceXOffset, sourceYOffset, 0);
// take into account the raster data offset
offset += tile.getDataOffset(0);
int lineStride = csm.getScanlineStride();
writeRowsOpt(data, offset, lineStride, compressor,
......
......@@ -158,13 +158,10 @@ abstract class GIFMetadata extends IIOMetadata {
}
}
String value = attr.getNodeValue();
// XXX Should be able to use equals() here instead of
// equalsIgnoreCase() but some boolean attributes are incorrectly
// set to "true" or "false" by the J2SE core metadata classes
// getAsTree() method (which are duplicated above). See bug 5082756.
if (value.equalsIgnoreCase("TRUE")) {
// Allow lower case booleans for backward compatibility, #5082756
if (value.equals("TRUE") || value.equals("true")) {
return true;
} else if (value.equalsIgnoreCase("FALSE")) {
} else if (value.equals("FALSE") || value.equals("false")) {
return false;
} else {
fatal(node, "Attribute " + name + " must be 'TRUE' or 'FALSE'!");
......
......@@ -202,7 +202,7 @@ public class GIFStreamMetadata extends GIFMetadata {
compression_node.appendChild(node);
node = new IIOMetadataNode("Lossless");
node.setAttribute("value", "true");
node.setAttribute("value", "TRUE");
compression_node.appendChild(node);
// NumProgressiveScans not in stream
......
......@@ -1003,7 +1003,7 @@ class JFIFMarkerSegment extends MarkerSegment {
3,
new int [] {0, 1, 2},
null);
ColorModel cm = new ComponentColorModel(JPEG.sRGB,
ColorModel cm = new ComponentColorModel(JPEG.JCS.sRGB,
false,
false,
ColorModel.OPAQUE,
......
......@@ -208,15 +208,24 @@ public class JPEG {
public static final int [] bOffsRGB = { 2, 1, 0 };
protected static final ColorSpace sRGB =
ColorSpace.getInstance(ColorSpace.CS_sRGB);
protected static ColorSpace YCC = null; // Can't be final
static {
try {
YCC = ColorSpace.getInstance(ColorSpace.CS_PYCC);
} catch (IllegalArgumentException e) {
// PYCC.pf may not always be installed
/* These are kept in the inner class to avoid static initialization
* of the CMM class until someone actually needs it.
* (e.g. do not init CMM on the request for jpeg mime types)
*/
public static class JCS {
public static final ColorSpace sRGB =
ColorSpace.getInstance(ColorSpace.CS_sRGB);
public static final ColorSpace YCC;
static {
ColorSpace cs = null;
try {
cs = ColorSpace.getInstance(ColorSpace.CS_PYCC);
} catch (IllegalArgumentException e) {
// PYCC.pf may not always be installed
} finally {
YCC = cs;
}
}
}
......
......@@ -228,31 +228,31 @@ public class JPEGImageReader extends ImageReader {
(BufferedImage.TYPE_BYTE_GRAY);
defaultTypes[JPEG.JCS_RGB] =
ImageTypeSpecifier.createInterleaved
(JPEG.sRGB,
(JPEG.JCS.sRGB,
JPEG.bOffsRGB,
DataBuffer.TYPE_BYTE,
false,
false);
defaultTypes[JPEG.JCS_RGBA] =
ImageTypeSpecifier.createPacked
(JPEG.sRGB,
(JPEG.JCS.sRGB,
0xff000000,
0x00ff0000,
0x0000ff00,
0x000000ff,
DataBuffer.TYPE_INT,
false);
if (JPEG.YCC != null) {
if (JPEG.JCS.YCC != null) {
defaultTypes[JPEG.JCS_YCC] =
ImageTypeSpecifier.createInterleaved
(JPEG.YCC,
(JPEG.JCS.YCC,
JPEG.bandOffsets[2],
DataBuffer.TYPE_BYTE,
false,
false);
defaultTypes[JPEG.JCS_YCCA] =
ImageTypeSpecifier.createInterleaved
(JPEG.YCC,
(JPEG.JCS.YCC,
JPEG.bandOffsets[3],
DataBuffer.TYPE_BYTE,
true,
......@@ -774,7 +774,7 @@ public class JPEGImageReader extends ImageReader {
case JPEG.JCS_RGB:
list.add(raw);
list.add(getImageType(JPEG.JCS_GRAYSCALE));
if (JPEG.YCC != null) {
if (JPEG.JCS.YCC != null) {
list.add(getImageType(JPEG.JCS_YCC));
}
break;
......@@ -811,7 +811,7 @@ public class JPEGImageReader extends ImageReader {
}
list.add(getImageType(JPEG.JCS_GRAYSCALE));
if (JPEG.YCC != null) { // Might be null if PYCC.pf not installed
if (JPEG.JCS.YCC != null) { // Might be null if PYCC.pf not installed
list.add(getImageType(JPEG.JCS_YCC));
}
break;
......@@ -893,7 +893,7 @@ public class JPEGImageReader extends ImageReader {
(!cs.isCS_sRGB()) &&
(cm.getNumComponents() == numComponents)) {
// Target isn't sRGB, so convert from sRGB to the target
convert = new ColorConvertOp(JPEG.sRGB, cs, null);
convert = new ColorConvertOp(JPEG.JCS.sRGB, cs, null);
} else if (csType != ColorSpace.TYPE_RGB) {
throw new IIOException("Incompatible color conversion");
}
......@@ -906,18 +906,18 @@ public class JPEGImageReader extends ImageReader {
}
break;
case JPEG.JCS_YCC:
if (JPEG.YCC == null) { // We can't do YCC at all
if (JPEG.JCS.YCC == null) { // We can't do YCC at all
throw new IIOException("Incompatible color conversion");
}
if ((cs != JPEG.YCC) &&
if ((cs != JPEG.JCS.YCC) &&
(cm.getNumComponents() == numComponents)) {
convert = new ColorConvertOp(JPEG.YCC, cs, null);
convert = new ColorConvertOp(JPEG.JCS.YCC, cs, null);
}
break;
case JPEG.JCS_YCCA:
// No conversions available; image must be YCCA
if ((JPEG.YCC == null) || // We can't do YCC at all
(cs != JPEG.YCC) ||
if ((JPEG.JCS.YCC == null) || // We can't do YCC at all
(cs != JPEG.JCS.YCC) ||
(cm.getNumComponents() != numComponents)) {
throw new IIOException("Incompatible color conversion");
}
......
......@@ -39,8 +39,6 @@ public class JPEGImageReaderSpi extends ImageReaderSpi {
private static String [] writerSpiNames =
{"com.sun.imageio.plugins.jpeg.JPEGImageWriterSpi"};
private boolean registered = false;
public JPEGImageReaderSpi() {
super(JPEG.vendor,
JPEG.version,
......@@ -61,26 +59,6 @@ public class JPEGImageReaderSpi extends ImageReaderSpi {
);
}
public void onRegistration(ServiceRegistry registry,
Class<?> category) {
if (registered) {
return;
}
try {
java.security.AccessController.doPrivileged(
new sun.security.action.LoadLibraryAction("jpeg"));
// Stuff it all into one lib for first pass
//java.security.AccessController.doPrivileged(
//new sun.security.action.LoadLibraryAction("imageioIJG"));
} catch (Throwable e) { // Fail on any Throwable
// if it can't be loaded, deregister and return
registry.deregisterServiceProvider(this);
return;
}
registered = true;
}
public String getDescription(Locale locale) {
return "Standard JPEG Image Reader";
}
......
......@@ -812,13 +812,13 @@ public class JPEGImageWriter extends ImageWriter {
}
break;
case ColorSpace.TYPE_3CLR:
if (cs == JPEG.YCC) {
if (cs == JPEG.JCS.YCC) {
if (!alpha) {
if (jfif != null) {
convertTosRGB = true;
convertOp =
new ColorConvertOp(cs,
JPEG.sRGB,
JPEG.JCS.sRGB,
null);
outCsType = JPEG.JCS_YCbCr;
} else if (adobe != null) {
......@@ -1494,7 +1494,7 @@ public class JPEGImageWriter extends ImageWriter {
}
break;
case ColorSpace.TYPE_3CLR:
if (cs == JPEG.YCC) {
if (cs == JPEG.JCS.YCC) {
if (alpha) {
retval = JPEG.JCS_YCCA;
} else {
......@@ -1533,7 +1533,7 @@ public class JPEGImageWriter extends ImageWriter {
}
break;
case ColorSpace.TYPE_3CLR:
if (cs == JPEG.YCC) {
if (cs == JPEG.JCS.YCC) {
if (alpha) {
retval = JPEG.JCS_YCCA;
} else {
......@@ -1579,7 +1579,7 @@ public class JPEGImageWriter extends ImageWriter {
}
break;
case ColorSpace.TYPE_3CLR:
if (cs == JPEG.YCC) {
if (cs == JPEG.JCS.YCC) {
if (alpha) {
retval = JPEG.JCS_YCCA;
} else {
......
......@@ -42,8 +42,6 @@ public class JPEGImageWriterSpi extends ImageWriterSpi {
private static String [] readerSpiNames =
{"com.sun.imageio.plugins.jpeg.JPEGImageReaderSpi"};
private boolean registered = false;
public JPEGImageWriterSpi() {
super(JPEG.vendor,
JPEG.version,
......@@ -68,23 +66,6 @@ public class JPEGImageWriterSpi extends ImageWriterSpi {
return "Standard JPEG Image Writer";
}
public void onRegistration(ServiceRegistry registry,
Class<?> category) {
if (registered) {
return;
}
try {
java.security.AccessController.doPrivileged(
new sun.security.action.LoadLibraryAction("jpeg"));
} catch (Throwable e) { // Fail on any Throwable
// if it can't be loaded, deregister and return
registry.deregisterServiceProvider(this);
return;
}
registered = true;
}
public boolean isFormatLossless() {
return false;
}
......
......@@ -490,7 +490,7 @@ public class JPEGMetadata extends IIOMetadata implements Cloneable {
}
break;
case ColorSpace.TYPE_3CLR:
if (cs == JPEG.YCC) {
if (cs == JPEG.JCS.YCC) {
wantJFIF = false;
componentIDs[0] = (byte) 'Y';
componentIDs[1] = (byte) 'C';
......@@ -955,7 +955,7 @@ public class JPEGMetadata extends IIOMetadata implements Cloneable {
// Lossless - false
IIOMetadataNode lossless = new IIOMetadataNode("Lossless");
lossless.setAttribute("value", "false");
lossless.setAttribute("value", "FALSE");
compression.appendChild(lossless);
// NumProgressiveScans - count sos segments
......
......@@ -37,6 +37,7 @@ import java.awt.image.WritableRaster;
import java.io.BufferedInputStream;
import java.io.ByteArrayInputStream;
import java.io.DataInputStream;
import java.io.EOFException;
import java.io.InputStream;
import java.io.IOException;
import java.io.SequenceInputStream;
......@@ -59,7 +60,7 @@ import com.sun.imageio.plugins.common.SubImageInputStream;
import java.io.ByteArrayOutputStream;
import sun.awt.image.ByteInterleavedRaster;
class PNGImageDataEnumeration implements Enumeration {
class PNGImageDataEnumeration implements Enumeration<InputStream> {
boolean firstTime = true;
ImageInputStream stream;
......@@ -72,7 +73,7 @@ class PNGImageDataEnumeration implements Enumeration {
int type = stream.readInt(); // skip chunk type
}
public Object nextElement() {
public InputStream nextElement() {
try {
firstTime = false;
ImageInputStream iis = new SubImageInputStream(stream, length);
......@@ -207,25 +208,17 @@ public class PNGImageReader extends ImageReader {
resetStreamSettings();
}
private String readNullTerminatedString(String charset) throws IOException {
private String readNullTerminatedString(String charset, int maxLen) throws IOException {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
int b;
while ((b = stream.read()) != 0) {
int count = 0;
while ((maxLen > count++) && ((b = stream.read()) != 0)) {
if (b == -1) throw new EOFException();
baos.write(b);
}
return new String(baos.toByteArray(), charset);
}
private String readNullTerminatedString() throws IOException {
StringBuilder b = new StringBuilder();
int c;
while ((c = stream.read()) != 0) {
b.append((char)c);
}
return b.toString();
}
private void readHeader() throws IIOException {
if (gotHeader) {
return;
......@@ -434,7 +427,7 @@ public class PNGImageReader extends ImageReader {
}
private void parse_iCCP_chunk(int chunkLength) throws IOException {
String keyword = readNullTerminatedString();
String keyword = readNullTerminatedString("ISO-8859-1", 80);
metadata.iCCP_profileName = keyword;
metadata.iCCP_compressionMethod = stream.readUnsignedByte();
......@@ -450,7 +443,7 @@ public class PNGImageReader extends ImageReader {
private void parse_iTXt_chunk(int chunkLength) throws IOException {
long chunkStart = stream.getStreamPosition();
String keyword = readNullTerminatedString();
String keyword = readNullTerminatedString("ISO-8859-1", 80);
metadata.iTXt_keyword.add(keyword);
int compressionFlag = stream.readUnsignedByte();
......@@ -459,15 +452,17 @@ public class PNGImageReader extends ImageReader {
int compressionMethod = stream.readUnsignedByte();
metadata.iTXt_compressionMethod.add(Integer.valueOf(compressionMethod));
String languageTag = readNullTerminatedString("UTF8");
String languageTag = readNullTerminatedString("UTF8", 80);
metadata.iTXt_languageTag.add(languageTag);
long pos = stream.getStreamPosition();
int maxLen = (int)(chunkStart + chunkLength - pos);
String translatedKeyword =
readNullTerminatedString("UTF8");
readNullTerminatedString("UTF8", maxLen);
metadata.iTXt_translatedKeyword.add(translatedKeyword);
String text;
long pos = stream.getStreamPosition();
pos = stream.getStreamPosition();
byte[] b = new byte[(int)(chunkStart + chunkLength - pos)];
stream.readFully(b);
......@@ -511,7 +506,7 @@ public class PNGImageReader extends ImageReader {
private void parse_sPLT_chunk(int chunkLength)
throws IOException, IIOException {
metadata.sPLT_paletteName = readNullTerminatedString();
metadata.sPLT_paletteName = readNullTerminatedString("ISO-8859-1", 80);
chunkLength -= metadata.sPLT_paletteName.length() + 1;
int sampleDepth = stream.readUnsignedByte();
......@@ -554,12 +549,12 @@ public class PNGImageReader extends ImageReader {
}
private void parse_tEXt_chunk(int chunkLength) throws IOException {
String keyword = readNullTerminatedString();
String keyword = readNullTerminatedString("ISO-8859-1", 80);
metadata.tEXt_keyword.add(keyword);
byte[] b = new byte[chunkLength - keyword.length() - 1];
stream.readFully(b);
metadata.tEXt_text.add(new String(b));
metadata.tEXt_text.add(new String(b, "ISO-8859-1"));
}
private void parse_tIME_chunk() throws IOException {
......@@ -640,7 +635,7 @@ public class PNGImageReader extends ImageReader {
}
private void parse_zTXt_chunk(int chunkLength) throws IOException {
String keyword = readNullTerminatedString();
String keyword = readNullTerminatedString("ISO-8859-1", 80);
metadata.zTXt_keyword.add(keyword);
int method = stream.readUnsignedByte();
......@@ -648,7 +643,7 @@ public class PNGImageReader extends ImageReader {
byte[] b = new byte[chunkLength - keyword.length() - 2];
stream.readFully(b);
metadata.zTXt_text.add(new String(inflate(b)));
metadata.zTXt_text.add(new String(inflate(b), "ISO-8859-1"));
}
private void readMetadata() throws IIOException {
......@@ -1263,7 +1258,7 @@ public class PNGImageReader extends ImageReader {
try {
stream.seek(imageStartPosition);
Enumeration e = new PNGImageDataEnumeration(stream);
Enumeration<InputStream> e = new PNGImageDataEnumeration(stream);
InputStream is = new SequenceInputStream(e);
/* InflaterInputStream uses an Inflater instance which consumes
......
......@@ -674,13 +674,8 @@ public class PNGImageWriter extends ImageWriter {
private byte[] deflate(byte[] b) throws IOException {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
DeflaterOutputStream dos = new DeflaterOutputStream(baos);
int len = b.length;
for (int i = 0; i < len; i++) {
dos.write((int)(0xff & b[i]));
}
dos.write(b);
dos.close();
return baos.toByteArray();
}
......@@ -736,7 +731,7 @@ public class PNGImageWriter extends ImageWriter {
cs.writeByte(compressionMethod);
String text = (String)textIter.next();
cs.write(deflate(text.getBytes()));
cs.write(deflate(text.getBytes("ISO-8859-1")));
cs.finish();
}
}
......
......@@ -211,8 +211,8 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
public int sRGB_renderingIntent;
// tEXt chunk
public ArrayList tEXt_keyword = new ArrayList(); // 1-79 char Strings
public ArrayList tEXt_text = new ArrayList(); // Strings
public ArrayList<String> tEXt_keyword = new ArrayList<String>(); // 1-79 characters
public ArrayList<String> tEXt_text = new ArrayList<String>();
// tIME chunk
public boolean tIME_present;
......@@ -235,13 +235,13 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
public int tRNS_blue;
// zTXt chunk
public ArrayList zTXt_keyword = new ArrayList(); // Strings
public ArrayList zTXt_compressionMethod = new ArrayList(); // Integers
public ArrayList zTXt_text = new ArrayList(); // Strings
public ArrayList<String> zTXt_keyword = new ArrayList<String>();
public ArrayList<Integer> zTXt_compressionMethod = new ArrayList<Integer>();
public ArrayList<String> zTXt_text = new ArrayList<String>();
// Unknown chunks
public ArrayList unknownChunkType = new ArrayList(); // Strings
public ArrayList unknownChunkData = new ArrayList(); // byte arrays
public ArrayList<String> unknownChunkType = new ArrayList<String>();
public ArrayList<byte[]> unknownChunkData = new ArrayList<byte[]>();
public PNGMetadata() {
super(true,
......@@ -426,21 +426,14 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
return false;
}
private ArrayList cloneBytesArrayList(ArrayList in) {
private ArrayList<byte[]> cloneBytesArrayList(ArrayList<byte[]> in) {
if (in == null) {
return null;
} else {
ArrayList list = new ArrayList(in.size());
Iterator iter = in.iterator();
while (iter.hasNext()) {
Object o = iter.next();
if (o == null) {
list.add(null);
} else {
list.add(((byte[])o).clone());
}
ArrayList<byte[]> list = new ArrayList<byte[]>(in.size());
for (byte[] b: in) {
list.add((b == null) ? null : (byte[])b.clone());
}
return list;
}
}
......@@ -600,7 +593,7 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
IIOMetadataNode iTXt_node = new IIOMetadataNode("iTXtEntry");
iTXt_node.setAttribute("keyword", iTXt_keyword.get(i));
iTXt_node.setAttribute("compressionFlag",
iTXt_compressionFlag.get(i) ? "1" : "0");
iTXt_compressionFlag.get(i) ? "TRUE" : "FALSE");
iTXt_node.setAttribute("compressionMethod",
iTXt_compressionMethod.get(i).toString());
iTXt_node.setAttribute("languageTag",
......@@ -832,7 +825,7 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
}
node = new IIOMetadataNode("BlackIsZero");
node.setAttribute("value", "true");
node.setAttribute("value", "TRUE");
chroma_node.appendChild(node);
if (PLTE_present) {
......@@ -894,7 +887,7 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
compression_node.appendChild(node);
node = new IIOMetadataNode("Lossless");
node.setAttribute("value", "true");
node.setAttribute("value", "TRUE");
compression_node.appendChild(node);
node = new IIOMetadataNode("NumProgressiveScans");
......@@ -1040,7 +1033,7 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
node.setAttribute("language",
iTXt_languageTag.get(i));
if (iTXt_compressionFlag.get(i)) {
node.setAttribute("compression", "deflate");
node.setAttribute("compression", "zip");
} else {
node.setAttribute("compression", "none");
}
......@@ -1052,7 +1045,7 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
node = new IIOMetadataNode("TextEntry");
node.setAttribute("keyword", (String)zTXt_keyword.get(i));
node.setAttribute("value", (String)zTXt_text.get(i));
node.setAttribute("compression", "deflate");
node.setAttribute("compression", "zip");
text_node.appendChild(node);
}
......@@ -1162,12 +1155,13 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
}
}
String value = attr.getNodeValue();
if (value.equals("true")) {
// Allow lower case booleans for backward compatibility, #5082756
if (value.equals("TRUE") || value.equals("true")) {
return true;
} else if (value.equals("false")) {
} else if (value.equals("FALSE") || value.equals("false")) {
return false;
} else {
fatal(node, "Attribute " + name + " must be 'true' or 'false'!");
fatal(node, "Attribute " + name + " must be 'TRUE' or 'FALSE'!");
return false;
}
}
......@@ -1421,26 +1415,30 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
}
String keyword = getAttribute(iTXt_node, "keyword");
iTXt_keyword.add(keyword);
if (isValidKeyword(keyword)) {
iTXt_keyword.add(keyword);
boolean compressionFlag =
getBooleanAttribute(iTXt_node, "compressionFlag");
iTXt_compressionFlag.add(Boolean.valueOf(compressionFlag));
boolean compressionFlag =
getBooleanAttribute(iTXt_node, "compressionFlag");
iTXt_compressionFlag.add(Boolean.valueOf(compressionFlag));
String compressionMethod =
getAttribute(iTXt_node, "compressionMethod");
iTXt_compressionMethod.add(Integer.valueOf(compressionMethod));
String compressionMethod =
getAttribute(iTXt_node, "compressionMethod");
iTXt_compressionMethod.add(Integer.valueOf(compressionMethod));
String languageTag =
getAttribute(iTXt_node, "languageTag");
iTXt_languageTag.add(languageTag);
String languageTag =
getAttribute(iTXt_node, "languageTag");
iTXt_languageTag.add(languageTag);
String translatedKeyword =
getAttribute(iTXt_node, "translatedKeyword");
iTXt_translatedKeyword.add(translatedKeyword);
String translatedKeyword =
getAttribute(iTXt_node, "translatedKeyword");
iTXt_translatedKeyword.add(translatedKeyword);
String text = getAttribute(iTXt_node, "text");
iTXt_text.add(text);
String text = getAttribute(iTXt_node, "text");
iTXt_text.add(text);
}
// silently skip invalid text entry
iTXt_node = iTXt_node.getNextSibling();
}
......@@ -1692,11 +1690,45 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
}
}
private boolean isISOLatin(String s) {
/*
* Accrding to PNG spec, keywords are restricted to 1 to 79 bytes
* in length. Keywords shall contain only printable Latin-1 characters
* and spaces; To reduce the chances for human misreading of a keyword,
* leading spaces, trailing spaces, and consecutive spaces are not
* permitted in keywords.
*
* See: http://www.w3.org/TR/PNG/#11keywords
*/
private boolean isValidKeyword(String s) {
int len = s.length();
if (len < 1 || len >= 80) {
return false;
}
if (s.startsWith(" ") || s.endsWith(" ") || s.contains(" ")) {
return false;
}
return isISOLatin(s, false);
}
/*
* According to PNG spec, keyword shall contain only printable
* Latin-1 [ISO-8859-1] characters and spaces; that is, only
* character codes 32-126 and 161-255 decimal are allowed.
* For Latin-1 value fields the 0x10 (linefeed) control
* character is aloowed too.
*
* See: http://www.w3.org/TR/PNG/#11keywords
*/
private boolean isISOLatin(String s, boolean isLineFeedAllowed) {
int len = s.length();
for (int i = 0; i < len; i++) {
if (s.charAt(i) > 255) {
return false;
char c = s.charAt(i);
if (c < 32 || c > 255 || (c > 126 && c < 161)) {
// not printable. Check whether this is an allowed
// control char
if (!isLineFeedAllowed || c != 0x10) {
return false;
}
}
}
return true;
......@@ -1929,19 +1961,22 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
while (child != null) {
String childName = child.getNodeName();
if (childName.equals("TextEntry")) {
String keyword = getAttribute(child, "keyword");
String keyword =
getAttribute(child, "keyword", "", false);
String value = getAttribute(child, "value");
String encoding = getAttribute(child, "encoding");
String language = getAttribute(child, "language");
String language =
getAttribute(child, "language", "", false);
String compression =
getAttribute(child, "compression");
getAttribute(child, "compression", "none", false);
if (isISOLatin(value)) {
if (!isValidKeyword(keyword)) {
// Just ignore this node, PNG requires keywords
} else if (isISOLatin(value, true)) {
if (compression.equals("zip")) {
// Use a zTXt node
zTXt_keyword.add(keyword);
zTXt_text.add(value);
zTXt_compressionMethod.add(new Integer(0));
zTXt_compressionMethod.add(Integer.valueOf(0));
} else {
// Use a tEXt node
tEXt_keyword.add(keyword);
......@@ -1998,14 +2033,14 @@ public class PNGMetadata extends IIOMetadata implements Cloneable {
sBIT_present = false;
sPLT_present = false;
sRGB_present = false;
tEXt_keyword = new ArrayList();
tEXt_text = new ArrayList();
tEXt_keyword = new ArrayList<String>();
tEXt_text = new ArrayList<String>();
tIME_present = false;
tRNS_present = false;
zTXt_keyword = new ArrayList();
zTXt_compressionMethod = new ArrayList();
zTXt_text = new ArrayList();
unknownChunkType = new ArrayList();
unknownChunkData = new ArrayList();
zTXt_keyword = new ArrayList<String>();
zTXt_compressionMethod = new ArrayList<Integer>();
zTXt_text = new ArrayList<String>();
unknownChunkType = new ArrayList<String>();
unknownChunkData = new ArrayList<byte[]>();
}
}
......@@ -94,6 +94,10 @@ public class StreamCloser {
tgn != null;
tg = tgn, tgn = tg.getParent());
streamCloser = new Thread(tg, streamCloserRunnable);
/* Set context class loader to null in order to avoid
* keeping a strong reference to an application classloader.
*/
streamCloser.setContextClassLoader(null);
Runtime.getRuntime().addShutdownHook(streamCloser);
return null;
}
......
......@@ -356,6 +356,9 @@ public abstract class GraphicsEnvironment {
* @since 1.5
*/
public void preferLocaleFonts() {
if (!(this instanceof SunGraphicsEnvironment)) {
return;
}
sun.font.FontManager.preferLocaleFonts();
}
......@@ -376,6 +379,9 @@ public abstract class GraphicsEnvironment {
* @since 1.5
*/
public void preferProportionalFonts() {
if (!(this instanceof SunGraphicsEnvironment)) {
return;
}
sun.font.FontManager.preferProportionalFonts();
}
......
......@@ -737,7 +737,7 @@ public class ICC_Profile implements Serializable {
ICC_Profile(ProfileDeferralInfo pdi) {
this.deferralInfo = pdi;
this.profileActivator = new ProfileActivator() {
public void activate() {
public void activate() throws ProfileDataException {
activateDeferredProfile();
}
};
......@@ -830,20 +830,16 @@ public class ICC_Profile implements Serializable {
case ColorSpace.CS_sRGB:
synchronized(ICC_Profile.class) {
if (sRGBprofile == null) {
try {
/*
* Deferral is only used for standard profiles.
* Enabling the appropriate access privileges is handled
* at a lower level.
*/
sRGBprofile = getDeferredInstance(
new ProfileDeferralInfo("sRGB.pf",
ColorSpace.TYPE_RGB,
3, CLASS_DISPLAY));
} catch (IOException e) {
throw new IllegalArgumentException(
"Can't load standard profile: sRGB.pf");
}
/*
* Deferral is only used for standard profiles.
* Enabling the appropriate access privileges is handled
* at a lower level.
*/
ProfileDeferralInfo pInfo =
new ProfileDeferralInfo("sRGB.pf",
ColorSpace.TYPE_RGB, 3,
CLASS_DISPLAY);
sRGBprofile = getDeferredInstance(pInfo);
}
thisProfile = sRGBprofile;
}
......@@ -853,7 +849,11 @@ public class ICC_Profile implements Serializable {
case ColorSpace.CS_CIEXYZ:
synchronized(ICC_Profile.class) {
if (XYZprofile == null) {
XYZprofile = getStandardProfile("CIEXYZ.pf");
ProfileDeferralInfo pInfo =
new ProfileDeferralInfo("CIEXYZ.pf",
ColorSpace.TYPE_XYZ, 3,
CLASS_DISPLAY);
XYZprofile = getDeferredInstance(pInfo);
}
thisProfile = XYZprofile;
}
......@@ -863,7 +863,11 @@ public class ICC_Profile implements Serializable {
case ColorSpace.CS_PYCC:
synchronized(ICC_Profile.class) {
if (PYCCprofile == null) {
PYCCprofile = getStandardProfile("PYCC.pf");
ProfileDeferralInfo pInfo =
new ProfileDeferralInfo("PYCC.pf",
ColorSpace.TYPE_3CLR, 3,
CLASS_DISPLAY);
PYCCprofile = getDeferredInstance(pInfo);
}
thisProfile = PYCCprofile;
}
......@@ -873,7 +877,11 @@ public class ICC_Profile implements Serializable {
case ColorSpace.CS_GRAY:
synchronized(ICC_Profile.class) {
if (GRAYprofile == null) {
GRAYprofile = getStandardProfile("GRAY.pf");
ProfileDeferralInfo pInfo =
new ProfileDeferralInfo("GRAY.pf",
ColorSpace.TYPE_GRAY, 1,
CLASS_DISPLAY);
GRAYprofile = getDeferredInstance(pInfo);
}
thisProfile = GRAYprofile;
}
......@@ -883,7 +891,11 @@ public class ICC_Profile implements Serializable {
case ColorSpace.CS_LINEAR_RGB:
synchronized(ICC_Profile.class) {
if (LINEAR_RGBprofile == null) {
LINEAR_RGBprofile = getStandardProfile("LINEAR_RGB.pf");
ProfileDeferralInfo pInfo =
new ProfileDeferralInfo("LINEAR_RGB.pf",
ColorSpace.TYPE_RGB, 3,
CLASS_DISPLAY);
LINEAR_RGBprofile = getDeferredInstance(pInfo);
}
thisProfile = LINEAR_RGBprofile;
}
......@@ -1047,9 +1059,7 @@ public class ICC_Profile implements Serializable {
* code will take care of access privileges.
* @see activateDeferredProfile()
*/
static ICC_Profile getDeferredInstance(ProfileDeferralInfo pdi)
throws IOException {
static ICC_Profile getDeferredInstance(ProfileDeferralInfo pdi) {
if (!ProfileDeferralMgr.deferring) {
return getStandardProfile(pdi.filename);
}
......@@ -1063,33 +1073,37 @@ public class ICC_Profile implements Serializable {
}
void activateDeferredProfile() {
byte profileData[];
FileInputStream fis;
String fileName = deferralInfo.filename;
void activateDeferredProfile() throws ProfileDataException {
byte profileData[];
FileInputStream fis;
String fileName = deferralInfo.filename;
profileActivator = null;
deferralInfo = null;
if ((fis = openProfile(fileName)) == null) {
throw new IllegalArgumentException("Cannot open file " + fileName);
throw new ProfileDataException("Cannot open file " + fileName);
}
try {
profileData = getProfileDataFromStream(fis);
fis.close(); /* close the file */
}
catch (IOException e) {
throw new IllegalArgumentException("Invalid ICC Profile Data" +
fileName);
ProfileDataException pde = new
ProfileDataException("Invalid ICC Profile Data" + fileName);
pde.initCause(e);
throw pde;
}
if (profileData == null) {
throw new IllegalArgumentException("Invalid ICC Profile Data" +
throw new ProfileDataException("Invalid ICC Profile Data" +
fileName);
}
try {
ID = CMSManager.getModule().loadProfile(profileData);
} catch (CMMException c) {
throw new IllegalArgumentException("Invalid ICC Profile Data" +
fileName);
ProfileDataException pde = new
ProfileDataException("Invalid ICC Profile Data" + fileName);
pde.initCause(c);
throw pde;
}
}
......
......@@ -215,6 +215,14 @@ public class LogManager {
// This private class is used as a shutdown hook.
// It does a "reset" to close all open handlers.
private class Cleaner extends Thread {
private Cleaner() {
/* Set context class loader to null in order to avoid
* keeping a strong reference to an application classloader.
*/
this.setContextClassLoader(null);
}
public void run() {
// This is to ensure the LogManager.<clinit> is completed
// before synchronized block. Otherwise deadlocks are possible.
......
......@@ -67,126 +67,13 @@ public class ImageTypeSpecifier {
* <code>BufferedImage</code> types.
*/
private static ImageTypeSpecifier[] BISpecifier;
private static ColorSpace sRGB;
// Initialize the standard specifiers
static {
ColorSpace sRGB = ColorSpace.getInstance(ColorSpace.CS_sRGB);
sRGB = ColorSpace.getInstance(ColorSpace.CS_sRGB);
BISpecifier =
new ImageTypeSpecifier[BufferedImage.TYPE_BYTE_INDEXED + 1];
BISpecifier[BufferedImage.TYPE_CUSTOM] = null;
BISpecifier[BufferedImage.TYPE_INT_RGB] =
createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0x0,
DataBuffer.TYPE_INT,
false);
BISpecifier[BufferedImage.TYPE_INT_ARGB] =
createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0xff000000,
DataBuffer.TYPE_INT,
false);
BISpecifier[BufferedImage.TYPE_INT_ARGB_PRE] =
createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0xff000000,
DataBuffer.TYPE_INT,
true);
BISpecifier[BufferedImage.TYPE_INT_BGR] =
createPacked(sRGB,
0x000000ff,
0x0000ff00,
0x00ff0000,
0x0,
DataBuffer.TYPE_INT,
false);
int[] bOffsRGB = { 2, 1, 0 };
BISpecifier[BufferedImage.TYPE_3BYTE_BGR] =
createInterleaved(sRGB,
bOffsRGB,
DataBuffer.TYPE_BYTE,
false,
false);
int[] bOffsABGR = { 3, 2, 1, 0 };
BISpecifier[BufferedImage.TYPE_4BYTE_ABGR] =
createInterleaved(sRGB,
bOffsABGR,
DataBuffer.TYPE_BYTE,
true,
false);
BISpecifier[BufferedImage.TYPE_4BYTE_ABGR_PRE] =
createInterleaved(sRGB,
bOffsABGR,
DataBuffer.TYPE_BYTE,
true,
true);
BISpecifier[BufferedImage.TYPE_USHORT_565_RGB] =
createPacked(sRGB,
0xF800,
0x07E0,
0x001F,
0x0,
DataBuffer.TYPE_USHORT,
false);
BISpecifier[BufferedImage.TYPE_USHORT_555_RGB] =
createPacked(sRGB,
0x7C00,
0x03E0,
0x001F,
0x0,
DataBuffer.TYPE_USHORT,
false);
BISpecifier[BufferedImage.TYPE_BYTE_GRAY] =
createGrayscale(8,
DataBuffer.TYPE_BYTE,
false);
BISpecifier[BufferedImage.TYPE_USHORT_GRAY] =
createGrayscale(16,
DataBuffer.TYPE_USHORT,
false);
BISpecifier[BufferedImage.TYPE_BYTE_BINARY] =
createGrayscale(1,
DataBuffer.TYPE_BYTE,
false);
BufferedImage bi =
new BufferedImage(1, 1, BufferedImage.TYPE_BYTE_INDEXED);
IndexColorModel icm = (IndexColorModel)bi.getColorModel();
int mapSize = icm.getMapSize();
byte[] redLUT = new byte[mapSize];
byte[] greenLUT = new byte[mapSize];
byte[] blueLUT = new byte[mapSize];
byte[] alphaLUT = new byte[mapSize];
icm.getReds(redLUT);
icm.getGreens(greenLUT);
icm.getBlues(blueLUT);
icm.getAlphas(alphaLUT);
BISpecifier[BufferedImage.TYPE_BYTE_INDEXED] =
createIndexed(redLUT, greenLUT, blueLUT, alphaLUT,
8,
DataBuffer.TYPE_BYTE);
}
/**
......@@ -1011,7 +898,7 @@ public class ImageTypeSpecifier {
ImageTypeSpecifier createFromBufferedImageType(int bufferedImageType) {
if (bufferedImageType >= BufferedImage.TYPE_INT_RGB &&
bufferedImageType <= BufferedImage.TYPE_BYTE_INDEXED) {
return BISpecifier[bufferedImageType];
return getSpecifier(bufferedImageType);
} else if (bufferedImageType == BufferedImage.TYPE_CUSTOM) {
throw new IllegalArgumentException("Cannot create from TYPE_CUSTOM!");
} else {
......@@ -1041,7 +928,7 @@ public class ImageTypeSpecifier {
if (image instanceof BufferedImage) {
int bufferedImageType = ((BufferedImage)image).getType();
if (bufferedImageType != BufferedImage.TYPE_CUSTOM) {
return BISpecifier[bufferedImageType];
return getSpecifier(bufferedImageType);
}
}
......@@ -1225,4 +1112,130 @@ public class ImageTypeSpecifier {
public int hashCode() {
return (9 * colorModel.hashCode()) + (14 * sampleModel.hashCode());
}
private static ImageTypeSpecifier getSpecifier(int type) {
if (BISpecifier[type] == null) {
BISpecifier[type] = createSpecifier(type);
}
return BISpecifier[type];
}
private static ImageTypeSpecifier createSpecifier(int type) {
switch(type) {
case BufferedImage.TYPE_INT_RGB:
return createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0x0,
DataBuffer.TYPE_INT,
false);
case BufferedImage.TYPE_INT_ARGB:
return createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0xff000000,
DataBuffer.TYPE_INT,
false);
case BufferedImage.TYPE_INT_ARGB_PRE:
return createPacked(sRGB,
0x00ff0000,
0x0000ff00,
0x000000ff,
0xff000000,
DataBuffer.TYPE_INT,
true);
case BufferedImage.TYPE_INT_BGR:
return createPacked(sRGB,
0x000000ff,
0x0000ff00,
0x00ff0000,
0x0,
DataBuffer.TYPE_INT,
false);
case BufferedImage.TYPE_3BYTE_BGR:
return createInterleaved(sRGB,
new int[] { 2, 1, 0 },
DataBuffer.TYPE_BYTE,
false,
false);
case BufferedImage.TYPE_4BYTE_ABGR:
return createInterleaved(sRGB,
new int[] { 3, 2, 1, 0 },
DataBuffer.TYPE_BYTE,
true,
false);
case BufferedImage.TYPE_4BYTE_ABGR_PRE:
return createInterleaved(sRGB,
new int[] { 3, 2, 1, 0 },
DataBuffer.TYPE_BYTE,
true,
true);
case BufferedImage.TYPE_USHORT_565_RGB:
return createPacked(sRGB,
0xF800,
0x07E0,
0x001F,
0x0,
DataBuffer.TYPE_USHORT,
false);
case BufferedImage.TYPE_USHORT_555_RGB:
return createPacked(sRGB,
0x7C00,
0x03E0,
0x001F,
0x0,
DataBuffer.TYPE_USHORT,
false);
case BufferedImage.TYPE_BYTE_GRAY:
return createGrayscale(8,
DataBuffer.TYPE_BYTE,
false);
case BufferedImage.TYPE_USHORT_GRAY:
return createGrayscale(16,
DataBuffer.TYPE_USHORT,
false);
case BufferedImage.TYPE_BYTE_BINARY:
return createGrayscale(1,
DataBuffer.TYPE_BYTE,
false);
case BufferedImage.TYPE_BYTE_INDEXED:
{
BufferedImage bi =
new BufferedImage(1, 1, BufferedImage.TYPE_BYTE_INDEXED);
IndexColorModel icm = (IndexColorModel)bi.getColorModel();
int mapSize = icm.getMapSize();
byte[] redLUT = new byte[mapSize];
byte[] greenLUT = new byte[mapSize];
byte[] blueLUT = new byte[mapSize];
byte[] alphaLUT = new byte[mapSize];
icm.getReds(redLUT);
icm.getGreens(greenLUT);
icm.getBlues(blueLUT);
icm.getAlphas(alphaLUT);
return createIndexed(redLUT, greenLUT, blueLUT, alphaLUT,
8,
DataBuffer.TYPE_BYTE);
}
default:
throw new IllegalArgumentException("Invalid BufferedImage type!");
}
}
}
......@@ -242,8 +242,12 @@ public interface IIOMetadataFormat {
/**
* A constant returned by <code>getAttributeDataType</code>
* indicating that the value of an attribute is one of 'true' or
* 'false'.
* indicating that the value of an attribute is one of the boolean
* values 'true' or 'false'.
* Attribute values of type DATATYPE_BOOLEAN should be marked as
* enumerations, and the permitted values should be the string
* literal values "TRUE" or "FALSE", although a plugin may also
* recognise lower or mixed case equivalents.
*/
int DATATYPE_BOOLEAN = 1;
......
......@@ -98,7 +98,7 @@ public abstract class FontConfiguration {
if (!inited) {
this.preferLocaleFonts = false;
this.preferPropFonts = false;
fontConfig = this; /* static initialization */
setFontConfiguration();
readFontConfigFile(fontConfigFile);
initFontConfig();
inited = true;
......@@ -1244,6 +1244,10 @@ public abstract class FontConfiguration {
return fontConfig;
}
protected void setFontConfiguration() {
fontConfig = this; /* static initialization */
}
//////////////////////////////////////////////////////////////////////
// FontConfig data tables and the index constants in binary file //
//////////////////////////////////////////////////////////////////////
......
......@@ -26,6 +26,7 @@
package sun.font;
import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference;
import java.awt.Font;
import java.awt.GraphicsEnvironment;
import java.awt.Rectangle;
......@@ -842,8 +843,36 @@ public class FileFontStrike extends PhysicalStrike {
return fileFont.getGlyphOutlineBounds(pScalerContext, glyphCode);
}
private
WeakReference<ConcurrentHashMap<Integer,GeneralPath>> outlineMapRef;
GeneralPath getGlyphOutline(int glyphCode, float x, float y) {
return fileFont.getGlyphOutline(pScalerContext, glyphCode, x, y);
GeneralPath gp = null;
ConcurrentHashMap<Integer, GeneralPath> outlineMap = null;
if (outlineMapRef != null) {
outlineMap = outlineMapRef.get();
if (outlineMap != null) {
gp = (GeneralPath)outlineMap.get(glyphCode);
}
}
if (gp == null) {
gp = fileFont.getGlyphOutline(pScalerContext, glyphCode, 0, 0);
if (outlineMap == null) {
outlineMap = new ConcurrentHashMap<Integer, GeneralPath>();
outlineMapRef =
new WeakReference
<ConcurrentHashMap<Integer,GeneralPath>>(outlineMap);
}
outlineMap.put(glyphCode, gp);
}
gp = (GeneralPath)gp.clone(); // mutable!
if (x != 0f || y != 0f) {
gp.transform(AffineTransform.getTranslateInstance(x, y));
}
return gp;
}
GeneralPath getGlyphVectorOutline(int[] glyphs, float x, float y) {
......
......@@ -1601,18 +1601,27 @@ public final class FontManager {
/* Path may be absolute or a base file name relative to one of
* the platform font directories
*/
private static String getPathName(String s) {
private static String getPathName(final String s) {
File f = new File(s);
if (f.isAbsolute()) {
return s;
} else if (pathDirs.length==1) {
return pathDirs[0] + File.separator + s;
} else {
for (int p=0; p<pathDirs.length; p++) {
f = new File(pathDirs[p] + File.separator + s);
if (f.exists()) {
return f.getAbsolutePath();
}
String path = java.security.AccessController.doPrivileged(
new java.security.PrivilegedAction<String>() {
public String run() {
for (int p=0; p<pathDirs.length; p++) {
File f = new File(pathDirs[p] +File.separator+ s);
if (f.exists()) {
return f.getAbsolutePath();
}
}
return null;
}
});
if (path != null) {
return path;
}
}
return s; // shouldn't happen, but harmless
......
......@@ -338,6 +338,8 @@ public final class GlyphLayout {
cache = new ConcurrentHashMap<SDKey, SDCache>(10);
cacheRef = new
SoftReference<ConcurrentHashMap<SDKey, SDCache>>(cache);
} else if (cache.size() >= 512) {
cache.clear();
}
cache.put(key, res);
}
......
......@@ -232,6 +232,16 @@ public final class StrikeCache {
if (disposer.pScalerContext != 0L) {
freeLongMemory(new long[0], disposer.pScalerContext);
}
} else if (disposer.pScalerContext != 0L) {
/* Rarely a strike may have been created that never cached
* any glyphs. In this case we still want to free the scaler
* context.
*/
if (FontManager.longAddresses) {
freeLongMemory(new long[0], disposer.pScalerContext);
} else {
freeIntMemory(new int[0], disposer.pScalerContext);
}
}
}
......
......@@ -25,6 +25,7 @@
package sun.java2d.cmm;
import java.awt.color.ProfileDataException;
/**
* An interface to allow the ProfileDeferralMgr to activate a
......@@ -35,6 +36,6 @@ public interface ProfileActivator {
/**
* Activate a previously deferred ICC_Profile object.
*/
public void activate();
public void activate() throws ProfileDataException;
}
......@@ -25,6 +25,7 @@
package sun.java2d.cmm;
import java.awt.color.ProfileDataException;
import java.util.Vector;
......@@ -39,7 +40,7 @@ import java.util.Vector;
public class ProfileDeferralMgr {
public static boolean deferring = true;
private static Vector aVector;
private static Vector<ProfileActivator> aVector;
/**
* Records a ProfileActivator object whose activate method will
......@@ -51,7 +52,7 @@ public class ProfileDeferralMgr {
return;
}
if (aVector == null) {
aVector = new Vector(3, 3);
aVector = new Vector<ProfileActivator>(3, 3);
}
aVector.addElement(pa);
return;
......@@ -89,8 +90,26 @@ public class ProfileDeferralMgr {
return;
}
n = aVector.size();
for (i = 0; i < n; i++) {
((ProfileActivator) aVector.get(i)).activate();
for (ProfileActivator pa : aVector) {
try {
pa.activate();
} catch (ProfileDataException e) {
/*
* Ignore profile activation error for now:
* such exception is pssible due to absence
* or corruption of standard color profile.
* As for now we expect all profiles should
* be shiped with jre and presence of this
* exception is indication of some configuration
* problem in jre installation.
*
* NB: we still are greedy loading deferred profiles
* and load them all if any of them is needed.
* Therefore broken profile (if any) might be never used.
* If there will be attempt to use broken profile then
* it will result in CMMException.
*/
}
}
aVector.removeAllElements();
aVector = null;
......
......@@ -120,7 +120,7 @@ public class Dasher extends LineSink {
// Normalize so 0 <= phase < dash[0]
int idx = 0;
dashOn = false;
dashOn = true;
int d;
while (phase >= (d = dash[idx])) {
phase -= d;
......
......@@ -245,6 +245,7 @@ public class PiscesRenderingEngine extends RenderingEngine {
FloatToS15_16(coords[1]));
break;
case PathIterator.SEG_CLOSE:
lsink.lineJoin();
lsink.close();
break;
default:
......
......@@ -2149,55 +2149,51 @@ public class ServiceDialog extends JDialog implements ActionListener {
}
}
}
}
rbPortrait.setEnabled(pSupported);
rbLandscape.setEnabled(lSupported);
rbRevPortrait.setEnabled(rpSupported);
rbRevLandscape.setEnabled(rlSupported);
OrientationRequested or = (OrientationRequested)asCurrent.get(orCategory);
if (or == null ||
!psCurrent.isAttributeValueSupported(or, docFlavor, asCurrent)) {
or = (OrientationRequested)psCurrent.getDefaultAttributeValue(orCategory);
// need to validate if default is not supported
if (!psCurrent.isAttributeValueSupported(or, docFlavor, asCurrent)) {
or = null;
values =
psCurrent.getSupportedAttributeValues(orCategory,
docFlavor,
asCurrent);
if (values instanceof OrientationRequested[]) {
OrientationRequested[] orValues =
(OrientationRequested[])values;
if (orValues.length > 1) {
// get the first in the list
or = orValues[0];
}
}
}
if (or == null) {
or = OrientationRequested.PORTRAIT;
rbPortrait.setEnabled(pSupported);
rbLandscape.setEnabled(lSupported);
rbRevPortrait.setEnabled(rpSupported);
rbRevLandscape.setEnabled(rlSupported);
OrientationRequested or = (OrientationRequested)asCurrent.get(orCategory);
if (or == null ||
!psCurrent.isAttributeValueSupported(or, docFlavor, asCurrent)) {
or = (OrientationRequested)psCurrent.getDefaultAttributeValue(orCategory);
// need to validate if default is not supported
if ((or != null) &&
!psCurrent.isAttributeValueSupported(or, docFlavor, asCurrent)) {
or = null;
Object values =
psCurrent.getSupportedAttributeValues(orCategory,
docFlavor,
asCurrent);
if (values instanceof OrientationRequested[]) {
OrientationRequested[] orValues =
(OrientationRequested[])values;
if (orValues.length > 1) {
// get the first in the list
or = orValues[0];
}
}
asCurrent.add(or);
}
if (or == OrientationRequested.PORTRAIT) {
rbPortrait.setSelected(true);
} else if (or == OrientationRequested.LANDSCAPE) {
rbLandscape.setSelected(true);
} else if (or == OrientationRequested.REVERSE_PORTRAIT) {
rbRevPortrait.setSelected(true);
} else { // if (or == OrientationRequested.REVERSE_LANDSCAPE)
rbRevLandscape.setSelected(true);
if (or == null) {
or = OrientationRequested.PORTRAIT;
}
} else {
rbPortrait.setEnabled(pSupported);
rbLandscape.setEnabled(lSupported);
rbRevPortrait.setEnabled(rpSupported);
rbRevLandscape.setEnabled(rlSupported);
asCurrent.add(or);
}
if (or == OrientationRequested.PORTRAIT) {
rbPortrait.setSelected(true);
} else if (or == OrientationRequested.LANDSCAPE) {
rbLandscape.setSelected(true);
} else if (or == OrientationRequested.REVERSE_PORTRAIT) {
rbRevPortrait.setSelected(true);
} else { // if (or == OrientationRequested.REVERSE_LANDSCAPE)
rbRevLandscape.setSelected(true);
}
}
}
......
......@@ -169,6 +169,7 @@ initCubemap(int* cmap,
int cubesize = cube_dim * cube_dim * cube_dim;
unsigned char *useFlags;
unsigned char *newILut = (unsigned char*)malloc(cubesize);
int cmap_mid = (cmap_len >> 1) + (cmap_len & 0x1);
if (newILut) {
useFlags = (unsigned char *)calloc(cubesize, 1);
......@@ -188,7 +189,7 @@ initCubemap(int* cmap,
currentState.iLUT = newILut;
currentState.rgb = (unsigned short *)
malloc(256 * sizeof(unsigned short));
malloc(cmap_len * sizeof(unsigned short));
if (currentState.rgb == NULL) {
free(newILut);
free(useFlags);
......@@ -199,7 +200,7 @@ initCubemap(int* cmap,
}
currentState.indices = (unsigned char *)
malloc(256 * sizeof(unsigned char));
malloc(cmap_len * sizeof(unsigned char));
if (currentState.indices == NULL) {
free(currentState.rgb);
free(newILut);
......@@ -210,18 +211,18 @@ initCubemap(int* cmap,
return NULL;
}
for (i = 0; i < 128; i++) {
for (i = 0; i < cmap_mid; i++) {
unsigned short rgb;
int pixel = cmap[i];
rgb = (pixel & 0x00f80000) >> 9;
rgb |= (pixel & 0x0000f800) >> 6;
rgb |= (pixel & 0xf8) >> 3;
INSERTNEW(currentState, rgb, i);
pixel = cmap[255-i];
pixel = cmap[cmap_len - i - 1];
rgb = (pixel & 0x00f80000) >> 9;
rgb |= (pixel & 0x0000f800) >> 6;
rgb |= (pixel & 0xf8) >> 3;
INSERTNEW(currentState, rgb, 255-i);
INSERTNEW(currentState, rgb, cmap_len - i - 1);
}
if (!recurseLevel(&currentState)) {
......
......@@ -396,7 +396,7 @@ static imageIODataPtr initImageioData (JNIEnv *env,
data->jpegObj = cinfo;
cinfo->client_data = data;
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("new structures: data is %p, cinfo is %p\n", data, cinfo);
#endif
......@@ -673,7 +673,7 @@ static int setQTables(JNIEnv *env,
j_decompress_ptr decomp;
qlen = (*env)->GetArrayLength(env, qtables);
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("in setQTables, qlen = %d, write is %d\n", qlen, write);
#endif
for (i = 0; i < qlen; i++) {
......@@ -876,7 +876,7 @@ imageio_fill_input_buffer(j_decompress_ptr cinfo)
return FALSE;
}
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("Filling input buffer, remaining skip is %ld, ",
sb->remaining_skip);
printf("Buffer length is %d\n", sb->bufferLength);
......@@ -906,7 +906,7 @@ imageio_fill_input_buffer(j_decompress_ptr cinfo)
cinfo->err->error_exit((j_common_ptr) cinfo);
}
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("Buffer filled. ret = %d\n", ret);
#endif
/*
......@@ -917,7 +917,7 @@ imageio_fill_input_buffer(j_decompress_ptr cinfo)
*/
if (ret <= 0) {
jobject reader = data->imageIOobj;
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("YO! Early EOI! ret = %d\n", ret);
#endif
RELEASE_ARRAYS(env, data, src->next_input_byte);
......@@ -1216,21 +1216,24 @@ read_icc_profile (JNIEnv *env, j_decompress_ptr cinfo)
{
jpeg_saved_marker_ptr marker;
int num_markers = 0;
int num_found_markers = 0;
int seq_no;
JOCTET *icc_data;
JOCTET *dst_ptr;
unsigned int total_length;
#define MAX_SEQ_NO 255 // sufficient since marker numbers are bytes
char marker_present[MAX_SEQ_NO+1]; // 1 if marker found
unsigned int data_length[MAX_SEQ_NO+1]; // size of profile data in marker
unsigned int data_offset[MAX_SEQ_NO+1]; // offset for data in marker
jpeg_saved_marker_ptr icc_markers[MAX_SEQ_NO + 1];
int first; // index of the first marker in the icc_markers array
int last; // index of the last marker in the icc_markers array
jbyteArray data = NULL;
/* This first pass over the saved markers discovers whether there are
* any ICC markers and verifies the consistency of the marker numbering.
*/
for (seq_no = 1; seq_no <= MAX_SEQ_NO; seq_no++)
marker_present[seq_no] = 0;
for (seq_no = 0; seq_no <= MAX_SEQ_NO; seq_no++)
icc_markers[seq_no] = NULL;
for (marker = cinfo->marker_list; marker != NULL; marker = marker->next) {
if (marker_is_icc(marker)) {
......@@ -1242,37 +1245,58 @@ read_icc_profile (JNIEnv *env, j_decompress_ptr cinfo)
return NULL;
}
seq_no = GETJOCTET(marker->data[12]);
if (seq_no <= 0 || seq_no > num_markers) {
/* Some third-party tools produce images with profile chunk
* numeration started from zero. It is inconsistent with ICC
* spec, but seems to be recognized by majority of image
* processing tools, so we should be more tolerant to this
* departure from the spec.
*/
if (seq_no < 0 || seq_no > num_markers) {
JNU_ThrowByName(env, "javax/imageio/IIOException",
"Invalid icc profile: bad sequence number");
return NULL;
}
if (marker_present[seq_no]) {
if (icc_markers[seq_no] != NULL) {
JNU_ThrowByName(env, "javax/imageio/IIOException",
"Invalid icc profile: duplicate sequence numbers");
return NULL;
}
marker_present[seq_no] = 1;
data_length[seq_no] = marker->data_length - ICC_OVERHEAD_LEN;
icc_markers[seq_no] = marker;
num_found_markers ++;
}
}
if (num_markers == 0)
return NULL; // There is no profile
/* Check for missing markers, count total space needed,
* compute offset of each marker's part of the data.
*/
if (num_markers != num_found_markers) {
JNU_ThrowByName(env, "javax/imageio/IIOException",
"Invalid icc profile: invalid number of icc markers");
return NULL;
}
first = icc_markers[0] ? 0 : 1;
last = num_found_markers + first;
/* Check for missing markers, count total space needed.
*/
total_length = 0;
for (seq_no = 1; seq_no <= num_markers; seq_no++) {
if (marker_present[seq_no] == 0) {
for (seq_no = first; seq_no < last; seq_no++) {
unsigned int length;
if (icc_markers[seq_no] == NULL) {
JNU_ThrowByName(env, "javax/imageio/IIOException",
"Invalid icc profile: missing sequence number");
return NULL;
}
data_offset[seq_no] = total_length;
total_length += data_length[seq_no];
/* check the data length correctness */
length = icc_markers[seq_no]->data_length;
if (ICC_OVERHEAD_LEN > length || length > MAX_BYTES_IN_MARKER) {
JNU_ThrowByName(env, "javax/imageio/IIOException",
"Invalid icc profile: invalid data length");
return NULL;
}
total_length += (length - ICC_OVERHEAD_LEN);
}
if (total_length <= 0) {
......@@ -1301,19 +1325,14 @@ read_icc_profile (JNIEnv *env, j_decompress_ptr cinfo)
}
/* and fill it in */
for (marker = cinfo->marker_list; marker != NULL; marker = marker->next) {
if (marker_is_icc(marker)) {
JOCTET FAR *src_ptr;
JOCTET *dst_ptr;
unsigned int length;
seq_no = GETJOCTET(marker->data[12]);
dst_ptr = icc_data + data_offset[seq_no];
src_ptr = marker->data + ICC_OVERHEAD_LEN;
length = data_length[seq_no];
while (length--) {
*dst_ptr++ = *src_ptr++;
}
}
dst_ptr = icc_data;
for (seq_no = first; seq_no < last; seq_no++) {
JOCTET FAR *src_ptr = icc_markers[seq_no]->data + ICC_OVERHEAD_LEN;
unsigned int length =
icc_markers[seq_no]->data_length - ICC_OVERHEAD_LEN;
memcpy(dst_ptr, src_ptr, length);
dst_ptr += length;
}
/* finally, unpin the array */
......@@ -1530,6 +1549,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImageHeader
j_decompress_ptr cinfo;
struct jpeg_source_mgr *src;
sun_jpeg_error_ptr jerr;
jbyteArray profileData = NULL;
if (data == NULL) {
JNU_ThrowByName(env,
......@@ -1557,7 +1577,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImageHeader
return retval;
}
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("In readImageHeader, data is %p cinfo is %p\n", data, cinfo);
printf("clearFirst is %d\n", clearFirst);
#endif
......@@ -1584,7 +1604,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImageHeader
if (ret == JPEG_HEADER_TABLES_ONLY) {
retval = JNI_TRUE;
imageio_term_source(cinfo); // Pushback remaining buffer contents
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("just read tables-only image; q table 0 at %p\n",
cinfo->quant_tbl_ptrs[0]);
#endif
......@@ -1691,6 +1711,14 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImageHeader
}
}
RELEASE_ARRAYS(env, data, src->next_input_byte);
/* read icc profile data */
profileData = read_icc_profile(env, cinfo);
if ((*env)->ExceptionCheck(env)) {
return retval;
}
(*env)->CallVoidMethod(env, this,
JPEGImageReader_setImageDataID,
cinfo->image_width,
......@@ -1698,7 +1726,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImageHeader
cinfo->jpeg_color_space,
cinfo->out_color_space,
cinfo->num_components,
read_icc_profile(env, cinfo));
profileData);
if (reset) {
jpeg_abort_decompress(cinfo);
}
......@@ -1827,7 +1855,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageReader_readImage
(*env)->ReleaseIntArrayElements(env, srcBands, body, JNI_ABORT);
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("---- in reader.read ----\n");
printf("numBands is %d\n", numBands);
printf("bands array: ");
......@@ -2487,7 +2515,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageWriter_writeTables
data->streamBuf.suspendable = FALSE;
if (qtables != NULL) {
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("in writeTables: qtables not NULL\n");
#endif
setQTables(env, (j_common_ptr) cinfo, qtables, TRUE);
......@@ -2763,7 +2791,7 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageWriter_writeImage
cinfo->restart_interval = restartInterval;
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
printf("writer setup complete, starting compressor\n");
#endif
......@@ -2812,13 +2840,13 @@ Java_com_sun_imageio_plugins_jpeg_JPEGImageWriter_writeImage
for (i = 0; i < numBands; i++) {
if (scale !=NULL && scale[i] != NULL) {
*out++ = scale[i][*(in+i)];
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
if (in == data->pixelBuf.buf.bp){ // Just the first pixel
printf("in %d -> out %d, ", *(in+i), *(out-i-1));
}
#endif
#ifdef DEBUG
#ifdef DEBUG_IIO_JPEG
if (in == data->pixelBuf.buf.bp){ // Just the first pixel
printf("\n");
}
......
......@@ -394,12 +394,14 @@ static int setupFTContext(JNIEnv *env,
scalerInfo->env = env;
scalerInfo->font2D = font2D;
FT_Set_Transform(scalerInfo->face, &context->transform, NULL);
if (context != NULL) {
FT_Set_Transform(scalerInfo->face, &context->transform, NULL);
errCode = FT_Set_Char_Size(scalerInfo->face, 0, context->ptsz, 72, 72);
errCode = FT_Set_Char_Size(scalerInfo->face, 0, context->ptsz, 72, 72);
if (errCode == 0) {
errCode = FT_Activate_Size(scalerInfo->face->size);
if (errCode == 0) {
errCode = FT_Activate_Size(scalerInfo->face->size);
}
}
return errCode;
......@@ -885,6 +887,14 @@ Java_sun_font_FreetypeFontScaler_disposeNativeScaler(
JNIEnv *env, jobject scaler, jlong pScaler) {
FTScalerInfo* scalerInfo = (FTScalerInfo *) jlong_to_ptr(pScaler);
/* Freetype functions *may* cause callback to java
that can use cached values. Make sure our cache is up to date.
NB: scaler context is not important at this point, can use NULL. */
int errCode = setupFTContext(env, scaler, scalerInfo, NULL);
if (errCode) {
return;
}
freeNativeResources(env, scalerInfo);
}
......@@ -932,12 +942,21 @@ Java_sun_font_FreetypeFontScaler_getGlyphCodeNative(
JNIEnv *env, jobject scaler, jlong pScaler, jchar charCode) {
FTScalerInfo* scalerInfo = (FTScalerInfo *) jlong_to_ptr(pScaler);
int errCode;
if (scaler == NULL || scalerInfo->face == NULL) { /* bad/null scaler */
invalidateJavaScaler(env, scaler, scalerInfo);
return 0;
}
/* Freetype functions *may* cause callback to java
that can use cached values. Make sure our cache is up to date.
Scaler context is not important here, can use NULL. */
errCode = setupFTContext(env, scaler, scalerInfo, NULL);
if (errCode) {
return 0;
}
return FT_Get_Char_Index(scalerInfo->face, charCode);
}
......
......@@ -30,6 +30,41 @@
#include "Disposer.h"
#include "lcms.h"
#define ALIGNLONG(x) (((x)+3) & ~(3)) // Aligns to DWORD boundary
#ifdef USE_BIG_ENDIAN
#define AdjustEndianess32(a)
#else
static
void AdjustEndianess32(LPBYTE pByte)
{
BYTE temp1;
BYTE temp2;
temp1 = *pByte++;
temp2 = *pByte++;
*(pByte-1) = *pByte;
*pByte++ = temp2;
*(pByte-3) = *pByte;
*pByte = temp1;
}
#endif
// Transports to properly encoded values - note that icc profiles does use
// big endian notation.
static
icInt32Number TransportValue32(icInt32Number Value)
{
icInt32Number Temp = Value;
AdjustEndianess32((LPBYTE) &Temp);
return Temp;
}
#define SigMake(a,b,c,d) \
( ( ((int) ((unsigned char) (a))) << 24) | \
( ((int) ((unsigned char) (b))) << 16) | \
......@@ -182,6 +217,8 @@ JNIEXPORT jlong JNICALL Java_sun_java2d_cmm_lcms_LCMS_loadProfile
sProf.pf = cmsOpenProfileFromMem((LPVOID)dataArray, (DWORD) dataSize);
(*env)->ReleaseByteArrayElements (env, data, dataArray, 0);
if (sProf.pf == NULL) {
JNU_ThrowIllegalArgumentException(env, "Invalid profile data");
}
......@@ -337,6 +374,10 @@ JNIEXPORT void JNICALL Java_sun_java2d_cmm_lcms_LCMS_getTagData
return;
}
// Modify data for a tag in a profile
LCMSBOOL LCMSEXPORT _cmsModifyTagData(cmsHPROFILE hProfile,
icTagSignature sig, void *data, size_t size);
/*
* Class: sun_java2d_cmm_lcms_LCMS
* Method: setTagData
......@@ -345,7 +386,23 @@ JNIEXPORT void JNICALL Java_sun_java2d_cmm_lcms_LCMS_getTagData
JNIEXPORT void JNICALL Java_sun_java2d_cmm_lcms_LCMS_setTagData
(JNIEnv *env, jobject obj, jlong id, jint tagSig, jbyteArray data)
{
fprintf(stderr, "setTagData operation is not implemented");
cmsHPROFILE profile;
storeID_t sProf;
jbyte* dataArray;
int tagSize;
if (tagSig == SigHead) {
J2dRlsTraceLn(J2D_TRACE_ERROR, "LCMS_setTagData on icSigHead not "
"permitted");
return;
}
sProf.j = id;
profile = (cmsHPROFILE) sProf.pf;
dataArray = (*env)->GetByteArrayElements(env, data, 0);
tagSize =(*env)->GetArrayLength(env, data);
_cmsModifyTagData(profile, (icTagSignature) tagSig, dataArray, tagSize);
(*env)->ReleaseByteArrayElements(env, data, dataArray, 0);
}
void* getILData (JNIEnv *env, jobject img, jint* pDataType,
......@@ -507,3 +564,174 @@ JNIEXPORT void JNICALL Java_sun_java2d_cmm_lcms_LCMS_initLCMS
PF_ID_fID = (*env)->GetFieldID (env, Pf, "ID", "J");
}
LCMSBOOL _cmsModifyTagData(cmsHPROFILE hProfile, icTagSignature sig,
void *data, size_t size)
{
LCMSBOOL isNew;
int i, idx, delta, count;
LPBYTE padChars[3] = {0, 0, 0};
LPBYTE beforeBuf, afterBuf, ptr;
size_t beforeSize, afterSize;
icUInt32Number profileSize, temp;
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
isNew = FALSE;
idx = _cmsSearchTag(Icc, sig, FALSE);
if (idx < 0) {
isNew = TRUE;
idx = Icc->TagCount++;
if (Icc->TagCount >= MAX_TABLE_TAG) {
J2dRlsTraceLn1(J2D_TRACE_ERROR, "_cmsModifyTagData: Too many tags "
"(%d)\n", Icc->TagCount);
Icc->TagCount = MAX_TABLE_TAG-1;
return FALSE;
}
}
/* Read in size from header */
Icc->Seek(Icc, 0);
Icc->Read(&profileSize, sizeof(icUInt32Number), 1, Icc);
AdjustEndianess32((LPBYTE) &profileSize);
/* Compute the change in profile size */
if (isNew) {
delta = sizeof(icTag) + ALIGNLONG(size);
} else {
delta = ALIGNLONG(size) - ALIGNLONG(Icc->TagSizes[idx]);
}
/* Add tag to internal structures */
ptr = malloc(size);
if (ptr == NULL) {
if(isNew) {
Icc->TagCount--;
}
J2dRlsTraceLn(J2D_TRACE_ERROR, "_cmsModifyTagData: ptr == NULL");
return FALSE;
}
if (!Icc->Grow(Icc, delta)) {
free(ptr);
if(isNew) {
Icc->TagCount--;
}
J2dRlsTraceLn(J2D_TRACE_ERROR,
"_cmsModifyTagData: Icc->Grow() == FALSE");
return FALSE;
}
/* Compute size of tag data before/after the modified tag */
beforeSize = ((isNew)?profileSize:Icc->TagOffsets[idx]) -
Icc->TagOffsets[0];
if (Icc->TagCount == (idx + 1)) {
afterSize = 0;
} else {
afterSize = profileSize - Icc->TagOffsets[idx+1];
}
/* Make copies of the data before/after the modified tag */
if (beforeSize > 0) {
beforeBuf = malloc(beforeSize);
if (!beforeBuf) {
if(isNew) {
Icc->TagCount--;
}
free(ptr);
J2dRlsTraceLn(J2D_TRACE_ERROR,
"_cmsModifyTagData: beforeBuf == NULL");
return FALSE;
}
Icc->Seek(Icc, Icc->TagOffsets[0]);
Icc->Read(beforeBuf, beforeSize, 1, Icc);
}
if (afterSize > 0) {
afterBuf = malloc(afterSize);
if (!afterBuf) {
free(ptr);
if(isNew) {
Icc->TagCount--;
}
if (beforeSize > 0) {
free(beforeBuf);
}
J2dRlsTraceLn(J2D_TRACE_ERROR,
"_cmsModifyTagData: afterBuf == NULL");
return FALSE;
}
Icc->Seek(Icc, Icc->TagOffsets[idx+1]);
Icc->Read(afterBuf, afterSize, 1, Icc);
}
CopyMemory(ptr, data, size);
Icc->TagSizes[idx] = size;
Icc->TagNames[idx] = sig;
if (Icc->TagPtrs[idx]) {
free(Icc->TagPtrs[idx]);
}
Icc->TagPtrs[idx] = ptr;
if (isNew) {
Icc->TagOffsets[idx] = profileSize;
}
/* Update the profile size in the header */
profileSize += delta;
Icc->Seek(Icc, 0);
temp = TransportValue32(profileSize);
Icc->Write(Icc, sizeof(icUInt32Number), &temp);
/* Adjust tag offsets: if the tag is new, we must account
for the new tag table entry; otherwise, only those tags after
the modified tag are changed (by delta) */
if (isNew) {
for (i = 0; i < Icc->TagCount; ++i) {
Icc->TagOffsets[i] += sizeof(icTag);
}
} else {
for (i = idx+1; i < Icc->TagCount; ++i) {
Icc->TagOffsets[i] += delta;
}
}
/* Write out a new tag table */
count = 0;
for (i = 0; i < Icc->TagCount; ++i) {
if (Icc->TagNames[i] != 0) {
++count;
}
}
Icc->Seek(Icc, sizeof(icHeader));
temp = TransportValue32(count);
Icc->Write(Icc, sizeof(icUInt32Number), &temp);
for (i = 0; i < Icc->TagCount; ++i) {
if (Icc->TagNames[i] != 0) {
icTag tag;
tag.sig = TransportValue32(Icc->TagNames[i]);
tag.offset = TransportValue32((icInt32Number) Icc->TagOffsets[i]);
tag.size = TransportValue32((icInt32Number) Icc->TagSizes[i]);
Icc->Write(Icc, sizeof(icTag), &tag);
}
}
/* Write unchanged data before the modified tag */
if (beforeSize > 0) {
Icc->Write(Icc, beforeSize, beforeBuf);
free(beforeBuf);
}
/* Write modified tag data */
Icc->Write(Icc, size, data);
if (size % 4) {
Icc->Write(Icc, 4 - (size % 4), padChars);
}
/* Write unchanged data after the modified tag */
if (afterSize > 0) {
Icc->Write(Icc, afterSize, afterBuf);
free(afterBuf);
}
return TRUE;
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -51,7 +51,7 @@
// CIECAM 02 appearance model
// CIECAM 02 appearance model. Many thanks to Jordi Vilar for the debugging.
#include "lcms.h"
......@@ -196,6 +196,10 @@ CAM02COLOR NonlinearCompression(CAM02COLOR clr, LPcmsCIECAM02 pMod)
clr.RGBpa[i] = (400.0 * temp) / (temp + 27.13) + 0.1;
}
}
clr.A = (((2.0 * clr.RGBpa[0]) + clr.RGBpa[1] +
(clr.RGBpa[2] / 20.0)) - 0.305) * pMod->Nbb;
return clr;
}
......@@ -249,9 +253,6 @@ CAM02COLOR ComputeCorrelates(CAM02COLOR clr, LPcmsCIECAM02 pMod)
clr.H = 300 + ((100*((clr.h - 237.53)/1.2)) / temp);
}
clr.A = (((2.0 * clr.RGBpa[0]) + clr.RGBpa[1] +
(clr.RGBpa[2] / 20.0)) - 0.305) * pMod->Nbb;
clr.J = 100.0 * pow((clr.A / pMod->adoptedWhite.A),
(pMod->c * pMod->z));
......@@ -395,7 +396,7 @@ LCMSHANDLE LCMSEXPORT cmsCIECAM02Init(LPcmsViewingConditions pVC)
LPcmsCIECAM02 lpMod;
if((lpMod = (LPcmsCIECAM02) malloc(sizeof(cmsCIECAM02))) == NULL) {
if((lpMod = (LPcmsCIECAM02) _cmsMalloc(sizeof(cmsCIECAM02))) == NULL) {
return (LCMSHANDLE) NULL;
}
......@@ -449,14 +450,19 @@ LCMSHANDLE LCMSEXPORT cmsCIECAM02Init(LPcmsViewingConditions pVC)
lpMod -> z = compute_z(lpMod);
lpMod -> Nbb = computeNbb(lpMod);
lpMod -> FL = computeFL(lpMod);
if (lpMod -> D == D_CALCULATE ||
lpMod -> D == D_CALCULATE_DISCOUNT) {
lpMod -> D = computeD(lpMod);
}
lpMod -> Ncb = lpMod -> Nbb;
lpMod -> adoptedWhite = XYZtoCAT02(lpMod -> adoptedWhite);
lpMod -> adoptedWhite = ChromaticAdaptation(lpMod -> adoptedWhite, lpMod);
lpMod -> adoptedWhite = CAT02toHPE(lpMod -> adoptedWhite);
lpMod -> adoptedWhite = NonlinearCompression(lpMod -> adoptedWhite, lpMod);
lpMod -> adoptedWhite = ComputeCorrelates(lpMod -> adoptedWhite, lpMod);
return (LCMSHANDLE) lpMod;
......@@ -465,7 +471,7 @@ LCMSHANDLE LCMSEXPORT cmsCIECAM02Init(LPcmsViewingConditions pVC)
void LCMSEXPORT cmsCIECAM02Done(LCMSHANDLE hModel)
{
LPcmsCIECAM02 lpMod = (LPcmsCIECAM02) (LPSTR) hModel;
if (lpMod) free(lpMod);
if (lpMod) _cmsFree(lpMod);
}
......@@ -510,3 +516,4 @@ void LCMSEXPORT cmsCIECAM02Reverse(LCMSHANDLE hModel, LPcmsJCh pIn, LPcmsCIEXYZ
pOut ->Z = clr.XYZ[2];
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -174,7 +174,7 @@ typedef struct {
LCMSAPI void LCMSEXPORT cmsCIECAM97sDone(LCMSHANDLE hModel)
{
LPcmsCIECAM97s lpMod = (LPcmsCIECAM97s) (LPSTR) hModel;
if (lpMod) free(lpMod);
if (lpMod) _cmsFree(lpMod);
}
// Partial discounting for adaptation degree computation
......@@ -331,7 +331,7 @@ LCMSAPI LCMSHANDLE LCMSEXPORT cmsCIECAM97sInit(LPcmsViewingConditions pVC)
LPcmsCIECAM97s lpMod;
VEC3 tmp;
if((lpMod = (LPcmsCIECAM97s) malloc(sizeof(cmsCIECAM97s))) == NULL) {
if((lpMod = (LPcmsCIECAM97s) _cmsMalloc(sizeof(cmsCIECAM97s))) == NULL) {
return (LCMSHANDLE) NULL;
}
......@@ -449,7 +449,7 @@ LCMSAPI LCMSHANDLE LCMSEXPORT cmsCIECAM97sInit(LPcmsViewingConditions pVC)
// RGB_subw = [MlamRigg][WP/YWp]
#ifdef USE_CIECAM97s2
MAT3eval(&lpMod -> RGB_subw, &lpMod -> MlamRigg, (LPVEC3) &lpMod -> WP);
MAT3eval(&lpMod -> RGB_subw, &lpMod -> MlamRigg, &lpMod -> WP);
#else
VEC3divK(&tmp, (LPVEC3) &lpMod -> WP, lpMod->WP.Y);
MAT3eval(&lpMod -> RGB_subw, &lpMod -> MlamRigg, &tmp);
......
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -256,7 +256,7 @@ void ComputeBlackPointCompensationFactors(LPcmsCIEXYZ BlackPointIn,
// Return TRUE if both m and of are empy -- "m" being identity and "of" being 0
static
BOOL IdentityParameters(LPWMAT3 m, LPWVEC3 of)
LCMSBOOL IdentityParameters(LPWMAT3 m, LPWVEC3 of)
{
WVEC3 wv0;
......@@ -661,3 +661,6 @@ int cmsChooseCnvrt(int Absolute,
return rc;
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -57,6 +57,7 @@
// errors.
void cdecl cmsSignalError(int ErrorCode, const char *ErrorText, ...);
int LCMSEXPORT cmsErrorAction(int lAbort);
void LCMSEXPORT cmsSetErrorHandler(cmsErrorHandlerFunction Fn);
......@@ -96,7 +97,7 @@ void cmsSignalError(int ErrorCode, const char *ErrorText, ...)
char Buffer[1024];
vsprintf(Buffer, ErrorText, args);
vsnprintf(Buffer, 1023, ErrorText, args);
va_end(args);
if (UserErrorHandler(ErrorCode, Buffer)) {
......@@ -118,8 +119,8 @@ void cmsSignalError(int ErrorCode, const char *ErrorText, ...)
char Buffer1[1024];
char Buffer2[256];
sprintf(Buffer1, "Error #%x; ", ErrorCode);
vsprintf(Buffer2, ErrorText, args);
snprintf(Buffer1, 767, "Error #%x; ", ErrorCode);
vsnprintf(Buffer2, 255, ErrorText, args);
strcat(Buffer1, Buffer2);
MessageBox(NULL, Buffer1, "Little cms",
MB_OK|MB_ICONSTOP|MB_TASKMODAL);
......
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -63,9 +63,9 @@ LPGAMMATABLE LCMSEXPORT cmsReverseGamma(int nResultSamples, LPGAMMATABLE InGamma
LPGAMMATABLE LCMSEXPORT cmsBuildParametricGamma(int nEntries, int Type, double Params[]);
LPGAMMATABLE LCMSEXPORT cmsJoinGamma(LPGAMMATABLE InGamma, LPGAMMATABLE OutGamma);
LPGAMMATABLE LCMSEXPORT cmsJoinGammaEx(LPGAMMATABLE InGamma, LPGAMMATABLE OutGamma, int nPoints);
BOOL LCMSEXPORT cmsSmoothGamma(LPGAMMATABLE Tab, double lambda);
LCMSBOOL LCMSEXPORT cmsSmoothGamma(LPGAMMATABLE Tab, double lambda);
BOOL cdecl _cmsSmoothEndpoints(LPWORD Table, int nPoints);
LCMSBOOL cdecl _cmsSmoothEndpoints(LPWORD Table, int nPoints);
// Sampled curves
......@@ -74,7 +74,7 @@ LPSAMPLEDCURVE cdecl cmsAllocSampledCurve(int nItems);
void cdecl cmsFreeSampledCurve(LPSAMPLEDCURVE p);
void cdecl cmsEndpointsOfSampledCurve(LPSAMPLEDCURVE p, double* Min, double* Max);
void cdecl cmsClampSampledCurve(LPSAMPLEDCURVE p, double Min, double Max);
BOOL cdecl cmsSmoothSampledCurve(LPSAMPLEDCURVE Tab, double SmoothingLambda);
LCMSBOOL cdecl cmsSmoothSampledCurve(LPSAMPLEDCURVE Tab, double SmoothingLambda);
void cdecl cmsRescaleSampledCurve(LPSAMPLEDCURVE p, double Min, double Max, int nPoints);
LPSAMPLEDCURVE cdecl cmsJoinSampledCurves(LPSAMPLEDCURVE X, LPSAMPLEDCURVE Y, int nResultingPoints);
......@@ -84,7 +84,6 @@ double LCMSEXPORT cmsEstimateGammaEx(LPWORD GammaTable, int nEntries, double The
// ----------------------------------------------------------------------------------------
// #define DEBUG 1
#define MAX_KNOTS 4096
typedef float vec[MAX_KNOTS+1];
......@@ -144,14 +143,14 @@ LPGAMMATABLE LCMSEXPORT cmsAllocGamma(int nEntries)
LPGAMMATABLE p;
size_t size;
if (nEntries > 65530) {
cmsSignalError(LCMS_ERRC_WARNING, "Couldn't create gammatable of more than 65530 entries; 65530 assumed");
nEntries = 65530;
if (nEntries > 65530 || nEntries <= 0) {
cmsSignalError(LCMS_ERRC_ABORTED, "Couldn't create gammatable of more than 65530 entries");
return NULL;
}
size = sizeof(GAMMATABLE) + (sizeof(WORD) * (nEntries-1));
p = (LPGAMMATABLE) malloc(size);
p = (LPGAMMATABLE) _cmsMalloc(size);
if (!p) return NULL;
ZeroMemory(p, size);
......@@ -164,7 +163,7 @@ LPGAMMATABLE LCMSEXPORT cmsAllocGamma(int nEntries)
void LCMSEXPORT cmsFreeGamma(LPGAMMATABLE Gamma)
{
if (Gamma) free(Gamma);
if (Gamma) _cmsFree(Gamma);
}
......@@ -278,6 +277,15 @@ LPGAMMATABLE LCMSEXPORT cmsReverseGamma(int nResultSamples, LPGAMMATABLE InGamma
LPWORD InPtr;
LPGAMMATABLE p;
// Try to reverse it analytically whatever possible
if (InGamma -> Seed.Type > 0 && InGamma -> Seed.Type <= 5 &&
_cmsCrc32OfGammaTable(InGamma) == InGamma -> Seed.Crc32) {
return cmsBuildParametricGamma(nResultSamples, -(InGamma -> Seed.Type), InGamma ->Seed.Params);
}
// Nope, reverse the table
p = cmsAllocGamma(nResultSamples);
if (!p) return NULL;
......@@ -528,7 +536,7 @@ void smooth2(vec w, vec y, vec z, float lambda, int m)
// Smooths a curve sampled at regular intervals
BOOL LCMSEXPORT cmsSmoothGamma(LPGAMMATABLE Tab, double lambda)
LCMSBOOL LCMSEXPORT cmsSmoothGamma(LPGAMMATABLE Tab, double lambda)
{
vec w, y, z;
......@@ -640,13 +648,13 @@ LPSAMPLEDCURVE cmsAllocSampledCurve(int nItems)
{
LPSAMPLEDCURVE pOut;
pOut = (LPSAMPLEDCURVE) malloc(sizeof(SAMPLEDCURVE));
pOut = (LPSAMPLEDCURVE) _cmsMalloc(sizeof(SAMPLEDCURVE));
if (pOut == NULL)
return NULL;
if((pOut->Values = (double *) malloc(nItems * sizeof(double))) == NULL)
if((pOut->Values = (double *) _cmsMalloc(nItems * sizeof(double))) == NULL)
{
free(pOut);
_cmsFree(pOut);
return NULL;
}
......@@ -659,8 +667,8 @@ LPSAMPLEDCURVE cmsAllocSampledCurve(int nItems)
void cmsFreeSampledCurve(LPSAMPLEDCURVE p)
{
free((LPVOID) p -> Values);
free((LPVOID) p);
_cmsFree((LPVOID) p -> Values);
_cmsFree((LPVOID) p);
}
......@@ -731,7 +739,7 @@ void cmsClampSampledCurve(LPSAMPLEDCURVE p, double Min, double Max)
// Smooths a curve sampled at regular intervals
BOOL cmsSmoothSampledCurve(LPSAMPLEDCURVE Tab, double lambda)
LCMSBOOL cmsSmoothSampledCurve(LPSAMPLEDCURVE Tab, double lambda)
{
vec w, y, z;
int i, nItems;
......@@ -915,14 +923,11 @@ LPSAMPLEDCURVE cmsConvertGammaToSampledCurve(LPGAMMATABLE Gamma, int nPoints)
// Smooth endpoints (used in Black/White compensation)
BOOL _cmsSmoothEndpoints(LPWORD Table, int nEntries)
LCMSBOOL _cmsSmoothEndpoints(LPWORD Table, int nEntries)
{
vec w, y, z;
int i, Zeros, Poles;
#ifdef DEBUG
ASAVE(Table, nEntries, "nonsmt.txt");
#endif
if (cmsIsLinear(Table, nEntries)) return FALSE; // Nothing to do
......
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -66,7 +66,7 @@ to use highlights, then it will be lost.
*/
BOOL _cmsEndPointsBySpace(icColorSpaceSignature Space, WORD **White, WORD **Black,
LCMSBOOL _cmsEndPointsBySpace(icColorSpaceSignature Space, WORD **White, WORD **Black,
int *nOutputs)
{
// Only most common spaces
......@@ -376,7 +376,6 @@ double LCMSEXPORT cmsCIE2000DeltaE(LPcmsCIELab Lab1, LPcmsCIELab Lab2,
double bs = Lab2 ->b;
double Cs = sqrt( Sqr(as) + Sqr(bs) );
double G = 0.5 * ( 1 - sqrt(pow((C + Cs) / 2 , 7.0) / (pow((C + Cs) / 2, 7.0) + pow(25.0, 7.0) ) ));
double a_p = (1 + G ) * a1;
......@@ -390,15 +389,21 @@ double LCMSEXPORT cmsCIE2000DeltaE(LPcmsCIELab Lab1, LPcmsCIELab Lab2,
double C_ps = sqrt(Sqr(a_ps) + Sqr(b_ps));
double h_ps = atan2deg(a_ps, b_ps);
double meanC_p =(C_p + C_ps) / 2;
double hps_plus_hp = h_ps + h_p;
double hps_minus_hp = h_ps - h_p;
double meanC_p =(C_p + C_ps) / 2;
double meanh_p = fabs(hps_minus_hp) <= 180.000001 ? (hps_plus_hp)/2 :
(hps_plus_hp) < 360 ? (hps_plus_hp + 360)/2 :
(hps_plus_hp - 360)/2;
double meanh_p = fabs(h_ps-h_p) <= 180 ? (h_ps + h_p)/2 : (h_ps+h_p-360)/2;
double delta_h = (hps_minus_hp) <= -180.000001 ? (hps_minus_hp + 360) :
(hps_minus_hp) > 180 ? (hps_minus_hp - 360) :
(hps_minus_hp);
double delta_L = (Ls - L1);
double delta_C = (C_ps - C_p );
double delta_h = fabs(h_p - h_ps) <= 180 ? fabs(h_p - h_ps) : 360 - fabs(h_p - h_ps);
double delta_L = fabs(L1 - Ls);
double delta_C = fabs(C_p - C_ps);
double delta_H =2 * sqrt(C_ps*C_p) * sin(RADIANES(delta_h) / 2);
......@@ -1065,7 +1070,7 @@ void SlopeLimiting(WORD Table[], int nEntries)
// Check for monotonicity.
static
BOOL IsMonotonic(LPGAMMATABLE t)
LCMSBOOL IsMonotonic(LPGAMMATABLE t)
{
int n = t -> nEntries;
int i, last;
......@@ -1088,7 +1093,7 @@ BOOL IsMonotonic(LPGAMMATABLE t)
// Check for endpoints
static
BOOL HasProperEndpoints(LPGAMMATABLE t)
LCMSBOOL HasProperEndpoints(LPGAMMATABLE t)
{
if (t ->GammaTable[0] != 0) return FALSE;
if (t ->GammaTable[t ->nEntries-1] != 0xFFFF) return FALSE;
......@@ -1109,7 +1114,7 @@ void _cmsComputePrelinearizationTablesFromXFORM(cmsHTRANSFORM h[], int nTransfor
unsigned int t, i, v;
int j;
WORD In[MAXCHANNELS], Out[MAXCHANNELS];
BOOL lIsSuitable;
LCMSBOOL lIsSuitable;
_LPcmsTRANSFORM InputXForm = (_LPcmsTRANSFORM) h[0];
_LPcmsTRANSFORM OutputXForm = (_LPcmsTRANSFORM) h[nTransforms-1];
......@@ -1126,10 +1131,10 @@ void _cmsComputePrelinearizationTablesFromXFORM(cmsHTRANSFORM h[], int nTransfor
}
// Do nothing on all but RGB to RGB transforms
// Do nothing on all but Gray/RGB to Gray/RGB transforms
if ((InputXForm ->EntryColorSpace != icSigRgbData) ||
(OutputXForm->ExitColorSpace != icSigRgbData)) return;
if (((InputXForm ->EntryColorSpace != icSigRgbData) && (InputXForm ->EntryColorSpace != icSigGrayData)) ||
((OutputXForm->ExitColorSpace != icSigRgbData) && (OutputXForm->ExitColorSpace != icSigGrayData))) return;
for (t = 0; t < Grid -> InputChan; t++)
......@@ -1169,10 +1174,13 @@ void _cmsComputePrelinearizationTablesFromXFORM(cmsHTRANSFORM h[], int nTransfor
if (!HasProperEndpoints(Trans[t]))
lIsSuitable = FALSE;
/*
// Exclude if transfer function is not smooth enough
// to be modelled as a gamma function, or the gamma is reversed
if (cmsEstimateGamma(Trans[t]) < 1.0)
lIsSuitable = FALSE;
*/
}
......
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -282,7 +282,7 @@ void Eval8Inputs(WORD StageABC[], WORD StageLMN[], WORD LutTable[], LPL16PARAMS
// Fills optimization parameters
void cmsCalcCLUT16ParamsEx(int nSamples, int InputChan, int OutputChan,
BOOL lUseTetrahedral, LPL16PARAMS p)
LCMSBOOL lUseTetrahedral, LPL16PARAMS p)
{
int clutPoints;
......@@ -579,7 +579,7 @@ WORD cmsReverseLinearInterpLUT16(WORD Value, WORD LutTable[], LPL16PARAMS p)
// Identify if value fall downto 0 or FFFF zone
if (Value == 0) return 0;
if (Value == 0xFFFF) return 0xFFFF;
// if (Value == 0xFFFF) return 0xFFFF;
// else restrict to valid zone
......@@ -631,7 +631,7 @@ WORD cmsReverseLinearInterpLUT16(WORD Value, WORD LutTable[], LPL16PARAMS p)
a = (y1 - y0) / (x1 - x0);
b = y0 - a * x0;
if (a == 0) return (WORD) x;
if (fabs(a) < 0.01) return (WORD) x;
f = ((Value - b) / a);
......@@ -763,7 +763,7 @@ void cmsTrilinearInterp16(WORD Input[], WORD Output[],
X0 = p -> opta3 * x0;
X1 = X0 + (Input[0] == 0xFFFFU ? 0 : p->opta3);
Y0 = p -> opta2 * y0;
Y0 = p -> opta2 * y0;
Y1 = Y0 + (Input[1] == 0xFFFFU ? 0 : p->opta2);
Z0 = p -> opta1 * z0;
......@@ -942,7 +942,7 @@ void cmsTetrahedralInterp16(WORD Input[],
X0 = p -> opta3 * x0;
X1 = X0 + (Input[0] == 0xFFFFU ? 0 : p->opta3);
Y0 = p -> opta2 * y0;
Y0 = p -> opta2 * y0;
Y1 = Y0 + (Input[1] == 0xFFFFU ? 0 : p->opta2);
Z0 = p -> opta1 * z0;
......@@ -1009,11 +1009,11 @@ void cmsTetrahedralInterp16(WORD Input[],
Rest = c1 * rx + c2 * ry + c3 * rz;
// There is a lot of math hidden in this expression. The rest is in fixed domain
// and the result in 0..ffff domain. So the complete expression should be
// ROUND_FIXED_TO_INT(ToFixedDomain(Rest)) But that can be optimized as (Rest + 0x7FFF) / 0xFFFF
// There is a lot of math hidden in this expression. The rest is in fixed domain
// and the result in 0..ffff domain. So the complete expression should be
// ROUND_FIXED_TO_INT(ToFixedDomain(Rest)) But that can be optimized as (Rest + 0x7FFF) / 0xFFFF
Output[OutChan] = (WORD) (c0 + ((Rest + 0x7FFF) / 0xFFFF));
Output[OutChan] = (WORD) (c0 + ((Rest + 0x7FFF) / 0xFFFF));
}
......@@ -1131,3 +1131,4 @@ void cmsTetrahedralInterp8(WORD Input[],
}
#undef DENS
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -62,7 +62,7 @@
typedef struct {
LPBYTE Block; // Points to allocated memory
size_t Size; // Size of allocated memory
int Pointer; // Points to current location
size_t Pointer; // Points to current location
int FreeBlockOnClose; // As title
} FILEMEM;
......@@ -70,18 +70,19 @@ typedef struct {
static
LPVOID MemoryOpen(LPBYTE Block, size_t Size, char Mode)
{
FILEMEM* fm = (FILEMEM*) malloc(sizeof(FILEMEM));
FILEMEM* fm = (FILEMEM*) _cmsMalloc(sizeof(FILEMEM));
if (fm == NULL) return NULL;
ZeroMemory(fm, sizeof(FILEMEM));
if (Mode == 'r') {
fm ->Block = (LPBYTE) malloc(Size);
fm ->Block = (LPBYTE) _cmsMalloc(Size);
if (fm ->Block == NULL) {
free(fm);
_cmsFree(fm);
return NULL;
}
CopyMemory(fm->Block, Block, Size);
fm ->FreeBlockOnClose = TRUE;
}
......@@ -103,13 +104,27 @@ size_t MemoryRead(LPVOID buffer, size_t size, size_t count, struct _lcms_iccprof
FILEMEM* ResData = (FILEMEM*) Icc ->stream;
LPBYTE Ptr;
size_t len = size * count;
size_t extent = ResData -> Pointer + len;
if (len == 0) {
return 0;
}
if (len / size != count) {
cmsSignalError(LCMS_ERRC_ABORTED, "Read from memory error. Integer overflow with count / size.");
return 0;
}
if (ResData -> Pointer + len > ResData -> Size){
if (extent < len || extent < ResData -> Pointer) {
cmsSignalError(LCMS_ERRC_ABORTED, "Read from memory error. Integer overflow with len.");
return 0;
}
len = (ResData -> Size - ResData -> Pointer);
cmsSignalError(LCMS_ERRC_WARNING, "Read from memory error. Got %d bytes, block should be of %d bytes", len * size, count * size);
if (ResData -> Pointer + len > ResData -> Size) {
len = (ResData -> Size - ResData -> Pointer);
cmsSignalError(LCMS_ERRC_ABORTED, "Read from memory error. Got %d bytes, block should be of %d bytes", len * size, count * size);
return 0;
}
Ptr = ResData -> Block;
......@@ -123,7 +138,7 @@ size_t MemoryRead(LPVOID buffer, size_t size, size_t count, struct _lcms_iccprof
// SEEK_CUR is assumed
static
BOOL MemorySeek(struct _lcms_iccprofile_struct* Icc, size_t offset)
LCMSBOOL MemorySeek(struct _lcms_iccprofile_struct* Icc, size_t offset)
{
FILEMEM* ResData = (FILEMEM*) Icc ->stream;
......@@ -147,18 +162,19 @@ size_t MemoryTell(struct _lcms_iccprofile_struct* Icc)
}
// Writes data to memory, also keeps used space for further reference
// Writes data to memory, also keeps used space for further reference. NO CHECK IS PERFORMED
static
BOOL MemoryWrite(struct _lcms_iccprofile_struct* Icc, size_t size, void *Ptr)
LCMSBOOL MemoryWrite(struct _lcms_iccprofile_struct* Icc, size_t size, void *Ptr)
{
FILEMEM* ResData = (FILEMEM*) Icc ->stream;
if (size == 0) return TRUE;
if (ResData != NULL)
CopyMemory(ResData ->Block + Icc ->UsedSpace, Ptr, size);
CopyMemory(ResData ->Block + ResData ->Pointer, Ptr, size);
ResData->Pointer += size;
Icc->UsedSpace += size;
return TRUE;
......@@ -166,15 +182,37 @@ BOOL MemoryWrite(struct _lcms_iccprofile_struct* Icc, size_t size, void *Ptr)
static
BOOL MemoryClose(struct _lcms_iccprofile_struct* Icc)
LCMSBOOL MemoryGrow(struct _lcms_iccprofile_struct* Icc, size_t size)
{
FILEMEM* ResData = (FILEMEM*) Icc->stream;
void* newBlock = NULL;
/* Follow same policies as functions in lcms.h */
if (ResData->Size + size < 0) return NULL;
if (ResData->Size + size > ((size_t)1024*1024*500)) return NULL;
newBlock = realloc(ResData->Block, ResData->Size + size);
if (!newBlock) {
return FALSE;
}
ResData->Block = newBlock;
ResData->Size += size;
return TRUE;
}
static
LCMSBOOL MemoryClose(struct _lcms_iccprofile_struct* Icc)
{
FILEMEM* ResData = (FILEMEM*) Icc ->stream;
if (ResData ->FreeBlockOnClose) {
if (ResData ->Block) free(ResData ->Block);
if (ResData ->Block) _cmsFree(ResData ->Block);
}
free(ResData);
_cmsFree(ResData);
return 0;
}
......@@ -192,7 +230,7 @@ size_t FileRead(void *buffer, size_t size, size_t count, struct _lcms_iccprofile
{
size_t nReaded = fread(buffer, size, count, (FILE*) Icc->stream);
if (nReaded != count) {
cmsSignalError(LCMS_ERRC_WARNING, "Read error. Got %d bytes, block should be of %d bytes", nReaded * size, count * size);
cmsSignalError(LCMS_ERRC_ABORTED, "Read error. Got %d bytes, block should be of %d bytes", nReaded * size, count * size);
return 0;
}
......@@ -201,7 +239,7 @@ size_t FileRead(void *buffer, size_t size, size_t count, struct _lcms_iccprofile
static
BOOL FileSeek(struct _lcms_iccprofile_struct* Icc, size_t offset)
LCMSBOOL FileSeek(struct _lcms_iccprofile_struct* Icc, size_t offset)
{
if (fseek((FILE*) Icc ->stream, (long) offset, SEEK_SET) != 0) {
......@@ -223,7 +261,7 @@ size_t FileTell(struct _lcms_iccprofile_struct* Icc)
static
BOOL FileWrite(struct _lcms_iccprofile_struct* Icc, size_t size, LPVOID Ptr)
LCMSBOOL FileWrite(struct _lcms_iccprofile_struct* Icc, size_t size, LPVOID Ptr)
{
if (size == 0) return TRUE;
......@@ -239,7 +277,14 @@ BOOL FileWrite(struct _lcms_iccprofile_struct* Icc, size_t size, LPVOID Ptr)
static
BOOL FileClose(struct _lcms_iccprofile_struct* Icc)
LCMSBOOL FileGrow(struct _lcms_iccprofile_struct* Icc, size_t size)
{
return TRUE;
}
static
LCMSBOOL FileClose(struct _lcms_iccprofile_struct* Icc)
{
return fclose((FILE*) Icc ->stream);
}
......@@ -252,7 +297,7 @@ BOOL FileClose(struct _lcms_iccprofile_struct* Icc)
cmsHPROFILE _cmsCreateProfilePlaceholder(void)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) malloc(sizeof(LCMSICCPROFILE));
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) _cmsMalloc(sizeof(LCMSICCPROFILE));
if (Icc == NULL) return NULL;
// Empty values
......@@ -290,7 +335,7 @@ icTagSignature LCMSEXPORT cmsGetTagSignature(cmsHPROFILE hProfile, icInt32Number
// Search for a specific tag in tag dictionary
// Returns position or -1 if tag not found
icInt32Number _cmsSearchTag(LPLCMSICCPROFILE Profile, icTagSignature sig, BOOL lSignalError)
icInt32Number _cmsSearchTag(LPLCMSICCPROFILE Profile, icTagSignature sig, LCMSBOOL lSignalError)
{
icInt32Number i;
......@@ -311,7 +356,7 @@ icInt32Number _cmsSearchTag(LPLCMSICCPROFILE Profile, icTagSignature sig, BOOL l
// Check existance
BOOL LCMSEXPORT cmsIsTag(cmsHPROFILE hProfile, icTagSignature sig)
LCMSBOOL LCMSEXPORT cmsIsTag(cmsHPROFILE hProfile, icTagSignature sig)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
return _cmsSearchTag(Icc, sig, FALSE) >= 0;
......@@ -330,7 +375,7 @@ LPVOID _cmsInitTag(LPLCMSICCPROFILE Icc, icTagSignature sig, size_t size, const
if (i >=0) {
if (Icc -> TagPtrs[i]) free(Icc -> TagPtrs[i]);
if (Icc -> TagPtrs[i]) _cmsFree(Icc -> TagPtrs[i]);
}
else {
......@@ -341,11 +386,14 @@ LPVOID _cmsInitTag(LPLCMSICCPROFILE Icc, icTagSignature sig, size_t size, const
cmsSignalError(LCMS_ERRC_ABORTED, "Too many tags (%d)", MAX_TABLE_TAG);
Icc ->TagCount = MAX_TABLE_TAG-1;
return NULL;
}
}
Ptr = malloc(size);
Ptr = _cmsMalloc(size);
if (Ptr == NULL) return NULL;
CopyMemory(Ptr, Init, size);
Icc ->TagNames[i] = sig;
......@@ -376,12 +424,15 @@ LPLCMSICCPROFILE _cmsCreateProfileFromFilePlaceholder(const char* FileName)
if (NewIcc == NULL) return NULL;
strncpy(NewIcc -> PhysicalFile, FileName, MAX_PATH-1);
NewIcc -> PhysicalFile[MAX_PATH-1] = 0;
NewIcc ->stream = ICCfile;
NewIcc ->Read = FileRead;
NewIcc ->Seek = FileSeek;
NewIcc ->Tell = FileTell;
NewIcc ->Close = FileClose;
NewIcc ->Grow = FileGrow;
NewIcc ->Write = NULL;
NewIcc ->IsWrite = FALSE;
......@@ -419,7 +470,8 @@ LPLCMSICCPROFILE _cmsCreateProfileFromMemPlaceholder(LPVOID MemPtr, DWORD dwSize
NewIcc ->Seek = MemorySeek;
NewIcc ->Tell = MemoryTell;
NewIcc ->Close = MemoryClose;
NewIcc ->Write = NULL;
NewIcc ->Grow = MemoryGrow;
NewIcc ->Write = MemoryWrite;
NewIcc ->IsWrite = FALSE;
......@@ -476,7 +528,7 @@ void _cmsSetSaveToMemory(LPLCMSICCPROFILE Icc, LPVOID MemPtr, size_t dwSize)
BOOL LCMSEXPORT cmsTakeMediaWhitePoint(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
LCMSBOOL LCMSEXPORT cmsTakeMediaWhitePoint(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
*Dest = Icc -> MediaWhitePoint;
......@@ -484,14 +536,14 @@ BOOL LCMSEXPORT cmsTakeMediaWhitePoint(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
}
BOOL LCMSEXPORT cmsTakeMediaBlackPoint(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
LCMSBOOL LCMSEXPORT cmsTakeMediaBlackPoint(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
*Dest = Icc -> MediaBlackPoint;
return TRUE;
}
BOOL LCMSEXPORT cmsTakeIluminant(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
LCMSBOOL LCMSEXPORT cmsTakeIluminant(LPcmsCIEXYZ Dest, cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
*Dest = Icc -> Illuminant;
......@@ -549,7 +601,7 @@ void LCMSEXPORT cmsSetProfileID(cmsHPROFILE hProfile, LPBYTE ProfileID)
}
BOOL LCMSEXPORT cmsTakeCreationDateTime(struct tm *Dest, cmsHPROFILE hProfile)
LCMSBOOL LCMSEXPORT cmsTakeCreationDateTime(struct tm *Dest, cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
CopyMemory(Dest, &Icc ->Created, sizeof(struct tm));
......@@ -570,23 +622,18 @@ void LCMSEXPORT cmsSetPCS(cmsHPROFILE hProfile, icColorSpaceSignature pcs)
Icc -> PCS = pcs;
}
icColorSpaceSignature LCMSEXPORT cmsGetColorSpace(cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
return Icc -> ColorSpace;
}
void LCMSEXPORT cmsSetColorSpace(cmsHPROFILE hProfile, icColorSpaceSignature sig)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
Icc -> ColorSpace = sig;
}
icProfileClassSignature LCMSEXPORT cmsGetDeviceClass(cmsHPROFILE hProfile)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
......@@ -599,7 +646,6 @@ DWORD LCMSEXPORT cmsGetProfileICCversion(cmsHPROFILE hProfile)
return (DWORD) Icc -> Version;
}
void LCMSEXPORT cmsSetProfileICCversion(cmsHPROFILE hProfile, DWORD Version)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) hProfile;
......@@ -638,7 +684,7 @@ LPVOID DupBlock(LPLCMSICCPROFILE Icc, LPVOID Block, size_t size)
// This is tricky, since LUT structs does have pointers
BOOL LCMSEXPORT _cmsAddLUTTag(cmsHPROFILE hProfile, icTagSignature sig, const void* lut)
LCMSBOOL LCMSEXPORT _cmsAddLUTTag(cmsHPROFILE hProfile, icTagSignature sig, const void* lut)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
LPLUT Orig, Stored;
......@@ -666,7 +712,7 @@ BOOL LCMSEXPORT _cmsAddLUTTag(cmsHPROFILE hProfile, icTagSignature sig, const vo
}
BOOL LCMSEXPORT _cmsAddXYZTag(cmsHPROFILE hProfile, icTagSignature sig, const cmsCIEXYZ* XYZ)
LCMSBOOL LCMSEXPORT _cmsAddXYZTag(cmsHPROFILE hProfile, icTagSignature sig, const cmsCIEXYZ* XYZ)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
......@@ -675,7 +721,7 @@ BOOL LCMSEXPORT _cmsAddXYZTag(cmsHPROFILE hProfile, icTagSignature sig, const cm
}
BOOL LCMSEXPORT _cmsAddTextTag(cmsHPROFILE hProfile, icTagSignature sig, const char* Text)
LCMSBOOL LCMSEXPORT _cmsAddTextTag(cmsHPROFILE hProfile, icTagSignature sig, const char* Text)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
......@@ -683,7 +729,7 @@ BOOL LCMSEXPORT _cmsAddTextTag(cmsHPROFILE hProfile, icTagSignature sig, const c
return TRUE;
}
BOOL LCMSEXPORT _cmsAddGammaTag(cmsHPROFILE hProfile, icTagSignature sig, LPGAMMATABLE TransferFunction)
LCMSBOOL LCMSEXPORT _cmsAddGammaTag(cmsHPROFILE hProfile, icTagSignature sig, LPGAMMATABLE TransferFunction)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
......@@ -692,7 +738,7 @@ BOOL LCMSEXPORT _cmsAddGammaTag(cmsHPROFILE hProfile, icTagSignature sig, LPGAMM
}
BOOL LCMSEXPORT _cmsAddChromaticityTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsCIExyYTRIPLE Chrm)
LCMSBOOL LCMSEXPORT _cmsAddChromaticityTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsCIExyYTRIPLE Chrm)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
......@@ -701,7 +747,7 @@ BOOL LCMSEXPORT _cmsAddChromaticityTag(cmsHPROFILE hProfile, icTagSignature sig,
}
BOOL LCMSEXPORT _cmsAddSequenceDescriptionTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsSEQ pseq)
LCMSBOOL LCMSEXPORT _cmsAddSequenceDescriptionTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsSEQ pseq)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
......@@ -711,28 +757,40 @@ BOOL LCMSEXPORT _cmsAddSequenceDescriptionTag(cmsHPROFILE hProfile, icTagSignatu
}
BOOL LCMSEXPORT _cmsAddNamedColorTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsNAMEDCOLORLIST nc)
LCMSBOOL LCMSEXPORT _cmsAddNamedColorTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsNAMEDCOLORLIST nc)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
_cmsInitTag(Icc, sig, sizeof(cmsNAMEDCOLORLIST) + (nc ->nColors - 1) * sizeof(cmsNAMEDCOLOR), nc);
return FALSE;
return TRUE;
}
BOOL LCMSEXPORT _cmsAddDateTimeTag(cmsHPROFILE hProfile, icTagSignature sig, struct tm *DateTime)
LCMSBOOL LCMSEXPORT _cmsAddDateTimeTag(cmsHPROFILE hProfile, icTagSignature sig, struct tm *DateTime)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
_cmsInitTag(Icc, sig, sizeof(struct tm), DateTime);
return FALSE;
return TRUE;
}
BOOL LCMSEXPORT _cmsAddColorantTableTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsNAMEDCOLORLIST nc)
LCMSBOOL LCMSEXPORT _cmsAddColorantTableTag(cmsHPROFILE hProfile, icTagSignature sig, LPcmsNAMEDCOLORLIST nc)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
_cmsInitTag(Icc, sig, sizeof(cmsNAMEDCOLORLIST) + (nc ->nColors - 1) * sizeof(cmsNAMEDCOLOR), nc);
return FALSE;
return TRUE;
}
LCMSBOOL LCMSEXPORT _cmsAddChromaticAdaptationTag(cmsHPROFILE hProfile, icTagSignature sig, const cmsCIEXYZ* mat)
{
LPLCMSICCPROFILE Icc = (LPLCMSICCPROFILE) (LPSTR) hProfile;
_cmsInitTag(Icc, sig, 3*sizeof(cmsCIEXYZ), mat);
return TRUE;
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -118,7 +118,7 @@ LPLUT LCMSEXPORT cmsAllocLUT(void)
{
LPLUT NewLUT;
NewLUT = (LPLUT) malloc(sizeof(LUT));
NewLUT = (LPLUT) _cmsMalloc(sizeof(LUT));
if (NewLUT)
ZeroMemory(NewLUT, sizeof(LUT));
......@@ -171,9 +171,10 @@ void LCMSEXPORT cmsFreeLUT(LPLUT Lut)
static
LPVOID DupBlockTab(LPVOID Org, size_t size)
{
LPVOID mem = malloc(size);
LPVOID mem = _cmsMalloc(size);
if (mem != NULL)
CopyMemory(mem, Org, size);
CopyMemory(mem, Org, size);
return mem;
}
......@@ -211,6 +212,37 @@ unsigned int UIpow(unsigned int a, unsigned int b)
}
LCMSBOOL _cmsValidateLUT(LPLUT NewLUT)
{
unsigned int calc = 1;
unsigned int oldCalc;
unsigned int power = NewLUT -> InputChan;
if (NewLUT -> cLutPoints > 100) return FALSE;
if (NewLUT -> InputChan > MAXCHANNELS) return FALSE;
if (NewLUT -> OutputChan > MAXCHANNELS) return FALSE;
if (NewLUT -> cLutPoints == 0) return TRUE;
for (; power > 0; power--) {
oldCalc = calc;
calc *= NewLUT -> cLutPoints;
if (calc / NewLUT -> cLutPoints != oldCalc) {
return FALSE;
}
}
oldCalc = calc;
calc *= NewLUT -> OutputChan;
if (NewLUT -> OutputChan && calc / NewLUT -> OutputChan != oldCalc) {
return FALSE;
}
return TRUE;
}
LPLUT LCMSEXPORT cmsAlloc3DGrid(LPLUT NewLUT, int clutPoints, int inputChan, int outputChan)
{
DWORD nTabSize;
......@@ -220,12 +252,17 @@ LPLUT LCMSEXPORT cmsAlloc3DGrid(LPLUT NewLUT, int clutPoints, int inputChan, int
NewLUT -> InputChan = inputChan;
NewLUT -> OutputChan = outputChan;
if (!_cmsValidateLUT(NewLUT)) {
return NULL;
}
nTabSize = NewLUT -> OutputChan * UIpow(NewLUT->cLutPoints,
NewLUT->InputChan);
nTabSize = (NewLUT -> OutputChan * UIpow(NewLUT->cLutPoints,
NewLUT->InputChan)
* sizeof(WORD));
NewLUT -> T = (LPWORD) _cmsCalloc(sizeof(WORD), nTabSize);
nTabSize *= sizeof(WORD);
if (NewLUT -> T == NULL) return NULL;
NewLUT -> T = (LPWORD) malloc(nTabSize);
ZeroMemory(NewLUT -> T, nTabSize);
NewLUT ->Tsize = nTabSize;
......@@ -254,10 +291,12 @@ LPLUT LCMSEXPORT cmsAllocLinearTable(LPLUT NewLUT, LPGAMMATABLE Tables[], int nT
for (i=0; i < NewLUT -> InputChan; i++) {
PtrW = (LPWORD) malloc(sizeof(WORD) * NewLUT -> InputEntries);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * NewLUT -> InputEntries);
if (PtrW == NULL) return NULL;
NewLUT -> L1[i] = PtrW;
CopyMemory(PtrW, Tables[i]->GammaTable, sizeof(WORD) * NewLUT -> InputEntries);
CopyMemory(&NewLUT -> LCurvesSeed[0][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
CopyMemory(&NewLUT -> LCurvesSeed[0][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
}
......@@ -268,10 +307,12 @@ LPLUT LCMSEXPORT cmsAllocLinearTable(LPLUT NewLUT, LPGAMMATABLE Tables[], int nT
NewLUT -> OutputEntries = Tables[0] -> nEntries;
for (i=0; i < NewLUT -> OutputChan; i++) {
PtrW = (LPWORD) malloc(sizeof(WORD) * NewLUT -> OutputEntries);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * NewLUT -> OutputEntries);
if (PtrW == NULL) return NULL;
NewLUT -> L2[i] = PtrW;
CopyMemory(PtrW, Tables[i]->GammaTable, sizeof(WORD) * NewLUT -> OutputEntries);
CopyMemory(&NewLUT -> LCurvesSeed[1][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
CopyMemory(&NewLUT -> LCurvesSeed[1][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
}
break;
......@@ -285,10 +326,12 @@ LPLUT LCMSEXPORT cmsAllocLinearTable(LPLUT NewLUT, LPGAMMATABLE Tables[], int nT
for (i=0; i < NewLUT -> InputChan; i++) {
PtrW = (LPWORD) malloc(sizeof(WORD) * NewLUT -> L3Entries);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * NewLUT -> L3Entries);
if (PtrW == NULL) return NULL;
NewLUT -> L3[i] = PtrW;
CopyMemory(PtrW, Tables[i]->GammaTable, sizeof(WORD) * NewLUT -> L3Entries);
CopyMemory(&NewLUT -> LCurvesSeed[2][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
CopyMemory(&NewLUT -> LCurvesSeed[2][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
}
break;
......@@ -298,10 +341,12 @@ LPLUT LCMSEXPORT cmsAllocLinearTable(LPLUT NewLUT, LPGAMMATABLE Tables[], int nT
NewLUT -> L4Entries = Tables[0] -> nEntries;
for (i=0; i < NewLUT -> OutputChan; i++) {
PtrW = (LPWORD) malloc(sizeof(WORD) * NewLUT -> L4Entries);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * NewLUT -> L4Entries);
if (PtrW == NULL) return NULL;
NewLUT -> L4[i] = PtrW;
CopyMemory(PtrW, Tables[i]->GammaTable, sizeof(WORD) * NewLUT -> L4Entries);
CopyMemory(&NewLUT -> LCurvesSeed[3][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
CopyMemory(&NewLUT -> LCurvesSeed[3][i], &Tables[i] -> Seed, sizeof(LCMSGAMMAPARAMS));
}
break;
......@@ -580,7 +625,7 @@ LPLUT _cmsBlessLUT8(LPLUT Lut)
LPL16PARAMS p = &Lut ->CLut16params;
p8 = (LPL8PARAMS) malloc(sizeof(L8PARAMS));
p8 = (LPL8PARAMS) _cmsMalloc(sizeof(L8PARAMS));
if (p8 == NULL) return NULL;
// values comes * 257, so we can safely take first byte (x << 8 + x)
......@@ -593,8 +638,8 @@ LPLUT _cmsBlessLUT8(LPLUT Lut)
if (Lut ->wFlags & LUT_HASTL1) {
for (j=0; j < 3; j++)
StageABC[i] = cmsLinearInterpLUT16(StageABC[i],
Lut -> L1[i],
StageABC[j] = cmsLinearInterpLUT16(StageABC[j],
Lut -> L1[j],
&Lut -> In16params);
Lut ->wFlags &= ~LUT_HASTL1;
}
......@@ -697,7 +742,7 @@ void EvalLUTdoubleKLab(LPLUT Lut, const VEC3* In, WORD FixedK, LPcmsCIELab Out)
wIn[3] = FixedK;
cmsEvalLUT(Lut, wIn, wOut);
cmsLabEncoded2Float(Out, wOut);
cmsLabEncoded2Float(Out, wOut);
}
// Builds a Jacobian CMY->Lab
......@@ -722,9 +767,9 @@ void ComputeJacobianLab(LPLUT Lut, LPMAT3 Jacobian, const VEC3* Colorant, WORD K
EvalLUTdoubleKLab(Lut, &ColorantD, K, &LabD);
Jacobian->v[0].n[j] = ((LabD.L - Lab.L) / JACOBIAN_EPSILON);
Jacobian->v[1].n[j] = ((LabD.a - Lab.a) / JACOBIAN_EPSILON);
Jacobian->v[2].n[j] = ((LabD.b - Lab.b) / JACOBIAN_EPSILON);
Jacobian->v[0].n[j] = ((LabD.L - Lab.L) / JACOBIAN_EPSILON);
Jacobian->v[1].n[j] = ((LabD.a - Lab.a) / JACOBIAN_EPSILON);
Jacobian->v[2].n[j] = ((LabD.b - Lab.b) / JACOBIAN_EPSILON);
}
}
......@@ -797,18 +842,18 @@ LCMSAPI double LCMSEXPORT cmsEvalLUTreverse(LPLUT Lut, WORD Target[], WORD Resul
// Obtain slope
ComputeJacobianLab(Lut, &Jacobian, &x, FixedK);
// Solve system
tmp2.n[0] = fx.L - Goal.L;
tmp2.n[1] = fx.a - Goal.a;
tmp2.n[2] = fx.b - Goal.b;
// Solve system
tmp2.n[0] = fx.L - Goal.L;
tmp2.n[1] = fx.a - Goal.a;
tmp2.n[2] = fx.b - Goal.b;
if (!MAT3solve(&tmp, &Jacobian, &tmp2))
break;
if (!MAT3solve(&tmp, &Jacobian, &tmp2))
break;
// Move our guess
x.n[0] -= tmp.n[0];
x.n[1] -= tmp.n[1];
x.n[2] -= tmp.n[2];
x.n[0] -= tmp.n[0];
x.n[1] -= tmp.n[1];
x.n[2] -= tmp.n[2];
// Some clipping....
VEC3saturate(&x);
......@@ -822,3 +867,6 @@ LCMSAPI double LCMSEXPORT cmsEvalLUTreverse(LPLUT Lut, WORD Target[], WORD Resul
return LastError;
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -62,6 +62,7 @@
// data yet in fixed point, so no additional process is required.
// Then, we obtain data on 15.16, so we need to shift >> by 1 to
// obtain 1.15 PCS format.
// On OUTPUT profiles, things are inverse, we must first expand 1 bit
// by shifting left, and then convert result between 0 and 1.000 to
// RGB, so FromFixedDomain() must be called before pass values to
......@@ -71,6 +72,7 @@
// input is encoded from 0 to 0xffff, we must first use the shaper and
// then the matrix, an additional FromFixedDomain() must be used to
// accomodate output values.
// For a sake of simplicity, I will handle this three behaviours
// with different routines, so the flags MATSHAPER_INPUT and MATSHAPER_OUTPUT
// can be conbined to signal smelted matrix-shapers
......@@ -89,7 +91,7 @@ int ComputeTables(LPGAMMATABLE Table[3], LPWORD Out[3], LPL16PARAMS p16)
{
LPWORD PtrW;
PtrW = (LPWORD) malloc(sizeof(WORD) * p16 -> nSamples);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * p16 -> nSamples);
if (PtrW == NULL) return -1; // Signal error
......@@ -119,7 +121,7 @@ LPMATSHAPER cmsAllocMatShaper2(LPMAT3 Matrix, LPGAMMATABLE In[], LPGAMMATABLE Ou
LPMATSHAPER NewMatShaper;
int rc;
NewMatShaper = (LPMATSHAPER) malloc(sizeof(MATSHAPER));
NewMatShaper = (LPMATSHAPER) _cmsMalloc(sizeof(MATSHAPER));
if (NewMatShaper)
ZeroMemory(NewMatShaper, sizeof(MATSHAPER));
......@@ -171,7 +173,13 @@ LPMATSHAPER cmsAllocMatShaper(LPMAT3 Matrix, LPGAMMATABLE Tables[], DWORD Behavi
LPMATSHAPER NewMatShaper;
int i, AllLinear;
NewMatShaper = (LPMATSHAPER) malloc(sizeof(MATSHAPER));
if (Matrix == NULL) return NULL;
for (i=0; i < 3; i++) {
if (Tables[i] == NULL) return NULL;
}
NewMatShaper = (LPMATSHAPER) _cmsMalloc(sizeof(MATSHAPER));
if (NewMatShaper)
ZeroMemory(NewMatShaper, sizeof(MATSHAPER));
......@@ -187,17 +195,16 @@ LPMATSHAPER cmsAllocMatShaper(LPMAT3 Matrix, LPGAMMATABLE Tables[], DWORD Behavi
NewMatShaper -> dwFlags |= MATSHAPER_HASMATRIX;
// Now, on the table characteristics
cmsCalcL16Params(Tables[0] -> nEntries, &NewMatShaper -> p16);
// Copy tables
AllLinear = 0;
for (i=0; i < 3; i++)
{
for (i=0; i < 3; i++) {
LPWORD PtrW;
PtrW = (LPWORD) malloc(sizeof(WORD) * NewMatShaper -> p16.nSamples);
PtrW = (LPWORD) _cmsMalloc(sizeof(WORD) * NewMatShaper -> p16.nSamples);
if (PtrW == NULL) {
cmsFreeMatShaper(NewMatShaper);
......@@ -235,11 +242,11 @@ void cmsFreeMatShaper(LPMATSHAPER MatShaper)
for (i=0; i < 3; i++)
{
if (MatShaper -> L[i]) free(MatShaper ->L[i]);
if (MatShaper -> L2[i]) free(MatShaper ->L2[i]);
if (MatShaper -> L[i]) _cmsFree(MatShaper ->L[i]);
if (MatShaper -> L2[i]) _cmsFree(MatShaper ->L2[i]);
}
free(MatShaper);
_cmsFree(MatShaper);
}
......
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -71,16 +71,16 @@ double cdecl VEC3length(LPVEC3 a);
double cdecl VEC3distance(LPVEC3 a, LPVEC3 b);
void cdecl MAT3identity(LPMAT3 a);
void cdecl MAT3per(LPMAT3 r, LPMAT3 a, LPMAT3 b);
int cdecl MAT3inverse(LPMAT3 a, LPMAT3 b);
BOOL cdecl MAT3solve(LPVEC3 x, LPMAT3 a, LPVEC3 b);
double cdecl MAT3det(LPMAT3 m);
void cdecl MAT3eval(LPVEC3 r, LPMAT3 a, LPVEC3 v);
void cdecl MAT3toFix(LPWMAT3 r, LPMAT3 v);
void cdecl MAT3evalW(LPWVEC3 r, LPWMAT3 a, LPWVEC3 v);
void cdecl MAT3perK(LPMAT3 r, LPMAT3 v, double d);
void cdecl MAT3scaleAndCut(LPWMAT3 r, LPMAT3 v, double d);
void cdecl MAT3identity(LPMAT3 a);
void cdecl MAT3per(LPMAT3 r, LPMAT3 a, LPMAT3 b);
int cdecl MAT3inverse(LPMAT3 a, LPMAT3 b);
LCMSBOOL cdecl MAT3solve(LPVEC3 x, LPMAT3 a, LPVEC3 b);
double cdecl MAT3det(LPMAT3 m);
void cdecl MAT3eval(LPVEC3 r, LPMAT3 a, LPVEC3 v);
void cdecl MAT3toFix(LPWMAT3 r, LPMAT3 v);
void cdecl MAT3evalW(LPWVEC3 r, LPWMAT3 a, LPWVEC3 v);
void cdecl MAT3perK(LPMAT3 r, LPMAT3 v, double d);
void cdecl MAT3scaleAndCut(LPWMAT3 r, LPMAT3 v, double d);
// --------------------- Implementation ----------------------------
......@@ -345,13 +345,13 @@ void VEC3minus(LPVEC3 r, LPVEC3 a, LPVEC3 b)
// Check id two vectors are the same, allowing tolerance
static
BOOL RangeCheck(double l, double h, double v)
LCMSBOOL RangeCheck(double l, double h, double v)
{
return (v >= l && v <= h);
}
BOOL VEC3equal(LPWVEC3 a, LPWVEC3 b, double Tolerance)
LCMSBOOL VEC3equal(LPWVEC3 a, LPWVEC3 b, double Tolerance)
{
int i;
double c;
......@@ -367,7 +367,7 @@ BOOL VEC3equal(LPWVEC3 a, LPWVEC3 b, double Tolerance)
return TRUE;
}
BOOL VEC3equalF(LPVEC3 a, LPVEC3 b, double Tolerance)
LCMSBOOL VEC3equalF(LPVEC3 a, LPVEC3 b, double Tolerance)
{
int i;
double c;
......@@ -462,7 +462,7 @@ void MAT3identity(LPMAT3 a)
// Check if matrix is Identity. Allow a tolerance as %
BOOL MAT3isIdentity(LPWMAT3 a, double Tolerance)
LCMSBOOL MAT3isIdentity(LPWMAT3 a, double Tolerance)
{
int i;
MAT3 Idd;
......@@ -545,16 +545,16 @@ int MAT3inverse(LPMAT3 a, LPMAT3 b)
// Solve a system in the form Ax = b
BOOL MAT3solve(LPVEC3 x, LPMAT3 a, LPVEC3 b)
LCMSBOOL MAT3solve(LPVEC3 x, LPMAT3 a, LPVEC3 b)
{
MAT3 m, a_1;
MAT3 m, a_1;
CopyMemory(&m, a, sizeof(MAT3));
CopyMemory(&m, a, sizeof(MAT3));
if (!MAT3inverse(&m, &a_1)) return FALSE; // Singular matrix
if (!MAT3inverse(&m, &a_1)) return FALSE; // Singular matrix
MAT3eval(x, &a_1, b);
return TRUE;
MAT3eval(x, &a_1, b);
return TRUE;
}
......@@ -839,3 +839,7 @@ void MAT3scaleAndCut(LPWMAT3 r, LPMAT3 v, double d)
VEC3scaleAndCut(&r -> v[1], &v -> v[1], d);
VEC3scaleAndCut(&r -> v[2], &v -> v[2], d);
}
......@@ -29,7 +29,7 @@
//
//
// Little cms
// Copyright (C) 1998-2006 Marti Maria
// Copyright (C) 1998-2007 Marti Maria
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the "Software"),
......@@ -624,3 +624,7 @@ void LCMSEXPORT cmsXYZEncoded2Float(LPcmsCIEXYZ fXYZ, const WORD XYZ[3])
fXYZ -> Z = XYZ2float(XYZ[2]);
}
......@@ -206,6 +206,11 @@ typedef __int32_t icInt64Number[2];
#if defined(__sun) || defined(__hpux) || defined (__MINGW) || defined(__MINGW32__)
#if defined (__MINGW) || defined(__MINGW32__)
#include <stdint.h>
#endif
typedef uint8_t icUInt8Number;
typedef uint16_t icUInt16Number;
typedef uint32_t icUInt32Number;
......
......@@ -27,9 +27,6 @@ package sun.awt.X11;
import sun.awt.PlatformFont;
import java.awt.GraphicsEnvironment;
/* FIX ME */
import sun.awt.motif.MFontConfiguration;
public class XFontPeer extends PlatformFont {
/*
......@@ -51,10 +48,6 @@ public class XFontPeer extends PlatformFont {
public XFontPeer(String name, int style){
super(name, style);
if (fontConfig != null){
xfsname = ((MFontConfiguration) fontConfig).getMotifFontSet(familyName, style);
}
}
protected char getMissingGlyphCharacter() {
......
......@@ -15,7 +15,7 @@
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* along with this work; if not, write to the Free Software Foundation,
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
......@@ -87,6 +87,7 @@ public class FcFontConfiguration extends FontConfiguration {
return true;
}
setFontConfiguration();
readFcInfo();
if (fcCompFonts == null) {
fcCompFonts = FontManager.loadFontConfig();
......@@ -172,7 +173,7 @@ public class FcFontConfiguration extends FontConfiguration {
@Override
public FontDescriptor[] getFontDescriptors(String fontName, int style) {
throw new InternalError("Not implemented");
return new FontDescriptor[0];
}
@Override
......
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册