?? rfbproto.java
字號:
updateRectH = is.readUnsignedShort();
updateRectEncoding = is.readInt();
if (updateRectEncoding == EncodingZlib
|| updateRectEncoding == EncodingTight)
wereZlibUpdates = true;
// If the session is being recorded:
if (rec != null) {
if (numUpdatesInSession > 1)
rec.flush(); // Flush the output on each rectangle.
rec.writeShortBE(updateRectX);
rec.writeShortBE(updateRectY);
rec.writeShortBE(updateRectW);
rec.writeShortBE(updateRectH);
if (updateRectEncoding == EncodingZlib && !recordFromBeginning) {
// Here we cannot write Zlib-encoded rectangles because the
// decoder won't be able to reproduce zlib stream state.
if (!zlibWarningShown) {
System.out.println(
"Warning: Raw encoding will be used "
+ "instead of Zlib in recorded session.");
zlibWarningShown = true;
}
rec.writeIntBE(EncodingRaw);
} else {
rec.writeIntBE(updateRectEncoding);
if (updateRectEncoding == EncodingTight
&& !recordFromBeginning
&& !tightWarningShown) {
System.out.println(
"Warning: Re-compressing Tight-encoded "
+ "updates for session recording.");
tightWarningShown = true;
}
}
}
if (updateRectEncoding == EncodingLastRect
|| updateRectEncoding == EncodingNewFBSize)
return;
if (updateRectX + updateRectW > framebufferWidth
|| updateRectY + updateRectH > framebufferHeight) {
throw new Exception(
"Framebuffer update rectangle too large: "
+ updateRectW
+ "x"
+ updateRectH
+ " at ("
+ updateRectX
+ ","
+ updateRectY
+ ")");
}
}
// Read CopyRect source X and Y.
int copyRectSrcX, copyRectSrcY;
void readCopyRect() throws IOException {
copyRectSrcX = is.readUnsignedShort();
copyRectSrcY = is.readUnsignedShort();
// If the session is being recorded:
if (rec != null) {
rec.writeShortBE(copyRectSrcX);
rec.writeShortBE(copyRectSrcY);
}
}
//
// Read a ServerCutText message
//
String readServerCutText() throws IOException {
byte[] pad = new byte[3];
is.readFully(pad);
int len = is.readInt();
byte[] text = new byte[len];
is.readFully(text);
return new String(text);
}
//
// Read an integer in compact representation (1..3 bytes).
// Such format is used as a part of the Tight encoding.
// Also, this method records data if session recording is active and
// the viewer's recordFromBeginning variable is set to true.
//
int readCompactLen() throws IOException {
int[] portion = new int[3];
portion[0] = is.readUnsignedByte();
int byteCount = 1;
int len = portion[0] & 0x7F;
if ((portion[0] & 0x80) != 0) {
portion[1] = is.readUnsignedByte();
byteCount++;
len |= (portion[1] & 0x7F) << 7;
if ((portion[1] & 0x80) != 0) {
portion[2] = is.readUnsignedByte();
byteCount++;
len |= (portion[2] & 0xFF) << 14;
}
}
if (rec != null && recordFromBeginning)
for (int i = 0; i < byteCount; i++)
rec.writeByte(portion[i]);
return len;
}
//Author: Kenn Min Chong/////////////////////////////////////////////
//Read/Write a rfbFileTransferMsg
/*typedef struct _rfbFileTransferMsg {
CARD8 type; // always rfbFileTransfer
CARD8 contentType; // See defines below
CARD16 contentParam;// Other possible content classification (Dir or File name, etc..)
CARD32 size; // FileSize or packet index or error or other
CARD32 length;
// followed by data char text[length]
} rfbFileTransferMsg;
*/
// Parsing Rfb message to see what type
void readRfbFileTransferMsg() throws IOException
{
int contentType = is.readUnsignedByte();
int contentParamT = is.readUnsignedByte();
int contentParam = contentParamT;
contentParamT = is.readUnsignedByte();
contentParamT = contentParamT << 8;
contentParam = contentParam | contentParamT;
if (contentType == rfbRDrivesList || contentType == rfbDirPacket)
{
readDriveOrDirectory(contentParam);
}
else if (contentType == rfbFileHeader)
{
receiveFileHeader();
}
else if (contentType == rfbFilePacket)
{
receiveFileChunk();
}
else if (contentType == rfbEndOfFile)
{
endOfReceiveFile(true); // Ok
}
else if (contentType == rfbAbortFileTransfer)
{
if (fFileReceptionRunning)
{
endOfReceiveFile(false); // Error
}
else
{
// sf@2004 - Todo: Add TestPermission
// System.out.println("File Transfer Aborted!");
}
}
else if (contentType == rfbCommandReturn)
{
createDirectoryorDeleteFile(contentParam);
}
else if (contentType == rfbFileAcceptHeader)
{
sendFile();
}
else if (contentType == rfbFileChecksums)
{
ReceiveDestinationFileChecksums();
}
else
{
System.out.println("ContentType: " + contentType);
}
}
//Refactored from readRfbFileTransferMsg()
public void createDirectoryorDeleteFile(int contentParam)
throws IOException {
if (contentParam == rfbADirCreate)
{
createRemoteDirectoryFeedback();
}
else if (contentParam == rfbAFileDelete)
{
deleteRemoteFileFeedback();
}
}
//Refactored from readRfbFileTransferMsg()
public void readDriveOrDirectory(int contentParam) throws IOException {
if (contentParam == rfbADrivesList)
{
readFTPMsgDriveList();
}
else if (contentParam == rfbADirectory && !inDirectory2)
{
inDirectory2 = true;
readFTPMsgDirectoryList();
}
else if (contentParam == rfbADirectory && inDirectory2)
{
readFTPMsgDirectoryListContent();
}
else if (contentParam == 0)
{
readFTPMsgDirectoryListEndContent();
inDirectory2 = false;
}
else
{
System.out.println("ContentParam: " + contentParam);
}
}
// Internally used. Write an Rfb message to the server
void writeRfbFileTransferMsg(
int contentType,
int contentParam,
long size, // 0 : compression not supported - 1 : compression supported
long length,
String text) throws IOException
{
byte b[] = new byte[12];
b[0] = (byte) rfbFileTransfer;
b[1] = (byte) contentType;
b[2] = (byte) contentParam;
byte by = 0;
long c = 0;
length++;
c = size & 0xFF000000;
by = (byte) (c >>> 24);
b[4] = by;
c = size & 0xFF0000;
by = (byte) (c >>> 16);
b[5] = by;
c = size & 0xFF00;
by = (byte) (c >>> 8);
b[6] = by;
c = size & 0xFF;
by = (byte) c;
b[7] = by;
c = length & 0xFF000000;
by = (byte) (c >>> 24);
b[8] = by;
c = length & 0xFF0000;
by = (byte) (c >>> 16);
b[9] = by;
c = length & 0xFF00;
by = (byte) (c >>> 8);
b[10] = by;
c = length & 0xFF;
by = (byte) c;
b[11] = by;
os.write(b);
if (text != null)
{
byte byteArray[] = text.getBytes();
byte byteArray2[] = new byte[byteArray.length + 1];
for (int i = 0; i < byteArray.length; i++) {
byteArray2[i] = byteArray[i];
}
byteArray2[byteArray2.length - 1] = 0;
os.write(byteArray2);
}
}
//Internally used. Write an rfb message to the server for sending files ONLY
int writeRfbFileTransferMsgForSendFile(
int contentType,
int contentParam,
long size,
long length,
String source
) throws IOException
{
File f = new File(source);
fis = new FileInputStream(f);
byte byteBuffer[] = new byte[sz_rfbBlockSize];
int bytesRead = fis.read(byteBuffer);
long counter=0;
boolean fError = false;
// sf@ - Manage compression
boolean fCompress = true;
Deflater myDeflater = new Deflater();
byte[] CompressionBuffer = new byte[sz_rfbBlockSize + 1024];
int compressedSize = 0;
while (bytesRead!=-1)
{
counter += bytesRead;
myDeflater.setInput(byteBuffer, 0, bytesRead);
myDeflater.finish();
compressedSize = myDeflater.deflate(CompressionBuffer);
myDeflater.reset();
// If the compressed data is larger than the original one, we're dealing with
// already compressed data
if (compressedSize > bytesRead)
fCompress = false;
this.writeRfbFileTransferMsg(
contentType,
contentParam,
(fCompress ? 1 : 0),
(fCompress ? compressedSize-1 : bytesRead-1),
null
);
// Todo: Test write error !
os.write(
fCompress ? CompressionBuffer : byteBuffer,
0,
fCompress ? compressedSize : bytesRead
);
// Todo: test read error !
bytesRead = fis.read(byteBuffer);
// viewer.ftp.connectionStatus.setText("Sent: "+ counter + " bytes of "+ f.length() + " bytes");
viewer.ftp.jProgressBar.setValue((int)((counter * 100) / f.length()));
viewer.ftp.connectionStatus.setText(">>> Sending File: " + source + " - Size: " + f.length() + " bytes - Progress: " + ((counter * 100) / f.length()) + "%");
if (fAbort == true)
{
fAbort = false;
fError = true;
break;
}
try
{
Thread.sleep(5);
}
catch(InterruptedException e)
{
System.err.println("Interrupted");
}
}
writeRfbFileTransferMsg(fError ? rfbAbortFileTransfer : rfbEndOfFile, 0, 0, 0, null);
fis.close();
return (fError ? -1 : 1);
}
//This method is internally used to send the file to the server once the server is ready
void sendFile()
{
try
{
viewer.ftp.disableButtons();
int size = is.readInt();
int length = is.readInt();
for (int i = 0; i < length; i++)
{
System.out.print((char) is.readUnsignedByte());
}
int ret = writeRfbFileTransferMsgForSendFile(
rfbFilePacket,
0,
0,
0,
sendFileSource);
viewer.ftp.refreshRemoteLocation();
if (ret != 1)
{
viewer.ftp.connectionStatus.setText(" > Error - File NOT sent");
viewer.ftp.historyComboBox.insertItemAt(new String(" > Error - File: <" + sendFileSource) + "> was not correctly sent (aborted by user or error)",0);
}
else
{
viewer.ftp.connectionStatus.setText(" > File sent");
viewer.ftp.historyComboBox.insertItemAt(new String(" > File: <" + sendFileSource) + "> was sent to Remote Machine",0);
}
viewer.ftp.historyComboBox.setSelectedIndex(0);
viewer.ftp.enableButtons();
}
catch (IOException e)
{
System.err.println(e);
}
}
//Call this method to send a file from local pc to server
void offerLocalFile(String source, String destinationPath)
{
try
{
sendFileSource = source;
File f = new File(source);
// sf@2004 - Add support for huge files
long lSize = f.length();
int iLowSize = (int)(lSize & 0x00000000FFFFFFFF);
int iHighSize = (int)(lSize >> 32);
String temp = destinationPath + f.getName();
writeRfbFileTransferMsg(
rfbFileTransferOffer,
0,
iLowSize, // f.length(),
temp.length(),
temp);
// sf@2004 - Send the high part of the size
byte b[] = new byte[4];
byte by = 0;
long c = 0;
c = iHighSize & 0xFF000000;
by = (byte) (c >>> 24);
b[0] = by;
c = iHighSize & 0xFF0000;
by = (byte) (c >>> 16);
b[1] = by;
c = iHighSize & 0xFF00;
by = (byte) (c >>> 8);
b[2] = by;
c = iHighSize & 0xFF;
by = (byte) c;
b[3] = by;
os.write(b);
}
catch (IOException e)
{
System.err.println(e);
}
}
//Internally used.
//Handles acknowledgement that the file has been deleted on the server
void deleteRemoteFileFeedback() throws IOException
{
is.readInt();
int length = is.readInt();
String f = "";
for (int i = 0; i < length; i++)
{
f += (char)is.readUnsignedByte();
}
viewer.ftp.refreshRemoteLocation();
viewer.ftp.historyComboBox.insertItemAt(new String(" > Deleted File On Remote Machine: " + f.substring(0, f.length()-1)),0);
viewer.ftp.historyComboBox.setSelectedIndex(0);
}
//Call this method to delete a file at server
void deleteRemoteFile(String text)
{
try
{
String temp = text;
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -