SYNERGY-1032 - Send secure input notifications to client (#7043)
* SYNERGY-1017 - Try usnig NSUserNotification * SYNERGY-1032 - Use UNUserNotificationCenter instead of deprecated notifications * SYNERGY-1032 - Update app delegate and add log after notification access * SYNERGY-1032 - Try using deprecated notification * SYNERGY-1032 - Add notifications to the platform dependant code * SYNERGY-1032 - Check for development builds before asking permission for notifications * SYNERGY-1032 - Remove old notification and secure input detection * SYNERGY-1032 - Add permission request to the main app * SYNERGY-1032 - Only show notifications on server * SYNERGY-1032 - Request and show notification from main app * SYNERGY-1032 - Remove logging from OSX helpers * SYNERGY-1032 - Add UN notification for testing * SYNERGY-1032 - Show notification once * SYNERGY-1032 - Try replicating old flow * SYNERGY-1032 - Reuse notification center * SYNERGY-1032 - Send notification after granting permission * SYNERGY-1032 - Update app delegate * SYNERGY-1032 - Remove deprecated property * SYNERGY-1032 - Add output for debugging * SYNERGY-1032 - Try updating delegate * SYNERGY-1032 - Print current bundle name * SYNERGY-1032 - Add AppDelegate to the server * SYNERGY-1032 - Move notification creation to synergy app * SYNERGY-1032 - Update notification text * SYNERGY-1032 - Fix QString conversion for notification * SYNERGY-1032 - Move notification creation outside the handler * SYNERGY-1032 - Remove debug notification, show notification with no delay * SYNERGY-1032 - Show notification inside the completion handler * SYNERGY-1032 - Remove timed notification trigger * SYNERGY-1032 - Request permissions on synergy start * SYNERGY-1032 - Remove unused includes * SYNERGY-1032 - Update changelog * SYNERGY-1032 - Add empty notification implementations for Windows and Linux * SYNERGY-1032 - Removed temporary debug messages * SYNERGY-1032 - Resolve code smell * SYNERGY-1032 - Add base code for handling sending secure input notification * SYNERGY-1032 - Compile on Mac * SYNERGY-1032 - Allow client downgrade for 1.7 down to 1.6 * SYNERGY-1032 - Add utility to show notifications. Update secure input message format * SYNERGY-1032 - Update notification util on Mac * SYNERGY-1032 - Don't disconnect on invalid message from client * SYNERGY-1032 - Remove unused code * SYNERGY-1032 - Update changelog * SYNERGY-1032 - Update secure input notification message * SYNERGY-1032 - Better formatting for debug comments * SYNERGY-1032 - Resolve code smells * SYNERGY-1032 - Resolve more code smells * SYNERGY-1032 - Revert log level change * SYNERGY-1032 - Resolve merge error
This commit is contained in:
parent
5843230169
commit
2fdde93f3d
30 changed files with 416 additions and 226 deletions
|
|
@ -15,7 +15,7 @@ Enhancements:
|
|||
- #7026 Update the way we package OpenSSL for Windows build
|
||||
- #7035 Add Fedora 34 build
|
||||
- #7037 Add Ubuntu 21.04 build
|
||||
- #7030 | #7041 Add user nofication for secure input on Mac
|
||||
- #7030 | #7041 | #7043 Add user notification for secure input on Mac
|
||||
===========
|
||||
|
||||
v1.14.0-stable
|
||||
|
|
|
|||
|
|
@ -730,7 +730,14 @@ Client::handleHello(const Event&, void*)
|
|||
|
||||
// check versions
|
||||
LOG((CLOG_DEBUG1 "got hello version %d.%d", major, minor));
|
||||
if (major < kProtocolMajorVersion ||
|
||||
SInt16 helloBackMajor = kProtocolMajorVersion;
|
||||
SInt16 helloBackMinor = kProtocolMinorVersion;
|
||||
if (major == kProtocolMajorVersion && minor == 6 && kProtocolMinorVersion == 7) {
|
||||
//because 1.6 and 1.7 is comptable - downgrading protocol for server
|
||||
LOG((CLOG_NOTE "Downgrading protocol version for server"));
|
||||
helloBackMinor = minor;
|
||||
}
|
||||
else if (major < kProtocolMajorVersion ||
|
||||
(major == kProtocolMajorVersion && minor < kProtocolMinorVersion)) {
|
||||
sendConnectionFailedEvent(XIncompatibleClient(major, minor).what());
|
||||
cleanupTimer();
|
||||
|
|
@ -739,10 +746,10 @@ Client::handleHello(const Event&, void*)
|
|||
}
|
||||
|
||||
// say hello back
|
||||
LOG((CLOG_DEBUG1 "say hello version %d.%d", kProtocolMajorVersion, kProtocolMinorVersion));
|
||||
LOG((CLOG_DEBUG1 "say hello version %d.%d", helloBackMajor, helloBackMinor));
|
||||
ProtocolUtil::writef(m_stream, kMsgHelloBack,
|
||||
kProtocolMajorVersion,
|
||||
kProtocolMinorVersion, &m_name);
|
||||
helloBackMajor,
|
||||
helloBackMinor, & m_name);
|
||||
|
||||
// now connected but waiting to complete handshake
|
||||
setupScreen();
|
||||
|
|
|
|||
|
|
@ -26,6 +26,7 @@
|
|||
#include "synergy/ProtocolUtil.h"
|
||||
#include "synergy/option_types.h"
|
||||
#include "synergy/protocol_types.h"
|
||||
#include "synergy/AppUtil.h"
|
||||
#include "io/IStream.h"
|
||||
#include "base/Log.h"
|
||||
#include "base/IEventQueue.h"
|
||||
|
|
@ -129,8 +130,10 @@ ServerProxy::handleData(const Event&, void*)
|
|||
|
||||
case kUnknown:
|
||||
LOG((CLOG_ERR "invalid message from server: %c%c%c%c", code[0], code[1], code[2], code[3]));
|
||||
m_client->disconnect("invalid message from server");
|
||||
return;
|
||||
// not possible to determine message boundaries
|
||||
// read the whole stream to discard unkonwn data
|
||||
while (m_stream->read(nullptr, 4));
|
||||
break;
|
||||
|
||||
case kDisconnect:
|
||||
return;
|
||||
|
|
@ -303,6 +306,9 @@ ServerProxy::parseMessage(const UInt8* code)
|
|||
else if (memcmp(code, kMsgDDragInfo, 4) == 0) {
|
||||
dragInfoReceived();
|
||||
}
|
||||
else if (memcmp(code, kMsgDSecureInputNotification, 4) == 0) {
|
||||
secureInputNotification();
|
||||
}
|
||||
|
||||
else if (memcmp(code, kMsgCClose, 4) == 0) {
|
||||
// server wants us to hangup
|
||||
|
|
@ -906,3 +912,19 @@ ServerProxy::sendDragInfo(UInt32 fileCount, const char* info, size_t size)
|
|||
String data(info, size);
|
||||
ProtocolUtil::writef(m_stream, kMsgDDragInfo, fileCount, &data);
|
||||
}
|
||||
|
||||
void
|
||||
ServerProxy::secureInputNotification()
|
||||
{
|
||||
String app;
|
||||
ProtocolUtil::readf(m_stream, kMsgDSecureInputNotification + 4, &app);
|
||||
|
||||
String secureInputNotificationBody =
|
||||
"'Secure input' enabled by " + app + " on the server. " \
|
||||
"To fix the keyboard, " + app + " must be closed.";
|
||||
|
||||
// display this notification on the client
|
||||
AppUtil::instance().showNotification(
|
||||
"The keyboard may stop working.",
|
||||
secureInputNotificationBody);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -112,6 +112,7 @@ private:
|
|||
void fileChunkReceived();
|
||||
void dragInfoReceived();
|
||||
void handleClipboardSendingEvent(const Event&, void*);
|
||||
void secureInputNotification();
|
||||
|
||||
private:
|
||||
typedef EResult (ServerProxy::*MessageParser)(const UInt8*);
|
||||
|
|
|
|||
|
|
@ -1988,10 +1988,11 @@ MSWindowsScreen::getDropTarget() const
|
|||
return m_desktopPath;
|
||||
}
|
||||
|
||||
void
|
||||
MSWindowsScreen::createNotification(const String& title, const String& content) const
|
||||
String
|
||||
MSWindowsScreen::getSecureInputApp() const
|
||||
{
|
||||
// TODO: implement notification
|
||||
// ignore on Windows
|
||||
return "";
|
||||
}
|
||||
|
||||
bool
|
||||
|
|
|
|||
|
|
@ -139,7 +139,7 @@ public:
|
|||
virtual String& getDraggingFilename();
|
||||
virtual const String&
|
||||
getDropTarget() const;
|
||||
void createNotification(const String& title, const String& content) const override;
|
||||
String getSecureInputApp() const override;
|
||||
|
||||
protected:
|
||||
// IPlatformScreen overrides
|
||||
|
|
|
|||
|
|
@ -59,55 +59,55 @@ public:
|
|||
IEventQueue* getEvents() const { return m_events; }
|
||||
|
||||
// IScreen overrides
|
||||
virtual void* getEventTarget() const;
|
||||
virtual bool getClipboard(ClipboardID id, IClipboard*) const;
|
||||
virtual void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const;
|
||||
virtual void getCursorPos(SInt32& x, SInt32& y) const;
|
||||
void* getEventTarget() const override;
|
||||
bool getClipboard(ClipboardID id, IClipboard*) const override;
|
||||
void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const override;
|
||||
void getCursorPos(SInt32& x, SInt32& y) const override;
|
||||
|
||||
// IPrimaryScreen overrides
|
||||
virtual void reconfigure(UInt32 activeSides);
|
||||
virtual void warpCursor(SInt32 x, SInt32 y);
|
||||
virtual UInt32 registerHotKey(KeyID key, KeyModifierMask mask);
|
||||
virtual void unregisterHotKey(UInt32 id);
|
||||
virtual void fakeInputBegin();
|
||||
virtual void fakeInputEnd();
|
||||
virtual SInt32 getJumpZoneSize() const;
|
||||
virtual bool isAnyMouseButtonDown(UInt32& buttonID) const;
|
||||
virtual void getCursorCenter(SInt32& x, SInt32& y) const;
|
||||
void reconfigure(UInt32 activeSides) override;
|
||||
void warpCursor(SInt32 x, SInt32 y) override;
|
||||
UInt32 registerHotKey(KeyID key, KeyModifierMask mask) override;
|
||||
void unregisterHotKey(UInt32 id) override;
|
||||
void fakeInputBegin() override;
|
||||
void fakeInputEnd() override;
|
||||
SInt32 getJumpZoneSize() const override;
|
||||
bool isAnyMouseButtonDown(UInt32& buttonID) const override;
|
||||
void getCursorCenter(SInt32& x, SInt32& y) const override;
|
||||
|
||||
// ISecondaryScreen overrides
|
||||
virtual void fakeMouseButton(ButtonID id, bool press);
|
||||
virtual void fakeMouseMove(SInt32 x, SInt32 y);
|
||||
virtual void fakeMouseRelativeMove(SInt32 dx, SInt32 dy) const;
|
||||
virtual void fakeMouseWheel(SInt32 xDelta, SInt32 yDelta) const;
|
||||
void fakeMouseButton(ButtonID id, bool press) override;
|
||||
void fakeMouseMove(SInt32 x, SInt32 y) override;
|
||||
void fakeMouseRelativeMove(SInt32 dx, SInt32 dy) const override;
|
||||
void fakeMouseWheel(SInt32 xDelta, SInt32 yDelta) const override;
|
||||
|
||||
// IPlatformScreen overrides
|
||||
virtual void enable();
|
||||
virtual void disable();
|
||||
virtual void enter();
|
||||
virtual bool leave();
|
||||
virtual bool setClipboard(ClipboardID, const IClipboard*);
|
||||
virtual void checkClipboards();
|
||||
virtual void openScreensaver(bool notify);
|
||||
virtual void closeScreensaver();
|
||||
virtual void screensaver(bool activate);
|
||||
virtual void resetOptions();
|
||||
virtual void setOptions(const OptionsList& options);
|
||||
virtual void setSequenceNumber(UInt32);
|
||||
virtual bool isPrimary() const;
|
||||
virtual void fakeDraggingFiles(DragFileList fileList);
|
||||
virtual String& getDraggingFilename();
|
||||
void enable() override;
|
||||
void disable() override;
|
||||
void enter() override;
|
||||
bool leave() override;
|
||||
bool setClipboard(ClipboardID, const IClipboard*) override;
|
||||
void checkClipboards() override;
|
||||
void openScreensaver(bool notify) override;
|
||||
void closeScreensaver() override;
|
||||
void screensaver(bool activate) override;
|
||||
void resetOptions() override;
|
||||
void setOptions(const OptionsList& options) override;
|
||||
void setSequenceNumber(UInt32) override;
|
||||
bool isPrimary() const override;
|
||||
void fakeDraggingFiles(DragFileList fileList) override;
|
||||
String& getDraggingFilename() override;
|
||||
String getSecureInputApp() const override;
|
||||
|
||||
const String& getDropTarget() const { return m_dropTarget; }
|
||||
void waitForCarbonLoop() const;
|
||||
void createNotification(const String& title, const String& content) const override;
|
||||
const String& getDropTarget() const override { return m_dropTarget; }
|
||||
void waitForCarbonLoop() const;
|
||||
|
||||
protected:
|
||||
// IPlatformScreen overrides
|
||||
virtual void handleSystemEvent(const Event&, void*);
|
||||
virtual void updateButtons();
|
||||
virtual IKeyState* getKeyState() const;
|
||||
void handleSystemEvent(const Event&, void*) override;
|
||||
void updateButtons() override;
|
||||
IKeyState* getKeyState() const override;
|
||||
|
||||
private:
|
||||
bool updateScreenShape();
|
||||
|
|
@ -203,8 +203,6 @@ private:
|
|||
static char* CFStringRefToUTF8String(CFStringRef aString);
|
||||
|
||||
void getDropTargetThread(void*);
|
||||
|
||||
void createSecureInputNotification();
|
||||
|
||||
private:
|
||||
struct HotKeyItem {
|
||||
|
|
|
|||
32
src/lib/platform/OSXScreen.mm
Executable file → Normal file
32
src/lib/platform/OSXScreen.mm
Executable file → Normal file
|
|
@ -59,6 +59,7 @@ enum {
|
|||
kCarbonLoopWaitTimeout = 10
|
||||
};
|
||||
|
||||
void createSecureInputNotification();
|
||||
int getSecureInputEventPID();
|
||||
String getProcessName(int pid);
|
||||
|
||||
|
|
@ -2158,26 +2159,31 @@ OSXScreen::waitForCarbonLoop() const
|
|||
|
||||
}
|
||||
|
||||
void
|
||||
OSXScreen::createNotification(const String& title, const String& content) const
|
||||
String
|
||||
OSXScreen::getSecureInputApp() const
|
||||
{
|
||||
LOG((CLOG_INFO "OSX Notification: %s|%s", title.c_str(), content.c_str()));
|
||||
if(IsSecureEventInputEnabled()) {
|
||||
int secureInputProcessPID = getSecureInputEventPID();
|
||||
if(secureInputProcessPID == 0) return "unknown";
|
||||
return getProcessName(secureInputProcessPID);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
void
|
||||
OSXScreen::createSecureInputNotification()
|
||||
createSecureInputNotification()
|
||||
{
|
||||
std::string secureInputNotificationBody =
|
||||
"Secure input was enabled in your system. " \
|
||||
"Synergy may not be able to send keyboard strokes. ";
|
||||
|
||||
int secureInputProcessPID = getSecureInputEventPID();
|
||||
std::string infringingProcessName = getProcessName(secureInputProcessPID);
|
||||
if(secureInputProcessPID == 0) infringingProcessName = "unknown";
|
||||
secureInputNotificationBody += "Infringing process is " + infringingProcessName;
|
||||
String app = getProcessName(secureInputProcessPID);
|
||||
if(secureInputProcessPID == 0) app = "unknown";
|
||||
|
||||
createNotification(
|
||||
"Keyboard may not work correctly",
|
||||
String secureInputNotificationBody =
|
||||
"'Secure input' enabled by " + app + ". " \
|
||||
"Close " + app + " to continue using keyboards on the clients.";
|
||||
|
||||
// display this notification on the server
|
||||
AppUtil::instance().showNotification(
|
||||
"The client keyboards may stop working.",
|
||||
secureInputNotificationBody);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -475,10 +475,11 @@ XWindowsScreen::isPrimary() const
|
|||
return m_isPrimary;
|
||||
}
|
||||
|
||||
void
|
||||
XWindowsScreen::createNotification(const String& title, const String& content) const
|
||||
String
|
||||
XWindowsScreen::getSecureInputApp() const
|
||||
{
|
||||
// TODO: implement notification
|
||||
// ignore on Linux
|
||||
return "";
|
||||
}
|
||||
|
||||
void*
|
||||
|
|
|
|||
|
|
@ -84,7 +84,7 @@ public:
|
|||
virtual void setOptions(const OptionsList& options);
|
||||
virtual void setSequenceNumber(UInt32);
|
||||
virtual bool isPrimary() const;
|
||||
void createNotification(const String& title, const String& content) const override;
|
||||
String getSecureInputApp() const override;
|
||||
|
||||
protected:
|
||||
// IPlatformScreen overrides
|
||||
|
|
|
|||
|
|
@ -89,6 +89,8 @@ public:
|
|||
virtual void sendDragInfo(UInt32 fileCount, const char* info,
|
||||
size_t size) = 0;
|
||||
virtual void fileChunkSending(UInt8 mark, char* data, size_t dataSize) = 0;
|
||||
virtual String getSecureInputApp() const = 0;
|
||||
virtual void secureInputNotification(const String& app) const = 0;
|
||||
virtual String getName() const;
|
||||
virtual synergy::IStream*
|
||||
getStream() const = 0;
|
||||
|
|
|
|||
|
|
@ -56,40 +56,41 @@ public:
|
|||
/*!
|
||||
Returns the original stream passed to the c'tor.
|
||||
*/
|
||||
synergy::IStream* getStream() const;
|
||||
synergy::IStream* getStream() const override;
|
||||
|
||||
//@}
|
||||
|
||||
// IScreen
|
||||
virtual void* getEventTarget() const;
|
||||
virtual bool getClipboard(ClipboardID id, IClipboard*) const = 0;
|
||||
virtual void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const = 0;
|
||||
virtual void getCursorPos(SInt32& x, SInt32& y) const = 0;
|
||||
void* getEventTarget() const override;
|
||||
bool getClipboard(ClipboardID id, IClipboard*) const override = 0;
|
||||
void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const override = 0;
|
||||
void getCursorPos(SInt32& x, SInt32& y) const override = 0;
|
||||
|
||||
// IClient overrides
|
||||
virtual void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
UInt32 seqNum, KeyModifierMask mask,
|
||||
bool forScreensaver) = 0;
|
||||
virtual bool leave() = 0;
|
||||
virtual void setClipboard(ClipboardID, const IClipboard*) = 0;
|
||||
virtual void grabClipboard(ClipboardID) = 0;
|
||||
virtual void setClipboardDirty(ClipboardID, bool) = 0;
|
||||
virtual void keyDown(KeyID, KeyModifierMask, KeyButton) = 0;
|
||||
virtual void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton) = 0;
|
||||
virtual void keyUp(KeyID, KeyModifierMask, KeyButton) = 0;
|
||||
virtual void mouseDown(ButtonID) = 0;
|
||||
virtual void mouseUp(ButtonID) = 0;
|
||||
virtual void mouseMove(SInt32 xAbs, SInt32 yAbs) = 0;
|
||||
virtual void mouseRelativeMove(SInt32 xRel, SInt32 yRel) = 0;
|
||||
virtual void mouseWheel(SInt32 xDelta, SInt32 yDelta) = 0;
|
||||
virtual void screensaver(bool activate) = 0;
|
||||
virtual void resetOptions() = 0;
|
||||
virtual void setOptions(const OptionsList& options) = 0;
|
||||
virtual void sendDragInfo(UInt32 fileCount, const char* info,
|
||||
size_t size) = 0;
|
||||
virtual void fileChunkSending(UInt8 mark, char* data, size_t dataSize) = 0;
|
||||
bool forScreensaver) override = 0;
|
||||
bool leave() override = 0;
|
||||
void setClipboard(ClipboardID, const IClipboard*) override = 0;
|
||||
void grabClipboard(ClipboardID) override = 0;
|
||||
void setClipboardDirty(ClipboardID, bool) override = 0;
|
||||
void keyDown(KeyID, KeyModifierMask, KeyButton) override = 0;
|
||||
void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton) override = 0;
|
||||
void keyUp(KeyID, KeyModifierMask, KeyButton) override = 0;
|
||||
void mouseDown(ButtonID) override = 0;
|
||||
void mouseUp(ButtonID) override = 0;
|
||||
void mouseMove(SInt32 xAbs, SInt32 yAbs) override = 0;
|
||||
void mouseRelativeMove(SInt32 xRel, SInt32 yRel) override = 0;
|
||||
void mouseWheel(SInt32 xDelta, SInt32 yDelta) override = 0;
|
||||
void screensaver(bool activate) override = 0;
|
||||
void resetOptions() override = 0;
|
||||
void setOptions(const OptionsList& options) override = 0;
|
||||
void sendDragInfo(UInt32 fileCount, const char* info,
|
||||
size_t size) override = 0;
|
||||
void fileChunkSending(UInt8 mark, char* data, size_t dataSize) override = 0;
|
||||
void secureInputNotification(const String& app) const override = 0;
|
||||
|
||||
private:
|
||||
synergy::IStream* m_stream;
|
||||
|
|
|
|||
|
|
@ -150,8 +150,9 @@ ClientProxy1_0::handleData(const Event&, void*)
|
|||
LOG((CLOG_DEBUG2 "msg from \"%s\": %c%c%c%c", getName().c_str(), code[0], code[1], code[2], code[3]));
|
||||
if (!(this->*m_parser)(code)) {
|
||||
LOG((CLOG_ERR "invalid message from client \"%s\": %c%c%c%c", getName().c_str(), code[0], code[1], code[2], code[3]));
|
||||
disconnect();
|
||||
return;
|
||||
// not possible to determine message boundaries
|
||||
// read the whole stream to discard unkonwn data
|
||||
while (getStream()->read(nullptr, 4));
|
||||
}
|
||||
|
||||
// next message
|
||||
|
|
@ -365,6 +366,21 @@ ClientProxy1_0::fileChunkSending(UInt8 mark, char* data, size_t dataSize)
|
|||
LOG((CLOG_DEBUG "fileChunkSending not supported"));
|
||||
}
|
||||
|
||||
String
|
||||
ClientProxy1_0::getSecureInputApp() const
|
||||
{
|
||||
// ignore -- not supported on clients
|
||||
LOG((CLOG_DEBUG "getSecureInputApp not supported"));
|
||||
return "";
|
||||
}
|
||||
|
||||
void
|
||||
ClientProxy1_0::secureInputNotification(const String& app) const
|
||||
{
|
||||
// ignore -- not supported in protocol 1.0
|
||||
LOG((CLOG_DEBUG "secureInputNotification not supported"));
|
||||
}
|
||||
|
||||
void
|
||||
ClientProxy1_0::screensaver(bool on)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -38,33 +38,35 @@ public:
|
|||
ClientProxy1_0& operator=(ClientProxy1_0 &&) =delete;
|
||||
|
||||
// IScreen
|
||||
virtual bool getClipboard(ClipboardID id, IClipboard*) const;
|
||||
virtual void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const;
|
||||
virtual void getCursorPos(SInt32& x, SInt32& y) const;
|
||||
bool getClipboard(ClipboardID id, IClipboard*) const override;
|
||||
void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const override;
|
||||
void getCursorPos(SInt32& x, SInt32& y) const override;
|
||||
|
||||
// IClient overrides
|
||||
virtual void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
UInt32 seqNum, KeyModifierMask mask,
|
||||
bool forScreensaver);
|
||||
virtual bool leave();
|
||||
virtual void setClipboard(ClipboardID, const IClipboard*);
|
||||
virtual void grabClipboard(ClipboardID);
|
||||
virtual void setClipboardDirty(ClipboardID, bool);
|
||||
virtual void keyDown(KeyID, KeyModifierMask, KeyButton);
|
||||
virtual void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton);
|
||||
virtual void keyUp(KeyID, KeyModifierMask, KeyButton);
|
||||
virtual void mouseDown(ButtonID);
|
||||
virtual void mouseUp(ButtonID);
|
||||
virtual void mouseMove(SInt32 xAbs, SInt32 yAbs);
|
||||
virtual void mouseRelativeMove(SInt32 xRel, SInt32 yRel);
|
||||
virtual void mouseWheel(SInt32 xDelta, SInt32 yDelta);
|
||||
virtual void screensaver(bool activate);
|
||||
virtual void resetOptions();
|
||||
virtual void setOptions(const OptionsList& options);
|
||||
virtual void sendDragInfo(UInt32 fileCount, const char* info, size_t size);
|
||||
virtual void fileChunkSending(UInt8 mark, char* data, size_t dataSize);
|
||||
bool forScreensaver) override;
|
||||
bool leave() override;
|
||||
void setClipboard(ClipboardID, const IClipboard*) override;
|
||||
void grabClipboard(ClipboardID) override;
|
||||
void setClipboardDirty(ClipboardID, bool) override;
|
||||
void keyDown(KeyID, KeyModifierMask, KeyButton) override;
|
||||
void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton) override;
|
||||
void keyUp(KeyID, KeyModifierMask, KeyButton) override;
|
||||
void mouseDown(ButtonID) override;
|
||||
void mouseUp(ButtonID) override;
|
||||
void mouseMove(SInt32 xAbs, SInt32 yAbs) override;
|
||||
void mouseRelativeMove(SInt32 xRel, SInt32 yRel) override;
|
||||
void mouseWheel(SInt32 xDelta, SInt32 yDelta) override;
|
||||
void screensaver(bool activate) override;
|
||||
void resetOptions() override;
|
||||
void setOptions(const OptionsList& options) override;
|
||||
void sendDragInfo(UInt32 fileCount, const char* info, size_t size) override;
|
||||
void fileChunkSending(UInt8 mark, char* data, size_t dataSize) override;
|
||||
String getSecureInputApp() const override;
|
||||
void secureInputNotification(const String& app) const override;
|
||||
|
||||
protected:
|
||||
virtual bool parseHandshakeMessage(const UInt8* code);
|
||||
|
|
|
|||
41
src/lib/server/ClientProxy1_7.cpp
Normal file
41
src/lib/server/ClientProxy1_7.cpp
Normal file
|
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* synergy -- mouse and keyboard sharing utility
|
||||
* Copyright (C) 2015-2016 Symless Ltd.
|
||||
*
|
||||
* This package is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* found in the file LICENSE that should have accompanied this file.
|
||||
*
|
||||
* This package is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "server/ClientProxy1_7.h"
|
||||
#include "server/Server.h"
|
||||
#include "synergy/AppUtil.h"
|
||||
#include "synergy/ProtocolUtil.h"
|
||||
#include "base/TMethodEventJob.h"
|
||||
#include "base/Log.h"
|
||||
|
||||
//
|
||||
// ClientProxy1_7
|
||||
//
|
||||
|
||||
ClientProxy1_7::ClientProxy1_7(const String& name, synergy::IStream* stream, Server* server, IEventQueue* events) :
|
||||
ClientProxy1_6(name, stream, server, events),
|
||||
m_events(events)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
ClientProxy1_7::secureInputNotification(const String& app) const
|
||||
{
|
||||
LOG((CLOG_DEBUG2 "send secure input notification to \"%s\" %s", getName().c_str(), app.c_str()));
|
||||
ProtocolUtil::writef(getStream(), kMsgDSecureInputNotification, &app);
|
||||
}
|
||||
33
src/lib/server/ClientProxy1_7.h
Normal file
33
src/lib/server/ClientProxy1_7.h
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
/*
|
||||
* synergy -- mouse and keyboard sharing utility
|
||||
* Copyright (C) 2015-2016 Symless Ltd.
|
||||
*
|
||||
* This package is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* found in the file LICENSE that should have accompanied this file.
|
||||
*
|
||||
* This package is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "server/ClientProxy1_6.h"
|
||||
|
||||
//! Proxy for client implementing protocol version 1.7
|
||||
class ClientProxy1_7 : public ClientProxy1_6 {
|
||||
public:
|
||||
ClientProxy1_7(const String& name, synergy::IStream* adoptedStream, Server* server, IEventQueue* events);
|
||||
~ClientProxy1_7() override = default;
|
||||
|
||||
void secureInputNotification(const String& app) const override;
|
||||
|
||||
private:
|
||||
|
||||
IEventQueue* m_events;
|
||||
};
|
||||
|
|
@ -26,6 +26,7 @@
|
|||
#include "server/ClientProxy1_4.h"
|
||||
#include "server/ClientProxy1_5.h"
|
||||
#include "server/ClientProxy1_6.h"
|
||||
#include "server/ClientProxy1_7.h"
|
||||
#include "synergy/protocol_types.h"
|
||||
#include "synergy/ProtocolUtil.h"
|
||||
#include "synergy/XSynergy.h"
|
||||
|
|
@ -232,6 +233,10 @@ ClientProxyUnknown::handleData(const Event&, void*)
|
|||
case 6:
|
||||
m_proxy = new ClientProxy1_6(name, m_stream, m_server, m_events);
|
||||
break;
|
||||
|
||||
case 7:
|
||||
m_proxy = new ClientProxy1_7(name, m_stream, m_server, m_events);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -261,6 +261,18 @@ PrimaryClient::fileChunkSending(UInt8 mark, char* data, size_t dataSize)
|
|||
// ignore
|
||||
}
|
||||
|
||||
String
|
||||
PrimaryClient::getSecureInputApp() const
|
||||
{
|
||||
return m_screen->getSecureInputApp();
|
||||
}
|
||||
|
||||
void
|
||||
PrimaryClient::secureInputNotification(const String& app) const
|
||||
{
|
||||
// ignore
|
||||
}
|
||||
|
||||
void
|
||||
PrimaryClient::resetOptions()
|
||||
{
|
||||
|
|
|
|||
|
|
@ -117,38 +117,40 @@ public:
|
|||
virtual void disable();
|
||||
|
||||
// IScreen overrides
|
||||
virtual void* getEventTarget() const;
|
||||
virtual bool getClipboard(ClipboardID id, IClipboard*) const;
|
||||
virtual void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const;
|
||||
virtual void getCursorPos(SInt32& x, SInt32& y) const;
|
||||
void* getEventTarget() const override;
|
||||
bool getClipboard(ClipboardID id, IClipboard*) const override;
|
||||
void getShape(SInt32& x, SInt32& y,
|
||||
SInt32& width, SInt32& height) const override;
|
||||
void getCursorPos(SInt32& x, SInt32& y) const override;
|
||||
|
||||
// IClient overrides
|
||||
virtual void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
void enter(SInt32 xAbs, SInt32 yAbs,
|
||||
UInt32 seqNum, KeyModifierMask mask,
|
||||
bool forScreensaver);
|
||||
virtual bool leave();
|
||||
virtual void setClipboard(ClipboardID, const IClipboard*);
|
||||
virtual void grabClipboard(ClipboardID);
|
||||
virtual void setClipboardDirty(ClipboardID, bool);
|
||||
virtual void keyDown(KeyID, KeyModifierMask, KeyButton);
|
||||
virtual void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton);
|
||||
virtual void keyUp(KeyID, KeyModifierMask, KeyButton);
|
||||
virtual void mouseDown(ButtonID);
|
||||
virtual void mouseUp(ButtonID);
|
||||
virtual void mouseMove(SInt32 xAbs, SInt32 yAbs);
|
||||
virtual void mouseRelativeMove(SInt32 xRel, SInt32 yRel);
|
||||
virtual void mouseWheel(SInt32 xDelta, SInt32 yDelta);
|
||||
virtual void screensaver(bool activate);
|
||||
virtual void resetOptions();
|
||||
virtual void setOptions(const OptionsList& options);
|
||||
virtual void sendDragInfo(UInt32 fileCount, const char* info, size_t size);
|
||||
virtual void fileChunkSending(UInt8 mark, char* data, size_t dataSize);
|
||||
bool forScreensaver) override;
|
||||
bool leave() override;
|
||||
void setClipboard(ClipboardID, const IClipboard*) override;
|
||||
void grabClipboard(ClipboardID) override;
|
||||
void setClipboardDirty(ClipboardID, bool) override;
|
||||
void keyDown(KeyID, KeyModifierMask, KeyButton) override;
|
||||
void keyRepeat(KeyID, KeyModifierMask,
|
||||
SInt32 count, KeyButton) override;
|
||||
void keyUp(KeyID, KeyModifierMask, KeyButton) override;
|
||||
void mouseDown(ButtonID) override;
|
||||
void mouseUp(ButtonID) override;
|
||||
void mouseMove(SInt32 xAbs, SInt32 yAbs) override;
|
||||
void mouseRelativeMove(SInt32 xRel, SInt32 yRel) override;
|
||||
void mouseWheel(SInt32 xDelta, SInt32 yDelta) override;
|
||||
void screensaver(bool activate) override;
|
||||
void resetOptions() override;
|
||||
void setOptions(const OptionsList& options) override;
|
||||
void sendDragInfo(UInt32 fileCount, const char* info, size_t size) override;
|
||||
void fileChunkSending(UInt8 mark, char* data, size_t dataSize) override;
|
||||
String getSecureInputApp() const override;
|
||||
void secureInputNotification(const String& app) const override;
|
||||
|
||||
virtual synergy::IStream*
|
||||
getStream() const { return NULL; }
|
||||
bool isPrimary() const { return true; }
|
||||
synergy::IStream*
|
||||
getStream() const override { return nullptr; }
|
||||
bool isPrimary() const override { return true; }
|
||||
private:
|
||||
synergy::Screen* m_screen;
|
||||
bool m_clipboardDirty[kClipboardEnd];
|
||||
|
|
|
|||
|
|
@ -511,6 +511,14 @@ Server::switchScreen(BaseClientProxy* dst,
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
#if defined(__APPLE__)
|
||||
String secureInputApplication = m_active->getSecureInputApp();
|
||||
if (m_active == m_primaryClient && secureInputApplication != "") {
|
||||
dst->secureInputNotification(secureInputApplication);
|
||||
}
|
||||
#endif
|
||||
|
||||
// cut over
|
||||
m_active = dst;
|
||||
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@
|
|||
|
||||
#include "common/IInterface.h"
|
||||
#include "synergy/IApp.h"
|
||||
#include "base/String.h"
|
||||
|
||||
class IAppUtil : public IInterface {
|
||||
public:
|
||||
|
|
@ -28,4 +29,5 @@ public:
|
|||
virtual int run(int argc, char** argv) = 0;
|
||||
virtual void beforeAppExit() = 0;
|
||||
virtual void startNode() = 0;
|
||||
virtual void showNotification(const String& title, const String& text) const = 0;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -133,11 +133,11 @@ public:
|
|||
//! Change dragging status
|
||||
virtual void setDraggingStarted(bool started) = 0;
|
||||
|
||||
//! Send desktop user notification
|
||||
//! Determine the name of the app causing a secure input state
|
||||
/*!
|
||||
Creates a platform dependant user notificaiton using native APIs
|
||||
On MacOS check which app causes a secure input state to be enabled. No alternative on other platforms
|
||||
*/
|
||||
virtual void createNotification(const String& title, const String& content) const = 0;
|
||||
virtual String getSecureInputApp() const = 0;
|
||||
|
||||
//@}
|
||||
//! @name accessors
|
||||
|
|
|
|||
|
|
@ -522,10 +522,10 @@ Screen::leaveSecondary()
|
|||
m_screen->fakeAllKeysUp();
|
||||
}
|
||||
|
||||
void
|
||||
Screen::createNotification(const String& title, const String& content) const
|
||||
String
|
||||
Screen::getSecureInputApp() const
|
||||
{
|
||||
m_screen->createNotification(title, content);
|
||||
return m_screen->getSecureInputApp();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -234,11 +234,11 @@ public:
|
|||
|
||||
void setEnableDragDrop(bool enabled);
|
||||
|
||||
//! Send desktop user notification
|
||||
//! Determine the name of the app causing a secure input state
|
||||
/*!
|
||||
Creates a platform dependant user notificaiton using native APIs
|
||||
On MacOS check which app causes a secure input state to be enabled. No alternative on other platforms
|
||||
*/
|
||||
virtual void createNotification(const String& title, const String& content) const;
|
||||
String getSecureInputApp() const;
|
||||
|
||||
//@}
|
||||
//! @name accessors
|
||||
|
|
|
|||
|
|
@ -18,36 +18,37 @@
|
|||
|
||||
#include "synergy/protocol_types.h"
|
||||
|
||||
const char* kMsgHello = "Synergy%2i%2i";
|
||||
const char* kMsgHelloBack = "Synergy%2i%2i%s";
|
||||
const char* kMsgCNoop = "CNOP";
|
||||
const char* kMsgCClose = "CBYE";
|
||||
const char* kMsgCEnter = "CINN%2i%2i%4i%2i";
|
||||
const char* kMsgCLeave = "COUT";
|
||||
const char* kMsgCClipboard = "CCLP%1i%4i";
|
||||
const char* kMsgCScreenSaver = "CSEC%1i";
|
||||
const char* kMsgCResetOptions = "CROP";
|
||||
const char* kMsgCInfoAck = "CIAK";
|
||||
const char* kMsgCKeepAlive = "CALV";
|
||||
const char* kMsgDKeyDown = "DKDN%2i%2i%2i";
|
||||
const char* kMsgDKeyDown1_0 = "DKDN%2i%2i";
|
||||
const char* kMsgDKeyRepeat = "DKRP%2i%2i%2i%2i";
|
||||
const char* kMsgDKeyRepeat1_0 = "DKRP%2i%2i%2i";
|
||||
const char* kMsgDKeyUp = "DKUP%2i%2i%2i";
|
||||
const char* kMsgDKeyUp1_0 = "DKUP%2i%2i";
|
||||
const char* kMsgDMouseDown = "DMDN%1i";
|
||||
const char* kMsgDMouseUp = "DMUP%1i";
|
||||
const char* kMsgDMouseMove = "DMMV%2i%2i";
|
||||
const char* kMsgDMouseRelMove = "DMRM%2i%2i";
|
||||
const char* kMsgDMouseWheel = "DMWM%2i%2i";
|
||||
const char* kMsgDMouseWheel1_0 = "DMWM%2i";
|
||||
const char* kMsgDClipboard = "DCLP%1i%4i%1i%s";
|
||||
const char* kMsgDInfo = "DINF%2i%2i%2i%2i%2i%2i%2i";
|
||||
const char* kMsgDSetOptions = "DSOP%4I";
|
||||
const char* kMsgDFileTransfer = "DFTR%1i%s";
|
||||
const char* kMsgDDragInfo = "DDRG%2i%s";
|
||||
const char* kMsgQInfo = "QINF";
|
||||
const char* kMsgEIncompatible = "EICV%2i%2i";
|
||||
const char* kMsgEBusy = "EBSY";
|
||||
const char* kMsgEUnknown = "EUNK";
|
||||
const char* kMsgEBad = "EBAD";
|
||||
const char* const kMsgHello = "Synergy%2i%2i";
|
||||
const char* const kMsgHelloBack = "Synergy%2i%2i%s";
|
||||
const char* const kMsgCNoop = "CNOP";
|
||||
const char* const kMsgCClose = "CBYE";
|
||||
const char* const kMsgCEnter = "CINN%2i%2i%4i%2i";
|
||||
const char* const kMsgCLeave = "COUT";
|
||||
const char* const kMsgCClipboard = "CCLP%1i%4i";
|
||||
const char* const kMsgCScreenSaver = "CSEC%1i";
|
||||
const char* const kMsgCResetOptions = "CROP";
|
||||
const char* const kMsgCInfoAck = "CIAK";
|
||||
const char* const kMsgCKeepAlive = "CALV";
|
||||
const char* const kMsgDKeyDown = "DKDN%2i%2i%2i";
|
||||
const char* const kMsgDKeyDown1_0 = "DKDN%2i%2i";
|
||||
const char* const kMsgDKeyRepeat = "DKRP%2i%2i%2i%2i";
|
||||
const char* const kMsgDKeyRepeat1_0 = "DKRP%2i%2i%2i";
|
||||
const char* const kMsgDKeyUp = "DKUP%2i%2i%2i";
|
||||
const char* const kMsgDKeyUp1_0 = "DKUP%2i%2i";
|
||||
const char* const kMsgDMouseDown = "DMDN%1i";
|
||||
const char* const kMsgDMouseUp = "DMUP%1i";
|
||||
const char* const kMsgDMouseMove = "DMMV%2i%2i";
|
||||
const char* const kMsgDMouseRelMove = "DMRM%2i%2i";
|
||||
const char* const kMsgDMouseWheel = "DMWM%2i%2i";
|
||||
const char* const kMsgDMouseWheel1_0 = "DMWM%2i";
|
||||
const char* const kMsgDClipboard = "DCLP%1i%4i%1i%s";
|
||||
const char* const kMsgDInfo = "DINF%2i%2i%2i%2i%2i%2i%2i";
|
||||
const char* const kMsgDSetOptions = "DSOP%4I";
|
||||
const char* const kMsgDFileTransfer = "DFTR%1i%s";
|
||||
const char* const kMsgDDragInfo = "DDRG%2i%s";
|
||||
const char* const kMsgDSecureInputNotification = "SECN%s";
|
||||
const char* const kMsgQInfo = "QINF";
|
||||
const char* const kMsgEIncompatible = "EICV%2i%2i";
|
||||
const char* const kMsgEBusy = "EBSY";
|
||||
const char* const kMsgEUnknown = "EUNK";
|
||||
const char* const kMsgEBad = "EBAD";
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@
|
|||
// 1.6: adds clipboard streaming
|
||||
// NOTE: with new version, synergy minor version should increment
|
||||
static const SInt16 kProtocolMajorVersion = 1;
|
||||
static const SInt16 kProtocolMinorVersion = 6;
|
||||
static const SInt16 kProtocolMinorVersion = 7;
|
||||
|
||||
// default contact port number
|
||||
static const UInt16 kDefaultPort = 24800;
|
||||
|
|
@ -103,13 +103,13 @@ enum EDataReceived {
|
|||
// say hello to client; primary -> secondary
|
||||
// $1 = protocol major version number supported by server. $2 =
|
||||
// protocol minor version number supported by server.
|
||||
extern const char* kMsgHello;
|
||||
extern const char* const kMsgHello;
|
||||
|
||||
// respond to hello from server; secondary -> primary
|
||||
// $1 = protocol major version number supported by client. $2 =
|
||||
// protocol minor version number supported by client. $3 = client
|
||||
// name.
|
||||
extern const char* kMsgHelloBack;
|
||||
extern const char* const kMsgHelloBack;
|
||||
|
||||
|
||||
//
|
||||
|
|
@ -117,10 +117,10 @@ extern const char* kMsgHelloBack;
|
|||
//
|
||||
|
||||
// no operation; secondary -> primary
|
||||
extern const char* kMsgCNoop;
|
||||
extern const char* const kMsgCNoop;
|
||||
|
||||
// close connection; primary -> secondary
|
||||
extern const char* kMsgCClose;
|
||||
extern const char* const kMsgCClose;
|
||||
|
||||
// enter screen: primary -> secondary
|
||||
// entering screen at screen position $1 = x, $2 = y. x,y are
|
||||
|
|
@ -130,7 +130,7 @@ extern const char* kMsgCClose;
|
|||
// mask. this will have bits set for each toggle modifier key
|
||||
// that is activated on entry to the screen. the secondary screen
|
||||
// should adjust its toggle modifiers to reflect that state.
|
||||
extern const char* kMsgCEnter;
|
||||
extern const char* const kMsgCEnter;
|
||||
|
||||
// leave screen: primary -> secondary
|
||||
// leaving screen. the secondary screen should send clipboard
|
||||
|
|
@ -139,28 +139,28 @@ extern const char* kMsgCEnter;
|
|||
// not received a kMsgCClipboard for with a greater sequence
|
||||
// number) and that were grabbed or have changed since the
|
||||
// last leave.
|
||||
extern const char* kMsgCLeave;
|
||||
extern const char* const kMsgCLeave;
|
||||
|
||||
// grab clipboard: primary <-> secondary
|
||||
// sent by screen when some other app on that screen grabs a
|
||||
// clipboard. $1 = the clipboard identifier, $2 = sequence number.
|
||||
// secondary screens must use the sequence number passed in the
|
||||
// most recent kMsgCEnter. the primary always sends 0.
|
||||
extern const char* kMsgCClipboard;
|
||||
extern const char* const kMsgCClipboard;
|
||||
|
||||
// screensaver change: primary -> secondary
|
||||
// screensaver on primary has started ($1 == 1) or closed ($1 == 0)
|
||||
extern const char* kMsgCScreenSaver;
|
||||
extern const char* const kMsgCScreenSaver;
|
||||
|
||||
// reset options: primary -> secondary
|
||||
// client should reset all of its options to their defaults.
|
||||
extern const char* kMsgCResetOptions;
|
||||
extern const char* const kMsgCResetOptions;
|
||||
|
||||
// resolution change acknowledgment: primary -> secondary
|
||||
// sent by primary in response to a secondary screen's kMsgDInfo.
|
||||
// this is sent for every kMsgDInfo, whether or not the primary
|
||||
// had sent a kMsgQInfo.
|
||||
extern const char* kMsgCInfoAck;
|
||||
extern const char* const kMsgCInfoAck;
|
||||
|
||||
// keep connection alive: primary <-> secondary
|
||||
// sent by the server periodically to verify that connections are still
|
||||
|
|
@ -170,7 +170,7 @@ extern const char* kMsgCInfoAck;
|
|||
// client doesn't receive these (or any message) periodically then it
|
||||
// should disconnect from the server. the appropriate interval is
|
||||
// defined by an option.
|
||||
extern const char* kMsgCKeepAlive;
|
||||
extern const char* const kMsgCKeepAlive;
|
||||
|
||||
//
|
||||
// data codes
|
||||
|
|
@ -187,57 +187,57 @@ extern const char* kMsgCKeepAlive;
|
|||
// the press. this can happen with combining (dead) keys or if
|
||||
// the keyboard layouts are not identical and the user releases
|
||||
// a modifier key before releasing the modified key.
|
||||
extern const char* kMsgDKeyDown;
|
||||
extern const char* const kMsgDKeyDown;
|
||||
|
||||
// key pressed 1.0: same as above but without KeyButton
|
||||
extern const char* kMsgDKeyDown1_0;
|
||||
extern const char* const kMsgDKeyDown1_0;
|
||||
|
||||
// key auto-repeat: primary -> secondary
|
||||
// $1 = KeyID, $2 = KeyModifierMask, $3 = number of repeats, $4 = KeyButton
|
||||
extern const char* kMsgDKeyRepeat;
|
||||
extern const char* const kMsgDKeyRepeat;
|
||||
|
||||
// key auto-repeat 1.0: same as above but without KeyButton
|
||||
extern const char* kMsgDKeyRepeat1_0;
|
||||
extern const char* const kMsgDKeyRepeat1_0;
|
||||
|
||||
// key released: primary -> secondary
|
||||
// $1 = KeyID, $2 = KeyModifierMask, $3 = KeyButton
|
||||
extern const char* kMsgDKeyUp;
|
||||
extern const char* const kMsgDKeyUp;
|
||||
|
||||
// key released 1.0: same as above but without KeyButton
|
||||
extern const char* kMsgDKeyUp1_0;
|
||||
extern const char* const kMsgDKeyUp1_0;
|
||||
|
||||
// mouse button pressed: primary -> secondary
|
||||
// $1 = ButtonID
|
||||
extern const char* kMsgDMouseDown;
|
||||
extern const char* const kMsgDMouseDown;
|
||||
|
||||
// mouse button released: primary -> secondary
|
||||
// $1 = ButtonID
|
||||
extern const char* kMsgDMouseUp;
|
||||
extern const char* const kMsgDMouseUp;
|
||||
|
||||
// mouse moved: primary -> secondary
|
||||
// $1 = x, $2 = y. x,y are absolute screen coordinates.
|
||||
extern const char* kMsgDMouseMove;
|
||||
extern const char* const kMsgDMouseMove;
|
||||
|
||||
// relative mouse move: primary -> secondary
|
||||
// $1 = dx, $2 = dy. dx,dy are motion deltas.
|
||||
extern const char* kMsgDMouseRelMove;
|
||||
extern const char* const kMsgDMouseRelMove;
|
||||
|
||||
// mouse scroll: primary -> secondary
|
||||
// $1 = xDelta, $2 = yDelta. the delta should be +120 for one tick forward
|
||||
// (away from the user) or right and -120 for one tick backward (toward
|
||||
// the user) or left.
|
||||
extern const char* kMsgDMouseWheel;
|
||||
extern const char* const kMsgDMouseWheel;
|
||||
|
||||
// mouse vertical scroll: primary -> secondary
|
||||
// like as kMsgDMouseWheel except only sends $1 = yDelta.
|
||||
extern const char* kMsgDMouseWheel1_0;
|
||||
extern const char* const kMsgDMouseWheel1_0;
|
||||
|
||||
// clipboard data: primary <-> secondary
|
||||
// $2 = sequence number, $3 = mark $4 = clipboard data. the sequence number
|
||||
// is 0 when sent by the primary. secondary screens should use the
|
||||
// sequence number from the most recent kMsgCEnter. $1 = clipboard
|
||||
// identifier.
|
||||
extern const char* kMsgDClipboard;
|
||||
extern const char* const kMsgDClipboard;
|
||||
|
||||
// client data: secondary -> primary
|
||||
// $1 = coordinate of leftmost pixel on secondary screen,
|
||||
|
|
@ -253,25 +253,30 @@ extern const char* kMsgDClipboard;
|
|||
// should ignore any kMsgDMouseMove messages until it receives a
|
||||
// kMsgCInfoAck in order to prevent attempts to move the mouse off
|
||||
// the new screen area.
|
||||
extern const char* kMsgDInfo;
|
||||
extern const char* const kMsgDInfo;
|
||||
|
||||
// set options: primary -> secondary
|
||||
// client should set the given option/value pairs. $1 = option/value
|
||||
// pairs.
|
||||
extern const char* kMsgDSetOptions;
|
||||
extern const char* const kMsgDSetOptions;
|
||||
|
||||
// file data: primary <-> secondary
|
||||
// transfer file data. A mark is used in the first byte.
|
||||
// 0 means the content followed is the file size.
|
||||
// 1 means the content followed is the chunk data.
|
||||
// 2 means the file transfer is finished.
|
||||
extern const char* kMsgDFileTransfer;
|
||||
extern const char* const kMsgDFileTransfer;
|
||||
|
||||
// drag infomation: primary <-> secondary
|
||||
// transfer drag infomation. The first 2 bytes are used for storing
|
||||
// the number of dragging objects. Then the following string consists
|
||||
// of each object's directory.
|
||||
extern const char* kMsgDDragInfo;
|
||||
extern const char* const kMsgDDragInfo;
|
||||
|
||||
// secure input notification: primary -> secondary
|
||||
// $1 = app. app only obtainable on MacOS since that's the only
|
||||
// platform facing secure input problems
|
||||
extern const char* const kMsgDSecureInputNotification;
|
||||
|
||||
//
|
||||
// query codes
|
||||
|
|
@ -279,7 +284,7 @@ extern const char* kMsgDDragInfo;
|
|||
|
||||
// query screen info: primary -> secondary
|
||||
// client should reply with a kMsgDInfo.
|
||||
extern const char* kMsgQInfo;
|
||||
extern const char* const kMsgQInfo;
|
||||
|
||||
|
||||
//
|
||||
|
|
@ -288,19 +293,19 @@ extern const char* kMsgQInfo;
|
|||
|
||||
// incompatible versions: primary -> secondary
|
||||
// $1 = major version of primary, $2 = minor version of primary.
|
||||
extern const char* kMsgEIncompatible;
|
||||
extern const char* const kMsgEIncompatible;
|
||||
|
||||
// name provided when connecting is already in use: primary -> secondary
|
||||
extern const char* kMsgEBusy;
|
||||
extern const char* const kMsgEBusy;
|
||||
|
||||
// unknown client: primary -> secondary
|
||||
// name provided when connecting is not in primary's screen
|
||||
// configuration map.
|
||||
extern const char* kMsgEUnknown;
|
||||
extern const char* const kMsgEUnknown;
|
||||
|
||||
// protocol violation: primary -> secondary
|
||||
// primary should disconnect after sending this message.
|
||||
extern const char* kMsgEBad;
|
||||
extern const char* const kMsgEBad;
|
||||
|
||||
|
||||
//
|
||||
|
|
|
|||
|
|
@ -18,6 +18,8 @@
|
|||
|
||||
#include "synergy/unix/AppUtilUnix.h"
|
||||
#include "synergy/ArgsBase.h"
|
||||
#include "base/Log.h"
|
||||
#include "base/log_outputters.h"
|
||||
|
||||
AppUtilUnix::AppUtilUnix(IEventQueue* events)
|
||||
{
|
||||
|
|
@ -44,3 +46,16 @@ AppUtilUnix::startNode()
|
|||
{
|
||||
app().startNode();
|
||||
}
|
||||
|
||||
void
|
||||
AppUtilUnix::showNotification(const String & title, const String & text) const
|
||||
{
|
||||
LOG((CLOG_DEBUG "Showing notification. Title: \"%s\". Text: \"%s\"", title.c_str(), text.c_str()));
|
||||
#if WINAPI_XWINDOWS
|
||||
|
||||
#elif WINAPI_CARBON
|
||||
// synergys and synergyc are not allowed to send native notifications on MacOS
|
||||
// instead ask main synergy process to show them instead
|
||||
LOG((CLOG_INFO "OSX Notification: %s|%s", title.c_str(), text.c_str()));
|
||||
#endif
|
||||
}
|
||||
|
|
|
|||
|
|
@ -31,4 +31,5 @@ public:
|
|||
|
||||
int run(int argc, char** argv);
|
||||
void startNode();
|
||||
void showNotification(const String& title, const String& text) const override;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -180,3 +180,9 @@ AppUtilWindows::startNode()
|
|||
{
|
||||
app().startNode();
|
||||
}
|
||||
|
||||
void
|
||||
AppUtilWindows::showNotification(const String & title, const String & text) const
|
||||
{
|
||||
LOG((CLOG_DEBUG "Showing notification. Title: \"%s\". Text: \"%s\"", title.c_str(), text.c_str()));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -54,6 +54,8 @@ public:
|
|||
|
||||
void startNode();
|
||||
|
||||
void showNotification(const String& title, const String& text) const override;
|
||||
|
||||
private:
|
||||
AppExitMode m_exitMode;
|
||||
IEventQueue* m_events;
|
||||
|
|
|
|||
Loading…
Reference in a new issue