1 9 10 32 33 34 package JSX; 35 import java.lang.reflect.*; 36 import java.io.*; 37 import java.util.*; 39 class XMLDeserialize { 40 41 45 private static final boolean VERSION_DEBUG = false; 46 48 private static final boolean DEBUG_CUSTOM = false; 49 51 private static final boolean DEBUG = false; 52 54 private static final boolean TESTCIRC = false; 55 57 private static final boolean ALIASDEBUG = false; 58 60 private static final boolean INTERNAL_DEBUG = false; 61 63 private static final boolean DEBUG_CLASS = false; 64 66 private static final boolean FINAL_DEBUG = false; 67 69 static final boolean GETFIELD_DEBUG = false; 70 72 static final boolean READRESOLVE_DEBUG = false; 73 75 static final boolean IBM_DEBUG = false; 76 78 static final boolean KELLY_DEBUG = false; 79 81 private static final boolean SUPER_DEBUG = false; 82 84 private static final boolean NESTED_DEBUG = false; 87 private static final boolean NESTEDREADOBJECT_DEBUG = false; 90 private static final boolean ADDATTR_NULL_DEBUG = false; 91 93 private static final boolean KELLYSUPER_DEBUG = false; 94 96 private static final boolean NOV_DEBUG = false; 97 99 private static final boolean CFG_DEBUG = false; 100 102 private static final boolean MIKE_DEBUG = false; 103 105 110 private ParserXML p; 111 private static JSX.magic.MagicClassI magic = JSX.magic.MagicClassFactory.newInstance(); 112 113 119 private int aliasSerialNumber; private Hashtable aliasHash = new Hashtable(); 121 124 125 126 131 public static void main(String args[]) { 132 System.err.println(XMLSerialize.VERSION); 133 } 134 135 136 137 141 148 XMLDeserialize(Reader in) { 149 reset(); p = new ParserXML(in); 151 } 152 153 private Config cfg = new Config(); XMLDeserialize(Reader in, Config cfg) { 155 this.cfg = cfg; 156 reset(); p = new ParserXML(in); 158 } 159 160 165 XMLDeserialize() { this(new InputStreamReader(System.in)); 167 } 168 169 170 171 175 176 GetFieldImpl currentGetField = new GetFieldImpl(); java.io.ObjectInputStream.GetField getCurrentGetField() { 179 currentGetField.setup(); return currentGetField; 181 } 182 183 final class GetFieldImpl extends java.io.ObjectInputStream.GetField { 186 HashMap objMap = new HashMap(); Class c; 189 Map fmap; 190 191 public String toString() { 192 return "GetFieldImpl state: "+objMap; 193 } 194 GetFieldImpl() { 195 } 196 197 void setup() { 198 c = (Class ) getFieldClassStack.peek(); fmap = SerialPF.getFieldNameType(c); 202 } 203 204 void putObj(String name, Object value) { 205 if (GETFIELD_DEBUG) System.err.println("putObj("+name+", "+value+");"); 206 objMap.put(name, value); 207 } 208 210 private boolean isSF(String name) { 211 if (fmap.containsKey(name)) 212 return true; 213 else 214 return false; } 216 217 public ObjectStreamClass getObjectStreamClass() { 218 return null; } 221 public boolean defaulted(String name) 222 throws IOException, IllegalArgumentException { 223 return !objMap.containsKey(name); } 225 public boolean get(String name, boolean defvalue) 226 throws IOException, IllegalArgumentException { 227 if (objMap.containsKey(name)) 228 return ParseUtilities.parseBoolean((String )objMap.get(name)); else if (isSF(name)) 230 return defvalue; 231 else 232 throw new IllegalArgumentException ("no such field"); 233 } 234 public char get(String name, char defvalue) 235 throws IOException, IllegalArgumentException { 236 if (objMap.containsKey(name)) 237 return ((String )objMap.get(name)).charAt(0); 238 else if (isSF(name)) 239 return defvalue; 240 else 241 throw new IllegalArgumentException ("no such field"); 242 } 243 public byte get(String name, byte defvalue) 244 throws IOException, IllegalArgumentException { 245 if (objMap.containsKey(name)) 246 return Byte.parseByte((String )objMap.get(name)); 247 else if (isSF(name)) 248 return defvalue; 249 else 250 throw new IllegalArgumentException ("no such field"); 251 } 252 public short get(String name, short defvalue) 253 throws IOException, IllegalArgumentException { 254 if (objMap.containsKey(name)) 255 return Short.parseShort((String )objMap.get(name)); 256 else if (isSF(name)) 257 return defvalue; 258 else 259 throw new IllegalArgumentException ("no such field"); 260 } 261 public int get(String name, int defvalue) 262 throws IOException, IllegalArgumentException { 263 if (objMap.containsKey(name)) 264 return Integer.parseInt((String )objMap.get(name)); 265 else if (isSF(name)) 266 return defvalue; 267 else 268 throw new IllegalArgumentException ("no such field"); 269 } 270 public long get(String name, long defvalue) 271 throws IOException, IllegalArgumentException { 272 if (objMap.containsKey(name)) 273 return Long.parseLong((String )objMap.get(name)); 274 else if (isSF(name)) 275 return defvalue; 276 else 277 throw new IllegalArgumentException ("no such field"); 278 } 279 public float get(String name, float defvalue) 280 throws IOException, IllegalArgumentException { 281 if (objMap.containsKey(name)) 282 return ParseUtilities.parseFloat((String )objMap.get(name)); 283 else if (isSF(name)) 284 return defvalue; 285 else 286 throw new IllegalArgumentException ("no such field"); 287 } 288 public double get(String name, double defvalue) 289 throws IOException, IllegalArgumentException { 290 if (objMap.containsKey(name)) 291 return ParseUtilities.parseDouble((String )objMap.get(name)); 292 else if (isSF(name)) 293 return defvalue; 294 else 295 throw new IllegalArgumentException ("no such field"); 296 } 297 public Object get(String name, Object defvalue) 298 throws IOException, IllegalArgumentException { 299 if (objMap.containsKey(name)) 300 return objMap.get(name); 301 else if (isSF(name)) 302 return defvalue; 303 else 304 throw new IllegalArgumentException ("no such field"); 305 } 306 } 307 308 309 310 int invocationCount = 0; 311 319 String jsxVersion; boolean superVersion = false; 323 334 Object deserialize() throws ParserXML.ExceptionXML, 335 ClassNotFoundException , 336 IOException { 338 if (MIKE_DEBUG) System.err.println("LOGGING: entering *deserialize* of the Mike Special"); 340 if (INTERNAL_DEBUG) System.err.println("RETRIEVE optional data object: "+objStoreIndex); 341 if (invocationCount==0) { 342 reset(); 343 invocationCount++; 344 ParserXML.Tag tag = p.readTag(); 345 if (tag==null) throw new EOFException("No XML found in input"); while (tag.isPI) { if (VERSION_DEBUG) System.err.println("start PI: "+ tag); 359 ParserXML.Attr attr; 360 while ( !(attr=p.readAttr()).isEndPI) { if (attr.isEnd) 362 throw new IOException("PI should end with '?>', not '/>'"); 363 if (attr.name.equals("version")) { if (VERSION_DEBUG) System.err.println("\tversion: "+attr.value); 365 if (tag.name.equals(XMLSerialize.JSX_HEADER_TARGET)) { 368 jsxVersion = attr.value; 369 if (jsxVersion.equals("1")) { 370 superVersion = false; 371 } else if (jsxVersion.equals("2")) { 372 superVersion = true; 373 } else { 374 throw new IOException("Unknown jsx version=\""+jsxVersion+"\". You need to upgrade to read this later version"); 375 } 376 } 377 } else if (attr.name.equals("encoding")) { 378 if (VERSION_DEBUG) System.err.println("\tencoding: "+attr.value); 379 } else { 382 if (VERSION_DEBUG) System.err.println("\tunknown attr: "+attr+" in PI: "+tag); 383 } 385 } 386 if (VERSION_DEBUG) System.err.println("end PI: ?>"); 387 tag = p.readTag(); } 390 405 if (!tag.start) 406 throw new ParserXML.ExceptionXML("Expected start tag, got \"</" +tag.name+ ">\""); 407 Object o = createObject(tag, null); if (TESTCIRC) 410 System.err.println("Count was: " + (aliasSerialNumber-XMLSerialize.ALIAS_INIT)); 411 if (ALIASDEBUG) System.err.println(aliasHash); 412 invocationCount--; 413 return o; } 415 else { if (superVersion) { 417 defROSubstitute(); ParserXML.Tag tag = p.readTag(); 419 if (NOV_DEBUG) 420 System.err.println("readObject: just read a "+ tag); 421 return createObject(tag, null); 422 } 423 else 424 return getObj(); 425 } 426 } 427 428 void defROSubstitute() throws IOException { 429 try { 430 if (NOV_DEBUG) System.err.println("entering defROSubstitute:"); 431 if (defROCalledStack.get()==false) { 432 if (NOV_DEBUG) System.err.println("\tfor first time"); 433 defROCalledStack.set(true); 434 defaultReadObject_ver2(); 447 } 448 } catch (ClassNotFoundException e) { 449 System.err.println("unexpected default fields - that's OK in itself," 450 + "the problem is: "+e); 451 e.printStackTrace(); 452 } 453 } 454 455 void reset() { 457 if (invocationCount!=0) 458 throw new Error ("Deserialize: Attempt to reset alias table mid-way."); 459 initAlias(); 460 } 461 void close() { p.close(); } 462 463 464 465 493 private void initAlias() { 494 aliasSerialNumber = XMLSerialize.ALIAS_INIT; 495 aliasHash.clear(); 496 } 497 508 510 516 boolean aliasNameMissing; private NamedObject getAlias(ParserXML.Attr[] addAttrTmp, String flag, Object parent) throws 518 IOException { 520 aliasNameMissing = false; 521 ParserXML.Attr attr = addAttrTmp[0]; String fieldName = null; 523 String aliasName = null; 524 if (flag.equals(XMLSerialize.ALIAS_TAG_TOKEN)) { if (!attr.isEnd) { 528 do { 529 if (attr.name.equals(XMLSerialize.NAME_TOKEN)) { 530 if (fieldName!=null) 531 throw new ParserXML.ExceptionXML("just one name field"); 532 fieldName = attr.value; 533 } 534 else if (attr.name.equals(XMLSerialize.ALIAS_ATTR_TOKEN)) { 535 if (aliasName!=null) 536 throw new ParserXML.ExceptionXML("just one alias name"); 537 aliasName = attr.value; } else 539 throw new ParserXML.ExceptionXML("unknown attribute: "+attr.name); 540 } while (!(attr=p.readAttr()).isEnd); 541 } if (!attr.emptyTag) { ParserXML.Tag closeTag = p.readTag(); 544 if (!closeTag.name.equals(XMLSerialize.ALIAS_TAG_TOKEN)) 545 throw new ParserXML.ExceptionXML(XMLSerialize.ALIAS_TAG_TOKEN, closeTag.name); 546 } 547 Object me = aliasHash.get(aliasName); 548 if (me==null) { throw new ParserXML.ExceptionXML("alias target '"+aliasName+"' not found"); 550 } 551 if (parent!=null) { if (fieldName==null) 553 aliasNameMissing = true; else { 555 currentGetField.putObj(fieldName, me); 557 Field f = getAllField(parent.getClass(), fieldName); 558 magic.setFinal(f, parent, me); 559 } 563 } 564 return new NamedObject(fieldName, me, !aliasNameMissing); 567 } 568 else 569 return null; } 571 572 573 574 582 private String putAlias(Object o) throws ParserXML.ExceptionXML { 583 if (o==null) return null; String alias; 586 if (cfg.aliasID) { alias = p.getAlias().value; } else { 589 ++aliasSerialNumber; alias = aliasSerialNumber+""; try { 592 p.getAlias(); 593 } catch (ParserXML.ExceptionXML e) {} } 595 aliasHash.put(alias, o); return alias; 599 } 600 617 618 623 624 625 651 652 658 private String updateAlias(Object o, String alias) throws IOException { 659 if (o==null) return null; if (aliasHash.put(alias, o)==null) throw new IOException("update called, but no existing alias"); 663 return alias; 665 } 666 667 668 private ObjIn oisSubclass; static final Class [] OIS_ARGS = {ObjectInputStream.class}; 671 Object [] readObjectArglist; 672 java.util.Stack getFieldClassStack = new java.util.Stack (); 673 679 void setArg(Object [] argList) { 680 readObjectArglist = argList; 681 oisSubclass = (ObjIn) argList[0]; } 683 Vector primStore = null; int primStoreIndex = -1; 691 String getPrimString() throws IOException { if (superVersion) { defROSubstitute(); return deserializePrimOptData(); 695 } else { 696 return (String ) primStore.get(primStoreIndex++); 697 } 698 } 699 700 private String deserializePrimOptData() throws IOException { 704 ParserXML.Tag tag = p.readTag(); 706 checkOpenTag(XMLSerialize.OPT_PRIM_DATA_TOKEN, tag); 707 ParserXML.Attr attr; 710 String value = null; 711 while (!(attr=p.readAttr()).isEnd) { if (attr.name.equals(XMLSerialize.VALUE_TOKEN)) 713 value = attr.value; 714 } 715 if (value==null) 716 throw new ParserXML.ExceptionXML("Expected: "+XMLSerialize.VALUE_TOKEN); 717 718 if (!attr.emptyTag) checkCloseTag(XMLSerialize.OPT_PRIM_DATA_TOKEN, p.readTag()); return value; } 723 724 725 Vector objStore = new Vector(); int objStoreIndex; 728 734 Object getObj() { 735 return objStore.get(objStoreIndex++); 736 } 738 739 752 class NamedObject { 753 String name; 754 Object object; boolean named; 756 NamedObject(String name, Object object, boolean named) { 757 this.name = name; 758 this.object = object; 759 this.named = named; 760 } 761 } 762 763 764 787 789 790 private Object createObject(ParserXML.Tag tag, Object parent) 791 throws IOException, 792 ClassNotFoundException { 794 ParserXML.Attr[] addAttrTmp = addName(); return createObject(tag, addAttrTmp, parent); 797 } 799 800 private Object createObject(ParserXML.Tag tag, ParserXML.Attr[] addAttrTmp, Object parent) 801 throws IOException, ClassNotFoundException { 802 String elementName = tag.name; if (KELLY_DEBUG) 804 System.err.println("adding "+elementName); 805 806 Object me = parent; 826 boolean nameMissing = false; NamedObject namedObject; 829 if (elementName.equals(XMLSerialize.NULL_TOKEN)) { 831 namedObject = deserializeNull(addAttrTmp, parent); me = namedObject.object; nameMissing = !namedObject.named; if (nameMissing) { if (parent!=null) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); 841 } 842 } 843 } 844 return me; 849 } 850 851 else if (elementName.startsWith(XMLSerialize.ARRAY_TOKEN)) { 853 namedObject = createArray(addAttrTmp, elementName, parent); 855 me = namedObject.object; 856 nameMissing = !namedObject.named; if (nameMissing) { if (parent!=null) { if (parent!=null && parent.getClass()!=Hashtable.class && 861 parent.getClass()!=Vector.class && 862 !parent.getClass().isArray()) { 863 objStore.add(me); } 865 } 866 } 867 return me; } 873 874 else if ( (namedObject=getAlias(addAttrTmp, elementName, parent))!=null ) { 876 me = namedObject.object; 877 nameMissing = !namedObject.named; if (nameMissing) { if (parent!=null) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); 884 } 885 } 886 } 887 return me; 888 } 889 890 else if (elementName.equals(XMLSerialize.BINARY_DATA_TOKEN)) { 892 namedObject = deserializeBinary(addAttrTmp, tag, parent); 893 nameMissing = !namedObject.named; me = namedObject.object; 897 if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); } 904 } 905 } 906 return me; 907 } 908 909 else if (elementName.equals("java.lang.String")) { 911 namedObject = deserializeWrapper(addAttrTmp, tag, parent); 914 nameMissing = !namedObject.named; me = namedObject.object; 918 if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); } 925 } 926 } 927 return me; 928 } 929 930 else if (elementName.equals("java.lang.Class")) { 932 if (DEBUG_CLASS) 933 System.err.println("Got a Class tag"); 934 namedObject = deserializeClass(addAttrTmp, tag, parent); 935 nameMissing = !namedObject.named; me = namedObject.object; 939 if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); } 946 } 947 } 948 if (DEBUG_CLASS) { 949 System.err.println(">>>>start>>>>>"); 950 System.err.println(me); 951 try { 952 System.err.println( ((Class )me).newInstance()); 953 new JSX.ObjOut(System.err).writeObject( ((Class )me).newInstance()); 954 } catch (InstantiationException e) { 955 System.err.println(e); 956 e.printStackTrace(); } catch (IllegalAccessException e) { 958 System.err.println("Should never get here - it means that we couldn't create a Hashtable with the no-arg constructor"); 959 e.printStackTrace(); 960 } 961 System.err.println("<<<<end<<<<"); 962 } 963 return me; 964 } 965 966 else if (elementName.equals("java.util.Vector")) { 968 Class clazz = Class.forName(ParseUtilities.descapeDollar(elementName)); me = null; try { 971 me = clazz.newInstance(); 972 } catch (InstantiationException e) { 973 if (DEBUG) { 974 System.err.println("Should never get here - it means that we couldn't create a Hashtable with the no-arg constructor"); 975 e.printStackTrace(); 976 } 977 } catch (IllegalAccessException e) { 978 if (DEBUG) { 979 System.err.println("Should never get here - it means that we couldn't create a Hashtable with the no-arg constructor"); 980 e.printStackTrace(); 981 } 982 } 983 ParserXML.Attr name = null; 984 name = addPrim(addAttrTmp, me, false); nameMissing = name.nameMissing; 986 if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); } 994 } 995 else { currentGetField.putObj(name.value, me); Field f = getAllField(parent.getClass(), name.value); 1000 magic.setFinal(f, parent, me); 1001 } 1005 } 1006 putAlias(me); if (!name.emptyTag) { addVectorElements((Vector) me); 1009 } 1010 return me; } 1012 1013 else if (elementName.equals("java.util.Hashtable")) { 1015 Class clazz = Class.forName(ParseUtilities.descapeDollar(elementName)); me = null; try { 1018 me = clazz.newInstance(); 1019 } catch (InstantiationException e) { 1020 if (DEBUG) { 1021 System.err.println("Should never get here - it means that we couldn't create a Hashtable with the no-arg constructor"); 1022 e.printStackTrace(); 1023 } 1024 } catch (IllegalAccessException e) { 1025 if (DEBUG) { 1026 System.err.println("Should never get here - it means that we couldn't create a Hashtable with the no-arg constructor"); 1027 e.printStackTrace(); 1028 } 1029 } 1030 ParserXML.Attr name = null; 1031 name = addPrim(addAttrTmp, me, false); nameMissing = name.nameMissing; 1033 if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); } 1041 } 1042 else { currentGetField.putObj(name.value, me); Field f = getAllField(parent.getClass(), name.value); 1047 magic.setFinal(f, parent, me); 1048 } 1052 } 1053 putAlias(me); if (!name.emptyTag) { addHashtableElements((Hashtable) me); 1056 } 1057 return me; } 1059 1060 1061 else { 1076 ParserXML.Attr name = addAttrTmp[1]; 1078 boolean subclass = false; if ( name!=null && name.value.equals(XMLSerialize.SUPER_TOKEN) ) { 1080 subclass = true; 1081 } 1082 String alias = null; Class meClassFrame; 1085 if (!subclass) { 1086 Class clazz = null; 1087 1090 1092 String escapedName = ParseUtilities.descapeDollar(elementName); 1095 ObjectStreamClass osc = magic.getOsc(escapedName); 1096 try { 1097 clazz = oisSubclass.resolveClass(osc); } catch (ClassNotFoundException noClass) { 1099 throw new ClassNotFoundException ("Could not load "+escapedName+": "+noClass); 1100 } 1101 1102 1108 1109 if (cfg.autoMemento) { 1110 Class [] innerClasses = clazz.getDeclaredClasses(); 1111 for (int i=0; i<innerClasses.length; i++) { 1112 if ( innerClasses[i].getName().endsWith("$Memento") ) { Class memento = innerClasses[i]; 1117 clazz = memento; 1119 escapedName = memento.getName(); 1120 elementName = ParseUtilities.escapeDollar(escapedName); 1121 break; 1123 } 1124 } 1125 } 1126 1127 1128 1130 1154 1157 1158 1159 me = null; try { 1161 if (Externalizable.class.isAssignableFrom(clazz)) { 1162 try { 1163 Constructor cons = clazz.getConstructor(new Class [0]); 1164 me = cons.newInstance(new Object [0]); } catch (NoSuchMethodException e) { 1167 throw new InvalidClassException("Missing public no-arg constructor for class "+ clazz.getName()); 1168 } catch (InstantiationException e) { 1169 throw new InvalidClassException("An interface or abstract class "+ clazz.getName()); 1170 } 1171 } else { 1172 me = magic.newInstance(clazz); if (me==null) 1174 throw new ClassNotFoundException ("magic.newInstance() failed to create a "+clazz+", from the name "+escapedName); 1175 } 1176 } catch (InvocationTargetException e) { 1177 Throwable thrown = e.getTargetException(); 1179 if (thrown instanceof ClassNotFoundException ) 1180 throw (ClassNotFoundException ) thrown; else if (thrown instanceof IOException) 1182 throw (IOException) thrown; else if (thrown instanceof RuntimeException ) 1184 throw (RuntimeException ) thrown; else { 1186 System.err.println("\nWrapper Exception:"); 1187 e.printStackTrace(); 1188 System.err.println("\nException wrapped up:"); 1189 thrown.printStackTrace(); 1190 } 1191 } catch (IllegalAccessException e) { 1192 e.printStackTrace(); 1193 } 1194 if (IBM_DEBUG) System.err.println("IBM: me is "+ 1195 (me==null?"null":"not null") ); 1196 if (KELLY_DEBUG) { 1197 if (me.getClass() == Class.forName("java.awt.Container")) { 1200 System.err.println("Got a java.awt.Container"); 1201 } 1202 } 1203 if (DEBUG) System.err.println("Made class \"" +elementName+ "\""); 1204 1208 alias = putAlias(me); meClassFrame = clazz; 1214 1215 if (superVersion) { 1216 if (false) throw new RuntimeException ("superVersion is disabled in this version of JSX"); 1217 lookahead.set(tag, addAttrTmp); 1218 f(me); } 1220 } else { meClassFrame = Class.forName(ParseUtilities.descapeDollar(elementName)); 1222 } 1223 1224 if (!superVersion) { 1225 Vector localStackPrimStore = primStore; int localStackPrimStoreIndex = primStoreIndex; 1227 primStore = new Vector(); primStoreIndex = 0; 1229 1231 1234 name = addPrim(addAttrTmp, me, false); 1239 1240 nameMissing = name.nameMissing; 1241 if (DEBUG && name!=null) System.err.println("Name: "+name); 1242 if (DEBUG) System.err.println("nameMissing: "+nameMissing); 1243 1244 1296 1297 if (INTERNAL_DEBUG) { 1298 if (primStore!=null) { 1299 for (Enumeration keys=primStore.elements(); keys.hasMoreElements();) { 1300 Object a = keys.nextElement(); 1301 System.err.println("In primStore: " +a+ " -- " 1302 + a.getClass() + " -- " +a.hashCode()); 1303 } 1304 } 1305 } 1306 1307 1315 Vector localStackObjStore = objStore; objStore = new Vector(); int localStackObjStoreIndex = objStoreIndex; objStoreIndex = 0; 1319 1320 Object localMeStore = meStore; meStore = me; Class localMeClassFrameStore = meClassFrameStore; meClassFrameStore = meClassFrame; 1324 boolean localEmptyTagStore = emptyTagStore; emptyTagStore = name.emptyTag; 1326 1331 1415 1416 boolean localDefaultCalledStore = defaultCalledStore; defaultCalledStore = false; 1419 Method m; 1420 if (me instanceof Externalizable) { 1421 ((Externalizable)me).readExternal(oisSubclass); 1423 } else { Vector classes = new Vector(); Class [] superClasses=XMLSerialize.getReversedSuperClasses(me.getClass()); 1430 if (SUPER_DEBUG) 1431 System.err.println(me.getClass().getName()+" "+(!nameMissing?name.value:"<unnamed>")+ ": superClasses.length = "+ superClasses.length); 1432 for (int j=0; j<superClasses.length; j++) { Class c = superClasses[j]; 1434 if ((m=XMLSerialize.getDeclaredMethod(c, "readObject", OIS_ARGS, 1435 Modifier.PRIVATE, Modifier.STATIC)) != null) { if (INTERNAL_DEBUG) System.err.print("\t--JSX deserialize--"); 1437 try { 1438 getFieldClassStack.push(c); 1439 m.invoke(me, readObjectArglist); getFieldClassStack.pop(); 1441 if (INTERNAL_DEBUG) 1442 System.err.println("\tinvoke "+m+" on "+me+" of " +me.getClass()); 1443 } catch (InvocationTargetException e) { 1444 if (DEBUG) { 1445 System.err.println("JSX InvocationTargetException:"); 1446 System.err.println("Object which is a: " +me.getClass()); 1447 e.printStackTrace(); } 1449 Throwable t = e.getTargetException(); 1452 if (t instanceof ClassNotFoundException ) 1453 throw (ClassNotFoundException )t; 1454 else if (t instanceof IOException) 1455 throw (IOException)t; 1456 else if (t instanceof RuntimeException ) 1457 throw (RuntimeException ) t; 1458 else if (t instanceof Error ) 1459 throw (Error ) t; 1460 else 1461 throw new Error ("interal error"); 1462 } catch (IllegalAccessException e) { 1463 defaultReadObject(); } 1465 } else { 1466 defaultReadObject(); } 1473 } 1474 if (superClasses.length==0) defaultReadObject(); } 1479 if (!subclass) { 1482 if (NOV_DEBUG) System.err.println("readResolve is called!!!!!!!!!!!"); 1483 me = readResolve(me, alias); } 1485 1486 defaultCalledStore = localDefaultCalledStore; meStore = localMeStore; meClassFrameStore = localMeClassFrameStore; emptyTagStore = localEmptyTagStore; 1492 objStoreIndex = localStackObjStoreIndex; objStore = localStackObjStore; 1496 primStoreIndex = localStackPrimStoreIndex; primStore = localStackPrimStore; } 1500 1501 if (superVersion) { if (!subclass) { 1503 if (NOV_DEBUG) System.err.println("readResolve is called!!!!!!!!!!!"); 1504 me = readResolve(me, alias); } 1506 } 1507 1508 1509 if (!subclass) { if (parent!=null) { if (nameMissing) { if (parent.getClass()!=Vector.class && parent.getClass()!=Hashtable.class && !parent.getClass().isArray()) { objStore.add(me); if (INTERNAL_DEBUG) 1535 System.err.println("custom obj["+objStoreIndex+"],"+objStore); 1536 } 1537 } 1538 else { 1540 if (DEBUG_CUSTOM) { 1541 System.err.println("getting field '"+name.value+"'"); 1542 } 1543 currentGetField.putObj(name.value, me); Field f = getAllField(parent.getClass(), name.value); 1546 magic.setFinal(f, parent, me); 1547 } 1551 } 1552 } 1554 1557 return me; 1558 } 1559 } 1560 1561 1562 void f(Object me) 1563 throws IOException, ParserXML.ExceptionXML, ClassNotFoundException { 1564 String openTagName = lookahead.tag.name; ParserXML.Attr[] addAttrTmp = {lookahead.attr, lookahead.name}; 1567 addPrim(addAttrTmp, me, false); lookahead.set(p.readTag(), addName()); 1570 if (lookahead.tag.start && lookahead.name.value.equals(XMLSerialize.SUPER_TOKEN)) 1571 nestedSubclass(me); 1572 else 1573 throw new ParserXML.ExceptionXML("subclass openTag", lookahead.tag.name); 1574 1575 checkCloseTag(openTagName, lookahead.tag); 1576 } 1578 1579 1580 1592 1593 1598 1599 private void eatClose(String expectedName) throws IOException, ParserXML.ExceptionXML { 1601 checkCloseTag(expectedName, lookahead.tag); 1602 advance(); 1603 } 1604 1605 private void eatOpen(String tagName, String objName) throws IOException, ParserXML.ExceptionXML { 1606 if (tagName!=null) checkOpenTag(tagName, lookahead.tag); if (objName!=null) checkObjName(objName, lookahead.name); 1608 advance(); 1609 } 1610 1611 private void checkCloseTag(String expectedName, ParserXML.Tag tag) throws ParserXML.ExceptionXML { 1612 if (tag.start) throw new ParserXML.ExceptionXML("Wanted a close tag, got an open tag", "</"+expectedName+">","<"+tag.name+">"); 1614 else if (!tag.name.equals(expectedName)) 1615 throw new ParserXML.ExceptionXML("</"+expectedName+">","</"+tag.name+">"); 1616 } 1617 1618 private void checkOpenTag(String expectedName, ParserXML.Tag tag) throws ParserXML.ExceptionXML { 1619 if (!tag.start) 1620 throw new ParserXML.ExceptionXML("Wanted an open tag, got a close tag", "</"+expectedName+">","<"+tag.name+">"); 1621 else if (!tag.name.equals(expectedName)) 1622 throw new ParserXML.ExceptionXML("</"+expectedName+">","</"+tag.name+">"); 1623 } 1624 1625 private void checkObjName(String expectedName, ParserXML.Attr name) throws ParserXML.ExceptionXML { 1626 if (name==null) 1627 throw new ParserXML.ExceptionXML("Expected a name, but none found"); 1628 else if (!name.value.equals(expectedName)) 1629 throw new ParserXML.ExceptionXML("</"+expectedName+">","</"+name.value+">"); 1630 } 1631 1632 1633 1649 1650 1690 1691 private void nestedSubclass(Object me) 1692 throws IOException, ClassNotFoundException { 1693 String frameName = lookahead.tag.name; generalReadObject(me); if (lookahead.tag.start && 1696 lookahead.name.value.equals(XMLSerialize.SUPER_TOKEN)) { 1697 nestedSubclass(me); 1698 } 1699 eatClose(frameName); 1700 } 1701 1702 1703 final Lookahead lookahead = new Lookahead(); 1704 static class Lookahead { 1705 ParserXML.Tag tag; 1706 ParserXML.Attr attr; 1707 ParserXML.Attr name; 1708 void set(ParserXML.Tag tag, ParserXML.Attr attr, ParserXML.Attr name) { 1709 this.tag = tag; 1710 this.attr = attr; 1711 this.name = name; 1712 } 1713 void set(ParserXML.Tag tag, ParserXML.Attr[] addAttrTmp) { 1714 this.tag = tag; 1715 if (addAttrTmp!=null) { 1716 this.attr = addAttrTmp[0]; 1717 this.name = addAttrTmp[1]; 1718 } 1719 } 1720 } 1721 1722 1723 1724 1730 1777 1778 1779 static class ObjStack { Vector v = new Vector(); 1781 void push(Object o) { 1782 v.add(o); 1783 } 1784 void set(Object o) { 1785 v.set(v.size()-1, o); 1786 } 1787 Object get() { 1788 return v.get(v.size()-1); 1789 } 1790 Object pop() { 1791 return v.remove(v.size()-1); 1792 } 1793 } 1794 1795 static class TagStack { ObjStack s = new ObjStack(); 1797 void push(ParserXML.Tag tag) { 1798 s.push(tag); 1800 } 1801 void set(ParserXML.Tag tag) { 1802 s.set(tag); 1804 } 1805 ParserXML.Tag get() { 1806 return (ParserXML.Tag)s.get(); 1807 } 1808 ParserXML.Tag pop() { 1809 return (ParserXML.Tag)s.pop(); 1811 } 1812 } 1813 1814 static class BooleanStack { ObjStack s = new ObjStack(); 1816 void push(boolean bool) { 1817 s.push(bool?Boolean.TRUE:Boolean.FALSE); } 1820 void set(boolean bool) { 1821 s.set(bool?Boolean.TRUE:Boolean.FALSE); 1822 } 1823 boolean get() { 1824 return ((Boolean )s.get()).booleanValue(); 1825 } 1826 boolean pop() { 1827 return ((Boolean )s.pop()).booleanValue(); 1829 } 1830 } 1831 1832 TagStack defROStack = new TagStack(); 1833 BooleanStack defROCalledStack = new BooleanStack(); 1834 1835 void generalReadObject(Object me) 1836 throws IOException, ClassNotFoundException { 1837 Class meClassFrame = Class.forName(ParseUtilities.descapeDollar(lookahead.tag.name)); 1838 ParserXML.Attr[] addAttrTmp = {lookahead.attr, lookahead.name}; 1840 defaultReadObject_attrs_in = addAttrTmp; 1841 defaultReadObject_me = me; 1842 defROStack.push(null); 1843 defROCalledStack.push(false); 1844 1845 Method readObjectMethod = XMLSerialize.getDeclaredMethod(meClassFrame, 1846"readObject", OIS_ARGS, Modifier.PRIVATE, Modifier.STATIC); 1847 if (readObjectMethod==null) { 1848 d(); 1850 } else { 1851 System.err.println(" ----- s() is called"); 1852 s(me, readObjectMethod); 1853 } 1854 defROStack.pop(); 1855 defROCalledStack.pop(); } 1857 1858 1866 1867 void d() throws ParserXML.ExceptionXML, IOException, ClassNotFoundException { 1868 defaultReadObject_ver2_from_d(); 1870 if (lookahead.tag.start && lookahead.tag.name.equals(XMLSerialize.OPT_DATA_TOKEN)) { 1871 eatOpen(XMLSerialize.OPT_DATA_TOKEN, null); eatClose(XMLSerialize.OPT_DATA_TOKEN); 1874 } 1875 } 1876 1877 1878 1879 1883 void s(Object me, Method readObjectMethod) 1884 throws ParserXML.ExceptionXML, IOException, ClassNotFoundException { 1885 invokeReadObject(me, readObjectMethod); 1886 if (!defROCalledStack.get()) { System.err.println("calling defRO from s()"); 1888 defaultReadObject_ver2_from_s(); } 1890 1891 1895 1896 1908 1909 ParserXML.Tag earlierOpt = defROStack.get(); 1910 if (earlierOpt.start && earlierOpt.name.equals(XMLSerialize.OPT_DATA_TOKEN)) { 1911 advance(); if (!earlierOpt.name.equals(lookahead.tag.name)) { 1913 System.err.println("earlier: "+earlierOpt); 1914 System.err.println("lookahead: "+lookahead.tag); 1915 System.exit(0); 1917 } 1918 System.err.println("reading <opt> in s()"); 1919 eatClose(XMLSerialize.OPT_DATA_TOKEN); 1920 } 1921 1922 1936 1937 } 1938 1939 1940 1941 void invokeReadObject(Object me, Method readObjectMethod) 1942 throws ClassNotFoundException , IOException { 1943 if (NOV_DEBUG) System.err.println("using correct class frame now (I believe)"); 1944 if (NESTEDREADOBJECT_DEBUG) System.err.print("\t--JSX deserialize--"); 1945 try { 1946 readObjectMethod.invoke(me, readObjectArglist); 1947 if (NESTEDREADOBJECT_DEBUG) 1948 System.err.println("\tinvoke "+readObjectMethod+" on "+me+" of " +me.getClass()); 1949 } catch (InvocationTargetException e) { 1950 if (DEBUG) { 1951 System.err.println("JSX InvocationTargetException:"); 1952 System.err.println("Object which is a: " +me.getClass()); 1953 e.printStackTrace(); } 1955 Throwable t = e.getTargetException(); 1958 if (t instanceof ClassNotFoundException ) 1959 throw (ClassNotFoundException ) t; 1960 else if (t instanceof IOException) 1961 throw (IOException)t; 1962 else if (t instanceof RuntimeException ) 1963 throw (RuntimeException ) t; 1964 else if (t instanceof Error ) 1965 throw (Error ) t; 1966 else 1967 throw new Error ("internal error"); 1968 } catch (IllegalAccessException e) { 1969 System.err.println("IllegalAccessExcetion - please report this error"); 1970 e.printStackTrace(); 1971 } 1973 } 1976 1977 1978 1979 2093 2094 2095 2096 2102 void defaultReadObject() throws IOException, ClassNotFoundException { 2103 if (superVersion) { 2104 ; defaultReadObject_ver2(); } else { 2108 defaultReadObject_ver1(); } 2110 } 2111 2112 2113 2114 2120 void defaultReadObject_ver2_from_d() throws IOException, ClassNotFoundException { 2121 defROCalledStack.set(true); 2122 Object me = defaultReadObject_me; 2123 2124 addPrim(new ParserXML.Attr[] {lookahead.attr, lookahead.name}, me, false); 2125 advance(); 2126 while (openF(me)) { 2127 createObject(lookahead.tag, new ParserXML.Attr[]{lookahead.attr,lookahead.name}, me); advance(); } 2130 } 2131 2132 2133 2138 void defaultReadObject_ver2_from_s() throws IOException, ClassNotFoundException { 2139 defROCalledStack.set(true); 2140 Object me = defaultReadObject_me; 2141 addPrim(defaultReadObject_attrs_in, me, false); 2144 advance(); while (openF(me)) { createObject(lookahead.tag, 2147 new ParserXML.Attr[]{lookahead.attr,lookahead.name}, 2148 me); advance(); } 2151 if (lookahead.tag.start && lookahead.tag.name.equals(XMLSerialize.OPT_DATA_TOKEN)) { addPrim(new ParserXML.Attr[] {lookahead.attr,lookahead.name}, me, false); 2153 } 2154 defaultReadObject_attrs_out = 2155 new ParserXML.Attr[] {lookahead.attr,lookahead.name}; 2156 defROStack.set(lookahead.tag); } 2158 2159 2160 Object defaultReadObject_me; 2161 ParserXML.Attr[] defaultReadObject_attrs_in; 2162 ParserXML.Attr[] defaultReadObject_attrs_out; 2163 void defaultReadObject_ver2() throws IOException, ClassNotFoundException { 2164 defROCalledStack.set(true); 2165 Object me = defaultReadObject_me; 2166 addPrim(defaultReadObject_attrs_in, me, false); 2169 advance(); while (openF(me)) { createObject(lookahead.tag, 2172 new ParserXML.Attr[]{lookahead.attr,lookahead.name}, 2173 me); advance(); } 2176 if (lookahead.tag.start && lookahead.tag.name.equals(XMLSerialize.OPT_DATA_TOKEN)) { addPrim(new ParserXML.Attr[] {lookahead.attr,lookahead.name}, me, false); 2178 } 2179 defaultReadObject_attrs_out = 2180 new ParserXML.Attr[] {lookahead.attr,lookahead.name}; 2181 defROStack.set(lookahead.tag); } 2183 2184 2185 2186 2190 void advance() throws IOException { 2191 ParserXML.Tag tag = p.readTag(); 2192 if (tag.start) lookahead.set(tag, addName()); 2193 else lookahead.set(tag, null, null); } 2195 2196 2201 2202 boolean openF(Object me) throws IOException, ClassNotFoundException { 2203 if (lookahead.tag==null) { 2204 throw new EOFException("Premature EOF"); 2205 } 2206 else if (lookahead.tag.start && lookahead.tag.name.equals(XMLSerialize.OPT_DATA_TOKEN)) { return false; } 2209 else if (lookahead.tag.start && lookahead.name!=null && lookahead.name.value.equals(XMLSerialize.SUPER_TOKEN)) { return false; } 2212 else if (lookahead.tag.start) { return true; 2214 } 2215 else if (!lookahead.tag.start) { return false; 2217 } 2218 else { 2219 throw new Error ("Internal error: Please send the stacktrace and XML "+ 2220 "input file to bren@mail.csse.monash.edu.au to report this problem"); 2221 } 2222 } 2223 2224 2225 2262 2263 2264 2268 2269 2270 2334 2335 2336 boolean defaultCalledStore; Object meStore; Class meClassFrameStore; 2341 boolean emptyTagStore; 2342 void defaultReadObject_ver1() throws 2344 IOException, 2345 ClassNotFoundException { 2347 if (!defaultCalledStore) { defaultCalledStore = true; 2350 if (!emptyTagStore) { 2351 Object me = meStore; Class meClassFrame = meClassFrameStore; 2354 ParserXML.Tag tag; 2355 while ( ((tag=p.readTag())!=null) && (tag.start)) { 2356 createObject(tag, me); 2357 } 2358 if (tag==null) throw new EOFException("Premature EOF"); 2359 else { 2360 String className = meClassFrame.getName(); String rightTag = ParseUtilities.escapeDollar(className); 2362 String closeTag = tag.name; 2363 if (cfg!=null && cfg.refactor!=null) 2364 closeTag = cfg.refactor.mapClassname(closeTag); if (!closeTag.equals(rightTag)) 2366 throw new ParserXML.ExceptionXML( 2367 "</"+rightTag+">","</"+closeTag+">"); 2368 } 2369 } 2370 } 2371 } 2372 2373 2374 2384 2414 2415 2416 2417 2429 Object readResolve(Object me, String alias) throws ObjectStreamException { 2430 if (READRESOLVE_DEBUG) 2431 System.err.println("entered readResolve, with "+me+" and alias="+alias); 2432 try { 2433 Method readResolveMethod = null; 2434 try { 2435 readResolveMethod = me.getClass().getDeclaredMethod("readResolve", new Class []{}); 2436 } catch (NoSuchMethodException e) { 2437 if (READRESOLVE_DEBUG) 2439 System.err.println("No readResolve() found - checking super"); 2440 Class clazz = me.getClass(); while (clazz!=Object .class) { try { 2444 clazz = clazz.getSuperclass(); 2445 readResolveMethod = clazz.getDeclaredMethod("readResolve", new Class []{}); 2446 break; } catch (NoSuchMethodException continueLoop) { 2448 } 2449 } 2450 if (readResolveMethod==null) return me; 2452 if (!checkSuperMethodAccess(readResolveMethod, me.getClass())) 2453 return me; 2456 } readResolveMethod.setAccessible(true); 2475 Object newme = readResolveMethod.invoke(me, new Object []{}); updateAlias(newme, alias); if (READRESOLVE_DEBUG) 2478 System.err.println("readResolve returned "+newme); 2479 return newme; 2481 } catch (InvocationTargetException e) { 2482 System.err.println("JSX InvocationTargetException:"); 2483 try { 2487 throw (ObjectStreamException) e.getTargetException(); } catch (ClassCastException f) { 2491 throw new Error ("readResolve() of "+me.getClass()+ " threw an '"+e.getTargetException()+"'. It should only be of type ObjectStreamException"); 2492 } 2493 } catch (Exception e) { 2494 System.err.println("not an InvocationTargetException"); 2495 e.printStackTrace(); 2496 } 2497 return null; } 2499 2500 static private boolean checkSuperMethodAccess(Method scMethod, Class ofClass) { 2502 if (scMethod == null) { 2503 return false; 2504 } 2505 int supermods = scMethod.getModifiers(); 2506 if (Modifier.isPublic(supermods) || Modifier.isProtected(supermods)) { 2507 return true; 2508 } else if (Modifier.isPrivate(supermods)) { 2509 return false; 2510 } else { 2511 return isSameClassPackage(scMethod.getDeclaringClass(), ofClass); 2513 } 2517 } 2518 2519 static private boolean isSameClassPackage(Class cl1, Class cl2) { 2520 if (cl1.getClassLoader() != cl2.getClassLoader()) { 2521 return false; 2522 } else { 2523 String clName1 = cl1.getName(); 2524 String clName2 = cl2.getName(); 2525 int idx1 = clName1.lastIndexOf('.'); 2526 int idx2 = clName2.lastIndexOf('.'); 2527 if (idx1 == -1 || idx2 == -1) { 2528 2531 return idx1 == idx2; 2532 } else { 2533 return clName1.regionMatches(false, 0, 2534 clName2, 0, idx1 - 1); 2535 } 2536 } 2537 } 2538 2539 2540 2541 2542 2543 2544 2545 2550 private NamedObject deserializeNull(ParserXML.Attr[] addAttrTmp, Object parent) throws 2552 ClassNotFoundException , 2553 NotActiveException, 2555 IOException { 2556 String name = null; 2557 Object me = null; 2558 boolean named = false; 2559 ParserXML.Attr firstAttr = addPrim(addAttrTmp, me, false); if (!firstAttr.nameMissing) { named = true; 2563 name = firstAttr.value; } 2565 if (!firstAttr.emptyTag) { ParserXML.Tag tag = p.readTag(); 2569 if (tag==null) 2570 throw new EOFException("Premature EOF"); 2571 else if (tag.start) throw new ParserXML.ExceptionXML( 2573 "</"+XMLSerialize.NULL_TOKEN+">","<"+tag.name+">"); 2574 else if (!tag.name.equals(XMLSerialize.NULL_TOKEN)) { throw new ParserXML.ExceptionXML( 2577 "</"+XMLSerialize.NULL_TOKEN+">","</"+tag.name+">"); 2578 } 2579 } 2580 2581 if (parent!=null) { 2583 if (named) { 2584 if (name==null) { throw new IOException("name: No " +XMLSerialize.NAME_TOKEN+ " attribute found for "+parent.getClass()); 2586 } 2587 currentGetField.putObj(name, me); Field f = getAllField(parent.getClass(), name); 2590 magic.setFinal(f, parent, me); 2591 return new NamedObject(name, me, named); 2595 } else { return new NamedObject(name, me, named); 2597 } 2598 } else { return new NamedObject(name, me, named); 2600 } 2601 } 2602 2603 2604 2605 2606 2623 private Field getAllField(Class c, String fieldName) 2624 throws SecurityException { 2625 Field field = null; 2626 try { 2627 field = attemptGetAllField(c, fieldName); } catch (NoSuchFieldException firstE) { if (cfg.noSuchFieldHandler!=null) { if (CFG_DEBUG) System.err.println("cfg = "+cfg); 2631 String mappedFieldName = null; 2632 try { 2633 mappedFieldName = cfg.noSuchFieldHandler.noSuchField(c, fieldName); 2634 } catch (NoSuchFieldException secondE) { 2635 throw new IllegalArgumentException (secondE+""); } try { 2638 field = attemptGetAllField(c, mappedFieldName); } catch (NoSuchFieldException secondE) { 2640 throw new IllegalArgumentException ( 2642 "Mapped '"+fieldName+"'" + 2643 " to '"+mappedFieldName+"'" + 2644 ", but neither found in "+c+": "+secondE); } } 2647 } return field; 2650 } 2651 2652 2653 2672 2673 2678 2679 private Field attemptGetAllField(Class c, String fieldName) throws 2680 NoSuchFieldException , 2681 SecurityException { 2682 if (fieldName==null) 2683 throw new NoSuchFieldException ("field name had value 'null'"); 2684 Field f = null; 2685 if ((f=getShadowedField(fieldName))!=null) { if (SerialPF.isFieldSerializable(f)) { f.setAccessible(true); return f; } 2691 else throw new NoSuchFieldException (f +": this field evolved to non-serializeable, it seems."); 2692 } 2693 Class initc = c; boolean isObjSer = Serializable.class.isAssignableFrom(initc); 2696 do { 2697 if (isObjSer && !Serializable.class.isAssignableFrom(c)) 2698 continue; try { 2700 f = c.getDeclaredField(fieldName); 2701 } catch (NoSuchFieldException e) { } catch (Exception e) { 2703 System.err.println(e +": No such field '"+ fieldName +"' in "+ c +" (superclass of " +initc); 2704 } 2705 } while ( f==null && (c = c.getSuperclass()) != Object .class); 2706 if (f==null) 2707 throw new NoSuchFieldException ("JSX can't find the field " 2708 +((fieldName==null)?"<null>":"'"+fieldName+"'") 2709 + ". Not in " +initc+ ", or private, or in superclasses\n" 2710 + "Could it be that the class lacks a readObject() method, or is a non-Serializable ancestor of a Serializable class? (see JOS rules on this)"); 2711 if (SerialPF.isFieldSerializable(f)) { f.setAccessible(true); return f; } 2716 else throw new NoSuchFieldException (f +": this field evolved to non-serializeable, it seems."); 2717 } 2718 2719 2720 Field getShadowedField(String s) throws NoSuchFieldException { 2722 int dotpos = s.lastIndexOf('.'); 2723 if (dotpos==-1) return null; 2725 String classQual = s.substring(0, dotpos); String fieldName = s.substring(dotpos+1); Class clazz = null; 2728 2729 String escapedName = ParseUtilities.descapeDollar(classQual); 2730 try { 2731 ObjectStreamClass osc = magic.getOsc(escapedName); 2732 clazz = oisSubclass.resolveClass(osc); } catch (IOException e) { 2734 e.printStackTrace(); 2735 } catch (ClassNotFoundException e) { 2736 System.err.println("The class-qualification of this shadowed field was not found: "+ s); 2740 e.printStackTrace(); 2741 } 2742 return clazz.getDeclaredField(fieldName); 2743 } 2744 2745 2746 2747 2748 2749 2750 2781 private NamedObject createArray(ParserXML.Attr[] addAttrTmp, String tagName, Object parent) throws 2783 ClassNotFoundException , 2784 IOException { 2786 int length = -1; String name = null; boolean named = false; boolean emptyTag = false; 2796 ParserXML.Attr firstAttr = addPrim(addAttrTmp, null, true); length = firstAttr.length; 2799 if (!firstAttr.nameMissing) { named = true; 2801 name = firstAttr.value; } 2803 emptyTag = firstAttr.emptyTag; 2804 2805 2813 2817 int dim = 0; 2820 int index=0; 2821 String tok = XMLSerialize.ARRAY_TOKEN; 2822 int skip = tok.length(); 2823 while (tagName.startsWith(tok, index)) { dim++; index+=skip; 2827 } 2828 if (DEBUG) System.err.println("dim= " +dim); 2829 String type = tagName.substring(index); if (DEBUG) System.err.println("type= " +type); 2831 Object me = null; 2832 int[] dimsArray = new int[dim]; 2834 dimsArray[0] = length; Class comp; 2836 if (type.equals("int")) comp = int.class; 2838 else if (type.equals("double")) comp = double.class; 2839 else if (type.equals("boolean")) comp = boolean.class; 2840 else if (type.equals("char")) comp = char.class; 2841 else if (type.equals("byte")) comp = byte.class; 2842 else if (type.equals("short")) comp = short.class; 2843 else if (type.equals("long")) comp = long.class; 2844 else if (type.equals("float")) comp = float.class; 2845 else { 2846 if (MIKE_DEBUG) System.err.println("LOGGING: array object component, within the Mike Special"); 2847 ObjectStreamClass osc = magic.getOsc(ParseUtilities.descapeDollar(type)); 2848 comp = oisSubclass.resolveClass(osc); } 2851 me = Array.newInstance(comp, dimsArray); 2852 putAlias(me); 2853 if (DEBUG) System.err.println("type= " +me.getClass().getName()); 2857 if (DEBUG) System.err.println("len= " +Array.getLength(me)); 2858 2859 2860 ParserXML.Tag tag; 2861 ParserXML.Attr secondAttr = null; 2862 if (dim==1 && me.getClass().getComponentType().isPrimitive()) { 2864 addAttrTmp = addName(); secondAttr = addPrim(addAttrTmp, me, true); length = -1; if (!secondAttr.nameMissing) { if (named) throw new IOException("two names: " 2871 +"'"+firstAttr.value+"' and '"+ secondAttr.value+"' " 2872 +"in "+parent.getClass()); 2873 named = true; 2874 name = secondAttr.value; } 2876 emptyTag = secondAttr.emptyTag; 2877 if (DEBUG) System.err.println("after setting primitive array, saw: " + secondAttr); 2881 } 2882 else { 2884 ParserXML.Attr end = p.readAttr(); if (DEBUG) System.err.println("after starting reference array, saw: " + end); 2889 for (int i=0; i<length; i++) { 2891 Object obj; 2893 tag=p.readTag(); 2894 if (tag==null) throw new EOFException("Premature EOF"); 2895 if (!tag.start) 2896 throw new IOException("Expected "+length+" elements in array; read only"+i); 2897 if (tag.name.equals("java.lang.String") || tag.name.equals("java.lang.Integer") 2899 || tag.name.equals("java.lang.Double") 2900 || tag.name.equals("java.lang.Boolean") 2901 || tag.name.equals("java.lang.Character") 2902 || tag.name.equals("java.lang.Byte") 2903 || tag.name.equals("java.lang.Short") 2904 || tag.name.equals("java.lang.Long") 2905 || tag.name.equals("java.lang.Float") 2906 ) 2907 obj = deserializeWrapper(tag, null).object; 2908 else 2909 obj = createObject(tag, null); if (DEBUG) System.err.println("Adding {"+obj+"} to Array"); 2912 Array.set(me, i, obj); 2913 } } 2916 if (!emptyTag) { tag=p.readTag(); 2918 if (tag==null) throw new EOFException("Premature EOF"); 2919 if (tag.start) 2920 throw new IOException("End of array"); 2921 if (!tag.name.equals(tagName)) throw new ParserXML.ExceptionXML( 2923 "</"+tagName+">","</"+tag.name+">"); 2924 } 2925 2930 if (parent!=null) { 2931 if (named) { 2932 if (name==null) { throw new IOException("name: No " +XMLSerialize.NAME_TOKEN+ " attribute found for "+parent.getClass()); 2934 } 2935 currentGetField.putObj(name, me); Field f = getAllField(parent.getClass(), name); 2942 magic.setFinal(f, parent, me); 2943 return new NamedObject(name, me, named); 2949 } else { return new NamedObject(name, me, named); 2951 } 2952 } else { return new NamedObject(name, me, named); 2954 } 2955 2956 } 2957 2958 2959 2968 3002 3003 3004 3005 3020 private ParserXML.Attr addAttr(Object o, boolean isArray) throws 3021 IOException, 3022 ClassNotFoundException , 3024 ParserXML.ExceptionXML { 3025 ParserXML.Attr[] addAttrTmp = addName(); return addPrim(addAttrTmp, o, isArray); 3027 } 3028 3029 3035 private ParserXML.Attr[] addName() throws 3036 IOException, 3037 ParserXML.ExceptionXML { 3040 ParserXML.Attr attr; ParserXML.Attr name = null; if ( !(attr=p.readAttr()).isEnd ) { 3043 if (DEBUG) System.err.println(attr); 3044 if (attr.name.equals(XMLSerialize.NAME_TOKEN)) { if (name!=null) 3046 throw new ParserXML.ExceptionXML("just one name field"); 3047 name = attr; 3048 } 3052 } 3053 return new ParserXML.Attr[] {attr, name}; 3054 } 3055 3056 private ParserXML.Attr addPrim(ParserXML.Attr[] addAttrTmp, Object o, boolean isArray) throws 3057 IOException, 3058 ClassNotFoundException , 3060 ParserXML.ExceptionXML { 3061 int length = -1; if (ADDATTR_NULL_DEBUG) 3064 System.err.println("addAttrTmp = "+addAttrTmp); 3065 ParserXML.Attr attr = addAttrTmp[0]; 3067 ParserXML.Attr name = addAttrTmp[1]; if (!attr.isEnd) { 3069 do { 3071 if (name==attr) continue; if (isArray) { if (attr.name.equals(XMLSerialize.LENGTH_TOKEN)) { if (INTERNAL_DEBUG) { 3076 System.err.println("ARRAY LENGTH: " +attr); 3077 } 3078 length = Integer.parseInt(attr.value); 3079 break; } 3081 if (INTERNAL_DEBUG) { 3082 System.err.println("ARRAY PRIMITIVE ATTRIBUTES: " +attr); 3083 } 3084 String indexStr = attr.name.substring(XMLSerialize.ARRAY_PRIMITIVE_INDEX_TOKEN.length()); 3087 int index = Integer.parseInt(indexStr); if (DEBUG) System.err.println(attr); 3089 Object value = getValue(o.getClass().getComponentType(), attr); 3090 Array.set(o, index, value); 3095 } 3096 else { if (attr.name.endsWith(XMLSerialize.ALIAS_STRING_TOKEN)) { if (INTERNAL_DEBUG) { 3099 System.err.println("STRING ALIAS: " +attr); 3100 } 3101 String fieldName = attr.name.substring(0, attr.name.indexOf(XMLSerialize.ALIAS_STRING_TOKEN)); 3103 Object strObj = aliasHash.get(attr.value); currentGetField.putObj(fieldName, strObj); Field f = getAllField(o.getClass(), fieldName); 3109 if (f!=null) { 3111 magic.setFinal(f, o, strObj); 3114 } 3115 } 3120 else { if (attr.name.startsWith(XMLSerialize.INTERNAL_PRIMITIVE_TOKEN)) { 3122 if (INTERNAL_DEBUG) { 3123 System.err.println("INTERNAL: " +attr); 3124 } 3125 String primString = attr.name.substring(XMLSerialize.INTERNAL_PRIMITIVE_TOKEN.length()); if (DEBUG) System.err.println(attr); 3127 primStore.add(attr.value); } 3154 else { if (INTERNAL_DEBUG) { 3156 System.err.println("ordinary: "+attr); 3157 } 3158 if (IBM_DEBUG) System.err.println("IBM: currentGetField = "+currentGetField); 3160 if (IBM_DEBUG) System.err.println("IBM: attr = "+attr); 3161 currentGetField.putObj(attr.name, attr.value); if (IBM_DEBUG) System.err.println("IBM: o is "+ 3163 (o==null?"null":"not null") ); 3164 Field f = getAllField(o.getClass(), attr.name); if (f!=null) { 3170 Class fc = f.getType(); if (DEBUG) System.err.println("Made Field \""+fc.getName()+"\""); 3172 magic.setFinal(f, o, getValue(fc, attr)); 3173 } 3174 } 3178 } 3179 } 3180 } while (!(attr=p.readAttr()).isEnd); 3181 } 3182 attr.length = length; 3184 if (name==null) { 3185 attr.nameMissing = true; 3187 return attr; } 3189 name.isEnd = attr.isEnd; 3191 name.emptyTag = attr.emptyTag; 3192 name.length = attr.length; 3193 return name; 3194 } 3195 3196 3197 3211 private Object getValue(Class fc, ParserXML.Attr attr) throws IOException { 3212 if (DEBUG) System.err.println("getting value of " +fc); 3213 if (fc.isPrimitive()) { if (fc==int.class) return new Integer (attr.value); else if (fc==double.class) 3216 return new Double (ParseUtilities.parseDouble(attr.value)); else if (fc==boolean.class) { 3218 return new Boolean (ParseUtilities.parseBoolean(attr.value)); 3219 } 3220 else if (fc==byte.class) return new Byte (attr.value); 3221 else if (fc==char.class) { 3222 String a = ParseUtilities.decodeXML(attr.value); if (a.length()!=1) throw new IllegalArgumentException ("Character data must be exactly one character long; instead we got: '" +a+ "'"); 3224 return new Character (a.charAt(0)); 3225 } 3226 else if (fc==short.class) return new Short (attr.value); 3227 else if (fc==long.class) return new Long (attr.value); 3229 else if (fc==float.class) 3230 return new Float (ParseUtilities.parseFloat(attr.value)); 3231 else throw new ParserXML.ExceptionXML( 3232 "Unimplemented primitive: \"" +fc.getName()+ "\""); 3233 } 3234 else { if (fc==String .class) { 3236 String s = ParseUtilities.decodeXML(attr.value); 3237 putAlias(s); return s; 3239 } 3240 else throw new ParserXML.ExceptionXML( 3241 "'"+attr.name+"' is not primitive or String"); 3242 } 3243 } 3244 3245 3246 3247 3248 3255 private void addVectorElements(Vector v) throws 3256 ClassNotFoundException , 3257 IOException { 3259 ParserXML.Tag tag; 3260 while (true) { 3261 Object obj; 3262 tag = p.readTag(); 3263 if (tag==null) throw new EOFException("Premature EOF"); 3264 if (!tag.start) return; if (tag.name.equals("java.lang.String") || tag.name.equals("java.lang.Integer") 3267 || tag.name.equals("java.lang.Double") 3268 || tag.name.equals("java.lang.Boolean") 3269 || tag.name.equals("java.lang.Character") 3270 || tag.name.equals("java.lang.Byte") 3271 || tag.name.equals("java.lang.Short") 3272 || tag.name.equals("java.lang.Long") 3273 || tag.name.equals("java.lang.Float") 3274 ) 3275 obj = deserializeWrapper(tag, null).object; 3276 else 3277 obj = createObject(tag, null); if (DEBUG) System.err.println("Adding {"+obj+"} to Vector"); 3280 v.add(obj); 3281 } 3282 } 3284 3285 3291 private void addHashtableElements(Hashtable h) throws 3292 ClassNotFoundException , 3293 IOException { 3295 ParserXML.Tag tag; 3296 while (true) { 3297 Object [] objs = {null, null}; 3298 for (int i=0; i<objs.length; i++) { tag = p.readTag(); 3300 if (tag==null) throw new EOFException("Premature EOF"); 3301 if (!tag.start) 3302 if (i==0) return; else throw new IOException("incomplete Hashtable entry"); 3304 if (tag.name.equals("java.lang.String") || tag.name.equals("java.lang.Integer") 3306 || tag.name.equals("java.lang.Double") 3307 || tag.name.equals("java.lang.Boolean") 3308 || tag.name.equals("java.lang.Character") 3309 || tag.name.equals("java.lang.Byte") 3310 || tag.name.equals("java.lang.Short") 3311 || tag.name.equals("java.lang.Long") 3312 || tag.name.equals("java.lang.Float") 3313 ) 3314 objs[i] = deserializeWrapper(tag, null).object; 3315 else 3316 objs[i] = createObject(tag, null); } 3319 if (DEBUG) System.err.println("Putting {"+objs[0]+", "+objs[1]+"}"); 3320 h.put(objs[0], objs[1]); 3321 } 3322 } 3324 3325 3332 private NamedObject deserializeClass(ParserXML.Attr[] addAttrTmp, ParserXML.Tag startTag, Object cheatParent) throws 3333 ClassNotFoundException , 3334 IOException { 3336 ParserXML.Attr attr = addAttrTmp[0]; 3337 ParserXML.Attr end, name = null; 3338 ParserXML.Tag tag; 3339 if (DEBUG) System.err.println("deserializeClass: "+ attr); 3341 if (attr.name.equals(XMLSerialize.NAME_TOKEN)) { 3342 name = attr; 3344 attr = p.readAttr(); 3345 } 3346 if (!attr.name.equals(XMLSerialize.CLASSNAME_TOKEN)) 3347 throw new ParserXML.ExceptionXML(XMLSerialize.CLASSNAME_TOKEN+ " expected"); 3348 if (!(end = p.readAttr()).isEnd) 3349 throw new ParserXML.ExceptionXML("\">\" or \"/>\" expected"); 3350 if (!end.emptyTag) { 3351 tag = p.readTag(); 3352 if (!tag.name.equals(startTag.name) || tag.start) 3353 throw new ParserXML.ExceptionXML("</"+tag.name+"> expected"); 3354 } 3355 if (DEBUG) System.err.println("String read in: " + attr.value); 3357 3358 String className = ParseUtilities.descapeDollar(attr.value); 3359 Class clazz = null; 3360 try { 3361 clazz=Thread.currentThread().getContextClassLoader().loadClass(className); 3371 } catch (ClassNotFoundException e) { 3372 if (className.equals("int")) clazz = int.class; 3373 else if (className.equals("double")) clazz = double.class; 3374 else if (className.equals("boolean")) clazz = boolean.class; 3375 else if (className.equals("byte")) clazz = byte.class; 3376 else if (className.equals("char")) clazz = char.class; 3377 else if (className.equals("short")) clazz = short.class; 3378 else if (className.equals("long")) clazz = long.class; 3379 else if (className.equals("float")) clazz = float.class; 3380 else if (className.equals("void")) clazz = void.class; 3381 else 3382 throw new ClassNotFoundException ("class '"+className+"' not found"); 3383 } 3384 3385 putAlias(clazz); if (name!=null) { currentGetField.putObj(name.value, clazz); Field f = getAllField(cheatParent.getClass(), name.value); 3390 magic.setFinal(f, cheatParent, clazz); 3391 return new NamedObject(name.value, clazz, true); } 3397 return new NamedObject(null, clazz, false); } 3399 3400 3401 3408 private NamedObject deserializeBinary(ParserXML.Attr[] addAttrTmp, ParserXML.Tag startTag, Object cheatParent) throws 3409 ClassNotFoundException , 3410 IOException { 3412 ParserXML.Attr attr = addAttrTmp[0]; 3413 ParserXML.Attr end, name = null; 3414 ParserXML.Tag tag; 3415 if (DEBUG) System.err.println("deserializeBinary: "+ attr); 3417 if (attr.name.equals(XMLSerialize.NAME_TOKEN)) { 3418 name = attr; 3420 attr = p.readAttr(); 3421 } 3422 if (!attr.name.equals(XMLSerialize.VALUE_TOKEN)) 3423 throw new ParserXML.ExceptionXML(XMLSerialize.VALUE_TOKEN+ " expected"); 3424 if (!(end = p.readAttr()).isEnd) 3425 throw new ParserXML.ExceptionXML("\">\" or \"/>\" expected"); 3426 if (!end.emptyTag) { 3427 tag = p.readTag(); 3428 if (!tag.name.equals(startTag.name) || tag.start) 3429 throw new ParserXML.ExceptionXML("</"+tag.name+"> expected"); 3430 } 3431 if (DEBUG) System.err.println("Binary data read in: " + attr.value); 3433 3434 byte[] binaryData = ParseUtilities.decodeHex(attr.value); 3435 putAlias(binaryData); if (name!=null) { currentGetField.putObj(name.value, binaryData); Field f = getAllField(cheatParent.getClass(), name.value); 3440 magic.setFinal(f, cheatParent, binaryData); 3441 return new NamedObject(name.value, binaryData, true); } 3447 return new NamedObject(null, binaryData, false); } 3449 3450 3451 3458 private NamedObject deserializeWrapper(ParserXML.Tag startTag, Object cheatParent) throws 3459 ClassNotFoundException , 3460 IOException { 3462 return deserializeWrapper(addName(), startTag, cheatParent); 3463 } 3464 private NamedObject deserializeWrapper(ParserXML.Attr[] addAttrTmp, ParserXML.Tag startTag, Object cheatParent) throws 3465 ClassNotFoundException , 3466 IOException { 3468 ParserXML.Attr attr = addAttrTmp[0]; 3469 ParserXML.Attr end, name = null; 3470 ParserXML.Tag tag; 3471 if (DEBUG) System.err.println("deserializeWrapper: "+ attr); 3473 if (attr.name.equals(XMLSerialize.NAME_TOKEN)) { 3474 name = attr; 3476 attr = p.readAttr(); 3477 } 3478 if (!attr.name.equals(XMLSerialize.VALUE_TOKEN)) 3479 throw new ParserXML.ExceptionXML(XMLSerialize.VALUE_TOKEN+ " expected"); 3480 if (!(end = p.readAttr()).isEnd) 3481 throw new ParserXML.ExceptionXML("\">\" or \"/>\" expected"); 3482 if (!end.emptyTag) { 3483 tag = p.readTag(); 3484 if (!tag.name.equals(startTag.name) || tag.start) 3485 throw new ParserXML.ExceptionXML("</"+tag.name+"> expected"); 3486 } 3487 if (DEBUG) System.err.println("String read in: " + attr.value); 3489 if (startTag.name.equals("java.lang.String")) { 3490 String s = ParseUtilities.decodeXML((String )attr.value); putAlias(s); if (name!=null) { currentGetField.putObj(name.value, s); Field f = getAllField(cheatParent.getClass(), name.value); 3496 magic.setFinal(f, cheatParent, s); 3497 return new NamedObject(name.value, s, true); } 3502 return new NamedObject(null, s, false); } 3504 Class c = Class.forName(ParseUtilities.descapeDollar(startTag.name)); 3505 try { 3506 Field f = c.getDeclaredField("TYPE"); Object o = getValue((Class )f.get(c), attr); 3513 putAlias(o); return new NamedObject(null, o, false); } catch (NoSuchFieldException e) { 3516 System.err.println("'" +c+ "' is not a wrapper class: "+e); 3518 } catch (IllegalAccessException e) { 3519 System.err.println("'" +c+ "' is not a wrapper class: "+e); 3520 } 3521 throw new IOException("Shouldn't get here"); 3522 } 3523 3524 3525 3526 3531 public static class Test { 3532 public static void main(String args[]) throws Exception { 3533 3534 XMLDeserialize d = new XMLDeserialize(); XMLSerialize s = new XMLSerialize(); Object o; 3537 while ( (o = d.deserialize()) != null) { 3546 s.serialize(o); 3547 } 3548 } 3549 } 3550} 3551
| Popular Tags
|