1. /*
  2. * @(#)BufferManagerWriteCollect.java 1.12 03/01/23
  3. *
  4. * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. package com.sun.corba.se.internal.iiop;
  8. import java.util.Iterator;
  9. import java.util.NoSuchElementException;
  10. import java.util.LinkedList;
  11. import com.sun.corba.se.internal.orbutil.ORBConstants;
  12. import com.sun.corba.se.internal.iiop.messages.Message;
  13. import com.sun.corba.se.internal.iiop.messages.MessageBase;
  14. import com.sun.corba.se.internal.iiop.messages.FragmentMessage;
  15. /**
  16. * Initial implementation of the collect buffer manager.
  17. */
  18. public class BufferManagerWriteCollect extends BufferManagerWrite
  19. {
  20. private BufferQueue queue = new BufferQueue();
  21. private int initialFragmentSize;
  22. public BufferManagerWriteCollect(int initialFragmentSize) {
  23. this.stream = null;
  24. this.initialFragmentSize = initialFragmentSize;
  25. }
  26. public ByteBufferWithInfo getInitialBuffer (int size)
  27. {
  28. return new ByteBufferWithInfo(size);
  29. }
  30. public int getInitialBufferSize () {
  31. return initialFragmentSize;
  32. }
  33. // Set the fragment's "more fragments" bit to true, put it in the
  34. // queue, and allocate a new bbwi.
  35. public void overflow (ByteBufferWithInfo bbwi)
  36. {
  37. // Set the fragment's moreFragments field to true
  38. MessageBase.setFlag(bbwi.buf, Message.MORE_FRAGMENTS_BIT);
  39. // Enqueue the previous fragment
  40. queue.enqueue(bbwi);
  41. // Create a new bbwi
  42. ByteBufferWithInfo newBbwi = new ByteBufferWithInfo(getInitialBufferSize());
  43. newBbwi.fragmented = true;
  44. stream.setByteBufferWithInfo(newBbwi);
  45. // Now we must marshal in the fragment header/GIOP header
  46. // REVISIT - we can optimize this by not creating the fragment message
  47. // each time.
  48. FragmentMessage header = stream.getMessage().createFragmentMessage();
  49. header.write(stream);
  50. }
  51. // Send all fragments
  52. public void sendMessage ()
  53. {
  54. // Enqueue the last fragment
  55. queue.enqueue(stream.getByteBufferWithInfo());
  56. Iterator bufs = iterator();
  57. IIOPConnection conn = (IIOPConnection)stream.getConnection();
  58. // With the collect strategy, we must lock the connection
  59. // while fragments are being sent. This is so that there are
  60. // no interleved fragments in GIOP 1.1.
  61. //
  62. // Note that this thread must not call writeLock again in any
  63. // of its send methods!
  64. conn.writeLock();
  65. //conn.createOutCallDescriptor(stream.getMessage().getRequestId());
  66. conn.createOutCallDescriptor(MessageBase.getRequestId(stream.getMessage()));
  67. try {
  68. while (bufs.hasNext()) {
  69. stream.setByteBufferWithInfo((ByteBufferWithInfo)bufs.next());
  70. conn.sendWithoutLock(stream);
  71. }
  72. } finally {
  73. conn.writeUnlock();
  74. }
  75. }
  76. private Iterator iterator ()
  77. {
  78. return new BufferManagerWriteCollectIterator();
  79. }
  80. private class BufferManagerWriteCollectIterator implements Iterator
  81. {
  82. public boolean hasNext ()
  83. {
  84. return queue.size() != 0;
  85. }
  86. public Object next ()
  87. {
  88. return queue.dequeue();
  89. }
  90. public void remove ()
  91. {
  92. throw new UnsupportedOperationException();
  93. }
  94. }
  95. }