src/share/jaxws_classes/com/sun/xml/internal/bind/v2/runtime/property/SingleMapNodeProperty.java

Print this page

        

*** 1,7 **** /* ! * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. Oracle designates this --- 1,7 ---- /* ! * Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. Oracle designates this
*** 138,163 **** * * The target will be set to a {@link Map}. */ private final Loader itemsLoader = new Loader(false) { ! private ThreadLocal<BeanT> target = new ThreadLocal<BeanT>(); ! private ThreadLocal<ValueT> map = new ThreadLocal<ValueT>(); ! private int depthCounter = 0; // needed to clean ThreadLocals @Override public void startElement(UnmarshallingContext.State state, TagName ea) throws SAXException { // create or obtain the Map object try { ! target.set((BeanT)state.prev.target); ! map.set(acc.get(target.get())); ! depthCounter++; ! if(map.get() == null) { ! map.set(ClassFactory.create(mapImplClass)); ! } ! map.get().clear(); ! state.target = map.get(); } catch (AccessorException e) { // recover from error by setting a dummy Map that receives and discards the values handleGenericException(e,true); state.target = new HashMap(); } --- 138,164 ---- * * The target will be set to a {@link Map}. */ private final Loader itemsLoader = new Loader(false) { ! private ThreadLocal<Stack<BeanT>> target = new ThreadLocal<Stack<BeanT>>(); ! private ThreadLocal<Stack<ValueT>> map = new ThreadLocal<Stack<ValueT>>(); @Override public void startElement(UnmarshallingContext.State state, TagName ea) throws SAXException { // create or obtain the Map object try { ! BeanT target = (BeanT) state.prev.target; ! ValueT mapValue = acc.get(target); ! if(mapValue == null) ! mapValue = ClassFactory.create(mapImplClass); ! else ! mapValue.clear(); ! ! Stack.push(this.target, target); ! Stack.push(map, mapValue); ! state.target = mapValue; } catch (AccessorException e) { // recover from error by setting a dummy Map that receives and discards the values handleGenericException(e,true); state.target = new HashMap(); }
*** 165,179 **** @Override public void leaveElement(State state, TagName ea) throws SAXException { super.leaveElement(state, ea); try { ! acc.set(target.get(), map.get()); ! if (--depthCounter == 0) { ! target.remove(); ! map.remove(); ! } } catch (AccessorException ex) { handleGenericException(ex,true); } } --- 166,176 ---- @Override public void leaveElement(State state, TagName ea) throws SAXException { super.leaveElement(state, ea); try { ! acc.set(Stack.pop(target), Stack.pop(map)); } catch (AccessorException ex) { handleGenericException(ex,true); } }
*** 287,292 **** --- 284,321 ---- public Accessor getElementPropertyAccessor(String nsUri, String localName) { if(tagName.equals(nsUri,localName)) return acc; return null; } + + private static final class Stack<T> { + private Stack<T> parent; + private T value; + + private Stack(Stack<T> parent, T value) { + this.parent = parent; + this.value = value; + } + + private Stack(T value) { + this.value = value; + } + + private static <T> void push(ThreadLocal<Stack<T>> holder, T value) { + Stack<T> parent = holder.get(); + if (parent == null) + holder.set(new Stack<T>(value)); + else + holder.set(new Stack<T>(parent, value)); + } + + private static <T> T pop(ThreadLocal<Stack<T>> holder) { + Stack<T> current = holder.get(); + if (current.parent == null) + holder.remove(); + else + holder.set(current.parent); + return current.value; + } + + } }