Path: blob/master/test/jdk/com/sun/jndi/ldap/Base64Test.java
41153 views
/*1* Copyright (c) 2014, 2020, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223/**24* @test25* @bug 803580726* @summary Confirm that old and new Base64 encodings are compatible.27*/2829import java.io.*;30import java.util.*;31import javax.naming.*;32import javax.naming.directory.*;3334/*35* RFC 2713 specifies an encoding for Java objects stored in an LDAP directory.36* Section 3.6 specifies how a binary-valued JNDI RefAddr object is encoded37* in the value of a javaReferenceAttribute LDAP attribute: first the RefAddr38* object is serialized and then it is encoded using Base64.39*40* Since JDK 9, the JNDI/LDAP provider uses the public Base64 encoder which41* adheres strictly to the MIME encoding rules. The encoder inserts '\r\n'42* as the line separator at intervals of 76 characters. Previously the43* JNDI/LDAP provider used a private Base64 encoder which inserted '\n'44* as the line separator. It is a compatible change.45*46* This test demonstrates that there is no compatability problem when47* decoding using the new Base64 coder:48*49* encoded bytes captured from s.m.BASE64Encoder, decode with j.u.Base64.Decoder => OK50* encoded bytes captured from j.u.Base64.Encoder, decode with j.u.Base64.Decoder => OK51*52*53* NOTE: The two Base64 encodings used in this test were captured from54* LDAP protocol exchanges during attempts by the JNDI/LDAP provider55* to store a JNDI Reference test object.56*/5758public class Base64Test {59/*60* The old Base64 encoding uses '\n' as the line separator at 76 character61* intervals:62*63* 0000: 72 4F 30 41 42 58 4E 79 41 42 70 71 59 58 5A 68 rO0ABXNyABpqYXZh64* 0010: 65 43 35 75 59 57 31 70 62 6D 63 75 51 6D 6C 75 eC5uYW1pbmcuQmlu65* 0020: 59 58 4A 35 55 6D 56 6D 51 57 52 6B 63 74 43 61 YXJ5UmVmQWRkctCa66* 0030: 6B 37 4C 65 73 34 68 48 41 67 41 42 57 77 41 44 k7Les4hHAgABWwAD67* 0040: 59 6E 56 6D 64 41 41 43 57 30 4A 34 0A 63 67 41 YnVmdAACW0J4.cgA <68* 0050: 55 61 6D 46 32 59 58 67 75 62 6D 46 74 61 57 35 UamF2YXgubmFtaW569* 0060: 6E 4C 6C 4A 6C 5A 6B 46 6B 5A 48 4C 72 6F 41 65 nLlJlZkFkZHLroAe70* 0070: 61 41 6A 69 76 53 67 49 41 41 55 77 41 43 47 46 aAjivSgIAAUwACGF71* 0080: 6B 5A 48 4A 55 65 58 42 6C 64 41 41 53 54 47 70 kZHJUeXBldAASTGp72* 0090: 68 64 6D 45 76 62 47 46 75 0A 5A 79 39 54 64 48 hdmEvbGFu.Zy9TdH <73* 00A0: 4A 70 62 6D 63 37 65 48 42 30 41 41 52 30 5A 58 Jpbmc7eHB0AAR0ZX74* 00B0: 4E 30 64 58 49 41 41 6C 74 43 72 50 4D 58 2B 41 N0dXIAAltCrPMX+A75* 00C0: 59 49 56 4F 41 43 41 41 42 34 63 41 41 41 41 49 YIVOACAAB4cAAAAI76* 00D0: 41 41 41 51 49 44 42 41 55 47 42 77 67 4A 43 67 AAAQIDBAUGBwgJCg77* 00E0: 73 4D 44 51 34 50 0A 45 42 45 53 45 78 51 56 46 sMDQ4P.EBESExQVF <78* 00F0: 68 63 59 47 52 6F 62 48 42 30 65 48 79 41 68 49 hcYGRobHB0eHyAhI79* 0100: 69 4D 6B 4A 53 59 6E 4B 43 6B 71 4B 79 77 74 4C iMkJSYnKCkqKywtL80* 0110: 69 38 77 4D 54 49 7A 4E 44 55 32 4E 7A 67 35 4F i8wMTIzNDU2Nzg5O81* 0120: 6A 73 38 50 54 34 2F 51 45 46 43 51 30 52 46 52 js8PT4/QEFCQ0RFR82* 0130: 6B 64 49 0A 53 55 70 4C 54 45 31 4F 54 31 42 52 kdI.SUpLTE1OT1BR <83* 0140: 55 6C 4E 55 56 56 5A 58 57 46 6C 61 57 31 78 64 UlNUVVZXWFlaW1xd84* 0150: 58 6C 39 67 59 57 4A 6A 5A 47 56 6D 5A 32 68 70 Xl9gYWJjZGVmZ2hp85* 0160: 61 6D 74 73 62 57 35 76 63 48 46 79 63 33 52 31 amtsbW5vcHFyc3R186* 0170: 64 6E 64 34 65 58 70 37 66 48 31 2B 66 77 3D 3D dnd4eXp7fH1+fw==87* 0180: 0A <88*/89private static final String OLD_ENCODING = "rO0ABXNyABpqYXZheC5uYW1pbmcuQmluYXJ5UmVmQWRkctCak7Les4hHAgABWwADYnVmdAACW0J4\ncgAUamF2YXgubmFtaW5nLlJlZkFkZHLroAeaAjivSgIAAUwACGFkZHJUeXBldAASTGphdmEvbGFu\nZy9TdHJpbmc7eHB0AAR0ZXN0dXIAAltCrPMX+AYIVOACAAB4cAAAAIAAAQIDBAUGBwgJCgsMDQ4P\nEBESExQVFhcYGRobHB0eHyAhIiMkJSYnKCkqKywtLi8wMTIzNDU2Nzg5Ojs8PT4/QEFCQ0RFRkdI\nSUpLTE1OT1BRUlNUVVZXWFlaW1xdXl9gYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXp7fH1+fw==\n";9091/*92* The new Base64 encoding uses '\r\n' as the line separator at 76 character93* intervals:94*95* 0000: 72 4F 30 41 42 58 4E 79 41 42 70 71 59 58 5A 68 rO0ABXNyABpqYXZh96* 0010: 65 43 35 75 59 57 31 70 62 6D 63 75 51 6D 6C 75 eC5uYW1pbmcuQmlu97* 0020: 59 58 4A 35 55 6D 56 6D 51 57 52 6B 63 74 43 61 YXJ5UmVmQWRkctCa98* 0030: 6B 37 4C 65 73 34 68 48 41 67 41 42 57 77 41 44 k7Les4hHAgABWwAD99* 0040: 59 6E 56 6D 64 41 41 43 57 30 4A 34 0D 0A 63 67 YnVmdAACW0J4..cg <100* 0050: 41 55 61 6D 46 32 59 58 67 75 62 6D 46 74 61 57 AUamF2YXgubmFtaW101* 0060: 35 6E 4C 6C 4A 6C 5A 6B 46 6B 5A 48 4C 72 6F 41 5nLlJlZkFkZHLroA102* 0070: 65 61 41 6A 69 76 53 67 49 41 41 55 77 41 43 47 eaAjivSgIAAUwACG103* 0080: 46 6B 5A 48 4A 55 65 58 42 6C 64 41 41 53 54 47 FkZHJUeXBldAASTG104* 0090: 70 68 64 6D 45 76 62 47 46 75 0D 0A 5A 79 39 54 phdmEvbGFu..Zy9T <105* 00A0: 64 48 4A 70 62 6D 63 37 65 48 42 30 41 41 52 30 dHJpbmc7eHB0AAR0106* 00B0: 5A 58 4E 30 64 58 49 41 41 6C 74 43 72 50 4D 58 ZXN0dXIAAltCrPMX107* 00C0: 2B 41 59 49 56 4F 41 43 41 41 42 34 63 41 41 41 +AYIVOACAAB4cAAA108* 00D0: 41 49 41 41 41 51 49 44 42 41 55 47 42 77 67 4A AIAAAQIDBAUGBwgJ109* 00E0: 43 67 73 4D 44 51 34 50 0D 0A 45 42 45 53 45 78 CgsMDQ4P..EBESEx <110* 00F0: 51 56 46 68 63 59 47 52 6F 62 48 42 30 65 48 79 QVFhcYGRobHB0eHy111* 0100: 41 68 49 69 4D 6B 4A 53 59 6E 4B 43 6B 71 4B 79 AhIiMkJSYnKCkqKy112* 0110: 77 74 4C 69 38 77 4D 54 49 7A 4E 44 55 32 4E 7A wtLi8wMTIzNDU2Nz113* 0120: 67 35 4F 6A 73 38 50 54 34 2F 51 45 46 43 51 30 g5Ojs8PT4/QEFCQ0114* 0130: 52 46 52 6B 64 49 0D 0A 53 55 70 4C 54 45 31 4F RFRkdI..SUpLTE1O <115* 0140: 54 31 42 52 55 6C 4E 55 56 56 5A 58 57 46 6C 61 T1BRUlNUVVZXWFla116* 0150: 57 31 78 64 58 6C 39 67 59 57 4A 6A 5A 47 56 6D W1xdXl9gYWJjZGVm117* 0160: 5A 32 68 70 61 6D 74 73 62 57 35 76 63 48 46 79 Z2hpamtsbW5vcHFy118* 0170: 63 33 52 31 64 6E 64 34 65 58 70 37 66 48 31 2B c3R1dnd4eXp7fH1+119* 0180: 66 77 3D 3D120*/121private static final String NEW_ENCODING = "rO0ABXNyABpqYXZheC5uYW1pbmcuQmluYXJ5UmVmQWRkctCak7Les4hHAgABWwADYnVmdAACW0J4\r\ncgAUamF2YXgubmFtaW5nLlJlZkFkZHLroAeaAjivSgIAAUwACGFkZHJUeXBldAASTGphdmEvbGFu\r\nZy9TdHJpbmc7eHB0AAR0ZXN0dXIAAltCrPMX+AYIVOACAAB4cAAAAIAAAQIDBAUGBwgJCgsMDQ4P\r\nEBESExQVFhcYGRobHB0eHyAhIiMkJSYnKCkqKywtLi8wMTIzNDU2Nzg5Ojs8PT4/QEFCQ0RFRkdI\r\nSUpLTE1OT1BRUlNUVVZXWFlaW1xdXl9gYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXp7fH1+fw==";122123/*124* Binary-valued JNDI RefAddr test object125*/126private static final RefAddr BINARY_REF_ADDR =127new BinaryRefAddr("test", new byte[] {1280x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B,1290x0C, 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,1300x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20, 0x21, 0x22, 0x23,1310x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F,1320x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B,1330x3C, 0x3D, 0x3E, 0x3F, 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,1340x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53,1350x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F,1360x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B,1370x6C, 0x6D, 0x6E, 0x6F, 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,1380x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F139});140141public static void main(String[] args) throws Exception {142143System.out.println("\nOriginal RefAddr object:\n" + BINARY_REF_ADDR);144System.out.println("Old Base64 encoded serialized RefAddr object:\n" +145OLD_ENCODING + "\n");146System.out.println("Decode using new Base64 decoder...");147deserialize(Base64.getMimeDecoder().decode(OLD_ENCODING));148149System.out.println("----");150151System.out.println("\nOriginal RefAddr object:\n" + BINARY_REF_ADDR);152System.out.println("New Base64 encoded serialized RefAddr object:\n" +153NEW_ENCODING + "\n");154System.out.println("Decode using new Base64 decoder...");155deserialize(Base64.getMimeDecoder().decode(NEW_ENCODING));156157System.out.println("----");158}159160/*161* Deserialize the decoded Base64 bytes to recover the BinaryRefAddr object.162*/163private static void deserialize(byte[] bytes) throws Exception {164165ObjectInputStream objectStream =166new ObjectInputStream(new ByteArrayInputStream(bytes));167Object object = objectStream.readObject();168if (!BINARY_REF_ADDR.equals(object)) {169throw new Exception("Recovered object does not match the original");170}171System.out.println("Recovered RefAddr object:\n" + object);172}173174/*175* Dumps the encoding of a JNDI Reference object during an attempt to store176* in an LDAP directory.177*/178private static void storeObjectInLDAP() {179Hashtable<Object, Object> env = new Hashtable<>();180env.put(Context.REFERRAL, "follow"); // omit an LDAP control181env.put("java.naming.ldap.version", "3"); // omit LDAP bind operation182env.put("com.sun.jndi.ldap.trace.ber", System.err); // dump protocol183try {184DirContext ctx = new InitialDirContext(env);185Reference reference = new Reference("test", BINARY_REF_ADDR);186ctx.bind("ldap://ldap.example.com/cn=test", reference);187} catch (NamingException ignore) {188}189}190}191192193