mirror of https://github.com/apache/cloudstack.git
1132 lines
52 KiB
Java
1132 lines
52 KiB
Java
// Licensed to the Apache Software Foundation (ASF) under one
|
|
// or more contributor license agreements. See the NOTICE file
|
|
// distributed with this work for additional information
|
|
// regarding copyright ownership. The ASF licenses this file
|
|
// to you under the Apache License, Version 2.0 (the
|
|
// "License"); you may not use this file except in compliance
|
|
// with the License. You may obtain a copy of the License at
|
|
//
|
|
// http://www.apache.org/licenses/LICENSE-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing,
|
|
// software distributed under the License is distributed on an
|
|
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
|
// KIND, either express or implied. See the License for the
|
|
// specific language governing permissions and limitations
|
|
// under the License.
|
|
package rdpclient.rdp;
|
|
|
|
import streamer.BaseElement;
|
|
import streamer.ByteBuffer;
|
|
import streamer.Element;
|
|
import streamer.Link;
|
|
import streamer.Pipeline;
|
|
import streamer.PipelineImpl;
|
|
import streamer.debug.MockSink;
|
|
import streamer.debug.MockSource;
|
|
import common.ScreenDescription;
|
|
|
|
/**
|
|
* @see <a href="http://msdn.microsoft.com/en-us/library/cc240488.aspx">microsoft msdn explanation</a>
|
|
*/
|
|
public class ClientConfirmActivePDU extends BaseElement {
|
|
|
|
public static final String SOURCE_DESC = "MSTSC";
|
|
|
|
public static final int CAPSTYPE_BITMAP = 0x2;
|
|
|
|
protected int numberCapabilities;
|
|
|
|
protected RdpState state;
|
|
protected ScreenDescription screen;
|
|
|
|
protected boolean desktopResize = false;
|
|
protected int prefferedBitsPerPixel = 16;
|
|
|
|
public ClientConfirmActivePDU(String id, ScreenDescription screen, RdpState state) {
|
|
super(id);
|
|
this.state = state;
|
|
this.screen = screen;
|
|
}
|
|
|
|
@Override
|
|
public void handleData(ByteBuffer aBuf, Link link) {
|
|
|
|
// Body
|
|
ByteBuffer buf = new ByteBuffer(1024, true);
|
|
numberCapabilities = 0;
|
|
writeCapabilities(buf);
|
|
buf.trimAtCursor();
|
|
|
|
// Header
|
|
ByteBuffer header = createMCSHeader(buf);
|
|
|
|
// Length of source descriptor, including NULL character (LE)
|
|
header.writeShortLE(SOURCE_DESC.length() + 1);
|
|
|
|
// Length of combined capabilities + 4 bytes (number of capabilities and
|
|
// padding) (LE)
|
|
header.writeShortLE(buf.length + 4);
|
|
|
|
header.writeString(SOURCE_DESC, RdpConstants.CHARSET_8);
|
|
header.writeByte(0);
|
|
|
|
// Number of capabilities
|
|
header.writeShortLE(numberCapabilities);
|
|
|
|
// Padding 2 bytes
|
|
header.writeShortLE(0);
|
|
|
|
header.trimAtCursor();
|
|
|
|
// Prepend header to capabilities
|
|
buf.prepend(header);
|
|
|
|
// Trim buffer to actual length of data written
|
|
buf.trimAtCursor();
|
|
|
|
pushDataToPad(STDOUT, buf);
|
|
|
|
sendOtherRequredPackets();
|
|
|
|
}
|
|
|
|
private ByteBuffer createMCSHeader(ByteBuffer buf) {
|
|
ByteBuffer header = new ByteBuffer(100);
|
|
// MCS Send Data Request
|
|
header.writeByte(0x64);
|
|
|
|
// Initiator: 1004 (1001+3)
|
|
header.writeShort(3);
|
|
|
|
// Channel ID: 1003 (I/O channel)
|
|
header.writeShort(RdpConstants.CHANNEL_IO);
|
|
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
header.writeByte(0x70);
|
|
|
|
int length = buf.length + 26;
|
|
|
|
// User data length: (variable length field, LE)
|
|
header.writeVariableShort(length);
|
|
|
|
// Total length: (LE)
|
|
header.writeShortLE(length);
|
|
|
|
// PDU type: Confirm Active PDU (0x3), TS_PROTOCOL_VERSION (0x10) (LE)
|
|
header.writeShortLE(0x13);
|
|
|
|
// PDU source: 1004 (LE)
|
|
header.writeShortLE(1004);
|
|
|
|
// Share ID, e.g. 0x000103ea (LE)
|
|
header.writeIntLE((int)state.serverShareId);
|
|
|
|
// Originator ID: 1002 (LE)
|
|
header.writeShortLE(1002);
|
|
return header;
|
|
}
|
|
|
|
private void sendOtherRequredPackets() {
|
|
// Send sequence in bulk
|
|
|
|
sendSynchronizePDU();
|
|
sendControlPDUActionCooperate();
|
|
sendControlPDUActionRequestControl();
|
|
// sendBitmapCachePersistentListPDU();
|
|
sendFontListPDU();
|
|
}
|
|
|
|
private void sendFontListPDU() {
|
|
{
|
|
int length = 1024; // Large enough
|
|
ByteBuffer buf = new ByteBuffer(length, true);
|
|
|
|
/* @formatter:off */
|
|
buf.writeBytes(new byte[] {
|
|
// MCS Send Data Request
|
|
(byte)0x64,
|
|
// Initiator: 1004 (1001+3)
|
|
(byte)0x00, (byte)0x03,
|
|
// Channel ID: 1003 (I/O channel)
|
|
(byte)0x03, (byte)0xeb,
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
(byte)0x70,
|
|
// User data length: 26 bytes (0x1a, variable length field)
|
|
(byte)0x80, (byte)0x1a,
|
|
|
|
// Total length: 26 bytes (0x1a, LE)
|
|
(byte)0x1a, (byte)0x00,
|
|
// PDU type: PDUTYPE_DATAPDU (0x7), PDU version: 1 (0x0010) (LE)
|
|
(byte)0x17, (byte)0x00,
|
|
// PDU source: 1004 (LE)
|
|
(byte)0xec, (byte)0x03,
|
|
});
|
|
// Share ID, 4 bytes (LE)
|
|
buf.writeIntLE((int)state.serverShareId);
|
|
|
|
buf.writeBytes(new byte[] {
|
|
// Padding 1 byte
|
|
(byte)0x00,
|
|
// Stream ID: STREAM_LOW (1)
|
|
(byte)0x01,
|
|
// uncompressedLength : 12 bytes (LE)
|
|
(byte)0x0c, (byte)0x00,
|
|
|
|
// pduType2: PDUTYPE2_FONTLIST (39)
|
|
(byte)0x27,
|
|
// generalCompressedType: 0
|
|
(byte)0x00,
|
|
// generalCompressedLength: 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
|
|
// numberEntries (should be set to zero): 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
// totalNumEntries (should be set to zero): 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
// listFlags (should be set to 0x3): 0x0003 (LE), FONTLIST_LAST(0x2) | FONTLIST_FIRST(0x1)
|
|
(byte)0x03, (byte)0x00,
|
|
// entrySize: 50 bytes (0x0032, LE)
|
|
(byte)0x32, (byte)0x00,
|
|
});
|
|
/* @formatter:on */
|
|
|
|
// Trim buffer to actual length of data written
|
|
buf.trimAtCursor();
|
|
|
|
pushDataToPad(STDOUT, buf);
|
|
}
|
|
}
|
|
|
|
private void sendControlPDUActionRequestControl() {
|
|
int length = 1024; // Large enough
|
|
ByteBuffer buf = new ByteBuffer(length, true);
|
|
|
|
/* @formatter:off */
|
|
buf.writeBytes(new byte[] {
|
|
// MCS Send Data Request
|
|
(byte)0x64,
|
|
// Initiator: 1004 (1001+3)
|
|
(byte)0x00, (byte)0x03,
|
|
// Channel ID: 1003 (I/O channel)
|
|
(byte)0x03, (byte)0xeb,
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
(byte)0x70,
|
|
// User data length: 26 bytes (0x1a, variable length field)
|
|
(byte)0x80, (byte)0x1a,
|
|
|
|
// Total length: 26 bytes (0x1a, LE)
|
|
(byte)0x1a, (byte)0x00,
|
|
// PDU type: PDUTYPE_DATAPDU (0x7), PDU version: 1 (0x0010) (LE)
|
|
(byte)0x17, (byte)0x00,
|
|
// PDU source: 1004 (LE)
|
|
(byte)0xec, (byte)0x03,
|
|
});
|
|
// Share ID, 4 bytes (LE)
|
|
buf.writeIntLE((int)state.serverShareId);
|
|
|
|
buf.writeBytes(new byte[] {
|
|
// Padding 1 byte
|
|
(byte)0x00,
|
|
// Stream ID: STREAM_LOW (1)
|
|
(byte)0x01,
|
|
// uncompressedLength : 12 bytes (LE)
|
|
(byte)0x0c, (byte)0x00,
|
|
// pduType2: PDUTYPE2_CONTROL (20)
|
|
(byte)0x14,
|
|
// generalCompressedType: 0
|
|
(byte)0x00,
|
|
// generalCompressedLength: 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
|
|
// action: CTRLACTION_REQUEST_CONTROL (1) (LE)
|
|
(byte)0x01, (byte)0x00,
|
|
// grantId: 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
// controlId: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
});
|
|
/* @formatter:on */
|
|
|
|
// Trim buffer to actual length of data written
|
|
buf.trimAtCursor();
|
|
|
|
pushDataToPad(STDOUT, buf);
|
|
}
|
|
|
|
private void sendControlPDUActionCooperate() {
|
|
int length = 1024; // Large enough
|
|
ByteBuffer buf = new ByteBuffer(length, true);
|
|
|
|
/* @formatter:off */
|
|
buf.writeBytes(new byte[] {
|
|
// MCS Send Data Request
|
|
(byte)0x64,
|
|
// Initiator: 1004 (1001+3)
|
|
(byte)0x00, (byte)0x03,
|
|
// Channel ID: 1003 (I/O channel)
|
|
(byte)0x03, (byte)0xeb,
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
(byte)0x70,
|
|
// User data length: 26 bytes (0x1a, variable length field)
|
|
(byte)0x80, (byte)0x1a,
|
|
|
|
// Total length: 26 bytes (0x1a, LE)
|
|
(byte)0x1a,(byte)0x00,
|
|
// PDU type: PDUTYPE_DATAPDU (0x7), PDU version: 1 (0x0010) (LE)
|
|
(byte)0x17, (byte)0x00,
|
|
// PDU source: 1004 (LE)
|
|
(byte)0xec, (byte)0x03,
|
|
});
|
|
// Share ID, 4 bytes (LE)
|
|
buf.writeIntLE((int)state.serverShareId);
|
|
|
|
buf.writeBytes(new byte[] {
|
|
// Padding 1 byte
|
|
(byte)0x00,
|
|
// Stream ID: STREAM_LOW (1)
|
|
(byte)0x01,
|
|
// uncompressedLength : 12 bytes (LE)
|
|
(byte)0x0c, (byte)0x00,
|
|
// pduType2: PDUTYPE2_CONTROL (20)
|
|
(byte)0x14,
|
|
// generalCompressedType: 0
|
|
(byte)0x00,
|
|
// generalCompressedLength: 0 (LE?)
|
|
(byte)0x00, (byte)0x00,
|
|
// action: CTRLACTION_COOPERATE (4) (LE)
|
|
(byte)0x04, (byte)0x00,
|
|
// grantId: 0 (LE)
|
|
(byte)0x00, (byte)0x00,
|
|
// controlId: 0
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
});
|
|
/* @formatter:on */
|
|
|
|
buf.trimAtCursor();
|
|
|
|
pushDataToPad(STDOUT, buf);
|
|
}
|
|
|
|
private void sendSynchronizePDU() {
|
|
|
|
ByteBuffer buf = new ByteBuffer(1024, true);
|
|
/* @formatter:off */
|
|
buf.writeBytes(new byte[] {
|
|
// MCS send data request
|
|
(byte)0x64,
|
|
// Initiator: 1004 (1001+3)
|
|
(byte)0x00, (byte)0x03,
|
|
// Channel ID: 1003 (I/O Channel)
|
|
(byte)0x03, (byte)0xeb,
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
(byte)0x70,
|
|
// Data length: 22 bytes (0x16, variable length field)
|
|
(byte)0x80, (byte)0x16,
|
|
|
|
// RDP: total length: 22 bytes (LE)
|
|
(byte)0x16, (byte)0x00,
|
|
|
|
// PDU type: PDUTYPE_DATAPDU (0x7), TS_PROTOCOL_VERSION (0x10) (LE)
|
|
(byte)0x17, (byte)0x00,
|
|
|
|
// PDU source: 1007 (LE)
|
|
(byte)0xec, (byte)0x03,
|
|
});
|
|
// Share ID, 4 bytes (LE)
|
|
buf.writeIntLE((int)state.serverShareId);
|
|
|
|
buf.writeBytes(new byte[] {
|
|
// Padding: 1 byte
|
|
(byte)0x00,
|
|
// Stream ID: STREAM_LOW (1)
|
|
(byte)0x01,
|
|
// uncompressedLength : 8 bytes (LE)
|
|
(byte)0x08, (byte)0x00,
|
|
// pduType2 = PDUTYPE2_SYNCHRONIZE (31)
|
|
(byte)0x1f,
|
|
// generalCompressedType: 0
|
|
(byte)0x00,
|
|
// generalCompressedLength: 0 (LE?)
|
|
(byte)0x00, (byte)0x00,
|
|
// messageType: SYNCMSGTYPE_SYNC (1) (LE)
|
|
(byte)0x01, (byte)0x00,
|
|
// targetUser: 0x03ea
|
|
(byte)0xea, (byte)0x03,
|
|
});
|
|
/* @formatter:on */
|
|
buf.trimAtCursor();
|
|
pushDataToPad(STDOUT, buf);
|
|
}
|
|
|
|
private void writeCapabilities(ByteBuffer buf) {
|
|
writeGeneralCS(buf);
|
|
|
|
writeBitmapCS(buf);
|
|
|
|
writeOrderCS(buf);
|
|
|
|
writeBitmapCache2CS(buf);
|
|
|
|
writeColorTableCacheCS(buf);
|
|
|
|
writeWindowActivationCS(buf);
|
|
|
|
writeControlCS(buf);
|
|
|
|
writePointerCS(buf);
|
|
|
|
writeShareCS(buf);
|
|
|
|
writeInputCS(buf);
|
|
|
|
writeBrushCS(buf);
|
|
|
|
writeSoundCS(buf);
|
|
|
|
writeFontCS(buf);
|
|
|
|
writeOffscreenBitmapCS(buf);
|
|
|
|
writeGlyphCacheCS(buf);
|
|
}
|
|
|
|
private void writeBrushCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Brush Capability Set (8 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240564.aspx
|
|
(byte)0x0f, (byte)0x00, // capability set type: CAPSTYPE_BRUSH (15,
|
|
// LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // brushSupportLevel:
|
|
// BRUSH_DEFAULT
|
|
// (0x0, LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeInputCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Input Capability Set (88 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240563.aspx
|
|
(byte)0x0d,
|
|
(byte)0x00, // capability set type: CAPSTYPE_INPUT (13, LE)
|
|
(byte)0x58,
|
|
(byte)0x00, // length of capability set: 88 bytes (LE)
|
|
(byte)0x35,
|
|
(byte)0x00, // inputFlags: 0x0035 (LE), INPUT_FLAG_FASTPATH_INPUT2
|
|
// (0x20), INPUT_FLAG_VKPACKET (0x10), INPUT_FLAG_MOUSEX
|
|
// (0x4), INPUT_FLAG_SCANCODES (0x1)
|
|
(byte)0x00,
|
|
(byte)0x00, // Padding 2 bytes
|
|
(byte)0x09,
|
|
(byte)0x04,
|
|
(byte)0x00,
|
|
(byte)0x00, // keyboardLayout: "US" keyboard layout (0x000409, LE)
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00, // keyboardType: unknown (LE)
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00, // keyboardSubType: unknown (LE)
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00,
|
|
(byte)0x00, // keyboardFunctionKey: unknown (LE)
|
|
// imeFileName: "", (64 bytes, including trailing NULL characters, UCS2)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
|
|
});
|
|
}
|
|
|
|
private void writeShareCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Share Capability Set (8 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240570.aspx
|
|
(byte)0x09, (byte)0x00, // capability set type: CAPSTYPE_SHARE (9, LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // nodeID (must be set to 0 by client): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes (LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writePointerCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Pointer Capability Set (10 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240562.aspx
|
|
(byte)0x08, (byte)0x00, // capability set type: CAPSTYPE_POINTER (8,
|
|
// LE)
|
|
(byte)0x0a, (byte)0x00, // length of capability set: 10 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // colorPointerFlag: FALSE (LE)
|
|
(byte)0x00, (byte)0x00, // colorPointerCacheSize: 0 (LE)
|
|
(byte)0x14, (byte)0x00, // pointerCacheSize: 20 (LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeControlCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Control Capability Set (12 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240568.aspx
|
|
(byte)0x05, (byte)0x00, // capability set type: CAPSTYPE_ACTIVATION
|
|
// (7)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // controlFlags (should be set to 0): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // remoteDetachFlag (should be set to 0): 0
|
|
// (LE)
|
|
(byte)0x02, (byte)0x00, // controlInterest (should be set to
|
|
// CONTROLPRIORITY_NEVER):
|
|
// CONTROLPRIORITY_NEVER (2) (LE)
|
|
(byte)0x02, (byte)0x00, // detachInterest (should be set to
|
|
// CONTROLPRIORITY_NEVER):
|
|
// CONTROLPRIORITY_NEVER (2) (LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeWindowActivationCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Window Activation Capability Set (12 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240569.aspx
|
|
(byte)0x07, (byte)0x00, // capability set type: CAPSTYPE_ACTIVATION
|
|
// (7) (LE)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // helpKeyFlag (should be set to FALSE (0)):
|
|
// FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // helpKeyIndexFlag (should be set to FALSE
|
|
// (0)): FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // helpExtendedKeyFlag (should be set to FALSE
|
|
// (0)): FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // windowManagerKeyFlag (should be set to
|
|
// FALSE (0)): FALSE (0, LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeColorTableCacheCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
|
|
//
|
|
// Color Table Cache Capability Set (8 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc241564.aspx
|
|
(byte)0x0a, (byte)0x00, // capability set type: CAPSTYPE_COLORCACHE
|
|
// (10) (LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x06, (byte)0x00, // Color table cache size (must be ignored
|
|
// during capability exchange and is assumed
|
|
// to be 0x0006): 6 (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
});
|
|
}
|
|
|
|
private void writeBitmapCache2CS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Bitmap Cache Rev. 2 Capability Set (40 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240560.aspx
|
|
(byte)0x13, (byte)0x00, // capability set type:
|
|
// CAPSTYPE_BITMAPCACHE_REV2 (19) (LE)
|
|
(byte)0x28, (byte)0x00, // length of capability set: 40 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // Cache flags: 0 (LE)
|
|
(byte)0x00, // Padding 1 byte
|
|
(byte)0x00, // Number of cell caches: 0
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache0
|
|
// cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache1
|
|
// cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache2
|
|
// cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache3
|
|
// cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache4
|
|
// cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding 12 bytes
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding
|
|
});
|
|
}
|
|
|
|
private void writeGeneralCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
// Capabilities, see
|
|
// http://msdn.microsoft.com/en-us/library/cc240486.aspx
|
|
|
|
//
|
|
// General capability set (24 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240549.aspx
|
|
(byte)0x01, (byte)0x00, // capability set type: CAPSTYPE_GENERAL (1)
|
|
// (LE)
|
|
(byte)0x18, (byte)0x00, // length of capability set: 24 bytes (LE)
|
|
(byte)0x01, (byte)0x00, // TS_OSMAJORTYPE_WINDOWS (1) (LE)
|
|
(byte)0x03, (byte)0x00, // TS_OSMINORTYPE_WINDOWS_NT (3) (LE)
|
|
(byte)0x00, (byte)0x02, // TS_CAPS_PROTOCOLVERSION (0x0200) (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x00, (byte)0x00, // generalCompressionTypes: 0 (LE)
|
|
|
|
// Extra flags: 0x040d (LE)
|
|
// FastPathOutput: (...............1) Advertiser supports fast-path
|
|
// output
|
|
// ShadowCompression: (..............0.) Advertiser NOT supports shadow
|
|
// compression
|
|
// LongLengthCredentials: (.............1..) Advertiser supports
|
|
// long-length credentials for the user name, password, or domain name
|
|
// SessionAutoreconnection: (............1...) Advertiser supports
|
|
// session auto-reconnection
|
|
// ImprovedEncryptionChecksum: (...........0....) Client and server NOT
|
|
// support improved encryption checksum
|
|
// Reserved1: (......00000.....)
|
|
// CompressedBitMapDataFlag: (.....1..........) No 8-UINT8 header is
|
|
// present for compressed bitmap data
|
|
// Reserved2: (00000...........)
|
|
(byte)0x0d, (byte)0x04,
|
|
|
|
(byte)0x00, (byte)0x00, // updateCapabilityFlag: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // remoteUnshareFlag: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // generalCompressionLevel: 0 (LE)
|
|
(byte)0x00, // refreshRectSupport: FALSE (0)
|
|
(byte)0x00, // suppressOutputSupport: FALSE (0)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeBitmapCS(ByteBuffer buf) {
|
|
// Bitmap capability set (28 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240554.aspx
|
|
|
|
numberCapabilities++;
|
|
|
|
// Capability set type: CAPSTYPE_BITMAP (2) (LE)
|
|
buf.writeShortLE(CAPSTYPE_BITMAP);
|
|
|
|
// Length of capability set: 28 bytes (LE)
|
|
buf.writeShortLE(28);
|
|
|
|
// preferredBitsPerPixel: 16 bpp (LE)
|
|
buf.writeShortLE(prefferedBitsPerPixel);
|
|
|
|
// receive1BitPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
buf.writeShortLE(1);
|
|
|
|
// receive4BitsPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
buf.writeShortLE(1);
|
|
|
|
// receive8BitsPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
buf.writeShortLE(1);
|
|
|
|
// Desktop width and height (LE)
|
|
buf.writeShortLE(screen.getFramebufferWidth());
|
|
buf.writeShortLE(screen.getFramebufferHeight());
|
|
|
|
// Padding 2 bytes
|
|
buf.writeShortLE(0);
|
|
|
|
// desktopResizeFlag (LE)
|
|
buf.writeShortLE((desktopResize) ? 1 : 0);
|
|
|
|
buf.writeBytes(new byte[] {
|
|
(byte)0x01, (byte)0x00, // bitmapCompressionFlag (must be set to TRUE
|
|
// (0x1)): TRUE (0x1) (LE)
|
|
(byte)0x00, // highColorFlags (field is ignored and SHOULD be set to
|
|
// zero): 0
|
|
(byte)0x01, // drawingFlags: 0x1 TODO: padding, why 0x1 ???
|
|
(byte)0x01, (byte)0x00, // multipleRectangleSupport: TRUE (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
});
|
|
}
|
|
|
|
private void writeOrderCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Order Capability Set (88 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240556.aspx
|
|
(byte)0x03,
|
|
(byte)0x00, // capability set type: CAPSTYPE_ORDER (3) (LE)
|
|
(byte)0x58,
|
|
(byte)0x00, // length of capability set: 88 bytes (LE)
|
|
// terminalDescriptor = "" (16 bytes, UCS2)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // pad4octetsA
|
|
(byte)0x01, (byte)0x00, // desktopSaveXGranularity (ignored): 1 (LE)
|
|
(byte)0x14, (byte)0x00, // desktopSaveYGranularity (ignored): 20 (LE)
|
|
(byte)0x00, (byte)0x00, // pad2octetsA (ignored)
|
|
(byte)0x01, (byte)0x00, // maximumOrderLevel: ORD_LEVEL_1_ORDERS (1)
|
|
(byte)0x00, (byte)0x00, // number of fonts (ignored): 0
|
|
(byte)0x4a, (byte)0x00, // orderFlags = 0x004a (LE),
|
|
// SOLIDPATTERNBRUSHONLY (0x40),
|
|
// ZEROBOUNDSDELTASSUPPORT (0x8, MUST),
|
|
// NEGOTIATEORDERSUPPORT (0x2, MUST)
|
|
// Order support: 32 bytes (no primary drawing orders are supported, so
|
|
// this array MUST be initialized to all zeros, use 0x01 for TRUE).
|
|
(byte)0x00, // TS_NEG_DSTBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_PATBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_SCRBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEMBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEM3BLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ATEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_AEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_DRAWNINEGRID_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_LINETO_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTI_DRAWNINEGRID_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_OPAQUERECT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_SAVEBITMAP_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEMBLT_R2_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEM3BLT_R2_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIDSTBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIPATBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTISCRBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIOPAQUERECT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_FAST_INDEX_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYGON_SC_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYGON_CB_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYLINE_INDEX: TRUE
|
|
(byte)0x00, // Unused: 0
|
|
(byte)0x00, // TS_NEG_FAST_GLYPH_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ELLIPSE_SC_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ELLIPSE_CB_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_INDEX_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WLONGTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WLONGEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // Unused: 0
|
|
(byte)0x00, (byte)0x00, // Text flags (ignored): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // Order support extra flags: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding 4 bytes
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Desktop save size
|
|
// (ignored): 0
|
|
// (assumed to be
|
|
// 230400 bytes
|
|
// (480*480,
|
|
// 0x38400, LE))
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0xe4, (byte)0x04, // Text ANSI Code Page: 1252, ANSI - Latin I
|
|
// (0x04e4, LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
});
|
|
}
|
|
|
|
private void writeSoundCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Sound Capability Set (8 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240552.aspx
|
|
(byte)0x0c, (byte)0x00, // capability set type: CAPSTYPE_SOUND (12,
|
|
// LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // soundFlags:
|
|
// 0x0000 (LE) //
|
|
// SOUND_FLAG_BEEPS
|
|
// (0x1)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeFontCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Font Capability Set (8 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240571.aspx
|
|
(byte)0x0e, (byte)0x00, (byte)0x08, (byte)0x00, (byte)0x01, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
|
|
});
|
|
}
|
|
|
|
private void writeOffscreenBitmapCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Offscreen Bitmap Cache Capability Set (12 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240550.aspx
|
|
(byte)0x11, (byte)0x00, // capability set type:
|
|
// CAPSTYPE_OFFSCREENCACHE (17, LE)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // offscreenSupportLevel:
|
|
// FALSE (LE)
|
|
(byte)0x00, (byte)0x00, // offscreenCacheSize: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // offscreenCacheEntries: 0 (LE)
|
|
|
|
});
|
|
}
|
|
|
|
private void writeGlyphCacheCS(ByteBuffer buf) {
|
|
numberCapabilities++;
|
|
buf.writeBytes(new byte[] {
|
|
//
|
|
// Glyph Cache Capability Set (52 bytes), see
|
|
// http://msdn.microsoft.com/en-us/library/cc240565.aspx
|
|
(byte)0x10, (byte)0x00, // capability set type:
|
|
// CAPSTYPE_OFFSCREENCACHE (16, LE)
|
|
(byte)0x34, (byte)0x00, // length of capability set: 52 bytes (LE)
|
|
// Glyph Cache (40 bytes)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x04, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x04, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x08, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x08, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x10, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x20, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x40, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x80, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x00, (byte)0x01, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0x40, (byte)0x00, // CacheEntries: 64 (LE)
|
|
(byte)0x00, (byte)0x08, // CacheMaximumCellSize: 2048 (LE)
|
|
// FragCache
|
|
(byte)0x00, (byte)0x01, // CacheEntries: 256 (LE)
|
|
(byte)0x00, (byte)0x01, // CacheMaximumCellSize: 256 (LE)
|
|
//
|
|
(byte)0x00, (byte)0x00, // GlyphSupportLevel: GLYPH_SUPPORT_NONE (0x0,
|
|
// LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Example.
|
|
*/
|
|
public static void main(String args[]) {
|
|
// System.setProperty("streamer.Link.debug", "true");
|
|
System.setProperty("streamer.Element.debug", "true");
|
|
// System.setProperty("streamer.Pipeline.debug", "true");
|
|
|
|
/* @formatter:off */
|
|
byte[] packet = new byte[] {
|
|
// MCS Send Data Request
|
|
(byte)0x64,
|
|
|
|
// Initiator: 1004 (1001+3)
|
|
(byte)0x00, (byte)0x03,
|
|
|
|
// Channel ID: 1003 (I/O channel)
|
|
(byte)0x03, (byte)0xeb,
|
|
|
|
// Data priority: high (0x40), segmentation: begin (0x20) | end (0x10)
|
|
(byte)0x70,
|
|
|
|
// User data length: 432 bytes (0x1b0, variable length field)
|
|
(byte)0x81, (byte)0xb0,
|
|
|
|
// Total length: 432 bytes (0x1b0, LE)
|
|
(byte)0xb0, (byte)0x01,
|
|
|
|
// PDU type: Confirm Active PDU (0x3), TS_PROTOCOL_VERSION (0x10) (LE)
|
|
(byte)0x13, (byte)0x00,
|
|
|
|
// PDU source: 1004 (LE)
|
|
(byte)0xec, (byte)0x03,
|
|
|
|
// Share ID: 0x000103ea (LE)
|
|
(byte)0xea, (byte)0x03, (byte)0x01, (byte)0x00,
|
|
|
|
// Originator ID: 1002 (LE)
|
|
(byte)0xea, (byte)0x03,
|
|
|
|
// Length of source descriptor: 6 bytes (including NULL character) (LE)
|
|
(byte)0x06, (byte)0x00,
|
|
|
|
// Length of combined capabilities: 410 bytes (LE)
|
|
(byte)0x9a, (byte)0x01,
|
|
|
|
// Source descriptor: "MSTSC" ???
|
|
(byte)0x4d, (byte)0x53, (byte)0x54, (byte)0x53, (byte)0x43, (byte)0x00,
|
|
|
|
// Number of capabilities: 15 (LE)
|
|
(byte)0x0f, (byte)0x00,
|
|
|
|
// Padding 2 bytes
|
|
(byte)0x00, (byte)0x00,
|
|
|
|
// Capabilities, see http://msdn.microsoft.com/en-us/library/cc240486.aspx
|
|
|
|
//
|
|
// General capability set (24 bytes), see http://msdn.microsoft.com/en-us/library/cc240549.aspx
|
|
(byte)0x01, (byte)0x00, // capability set type: CAPSTYPE_GENERAL (1) (LE)
|
|
(byte)0x18, (byte)0x00, // length of capability set: 24 bytes (LE)
|
|
(byte)0x01, (byte)0x00, // TS_OSMAJORTYPE_WINDOWS (1) (LE)
|
|
(byte)0x03, (byte)0x00, // TS_OSMINORTYPE_WINDOWS_NT (3) (LE)
|
|
(byte)0x00, (byte)0x02, // TS_CAPS_PROTOCOLVERSION (0x0200) (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x00, (byte)0x00, // generalCompressionTypes: 0 (LE)
|
|
|
|
// Extra flags: 0x040d (LE)
|
|
// FastPathOutput: (...............1) Advertiser supports fast-path output
|
|
// ShadowCompression: (..............0.) Advertiser NOT supports shadow compression
|
|
// LongLengthCredentials: (.............1..) Advertiser supports long-length credentials for the user name, password, or domain name
|
|
// SessionAutoreconnection: (............1...) Advertiser supports session auto-reconnection
|
|
// ImprovedEncryptionChecksum: (...........0....) Client and server NOT support improved encryption checksum
|
|
// Reserved1: (......00000.....)
|
|
// CompressedBitMapDataFlag: (.....1..........) No 8-UINT8 header is present for compressed bitmap data
|
|
// Reserved2: (00000...........)
|
|
(byte)0x0d, (byte)0x04,
|
|
|
|
(byte)0x00, (byte)0x00, // updateCapabilityFlag: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // remoteUnshareFlag: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // generalCompressionLevel: 0 (LE)
|
|
(byte)0x00, // refreshRectSupport: FALSE (0)
|
|
(byte)0x00, // suppressOutputSupport: FALSE (0)
|
|
|
|
//
|
|
// Bitmap capability set (28 bytes), see http://msdn.microsoft.com/en-us/library/cc240554.aspx
|
|
(byte)0x02, (byte)0x00, // capability set type: CAPSTYPE_BITMAP (2) (LE)
|
|
(byte)0x1c, (byte)0x00, // length of capability set: 28 bytes (LE)
|
|
(byte)0x10, (byte)0x00, // preferredBitsPerPixel: 16 bpp (LE)
|
|
(byte)0x01, (byte)0x00, // receive1BitPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
(byte)0x01, (byte)0x00, // receive4BitsPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
(byte)0x01, (byte)0x00, // receive8BitsPerPixel (ignored and SHOULD be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
(byte)0x00, (byte)0x04, // desktopWidth = 1024 pixels (LE)
|
|
(byte)0x00, (byte)0x03, // desktopHeight = 768 pixels (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x00, (byte)0x00, // desktopResizeFlag: FALSE (0x0) (LE)
|
|
(byte)0x01, (byte)0x00, // bitmapCompressionFlag (must be set to TRUE (0x1)): TRUE (0x1) (LE)
|
|
(byte)0x00, // highColorFlags (field is ignored and SHOULD be set to zero): 0
|
|
(byte)0x01, // drawingFlags: 0x1 TODO: padding, why 0x1 ???
|
|
(byte)0x01, (byte)0x00, // multipleRectangleSupport: TRUE (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
//
|
|
// Order Capability Set (88 bytes), see http://msdn.microsoft.com/en-us/library/cc240556.aspx
|
|
(byte)0x03, (byte)0x00, // capability set type: CAPSTYPE_ORDER (3) (LE)
|
|
(byte)0x58, (byte)0x00, // length of capability set: 88 bytes (LE)
|
|
// terminalDescriptor = "" (16 bytes, UCS2)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // pad4octetsA
|
|
(byte)0x01, (byte)0x00, // desktopSaveXGranularity (ignored): 1 (LE)
|
|
(byte)0x14, (byte)0x00, // desktopSaveYGranularity (ignored): 20 (LE)
|
|
(byte)0x00, (byte)0x00, // pad2octetsA (ignored)
|
|
(byte)0x01, (byte)0x00, // maximumOrderLevel: ORD_LEVEL_1_ORDERS (1)
|
|
(byte)0x00, (byte)0x00, // number of fonts (ignored): 0
|
|
(byte)0x4a, (byte)0x00, // orderFlags = 0x004a (LE), SOLIDPATTERNBRUSHONLY (0x40), ZEROBOUNDSDELTASSUPPORT (0x8, MUST), NEGOTIATEORDERSUPPORT (0x2, MUST)
|
|
// Order support: 32 bytes (no primary drawing orders are supported, so this array MUST be initialized to all zeros, use 0x01 for TRUE).
|
|
(byte)0x00, // TS_NEG_DSTBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_PATBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_SCRBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEMBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEM3BLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ATEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_AEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_DRAWNINEGRID_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_LINETO_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTI_DRAWNINEGRID_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_OPAQUERECT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_SAVEBITMAP_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEMBLT_R2_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MEM3BLT_R2_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIDSTBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIPATBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTISCRBLT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_MULTIOPAQUERECT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_FAST_INDEX_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYGON_SC_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYGON_CB_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_POLYLINE_INDEX: TRUE
|
|
(byte)0x00, // Unused: 0
|
|
(byte)0x00, // TS_NEG_FAST_GLYPH_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ELLIPSE_SC_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_ELLIPSE_CB_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_INDEX_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WLONGTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // TS_NEG_WLONGEXTTEXTOUT_INDEX: FALSE
|
|
(byte)0x00, // Unused: 0
|
|
(byte)0x00, (byte)0x00, // Text flags (ignored): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // Order support extra flags: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding 4 bytes
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Desktop save size (ignored): 0 (assumed to be 230400 bytes (480*480, 0x38400, LE))
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0xe4, (byte)0x04, // Text ANSI Code Page: 1252, ANSI - Latin I (0x04e4, LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
//
|
|
// Bitmap Cache Rev. 2 Capability Set (40 bytes), see http://msdn.microsoft.com/en-us/library/cc240560.aspx
|
|
(byte)0x13, (byte)0x00, // capability set type: CAPSTYPE_BITMAPCACHE_REV2 (19) (LE)
|
|
(byte)0x28, (byte)0x00, // length of capability set: 40 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // Cache flags: 0 (LE)
|
|
(byte)0x00, // Padding 1 byte
|
|
(byte)0x00, // Number of cell caches: 0
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache0 cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache1 cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache2 cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache3 cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Bitmap cache4 cell info: 0 (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding 12 bytes
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // Padding
|
|
|
|
//
|
|
// Color Table Cache Capability Set (8 bytes), see http://msdn.microsoft.com/en-us/library/cc241564.aspx
|
|
(byte)0x0a, (byte)0x00, // capability set type: CAPSTYPE_COLORCACHE (10) (LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x06, (byte)0x00, // Color table cache size (must be ignored during capability exchange and is assumed to be 0x0006): 6 (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
|
|
//
|
|
// Window Activation Capability Set (12 bytes), see http://msdn.microsoft.com/en-us/library/cc240569.aspx
|
|
(byte)0x07, (byte)0x00, // capability set type: CAPSTYPE_ACTIVATION (7) (LE)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // helpKeyFlag (should be set to FALSE (0)): FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // helpKeyIndexFlag (should be set to FALSE (0)): FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // helpExtendedKeyFlag (should be set to FALSE (0)): FALSE (0, LE)
|
|
(byte)0x00, (byte)0x00, // windowManagerKeyFlag (should be set to FALSE (0)): FALSE (0, LE)
|
|
|
|
//
|
|
// Control Capability Set (12 bytes), see http://msdn.microsoft.com/en-us/library/cc240568.aspx
|
|
(byte)0x05, (byte)0x00, // capability set type: CAPSTYPE_ACTIVATION (7)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // controlFlags (should be set to 0): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // remoteDetachFlag (should be set to 0): 0 (LE)
|
|
(byte)0x02, (byte)0x00, // controlInterest (should be set to CONTROLPRIORITY_NEVER): CONTROLPRIORITY_NEVER (2) (LE)
|
|
(byte)0x02, (byte)0x00, // detachInterest (should be set to CONTROLPRIORITY_NEVER): CONTROLPRIORITY_NEVER (2) (LE)
|
|
|
|
//
|
|
// Pointer Capability Set (10 bytes), see http://msdn.microsoft.com/en-us/library/cc240562.aspx
|
|
(byte)0x08, (byte)0x00, // capability set type: CAPSTYPE_POINTER (8, LE)
|
|
(byte)0x0a, (byte)0x00, // length of capability set: 10 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // colorPointerFlag: FALSE (LE)
|
|
(byte)0x00, (byte)0x00, // colorPointerCacheSize: 0 (LE)
|
|
(byte)0x14, (byte)0x00, // pointerCacheSize: 20 (LE)
|
|
|
|
//
|
|
// Share Capability Set (8 bytes), see http://msdn.microsoft.com/en-us/library/cc240570.aspx
|
|
(byte)0x09, (byte)0x00, // capability set type: CAPSTYPE_SHARE (9, LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, // nodeID (must be set to 0 by client): 0 (LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes (LE)
|
|
|
|
//
|
|
// Input Capability Set (88 bytes), see http://msdn.microsoft.com/en-us/library/cc240563.aspx
|
|
(byte)0x0d, (byte)0x00, // capability set type: CAPSTYPE_INPUT (13, LE)
|
|
(byte)0x58, (byte)0x00, // length of capability set: 88 bytes (LE)
|
|
(byte)0x35, (byte)0x00, // inputFlags: 0x0035 (LE), INPUT_FLAG_FASTPATH_INPUT2 (0x20), INPUT_FLAG_VKPACKET (0x10), INPUT_FLAG_MOUSEX (0x4), INPUT_FLAG_SCANCODES (0x1)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
(byte)0x09, (byte)0x04, (byte)0x00, (byte)0x00, // keyboardLayout: "US" keyboard layout (0x000409, LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // keyboardType: unknown (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // keyboardSubType: unknown (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // keyboardFunctionKey: unknown (LE)
|
|
// imeFileName: "", (64 bytes, including trailing NULL characters, UCS2)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
|
|
//
|
|
// Brush Capability Set (8 bytes), see http://msdn.microsoft.com/en-us/library/cc240564.aspx
|
|
(byte)0x0f, (byte)0x00, // capability set type: CAPSTYPE_BRUSH (15, LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // brushSupportLevel: BRUSH_DEFAULT (0x0, LE)
|
|
|
|
//
|
|
// Sound Capability Set (8 bytes), see http://msdn.microsoft.com/en-us/library/cc240552.aspx
|
|
(byte)0x0c, (byte)0x00, // capability set type: CAPSTYPE_SOUND (12, LE)
|
|
(byte)0x08, (byte)0x00, // length of capability set: 8 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // soundFlags: 0x0000 (LE) // SOUND_FLAG_BEEPS (0x1)
|
|
|
|
//
|
|
// Font Capability Set (8 bytes), see http://msdn.microsoft.com/en-us/library/cc240571.aspx
|
|
(byte)0x0e, (byte)0x00,
|
|
(byte)0x08, (byte)0x00,
|
|
(byte)0x01, (byte)0x00, (byte)0x00, (byte)0x00,
|
|
|
|
//
|
|
// Offscreen Bitmap Cache Capability Set (12 bytes), see http://msdn.microsoft.com/en-us/library/cc240550.aspx
|
|
(byte)0x11, (byte)0x00, // capability set type: CAPSTYPE_OFFSCREENCACHE (17, LE)
|
|
(byte)0x0c, (byte)0x00, // length of capability set: 12 bytes (LE)
|
|
(byte)0x00, (byte)0x00, (byte)0x00, (byte)0x00, // offscreenSupportLevel: FALSE (LE)
|
|
(byte)0x00, (byte)0x00, // offscreenCacheSize: 0 (LE)
|
|
(byte)0x00, (byte)0x00, // offscreenCacheEntries: 0 (LE)
|
|
|
|
//
|
|
// Glyph Cache Capability Set (52 bytes), see http://msdn.microsoft.com/en-us/library/cc240565.aspx
|
|
(byte)0x10, (byte)0x00, // capability set type: CAPSTYPE_OFFSCREENCACHE (16, LE)
|
|
(byte)0x34, (byte)0x00, // length of capability set: 52 bytes (LE)
|
|
// Glyph Cache (40 bytes)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x04, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x04, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x08, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x08, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x10, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x20, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x40, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x80, (byte)0x00, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0xfe, (byte)0x00, // CacheEntries: 254 (LE)
|
|
(byte)0x00, (byte)0x01, // CacheMaximumCellSize: 4 (LE)
|
|
(byte)0x40, (byte)0x00, // CacheEntries: 64 (LE)
|
|
(byte)0x00, (byte)0x08, // CacheMaximumCellSize: 2048 (LE)
|
|
// FragCache
|
|
(byte)0x00, (byte)0x01, // CacheEntries: 256 (LE)
|
|
(byte)0x00, (byte)0x01, // CacheMaximumCellSize: 256 (LE)
|
|
//
|
|
(byte)0x00, (byte)0x00, // GlyphSupportLevel: GLYPH_SUPPORT_NONE (0x0, LE)
|
|
(byte)0x00, (byte)0x00, // Padding 2 bytes
|
|
};
|
|
/* @formatter:on */
|
|
|
|
RdpState rdpState = new RdpState();
|
|
ScreenDescription screenDescription = new ScreenDescription();
|
|
screenDescription.setFramebufferSize(1024, 768);
|
|
|
|
rdpState.serverShareId = 0x000103ea;
|
|
|
|
MockSource source = new MockSource("source", ByteBuffer.convertByteArraysToByteBuffers(new byte[] {}));
|
|
Element confirm_active = new ClientConfirmActivePDU("confirm_active", screenDescription, rdpState);
|
|
Element sink = new MockSink("sink", ByteBuffer.convertByteArraysToByteBuffers(packet));
|
|
|
|
Pipeline pipeline = new PipelineImpl("test");
|
|
pipeline.add(source, confirm_active, sink);
|
|
pipeline.link("source", "confirm_active", "sink");
|
|
pipeline.runMainLoop("source", STDOUT, false, false);
|
|
}
|
|
|
|
}
|