📄 nestedcollection.java
字号:
// object, build message in StringBuffer using type of item // from stack, convert StringBuffer to String, invoke the // exeception constructor with the String, and finally throw // the exception mb.targetNext(link); mb.appendCreateNew("java.lang.StringBuffer"); mb.appendDUP(); mb.appendLoadConstant("Collection item of type "); mb.appendCallInit("java.lang.StringBuffer", "(Ljava/lang/String;)V"); mb.appendSWAP(); mb.appendDUP(); BranchWrapper ifnull = mb.appendIFNULL(this); mb.appendCallVirtual("java.lang.Object.getClass", "()Ljava/lang/Class;"); mb.appendCallVirtual("java.lang.Class.getName", "()Ljava/lang/String;"); BranchWrapper toend = mb.appendUnconditionalBranch(this); mb.targetNext(ifnull); mb.appendPOP(); mb.appendLoadConstant("NULL"); mb.targetNext(toend); mb.appendCallVirtual("java.lang.StringBuffer.append", "(Ljava/lang/String;)Ljava/lang/StringBuffer;"); mb.appendLoadConstant(" has no binding defined"); mb.appendCallVirtual("java.lang.StringBuffer.append", "(Ljava/lang/String;)Ljava/lang/StringBuffer;"); mb.appendCallVirtual("java.lang.StringBuffer.toString", "()Ljava/lang/String;"); mb.appendCreateNew(MethodBuilder.FRAMEWORK_EXCEPTION_CLASS); mb.appendDUP_X1(); mb.appendSWAP(); mb.appendCallInit(MethodBuilder.FRAMEWORK_EXCEPTION_CLASS, MethodBuilder.EXCEPTION_CONSTRUCTOR_SIGNATURE1); mb.appendThrow(); } // finish by setting target for collection empty case(s) m_loadStrategy.genLoadDone(mb); mb.targetNext(ifempties); } else { throw new IllegalStateException ("Internal error - no content present"); } } public boolean hasId() { return false; } public void genLoadId(ContextMethodBuilder mb) throws JiBXException { throw new IllegalStateException("No ID child"); } public NameDefinition getWrapperName() { return null; } public boolean isOptional() { return m_isOptional; } public void setLinkages() throws JiBXException { for (int i = 0; i < m_contents.size(); i++) { ((IComponent)m_contents.get(i)).setLinkages(); } } // DEBUG public void print(int depth) { BindingDefinition.indent(depth); System.out.print("collection " + (m_isOrdered ? "ordered" : "unordered")); if (m_itemType != null) { System.out.print(" (" + m_itemType + ")"); } if (isFlexible()) { System.out.print(", flexible"); } System.out.println(); for (int i = 0; i < m_contents.size(); i++) { IComponent comp = (IComponent)m_contents.get(i); comp.print(depth+1); } } /** * Base class for collection item load strategy. The implementation class * must handle the appropriate form of code generation for the type of * collection being used. */ /*package*/ static abstract class CollectionBase { /** Double word value flag. */ private final boolean m_isDoubleWord; /** * Constructor. * * @param doubword double word value flag */ protected CollectionBase(boolean doubword) { m_isDoubleWord = doubword; } /** * Append the appropriate instruction to swap the top of the stack * (which must be a single-word value) with an item value (which may * be one or two words, as configured for this collection). * * @param mb method */ protected void appendSWAP(MethodBuilder mb) { if (m_isDoubleWord) { mb.appendSWAP1For2(); } else { mb.appendSWAP(); } } /** * Append the appropriate instruction to pop the item value (which may * be one or two words, as configured for this collection) from the top * of the stack. * * @param mb method */ protected void appendPOP(MethodBuilder mb) { if (m_isDoubleWord) { mb.appendPOP2(); } else { mb.appendPOP(); } } } /** * Base class for collection item load strategy. The implementation class * must handle the appropriate form of code generation for the type of * collection being used. */ /*package*/ static abstract class CollectionLoad extends CollectionBase { /** * Constructor. * * @param add method used to add item to collection * @param doubword double word value flag * @param ret value returned by add flag */ protected CollectionLoad(boolean doubword) { super(doubword); } /** * Generate code to initialize collection for loading items. This * generates the necessary code for handling the initialization. It * must be called before attempting to call the {@link #genLoadItem} * method. The base class implementation does nothing. * * @param mb method builder * @throws JiBXException if error in configuration */ protected void genLoadInit(ContextMethodBuilder mb) throws JiBXException {} /** * Generate code to load next item from collection. This generates the * necessary code for handling the load operation, leaving the item on * the stack. The {@link #genLoadInit} method must be called before * calling this method, and the {@link #genLoadDone} method must be * called after the last call to this method. This method must be * overridden by each subclass. * * @param mb method builder * @return branch wrapper for case of done with collection * @throws JiBXException if error in configuration */ protected abstract BranchWrapper genLoadItem(ContextMethodBuilder mb) throws JiBXException; /** * Generate code to clean up after loading items from collection. This * generates the necessary code for handling the clean up. It must be * called after the last call to {@link #genLoadItem}. The base class * implementation does nothing. * * @param mb method builder * @throws JiBXException if error in configuration */ protected void genLoadDone(ContextMethodBuilder mb) throws JiBXException {} } /** * Base class for collection item store strategy. The implementation class * must handle the appropriate form of code generation for the type of * collection being used. */ /*package*/ static abstract class CollectionStore extends CollectionBase { /** * Constructor. * * @param doubword double word value flag */ protected CollectionStore(boolean doubword) { super(doubword); } /** * Generate code to initialize collection for storing items. This * generates the necessary code for handling the initialization, * including creating the collection object if appropriate. It must be * called before attempting to call the {@link #genStoreItem} method. * The base class implementation does nothing. * * @param mb method builder * @throws JiBXException if error in configuration */ protected void genStoreInit(ContextMethodBuilder mb) throws JiBXException {} /** * Generate code to store next item to collection. This generates the * necessary code for handling the store operation, removing the item * from the stack. The {@link #genStoreInit} method must be called * before calling this method, and the {@link #genStoreDone} method must * be called after the last call to this method. This method must be * overridden by each subclass. * * @param mb method builder * @throws JiBXException if error in configuration */ protected abstract void genStoreItem(ContextMethodBuilder mb) throws JiBXException; /** * Generate code to clean up after storing items to collection. This * generates the necessary code for handling the clean up. It must be * called after the last call to {@link #genStoreItem}. The base class * implementation does nothing. * * @param mb method builder * @throws JiBXException if error in configuration */ protected void genStoreDone(ContextMethodBuilder mb) throws JiBXException {} } /** * Collection item load strategy for collection with items accessed by * index number. */ /*package*/ static class IndexedLoad extends CollectionLoad { /** Method used to get count of items in collection. */ private final ClassItem m_sizeMethod; /** Method used to get items by index from collection. */ private final ClassItem m_getMethod; /** * Constructor. * * @param size method used to get count of items in collection * @param doubword double word value flag * @param get method used to retrieve items by index from collection */ /*package*/ IndexedLoad(ClassItem size, boolean doubword, ClassItem get) { super(doubword); m_sizeMethod = size; m_getMethod = get; } protected void genLoadInit(ContextMethodBuilder mb) throws JiBXException { // create index local with appended code to set initial value mb.appendLoadConstant(-1); mb.defineSlot(m_getMethod, Type.INT); // create size local with appended code to set initial value from // collection method call if (!m_sizeMethod.isStatic()) { mb.loadObject(); } mb.appendCall(m_sizeMethod); mb.defineSlot(m_sizeMethod, Type.INT); } protected BranchWrapper genLoadItem(ContextMethodBuilder mb) throws JiBXException { // start by getting local variable slots for the index and size int islot = mb.getSlot(m_getMethod); int sslot = mb.getSlot(m_sizeMethod); // append code to first increment index, then check for end of // collection reached mb.appendIncrementLocal(1, islot); mb.appendLoadLocal(islot); mb.appendLoadLocal(sslot); mb.appendISUB(); BranchWrapper ifempty = mb.appendIFGE(this); // finish by calling collection method to load item at current index // position
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -