2026-03-17 13:31:18 -07:00

354 lines
11 KiB
Java

/*
* Decompiled with CFR 0.152.
*/
package com.tridium.fox.session;
import com.tridium.fox.message.FoxMessage;
import com.tridium.fox.message.MessageReader;
import com.tridium.fox.message.MessageWriter;
import com.tridium.fox.session.Fox;
import com.tridium.fox.session.FoxAsyncCallbacks;
import com.tridium.fox.session.FoxRequest;
import com.tridium.fox.session.FoxSession;
import java.io.IOException;
import java.io.InputStream;
import java.io.InterruptedIOException;
import java.io.OutputStream;
public class FoxCircuit {
private static final boolean TRACE = false;
public final int id;
public final String channel;
public final String command;
boolean open = true;
FoxSession session;
CircuitOutputStream out;
CircuitInputStream in;
Object outgoingLock = new Object();
byte[] outgoing = new byte[Fox.circuitChunkSize];
int nOutgoing;
Object incomingLock = new Object();
BufferEntry incomingHead = null;
BufferEntry incomingTail = null;
int nIncoming;
FoxCircuit(int n, FoxSession foxSession, String string, String string2) {
this.id = n;
this.session = foxSession;
this.channel = string;
this.command = string2;
this.out = new CircuitOutputStream();
this.in = new CircuitInputStream();
}
public boolean isOpen() {
return this.open;
}
public FoxSession session() {
return this.session;
}
public InputStream getInputStream() {
return this.in;
}
public OutputStream getOutputStream() {
return this.out;
}
public FoxMessage readMessage() throws Exception {
MessageReader messageReader = new MessageReader(this.in);
FoxMessage foxMessage = new FoxMessage();
foxMessage.readValue(messageReader);
return foxMessage;
}
public void writeMessage(FoxMessage foxMessage) throws Exception {
MessageWriter messageWriter = new MessageWriter(this.out);
foxMessage.writeValue(messageWriter);
messageWriter.flush();
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
public FoxMessage write(byte[] byArray, int n, int n2, FoxAsyncCallbacks foxAsyncCallbacks) throws Exception {
if (foxAsyncCallbacks == null) {
this.out.write(byArray, n, n2);
return null;
}
Object object = this.outgoingLock;
synchronized (object) {
int n3;
this.flush();
byte[] byArray2 = new byte[n2];
System.arraycopy(byArray, n, byArray2, 0, n2);
FoxRequest foxRequest = null;
int n4 = n2;
for (int i = 0; i != n4; i += n3) {
int n5 = n4 - i;
foxRequest = this.sendStream(byArray2, i, n3, (n3 = Math.min(Fox.circuitChunkSize, n5)) == n5 ? foxAsyncCallbacks : null);
}
return foxRequest;
}
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
public void close() {
if (!this.open) {
return;
}
try {
this.flush();
}
catch (IOException iOException) {
// empty catch block
}
this.session.closeCircuit(this);
this.open = false;
Object object = this.incomingLock;
synchronized (object) {
this.incomingLock.notifyAll();
}
object = this.outgoingLock;
synchronized (object) {
this.outgoingLock.notifyAll();
}
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
void writeOut(byte[] byArray, int n, int n2) throws IOException {
this.assertOpen();
Object object = this.outgoingLock;
synchronized (object) {
while (this.open && n2 > 0) {
int n3 = Math.min(this.outgoing.length - this.nOutgoing, n2);
System.arraycopy(byArray, n, this.outgoing, this.nOutgoing, n3);
this.nOutgoing += n3;
n += n3;
n2 -= n3;
if (this.nOutgoing < this.outgoing.length) continue;
this.flush();
}
}
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
public void flush() throws IOException {
Object object = this.outgoingLock;
synchronized (object) {
if (this.open && this.nOutgoing > 0) {
try {
this.sendStream(this.outgoing, this.nOutgoing);
this.outgoing = new byte[Fox.circuitChunkSize];
this.nOutgoing = 0;
}
catch (IOException iOException) {
throw iOException;
}
catch (Exception exception) {
exception.printStackTrace();
throw new IOException(exception.toString());
}
}
}
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
void pushIn(byte[] byArray) throws InterruptedException {
if (byArray.length == 0) {
return;
}
Object object = this.incomingLock;
synchronized (object) {
while (this.open && this.incomingHead != null && this.nIncoming + byArray.length > Fox.circuitMaxReceiveBuffer) {
this.incomingLock.wait();
}
BufferEntry bufferEntry = new BufferEntry(byArray);
if (this.incomingHead == null) {
this.incomingHead = bufferEntry;
}
if (this.incomingTail != null) {
this.incomingTail.next = bufferEntry;
}
this.incomingTail = bufferEntry;
this.nIncoming += byArray.length;
this.incomingLock.notifyAll();
}
}
/*
* WARNING - Removed try catching itself - possible behaviour change.
*/
int pullIn(byte[] byArray, int n, int n2) throws IOException {
Object object = this.incomingLock;
synchronized (object) {
BufferEntry bufferEntry;
while (this.nIncoming <= 0) {
if (!this.open) {
return -1;
}
try {
this.incomingLock.wait();
}
catch (InterruptedException interruptedException) {
throw new InterruptedIOException();
}
}
int n3 = 0;
while (n2 > 0 && (bufferEntry = this.incomingHead) != null) {
int n4 = Math.min(bufferEntry.avail, n2);
System.arraycopy(bufferEntry.data, bufferEntry.data.length - bufferEntry.avail, byArray, n, n4);
n3 += n4;
n += n4;
n2 -= n4;
bufferEntry.avail -= n4;
if (bufferEntry.avail > 0) continue;
this.incomingHead = bufferEntry.next;
if (this.incomingTail == bufferEntry) {
this.incomingTail = null;
}
bufferEntry.next = null;
}
this.nIncoming -= n3;
this.incomingLock.notifyAll();
return n3;
}
}
private void assertOpen() throws IOException {
if (!this.open) {
throw new IOException("circuit closed");
}
}
void sendOpen() throws Exception {
FoxRequest foxRequest = new FoxRequest("circuit", "open");
foxRequest.add("id", this.id);
foxRequest.add("channel", this.channel);
foxRequest.add("command", this.command);
this.session.sendAsync(foxRequest);
}
void sendStream(byte[] byArray, int n) throws Exception {
FoxRequest foxRequest = new FoxRequest("circuit", "stream");
foxRequest.add("id", this.id);
foxRequest.add("data", byArray, n);
this.session.sendAsync(foxRequest);
}
FoxRequest sendStream(byte[] byArray, int n, int n2, FoxAsyncCallbacks foxAsyncCallbacks) throws Exception {
FoxRequest foxRequest = new FoxRequest("circuit", "stream");
foxRequest.add("id", this.id);
foxRequest.add("data", byArray, n, n2);
this.session.sendAsync(foxRequest, foxAsyncCallbacks);
return foxRequest;
}
void sendClose() throws Exception {
if (this.open && !this.session.isClosed()) {
FoxRequest foxRequest = new FoxRequest("circuit", "close");
foxRequest.add("id", this.id);
this.session.sendAsync(foxRequest);
}
}
public String toString() {
return "Circuit [" + this.session.getId() + "] " + this.channel + "." + this.command + " out=" + this.nOutgoing + " in=" + this.nIncoming + " open=" + this.open;
}
public void dumpIncomingList() {
System.out.println("Incoming List:");
System.out.println(" head=" + this.incomingHead);
System.out.println(" tail=" + this.incomingTail);
System.out.println(" chain=");
BufferEntry bufferEntry = this.incomingHead;
while (bufferEntry != null) {
System.out.println(" " + bufferEntry);
bufferEntry = bufferEntry.next;
}
}
private static void trace(String string) {
System.out.println(string);
}
static class BufferEntry {
byte[] data;
int avail;
BufferEntry next;
BufferEntry(byte[] byArray) {
this.data = byArray;
this.avail = byArray.length;
}
public String toString() {
return Integer.toString(System.identityHashCode(this), 36) + " avail=" + this.avail + " length=" + this.data.length;
}
}
class CircuitInputStream
extends InputStream {
byte[] temp = new byte[1];
CircuitInputStream() {
}
public int read() throws IOException {
return this.read(this.temp, 0, 1) <= 0 ? -1 : this.temp[0] & 0xFF;
}
public int read(byte[] byArray) throws IOException {
return this.read(byArray, 0, byArray.length);
}
public int read(byte[] byArray, int n, int n2) throws IOException {
return FoxCircuit.this.pullIn(byArray, n, n2);
}
public void close() throws IOException {
FoxCircuit.this.close();
}
}
class CircuitOutputStream
extends OutputStream {
byte[] temp = new byte[1];
CircuitOutputStream() {
}
public void write(int n) throws IOException {
this.temp[0] = (byte)n;
this.write(this.temp, 0, 1);
}
public void write(byte[] byArray) throws IOException {
this.write(byArray, 0, byArray.length);
}
public void write(byte[] byArray, int n, int n2) throws IOException {
FoxCircuit.this.writeOut(byArray, n, n2);
}
public void flush() throws IOException {
FoxCircuit.this.flush();
}
public void close() {
FoxCircuit.this.close();
}
}
}