7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25 package jdk.jshell.execution;
26
27 import java.io.InputStream;
28
29 /**
30 *
31 * @author Jan Lahoda
32 */
33 class PipeInputStream extends InputStream {
34
35 private static final int INITIAL_SIZE = 128;
36 private int[] buffer = new int[INITIAL_SIZE];
37 private int start;
38 private int end;
39 private boolean closed;
40
41 @Override
42 public synchronized int read() {
43 while (start == end) {
44 if (closed) {
45 return -1;
46 }
47 try {
48 wait();
49 } catch (InterruptedException ex) {
50 //ignore
51 }
52 }
53 try {
54 return buffer[start];
55 } finally {
56 start = (start + 1) % buffer.length;
57 }
58 }
59
60 public synchronized void write(int b) {
61 if (closed) {
62 throw new IllegalStateException("Already closed.");
63 }
64 int newEnd = (end + 1) % buffer.length;
65 if (newEnd == start) {
66 //overflow:
67 int[] newBuffer = new int[buffer.length * 2];
68 int rightPart = (end > start ? end : buffer.length) - start;
69 int leftPart = end > start ? 0 : start - 1;
70 System.arraycopy(buffer, start, newBuffer, 0, rightPart);
71 System.arraycopy(buffer, 0, newBuffer, rightPart, leftPart);
72 buffer = newBuffer;
73 start = 0;
74 end = rightPart + leftPart;
75 newEnd = end + 1;
76 }
77 buffer[end] = b;
78 end = newEnd;
79 notifyAll();
80 }
81
82 @Override
83 public synchronized void close() {
84 closed = true;
85 notifyAll();
86 }
87
88 }
|
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25 package jdk.jshell.execution;
26
27 import java.io.IOException;
28 import java.io.InputStream;
29 import java.io.OutputStream;
30
31 /**
32 *
33 * @author Jan Lahoda
34 */
35 class PipeInputStream extends InputStream {
36
37 private static final int INITIAL_SIZE = 128;
38 private int[] buffer = new int[INITIAL_SIZE];
39 private int start;
40 private int end;
41 private boolean closed;
42
43 @Override
44 public synchronized int read() throws IOException {
45 if (start == end) {
46 inputNeeded();
47 }
48 while (start == end) {
49 if (closed) {
50 return -1;
51 }
52 try {
53 wait();
54 } catch (InterruptedException ex) {
55 //ignore
56 }
57 }
58 try {
59 return buffer[start];
60 } finally {
61 start = (start + 1) % buffer.length;
62 }
63 }
64
65 protected void inputNeeded() throws IOException {}
66
67 private synchronized void write(int b) {
68 if (closed) {
69 throw new IllegalStateException("Already closed.");
70 }
71 int newEnd = (end + 1) % buffer.length;
72 if (newEnd == start) {
73 //overflow:
74 int[] newBuffer = new int[buffer.length * 2];
75 int rightPart = (end > start ? end : buffer.length) - start;
76 int leftPart = end > start ? 0 : start - 1;
77 System.arraycopy(buffer, start, newBuffer, 0, rightPart);
78 System.arraycopy(buffer, 0, newBuffer, rightPart, leftPart);
79 buffer = newBuffer;
80 start = 0;
81 end = rightPart + leftPart;
82 newEnd = end + 1;
83 }
84 buffer[end] = b;
85 end = newEnd;
86 notifyAll();
87 }
88
89 @Override
90 public synchronized void close() {
91 closed = true;
92 notifyAll();
93 }
94
95 public OutputStream createOutput() {
96 return new OutputStream() {
97 @Override public void write(int b) throws IOException {
98 PipeInputStream.this.write(b);
99 }
100 @Override
101 public void write(byte[] b, int off, int len) throws IOException {
102 for (int i = 0 ; i < len ; i++) {
103 write(Byte.toUnsignedInt(b[off + i]));
104 }
105 }
106 @Override
107 public void close() throws IOException {
108 PipeInputStream.this.close();
109 }
110 };
111 }
112
113 }
|