Initial commit

This commit is contained in:
matt
2020-09-20 12:16:44 +00:00
parent 09a4460ddb
commit 408c005d3e
839 changed files with 190481 additions and 0 deletions

1
unix/vncconfig/.gitignore vendored Normal file
View File

@@ -0,0 +1 @@
vncconfig

View File

@@ -0,0 +1,15 @@
include_directories(${X11_INCLUDE_DIR})
include_directories(${CMAKE_SOURCE_DIR}/common)
include_directories(${CMAKE_SOURCE_DIR}/unix/tx)
add_executable(vncconfig
buildtime.c
vncExt.c
vncconfig.cxx
QueryConnectDialog.cxx)
target_link_libraries(vncconfig tx rfb network rdr ${X11_LIBRARIES})
install(TARGETS vncconfig DESTINATION ${BIN_DIR})
install(FILES vncconfig.man DESTINATION ${MAN_DIR}/man1 RENAME vncconfig.1)

View File

@@ -0,0 +1,88 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#include <stdio.h>
#include <rdr/Exception.h>
#include "QueryConnectDialog.h"
#include "vncExt.h"
QueryConnectDialog::QueryConnectDialog(Display* dpy,
const char* address_,
const char* user_,
int timeout_,
QueryResultCallback* cb)
: TXDialog(dpy, 300, 100, "VNC Server : Accept Connection?"),
addressLbl(dpy, "Host:",this),
address(dpy, address_, this),
userLbl(dpy, "User:", this),
user(dpy, user_, this),
timeoutLbl(dpy, "Seconds until automatic reject:", this),
timeout(dpy, "0000000000", this),
accept(dpy, "Accept", this, this, 60),
reject(dpy, "Reject", this, this, 60),
callback(cb), timeUntilReject(timeout_), timer(this)
{
const int pad = 4;
int y=pad;
int lblWidth = __rfbmax(addressLbl.width(), userLbl.width());
userLbl.move(pad+lblWidth-userLbl.width(), y);
user.move(pad+lblWidth, y);
addressLbl.move(pad+lblWidth-addressLbl.width(), y+=userLbl.height());
address.move(pad+lblWidth, y);
timeoutLbl.move(pad, y+=addressLbl.height());
timeout.move(pad+timeoutLbl.width(), y);
accept.move(pad, y+=addressLbl.height());
int maxWidth = __rfbmax(user.width(), address.width()+pad+lblWidth);
maxWidth = __rfbmax(maxWidth, accept.width()*3);
maxWidth = __rfbmax(maxWidth, timeoutLbl.width()+timeout.width()+pad);
reject.move(maxWidth-reject.width(), y);
resize(maxWidth + pad, y+reject.height()+pad);
setBorderWidth(1);
refreshTimeout();
timer.start(1000);
}
void QueryConnectDialog::deleteWindow(TXWindow*) {
unmap();
callback->queryRejected();
}
void QueryConnectDialog::buttonActivate(TXButton* b) {
unmap();
if (b == &accept)
callback->queryApproved();
else if (b == &reject)
callback->queryRejected();
}
bool QueryConnectDialog::handleTimeout(rfb::Timer* t) {
if (timeUntilReject-- == 0) {
unmap();
callback->queryTimedOut();
return false;
} else {
refreshTimeout();
return true;
}
}
void QueryConnectDialog::refreshTimeout() {
char buf[16];
sprintf(buf, "%d", timeUntilReject);
timeout.setText(buf);
}

View File

@@ -0,0 +1,56 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#ifndef __QUERYCONNECTDIALOG_H__
#define __QUERYCONNECTDIALOG_H__
#include <rfb/Timer.h>
#include "TXLabel.h"
#include "TXButton.h"
#include "TXDialog.h"
class QueryResultCallback {
public:
virtual ~QueryResultCallback() {}
virtual void queryApproved() = 0;
virtual void queryRejected() = 0;
virtual void queryTimedOut() { queryRejected(); };
};
class QueryConnectDialog : public TXDialog, public TXEventHandler,
public TXButtonCallback,
public rfb::Timer::Callback
{
public:
QueryConnectDialog(Display* dpy, const char* address_,
const char* user_, int timeout_,
QueryResultCallback* cb);
void handleEvent(TXWindow*, XEvent* ) { }
void deleteWindow(TXWindow*);
void buttonActivate(TXButton* b);
bool handleTimeout(rfb::Timer* t);
private:
void refreshTimeout();
TXLabel addressLbl, address, userLbl, user, timeoutLbl, timeout;
TXButton accept, reject;
QueryResultCallback* callback;
int timeUntilReject;
rfb::Timer timer;
};
#endif

View File

@@ -0,0 +1,18 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
char buildtime[] = __DATE__ " " __TIME__;

319
unix/vncconfig/vncExt.c Normal file
View File

@@ -0,0 +1,319 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#include <stdio.h>
#include <stdint.h>
#define NEED_REPLIES
#include <X11/Xlib.h>
#include <X11/Xlibint.h>
#define _VNCEXT_PROTO_
#include "vncExt.h"
static Bool XVncExtQueryConnectNotifyWireToEvent(Display* dpy, XEvent* e,
xEvent* w);
static Bool extensionInited = False;
static XExtCodes* codes = 0;
static Bool checkExtension(Display* dpy)
{
if (!extensionInited) {
extensionInited = True;
codes = XInitExtension(dpy, VNCEXTNAME);
if (!codes) return False;
XESetWireToEvent(dpy, codes->first_event + VncExtQueryConnectNotify,
XVncExtQueryConnectNotifyWireToEvent);
}
return codes != 0;
}
Bool XVncExtQueryExtension(Display* dpy, int* event_basep, int* error_basep)
{
if (!checkExtension(dpy)) return False;
*event_basep = codes->first_event;
*error_basep = codes->first_error;
return True;
}
Bool XVncExtSetParam(Display* dpy, const char* param)
{
xVncExtSetParamReq* req;
xVncExtSetParamReply rep;
int paramLen = strlen(param);
if (paramLen > 255) return False;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtSetParam, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtSetParam;
req->length += (paramLen + 3) >> 2;
req->paramLen = paramLen;
Data(dpy, param, paramLen);
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
UnlockDisplay(dpy);
SyncHandle();
return rep.success;
}
Bool XVncExtGetParam(Display* dpy, const char* param, char** value, int* len)
{
xVncExtGetParamReq* req;
xVncExtGetParamReply rep;
int paramLen = strlen(param);
*value = 0;
*len = 0;
if (paramLen > 255) return False;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtGetParam, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtGetParam;
req->length += (paramLen + 3) >> 2;
req->paramLen = paramLen;
Data(dpy, param, paramLen);
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
if (rep.success) {
*len = rep.valueLen;
*value = (char*) Xmalloc (*len+1);
if (!*value) {
_XEatData(dpy, (*len+1)&~1);
return False;
}
_XReadPad(dpy, *value, *len);
(*value)[*len] = 0;
}
UnlockDisplay(dpy);
SyncHandle();
return rep.success;
}
char* XVncExtGetParamDesc(Display* dpy, const char* param)
{
xVncExtGetParamDescReq* req;
xVncExtGetParamDescReply rep;
char* desc = 0;
int paramLen = strlen(param);
if (paramLen > 255) return False;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtGetParamDesc, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtGetParamDesc;
req->length += (paramLen + 3) >> 2;
req->paramLen = paramLen;
Data(dpy, param, paramLen);
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
if (rep.success) {
desc = (char*)Xmalloc(rep.descLen+1);
if (!desc) {
_XEatData(dpy, (rep.descLen+1)&~1);
return False;
}
_XReadPad(dpy, desc, rep.descLen);
desc[rep.descLen] = 0;
}
UnlockDisplay(dpy);
SyncHandle();
return desc;
}
char** XVncExtListParams(Display* dpy, int* nParams)
{
xVncExtListParamsReq* req;
xVncExtListParamsReply rep;
char** list = 0;
char* ch;
int rlen, paramLen, i;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtListParams, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtListParams;
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
UnlockDisplay(dpy);
SyncHandle();
if (rep.nParams) {
list = (char**)Xmalloc(rep.nParams * sizeof(char*));
rlen = rep.length << 2;
ch = (char*)Xmalloc(rlen + 1);
if (!list || !ch) {
if (list) Xfree((char*)list);
if (ch) Xfree(ch);
_XEatData(dpy, rlen);
UnlockDisplay(dpy);
SyncHandle();
return 0;
}
_XReadPad(dpy, ch, rlen);
paramLen = *ch++;
for (i = 0; i < rep.nParams; i++) {
list[i] = ch;
ch += paramLen;
paramLen = *ch;
*ch++ = 0;
}
}
*nParams = rep.nParams;
UnlockDisplay(dpy);
SyncHandle();
return list;
}
void XVncExtFreeParamList(char** list)
{
if (list) {
Xfree(list[0]-1);
Xfree((char*)list);
}
}
Bool XVncExtSelectInput(Display* dpy, Window w, int mask)
{
xVncExtSelectInputReq* req;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtSelectInput, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtSelectInput;
req->window = w;
req->mask = mask;
UnlockDisplay(dpy);
SyncHandle();
return True;
}
Bool XVncExtConnect(Display* dpy, const char* hostAndPort)
{
xVncExtConnectReq* req;
xVncExtConnectReply rep;
int strLen = strlen(hostAndPort);
if (strLen > 255) return False;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtConnect, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtConnect;
req->length += (strLen + 3) >> 2;
req->strLen = strLen;
Data(dpy, hostAndPort, strLen);
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
UnlockDisplay(dpy);
SyncHandle();
return rep.success;
}
Bool XVncExtGetQueryConnect(Display* dpy, char** addr, char** user,
int* timeout, void** opaqueId)
{
xVncExtGetQueryConnectReq* req;
xVncExtGetQueryConnectReply rep;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtGetQueryConnect, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtGetQueryConnect;
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
return False;
}
UnlockDisplay(dpy);
SyncHandle();
*addr = Xmalloc(rep.addrLen+1);
*user = Xmalloc(rep.userLen+1);
if (!*addr || !*user) {
Xfree(*addr);
Xfree(*user);
_XEatData(dpy, ((rep.addrLen+1)&~1) + ((rep.userLen+1)&~1));
return False;
}
_XReadPad(dpy, *addr, rep.addrLen);
(*addr)[rep.addrLen] = 0;
_XReadPad(dpy, *user, rep.userLen);
(*user)[rep.userLen] = 0;
*timeout = rep.timeout;
*opaqueId = (void*)(intptr_t)rep.opaqueId;
return True;
}
Bool XVncExtApproveConnect(Display* dpy, void* opaqueId, int approve)
{
xVncExtApproveConnectReq* req;
if (!checkExtension(dpy)) return False;
LockDisplay(dpy);
GetReq(VncExtApproveConnect, req);
req->reqType = codes->major_opcode;
req->vncExtReqType = X_VncExtApproveConnect;
req->approve = approve;
req->opaqueId = (CARD32)(intptr_t)opaqueId;
UnlockDisplay(dpy);
SyncHandle();
return True;
}
static Bool XVncExtQueryConnectNotifyWireToEvent(Display* dpy, XEvent* e,
xEvent* w)
{
XVncExtQueryConnectEvent* ev = (XVncExtQueryConnectEvent*)e;
xVncExtQueryConnectNotifyEvent* wire
= (xVncExtQueryConnectNotifyEvent*)w;
ev->type = wire->type & 0x7f;
ev->serial = _XSetLastRequestRead(dpy,(xGenericReply*)wire);
ev->send_event = (wire->type & 0x80) != 0;
ev->display = dpy;
ev->window = wire->window;
return True;
}

258
unix/vncconfig/vncExt.h Normal file
View File

@@ -0,0 +1,258 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
#ifndef _VNCEXT_H_
#define _VNCEXT_H_
#ifdef __cplusplus
extern "C" {
#endif
#define X_VncExtSetParam 0
#define X_VncExtGetParam 1
#define X_VncExtGetParamDesc 2
#define X_VncExtListParams 3
#define X_VncExtSelectInput 6
#define X_VncExtConnect 7
#define X_VncExtGetQueryConnect 8
#define X_VncExtApproveConnect 9
#define VncExtQueryConnectNotify 2
#define VncExtQueryConnectMask (1 << VncExtQueryConnectNotify)
#define VncExtNumberEvents 3
#define VncExtNumberErrors 0
#ifndef _VNCEXT_SERVER_
Bool XVncExtQueryExtension(Display* dpy, int* event_basep, int* error_basep);
Bool XVncExtSetParam(Display* dpy, const char* param);
Bool XVncExtGetParam(Display* dpy, const char* param, char** value, int* len);
char* XVncExtGetParamDesc(Display* dpy, const char* param);
char** XVncExtListParams(Display* dpy, int* nParams);
void XVncExtFreeParamList(char** list);
Bool XVncExtSelectInput(Display* dpy, Window w, int mask);
Bool XVncExtConnect(Display* dpy, const char* hostAndPort);
Bool XVncExtGetQueryConnect(Display* dpy, char** addr,
char** user, int* timeout, void** opaqueId);
Bool XVncExtApproveConnect(Display* dpy, void* opaqueId, int approve);
typedef struct {
int type;
unsigned long serial;
Bool send_event;
Display *display;
Window window;
} XVncExtQueryConnectEvent;
#endif
#ifdef _VNCEXT_PROTO_
#define VNCEXTNAME "VNC-EXTENSION"
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtSetParam */
CARD16 length B16;
CARD8 paramLen;
CARD8 pad0;
CARD16 pad1 B16;
} xVncExtSetParamReq;
#define sz_xVncExtSetParamReq 8
typedef struct {
BYTE type; /* X_Reply */
BYTE success;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 pad0 B32;
CARD32 pad1 B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtSetParamReply;
#define sz_xVncExtSetParamReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtGetParam */
CARD16 length B16;
CARD8 paramLen;
CARD8 pad0;
CARD16 pad1 B16;
} xVncExtGetParamReq;
#define sz_xVncExtGetParamReq 8
typedef struct {
BYTE type; /* X_Reply */
BYTE success;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD16 valueLen B16;
CARD16 pad0 B16;
CARD32 pad1 B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtGetParamReply;
#define sz_xVncExtGetParamReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtGetParamDesc */
CARD16 length B16;
CARD8 paramLen;
CARD8 pad0;
CARD16 pad1 B16;
} xVncExtGetParamDescReq;
#define sz_xVncExtGetParamDescReq 8
typedef struct {
BYTE type; /* X_Reply */
BYTE success;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD16 descLen B16;
CARD16 pad0 B16;
CARD32 pad1 B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtGetParamDescReply;
#define sz_xVncExtGetParamDescReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtListParams */
CARD16 length B16;
} xVncExtListParamsReq;
#define sz_xVncExtListParamsReq 4
typedef struct {
BYTE type; /* X_Reply */
BYTE pad0;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD16 nParams B16;
CARD16 pad1 B16;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xVncExtListParamsReply;
#define sz_xVncExtListParamsReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtSelectInput */
CARD16 length B16;
CARD32 window B32;
CARD32 mask B32;
} xVncExtSelectInputReq;
#define sz_xVncExtSelectInputReq 12
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtConnect */
CARD16 length B16;
CARD8 strLen;
CARD8 pad0;
CARD16 pad1 B16;
} xVncExtConnectReq;
#define sz_xVncExtConnectReq 8
typedef struct {
BYTE type; /* X_Reply */
BYTE success;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 pad0 B32;
CARD32 pad1 B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtConnectReply;
#define sz_xVncExtConnectReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtGetQueryConnect */
CARD16 length B16;
} xVncExtGetQueryConnectReq;
#define sz_xVncExtGetQueryConnectReq 4
typedef struct {
BYTE type; /* X_Reply */
BYTE pad0;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 addrLen B32;
CARD32 userLen B32;
CARD32 timeout B32;
CARD32 opaqueId B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtGetQueryConnectReply;
#define sz_xVncExtGetQueryConnectReply 32
typedef struct {
CARD8 reqType; /* always VncExtReqCode */
CARD8 vncExtReqType; /* always VncExtApproveConnect */
CARD16 length B16;
CARD8 approve;
CARD8 pad0;
CARD16 pad1;
CARD32 opaqueId B32;
} xVncExtApproveConnectReq;
#define sz_xVncExtApproveConnectReq 12
typedef struct {
BYTE type; /* always eventBase + VncExtQueryConnectNotify */
BYTE pad0;
CARD16 sequenceNumber B16;
CARD32 window B32;
CARD32 pad6 B32;
CARD32 pad1 B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
} xVncExtQueryConnectNotifyEvent;
#define sz_xVncExtQueryConnectNotifyEvent 32
#endif
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,335 @@
/* Copyright (C) 2002-2005 RealVNC Ltd. All Rights Reserved.
* Copyright 2012-2016 Pierre Ossman for Cendio AB
*
* This is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
* USA.
*/
//
// VNC server configuration utility
//
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
#include <errno.h>
#include <signal.h>
#include <X11/X.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <X11/Xutil.h>
#include <X11/keysym.h>
#include "vncExt.h"
#include <rdr/Exception.h>
#include <rfb/Configuration.h>
#include <rfb/Logger_stdio.h>
#include <rfb/LogWriter.h>
#include "TXWindow.h"
#include "TXCheckbox.h"
#include "TXLabel.h"
#include "QueryConnectDialog.h"
using namespace rfb;
LogWriter vlog("vncconfig");
StringParameter displayname("display", "The X display", "");
BoolParameter noWindow("nowin", "Don't display a window", 0);
BoolParameter iconic("iconic", "Start with window iconified", 0);
#define ACCEPT_CUT_TEXT "AcceptCutText"
#define SEND_CUT_TEXT "SendCutText"
#define SET_PRIMARY "SetPrimary"
#define SEND_PRIMARY "SendPrimary"
char* programName = 0;
Display* dpy;
int vncExtEventBase, vncExtErrorBase;
static bool getBoolParam(Display* dpy, const char* param) {
char* data;
int len;
if (XVncExtGetParam(dpy, param, &data, &len)) {
if (strcmp(data,"1") == 0) return true;
}
return false;
}
class VncConfigWindow : public TXWindow, public TXEventHandler,
public TXDeleteWindowCallback,
public TXCheckboxCallback,
public QueryResultCallback {
public:
VncConfigWindow(Display* dpy)
: TXWindow(dpy, 300, 100),
acceptClipboard(dpy, "Accept clipboard from viewers", this, false, this),
setPrimaryCB(dpy, "Also set primary selection", this, false, this),
sendClipboard(dpy, "Send clipboard to viewers", this, false, this),
sendPrimaryCB(dpy, "Send primary selection to viewers", this,false,this),
queryConnectDialog(0)
{
int y = yPad;
acceptClipboard.move(xPad, y);
acceptClipboard.checked(getBoolParam(dpy, ACCEPT_CUT_TEXT));
y += acceptClipboard.height();
setPrimaryCB.move(xPad + 10, y);
setPrimaryCB.checked(getBoolParam(dpy, SET_PRIMARY));
setPrimaryCB.disabled(!acceptClipboard.checked());
y += setPrimaryCB.height();
sendClipboard.move(xPad, y);
sendClipboard.checked(getBoolParam(dpy, SEND_CUT_TEXT));
y += sendClipboard.height();
sendPrimaryCB.move(xPad + 10, y);
sendPrimaryCB.checked(getBoolParam(dpy, SEND_PRIMARY));
sendPrimaryCB.disabled(!sendClipboard.checked());
y += sendPrimaryCB.height();
setEventHandler(this);
toplevel("VNC config", this, 0, 0, 0, iconic);
XVncExtSelectInput(dpy, win(), VncExtQueryConnectMask);
}
// handleEvent()
virtual void handleEvent(TXWindow* w, XEvent* ev) {
if (ev->type == vncExtEventBase + VncExtQueryConnectNotify) {
vlog.debug("query connection event");
if (queryConnectDialog)
delete queryConnectDialog;
queryConnectDialog = 0;
char* qcAddress;
char* qcUser;
int qcTimeout;
if (XVncExtGetQueryConnect(dpy, &qcAddress, &qcUser,
&qcTimeout, &queryConnectId)) {
if (qcTimeout)
queryConnectDialog = new QueryConnectDialog(dpy, qcAddress,
qcUser, qcTimeout,
this);
if (queryConnectDialog)
queryConnectDialog->map();
XFree(qcAddress);
XFree(qcUser);
}
}
}
// TXDeleteWindowCallback method
virtual void deleteWindow(TXWindow* w) {
exit(1);
}
// TXCheckboxCallback method
virtual void checkboxSelect(TXCheckbox* checkbox) {
if (checkbox == &acceptClipboard) {
XVncExtSetParam(dpy, (acceptClipboard.checked()
? ACCEPT_CUT_TEXT "=1" : ACCEPT_CUT_TEXT "=0"));
setPrimaryCB.disabled(!acceptClipboard.checked());
} else if (checkbox == &sendClipboard) {
XVncExtSetParam(dpy, (sendClipboard.checked()
? SEND_CUT_TEXT "=1" : SEND_CUT_TEXT "=0"));
sendPrimaryCB.disabled(!sendClipboard.checked());
} else if (checkbox == &setPrimaryCB) {
XVncExtSetParam(dpy, (setPrimaryCB.checked()
? SET_PRIMARY "=1" : SET_PRIMARY "=0"));
} else if (checkbox == &sendPrimaryCB) {
XVncExtSetParam(dpy, (sendPrimaryCB.checked()
? SEND_PRIMARY "=1" : SEND_PRIMARY "=0"));
}
}
// QueryResultCallback interface
virtual void queryApproved() {
XVncExtApproveConnect(dpy, queryConnectId, 1);
}
virtual void queryRejected() {
XVncExtApproveConnect(dpy, queryConnectId, 0);
}
private:
TXCheckbox acceptClipboard, setPrimaryCB;
TXCheckbox sendClipboard, sendPrimaryCB;
QueryConnectDialog* queryConnectDialog;
void* queryConnectId;
};
static void usage()
{
fprintf(stderr,"usage: %s [parameters]\n",
programName);
fprintf(stderr," %s [parameters] -connect <host>[:<port>]\n",
programName);
fprintf(stderr," %s [parameters] -disconnect\n", programName);
fprintf(stderr," %s [parameters] [-set] <Xvnc-param>=<value> ...\n",
programName);
fprintf(stderr," %s [parameters] -list\n", programName);
fprintf(stderr," %s [parameters] -get <param>\n", programName);
fprintf(stderr," %s [parameters] -desc <param>\n",programName);
fprintf(stderr,"\n"
"Parameters can be turned on with -<param> or off with -<param>=0\n"
"Parameters which take a value can be specified as "
"-<param> <value>\n"
"Other valid forms are <param>=<value> -<param>=<value> "
"--<param>=<value>\n"
"Parameter names are case-insensitive. The parameters are:\n\n");
Configuration::listParams(79, 14);
exit(1);
}
void removeArgs(int* argc, char** argv, int first, int n)
{
if (first + n > *argc) return;
for (int i = first + n; i < *argc; i++)
argv[i-n] = argv[i];
*argc -= n;
}
int main(int argc, char** argv)
{
programName = argv[0];
rfb::initStdIOLoggers();
rfb::LogWriter::setLogParams("*:stderr:30");
// Process vncconfig's own parameters first, then we process the
// other arguments when we have the X display.
int i;
for (i = 1; i < argc; i++) {
if (Configuration::setParam(argv[i]))
continue;
if (argv[i][0] == '-' && i+1 < argc &&
Configuration::setParam(&argv[i][1], argv[i+1])) {
i++;
continue;
}
break;
}
CharArray displaynameStr(displayname.getData());
if (!(dpy = XOpenDisplay(displaynameStr.buf))) {
fprintf(stderr,"%s: unable to open display \"%s\"\n",
programName, XDisplayName(displaynameStr.buf));
exit(1);
}
if (!XVncExtQueryExtension(dpy, &vncExtEventBase, &vncExtErrorBase)) {
fprintf(stderr,"No VNC extension on display %s\n",
XDisplayName(displaynameStr.buf));
exit(1);
}
if (i < argc) {
for (; i < argc; i++) {
if (strcmp(argv[i], "-connect") == 0) {
i++;
if (i >= argc) usage();
if (!XVncExtConnect(dpy, argv[i])) {
fprintf(stderr,"connecting to %s failed\n",argv[i]);
}
} else if (strcmp(argv[i], "-disconnect") == 0) {
if (!XVncExtConnect(dpy, "")) {
fprintf(stderr,"disconnecting all clients failed\n");
}
} else if (strcmp(argv[i], "-get") == 0) {
i++;
if (i >= argc) usage();
char* data;
int len;
if (XVncExtGetParam(dpy, argv[i], &data, &len)) {
printf("%.*s\n",len,data);
} else {
fprintf(stderr,"getting param %s failed\n",argv[i]);
}
XFree(data);
} else if (strcmp(argv[i], "-desc") == 0) {
i++;
if (i >= argc) usage();
char* desc = XVncExtGetParamDesc(dpy, argv[i]);
if (desc) {
printf("%s\n",desc);
} else {
fprintf(stderr,"getting description for param %s failed\n",argv[i]);
}
XFree(desc);
} else if (strcmp(argv[i], "-list") == 0) {
int nParams;
char** list = XVncExtListParams(dpy, &nParams);
for (int i = 0; i < nParams; i++) {
printf("%s\n",list[i]);
}
XVncExtFreeParamList(list);
} else if (strcmp(argv[i], "-set") == 0) {
i++;
if (i >= argc) usage();
if (!XVncExtSetParam(dpy, argv[i])) {
fprintf(stderr,"setting param %s failed\n",argv[i]);
}
} else if (XVncExtSetParam(dpy, argv[i])) {
fprintf(stderr,"set parameter %s\n",argv[i]);
} else {
usage();
}
}
return 0;
}
try {
TXWindow::init(dpy,"Vncconfig");
VncConfigWindow w(dpy);
if (!noWindow) w.map();
while (true) {
struct timeval tv;
struct timeval* tvp = 0;
// Process any incoming X events
TXWindow::handleXEvents(dpy);
// Process expired timers and get the time until the next one
int timeoutMs = Timer::checkTimeouts();
if (timeoutMs) {
tv.tv_sec = timeoutMs / 1000;
tv.tv_usec = (timeoutMs % 1000) * 1000;
tvp = &tv;
}
// If there are X requests pending then poll, don't wait!
if (XPending(dpy)) {
tv.tv_usec = tv.tv_sec = 0;
tvp = &tv;
}
// Wait for X events, VNC traffic, or the next timer expiry
fd_set rfds;
FD_ZERO(&rfds);
FD_SET(ConnectionNumber(dpy), &rfds);
int n = select(FD_SETSIZE, &rfds, 0, 0, tvp);
if (n < 0) throw rdr::SystemException("select",errno);
}
XCloseDisplay(dpy);
} catch (rdr::Exception &e) {
vlog.error("%s", e.str());
}
return 0;
}

View File

@@ -0,0 +1,126 @@
.TH vncconfig 1 "" "KasmVNC" "Virtual Network Computing"
.SH NAME
vncconfig \- configure and control a VNC server
.SH SYNOPSIS
.B vncconfig
.RI [ parameters ]
.br
.B vncconfig
.RI [ parameters ]
.B \-connect
.IR host [: port ]
.br
.B vncconfig
.RI [ parameters ]
.B \-disconnect
.br
.B vncconfig
.RI [ parameters ]
.RB [ -set ]
.IR Xvnc-param = value " ..."
.br
.B vncconfig
.RI [ parameters ]
.B \-list
.br
.B vncconfig
.RI [ parameters ]
\fB\-get\fP \fIXvnc-param\fP
.br
.B vncconfig
.RI [ parameters ]
\fB\-desc\fP \fIXvnc-param\fP
.SH DESCRIPTION
.B vncconfig
is used to configure and control a running instance of Xvnc, or any other X
server with the VNC extension. Note that it cannot be used to control VNC
servers prior to version 4.
When run with no options, it runs as a kind of "helper" application for Xvnc.
Its main purpose when run in this mode is to query the user how new
connections should be handled (provided this feature is enabled). The
\fB-nowin\fP flag can be used if you always want the query support but don't
wish to clutter the desktop with the settings window - alternatively the
\fB-iconic\fP option can be used to make it iconified by default.
When run in any other mode, \fBvncconfig\fP is a one-shot program used to
configure or control Xvnc as appropriate. It can be used to tell Xvnc to
connect or disconnect from listening viewers, and to set and retrieve Xvnc's
parameters.
Note that the DISPLAY environment variable or the \fB\-display\fP option
must be set as appropriate to control Xvnc. If you run it on an ordinary X
server (or on a version 3 Xvnc) you will get an error message saying that there
is no VNC extension.
.SH OPTIONS
.TP
.B \-connect \fIhost\fP[:\fIport\fP]
Tells an Xvnc server to make a "reverse" connection to a listening VNC viewer
(normally connections are made the other way round - the viewer connects to the
server). \fIhost\fP is the host where the listening viewer is running. If it's
not listening on the default port of 5500, you can specify \fIhost:port\fP
instead.
.
.TP
.B \-disconnect
This causes Xvnc to disconnect from all viewers so that the VNC desktop is not
displayed anywhere.
.
.TP
[\fB-set\fP] \fIXvnc-param\fP=\fIvalue\fP
Sets an Xvnc parameter to the given value. Note that some of Xvnc's parameters
are read only once at startup so that changing them in this way may not have
any effect.
.
.TP
.B \-list
Lists all the parameters supported by Xvnc.
.
.TP
.B \-get \fIXvnc-param\fP
Prints the current value of the given Xvnc parameter.
.
.TP
.B \-desc \fIXvnc-param\fP
Prints a short description of the given Xvnc parameter.
.SH PARAMETERS
.B vncconfig
also has parameters of its own which can be set on the command line. These
should not be confused with Xvnc's parameters which are manipulated with the
\fB-set\fP, \fB-get\fP, \fB-list\fP and \fB-desc\fP options.
Parameters can be turned on with -\fIparam\fP or off with -\fIparam\fP=0.
Parameters which take a value can be specified as -\fIparam\fP \fIvalue\fP.
Other valid forms are \fIparam\fP\fB=\fP\fIvalue\fP -\fIparam\fP=\fIvalue\fP
--\fIparam\fP=\fIvalue\fP. Parameter names are case-insensitive.
.TP
.B \-display \fIXdisplay\fP
Specifies the Xvnc server to control.
.
.TP
.B \-nowin
When run as a "helper" app, don't put up a window.
.
.TP
.B \-iconic
When run as a "helper" app, make the window iconified at startup.
.SH SEE ALSO
.BR vncpasswd (1),
.BR vncviewer (1),
.BR vncserver (1),
.BR Xvnc (1)
.br
http://kasmweb.com
.SH AUTHOR
Tristan Richardson, RealVNC Ltd. and others.
VNC was originally developed by the RealVNC team while at Olivetti
Research Ltd / AT&T Laboratories Cambridge. TightVNC additions were
implemented by Constantin Kaplinsky. Many other people have since
participated in development, testing and support. This manual is part
of the KasmVNC software suite.