use of dev.hypnotic.ui.clickgui2.frame.Frame in project service-proxy by membrane.
the class Http2ExchangeHandler method createHeadersFrames.
public static List<Frame> createHeadersFrames(Message res, int streamId, Encoder encoder, Settings peerSettings, boolean isAtEof) throws IOException {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
encoder.setMaxHeaderTableSize(baos, peerSettings.getHeaderTableSize());
StringBuilder sb = log.isDebugEnabled() ? new StringBuilder() : null;
if (res instanceof Request) {
Request req = (Request) res;
String key = ":method";
String val = req.getMethod();
encoder.encodeHeader(baos, key.getBytes(StandardCharsets.US_ASCII), val.getBytes(StandardCharsets.US_ASCII), false);
if (sb != null) {
sb.append("Headers on stream ");
sb.append(streamId);
sb.append(":\n");
sb.append(key);
sb.append(": ");
sb.append(val);
sb.append("\n");
}
key = ":scheme";
val = "https";
encoder.encodeHeader(baos, key.getBytes(StandardCharsets.US_ASCII), val.getBytes(StandardCharsets.US_ASCII), false);
if (sb != null) {
sb.append(key);
sb.append(": ");
sb.append(val);
sb.append("\n");
}
key = ":path";
val = req.getUri();
encoder.encodeHeader(baos, key.getBytes(StandardCharsets.US_ASCII), val.getBytes(StandardCharsets.US_ASCII), false);
if (sb != null) {
sb.append(key);
sb.append(": ");
sb.append(val);
sb.append("\n");
}
key = ":authority";
val = req.getHeader().getHost();
encoder.encodeHeader(baos, key.getBytes(StandardCharsets.US_ASCII), val.getBytes(StandardCharsets.US_ASCII), false);
if (sb != null) {
sb.append(key);
sb.append(": ");
sb.append(val);
sb.append("\n");
}
}
if (res instanceof Response) {
String keyStatus = ":status";
String valStatus = "" + ((Response) res).getStatusCode();
encoder.encodeHeader(baos, keyStatus.getBytes(StandardCharsets.US_ASCII), valStatus.getBytes(StandardCharsets.US_ASCII), false);
if (sb != null) {
sb.append("Headers on stream ");
sb.append(streamId);
sb.append(":\n");
sb.append(keyStatus);
sb.append(": ");
sb.append(valStatus);
sb.append("\n");
}
}
for (HeaderField hf : res.getHeader().getAllHeaderFields()) {
String key = hf.getHeaderName().toString().toLowerCase();
if ("keep-alive".equals(key) || "proxy-connection".equals(key) || "transfer-encoding".equals(key) || "upgrade".equals(key) || "connection".equals(key) || "host".equals(key))
continue;
boolean sensitive = "set-cookie".equals(key);
encoder.encodeHeader(baos, key.getBytes(StandardCharsets.US_ASCII), hf.getValue().getBytes(StandardCharsets.US_ASCII), sensitive);
if (sb != null) {
sb.append(key);
sb.append(": ");
sb.append(hf.getValue());
if (sensitive)
sb.append(" (sensitive)");
sb.append("\n");
}
}
if (sb != null)
log.debug(sb.toString());
byte[] header = baos.toByteArray();
List<Frame> frames = new ArrayList<>();
int maxFrameSize = peerSettings.getMaxFrameSize();
for (int offset = 0; offset < header.length; offset += maxFrameSize) {
Frame frame = new Frame();
boolean isLast = offset + maxFrameSize >= header.length;
frame.fill(offset == 0 ? TYPE_HEADERS : TYPE_CONTINUATION, (isLast ? FLAG_END_HEADERS : 0) + (isAtEof ? FLAG_END_STREAM : 0), streamId, header, offset, Math.min(maxFrameSize, header.length - offset));
frames.add(frame);
}
return frames;
}
use of dev.hypnotic.ui.clickgui2.frame.Frame in project service-proxy by membrane.
the class Http2ExchangeHandler method writeMessageBody.
public static void writeMessageBody(final int streamId, final StreamInfo streamInfo, final FrameSender sender, final Settings peerSettings, final PeerFlowControl peerFlowControl, Message res) throws IOException {
res.getBody().write(new AbstractBodyTransferrer() {
@Override
public void write(byte[] content, int i, int length) throws IOException {
sendData(content, i, length);
}
private void sendData(byte[] content, int offset, int length) throws IOException {
int mOffset = offset;
while (mOffset < offset + length) {
int mLength = Math.min(peerSettings.getMaxFrameSize(), length - (mOffset - offset));
// as we do not send padding, reserve exactly the length we want to send
streamInfo.getPeerFlowControl().reserve(mLength, streamId);
peerFlowControl.reserve(mLength, streamId);
Frame frame = new Frame();
frame.fill(TYPE_DATA, 0, streamId, content, mOffset, mLength);
sender.send(frame);
mOffset += mLength;
}
}
@Override
public void write(Chunk chunk) throws IOException {
sendData(chunk.getContent(), 0, chunk.getLength());
}
@Override
public void finish() throws IOException {
}
}, false);
Frame frame = new Frame();
frame.fill(TYPE_DATA, FLAG_END_STREAM, streamId, null, 0, 0);
sender.send(frame);
}
use of dev.hypnotic.ui.clickgui2.frame.Frame in project service-proxy by membrane.
the class FrameSender method stop.
public void stop() {
Frame e = new Frame();
e.fill(TYPE_STOP, 0, 0, null, 0, 0);
queue.add(e);
}
use of dev.hypnotic.ui.clickgui2.frame.Frame in project service-proxy by membrane.
the class FrameSender method run.
@Override
public void run() {
try {
updateThreadName(true);
while (true) {
Frame frame = getNextFrame();
if (frame == null) {
out.flush();
log.info("found no frame to send, starting wait loop.");
while (frame == null) frame = waitForNextFrame();
log.info("found found another frame to send.");
}
if (frame.getType() == TYPE_STOP)
break;
if (frame.getType() == Frame.TYPE_RST_STREAM)
streams.get(frame.getStreamId()).sendRstStream();
if (frame.getType() == Frame.TYPE_HEADERS)
streams.get(frame.getStreamId()).sendHeaders();
if ((frame.getType() == Frame.TYPE_HEADERS || frame.getType() == Frame.TYPE_DATA) && (frame.getFlags() & HeadersFrame.FLAG_END_STREAM) != 0)
streams.get(frame.getStreamId()).sendEndStream();
if (log.isTraceEnabled())
log.trace("sending: " + frame);
else if (log.isDebugEnabled())
log.debug("sending: " + frame.getTypeString() + " length=" + frame.getLength());
frame.write(out);
}
} catch (Throwable e) {
e.printStackTrace();
} finally {
updateThreadName(false);
}
log.debug("frame sender shutdown");
}
use of dev.hypnotic.ui.clickgui2.frame.Frame in project service-proxy by membrane.
the class Http2Logic method handleFrame.
private void handleFrame(HeadersFrame headers) throws IOException {
int streamId1 = headers.getFrame().getStreamId();
if (streamId1 == 0)
throw new FatalConnectionException(ERROR_PROTOCOL_ERROR);
StreamInfo streamInfo = streams.get(streamId1);
if (streamInfo == null) {
streamInfo = new StreamInfo(streamId1, sender, peerSettings, ourSettings);
streams.put(streamId1, streamInfo);
}
streamInfo.receivedHeaders();
if (headers.isPriority())
priorityTree.reprioritize(streamInfo, headers.getWeight(), streams.get(headers.getStreamDependency()), headers.isExclusive());
else
priorityTree.reprioritize(streamInfo, 16, null, false);
List<HeaderBlockFragment> headerFrames = new ArrayList<>();
headerFrames.add(headers);
HeaderBlockFragment last = headers;
while (!last.isEndHeaders()) {
Frame frame = new Frame(ourSettings);
frame.read(srcIn);
if (frame.getType() != TYPE_CONTINUATION)
throw new FatalConnectionException(ERROR_PROTOCOL_ERROR);
last = frame.asContinuation();
int streamId = frame.getStreamId();
if (streamId != streamId1)
throw new FatalConnectionException(ERROR_PROTOCOL_ERROR);
headerFrames.add(last);
}
Message request = messageHandler.createMessage();
StringBuilder sb = log.isDebugEnabled() ? new StringBuilder() : null;
if (sb != null) {
sb.append("Headers on stream ");
sb.append(streamId1);
sb.append(":\n");
}
decoder.decode(getPackedHeaderStream(headerFrames), new HeaderListener() {
@Override
public void addHeader(byte[] name, byte[] value, boolean sensitive) {
String key = new String(name);
String val = new String(value);
if (sb != null) {
sb.append(key);
sb.append(": ");
sb.append(val);
sb.append("\n");
}
if (":method".equals(key) && request instanceof Request)
((Request) request).setMethod(val);
else if (":scheme".equals(key))
// ignore
;
else if (":authority".equals(key))
request.getHeader().setHost(val);
else if (":path".equals(key) && request instanceof Request) {
((Request) request).setUri(val);
log.info("streamId=" + streamId1 + " uri=" + val);
} else if (":status".equals(key) && request instanceof Response) {
((Response) request).setStatusCode(Integer.parseInt(val));
log.debug("streamId=" + streamId1 + " status=" + val);
} else
request.getHeader().add(key, val);
}
});
decoder.endHeaderBlock();
if (sb != null)
log.debug(sb.toString());
if (!headers.isEndStream())
request.setBody(streamInfo.createBody());
messageHandler.handleExchange(streamInfo, request, showSSLExceptions, remoteAddr);
if (headers.isEndStream())
streamInfo.receivedEndStream(false);
}
Aggregations