4#include "rfb/SSecurityVncAuth.h"
5#include "rfb/SMsgWriter.h"
6#include "rfb/screenTypes.h"
7#include "rfb/fenceTypes.h"
8#include "RabbitCommonTools.h"
10#include "InputDevice.h"
12#include <QApplication>
14#include <QLoggingCategory>
15Q_DECLARE_LOGGING_CATEGORY(RabbitVNC)
19 const char* file =
"/home/build-RabbitRemoteControl-Desktop_Qt_5_12_11_GCC_64bit-Debug/password";
20 char* pPass =
new char[9];
21 strcpy(pPass,
"123456");
22 rfb::PlainPasswd password(pPass);
23 rfb::ObfuscatedPasswd oPassword(password);
28 out.write(oPassword.takeBuf(), oPassword.length);
31 rfb::SSecurityVncAuth::vncAuthPasswdFile.setParam(file);
33bool g_setfile =
false;
35CConnection::CConnection(QSharedPointer<CChannel> channel,
37 : QObject(), rfb::SConnection(),
40 m_PixelFormat(32, 24, false, true, 255, 255, 255, 16, 8, 0),
41 inProcessMessages(false),
42 pendingSyncFence(false),
47 m_EncodeManager(this),
48 continuousUpdates(false)
52 check = connect(m_Channel.data(), SIGNAL(sigConnected()),
53 this, SLOT(slotConnected()));
55 check = connect(m_Channel.data(), SIGNAL(readyRead()),
56 this, SLOT(slotReadyRead()));
58 check = connect(m_Channel.data(), SIGNAL(sigDisconnected()),
59 this, SLOT(slotDisconnected()));
61 check = connect(m_Channel.data(), SIGNAL(sigError(
int,
const QString&)),
62 this, SLOT(slotError(
int,
const QString&)));
65 m_InputDevice = CInputDevice::GenerateObject();
68CConnection::~CConnection()
70 qDebug(RabbitVNC) <<
"CConnection::~CConnection";
73void CConnection::slotConnected()
76 m_InStream = QSharedPointer<rdr::InStream>(
new CInStreamChannel(m_Channel.data()));
77 m_OutStream = QSharedPointer<rdr::OutStream>(
new COutStreamChannel(m_Channel.data()));
78 setStreams(m_InStream.data(), m_OutStream.data());
80 char* pass =
new char[128];
81 strcpy(pass, m_pPara->getPassword().toStdString().c_str());
82 rfb::PlainPasswd password(pass);
83 rfb::ObfuscatedPasswd oPassword(password);
84 rfb::SSecurityVncAuth::vncAuthPasswd.setParam(oPassword.buf, oPassword.length);
86 client.setDimensions(CDesktop::Instance()->Width(), CDesktop::Instance()->Height());
89 }
catch(rdr::Exception& e) {
90 std::string szErr (
"initialistProtocol() fail:");
92 qCritical(RabbitVNC) << szErr.c_str();
93 emit sigError(-1, szErr.c_str());
94 }
catch(std::exception& e) {
95 std::string szErr (
"initialistProtocol() fail:");
97 qCritical(RabbitVNC) << szErr.c_str();
98 emit sigError(-1, szErr.c_str());
100 std::string szErr (
"initialistProtocol() fail.");
101 qCritical(RabbitVNC) << szErr.c_str();
102 emit sigError(-1, szErr.c_str());
106void CConnection::slotReadyRead()
108 qDebug(RabbitVNC) <<
"CConnection::slotReadyRead()";
109 if (state() == RFBSTATE_CLOSING)
return;
111 inProcessMessages =
true;
115 getOutStream()->cork(
true);
118 if (pendingSyncFence)
125 writer()->writeFence(fenceFlags, fenceDataLen, fenceData);
127 pendingSyncFence =
false;
132 getOutStream()->cork(
false);
134 inProcessMessages =
false;
141 QImage img = CDesktop::Instance()->GetDesktop();
142 slotDesktopUpdate(img, img.rect());
144 }
catch (rdr::Exception e) {
145 qCritical(RabbitVNC) <<
"Exception:" << e.str();
146 emit sigError(-1, QString(
"processMsg exception:") + e.str());
147 }
catch (std::exception e) {
148 qCritical(RabbitVNC) <<
"std Exception:" << e.what();
149 emit sigError(-1, QString(
"std Exception:") + e.what());
151 qCritical(RabbitVNC) <<
"exception";
152 emit sigError(-1, QString(
"Exception:"));
156void CConnection::slotDisconnected()
158 qDebug(RabbitVNC) <<
"The connect disconnect";
159 emit sigDisconnected();
162void CConnection::slotError(
int nErr,
const QString& szErr)
164 emit sigError(nErr, szErr);
167void CConnection::queryConnection(
const char *userName)
169 qDebug(RabbitVNC) <<
"queryConnection:" << userName;
171 SConnection::queryConnection(userName);
174void CConnection::authSuccess()
176 qDebug(RabbitVNC) <<
"CConnection::authSuccess(): state:" << state();
178 QString name = RabbitCommon::CTools::GetHostName()
179 +
"@" + RabbitCommon::CTools::GetCurrentUser();
180 client.setName(name.toStdString().c_str());
185 int w = CDesktop::Instance()->Width();
186 int h = CDesktop::Instance()->Height();
187 client.setDimensions(w, h);
188 client.setPF(m_PixelFormat);
190 client.pf().print(buffer, 256);
191 qInfo(RabbitVNC) <<
"Set server pixel format:" << buffer <<
"width:" << w <<
"height:" << h;
194 m_Updates.add_changed(rfb::Rect(0, 0, w, w));
197void CConnection::clientInit(
bool shared)
199 qInfo(RabbitVNC) <<
"clientInit shared:" << shared;
200 SConnection::clientInit(shared);
202 bool check = connect(CDesktop::Instance(), SIGNAL(sigUpdate(QImage, QRect)),
203 this, SLOT(slotDesktopUpdate(QImage, QRect)));
207void CConnection::setDesktopSize(
int fb_width,
int fb_height,
const rfb::ScreenSet &layout)
209 qInfo(RabbitVNC) <<
"setDesktopSize: " << fb_width << fb_height;
214 writer()->writeDesktopSize(rfb::reasonClient, rfb::resultSuccess);
217void CConnection::setPixelFormat(
const rfb::PixelFormat &pf)
219 SConnection::setPixelFormat(pf);
221 pf.print(buffer, 256);
222 qDebug(RabbitVNC) <<
"Set pixel format:" << buffer;
228void CConnection::framebufferUpdateRequest(
const rfb::Rect &r,
bool incremental)
234 if (!accessCheck(AccessView))
return;
236 SConnection::framebufferUpdateRequest(r, incremental);
240 if (!r.enclosed_by(rfb::Rect(0, 0, client.width(), client.height()))) {
241 qCritical(RabbitVNC,
"FramebufferUpdateRequest %dx%d at %d,%d exceeds framebuffer %dx%d",
242 r.width(), r.height(), r.tl.x, r.tl.y,
243 client.width(), client.height());
244 safeRect = r.intersect(rfb::Rect(0, 0, client.width(), client.height()));
251 rfb::Region reqRgn(safeRect);
252 if (!incremental || !continuousUpdates)
253 requested.assign_union(reqRgn);
257 m_Updates.add_changed(reqRgn);
261 if (client.supportsEncoding(rfb::pseudoEncodingExtendedDesktopSize))
262 writer()->writeDesktopSize(rfb::reasonServer);
271void CConnection::fence(rdr::U32 flags,
unsigned len,
const char data[])
273 qDebug(RabbitVNC,
"fence: flags:%d,len:%d", flags, len);
276 if (flags & rfb::fenceFlagRequest) {
277 if (flags & rfb::fenceFlagSyncNext) {
278 pendingSyncFence =
true;
280 fenceFlags = flags & (rfb::fenceFlagBlockBefore | rfb::fenceFlagBlockAfter | rfb::fenceFlagSyncNext);
285 fenceData =
new char[len];
286 memcpy(fenceData, data, len);
293 flags = flags & (rfb::fenceFlagBlockBefore | rfb::fenceFlagBlockAfter);
295 writer()->writeFence(flags, len, data);
300 qCritical(RabbitVNC,
"Fence response of unexpected size received");
312 qCritical(RabbitVNC) <<
"Fence response of unexpected type received";
316void CConnection::enableContinuousUpdates(
bool enable,
int x,
int y,
int w,
int h)
318 qDebug(RabbitVNC,
"enableContinuousUpdates: %d, %d,%d,%d,%d",
324 if (!client.supportsFence() || !client.supportsContinuousUpdates())
325 throw rdr::Exception(
"Client tried to enable continuous updates when not allowed");
327 continuousUpdates = enable;
329 rect.setXYWH(x, y, w, h);
330 cuRegion.reset(rect);
335 writer()->writeEndOfContinuousUpdates();
339void CConnection::keyEvent(rdr::U32 keysym, rdr::U32 keycode,
bool down)
341 qDebug(RabbitVNC,
"keysym:%d;keycode:%d;down:%d", keysym, keycode, down);
343 m_InputDevice->KeyEvent(keysym, keycode, down);
346void CConnection::pointerEvent(
const rfb::Point &pos,
int buttonMask)
349 CInputDevice::MouseButtons button;
351 button |= CInputDevice::LeftButton;
353 button |= CInputDevice::MouseButton::MiddleButton;
355 button |= CInputDevice::MouseButton::RightButton;
357 button |= CInputDevice::MouseButton::UWheelButton;
358 if(buttonMask & 0x10)
359 button |= CInputDevice::MouseButton::DWheelButton;
360 if(buttonMask & 0x20)
361 button |= CInputDevice::MouseButton::LWheelButton;
362 if(buttonMask & 0x40)
363 button |= CInputDevice::MouseButton::RWheelButton;
366 m_InputDevice->MouseEvent(button, QPoint(pos.x, pos.y));
369void CConnection::clientCutText(
const char *str)
371 qDebug(RabbitVNC,
"cut text:%s", str);
374QSharedPointer<rfb::PixelBuffer> CConnection::GetBufferFromQImage(QImage &img)
379 QSharedPointer<rfb::PixelBuffer> pb(
380 new rfb::FullFramePixelBuffer(m_PixelFormat,
385 / (m_PixelFormat.bpp / 8)));
389void CConnection::writeNoDataUpdate()
394 writer()->writeNoDataUpdate();
400void CConnection::writeDataUpdate(QImage img, QRect rect)
404 const rfb::RenderedCursor *cursor =
nullptr;
406 if(!writer())
return;
409 if (continuousUpdates)
410 req = cuRegion.union_(requested);
423 m_Updates.getUpdateInfo(&ui, req);
425 QSharedPointer<rfb::PixelBuffer> buffer = GetBufferFromQImage(img);
426 m_EncodeManager.writeUpdate(ui, buffer.data(), cursor);
430void CConnection::slotDesktopUpdate(QImage img, QRect rect)
433 if(img.isNull() || !writer())
435 qCritical(RabbitVNC) <<
"Image is null";
439 writeDataUpdate(img, rect);