View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   * http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  
20  package org.apache.commons.compress.archivers.zip;
21  
22  import static org.hamcrest.MatcherAssert.assertThat;
23  import static org.junit.jupiter.api.Assertions.assertFalse;
24  import static org.junit.jupiter.api.Assertions.assertNotNull;
25  import static org.junit.jupiter.api.Assertions.assertTrue;
26  
27  import java.io.IOException;
28  import java.nio.ByteBuffer;
29  import java.nio.charset.Charset;
30  import java.nio.charset.StandardCharsets;
31  
32  import org.hamcrest.core.IsInstanceOf;
33  import org.junit.jupiter.api.Assertions;
34  import org.junit.jupiter.api.Test;
35  
36  /**
37   * Test ZIP encodings.
38   */
39  public class ZipEncodingTest {
40  
41      private static final String UNENC_STRING = "\u2016";
42  
43      // stress test for internal grow method.
44      private static final String BAD_STRING = "\u2016\u2015\u2016\u2015\u2016\u2015\u2016\u2015\u2016\u2015\u2016";
45  
46      private static final String BAD_STRING_ENC = "%U2016%U2015%U2016%U2015%U2016%U2015%U2016%U2015%U2016%U2015%U2016";
47  
48      private static void assertEquals(final byte[] expected, final ByteBuffer actual) {
49  
50          Assertions.assertEquals(expected.length, actual.limit());
51  
52          for (final byte anExpected : expected) {
53              final byte a = actual.get();
54              Assertions.assertEquals(anExpected, a);
55          }
56  
57      }
58  
59      private void doSimpleEncodingsTest(final int n) throws IOException {
60  
61          doSimpleEncodingTest("Cp" + n, null);
62          doSimpleEncodingTest("cp" + n, null);
63          doSimpleEncodingTest("CP" + n, null);
64          doSimpleEncodingTest("IBM" + n, null);
65          doSimpleEncodingTest("ibm" + n, null);
66      }
67  
68      private void doSimpleEncodingTest(final String name, byte[] testBytes) throws IOException {
69  
70          final ZipEncoding enc = ZipEncodingHelper.getZipEncoding(name);
71          assertThat(enc, IsInstanceOf.instanceOf(NioZipEncoding.class));
72          if (testBytes == null) {
73  
74              testBytes = new byte[256];
75              for (int i = 0; i < 256; ++i) {
76                  testBytes[i] = (byte) i;
77              }
78          }
79  
80          final String decoded = enc.decode(testBytes);
81  
82          assertTrue(enc.canEncode(decoded));
83  
84          final ByteBuffer encoded = enc.encode(decoded);
85  
86          assertEquals(testBytes, encoded);
87  
88          assertFalse(enc.canEncode(UNENC_STRING));
89          assertEquals("%U2016".getBytes(name), enc.encode(UNENC_STRING));
90          assertFalse(enc.canEncode(BAD_STRING));
91          assertEquals(BAD_STRING_ENC.getBytes(name), enc.encode(BAD_STRING));
92      }
93  
94      @Test
95      public void testEbcidic() throws IOException {
96  
97          doSimpleEncodingTest("IBM1047", null);
98      }
99  
100     @Test
101     public void testGetNonexistentEncoding() {
102         final ZipEncoding ze = ZipEncodingHelper.getZipEncoding("I-am-a-banana");
103         assertNotNull(ze);
104         if (ze instanceof CharsetAccessor) {
105             final CharsetAccessor hasCharset = (CharsetAccessor) ze;
106             Assertions.assertEquals(Charset.defaultCharset(), hasCharset.getCharset());
107         }
108     }
109 
110     @Test
111     public void testIsUTF8() {
112         assertTrue(ZipEncodingHelper.isUTF8(StandardCharsets.UTF_8.name()));
113         assertTrue(ZipEncodingHelper.isUTF8("UTF8"));
114         Assertions.assertEquals(Charset.defaultCharset().name().equals(StandardCharsets.UTF_8.name()), ZipEncodingHelper.isUTF8((Charset) null));
115         Assertions.assertEquals(Charset.defaultCharset().name().equals(StandardCharsets.UTF_8.name()), ZipEncodingHelper.isUTF8((String) null));
116     }
117 
118     @Test
119     public void testNioCp1252Encoding() throws IOException {
120         // CP1252 has some undefined code points, these are
121         // the defined ones
122         // retrieved by
123         // awk '/^0x/ && NF>2 {print $1;}' CP1252.TXT
124         final byte[] b = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15,
125                 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D,
126                 0x2E, 0x2F, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, 0x40, 0x41, 0x42, 0x43, 0x44, 0x45,
127                 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D,
128                 0x5E, 0x5F, 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, 0x70, 0x71, 0x72, 0x73, 0x74, 0x75,
129                 0x76, 0x77, 0x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, (byte) 0x80, (byte) 0x82, (byte) 0x83, (byte) 0x84, (byte) 0x85, (byte) 0x86,
130                 (byte) 0x87, (byte) 0x88, (byte) 0x89, (byte) 0x8A, (byte) 0x8B, (byte) 0x8C, (byte) 0x8E, (byte) 0x91, (byte) 0x92, (byte) 0x93, (byte) 0x94,
131                 (byte) 0x95, (byte) 0x96, (byte) 0x97, (byte) 0x98, (byte) 0x99, (byte) 0x9A, (byte) 0x9B, (byte) 0x9C, (byte) 0x9E, (byte) 0x9F, (byte) 0xA0,
132                 (byte) 0xA1, (byte) 0xA2, (byte) 0xA3, (byte) 0xA4, (byte) 0xA5, (byte) 0xA6, (byte) 0xA7, (byte) 0xA8, (byte) 0xA9, (byte) 0xAA, (byte) 0xAB,
133                 (byte) 0xAC, (byte) 0xAD, (byte) 0xAE, (byte) 0xAF, (byte) 0xB0, (byte) 0xB1, (byte) 0xB2, (byte) 0xB3, (byte) 0xB4, (byte) 0xB5, (byte) 0xB6,
134                 (byte) 0xB7, (byte) 0xB8, (byte) 0xB9, (byte) 0xBA, (byte) 0xBB, (byte) 0xBC, (byte) 0xBD, (byte) 0xBE, (byte) 0xBF, (byte) 0xC0, (byte) 0xC1,
135                 (byte) 0xC2, (byte) 0xC3, (byte) 0xC4, (byte) 0xC5, (byte) 0xC6, (byte) 0xC7, (byte) 0xC8, (byte) 0xC9, (byte) 0xCA, (byte) 0xCB, (byte) 0xCC,
136                 (byte) 0xCD, (byte) 0xCE, (byte) 0xCF, (byte) 0xD0, (byte) 0xD1, (byte) 0xD2, (byte) 0xD3, (byte) 0xD4, (byte) 0xD5, (byte) 0xD6, (byte) 0xD7,
137                 (byte) 0xD8, (byte) 0xD9, (byte) 0xDA, (byte) 0xDB, (byte) 0xDC, (byte) 0xDD, (byte) 0xDE, (byte) 0xDF, (byte) 0xE0, (byte) 0xE1, (byte) 0xE2,
138                 (byte) 0xE3, (byte) 0xE4, (byte) 0xE5, (byte) 0xE6, (byte) 0xE7, (byte) 0xE8, (byte) 0xE9, (byte) 0xEA, (byte) 0xEB, (byte) 0xEC, (byte) 0xED,
139                 (byte) 0xEE, (byte) 0xEF, (byte) 0xF0, (byte) 0xF1, (byte) 0xF2, (byte) 0xF3, (byte) 0xF4, (byte) 0xF5, (byte) 0xF6, (byte) 0xF7, (byte) 0xF8,
140                 (byte) 0xF9, (byte) 0xFA, (byte) 0xFB, (byte) 0xFC, (byte) 0xFD, (byte) 0xFE, (byte) 0xFF };
141 
142         doSimpleEncodingTest("Cp1252", b);
143     }
144 
145     @Test
146     public void testNothingToMakeCoverallsHappier() {
147         final Object o = new ZipEncodingHelper() {
148         };
149         assertNotNull(o);
150     }
151 
152     @Test
153     public void testSimpleCp437Encoding() throws IOException {
154         doSimpleEncodingsTest(437);
155     }
156 
157     @Test
158     public void testSimpleCp850Encoding() throws IOException {
159         doSimpleEncodingsTest(850);
160     }
161 
162 }