mirror of https://github.com/apache/poi.git
Charset.forName() for known encodings makes catching UnknownEncodingException obsolete
Unify UTF-16LE conversion to StringUtil BugFix for RecordInputStream.readFully in combination with continuing records BugFix for integration tests - fix pathname for handler/exclude lookup on windows git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1648032 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
70d7ec0e69
commit
b91e480006
|
@ -16,3 +16,8 @@ This product contains the Piccolo XML Parser for Java
|
||||||
|
|
||||||
This product contains the chunks_parse_cmds.tbl file from the vsdump program.
|
This product contains the chunks_parse_cmds.tbl file from the vsdump program.
|
||||||
Copyright (C) 2006-2007 Valek Filippov (frob@df.ru)
|
Copyright (C) 2006-2007 Valek Filippov (frob@df.ru)
|
||||||
|
|
||||||
|
This product contains parts of the eID Applet project
|
||||||
|
(http://eid-applet.googlecode.com). Copyright (c) 2009-2014
|
||||||
|
FedICT (federal ICT department of Belgium), e-Contract.be BVBA (https://www.e-contract.be),
|
||||||
|
Bart Hanssens from FedICT
|
|
@ -22,8 +22,8 @@ import java.io.FileOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.OutputStreamWriter;
|
import java.io.OutputStreamWriter;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.io.Writer;
|
import java.io.Writer;
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.hwpf.model.StyleDescription;
|
import org.apache.poi.hwpf.model.StyleDescription;
|
||||||
import org.apache.poi.hwpf.model.StyleSheet;
|
import org.apache.poi.hwpf.model.StyleSheet;
|
||||||
|
@ -37,10 +37,9 @@ public final class Word2Forrest
|
||||||
HWPFDocument _doc;
|
HWPFDocument _doc;
|
||||||
|
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
public Word2Forrest(HWPFDocument doc, OutputStream stream)
|
public Word2Forrest(HWPFDocument doc, OutputStream stream) throws IOException
|
||||||
throws IOException, UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
OutputStreamWriter out = new OutputStreamWriter (stream, "UTF-8");
|
OutputStreamWriter out = new OutputStreamWriter (stream, Charset.forName("UTF-8"));
|
||||||
_out = out;
|
_out = out;
|
||||||
_doc = doc;
|
_doc = doc;
|
||||||
|
|
||||||
|
|
|
@ -20,6 +20,7 @@ package org.apache.poi;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
import static org.junit.Assert.assertNotNull;
|
import static org.junit.Assert.assertNotNull;
|
||||||
|
|
||||||
|
import java.io.BufferedInputStream;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileInputStream;
|
import java.io.FileInputStream;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
@ -153,7 +154,6 @@ public class TestAllFiles {
|
||||||
private static final Set<String> EXPECTED_FAILURES = new HashSet<String>();
|
private static final Set<String> EXPECTED_FAILURES = new HashSet<String>();
|
||||||
static {
|
static {
|
||||||
// password protected files
|
// password protected files
|
||||||
EXPECTED_FAILURES.add("poifs/protect.xlsx");
|
|
||||||
EXPECTED_FAILURES.add("spreadsheet/password.xls");
|
EXPECTED_FAILURES.add("spreadsheet/password.xls");
|
||||||
EXPECTED_FAILURES.add("spreadsheet/51832.xls");
|
EXPECTED_FAILURES.add("spreadsheet/51832.xls");
|
||||||
EXPECTED_FAILURES.add("document/PasswordProtected.doc");
|
EXPECTED_FAILURES.add("document/PasswordProtected.doc");
|
||||||
|
@ -161,10 +161,14 @@ public class TestAllFiles {
|
||||||
EXPECTED_FAILURES.add("slideshow/Password_Protected-56-hello.ppt");
|
EXPECTED_FAILURES.add("slideshow/Password_Protected-56-hello.ppt");
|
||||||
EXPECTED_FAILURES.add("slideshow/Password_Protected-np-hello.ppt");
|
EXPECTED_FAILURES.add("slideshow/Password_Protected-np-hello.ppt");
|
||||||
EXPECTED_FAILURES.add("slideshow/cryptoapi-proc2356.ppt");
|
EXPECTED_FAILURES.add("slideshow/cryptoapi-proc2356.ppt");
|
||||||
EXPECTED_FAILURES.add("document/bug53475-password-is-pass.docx");
|
//EXPECTED_FAILURES.add("document/bug53475-password-is-pass.docx");
|
||||||
EXPECTED_FAILURES.add("document/bug53475-password-is-solrcell.docx");
|
//EXPECTED_FAILURES.add("document/bug53475-password-is-solrcell.docx");
|
||||||
EXPECTED_FAILURES.add("spreadsheet/xor-encryption-abc.xls");
|
EXPECTED_FAILURES.add("spreadsheet/xor-encryption-abc.xls");
|
||||||
EXPECTED_FAILURES.add("spreadsheet/35897-type4.xls");
|
EXPECTED_FAILURES.add("spreadsheet/35897-type4.xls");
|
||||||
|
//EXPECTED_FAILURES.add("poifs/protect.xlsx");
|
||||||
|
//EXPECTED_FAILURES.add("poifs/protected_sha512.xlsx");
|
||||||
|
//EXPECTED_FAILURES.add("poifs/extenxls_pwd123.xlsx");
|
||||||
|
//EXPECTED_FAILURES.add("poifs/protected_agile.docx");
|
||||||
|
|
||||||
// TODO: fails XMLExportTest, is this ok?
|
// TODO: fails XMLExportTest, is this ok?
|
||||||
EXPECTED_FAILURES.add("spreadsheet/CustomXMLMapping-singleattributenamespace.xlsx");
|
EXPECTED_FAILURES.add("spreadsheet/CustomXMLMapping-singleattributenamespace.xlsx");
|
||||||
|
@ -178,15 +182,12 @@ public class TestAllFiles {
|
||||||
// TODO: good to ignore?
|
// TODO: good to ignore?
|
||||||
EXPECTED_FAILURES.add("spreadsheet/sample-beta.xlsx");
|
EXPECTED_FAILURES.add("spreadsheet/sample-beta.xlsx");
|
||||||
EXPECTED_FAILURES.add("spreadsheet/49931.xls");
|
EXPECTED_FAILURES.add("spreadsheet/49931.xls");
|
||||||
EXPECTED_FAILURES.add("poifs/protected_sha512.xlsx");
|
|
||||||
EXPECTED_FAILURES.add("poifs/extenxls_pwd123.xlsx");
|
|
||||||
EXPECTED_FAILURES.add("openxml4j/ContentTypeHasParameters.ooxml");
|
EXPECTED_FAILURES.add("openxml4j/ContentTypeHasParameters.ooxml");
|
||||||
|
|
||||||
// This is actually a spreadsheet!
|
// This is actually a spreadsheet!
|
||||||
EXPECTED_FAILURES.add("hpsf/TestRobert_Flaherty.doc");
|
EXPECTED_FAILURES.add("hpsf/TestRobert_Flaherty.doc");
|
||||||
|
|
||||||
// some files that are broken, Excel 5.0/95, Word 95, ...
|
// some files that are broken, Excel 5.0/95, Word 95, ...
|
||||||
EXPECTED_FAILURES.add("poifs/protected_agile.docx");
|
|
||||||
EXPECTED_FAILURES.add("spreadsheet/43493.xls");
|
EXPECTED_FAILURES.add("spreadsheet/43493.xls");
|
||||||
EXPECTED_FAILURES.add("spreadsheet/46904.xls");
|
EXPECTED_FAILURES.add("spreadsheet/46904.xls");
|
||||||
EXPECTED_FAILURES.add("document/56880.doc");
|
EXPECTED_FAILURES.add("document/56880.doc");
|
||||||
|
@ -231,6 +232,7 @@ public class TestAllFiles {
|
||||||
|
|
||||||
List<Object[]> files = new ArrayList<Object[]>();
|
List<Object[]> files = new ArrayList<Object[]>();
|
||||||
for(String file : scanner.getIncludedFiles()) {
|
for(String file : scanner.getIncludedFiles()) {
|
||||||
|
file = file.replace('\\', '/'); // ... failures/handlers lookup doesn't work on windows otherwise
|
||||||
files.add(new Object[] { file, HANDLERS.get(getExtension(file)) });
|
files.add(new Object[] { file, HANDLERS.get(getExtension(file)) });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -246,7 +248,7 @@ public class TestAllFiles {
|
||||||
@Test
|
@Test
|
||||||
public void testAllFiles() throws Exception {
|
public void testAllFiles() throws Exception {
|
||||||
assertNotNull("Unknown file extension for file: " + file + ": " + getExtension(file), handler);
|
assertNotNull("Unknown file extension for file: " + file + ": " + getExtension(file), handler);
|
||||||
InputStream stream = new FileInputStream(new File("test-data", file));
|
InputStream stream = new BufferedInputStream(new FileInputStream(new File("test-data", file)),100);
|
||||||
try {
|
try {
|
||||||
handler.handleFile(stream);
|
handler.handleFile(stream);
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,11 @@ package org.apache.poi.stress;
|
||||||
|
|
||||||
import static org.junit.Assert.assertNotNull;
|
import static org.junit.Assert.assertNotNull;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
|
||||||
import org.apache.poi.POIXMLDocument;
|
import org.apache.poi.POIXMLDocument;
|
||||||
|
import org.apache.poi.poifs.filesystem.POIFSFileSystem;
|
||||||
|
|
||||||
public final class POIXMLDocumentHandler {
|
public final class POIXMLDocumentHandler {
|
||||||
protected void handlePOIXMLDocument(POIXMLDocument doc) throws Exception {
|
protected void handlePOIXMLDocument(POIXMLDocument doc) throws Exception {
|
||||||
|
@ -28,4 +32,15 @@ public final class POIXMLDocumentHandler {
|
||||||
assertNotNull(doc.getProperties());
|
assertNotNull(doc.getProperties());
|
||||||
assertNotNull(doc.getRelations());
|
assertNotNull(doc.getRelations());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected static boolean isEncrypted(InputStream stream) throws IOException {
|
||||||
|
if (POIFSFileSystem.hasPOIFSHeader(stream)) {
|
||||||
|
POIFSFileSystem poifs = new POIFSFileSystem(stream);
|
||||||
|
if (poifs.getRoot().hasEntry("EncryptedPackage")) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
throw new IOException("wrong file format or file extension for OO XML file");
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,7 +28,10 @@ import org.junit.Test;
|
||||||
public class XSLFFileHandler implements FileHandler {
|
public class XSLFFileHandler implements FileHandler {
|
||||||
@Override
|
@Override
|
||||||
public void handleFile(InputStream stream) throws Exception {
|
public void handleFile(InputStream stream) throws Exception {
|
||||||
XSLFSlideShow slide = new XSLFSlideShow(OPCPackage.open(stream));
|
// ignore password protected files
|
||||||
|
if (POIXMLDocumentHandler.isEncrypted(stream)) return;
|
||||||
|
|
||||||
|
XSLFSlideShow slide = new XSLFSlideShow(OPCPackage.open(stream));
|
||||||
assertNotNull(slide.getPresentation());
|
assertNotNull(slide.getPresentation());
|
||||||
assertNotNull(slide.getSlideMasterReferences());
|
assertNotNull(slide.getSlideMasterReferences());
|
||||||
assertNotNull(slide.getSlideReferences());
|
assertNotNull(slide.getSlideReferences());
|
||||||
|
|
|
@ -32,6 +32,9 @@ import org.xml.sax.SAXException;
|
||||||
public class XSSFFileHandler extends SpreadsheetHandler {
|
public class XSSFFileHandler extends SpreadsheetHandler {
|
||||||
@Override
|
@Override
|
||||||
public void handleFile(InputStream stream) throws Exception {
|
public void handleFile(InputStream stream) throws Exception {
|
||||||
|
// ignore password protected files
|
||||||
|
if (POIXMLDocumentHandler.isEncrypted(stream)) return;
|
||||||
|
|
||||||
XSSFWorkbook wb = new XSSFWorkbook(stream);
|
XSSFWorkbook wb = new XSSFWorkbook(stream);
|
||||||
|
|
||||||
// use the combined handler for HSSF/XSSF
|
// use the combined handler for HSSF/XSSF
|
||||||
|
@ -57,7 +60,7 @@ public class XSSFFileHandler extends SpreadsheetHandler {
|
||||||
exporter.exportToXML(os, true);
|
exporter.exportToXML(os, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// a test-case to test this locally without executing the full TestAllFiles
|
// a test-case to test this locally without executing the full TestAllFiles
|
||||||
@Test
|
@Test
|
||||||
public void test() throws Exception {
|
public void test() throws Exception {
|
||||||
|
|
|
@ -25,7 +25,10 @@ import org.junit.Test;
|
||||||
public class XWPFFileHandler implements FileHandler {
|
public class XWPFFileHandler implements FileHandler {
|
||||||
@Override
|
@Override
|
||||||
public void handleFile(InputStream stream) throws Exception {
|
public void handleFile(InputStream stream) throws Exception {
|
||||||
XWPFDocument doc = new XWPFDocument(stream);
|
// ignore password protected files
|
||||||
|
if (POIXMLDocumentHandler.isEncrypted(stream)) return;
|
||||||
|
|
||||||
|
XWPFDocument doc = new XWPFDocument(stream);
|
||||||
|
|
||||||
new POIXMLDocumentHandler().handlePOIXMLDocument(doc);
|
new POIXMLDocumentHandler().handlePOIXMLDocument(doc);
|
||||||
}
|
}
|
||||||
|
|
|
@ -285,9 +285,30 @@ public final class RecordInputStream implements LittleEndianInput {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void readFully(byte[] buf, int off, int len) {
|
public void readFully(byte[] buf, int off, int len) {
|
||||||
checkRecordPosition(len);
|
int origLen = len;
|
||||||
_dataInput.readFully(buf, off, len);
|
if (buf == null) {
|
||||||
_currentDataOffset+=len;
|
throw new NullPointerException();
|
||||||
|
} else if (off < 0 || len < 0 || len > buf.length - off) {
|
||||||
|
throw new IndexOutOfBoundsException();
|
||||||
|
}
|
||||||
|
|
||||||
|
while (len > 0) {
|
||||||
|
int nextChunk = Math.min(available(),len);
|
||||||
|
if (nextChunk == 0) {
|
||||||
|
if (!hasNextRecord()) {
|
||||||
|
throw new RecordFormatException("Can't read the remaining "+len+" bytes of the requested "+origLen+" bytes. No further record exists.");
|
||||||
|
} else {
|
||||||
|
nextRecord();
|
||||||
|
nextChunk = Math.min(available(),len);
|
||||||
|
assert(nextChunk > 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
checkRecordPosition(nextChunk);
|
||||||
|
_dataInput.readFully(buf, off, nextChunk);
|
||||||
|
_currentDataOffset+=nextChunk;
|
||||||
|
off += nextChunk;
|
||||||
|
len -= nextChunk;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public String readString() {
|
public String readString() {
|
||||||
|
@ -362,6 +383,7 @@ public final class RecordInputStream implements LittleEndianInput {
|
||||||
nextRecord();
|
nextRecord();
|
||||||
// note - the compressed flag may change on the fly
|
// note - the compressed flag may change on the fly
|
||||||
byte compressFlag = readByte();
|
byte compressFlag = readByte();
|
||||||
|
assert(compressFlag == 0 || compressFlag == 1);
|
||||||
isCompressedEncoding = (compressFlag == 0);
|
isCompressedEncoding = (compressFlag == 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,8 +19,6 @@ package org.apache.poi.hssf.usermodel;
|
||||||
|
|
||||||
import java.awt.Dimension;
|
import java.awt.Dimension;
|
||||||
import java.io.ByteArrayInputStream;
|
import java.io.ByteArrayInputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.nio.charset.Charset;
|
|
||||||
|
|
||||||
import org.apache.poi.ddf.DefaultEscherRecordFactory;
|
import org.apache.poi.ddf.DefaultEscherRecordFactory;
|
||||||
import org.apache.poi.ddf.EscherBSERecord;
|
import org.apache.poi.ddf.EscherBSERecord;
|
||||||
|
@ -40,12 +38,14 @@ import org.apache.poi.ss.usermodel.Picture;
|
||||||
import org.apache.poi.ss.util.ImageUtils;
|
import org.apache.poi.ss.util.ImageUtils;
|
||||||
import org.apache.poi.util.POILogFactory;
|
import org.apache.poi.util.POILogFactory;
|
||||||
import org.apache.poi.util.POILogger;
|
import org.apache.poi.util.POILogger;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents a escher picture. Eg. A GIF, JPEG etc...
|
* Represents a escher picture. Eg. A GIF, JPEG etc...
|
||||||
*/
|
*/
|
||||||
public class HSSFPicture extends HSSFSimpleShape implements Picture {
|
public class HSSFPicture extends HSSFSimpleShape implements Picture {
|
||||||
private static POILogger logger = POILogFactory.getLogger(HSSFPicture.class);
|
@SuppressWarnings("unused")
|
||||||
|
private static POILogger logger = POILogFactory.getLogger(HSSFPicture.class);
|
||||||
|
|
||||||
public static final int PICTURE_TYPE_EMF = HSSFWorkbook.PICTURE_TYPE_EMF; // Windows Enhanced Metafile
|
public static final int PICTURE_TYPE_EMF = HSSFWorkbook.PICTURE_TYPE_EMF; // Windows Enhanced Metafile
|
||||||
public static final int PICTURE_TYPE_WMF = HSSFWorkbook.PICTURE_TYPE_WMF; // Windows Metafile
|
public static final int PICTURE_TYPE_WMF = HSSFWorkbook.PICTURE_TYPE_WMF; // Windows Metafile
|
||||||
|
@ -226,16 +226,14 @@ public class HSSFPicture extends HSSFSimpleShape implements Picture {
|
||||||
EscherProperties.BLIP__BLIPFILENAME);
|
EscherProperties.BLIP__BLIPFILENAME);
|
||||||
return (null == propFile)
|
return (null == propFile)
|
||||||
? ""
|
? ""
|
||||||
: new String(propFile.getComplexData(), Charset.forName("UTF-16LE")).trim();
|
: StringUtil.getFromUnicodeLE(propFile.getComplexData()).trim();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setFileName(String data){
|
public void setFileName(String data){
|
||||||
try {
|
// TODO: add trailing \u0000?
|
||||||
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.BLIP__BLIPFILENAME, true, data.getBytes("UTF-16LE"));
|
byte bytes[] = StringUtil.getToUnicodeLE(data);
|
||||||
setPropertyValue(prop);
|
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.BLIP__BLIPFILENAME, true, bytes);
|
||||||
} catch (UnsupportedEncodingException e) {
|
setPropertyValue(prop);
|
||||||
logger.log( POILogger.ERROR, "Unsupported encoding: UTF-16LE");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -35,6 +35,7 @@ import javax.crypto.spec.RC2ParameterSpec;
|
||||||
import org.apache.poi.EncryptedDocumentException;
|
import org.apache.poi.EncryptedDocumentException;
|
||||||
import org.apache.poi.util.LittleEndian;
|
import org.apache.poi.util.LittleEndian;
|
||||||
import org.apache.poi.util.LittleEndianConsts;
|
import org.apache.poi.util.LittleEndianConsts;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper functions used for standard and agile encryption
|
* Helper functions used for standard and agile encryption
|
||||||
|
@ -100,7 +101,7 @@ public class CryptoFunctions {
|
||||||
MessageDigest hashAlg = getMessageDigest(hashAlgorithm);
|
MessageDigest hashAlg = getMessageDigest(hashAlgorithm);
|
||||||
|
|
||||||
hashAlg.update(salt);
|
hashAlg.update(salt);
|
||||||
byte[] hash = hashAlg.digest(getUtf16LeString(password));
|
byte[] hash = hashAlg.digest(StringUtil.getToUnicodeLE(password));
|
||||||
byte[] iterator = new byte[LittleEndianConsts.INT_SIZE];
|
byte[] iterator = new byte[LittleEndianConsts.INT_SIZE];
|
||||||
|
|
||||||
byte[] first = (iteratorFirst ? iterator : hash);
|
byte[] first = (iteratorFirst ? iterator : hash);
|
||||||
|
@ -266,10 +267,6 @@ public class CryptoFunctions {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static byte[] getUtf16LeString(String str) {
|
|
||||||
return str.getBytes(Charset.forName("UTF-16LE"));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static MessageDigest getMessageDigest(HashAlgorithm hashAlgorithm) {
|
public static MessageDigest getMessageDigest(HashAlgorithm hashAlgorithm) {
|
||||||
try {
|
try {
|
||||||
if (hashAlgorithm.needsBouncyCastle) {
|
if (hashAlgorithm.needsBouncyCastle) {
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
package org.apache.poi.poifs.crypt;
|
package org.apache.poi.poifs.crypt;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.EncryptedDocumentException;
|
import org.apache.poi.EncryptedDocumentException;
|
||||||
import org.apache.poi.poifs.crypt.standard.EncryptionRecord;
|
import org.apache.poi.poifs.crypt.standard.EncryptionRecord;
|
||||||
|
@ -30,6 +30,7 @@ import org.apache.poi.util.LittleEndianByteArrayOutputStream;
|
||||||
import org.apache.poi.util.LittleEndianConsts;
|
import org.apache.poi.util.LittleEndianConsts;
|
||||||
import org.apache.poi.util.LittleEndianInput;
|
import org.apache.poi.util.LittleEndianInput;
|
||||||
import org.apache.poi.util.LittleEndianOutput;
|
import org.apache.poi.util.LittleEndianOutput;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
public class DataSpaceMapUtils {
|
public class DataSpaceMapUtils {
|
||||||
public static void addDefaultDataSpace(DirectoryEntry dir) throws IOException {
|
public static void addDefaultDataSpace(DirectoryEntry dir) throws IOException {
|
||||||
|
@ -302,31 +303,29 @@ public class DataSpaceMapUtils {
|
||||||
|
|
||||||
public static String readUnicodeLPP4(LittleEndianInput is) {
|
public static String readUnicodeLPP4(LittleEndianInput is) {
|
||||||
int length = is.readInt();
|
int length = is.readInt();
|
||||||
byte data[] = new byte[length];
|
if (length%2 != 0) {
|
||||||
is.readFully(data);
|
throw new EncryptedDocumentException(
|
||||||
|
"UNICODE-LP-P4 structure is a multiple of 4 bytes. "
|
||||||
|
+ "If Padding is present, it MUST be exactly 2 bytes long");
|
||||||
|
}
|
||||||
|
|
||||||
|
String result = StringUtil.readUnicodeLE(is, length/2);
|
||||||
if (length%4==2) {
|
if (length%4==2) {
|
||||||
// Padding (variable): A set of bytes that MUST be of the correct size such that the size of the
|
// Padding (variable): A set of bytes that MUST be of the correct size such that the size of the
|
||||||
// UNICODE-LP-P4 structure is a multiple of 4 bytes. If Padding is present, it MUST be exactly
|
// UNICODE-LP-P4 structure is a multiple of 4 bytes. If Padding is present, it MUST be exactly
|
||||||
// 2 bytes long, and each byte MUST be 0x00.
|
// 2 bytes long, and each byte MUST be 0x00.
|
||||||
is.readShort();
|
is.readShort();
|
||||||
}
|
}
|
||||||
try {
|
|
||||||
return new String(data, 0, data.length, "UTF-16LE");
|
return result;
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new EncryptedDocumentException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeUnicodeLPP4(LittleEndianOutput os, String str) {
|
public static void writeUnicodeLPP4(LittleEndianOutput os, String string) {
|
||||||
try {
|
byte buf[] = StringUtil.getToUnicodeLE(string);
|
||||||
byte buf[] = str.getBytes("UTF-16LE");
|
os.writeInt(buf.length);
|
||||||
os.writeInt(buf.length);
|
os.write(buf);
|
||||||
os.write(buf);
|
if (buf.length%4==2) {
|
||||||
if (buf.length%4==2) {
|
os.writeShort(0);
|
||||||
os.writeShort(0);
|
|
||||||
}
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new EncryptedDocumentException(e);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -352,11 +351,8 @@ public class DataSpaceMapUtils {
|
||||||
is.readByte();
|
is.readByte();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
try {
|
|
||||||
return new String(data, 0, data.length, "UTF-8");
|
return new String(data, 0, data.length, Charset.forName("UTF-8"));
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new EncryptedDocumentException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void writeUtf8LPP4(LittleEndianOutput os, String str) {
|
public static void writeUtf8LPP4(LittleEndianOutput os, String str) {
|
||||||
|
@ -364,18 +360,14 @@ public class DataSpaceMapUtils {
|
||||||
os.writeInt(str == null ? 0 : 4);
|
os.writeInt(str == null ? 0 : 4);
|
||||||
os.writeInt(0);
|
os.writeInt(0);
|
||||||
} else {
|
} else {
|
||||||
try {
|
byte buf[] = str.getBytes(Charset.forName("UTF-8"));
|
||||||
byte buf[] = str.getBytes("UTF-8");
|
os.writeInt(buf.length);
|
||||||
os.writeInt(buf.length);
|
os.write(buf);
|
||||||
os.write(buf);
|
int scratchBytes = buf.length%4;
|
||||||
int scratchBytes = buf.length%4;
|
if (scratchBytes > 0) {
|
||||||
if (scratchBytes > 0) {
|
for (int i=0; i<(4-scratchBytes); i++) {
|
||||||
for (int i=0; i<(4-scratchBytes); i++) {
|
os.writeByte(0);
|
||||||
os.writeByte(0);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new EncryptedDocumentException(e);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,14 +22,17 @@ import java.io.InputStream;
|
||||||
import java.security.GeneralSecurityException;
|
import java.security.GeneralSecurityException;
|
||||||
import java.security.MessageDigest;
|
import java.security.MessageDigest;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
|
||||||
import javax.crypto.Cipher;
|
import javax.crypto.Cipher;
|
||||||
import javax.crypto.SecretKey;
|
import javax.crypto.SecretKey;
|
||||||
import javax.crypto.spec.SecretKeySpec;
|
import javax.crypto.spec.SecretKeySpec;
|
||||||
|
|
||||||
import org.apache.poi.EncryptedDocumentException;
|
import org.apache.poi.EncryptedDocumentException;
|
||||||
import org.apache.poi.poifs.crypt.*;
|
import org.apache.poi.poifs.crypt.*;
|
||||||
import org.apache.poi.poifs.filesystem.DirectoryNode;
|
import org.apache.poi.poifs.filesystem.DirectoryNode;
|
||||||
import org.apache.poi.poifs.filesystem.DocumentInputStream;
|
import org.apache.poi.poifs.filesystem.DocumentInputStream;
|
||||||
import org.apache.poi.util.LittleEndian;
|
import org.apache.poi.util.LittleEndian;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
public class BinaryRC4Decryptor extends Decryptor {
|
public class BinaryRC4Decryptor extends Decryptor {
|
||||||
private long _length = -1L;
|
private long _length = -1L;
|
||||||
|
@ -99,7 +102,7 @@ public class BinaryRC4Decryptor extends Decryptor {
|
||||||
password = password.substring(0, 255);
|
password = password.substring(0, 255);
|
||||||
HashAlgorithm hashAlgo = ver.getHashAlgorithm();
|
HashAlgorithm hashAlgo = ver.getHashAlgorithm();
|
||||||
MessageDigest hashAlg = CryptoFunctions.getMessageDigest(hashAlgo);
|
MessageDigest hashAlg = CryptoFunctions.getMessageDigest(hashAlgo);
|
||||||
byte hash[] = hashAlg.digest(CryptoFunctions.getUtf16LeString(password));
|
byte hash[] = hashAlg.digest(StringUtil.getToUnicodeLE(password));
|
||||||
byte salt[] = ver.getSalt();
|
byte salt[] = ver.getSalt();
|
||||||
hashAlg.reset();
|
hashAlg.reset();
|
||||||
for (int i = 0; i < 16; i++) {
|
for (int i = 0; i < 16; i++) {
|
||||||
|
|
|
@ -21,7 +21,6 @@ import java.io.ByteArrayInputStream;
|
||||||
import java.io.ByteArrayOutputStream;
|
import java.io.ByteArrayOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.nio.charset.Charset;
|
|
||||||
import java.security.GeneralSecurityException;
|
import java.security.GeneralSecurityException;
|
||||||
import java.security.MessageDigest;
|
import java.security.MessageDigest;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
@ -48,6 +47,7 @@ import org.apache.poi.util.BoundedInputStream;
|
||||||
import org.apache.poi.util.IOUtils;
|
import org.apache.poi.util.IOUtils;
|
||||||
import org.apache.poi.util.LittleEndian;
|
import org.apache.poi.util.LittleEndian;
|
||||||
import org.apache.poi.util.LittleEndianInputStream;
|
import org.apache.poi.util.LittleEndianInputStream;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
public class CryptoAPIDecryptor extends Decryptor {
|
public class CryptoAPIDecryptor extends Decryptor {
|
||||||
|
|
||||||
|
@ -185,7 +185,7 @@ public class CryptoAPIDecryptor extends Decryptor {
|
||||||
HashAlgorithm hashAlgo = ver.getHashAlgorithm();
|
HashAlgorithm hashAlgo = ver.getHashAlgorithm();
|
||||||
MessageDigest hashAlg = CryptoFunctions.getMessageDigest(hashAlgo);
|
MessageDigest hashAlg = CryptoFunctions.getMessageDigest(hashAlgo);
|
||||||
hashAlg.update(ver.getSalt());
|
hashAlg.update(ver.getSalt());
|
||||||
byte hash[] = hashAlg.digest(CryptoFunctions.getUtf16LeString(password));
|
byte hash[] = hashAlg.digest(StringUtil.getToUnicodeLE(password));
|
||||||
SecretKey skey = new SecretKeySpec(hash, ver.getCipherAlgorithm().jceId);
|
SecretKey skey = new SecretKeySpec(hash, ver.getCipherAlgorithm().jceId);
|
||||||
return skey;
|
return skey;
|
||||||
}
|
}
|
||||||
|
@ -224,9 +224,7 @@ public class CryptoAPIDecryptor extends Decryptor {
|
||||||
entry.flags = leis.readUByte();
|
entry.flags = leis.readUByte();
|
||||||
boolean isStream = StreamDescriptorEntry.flagStream.isSet(entry.flags);
|
boolean isStream = StreamDescriptorEntry.flagStream.isSet(entry.flags);
|
||||||
entry.reserved2 = leis.readInt();
|
entry.reserved2 = leis.readInt();
|
||||||
byte nameBuf[] = new byte[nameSize * 2];
|
entry.streamName = StringUtil.readUnicodeLE(leis, nameSize);
|
||||||
leis.read(nameBuf);
|
|
||||||
entry.streamName = new String(nameBuf, Charset.forName("UTF-16LE"));
|
|
||||||
leis.readShort();
|
leis.readShort();
|
||||||
assert(entry.streamName.length() == nameSize);
|
assert(entry.streamName.length() == nameSize);
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,7 +21,6 @@ import java.io.ByteArrayInputStream;
|
||||||
import java.io.ByteArrayOutputStream;
|
import java.io.ByteArrayOutputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.nio.charset.Charset;
|
|
||||||
import java.security.GeneralSecurityException;
|
import java.security.GeneralSecurityException;
|
||||||
import java.security.MessageDigest;
|
import java.security.MessageDigest;
|
||||||
import java.security.SecureRandom;
|
import java.security.SecureRandom;
|
||||||
|
@ -49,6 +48,7 @@ import org.apache.poi.poifs.filesystem.DocumentInputStream;
|
||||||
import org.apache.poi.util.IOUtils;
|
import org.apache.poi.util.IOUtils;
|
||||||
import org.apache.poi.util.LittleEndian;
|
import org.apache.poi.util.LittleEndian;
|
||||||
import org.apache.poi.util.LittleEndianByteArrayOutputStream;
|
import org.apache.poi.util.LittleEndianByteArrayOutputStream;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
public class CryptoAPIEncryptor extends Encryptor {
|
public class CryptoAPIEncryptor extends Encryptor {
|
||||||
private final CryptoAPIEncryptionInfoBuilder builder;
|
private final CryptoAPIEncryptionInfoBuilder builder;
|
||||||
|
@ -164,7 +164,7 @@ public class CryptoAPIEncryptor extends Encryptor {
|
||||||
bos.write(buf, 0, 1);
|
bos.write(buf, 0, 1);
|
||||||
LittleEndian.putUInt(buf, 0, sde.reserved2);
|
LittleEndian.putUInt(buf, 0, sde.reserved2);
|
||||||
bos.write(buf, 0, 4);
|
bos.write(buf, 0, 4);
|
||||||
byte nameBytes[] = sde.streamName.getBytes(Charset.forName("UTF-16LE"));
|
byte nameBytes[] = StringUtil.getToUnicodeLE(sde.streamName);
|
||||||
bos.write(nameBytes, 0, nameBytes.length);
|
bos.write(nameBytes, 0, nameBytes.length);
|
||||||
LittleEndian.putShort(buf, 0, (short)0); // null-termination
|
LittleEndian.putShort(buf, 0, (short)0); // null-termination
|
||||||
bos.write(buf, 0, 2);
|
bos.write(buf, 0, 2);
|
||||||
|
|
|
@ -16,7 +16,6 @@
|
||||||
==================================================================== */
|
==================================================================== */
|
||||||
package org.apache.poi.poifs.crypt.standard;
|
package org.apache.poi.poifs.crypt.standard;
|
||||||
|
|
||||||
import static org.apache.poi.poifs.crypt.CryptoFunctions.getUtf16LeString;
|
|
||||||
import static org.apache.poi.poifs.crypt.EncryptionInfo.flagAES;
|
import static org.apache.poi.poifs.crypt.EncryptionInfo.flagAES;
|
||||||
import static org.apache.poi.poifs.crypt.EncryptionInfo.flagCryptoAPI;
|
import static org.apache.poi.poifs.crypt.EncryptionInfo.flagCryptoAPI;
|
||||||
|
|
||||||
|
@ -32,6 +31,7 @@ import org.apache.poi.util.LittleEndianByteArrayOutputStream;
|
||||||
import org.apache.poi.util.LittleEndianConsts;
|
import org.apache.poi.util.LittleEndianConsts;
|
||||||
import org.apache.poi.util.LittleEndianInput;
|
import org.apache.poi.util.LittleEndianInput;
|
||||||
import org.apache.poi.util.LittleEndianOutput;
|
import org.apache.poi.util.LittleEndianOutput;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
public class StandardEncryptionHeader extends EncryptionHeader implements EncryptionRecord {
|
public class StandardEncryptionHeader extends EncryptionHeader implements EncryptionRecord {
|
||||||
|
|
||||||
|
@ -103,7 +103,7 @@ public class StandardEncryptionHeader extends EncryptionHeader implements Encryp
|
||||||
bos.writeInt(0); // reserved2
|
bos.writeInt(0); // reserved2
|
||||||
String cspName = getCspName();
|
String cspName = getCspName();
|
||||||
if (cspName == null) cspName = getCipherProvider().cipherProviderName;
|
if (cspName == null) cspName = getCipherProvider().cipherProviderName;
|
||||||
bos.write(getUtf16LeString(cspName));
|
bos.write(StringUtil.getToUnicodeLE(cspName));
|
||||||
bos.writeShort(0);
|
bos.writeShort(0);
|
||||||
int headerSize = bos.getWriteIndex()-startIdx-LittleEndianConsts.INT_SIZE;
|
int headerSize = bos.getWriteIndex()-startIdx-LittleEndianConsts.INT_SIZE;
|
||||||
sizeOutput.writeInt(headerSize);
|
sizeOutput.writeInt(headerSize);
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
|
|
||||||
package org.apache.poi.util;
|
package org.apache.poi.util;
|
||||||
|
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
import java.text.FieldPosition;
|
import java.text.FieldPosition;
|
||||||
import java.text.NumberFormat;
|
import java.text.NumberFormat;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
|
@ -26,16 +26,17 @@ import org.apache.poi.hssf.record.RecordInputStream;
|
||||||
/**
|
/**
|
||||||
* Title: String Utility Description: Collection of string handling utilities<p/>
|
* Title: String Utility Description: Collection of string handling utilities<p/>
|
||||||
*
|
*
|
||||||
* Note - none of the methods in this class deals with {@link org.apache.poi.hssf.record.ContinueRecord}s. For such
|
* Note - none of the methods in this class deals with {@link org.apache.poi.hssf.record.ContinueRecord}s.
|
||||||
* functionality, consider using {@link RecordInputStream
|
* For such functionality, consider using {@link RecordInputStream}
|
||||||
} *
|
*
|
||||||
*
|
*
|
||||||
*@author Andrew C. Oliver
|
*@author Andrew C. Oliver
|
||||||
*@author Sergei Kozello (sergeikozello at mail.ru)
|
*@author Sergei Kozello (sergeikozello at mail.ru)
|
||||||
*@author Toshiaki Kamoshida (kamoshida.toshiaki at future dot co dot jp)
|
*@author Toshiaki Kamoshida (kamoshida.toshiaki at future dot co dot jp)
|
||||||
*/
|
*/
|
||||||
public class StringUtil {
|
public class StringUtil {
|
||||||
private static final String ENCODING_ISO_8859_1 = "ISO-8859-1";
|
private static final Charset ISO_8859_1 = Charset.forName("ISO-8859-1");
|
||||||
|
private static final Charset UTF16LE = Charset.forName("UTF-16LE");
|
||||||
|
|
||||||
private StringUtil() {
|
private StringUtil() {
|
||||||
// no instances of this class
|
// no instances of this class
|
||||||
|
@ -73,11 +74,7 @@ public class StringUtil {
|
||||||
throw new IllegalArgumentException("Illegal length " + len);
|
throw new IllegalArgumentException("Illegal length " + len);
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
return new String(string, offset, len * 2, UTF16LE);
|
||||||
return new String(string, offset, len * 2, "UTF-16LE");
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -91,8 +88,18 @@ public class StringUtil {
|
||||||
* @return the converted string, never <code>null</code>
|
* @return the converted string, never <code>null</code>
|
||||||
*/
|
*/
|
||||||
public static String getFromUnicodeLE(byte[] string) {
|
public static String getFromUnicodeLE(byte[] string) {
|
||||||
if(string.length == 0) { return ""; }
|
if(string.length == 0) { return ""; }
|
||||||
return getFromUnicodeLE(string, 0, string.length / 2);
|
return getFromUnicodeLE(string, 0, string.length / 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert String to 16-bit unicode characters in little endian format
|
||||||
|
*
|
||||||
|
* @param string the string
|
||||||
|
* @return the byte array of 16-bit unicode characters
|
||||||
|
*/
|
||||||
|
public static byte[] getToUnicodeLE(String string) {
|
||||||
|
return string.getBytes(UTF16LE);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -109,20 +116,16 @@ public class StringUtil {
|
||||||
final byte[] string,
|
final byte[] string,
|
||||||
final int offset,
|
final int offset,
|
||||||
final int len) {
|
final int len) {
|
||||||
try {
|
int len_to_use = Math.min(len, string.length - offset);
|
||||||
int len_to_use = Math.min(len, string.length - offset);
|
return new String(string, offset, len_to_use, ISO_8859_1);
|
||||||
return new String(string, offset, len_to_use, ENCODING_ISO_8859_1);
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String readCompressedUnicode(LittleEndianInput in, int nChars) {
|
public static String readCompressedUnicode(LittleEndianInput in, int nChars) {
|
||||||
char[] buf = new char[nChars];
|
byte[] buf = new byte[nChars];
|
||||||
for (int i = 0; i < buf.length; i++) {
|
in.readFully(buf);
|
||||||
buf[i] = (char) in.readUByte();
|
return new String(buf, ISO_8859_1);
|
||||||
}
|
|
||||||
return new String(buf);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* InputStream <tt>in</tt> is expected to contain:
|
* InputStream <tt>in</tt> is expected to contain:
|
||||||
* <ol>
|
* <ol>
|
||||||
|
@ -225,21 +228,12 @@ public class StringUtil {
|
||||||
* when written
|
* when written
|
||||||
*/
|
*/
|
||||||
public static void putCompressedUnicode(String input, byte[] output, int offset) {
|
public static void putCompressedUnicode(String input, byte[] output, int offset) {
|
||||||
byte[] bytes;
|
byte[] bytes = input.getBytes(ISO_8859_1);
|
||||||
try {
|
|
||||||
bytes = input.getBytes(ENCODING_ISO_8859_1);
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
System.arraycopy(bytes, 0, output, offset, bytes.length);
|
System.arraycopy(bytes, 0, output, offset, bytes.length);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void putCompressedUnicode(String input, LittleEndianOutput out) {
|
public static void putCompressedUnicode(String input, LittleEndianOutput out) {
|
||||||
byte[] bytes;
|
byte[] bytes = input.getBytes(ISO_8859_1);
|
||||||
try {
|
|
||||||
bytes = input.getBytes(ENCODING_ISO_8859_1);
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
out.write(bytes);
|
out.write(bytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -253,30 +247,18 @@ public class StringUtil {
|
||||||
* @param offset the offset to start writing into the byte array
|
* @param offset the offset to start writing into the byte array
|
||||||
*/
|
*/
|
||||||
public static void putUnicodeLE(String input, byte[] output, int offset) {
|
public static void putUnicodeLE(String input, byte[] output, int offset) {
|
||||||
byte[] bytes;
|
byte[] bytes = input.getBytes(UTF16LE);
|
||||||
try {
|
|
||||||
bytes = input.getBytes("UTF-16LE");
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
System.arraycopy(bytes, 0, output, offset, bytes.length);
|
System.arraycopy(bytes, 0, output, offset, bytes.length);
|
||||||
}
|
}
|
||||||
public static void putUnicodeLE(String input, LittleEndianOutput out) {
|
public static void putUnicodeLE(String input, LittleEndianOutput out) {
|
||||||
byte[] bytes;
|
byte[] bytes = input.getBytes(UTF16LE);
|
||||||
try {
|
|
||||||
bytes = input.getBytes("UTF-16LE");
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
out.write(bytes);
|
out.write(bytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String readUnicodeLE(LittleEndianInput in, int nChars) {
|
public static String readUnicodeLE(LittleEndianInput in, int nChars) {
|
||||||
char[] buf = new char[nChars];
|
byte[] bytes = new byte[nChars*2];
|
||||||
for (int i = 0; i < buf.length; i++) {
|
in.readFully(bytes);
|
||||||
buf[i] = (char) in.readUShort();
|
return new String(bytes, UTF16LE);
|
||||||
}
|
|
||||||
return new String(buf);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -358,7 +340,7 @@ public class StringUtil {
|
||||||
* @return the encoding we want to use, currently hardcoded to ISO-8859-1
|
* @return the encoding we want to use, currently hardcoded to ISO-8859-1
|
||||||
*/
|
*/
|
||||||
public static String getPreferredEncoding() {
|
public static String getPreferredEncoding() {
|
||||||
return ENCODING_ISO_8859_1;
|
return ISO_8859_1.name();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -386,12 +368,7 @@ public class StringUtil {
|
||||||
* @return true if string needs Unicode to be represented.
|
* @return true if string needs Unicode to be represented.
|
||||||
*/
|
*/
|
||||||
public static boolean isUnicodeString(final String value) {
|
public static boolean isUnicodeString(final String value) {
|
||||||
try {
|
return !value.equals(new String(value.getBytes(ISO_8859_1), ISO_8859_1));
|
||||||
return !value.equals(new String(value.getBytes(ENCODING_ISO_8859_1),
|
|
||||||
ENCODING_ISO_8859_1));
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -20,7 +20,7 @@ package org.apache.poi.openxml4j.opc;
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
import java.net.URISyntaxException;
|
import java.net.URISyntaxException;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
|
|
||||||
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
|
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
|
||||||
|
@ -748,13 +748,7 @@ public final class PackagingURIHelper {
|
||||||
int n = s.length();
|
int n = s.length();
|
||||||
if (n == 0) return s;
|
if (n == 0) return s;
|
||||||
|
|
||||||
ByteBuffer bb;
|
ByteBuffer bb = ByteBuffer.wrap(s.getBytes(Charset.forName("UTF-8")));
|
||||||
try {
|
|
||||||
bb = ByteBuffer.wrap(s.getBytes("UTF-8"));
|
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
// should not happen
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
StringBuilder sb = new StringBuilder();
|
StringBuilder sb = new StringBuilder();
|
||||||
while (bb.hasRemaining()) {
|
while (bb.hasRemaining()) {
|
||||||
int b = bb.get() & 0xff;
|
int b = bb.get() & 0xff;
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
package org.apache.poi.xssf.usermodel;
|
package org.apache.poi.xssf.usermodel;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
|
||||||
import junit.framework.TestCase;
|
import junit.framework.TestCase;
|
||||||
|
@ -66,9 +66,10 @@ public final class TestUnfixedBugs extends TestCase {
|
||||||
verifyBug54084Unicode(wbStreamingWritten);
|
verifyBug54084Unicode(wbStreamingWritten);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void verifyBug54084Unicode(Workbook wb) throws UnsupportedEncodingException {
|
private void verifyBug54084Unicode(Workbook wb) {
|
||||||
// expected data is stored in UTF-8 in a text-file
|
// expected data is stored in UTF-8 in a text-file
|
||||||
String testData = new String(HSSFTestDataSamples.getTestDataFileContent("54084 - Greek - beyond BMP.txt"), "UTF-8").trim();
|
byte data[] = HSSFTestDataSamples.getTestDataFileContent("54084 - Greek - beyond BMP.txt");
|
||||||
|
String testData = new String(data, Charset.forName("UTF-8")).trim();
|
||||||
|
|
||||||
Sheet sheet = wb.getSheetAt(0);
|
Sheet sheet = wb.getSheetAt(0);
|
||||||
Row row = sheet.getRow(0);
|
Row row = sheet.getRow(0);
|
||||||
|
|
|
@ -20,7 +20,7 @@ package org.apache.poi.hmef;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.util.IOUtils;
|
import org.apache.poi.util.IOUtils;
|
||||||
import org.apache.poi.util.LZWDecompresser;
|
import org.apache.poi.util.LZWDecompresser;
|
||||||
|
@ -73,6 +73,7 @@ public final class CompressedRTF extends LZWDecompresser {
|
||||||
compressedSize = LittleEndian.readInt(src);
|
compressedSize = LittleEndian.readInt(src);
|
||||||
decompressedSize = LittleEndian.readInt(src);
|
decompressedSize = LittleEndian.readInt(src);
|
||||||
int compressionType = LittleEndian.readInt(src);
|
int compressionType = LittleEndian.readInt(src);
|
||||||
|
@SuppressWarnings("unused")
|
||||||
int dataCRC = LittleEndian.readInt(src);
|
int dataCRC = LittleEndian.readInt(src);
|
||||||
|
|
||||||
// TODO - Handle CRC checking on the output side
|
// TODO - Handle CRC checking on the output side
|
||||||
|
@ -117,15 +118,11 @@ public final class CompressedRTF extends LZWDecompresser {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected int populateDictionary(byte[] dict) {
|
protected int populateDictionary(byte[] dict) {
|
||||||
try {
|
// Copy in the RTF constants
|
||||||
// Copy in the RTF constants
|
byte[] preload = LZW_RTF_PRELOAD.getBytes(Charset.forName("US-ASCII"));
|
||||||
byte[] preload = LZW_RTF_PRELOAD.getBytes("US-ASCII");
|
System.arraycopy(preload, 0, dict, 0, preload.length);
|
||||||
System.arraycopy(preload, 0, dict, 0, preload.length);
|
|
||||||
|
// Start adding new codes after the constants
|
||||||
// Start adding new codes after the constants
|
return preload.length;
|
||||||
return preload.length;
|
|
||||||
} catch(UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Your JVM is broken as it doesn't support US ASCII");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
|
|
||||||
package org.apache.poi.hmef.attribute;
|
package org.apache.poi.hmef.attribute;
|
||||||
|
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.hmef.Attachment;
|
import org.apache.poi.hmef.Attachment;
|
||||||
import org.apache.poi.hmef.HMEFMessage;
|
import org.apache.poi.hmef.HMEFMessage;
|
||||||
|
@ -41,11 +41,7 @@ public final class MAPIStringAttribute extends MAPIAttribute {
|
||||||
|
|
||||||
String tmpData = null;
|
String tmpData = null;
|
||||||
if(type == Types.ASCII_STRING.getId()) {
|
if(type == Types.ASCII_STRING.getId()) {
|
||||||
try {
|
tmpData = new String(data, Charset.forName(CODEPAGE));
|
||||||
tmpData = new String(data, CODEPAGE);
|
|
||||||
} catch(UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("JVM Broken - core encoding " + CODEPAGE + " missing");
|
|
||||||
}
|
|
||||||
} else if(type == Types.UNICODE_STRING.getId()) {
|
} else if(type == Types.UNICODE_STRING.getId()) {
|
||||||
tmpData = StringUtil.getFromUnicodeLE(data);
|
tmpData = StringUtil.getFromUnicodeLE(data);
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -17,15 +17,26 @@
|
||||||
|
|
||||||
package org.apache.poi.hslf.model;
|
package org.apache.poi.hslf.model;
|
||||||
|
|
||||||
import org.apache.poi.ddf.*;
|
|
||||||
import org.apache.poi.hslf.record.*;
|
|
||||||
import org.apache.poi.hslf.exceptions.HSLFException;
|
|
||||||
import org.apache.poi.util.LittleEndian;
|
|
||||||
|
|
||||||
import java.io.ByteArrayOutputStream;
|
import java.io.ByteArrayOutputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
|
|
||||||
|
import org.apache.poi.ddf.EscherClientDataRecord;
|
||||||
|
import org.apache.poi.ddf.EscherComplexProperty;
|
||||||
|
import org.apache.poi.ddf.EscherContainerRecord;
|
||||||
|
import org.apache.poi.ddf.EscherOptRecord;
|
||||||
|
import org.apache.poi.ddf.EscherProperties;
|
||||||
|
import org.apache.poi.ddf.EscherRecord;
|
||||||
|
import org.apache.poi.ddf.EscherSpRecord;
|
||||||
|
import org.apache.poi.hslf.exceptions.HSLFException;
|
||||||
|
import org.apache.poi.hslf.record.Document;
|
||||||
|
import org.apache.poi.hslf.record.ExControl;
|
||||||
|
import org.apache.poi.hslf.record.ExObjList;
|
||||||
|
import org.apache.poi.hslf.record.OEShapeAtom;
|
||||||
|
import org.apache.poi.hslf.record.Record;
|
||||||
|
import org.apache.poi.hslf.record.RecordTypes;
|
||||||
|
import org.apache.poi.util.LittleEndian;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents an ActiveX control in a PowerPoint document.
|
* Represents an ActiveX control in a PowerPoint document.
|
||||||
*
|
*
|
||||||
|
@ -155,14 +166,10 @@ public final class ActiveXShape extends Picture {
|
||||||
ExControl ctrl = getExControl();
|
ExControl ctrl = getExControl();
|
||||||
ctrl.getExControlAtom().setSlideId(sheet._getSheetNumber());
|
ctrl.getExControlAtom().setSlideId(sheet._getSheetNumber());
|
||||||
|
|
||||||
try {
|
String name = ctrl.getProgId() + "-" + getControlIndex() + '\u0000';
|
||||||
String name = ctrl.getProgId() + "-" + getControlIndex();
|
byte[] data = StringUtil.getToUnicodeLE(name);
|
||||||
byte[] data = (name + '\u0000').getBytes("UTF-16LE");
|
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.GROUPSHAPE__SHAPENAME, false, data);
|
||||||
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.GROUPSHAPE__SHAPENAME, false, data);
|
EscherOptRecord opt = getEscherOptRecord();
|
||||||
EscherOptRecord opt = getEscherOptRecord();
|
opt.addEscherProperty(prop);
|
||||||
opt.addEscherProperty(prop);
|
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
throw new HSLFException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,23 +17,30 @@
|
||||||
|
|
||||||
package org.apache.poi.hslf.model;
|
package org.apache.poi.hslf.model;
|
||||||
|
|
||||||
import org.apache.poi.ddf.*;
|
import java.awt.Graphics2D;
|
||||||
import org.apache.poi.hslf.usermodel.PictureData;
|
|
||||||
import org.apache.poi.hslf.usermodel.SlideShow;
|
|
||||||
import org.apache.poi.hslf.record.Document;
|
|
||||||
import org.apache.poi.hslf.blip.Bitmap;
|
|
||||||
import org.apache.poi.hslf.exceptions.HSLFException;
|
|
||||||
import org.apache.poi.util.POILogger;
|
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.awt.*;
|
|
||||||
import java.awt.geom.AffineTransform;
|
import java.awt.geom.AffineTransform;
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
import java.io.ByteArrayInputStream;
|
import java.io.ByteArrayInputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import org.apache.poi.ddf.EscherBSERecord;
|
||||||
|
import org.apache.poi.ddf.EscherComplexProperty;
|
||||||
|
import org.apache.poi.ddf.EscherContainerRecord;
|
||||||
|
import org.apache.poi.ddf.EscherOptRecord;
|
||||||
|
import org.apache.poi.ddf.EscherProperties;
|
||||||
|
import org.apache.poi.ddf.EscherRecord;
|
||||||
|
import org.apache.poi.ddf.EscherSimpleProperty;
|
||||||
|
import org.apache.poi.ddf.EscherSpRecord;
|
||||||
|
import org.apache.poi.hslf.blip.Bitmap;
|
||||||
|
import org.apache.poi.hslf.record.Document;
|
||||||
|
import org.apache.poi.hslf.usermodel.PictureData;
|
||||||
|
import org.apache.poi.hslf.usermodel.SlideShow;
|
||||||
|
import org.apache.poi.util.POILogger;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Represents a picture in a PowerPoint document.
|
* Represents a picture in a PowerPoint document.
|
||||||
|
@ -199,7 +206,7 @@ public class Picture extends SimpleShape {
|
||||||
logger.log(POILogger.DEBUG, "EscherContainerRecord.BSTORE_CONTAINER was not found ");
|
logger.log(POILogger.DEBUG, "EscherContainerRecord.BSTORE_CONTAINER was not found ");
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
List lst = bstore.getChildRecords();
|
List<EscherRecord> lst = bstore.getChildRecords();
|
||||||
int idx = getPictureIndex();
|
int idx = getPictureIndex();
|
||||||
if (idx == 0){
|
if (idx == 0){
|
||||||
logger.log(POILogger.DEBUG, "picture index was not found, returning ");
|
logger.log(POILogger.DEBUG, "picture index was not found, returning ");
|
||||||
|
@ -216,17 +223,9 @@ public class Picture extends SimpleShape {
|
||||||
public String getPictureName(){
|
public String getPictureName(){
|
||||||
EscherOptRecord opt = getEscherOptRecord();
|
EscherOptRecord opt = getEscherOptRecord();
|
||||||
EscherComplexProperty prop = (EscherComplexProperty)getEscherProperty(opt, EscherProperties.BLIP__BLIPFILENAME);
|
EscherComplexProperty prop = (EscherComplexProperty)getEscherProperty(opt, EscherProperties.BLIP__BLIPFILENAME);
|
||||||
String name = null;
|
if (prop == null) return null;
|
||||||
if(prop != null){
|
String name = StringUtil.getFromUnicodeLE(prop.getComplexData());
|
||||||
try {
|
return name.trim();
|
||||||
name = new String(prop.getComplexData(), "UTF-16LE");
|
|
||||||
int idx = name.indexOf('\u0000');
|
|
||||||
return idx == -1 ? name : name.substring(0, idx);
|
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
throw new HSLFException(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return name;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -236,13 +235,9 @@ public class Picture extends SimpleShape {
|
||||||
*/
|
*/
|
||||||
public void setPictureName(String name){
|
public void setPictureName(String name){
|
||||||
EscherOptRecord opt = getEscherOptRecord();
|
EscherOptRecord opt = getEscherOptRecord();
|
||||||
try {
|
byte[] data = StringUtil.getToUnicodeLE(name + '\u0000');
|
||||||
byte[] data = (name + '\u0000').getBytes("UTF-16LE");
|
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.BLIP__BLIPFILENAME, false, data);
|
||||||
EscherComplexProperty prop = new EscherComplexProperty(EscherProperties.BLIP__BLIPFILENAME, false, data);
|
opt.addEscherProperty(prop);
|
||||||
opt.addEscherProperty(prop);
|
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
throw new HSLFException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -17,10 +17,11 @@
|
||||||
|
|
||||||
package org.apache.poi.hslf.record;
|
package org.apache.poi.hslf.record;
|
||||||
|
|
||||||
import org.apache.poi.util.LittleEndian;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
|
import org.apache.poi.util.LittleEndian;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This atom corresponds exactly to a Windows Logical Font (LOGFONT) structure.
|
* This atom corresponds exactly to a Windows Logical Font (LOGFONT) structure.
|
||||||
|
@ -77,21 +78,14 @@ public final class FontEntityAtom extends RecordAtom {
|
||||||
* @return font name
|
* @return font name
|
||||||
*/
|
*/
|
||||||
public String getFontName(){
|
public String getFontName(){
|
||||||
String name = null;
|
int maxLen = Math.min(_recdata.length,64);
|
||||||
try {
|
for(int i = 0; i < maxLen; i+=2){
|
||||||
int i = 0;
|
//loop until find null-terminated end of the font name
|
||||||
while(i < 64){
|
if(_recdata[i] == 0 && _recdata[i + 1] == 0) {
|
||||||
//loop until find null-terminated end of the font name
|
return StringUtil.getFromUnicodeLE(_recdata, 0, i/2);
|
||||||
if(_recdata[i] == 0 && _recdata[i + 1] == 0) {
|
|
||||||
name = new String(_recdata, 0, i, "UTF-16LE");
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
i += 2;
|
|
||||||
}
|
}
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
throw new RuntimeException(e.getMessage(), e);
|
|
||||||
}
|
}
|
||||||
return name;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -103,8 +97,8 @@ public final class FontEntityAtom extends RecordAtom {
|
||||||
*/
|
*/
|
||||||
public void setFontName(String name){
|
public void setFontName(String name){
|
||||||
// Add a null termination if required
|
// Add a null termination if required
|
||||||
if(! name.endsWith("\000")) {
|
if(! name.endsWith("\u0000")) {
|
||||||
name = name + "\000";
|
name += '\u0000';
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ensure it's not now too long
|
// Ensure it's not now too long
|
||||||
|
@ -113,12 +107,8 @@ public final class FontEntityAtom extends RecordAtom {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Everything's happy, so save the name
|
// Everything's happy, so save the name
|
||||||
try {
|
byte[] bytes = StringUtil.getToUnicodeLE(name);
|
||||||
byte[] bytes = name.getBytes("UTF-16LE");
|
System.arraycopy(bytes, 0, _recdata, 0, bytes.length);
|
||||||
System.arraycopy(bytes, 0, _recdata, 0, bytes.length);
|
|
||||||
} catch (UnsupportedEncodingException e){
|
|
||||||
throw new RuntimeException(e.getMessage(), e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setFontIndex(int idx){
|
public void setFontIndex(int idx){
|
||||||
|
|
|
@ -19,7 +19,7 @@ package org.apache.poi.hsmf.datatypes;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
import java.util.Calendar;
|
import java.util.Calendar;
|
||||||
import java.util.regex.Matcher;
|
import java.util.regex.Matcher;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
|
@ -61,12 +61,8 @@ public class MessageSubmissionChunk extends Chunk {
|
||||||
|
|
||||||
public void readValue(InputStream value) throws IOException {
|
public void readValue(InputStream value) throws IOException {
|
||||||
// Stored in the file as us-ascii
|
// Stored in the file as us-ascii
|
||||||
try {
|
byte[] data = IOUtils.toByteArray(value);
|
||||||
byte[] data = IOUtils.toByteArray(value);
|
rawId = new String(data, Charset.forName("ASCII"));
|
||||||
rawId = new String(data, "ASCII");
|
|
||||||
} catch(UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Core encoding not found, JVM broken?", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Now process the date
|
// Now process the date
|
||||||
String[] parts = rawId.split(";");
|
String[] parts = rawId.split(";");
|
||||||
|
@ -97,12 +93,8 @@ public class MessageSubmissionChunk extends Chunk {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void writeValue(OutputStream out) throws IOException {
|
public void writeValue(OutputStream out) throws IOException {
|
||||||
try {
|
byte[] data = rawId.getBytes(Charset.forName("ASCII"));
|
||||||
byte[] data = rawId.getBytes("ASCII");
|
out.write(data);
|
||||||
out.write(data);
|
|
||||||
} catch(UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Core encoding not found, JVM broken?", e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -20,7 +20,7 @@ package org.apache.poi.hsmf.datatypes;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.hsmf.datatypes.Types.MAPIType;
|
import org.apache.poi.hsmf.datatypes.Types.MAPIType;
|
||||||
import org.apache.poi.util.IOUtils;
|
import org.apache.poi.util.IOUtils;
|
||||||
|
@ -98,14 +98,9 @@ public class StringChunk extends Chunk {
|
||||||
}
|
}
|
||||||
private void storeString() {
|
private void storeString() {
|
||||||
if (type == Types.ASCII_STRING) {
|
if (type == Types.ASCII_STRING) {
|
||||||
try {
|
rawValue = value.getBytes(Charset.forName(encoding7Bit));
|
||||||
rawValue = value.getBytes(encoding7Bit);
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Encoding not found - " + encoding7Bit, e);
|
|
||||||
}
|
|
||||||
} else if (type == Types.UNICODE_STRING) {
|
} else if (type == Types.UNICODE_STRING) {
|
||||||
rawValue = new byte[value.length()*2];
|
rawValue = StringUtil.getToUnicodeLE(value);
|
||||||
StringUtil.putUnicodeLE(value, rawValue, 0);
|
|
||||||
} else {
|
} else {
|
||||||
throw new IllegalArgumentException("Invalid type " + type + " for String Chunk");
|
throw new IllegalArgumentException("Invalid type " + type + " for String Chunk");
|
||||||
}
|
}
|
||||||
|
@ -149,10 +144,6 @@ public class StringChunk extends Chunk {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Decode
|
// Decode
|
||||||
try {
|
return new String(data, Charset.forName(encoding));
|
||||||
return new String(data, encoding);
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Encoding not found - " + encoding, e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,18 +16,16 @@
|
||||||
==================================================================== */
|
==================================================================== */
|
||||||
package org.apache.poi.hwpf.model;
|
package org.apache.poi.hwpf.model;
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
import org.apache.poi.util.Internal;
|
import org.apache.poi.util.Internal;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
@Internal
|
@Internal
|
||||||
public class SinglentonTextPiece extends TextPiece
|
public class SinglentonTextPiece extends TextPiece
|
||||||
{
|
{
|
||||||
|
|
||||||
public SinglentonTextPiece( StringBuilder buffer ) throws IOException
|
public SinglentonTextPiece( StringBuilder buffer )
|
||||||
{
|
{
|
||||||
super( 0, buffer.length(), buffer.toString().getBytes( "UTF-16LE" ),
|
super( 0, buffer.length(), StringUtil.getToUnicodeLE(buffer.toString()), new PieceDescriptor( new byte[8], 0 ) );
|
||||||
new PieceDescriptor( new byte[8], 0 ) );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -17,7 +17,6 @@
|
||||||
|
|
||||||
package org.apache.poi.hwpf.model;
|
package org.apache.poi.hwpf.model;
|
||||||
|
|
||||||
import java.io.UnsupportedEncodingException;
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
|
||||||
import org.apache.poi.hwpf.usermodel.CharacterProperties;
|
import org.apache.poi.hwpf.usermodel.CharacterProperties;
|
||||||
|
@ -26,6 +25,7 @@ import org.apache.poi.util.Internal;
|
||||||
import org.apache.poi.util.LittleEndian;
|
import org.apache.poi.util.LittleEndian;
|
||||||
import org.apache.poi.util.POILogFactory;
|
import org.apache.poi.util.POILogFactory;
|
||||||
import org.apache.poi.util.POILogger;
|
import org.apache.poi.util.POILogger;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Comment me
|
* Comment me
|
||||||
|
@ -104,14 +104,7 @@ public final class StyleDescription implements HDFType
|
||||||
nameLength = std[nameStart];
|
nameLength = std[nameStart];
|
||||||
}
|
}
|
||||||
|
|
||||||
try
|
_name = StringUtil.getFromUnicodeLE(std, nameStart, (nameLength*multiplier)/2);
|
||||||
{
|
|
||||||
_name = new String(std, nameStart, nameLength * multiplier, "UTF-16LE");
|
|
||||||
}
|
|
||||||
catch (UnsupportedEncodingException ignore)
|
|
||||||
{
|
|
||||||
// ignore
|
|
||||||
}
|
|
||||||
|
|
||||||
//length then null terminator.
|
//length then null terminator.
|
||||||
int grupxStart = ((nameLength + 1) * multiplier) + nameStart;
|
int grupxStart = ((nameLength + 1) * multiplier) + nameStart;
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
package org.apache.poi.hwpf.model;
|
package org.apache.poi.hwpf.model;
|
||||||
|
|
||||||
|
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
|
|
||||||
import org.apache.poi.util.Internal;
|
import org.apache.poi.util.Internal;
|
||||||
|
|
||||||
|
@ -81,17 +81,9 @@ public class TextPiece extends PropertyNode<TextPiece>
|
||||||
* Create the StringBuilder from the text and unicode flag
|
* Create the StringBuilder from the text and unicode flag
|
||||||
*/
|
*/
|
||||||
private static StringBuilder buildInitSB(byte[] text, PieceDescriptor pd) {
|
private static StringBuilder buildInitSB(byte[] text, PieceDescriptor pd) {
|
||||||
String str;
|
String str = new String(text, Charset.forName(pd.isUnicode() ? "UTF-16LE" : "Cp1252"));
|
||||||
try {
|
|
||||||
if(pd.isUnicode()) {
|
return new StringBuilder(str);
|
||||||
str = new String(text, "UTF-16LE");
|
|
||||||
} else {
|
|
||||||
str = new String(text, "Cp1252");
|
|
||||||
}
|
|
||||||
} catch(UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException("Your Java is broken! It doesn't know about basic, required character encodings!");
|
|
||||||
}
|
|
||||||
return new StringBuilder(str);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -120,12 +112,9 @@ public class TextPiece extends PropertyNode<TextPiece>
|
||||||
|
|
||||||
public byte[] getRawBytes()
|
public byte[] getRawBytes()
|
||||||
{
|
{
|
||||||
try {
|
return ((CharSequence)_buf).toString().getBytes(
|
||||||
return ((CharSequence)_buf).toString().getBytes(_usesUnicode ?
|
Charset.forName(_usesUnicode ? "UTF-16LE" : "Cp1252")
|
||||||
"UTF-16LE" : "Cp1252");
|
);
|
||||||
} catch (UnsupportedEncodingException ignore) {
|
|
||||||
throw new RuntimeException("Your Java is broken! It doesn't know about basic, required character encodings!");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -392,7 +392,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public CharacterRun insertBefore(String text, CharacterProperties props)
|
public CharacterRun insertBefore(String text, CharacterProperties props)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
initAll();
|
initAll();
|
||||||
PAPX papx = _paragraphs.get(_parStart);
|
PAPX papx = _paragraphs.get(_parStart);
|
||||||
|
@ -421,7 +420,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public CharacterRun insertAfter(String text, CharacterProperties props)
|
public CharacterRun insertAfter(String text, CharacterProperties props)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
initAll();
|
initAll();
|
||||||
PAPX papx = _paragraphs.get(_parEnd - 1);
|
PAPX papx = _paragraphs.get(_parEnd - 1);
|
||||||
|
@ -448,7 +446,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public Paragraph insertBefore(ParagraphProperties props, int styleIndex)
|
public Paragraph insertBefore(ParagraphProperties props, int styleIndex)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
return this.insertBefore(props, styleIndex, "\r");
|
return this.insertBefore(props, styleIndex, "\r");
|
||||||
}
|
}
|
||||||
|
@ -471,7 +468,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
protected Paragraph insertBefore(ParagraphProperties props, int styleIndex, String text)
|
protected Paragraph insertBefore(ParagraphProperties props, int styleIndex, String text)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
initAll();
|
initAll();
|
||||||
StyleSheet ss = _doc.getStyleSheet();
|
StyleSheet ss = _doc.getStyleSheet();
|
||||||
|
@ -501,7 +497,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public Paragraph insertAfter(ParagraphProperties props, int styleIndex)
|
public Paragraph insertAfter(ParagraphProperties props, int styleIndex)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
return this.insertAfter(props, styleIndex, "\r");
|
return this.insertAfter(props, styleIndex, "\r");
|
||||||
}
|
}
|
||||||
|
@ -524,7 +519,6 @@ public class Range { // TODO -instantiable superclass
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
protected Paragraph insertAfter(ParagraphProperties props, int styleIndex, String text)
|
protected Paragraph insertAfter(ParagraphProperties props, int styleIndex, String text)
|
||||||
// throws UnsupportedEncodingException
|
|
||||||
{
|
{
|
||||||
initAll();
|
initAll();
|
||||||
StyleSheet ss = _doc.getStyleSheet();
|
StyleSheet ss = _doc.getStyleSheet();
|
||||||
|
|
|
@ -23,6 +23,7 @@ import org.apache.poi.ddf.EscherContainerRecord;
|
||||||
import org.apache.poi.ddf.EscherOptRecord;
|
import org.apache.poi.ddf.EscherOptRecord;
|
||||||
import org.apache.poi.hwpf.HWPFDocument;
|
import org.apache.poi.hwpf.HWPFDocument;
|
||||||
import org.apache.poi.hwpf.HWPFTestDataSamples;
|
import org.apache.poi.hwpf.HWPFTestDataSamples;
|
||||||
|
import org.apache.poi.util.StringUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Test cases for {@link OfficeDrawing} and {@link OfficeDrawingsImpl} classes.
|
* Test cases for {@link OfficeDrawing} and {@link OfficeDrawingsImpl} classes.
|
||||||
|
@ -48,7 +49,7 @@ public class TestOfficeDrawings extends TestCase
|
||||||
EscherComplexProperty gtextUNICODE = (EscherComplexProperty) officeArtFOPT
|
EscherComplexProperty gtextUNICODE = (EscherComplexProperty) officeArtFOPT
|
||||||
.lookup( 0x00c0 );
|
.lookup( 0x00c0 );
|
||||||
|
|
||||||
String text = new String( gtextUNICODE.getComplexData(), "UTF-16LE" );
|
String text = StringUtil.getFromUnicodeLE(gtextUNICODE.getComplexData());
|
||||||
assertEquals( "DRAFT CONTRACT\0", text );
|
assertEquals( "DRAFT CONTRACT\0", text );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,13 +17,13 @@
|
||||||
|
|
||||||
package org.apache.poi.util;
|
package org.apache.poi.util;
|
||||||
|
|
||||||
import java.io.UnsupportedEncodingException;
|
import java.nio.charset.Charset;
|
||||||
import java.text.NumberFormat;
|
import java.text.NumberFormat;
|
||||||
|
|
||||||
import org.apache.poi.util.StringUtil.StringsIterator;
|
|
||||||
|
|
||||||
import junit.framework.TestCase;
|
import junit.framework.TestCase;
|
||||||
|
|
||||||
|
import org.apache.poi.util.StringUtil.StringsIterator;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Unit test for StringUtil
|
* Unit test for StringUtil
|
||||||
*
|
*
|
||||||
|
@ -61,12 +61,7 @@ public final class TestStringUtil extends TestCase {
|
||||||
(byte) 'o', (byte) ' ', (byte) 'W', (byte) 'o',
|
(byte) 'o', (byte) ' ', (byte) 'W', (byte) 'o',
|
||||||
(byte) 'r', (byte) 'l', (byte) 'd', (byte) 0xAE
|
(byte) 'r', (byte) 'l', (byte) 'd', (byte) 0xAE
|
||||||
};
|
};
|
||||||
String input;
|
String input = new String( expected_output, Charset.forName(StringUtil.getPreferredEncoding()) );
|
||||||
try {
|
|
||||||
input = new String( expected_output, StringUtil.getPreferredEncoding() );
|
|
||||||
} catch (UnsupportedEncodingException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
StringUtil.putCompressedUnicode( input, output, 0 );
|
StringUtil.putCompressedUnicode( input, output, 0 );
|
||||||
for ( int j = 0; j < expected_output.length; j++ )
|
for ( int j = 0; j < expected_output.length; j++ )
|
||||||
|
|
Loading…
Reference in New Issue