📄 rdp.java
字号:
*/
protected int processDisconnectPdu(RdpPacket_Localised data) {
logger.debug("Received disconnect PDU");
return data.getLittleEndian32();
}
/**
* Initialise RDP comms layer, and register virtual channels
* @param channels Virtual channels to be used in connection
*/
public Rdp(VChannels channels) {
this.SecureLayer = new Secure(channels);
Common.secure = SecureLayer;
this.orders = new Orders();
this.cache = new Cache();
orders.registerCache(cache);
}
/**
* Initialise a packet for sending data on the RDP layer
* @param size Size of RDP data
* @return Packet initialised for RDP
* @throws RdesktopException
*/
private RdpPacket_Localised initData(int size) throws RdesktopException {
RdpPacket_Localised buffer = null;
buffer = SecureLayer.init(
Constants.encryption ? Secure.SEC_ENCRYPT : 0, size + 18);
buffer.pushLayer(RdpPacket_Localised.RDP_HEADER, 18);
// buffer.setHeader(RdpPacket_Localised.RDP_HEADER);
// buffer.incrementPosition(18);
// buffer.setStart(buffer.getPosition());
return buffer;
}
/**
* Send a packet on the RDP layer
* @param data Packet to send
* @param data_pdu_type Type of data
* @throws RdesktopException
* @throws IOException
* @throws CryptoException
*/
private void sendData(RdpPacket_Localised data, int data_pdu_type)
throws RdesktopException, IOException, CryptoException {
CommunicationMonitor.lock(this);
int length;
data.setPosition(data.getHeader(RdpPacket_Localised.RDP_HEADER));
length = data.getEnd() - data.getPosition();
data.setLittleEndian16(length);
data.setLittleEndian16(RDP_PDU_DATA | 0x10);
data.setLittleEndian16(SecureLayer.getUserID() + 1001);
data.setLittleEndian32(this.rdp_shareid);
data.set8(0); // pad
data.set8(1); // stream id
data.setLittleEndian16(length - 14);
data.set8(data_pdu_type);
data.set8(0); // compression type
data.setLittleEndian16(0); // compression length
SecureLayer.send(data, Constants.encryption ? Secure.SEC_ENCRYPT : 0);
CommunicationMonitor.unlock(this);
}
/**
* Receive a packet from the RDP layer
* @param type Type of PDU received, stored in type[0]
* @return Packet received from RDP layer
* @throws IOException
* @throws RdesktopException
* @throws CryptoException
* @throws OrderException
*/
private RdpPacket_Localised receive(int[] type) throws IOException,
RdesktopException, CryptoException, OrderException {
int length = 0;
if ((this.stream == null) || (this.next_packet >= this.stream.getEnd())) {
this.stream = SecureLayer.receive();
if (stream == null)
return null;
this.next_packet = this.stream.getPosition();
} else {
this.stream.setPosition(this.next_packet);
}
length = this.stream.getLittleEndian16();
/* 32k packets are really 8, keepalive fix - rdesktop 1.2.0 */
if (length == 0x8000) {
logger.warn("32k packet keepalive fix");
next_packet += 8;
type[0] = 0;
return stream;
}
type[0] = this.stream.getLittleEndian16() & 0xf;
if (stream.getPosition() != stream.getEnd()) {
stream.incrementPosition(2);
}
this.next_packet += length;
return stream;
}
/**
* Connect to a server
* @param username Username for log on
* @param server Server to connect to
* @param flags Flags defining logon type
* @param domain Domain for log on
* @param password Password for log on
* @param command Alternative shell for session
* @param directory Initial working directory for connection
* @throws ConnectionException
*/
public void connect(String username, InetAddress server, int flags,
String domain, String password, String command, String directory)
throws ConnectionException {
try {
SecureLayer.connect(server);
this.connected = true;
this.sendLogonInfo(flags, domain, username, password, command,
directory);
}
// Handle an unresolvable hostname
catch (UnknownHostException e) {
throw new ConnectionException("Could not resolve host name: "
+ server);
}
// Handle a refused connection
catch (ConnectException e) {
throw new ConnectionException(
"Connection refused when trying to connect to " + server
+ " on port " + Options.port);
}
// Handle a timeout on connecting
catch (NoRouteToHostException e) {
throw new ConnectionException(
"Connection timed out when attempting to connect to "
+ server);
} catch (IOException e) {
throw new ConnectionException("Connection Failed");
} catch (RdesktopException e) {
throw new ConnectionException(e.getMessage());
} catch (OrderException e) {
throw new ConnectionException(e.getMessage());
} catch (CryptoException e) {
throw new ConnectionException(e.getMessage());
}
}
/**
* Disconnect from an RDP session
*/
public void disconnect() {
this.connected = false;
SecureLayer.disconnect();
}
/**
* Retrieve status of connection
* @return True if connection to RDP session
*/
public boolean isConnected() {
return this.connected;
}
boolean deactivated;
int ext_disc_reason;
/**
* RDP receive loop
* @param deactivated On return, stores true in deactivated[0] if the session disconnected cleanly
* @param ext_disc_reason On return, stores the reason for disconnection in ext_disc_reason[0]
* @throws IOException
* @throws RdesktopException
* @throws OrderException
* @throws CryptoException
*/
public void mainLoop(boolean[] deactivated, int[] ext_disc_reason)
throws IOException, RdesktopException, OrderException,
CryptoException {
int[] type = new int[1];
boolean disc = false; /* True when a disconnect PDU was received */
boolean cont = true;
RdpPacket_Localised data = null;
while (cont) {
try {
data = this.receive(type);
if (data == null)
return;
} catch (EOFException e) {
return;
}
switch (type[0]) {
case (Rdp.RDP_PDU_DEMAND_ACTIVE):
logger.debug("Rdp.RDP_PDU_DEMAND_ACTIVE");
// get this after licence negotiation, just before the 1st
// order...
NDC.push("processDemandActive");
this.processDemandActive(data);
// can use this to trigger things that have to be done before
// 1st order
logger.debug("ready to send (got past licence negotiation)");
Rdesktop.readytosend = true;
frame.triggerReadyToSend();
NDC.pop();
deactivated[0] = false;
break;
case (Rdp.RDP_PDU_DEACTIVATE):
// get this on log off
deactivated[0] = true;
this.stream = null; // ty this fix
break;
case (Rdp.RDP_PDU_DATA):
logger.debug("Rdp.RDP_PDU_DATA");
// all the others should be this
NDC.push("processData");
disc = this.processData(data, ext_disc_reason);
NDC.pop();
break;
case 0:
break; // 32K keep alive fix, see receive() - rdesktop 1.2.0.
default:
throw new RdesktopException("Unimplemented type in main loop :"
+ type[0]);
}
if (disc)
return;
}
return;
}
/**
* Send user logon details to the server
* @param flags Set of flags defining logon type
* @param domain Domain for logon
* @param username Username for logon
* @param password Password for logon
* @param command Alternative shell for session
* @param directory Starting working directory for session
* @throws RdesktopException
* @throws IOException
* @throws CryptoException
*/
private void sendLogonInfo(int flags, String domain, String username,
String password, String command, String directory)
throws RdesktopException, IOException, CryptoException {
int len_ip = 2 * "127.0.0.1".length();
int len_dll = 2 * "C:\\WINNT\\System32\\mstscax.dll".length();
int packetlen = 0;
int sec_flags = Constants.encryption ? (Secure.SEC_LOGON_INFO | Secure.SEC_ENCRYPT)
: Secure.SEC_LOGON_INFO;
int domainlen = 2 * domain.length();
int userlen = 2 * username.length();
int passlen = 2 * password.length();
int commandlen = 2 * command.length();
int dirlen = 2 * directory.length();
RdpPacket_Localised data;
if (!Options.use_rdp5 || 1 == Options.server_rdp_version) {
logger.debug("Sending RDP4-style Logon packet");
data = SecureLayer.init(sec_flags, 18 + domainlen + userlen
+ passlen + commandlen + dirlen + 10);
data.setLittleEndian32(0);
data.setLittleEndian32(flags);
data.setLittleEndian16(domainlen);
data.setLittleEndian16(userlen);
data.setLittleEndian16(passlen);
data.setLittleEndian16(commandlen);
data.setLittleEndian16(dirlen);
data.outUnicodeString(domain, domainlen);
data.outUnicodeString(username, userlen);
data.outUnicodeString(password, passlen);
data.outUnicodeString(command, commandlen);
data.outUnicodeString(directory, dirlen);
} else {
flags |= RDP_LOGON_BLOB;
logger.debug("Sending RDP5-style Logon packet");
packetlen = 4
+ // Unknown uint32
4
+ // flags
2
+ // len_domain
2
+ // len_user
((flags & RDP_LOGON_AUTO) != 0 ? 2 : 0)
+ // len_password
((flags & RDP_LOGON_BLOB) != 0 ? 2 : 0)
+ // Length of BLOB
2
+ // len_program
2
+ // len_directory
(0 < domainlen ? domainlen + 2 : 2)
+ // domain
userlen
+ ((flags & RDP_LOGON_AUTO) != 0 ? passlen : 0)
+ 0
+ // We have no 512 byte BLOB. Perhaps we must?
((flags & RDP_LOGON_BLOB) != 0
&& (flags & RDP_LOGON_AUTO) == 0 ? 2 : 0)
+ (0 < commandlen ? commandlen + 2 : 2)
+ (0 < dirlen ? dirlen + 2 : 2) + 2 + // Unknown (2)
2 + // Client ip length
len_ip + // Client ip
2 + // DLL string length
len_dll + // DLL string
2 + // Unknown
2 + // Unknown
64 + // Time zone #0
20 + // Unknown
64 + // Time zone #1
32 + 6; // Unknown
data = SecureLayer.init(sec_flags, packetlen); // s =
// sec_init(sec_flags,
// packetlen);
// logger.debug("Called sec_init with packetlen " + packetlen);
data.setLittleEndian32(0); // out_uint32(s, 0); // Unknown
data.setLittleEndian32(flags); // out_uint32_le(s, flags);
data.setLittleEndian16(domainlen); // out_uint16_le(s, len_domain);
data.setLittleEndian16(userlen); // out_uint16_le(s, len_user);
if ((flags & RDP_LOGON_AUTO) != 0) {
data.setLittleEndian16(passlen); // out_uint16_le(s,
// len_password);
}
if ((flags & RDP_LOGON_BLOB) != 0
&& ((flags & RDP_LOGON_AUTO) == 0)) {
data.setLittleEndian16(0); // out_uint16_le(s, 0);
}
data.setLittleEndian16(commandlen); // out_uint16_le(s,
// len_program);
data.setLittleEndian16(dirlen); // out_uint16_le(s, len_directory);
if (0 < domainlen)
data.outUnicodeString(domain, domainlen); // rdp_out_unistr(s,
// domain,
// len_domain);
else
data.setLittleEndian16(0); // out_uint16_le(s, 0);
data.outUnicodeString(username, userlen); // rdp_out_unistr(s,
// user, len_user);
if ((flags & RDP_LOGON_AUTO) != 0) {
data.outUnicodeString(password, passlen); // rdp_out_unistr(s,
// password,
// len_password);
}
if ((flags & RDP_LOGON_BLOB) != 0 && (flags & RDP_LOGON_AUTO) == 0) {
data.setLittleEndian16(0); // out_uint16_le(s, 0);
}
if (0 < commandlen) {
data.outUnicodeString(command, commandlen); // rdp_out_unistr(s,
// program,
// len_program);
} else {
data.setLittleEndian16(0); // out_uint16_le(s, 0);
}
if (0 < dirlen) {
data.outUnicodeString(directory, dirlen); // rdp_out_unistr(s,
// directory,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -