1. /*
  2. * @(#)IDLJavaSerializationInputStream.java 1.4 04/06/07
  3. *
  4. * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. package com.sun.corba.se.impl.encoding;
  8. import java.io.Serializable;
  9. import java.io.ObjectInputStream;
  10. import java.io.ByteArrayInputStream;
  11. import java.io.IOException;
  12. import java.nio.ByteBuffer;
  13. import java.math.BigDecimal;
  14. import java.util.LinkedList;
  15. import com.sun.corba.se.spi.orb.ORB;
  16. import com.sun.corba.se.spi.ior.IOR;
  17. import com.sun.corba.se.spi.ior.IORFactories;
  18. import com.sun.corba.se.spi.ior.iiop.GIOPVersion;
  19. import com.sun.corba.se.spi.logging.CORBALogDomains;
  20. import com.sun.corba.se.spi.presentation.rmi.StubAdapter;
  21. import com.sun.corba.se.spi.presentation.rmi.PresentationManager;
  22. import com.sun.corba.se.spi.presentation.rmi.PresentationDefaults;
  23. import com.sun.corba.se.impl.util.Utility;
  24. import com.sun.corba.se.impl.orbutil.ORBUtility;
  25. import com.sun.corba.se.impl.corba.TypeCodeImpl;
  26. import com.sun.corba.se.impl.util.RepositoryId;
  27. import com.sun.corba.se.impl.orbutil.ORBConstants;
  28. import com.sun.corba.se.impl.logging.ORBUtilSystemException;
  29. import com.sun.corba.se.impl.protocol.giopmsgheaders.Message;
  30. import org.omg.CORBA.Any;
  31. import org.omg.CORBA.TypeCode;
  32. import org.omg.CORBA.Principal;
  33. import org.omg.CORBA.portable.IDLEntity;
  34. /**
  35. * Implementation class that uses Java serialization for input streams.
  36. * This assumes a GIOP version 1.2 message format.
  37. *
  38. * This class uses a ByteArrayInputStream as the underlying buffer. The
  39. * first 16 bytes are directly read out of the underlying buffer. This allows
  40. * [GIOPHeader (12 bytes) + requestID (4 bytes)] to be read as bytes.
  41. * Subsequent write operations on this output stream object uses
  42. * ObjectInputStream class to read into the buffer. This allows unmarshaling
  43. * complex types and graphs using the ObjectInputStream implementation.
  44. *
  45. * Note, this class assumes a GIOP 1.2 style header. Further, the first
  46. * 12 bytes, that is, the GIOPHeader is read directly from the received
  47. * message, before this stream object is called. So, this class effectively
  48. * reads only the requestID (4 bytes) directly, and uses the
  49. * ObjectInputStream for further unmarshaling.
  50. *
  51. * @author Ram Jeyaraman
  52. */
  53. public class IDLJavaSerializationInputStream extends CDRInputStreamBase {
  54. private ORB orb;
  55. private int bufSize;
  56. private ByteBuffer buffer;
  57. private byte encodingVersion;
  58. private ObjectInputStream is;
  59. private _ByteArrayInputStream bis;
  60. private BufferManagerRead bufferManager;
  61. // [GIOPHeader(12) + requestID(4)] bytes
  62. private final int directReadLength = Message.GIOPMessageHeaderLength + 4;
  63. // Used for mark / reset operations.
  64. private boolean markOn;
  65. private int peekIndex, peekCount;
  66. private LinkedList markedItemQ = new LinkedList();
  67. protected ORBUtilSystemException wrapper;
  68. class _ByteArrayInputStream extends ByteArrayInputStream {
  69. _ByteArrayInputStream(byte[] buf) {
  70. super(buf);
  71. }
  72. int getPosition() {
  73. return this.pos;
  74. }
  75. void setPosition(int value) {
  76. if (value < 0 || value > count) {
  77. throw new IndexOutOfBoundsException();
  78. }
  79. this.pos = value;
  80. }
  81. }
  82. class MarshalObjectInputStream extends ObjectInputStream {
  83. ORB orb;
  84. MarshalObjectInputStream(java.io.InputStream out, ORB orb)
  85. throws IOException {
  86. super(out);
  87. this.orb = orb;
  88. java.security.AccessController.doPrivileged(
  89. new java.security.PrivilegedAction() {
  90. public Object run() {
  91. // needs SerializablePermission("enableSubstitution")
  92. enableResolveObject(true);
  93. return null;
  94. }
  95. }
  96. );
  97. }
  98. /**
  99. * Connect the Stub to the ORB.
  100. */
  101. protected final Object resolveObject(Object obj) throws IOException {
  102. try {
  103. if (StubAdapter.isStub(obj)) {
  104. StubAdapter.connect(obj, orb);
  105. }
  106. } catch (java.rmi.RemoteException re) {
  107. IOException ie = new IOException("resolveObject failed");
  108. ie.initCause(re);
  109. throw ie;
  110. }
  111. return obj;
  112. }
  113. }
  114. public IDLJavaSerializationInputStream(byte encodingVersion) {
  115. super();
  116. this.encodingVersion = encodingVersion;
  117. }
  118. public void init(org.omg.CORBA.ORB orb,
  119. ByteBuffer byteBuffer,
  120. int bufSize,
  121. boolean littleEndian,
  122. BufferManagerRead bufferManager) {
  123. this.orb = (ORB) orb;
  124. this.bufSize = bufSize;
  125. this.bufferManager = bufferManager;
  126. buffer = byteBuffer;
  127. wrapper =
  128. ORBUtilSystemException.get((ORB)orb, CORBALogDomains.RPC_ENCODING);
  129. byte[] buf;
  130. if (buffer.hasArray()) {
  131. buf = buffer.array();
  132. } else {
  133. buf = new byte[bufSize];
  134. buffer.get(buf);
  135. }
  136. // Note: at this point, the buffer position is zero. The setIndex()
  137. // method call can be used to set a desired read index.
  138. bis = new _ByteArrayInputStream(buf);
  139. }
  140. // Called from read_octet or read_long or read_ulong method.
  141. private void initObjectInputStream() {
  142. //System.out.print(" is ");
  143. if (is != null) {
  144. throw wrapper.javaStreamInitFailed();
  145. }
  146. try {
  147. is = new MarshalObjectInputStream(bis, orb);
  148. } catch (Exception e) {
  149. throw wrapper.javaStreamInitFailed(e);
  150. }
  151. }
  152. // org.omg.CORBA.portable.InputStream
  153. // Primitive types.
  154. public boolean read_boolean() {
  155. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  156. return ((Boolean)markedItemQ.removeFirst()).booleanValue();
  157. }
  158. if (markOn && !(markedItemQ.isEmpty()) &&
  159. (peekIndex < peekCount)) { // peek
  160. return ((Boolean)markedItemQ.get(peekIndex++)).booleanValue();
  161. }
  162. try {
  163. boolean value = is.readBoolean();
  164. if (markOn) { // enqueue
  165. markedItemQ.addLast(Boolean.valueOf(value));
  166. }
  167. return value;
  168. } catch (Exception e) {
  169. throw wrapper.javaSerializationException(e, "read_boolean");
  170. }
  171. }
  172. public char read_char() {
  173. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  174. return ((Character)markedItemQ.removeFirst()).charValue();
  175. }
  176. if (markOn && !(markedItemQ.isEmpty()) &&
  177. (peekIndex < peekCount)) { // peek
  178. return ((Character)markedItemQ.get(peekIndex++)).charValue();
  179. }
  180. try {
  181. char value = is.readChar();
  182. if (markOn) { // enqueue
  183. markedItemQ.addLast(new Character(value));
  184. }
  185. return value;
  186. } catch (Exception e) {
  187. throw wrapper.javaSerializationException(e, "read_char");
  188. }
  189. }
  190. public char read_wchar() {
  191. return this.read_char();
  192. }
  193. public byte read_octet() {
  194. // check if size < [ GIOPHeader(12) + requestID(4)] bytes
  195. if (bis.getPosition() < directReadLength) {
  196. byte b = (byte) bis.read();
  197. if (bis.getPosition() == directReadLength) {
  198. initObjectInputStream();
  199. }
  200. return b;
  201. }
  202. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  203. return ((Byte)markedItemQ.removeFirst()).byteValue();
  204. }
  205. if (markOn && !(markedItemQ.isEmpty()) &&
  206. (peekIndex < peekCount)) { // peek
  207. return ((Byte)markedItemQ.get(peekIndex++)).byteValue();
  208. }
  209. try {
  210. byte value = is.readByte();
  211. if (markOn) { // enqueue
  212. //markedItemQ.addLast(Byte.valueOf(value)); // only in JDK 1.5
  213. markedItemQ.addLast(new Byte(value));
  214. }
  215. return value;
  216. } catch (Exception e) {
  217. throw wrapper.javaSerializationException(e, "read_octet");
  218. }
  219. }
  220. public short read_short() {
  221. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  222. return ((Short)markedItemQ.removeFirst()).shortValue();
  223. }
  224. if (markOn && !(markedItemQ.isEmpty()) &&
  225. (peekIndex < peekCount)) { // peek
  226. return ((Short)markedItemQ.get(peekIndex++)).shortValue();
  227. }
  228. try {
  229. short value = is.readShort();
  230. if (markOn) { // enqueue
  231. markedItemQ.addLast(new Short(value));
  232. }
  233. return value;
  234. } catch (Exception e) {
  235. throw wrapper.javaSerializationException(e, "read_short");
  236. }
  237. }
  238. public short read_ushort() {
  239. return this.read_short();
  240. }
  241. public int read_long() {
  242. // check if size < [ GIOPHeader(12) + requestID(4)] bytes
  243. if (bis.getPosition() < directReadLength) {
  244. // Use big endian (network byte order). This is fixed.
  245. // Both the writer and reader use the same byte order.
  246. int b1 = (bis.read() << 24) & 0xFF000000;
  247. int b2 = (bis.read() << 16) & 0x00FF0000;
  248. int b3 = (bis.read() << 8) & 0x0000FF00;
  249. int b4 = (bis.read() << 0) & 0x000000FF;
  250. if (bis.getPosition() == directReadLength) {
  251. initObjectInputStream();
  252. } else if (bis.getPosition() > directReadLength) {
  253. // Cannot happen. All direct reads are contained
  254. // within the first 16 bytes.
  255. wrapper.javaSerializationException("read_long");
  256. }
  257. return (b1 | b2 | b3 | b4);
  258. }
  259. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  260. return ((Integer)markedItemQ.removeFirst()).intValue();
  261. }
  262. if (markOn && !(markedItemQ.isEmpty()) &&
  263. (peekIndex < peekCount)) { // peek
  264. return ((Integer)markedItemQ.get(peekIndex++)).intValue();
  265. }
  266. try {
  267. int value = is.readInt();
  268. if (markOn) { // enqueue
  269. markedItemQ.addLast(new Integer(value));
  270. }
  271. return value;
  272. } catch (Exception e) {
  273. throw wrapper.javaSerializationException(e, "read_long");
  274. }
  275. }
  276. public int read_ulong() {
  277. return this.read_long();
  278. }
  279. public long read_longlong() {
  280. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  281. return ((Long)markedItemQ.removeFirst()).longValue();
  282. }
  283. if (markOn && !(markedItemQ.isEmpty()) &&
  284. (peekIndex < peekCount)) { // peek
  285. return ((Long)markedItemQ.get(peekIndex++)).longValue();
  286. }
  287. try {
  288. long value = is.readLong();
  289. if (markOn) { // enqueue
  290. markedItemQ.addLast(new Long(value));
  291. }
  292. return value;
  293. } catch (Exception e) {
  294. throw wrapper.javaSerializationException(e, "read_longlong");
  295. }
  296. }
  297. public long read_ulonglong() {
  298. return read_longlong();
  299. }
  300. public float read_float() {
  301. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  302. return ((Float)markedItemQ.removeFirst()).floatValue();
  303. }
  304. if (markOn && !(markedItemQ.isEmpty()) &&
  305. (peekIndex < peekCount)) { // peek
  306. return ((Float)markedItemQ.get(peekIndex++)).floatValue();
  307. }
  308. try {
  309. float value = is.readFloat();
  310. if (markOn) { // enqueue
  311. markedItemQ.addLast(new Float(value));
  312. }
  313. return value;
  314. } catch (Exception e) {
  315. throw wrapper.javaSerializationException(e, "read_float");
  316. }
  317. }
  318. public double read_double() {
  319. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  320. return ((Double)markedItemQ.removeFirst()).doubleValue();
  321. }
  322. if (markOn && !(markedItemQ.isEmpty()) &&
  323. (peekIndex < peekCount)) { // peek
  324. return ((Double)markedItemQ.get(peekIndex++)).doubleValue();
  325. }
  326. try {
  327. double value = is.readDouble();
  328. if (markOn) { // enqueue
  329. markedItemQ.addLast(new Double(value));
  330. }
  331. return value;
  332. } catch (Exception e) {
  333. throw wrapper.javaSerializationException(e, "read_double");
  334. }
  335. }
  336. // String types.
  337. public String read_string() {
  338. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  339. return (String) markedItemQ.removeFirst();
  340. }
  341. if (markOn && !(markedItemQ.isEmpty()) &&
  342. (peekIndex < peekCount)) { // peek
  343. return (String) markedItemQ.get(peekIndex++);
  344. }
  345. try {
  346. String value = is.readUTF();
  347. if (markOn) { // enqueue
  348. markedItemQ.addLast(value);
  349. }
  350. return value;
  351. } catch (Exception e) {
  352. throw wrapper.javaSerializationException(e, "read_string");
  353. }
  354. }
  355. public String read_wstring() {
  356. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  357. return (String) markedItemQ.removeFirst();
  358. }
  359. if (markOn && !(markedItemQ.isEmpty()) &&
  360. (peekIndex < peekCount)) { // peek
  361. return (String) markedItemQ.get(peekIndex++);
  362. }
  363. try {
  364. String value = (String) is.readObject();
  365. if (markOn) { // enqueue
  366. markedItemQ.addLast(value);
  367. }
  368. return value;
  369. } catch (Exception e) {
  370. throw wrapper.javaSerializationException(e, "read_wstring");
  371. }
  372. }
  373. // Array types.
  374. public void read_boolean_array(boolean[] value, int offset, int length){
  375. for(int i = 0; i < length; i++) {
  376. value[i+offset] = read_boolean();
  377. }
  378. }
  379. public void read_char_array(char[] value, int offset, int length) {
  380. for(int i=0; i < length; i++) {
  381. value[i+offset] = read_char();
  382. }
  383. }
  384. public void read_wchar_array(char[] value, int offset, int length) {
  385. read_char_array(value, offset, length);
  386. }
  387. public void read_octet_array(byte[] value, int offset, int length) {
  388. for(int i=0; i < length; i++) {
  389. value[i+offset] = read_octet();
  390. }
  391. /* // Cannot use this efficient read due to mark/reset support.
  392. try {
  393. while (length > 0) {
  394. int n = is.read(value, offset, length);
  395. offset += n;
  396. length -= n;
  397. }
  398. } catch (Exception e) {
  399. throw wrapper.javaSerializationException(e, "read_octet_array");
  400. }
  401. */
  402. }
  403. public void read_short_array(short[] value, int offset, int length) {
  404. for(int i=0; i < length; i++) {
  405. value[i+offset] = read_short();
  406. }
  407. }
  408. public void read_ushort_array(short[] value, int offset, int length) {
  409. read_short_array(value, offset, length);
  410. }
  411. public void read_long_array(int[] value, int offset, int length) {
  412. for(int i=0; i < length; i++) {
  413. value[i+offset] = read_long();
  414. }
  415. }
  416. public void read_ulong_array(int[] value, int offset, int length) {
  417. read_long_array(value, offset, length);
  418. }
  419. public void read_longlong_array(long[] value, int offset, int length) {
  420. for(int i=0; i < length; i++) {
  421. value[i+offset] = read_longlong();
  422. }
  423. }
  424. public void read_ulonglong_array(long[] value, int offset, int length) {
  425. read_longlong_array(value, offset, length);
  426. }
  427. public void read_float_array(float[] value, int offset, int length) {
  428. for(int i=0; i < length; i++) {
  429. value[i+offset] = read_float();
  430. }
  431. }
  432. public void read_double_array(double[] value, int offset, int length) {
  433. for(int i=0; i < length; i++) {
  434. value[i+offset] = read_double();
  435. }
  436. }
  437. // Complex types.
  438. public org.omg.CORBA.Object read_Object() {
  439. return read_Object(null);
  440. }
  441. public TypeCode read_TypeCode() {
  442. TypeCodeImpl tc = new TypeCodeImpl(orb);
  443. tc.read_value(parent);
  444. return tc;
  445. }
  446. public Any read_any() {
  447. Any any = orb.create_any();
  448. TypeCodeImpl tc = new TypeCodeImpl(orb);
  449. // read off the typecode
  450. // REVISIT We could avoid this try-catch if we could peek the typecode
  451. // kind off this stream and see if it is a tk_value.
  452. // Looking at the code we know that for tk_value the Any.read_value()
  453. // below ignores the tc argument anyway (except for the kind field).
  454. // But still we would need to make sure that the whole typecode,
  455. // including encapsulations, is read off.
  456. try {
  457. tc.read_value(parent);
  458. } catch (org.omg.CORBA.MARSHAL ex) {
  459. if (tc.kind().value() != org.omg.CORBA.TCKind._tk_value) {
  460. throw ex;
  461. }
  462. // We can be sure that the whole typecode encapsulation has been
  463. // read off.
  464. ex.printStackTrace();
  465. }
  466. // read off the value of the any.
  467. any.read_value(parent, tc);
  468. return any;
  469. }
  470. public Principal read_Principal() {
  471. // We don't need an implementation for this method, since principal
  472. // is absent in GIOP version 1.2 or above.
  473. int len = read_long();
  474. byte[] pvalue = new byte[len];
  475. read_octet_array(pvalue,0,len);
  476. Principal p = new com.sun.corba.se.impl.corba.PrincipalImpl();
  477. p.name(pvalue);
  478. return p;
  479. }
  480. public BigDecimal read_fixed() {
  481. return new BigDecimal(read_fixed_buffer().toString());
  482. }
  483. // Each octet contains (up to) two decimal digits. If the fixed type has
  484. // an odd number of decimal digits, then the representation
  485. // begins with the first (most significant) digit.
  486. // Otherwise, this first half-octet is all zero, and the first digit
  487. // is in the second half-octet.
  488. // The sign configuration, in the last half-octet of the representation,
  489. // is 0xD for negative numbers and 0xC for positive and zero values.
  490. private StringBuffer read_fixed_buffer() {
  491. StringBuffer buffer = new StringBuffer(64);
  492. byte doubleDigit;
  493. int firstDigit;
  494. int secondDigit;
  495. boolean wroteFirstDigit = false;
  496. boolean more = true;
  497. while (more) {
  498. doubleDigit = read_octet();
  499. firstDigit = (int)((doubleDigit & 0xf0) >> 4);
  500. secondDigit = (int)(doubleDigit & 0x0f);
  501. if (wroteFirstDigit || firstDigit != 0) {
  502. buffer.append(Character.forDigit(firstDigit, 10));
  503. wroteFirstDigit = true;
  504. }
  505. if (secondDigit == 12) {
  506. // positive number or zero
  507. if ( ! wroteFirstDigit) {
  508. // zero
  509. return new StringBuffer("0.0");
  510. } else {
  511. // positive number
  512. // done
  513. }
  514. more = false;
  515. } else if (secondDigit == 13) {
  516. // negative number
  517. buffer.insert(0, '-');
  518. more = false;
  519. } else {
  520. buffer.append(Character.forDigit(secondDigit, 10));
  521. wroteFirstDigit = true;
  522. }
  523. }
  524. return buffer;
  525. }
  526. public org.omg.CORBA.Object read_Object(java.lang.Class clz) {
  527. // In any case, we must first read the IOR.
  528. IOR ior = IORFactories.makeIOR(parent) ;
  529. if (ior.isNil()) {
  530. return null;
  531. }
  532. PresentationManager.StubFactoryFactory sff =
  533. ORB.getStubFactoryFactory();
  534. String codeBase = ior.getProfile().getCodebase();
  535. PresentationManager.StubFactory stubFactory = null;
  536. if (clz == null) {
  537. RepositoryId rid = RepositoryId.cache.getId(ior.getTypeId() );
  538. String className = rid.getClassName();
  539. boolean isIDLInterface = rid.isIDLType();
  540. if (className == null || className.equals( "" )) {
  541. stubFactory = null;
  542. } else {
  543. try {
  544. stubFactory = sff.createStubFactory(className,
  545. isIDLInterface, codeBase, (Class) null,
  546. (ClassLoader) null);
  547. } catch (Exception exc) {
  548. // Could not create stubFactory, so use null.
  549. // XXX stubFactory handling is still too complex:
  550. // Can we resolve the stubFactory question once in
  551. // a single place?
  552. stubFactory = null ;
  553. }
  554. }
  555. } else if (StubAdapter.isStubClass(clz)) {
  556. stubFactory = PresentationDefaults.makeStaticStubFactory(clz);
  557. } else {
  558. // clz is an interface class
  559. boolean isIDL = IDLEntity.class.isAssignableFrom(clz);
  560. stubFactory = sff.createStubFactory(
  561. clz.getName(), isIDL, codeBase, clz, clz.getClassLoader());
  562. }
  563. return CDRInputStream_1_0.internalIORToObject(ior, stubFactory, orb);
  564. }
  565. public org.omg.CORBA.ORB orb() {
  566. return this.orb;
  567. }
  568. // org.omg.CORBA_2_3.portable.InputStream
  569. public java.io.Serializable read_value() {
  570. if (!markOn && !(markedItemQ.isEmpty())) { // dequeue
  571. return (Serializable) markedItemQ.removeFirst();
  572. }
  573. if (markOn && !(markedItemQ.isEmpty()) &&
  574. (peekIndex < peekCount)) { // peek
  575. return (Serializable) markedItemQ.get(peekIndex++);
  576. }
  577. try {
  578. Serializable value = (java.io.Serializable) is.readObject();
  579. if (markOn) { // enqueue
  580. markedItemQ.addLast(value);
  581. }
  582. return value;
  583. } catch (Exception e) {
  584. throw wrapper.javaSerializationException(e, "read_value");
  585. }
  586. }
  587. public java.io.Serializable read_value(java.lang.Class clz) {
  588. return read_value();
  589. }
  590. public java.io.Serializable read_value(
  591. org.omg.CORBA.portable.BoxedValueHelper factory) {
  592. return read_value();
  593. }
  594. public java.io.Serializable read_value(java.lang.String rep_id) {
  595. return read_value();
  596. }
  597. public java.io.Serializable read_value(java.io.Serializable value) {
  598. return read_value();
  599. }
  600. public java.lang.Object read_abstract_interface() {
  601. return read_abstract_interface(null);
  602. }
  603. public java.lang.Object read_abstract_interface(java.lang.Class clz) {
  604. boolean isObject = read_boolean();
  605. if (isObject) {
  606. return read_Object(clz);
  607. } else {
  608. return read_value();
  609. }
  610. }
  611. // com.sun.corba.se.impl.encoding.MarshalInputStream
  612. public void consumeEndian() {
  613. throw wrapper.giopVersionError();
  614. }
  615. public int getPosition() {
  616. try {
  617. return bis.getPosition();
  618. } catch (Exception e) {
  619. throw wrapper.javaSerializationException(e, "getPosition");
  620. }
  621. }
  622. // org.omg.CORBA.DataInputStream
  623. public java.lang.Object read_Abstract() {
  624. return read_abstract_interface();
  625. }
  626. public java.io.Serializable read_Value() {
  627. return read_value();
  628. }
  629. public void read_any_array (org.omg.CORBA.AnySeqHolder seq,
  630. int offset, int length) {
  631. read_any_array(seq.value, offset, length);
  632. }
  633. private final void read_any_array(org.omg.CORBA.Any[] value,
  634. int offset, int length) {
  635. for(int i=0; i < length; i++) {
  636. value[i+offset] = read_any();
  637. }
  638. }
  639. public void read_boolean_array (org.omg.CORBA.BooleanSeqHolder seq,
  640. int offset, int length){
  641. read_boolean_array(seq.value, offset, length);
  642. }
  643. public void read_char_array (org.omg.CORBA.CharSeqHolder seq,
  644. int offset, int length){
  645. read_char_array(seq.value, offset, length);
  646. }
  647. public void read_wchar_array (org.omg.CORBA.WCharSeqHolder seq,
  648. int offset, int length){
  649. read_wchar_array(seq.value, offset, length);
  650. }
  651. public void read_octet_array (org.omg.CORBA.OctetSeqHolder seq,
  652. int offset, int length){
  653. read_octet_array(seq.value, offset, length);
  654. }
  655. public void read_short_array (org.omg.CORBA.ShortSeqHolder seq,
  656. int offset, int length){
  657. read_short_array(seq.value, offset, length);
  658. }
  659. public void read_ushort_array (org.omg.CORBA.UShortSeqHolder seq,
  660. int offset, int length){
  661. read_ushort_array(seq.value, offset, length);
  662. }
  663. public void read_long_array (org.omg.CORBA.LongSeqHolder seq,
  664. int offset, int length){
  665. read_long_array(seq.value, offset, length);
  666. }
  667. public void read_ulong_array (org.omg.CORBA.ULongSeqHolder seq,
  668. int offset, int length){
  669. read_ulong_array(seq.value, offset, length);
  670. }
  671. public void read_ulonglong_array (org.omg.CORBA.ULongLongSeqHolder seq,
  672. int offset, int length){
  673. read_ulonglong_array(seq.value, offset, length);
  674. }
  675. public void read_longlong_array (org.omg.CORBA.LongLongSeqHolder seq,
  676. int offset, int length){
  677. read_longlong_array(seq.value, offset, length);
  678. }
  679. public void read_float_array (org.omg.CORBA.FloatSeqHolder seq,
  680. int offset, int length){
  681. read_float_array(seq.value, offset, length);
  682. }
  683. public void read_double_array (org.omg.CORBA.DoubleSeqHolder seq,
  684. int offset, int length){
  685. read_double_array(seq.value, offset, length);
  686. }
  687. // org.omg.CORBA.portable.ValueBase
  688. public String[] _truncatable_ids() {
  689. throw wrapper.giopVersionError();
  690. }
  691. // java.io.InputStream
  692. // REVISIT - should we make these throw UnsupportedOperationExceptions?
  693. // Right now, they'll go up to the java.io versions!
  694. // public int read(byte b[]) throws IOException;
  695. // public int read(byte b[], int off, int len) throws IOException
  696. // public long skip(long n) throws IOException;
  697. // public int available() throws IOException;
  698. // public void close() throws IOException;
  699. public void mark(int readLimit) {
  700. // Nested mark disallowed.
  701. // Further, mark is not supported until first 16 bytes are read.
  702. if (markOn || is == null) {
  703. throw wrapper.javaSerializationException("mark");
  704. }
  705. markOn = true;
  706. if (!(markedItemQ.isEmpty())) {
  707. peekIndex = 0;
  708. peekCount = markedItemQ.size();
  709. }
  710. /*
  711. // Note: only ByteArrayInputStream supports mark/reset.
  712. if (is == null || is.markSupported() == false) {
  713. throw wrapper.javaSerializationException("mark");
  714. }
  715. is.mark(readLimit);
  716. */
  717. }
  718. public void reset() {
  719. markOn = false;
  720. peekIndex = 0;
  721. peekCount = 0;
  722. /*
  723. // Note: only ByteArrayInputStream supports mark/reset.
  724. if (is == null || is.markSupported() == false) {
  725. throw wrapper.javaSerializationException("mark");
  726. }
  727. try {
  728. is.reset();
  729. } catch (Exception e) {
  730. throw wrapper.javaSerializationException(e, "reset");
  731. }
  732. */
  733. }
  734. // This should return false so that outside users (people using the JDK)
  735. // don't have any guarantees that mark/reset will work in their
  736. // custom marshaling code. This is necessary since they could do things
  737. // like expect obj1a == obj1b in the following code:
  738. //
  739. // is.mark(10000);
  740. // Object obj1a = is.readObject();
  741. // is.reset();
  742. // Object obj1b = is.readObject();
  743. //
  744. public boolean markSupported() {
  745. return true;
  746. }
  747. // Needed by AnyImpl and ServiceContexts
  748. public CDRInputStreamBase dup() {
  749. CDRInputStreamBase result = null ;
  750. try {
  751. result = (CDRInputStreamBase) this.getClass().newInstance();
  752. } catch (Exception e) {
  753. throw wrapper.couldNotDuplicateCdrInputStream(e);
  754. }
  755. result.init(this.orb, this.buffer, this.bufSize, false, null);
  756. // Set the buffer position.
  757. ((IDLJavaSerializationInputStream)result).skipBytes(getPosition());
  758. // Set mark related data.
  759. ((IDLJavaSerializationInputStream)result).
  760. setMarkData(markOn, peekIndex, peekCount,
  761. (LinkedList) markedItemQ.clone());
  762. return result;
  763. }
  764. // Used exclusively by the dup() method.
  765. void skipBytes(int len) {
  766. try {
  767. is.skipBytes(len);
  768. } catch (Exception e) {
  769. throw wrapper.javaSerializationException(e, "skipBytes");
  770. }
  771. }
  772. // Used exclusively by the dup() method.
  773. void setMarkData(boolean markOn, int peekIndex, int peekCount,
  774. LinkedList markedItemQ) {
  775. this.markOn = markOn;
  776. this.peekIndex = peekIndex;
  777. this.peekCount = peekCount;
  778. this.markedItemQ = markedItemQ;
  779. }
  780. // Needed by TCUtility
  781. public java.math.BigDecimal read_fixed(short digits, short scale) {
  782. // digits isn't really needed here
  783. StringBuffer buffer = read_fixed_buffer();
  784. if (digits != buffer.length())
  785. throw wrapper.badFixed( new Integer(digits),
  786. new Integer(buffer.length()) ) ;
  787. buffer.insert(digits - scale, '.');
  788. return new BigDecimal(buffer.toString());
  789. }
  790. // Needed by TypeCodeImpl
  791. public boolean isLittleEndian() {
  792. throw wrapper.giopVersionError();
  793. }
  794. // Needed by request and reply messages for GIOP versions >= 1.2 only.
  795. void setHeaderPadding(boolean headerPadding) {
  796. // no-op. We don't care about body alignment while using
  797. // Java serialization. What the GIOP spec states does not apply here.
  798. }
  799. // Needed by IIOPInputStream and other subclasses
  800. public ByteBuffer getByteBuffer() {
  801. throw wrapper.giopVersionError();
  802. }
  803. public void setByteBuffer(ByteBuffer byteBuffer) {
  804. throw wrapper.giopVersionError();
  805. }
  806. public void setByteBufferWithInfo(ByteBufferWithInfo bbwi) {
  807. throw wrapper.giopVersionError();
  808. }
  809. public int getBufferLength() {
  810. return bufSize;
  811. }
  812. public void setBufferLength(int value) {
  813. // this is redundant, since buffer size was already specified
  814. // as part of the init call. So, ignore.
  815. }
  816. public int getIndex() {
  817. return bis.getPosition();
  818. }
  819. public void setIndex(int value) {
  820. try {
  821. bis.setPosition(value);
  822. } catch (IndexOutOfBoundsException e) {
  823. throw wrapper.javaSerializationException(e, "setIndex");
  824. }
  825. }
  826. public void orb(org.omg.CORBA.ORB orb) {
  827. this.orb = (ORB) orb;
  828. }
  829. public BufferManagerRead getBufferManager() {
  830. return bufferManager;
  831. }
  832. public GIOPVersion getGIOPVersion() {
  833. return GIOPVersion.V1_2;
  834. }
  835. com.sun.org.omg.SendingContext.CodeBase getCodeBase() {
  836. return parent.getCodeBase();
  837. }
  838. void printBuffer() {
  839. byte[] buf = this.buffer.array();
  840. System.out.println("+++++++ Input Buffer ++++++++");
  841. System.out.println();
  842. System.out.println("Current position: " + getPosition());
  843. System.out.println("Total length : " + this.bufSize);
  844. System.out.println();
  845. char[] charBuf = new char[16];
  846. try {
  847. for (int i = 0; i < buf.length; i += 16) {
  848. int j = 0;
  849. // For every 16 bytes, there is one line
  850. // of output. First, the hex output of
  851. // the 16 bytes with each byte separated
  852. // by a space.
  853. while (j < 16 && j + i < buf.length) {
  854. int k = buf[i + j];
  855. if (k < 0)
  856. k = 256 + k;
  857. String hex = Integer.toHexString(k);
  858. if (hex.length() == 1)
  859. hex = "0" + hex;
  860. System.out.print(hex + " ");
  861. j++;
  862. }
  863. // Add any extra spaces to align the
  864. // text column in case we didn't end
  865. // at 16
  866. while (j < 16) {
  867. System.out.print(" ");
  868. j++;
  869. }
  870. // Now output the ASCII equivalents. Non-ASCII
  871. // characters are shown as periods.
  872. int x = 0;
  873. while (x < 16 && x + i < buf.length) {
  874. if (ORBUtility.isPrintable((char)buf[i + x])) {
  875. charBuf[x] = (char) buf[i + x];
  876. } else {
  877. charBuf[x] = '.';
  878. }
  879. x++;
  880. }
  881. System.out.println(new String(charBuf, 0, x));
  882. }
  883. } catch (Throwable t) {
  884. t.printStackTrace();
  885. }
  886. System.out.println("++++++++++++++++++++++++++++++");
  887. }
  888. void alignOnBoundary(int octetBoundary) {
  889. throw wrapper.giopVersionError();
  890. }
  891. void performORBVersionSpecificInit() {
  892. // No-op.
  893. }
  894. public void resetCodeSetConverters() {
  895. // No-op.
  896. }
  897. // ValueInputStream -------------------------
  898. public void start_value() {
  899. throw wrapper.giopVersionError();
  900. }
  901. public void end_value() {
  902. throw wrapper.giopVersionError();
  903. }
  904. }