Merge branch 'XACE-modular'

This commit is contained in:
Alan Coopersmith 2006-10-06 18:01:13 -07:00
commit 4c34224630
30 changed files with 1271 additions and 560 deletions

View File

@ -33,6 +33,10 @@ MODULE_SRCS = \
sync.c \
xcmisc.c
# Extra configuration files ship with some extensions
SERVERCONFIGdir = $(libdir)/xserver
SERVERCONFIG_DATA =
# Optional sources included if extension enabled by configure.ac rules
# MIT Shared Memory extension
@ -65,13 +69,19 @@ if XINERAMA
BUILTIN_SRCS += $(XINERAMA_SRCS)
endif
# X-ACE extension: provides hooks for building security policy extensions
# like XC-Security, X-SELinux & XTSol
XACE_SRCS = xace.c xace.h xacestr.h
if XACE
BUILTIN_SRCS += $(XACE_SRCS)
endif
# Security extension: multi-level security to protect clients from each other
XCSECURITY_SRCS = security.c securitysrv.h
if XCSECURITY
BUILTIN_SRCS += $(XCSECURITY_SRCS)
SERVERCONFIGdir = $(libdir)/xserver
SERVERCONFIG_DATA = SecurityPolicy
SERVERCONFIG_DATA += SecurityPolicy
AM_CFLAGS += -DDEFAULTPOLICYFILE=\"$(SERVERCONFIGdir)/SecurityPolicy\"
endif
@ -150,11 +160,12 @@ libXextmodule_la_SOURCES = $(MODULE_SRCS)
endif
EXTRA_DIST = \
SecurityPolicy \
$(SERVERCONFIG_DATA) \
$(MITSHM_SRCS) \
$(XV_SRCS) \
$(RES_SRCS) \
$(SCREENSAVER_SRCS) \
$(XACE_SRCS) \
$(XCSECURITY_SRCS) \
$(XCALIBRATE_SRCS) \
$(XINERAMA_SRCS) \

View File

@ -41,6 +41,7 @@ from The Open Group.
#include "servermd.h"
#define _XAG_SERVER_
#include <X11/extensions/Xagstr.h>
#include "xacestr.h"
#include "securitysrv.h"
#include <X11/Xfuncproto.h>
@ -121,62 +122,11 @@ void XagClientStateChange(
pointer nulldata,
pointer calldata)
{
SecurityAuthorizationPtr pAuth;
NewClientInfoRec* pci = (NewClientInfoRec*) calldata;
ClientPtr pClient = pci->client;
AppGroupPtr pAppGrp;
XID authId = 0;
AppGroupPtr pAppGrp = pClient->appgroup;
int slot;
if (!pClient->appgroup) {
switch (pClient->clientState) {
case ClientStateAuthenticating:
case ClientStateRunning:
case ClientStateCheckingSecurity:
return;
case ClientStateInitial:
case ClientStateCheckedSecurity:
/*
* If the client is connecting via a firewall proxy (which
* uses XC-QUERY-SECURITY-1, then the authId is available
* during ClientStateCheckedSecurity, otherwise it's
* available during ClientStateInitial.
*
* Don't get it from pClient because can't guarantee the order
* of the callbacks and the security extension might not have
* plugged it in yet.
*/
authId = AuthorizationIDOfClient(pClient);
break;
case ClientStateGone:
case ClientStateRetained:
/*
* Don't get if from AuthorizationIDOfClient because can't
* guarantee the order of the callbacks and the security
* extension may have torn down the client's private data
*/
authId = pClient->authId;
break;
}
if (authId == None)
return;
pAuth = (SecurityAuthorizationPtr)SecurityLookupIDByType(pClient,
authId, SecurityAuthorizationResType, SecurityReadAccess);
if (pAuth == NULL)
return;
for (pAppGrp = appGrpList; pAppGrp != NULL; pAppGrp = pAppGrp->next)
if (pAppGrp->appgroupId == pAuth->group) break;
} else {
pAppGrp = pClient->appgroup;
}
if (!pAppGrp)
return;
@ -233,6 +183,7 @@ XagExtensionInit(INITARGS)
XagResetProc,
StandardMinorOpcode)) {
RT_APPGROUP = CreateNewResourceType (XagAppGroupFree);
XaceRegisterCallback(XACE_AUTH_AVAIL, XagCallClientStateChange, NULL);
}
}
@ -799,12 +750,33 @@ void XagGetDeltaInfo(
}
void XagCallClientStateChange(
ClientPtr client)
CallbackListPtr *pcbl,
pointer nulldata,
pointer calldata)
{
if (appGrpList) {
XaceAuthAvailRec* rec = (XaceAuthAvailRec*) calldata;
ClientPtr pClient = rec->client;
if (!pClient->appgroup) {
SecurityAuthorizationPtr pAuth;
XID authId = rec->authId;
/* can't use SecurityLookupIDByType here -- client
* security state hasn't been setup yet.
*/
pAuth = (SecurityAuthorizationPtr)LookupIDByType(authId,
SecurityAuthorizationResType);
if (!pAuth)
return;
pClient->appgroup = (AppGroupPtr)LookupIDByType(pAuth->group,
RT_APPGROUP);
}
if (pClient->appgroup) {
NewClientInfoRec clientinfo;
clientinfo.client = client;
clientinfo.client = pClient;
XagClientStateChange (NULL, NULL, (pointer)&clientinfo);
}
}

View File

@ -51,7 +51,9 @@ extern ClientPtr XagLeader(
);
extern void XagCallClientStateChange(
ClientPtr /* client */
CallbackListPtr * /* pcbl */,
pointer /* nulldata */,
pointer /* calldata */
);
extern Bool XagIsControlledRoot (

View File

@ -36,6 +36,7 @@ in this Software without prior written authorization from The Open Group.
#include "gcstruct.h"
#include "colormapst.h"
#include "propertyst.h"
#include "xacestr.h"
#include "securitysrv.h"
#include <X11/extensions/securstr.h>
#include <assert.h>
@ -58,6 +59,23 @@ in this Software without prior written authorization from The Open Group.
static int SecurityErrorBase; /* first Security error number */
static int SecurityEventBase; /* first Security event number */
static int securityClientPrivateIndex;
static int securityExtnsnPrivateIndex;
/* this is what we store as client security state */
typedef struct {
unsigned int trustLevel;
XID authId;
} SecurityClientStateRec;
#define STATEVAL(extnsn) \
((extnsn)->devPrivates[securityExtnsnPrivateIndex].val)
#define STATEPTR(client) \
((client)->devPrivates[securityClientPrivateIndex].ptr)
#define TRUSTLEVEL(client) \
(((SecurityClientStateRec*)STATEPTR(client))->trustLevel)
#define AUTHID(client) \
(((SecurityClientStateRec*)STATEPTR(client))->authId)
CallbackListPtr SecurityValidateGroupCallback = NULL; /* see security.h */
@ -65,19 +83,8 @@ RESTYPE SecurityAuthorizationResType; /* resource type for authorizations */
static RESTYPE RTEventClient;
/* Proc vectors for untrusted clients, swapped and unswapped versions.
* These are the same as the normal proc vectors except that extensions
* that haven't declared themselves secure will have ProcBadRequest plugged
* in for their major opcode dispatcher. This prevents untrusted clients
* from guessing extension major opcodes and using the extension even though
* the extension can't be listed or queried.
*/
int (*UntrustedProcVector[256])(
ClientPtr /*client*/
);
int (*SwappedUntrustedProcVector[256])(
ClientPtr /*client*/
);
#define CALLBACK(name) static void \
name(CallbackListPtr *pcbl, pointer nulldata, pointer calldata)
/* SecurityAudit
*
@ -91,7 +98,7 @@ int (*SwappedUntrustedProcVector[256])(
* Writes the message to the log file if security logging is on.
*/
void
static void
SecurityAudit(char *format, ...)
{
va_list args;
@ -164,7 +171,7 @@ SecurityDeleteAuthorization(
for (i = 1; i<currentMaxClients; i++)
{
if (clients[i] && (clients[i]->authId == pAuth->id))
if (clients[i] && (AUTHID(clients[i]) == pAuth->id))
CloseDownClient(clients[i]);
}
@ -318,7 +325,7 @@ ProcSecurityQueryVersion(
/* paranoia: this "can't happen" because this extension is hidden
* from untrusted clients, but just in case...
*/
if (client->trustLevel != XSecurityClientTrusted)
if (TRUSTLEVEL(client) != XSecurityClientTrusted)
return BadRequest;
REQUEST_SIZE_MATCH(xSecurityQueryVersionReq);
@ -404,7 +411,7 @@ ProcSecurityGenerateAuthorization(
/* paranoia: this "can't happen" because this extension is hidden
* from untrusted clients, but just in case...
*/
if (client->trustLevel != XSecurityClientTrusted)
if (TRUSTLEVEL(client) != XSecurityClientTrusted)
return BadRequest;
/* check request length */
@ -587,7 +594,7 @@ ProcSecurityRevokeAuthorization(
/* paranoia: this "can't happen" because this extension is hidden
* from untrusted clients, but just in case...
*/
if (client->trustLevel != XSecurityClientTrusted)
if (TRUSTLEVEL(client) != XSecurityClientTrusted)
return BadRequest;
REQUEST_SIZE_MATCH(xSecurityRevokeAuthorizationReq);
@ -772,12 +779,12 @@ SecurityDetermineEventPropogationLimits(
* An audit message is generated if access is denied.
*/
Bool
SecurityCheckDeviceAccess(client, dev, fromRequest)
ClientPtr client;
DeviceIntPtr dev;
Bool fromRequest;
CALLBACK(SecurityCheckDeviceAccess)
{
XaceDeviceAccessRec *rec = (XaceDeviceAccessRec*)calldata;
ClientPtr client = rec->client;
DeviceIntPtr dev = rec->dev;
Bool fromRequest = rec->fromRequest;
WindowPtr pWin, pStopWin;
Bool untrusted_got_event;
Bool found_event_window;
@ -785,12 +792,12 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
int reqtype = 0;
/* trusted clients always allowed to do anything */
if (client->trustLevel == XSecurityClientTrusted)
return TRUE;
if (TRUSTLEVEL(client) == XSecurityClientTrusted)
return;
/* device security other than keyboard is not implemented yet */
if (dev != inputInfo.keyboard)
return TRUE;
return;
/* some untrusted client wants access */
@ -805,7 +812,8 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
case X_SetModifierMapping:
SecurityAudit("client %d attempted request %d\n",
client->index, reqtype);
return FALSE;
rec->rval = FALSE;
return;
default:
break;
}
@ -817,7 +825,7 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
if (dev->grab)
{
untrusted_got_event =
((rClient(dev->grab))->trustLevel != XSecurityClientTrusted);
(TRUSTLEVEL(rClient(dev->grab)) != XSecurityClientTrusted);
}
else
{
@ -832,7 +840,7 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
{
found_event_window = TRUE;
client = wClient(pWin);
if (client->trustLevel != XSecurityClientTrusted)
if (TRUSTLEVEL(client) != XSecurityClientTrusted)
{
untrusted_got_event = TRUE;
}
@ -845,7 +853,7 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
if (other->mask & eventmask)
{
client = rClient(other);
if (client->trustLevel != XSecurityClientTrusted)
if (TRUSTLEVEL(client) != XSecurityClientTrusted)
{
untrusted_got_event = TRUE;
break;
@ -873,8 +881,9 @@ SecurityCheckDeviceAccess(client, dev, fromRequest)
else
SecurityAudit("client %d attempted to access device %d (%s)\n",
client->index, dev->id, devname);
rec->rval = FALSE;
}
return untrusted_got_event;
return;
} /* SecurityCheckDeviceAccess */
@ -946,20 +955,22 @@ SecurityAuditResourceIDAccess(
* Disallowed resource accesses are audited.
*/
static pointer
SecurityCheckResourceIDAccess(
ClientPtr client,
XID id,
RESTYPE rtype,
Mask access_mode,
pointer rval)
CALLBACK(SecurityCheckResourceIDAccess)
{
int cid = CLIENT_ID(id);
int reqtype = ((xReq *)client->requestBuffer)->reqType;
XaceResourceAccessRec *rec = (XaceResourceAccessRec*)calldata;
ClientPtr client = rec->client;
XID id = rec->id;
RESTYPE rtype = rec->rtype;
Mask access_mode = rec->access_mode;
pointer rval = rec->res;
int cid, reqtype;
if (SecurityUnknownAccess == access_mode)
return rval; /* for compatibility, we have to allow access */
if (TRUSTLEVEL(client) == XSecurityClientTrusted ||
SecurityUnknownAccess == access_mode)
return; /* for compatibility, we have to allow access */
cid = CLIENT_ID(id);
reqtype = ((xReq *)client->requestBuffer)->reqType;
switch (reqtype)
{ /* these are always allowed */
case X_QueryTree:
@ -971,7 +982,7 @@ SecurityCheckResourceIDAccess(
case X_DeleteProperty:
case X_RotateProperties:
case X_ListProperties:
return rval;
return;
default:
break;
}
@ -991,15 +1002,15 @@ SecurityCheckResourceIDAccess(
* competing alternative for grouping clients for security purposes is to
* use app groups. dpw
*/
if (client->trustLevel == clients[cid]->trustLevel
if (TRUSTLEVEL(client) == TRUSTLEVEL(clients[cid])
#ifdef XAPPGROUP
|| (RT_COLORMAP == rtype &&
XagDefaultColormap (client) == (Colormap) id)
#endif
)
return rval;
return;
else
return SecurityAuditResourceIDAccess(client, id);
goto deny;
}
else /* server-owned resource - probably a default colormap or root window */
{
@ -1035,7 +1046,7 @@ SecurityCheckResourceIDAccess(
)
)
{ /* not an ICCCM event */
return SecurityAuditResourceIDAccess(client, id);
goto deny;
}
break;
} /* case X_SendEvent on root */
@ -1053,28 +1064,31 @@ SecurityCheckResourceIDAccess(
~(PropertyChangeMask|StructureNotifyMask)) == 0)
break;
}
return SecurityAuditResourceIDAccess(client, id);
goto deny;
} /* case X_ChangeWindowAttributes on root */
default:
{
/* others not allowed */
return SecurityAuditResourceIDAccess(client, id);
goto deny;
}
}
} /* end server-owned window or drawable */
else if (SecurityAuthorizationResType == rtype)
{
SecurityAuthorizationPtr pAuth = (SecurityAuthorizationPtr)rval;
if (pAuth->trustLevel != client->trustLevel)
return SecurityAuditResourceIDAccess(client, id);
if (pAuth->trustLevel != TRUSTLEVEL(client))
goto deny;
}
else if (RT_COLORMAP != rtype)
{ /* don't allow anything else besides colormaps */
return SecurityAuditResourceIDAccess(client, id);
goto deny;
}
}
return rval;
return;
deny:
SecurityAuditResourceIDAccess(client, id);
rec->rval = FALSE; /* deny access */
} /* SecurityCheckResourceIDAccess */
@ -1093,30 +1107,32 @@ SecurityCheckResourceIDAccess(
* If a new client is connecting, its authorization ID is copied to
* client->authID. If this is a generated authorization, its reference
* count is bumped, its timer is cancelled if it was running, and its
* trustlevel is copied to client->trustLevel.
* trustlevel is copied to TRUSTLEVEL(client).
*
* If a client is disconnecting and the client was using a generated
* authorization, the authorization's reference count is decremented, and
* if it is now zero, the timer for this authorization is started.
*/
static void
SecurityClientStateCallback(
CallbackListPtr *pcbl,
pointer nulldata,
pointer calldata)
CALLBACK(SecurityClientStateCallback)
{
NewClientInfoRec *pci = (NewClientInfoRec *)calldata;
ClientPtr client = pci->client;
switch (client->clientState)
{
case ClientStateInitial:
TRUSTLEVEL(serverClient) = XSecurityClientTrusted;
AUTHID(serverClient) = None;
break;
case ClientStateRunning:
{
XID authId = AuthorizationIDOfClient(client);
SecurityAuthorizationPtr pAuth;
client->authId = authId;
TRUSTLEVEL(client) = XSecurityClientTrusted;
AUTHID(client) = authId;
pAuth = (SecurityAuthorizationPtr)LookupIDByType(authId,
SecurityAuthorizationResType);
if (pAuth)
@ -1126,23 +1142,20 @@ SecurityClientStateCallback(
{
if (pAuth->timer) TimerCancel(pAuth->timer);
}
client->trustLevel = pAuth->trustLevel;
if (client->trustLevel != XSecurityClientTrusted)
{
client->CheckAccess = SecurityCheckResourceIDAccess;
client->requestVector = client->swapped ?
SwappedUntrustedProcVector : UntrustedProcVector;
}
TRUSTLEVEL(client) = pAuth->trustLevel;
}
break;
}
case ClientStateGone:
case ClientStateRetained: /* client disconnected */
{
XID authId = client->authId;
SecurityAuthorizationPtr pAuth;
pAuth = (SecurityAuthorizationPtr)LookupIDByType(authId,
/* client may not have any state (bad authorization) */
if (!STATEPTR(client))
break;
pAuth = (SecurityAuthorizationPtr)LookupIDByType(AUTHID(client),
SecurityAuthorizationResType);
if (pAuth)
{ /* it is a generated authorization */
@ -1158,124 +1171,68 @@ SecurityClientStateCallback(
}
} /* SecurityClientStateCallback */
/* SecurityCensorImage
*
* Called after pScreen->GetImage to prevent pieces or trusted windows from
* being returned in image data from an untrusted window.
*
* Arguments:
* client is the client doing the GetImage.
* pVisibleRegion is the visible region of the window.
* widthBytesLine is the width in bytes of one horizontal line in pBuf.
* pDraw is the source window.
* x, y, w, h is the rectangle of image data from pDraw in pBuf.
* format is the format of the image data in pBuf: ZPixmap or XYPixmap.
* pBuf is the image data.
*
* Returns: nothing.
*
* Side Effects:
* Any part of the rectangle (x, y, w, h) that is outside the visible
* region of the window will be destroyed (overwritten) in pBuf.
*/
void
SecurityCensorImage(client, pVisibleRegion, widthBytesLine, pDraw, x, y, w, h,
format, pBuf)
ClientPtr client;
RegionPtr pVisibleRegion;
long widthBytesLine;
DrawablePtr pDraw;
int x, y, w, h;
unsigned int format;
char * pBuf;
CALLBACK(SecurityCheckDrawableAccess)
{
RegionRec imageRegion; /* region representing x,y,w,h */
RegionRec censorRegion; /* region to obliterate */
BoxRec imageBox;
int nRects;
XaceDrawableAccessRec *rec = (XaceDrawableAccessRec*)calldata;
imageBox.x1 = x;
imageBox.y1 = y;
imageBox.x2 = x + w;
imageBox.y2 = y + h;
REGION_INIT(pScreen, &imageRegion, &imageBox, 1);
REGION_NULL(pScreen, &censorRegion);
if (TRUSTLEVEL(rec->client) != XSecurityClientTrusted)
rec->rval = FALSE;
}
/* censorRegion = imageRegion - visibleRegion */
REGION_SUBTRACT(pScreen, &censorRegion, &imageRegion, pVisibleRegion);
nRects = REGION_NUM_RECTS(&censorRegion);
if (nRects > 0)
{ /* we have something to censor */
GCPtr pScratchGC = NULL;
PixmapPtr pPix = NULL;
xRectangle *pRects = NULL;
Bool failed = FALSE;
int depth = 1;
int bitsPerPixel = 1;
int i;
BoxPtr pBox;
CALLBACK(SecurityCheckMapAccess)
{
XaceMapAccessRec *rec = (XaceMapAccessRec*)calldata;
WindowPtr pWin = rec->pWin;
/* convert region to list-of-rectangles for PolyFillRect */
if (STATEPTR(rec->client) &&
(TRUSTLEVEL(rec->client) != XSecurityClientTrusted) &&
(pWin->drawable.class == InputOnly) &&
(TRUSTLEVEL(wClient(pWin->parent)) == XSecurityClientTrusted))
pRects = (xRectangle *)ALLOCATE_LOCAL(nRects * sizeof(xRectangle *));
if (!pRects)
{
failed = TRUE;
goto failSafe;
}
for (pBox = REGION_RECTS(&censorRegion), i = 0;
i < nRects;
i++, pBox++)
{
pRects[i].x = pBox->x1;
pRects[i].y = pBox->y1 - imageBox.y1;
pRects[i].width = pBox->x2 - pBox->x1;
pRects[i].height = pBox->y2 - pBox->y1;
}
rec->rval = FALSE;
}
/* use pBuf as a fake pixmap */
CALLBACK(SecurityCheckBackgrndAccess)
{
XaceMapAccessRec *rec = (XaceMapAccessRec*)calldata;
if (format == ZPixmap)
{
depth = pDraw->depth;
bitsPerPixel = pDraw->bitsPerPixel;
}
if (TRUSTLEVEL(rec->client) != XSecurityClientTrusted)
rec->rval = FALSE;
}
pPix = GetScratchPixmapHeader(pDraw->pScreen, w, h,
depth, bitsPerPixel,
widthBytesLine, (pointer)pBuf);
if (!pPix)
{
failed = TRUE;
goto failSafe;
}
CALLBACK(SecurityCheckExtAccess)
{
XaceExtAccessRec *rec = (XaceExtAccessRec*)calldata;
pScratchGC = GetScratchGC(depth, pPix->drawable.pScreen);
if (!pScratchGC)
{
failed = TRUE;
goto failSafe;
}
if ((TRUSTLEVEL(rec->client) != XSecurityClientTrusted) &&
!STATEVAL(rec->ext))
ValidateGC(&pPix->drawable, pScratchGC);
(* pScratchGC->ops->PolyFillRect)(&pPix->drawable,
pScratchGC, nRects, pRects);
rec->rval = FALSE;
}
failSafe:
if (failed)
{
/* Censoring was not completed above. To be safe, wipe out
* all the image data so that nothing trusted gets out.
*/
bzero(pBuf, (int)(widthBytesLine * h));
}
if (pRects) DEALLOCATE_LOCAL(pRects);
if (pScratchGC) FreeScratchGC(pScratchGC);
if (pPix) FreeScratchPixmapHeader(pPix);
CALLBACK(SecurityCheckHostlistAccess)
{
XaceHostlistAccessRec *rec = (XaceHostlistAccessRec*)calldata;
if (TRUSTLEVEL(rec->client) != XSecurityClientTrusted)
{
rec->rval = FALSE;
if (rec->access_mode == SecurityWriteAccess)
SecurityAudit("client %d attempted to change host access\n",
rec->client->index);
else
SecurityAudit("client %d attempted to list hosts\n",
rec->client->index);
}
REGION_UNINIT(pScreen, &imageRegion);
REGION_UNINIT(pScreen, &censorRegion);
} /* SecurityCensorImage */
}
CALLBACK(SecurityDeclareExtSecure)
{
XaceDeclareExtSecureRec *rec = (XaceDeclareExtSecureRec*)calldata;
/* security state for extensions is simply a boolean trust value */
STATEVAL(rec->ext) = rec->secure;
}
/**********************************************************************/
@ -1734,21 +1691,21 @@ SecurityMatchString(
#endif
char
SecurityCheckPropertyAccess(client, pWin, propertyName, access_mode)
ClientPtr client;
WindowPtr pWin;
ATOM propertyName;
Mask access_mode;
CALLBACK(SecurityCheckPropertyAccess)
{
XacePropertyAccessRec *rec = (XacePropertyAccessRec*)calldata;
ClientPtr client = rec->client;
WindowPtr pWin = rec->pWin;
ATOM propertyName = rec->propertyName;
Mask access_mode = rec->access_mode;
PropertyAccessPtr pacl;
char action = SecurityDefaultAction;
/* if client trusted or window untrusted, allow operation */
if ( (client->trustLevel == XSecurityClientTrusted) ||
(wClient(pWin)->trustLevel != XSecurityClientTrusted) )
return SecurityAllowOperation;
if ( (TRUSTLEVEL(client) == XSecurityClientTrusted) ||
(TRUSTLEVEL(wClient(pWin)) != XSecurityClientTrusted) )
return;
#ifdef PROPDEBUG
/* For testing, it's more convenient if the property rules file gets
@ -1861,7 +1818,9 @@ SecurityCheckPropertyAccess(client, pWin, propertyName, access_mode)
client->index, reqtype, pWin->drawable.id,
NameForAtom(propertyName), propertyName, cid, actionstr);
}
return action;
/* return codes increase with strictness */
if (action > rec->rval)
rec->rval = action;
} /* SecurityCheckPropertyAccess */
@ -1901,6 +1860,46 @@ XSecurityOptions(argc, argv, i)
} /* XSecurityOptions */
/* SecurityExtensionSetup
*
* Arguments: none.
*
* Returns: nothing.
*
* Side Effects:
* Sets up the Security extension if possible.
* This function contains things that need to be done
* before any other extension init functions get called.
*/
void
SecurityExtensionSetup(INITARGS)
{
/* Allocate the client private index */
securityClientPrivateIndex = AllocateClientPrivateIndex();
if (!AllocateClientPrivate(securityClientPrivateIndex,
sizeof (SecurityClientStateRec)))
FatalError("SecurityExtensionSetup: Can't allocate client private.\n");
/* Allocate the extension private index */
securityExtnsnPrivateIndex = AllocateExtensionPrivateIndex();
if (!AllocateExtensionPrivate(securityExtnsnPrivateIndex, 0))
FatalError("SecurityExtensionSetup: Can't allocate extnsn private.\n");
/* register callbacks */
#define XaceRC XaceRegisterCallback
XaceRC(XACE_RESOURCE_ACCESS, SecurityCheckResourceIDAccess, NULL);
XaceRC(XACE_DEVICE_ACCESS, SecurityCheckDeviceAccess, NULL);
XaceRC(XACE_PROPERTY_ACCESS, SecurityCheckPropertyAccess, NULL);
XaceRC(XACE_DRAWABLE_ACCESS, SecurityCheckDrawableAccess, NULL);
XaceRC(XACE_MAP_ACCESS, SecurityCheckMapAccess, NULL);
XaceRC(XACE_BACKGRND_ACCESS, SecurityCheckBackgrndAccess, NULL);
XaceRC(XACE_EXT_DISPATCH, SecurityCheckExtAccess, NULL);
XaceRC(XACE_EXT_ACCESS, SecurityCheckExtAccess, NULL);
XaceRC(XACE_HOSTLIST_ACCESS, SecurityCheckHostlistAccess, NULL);
XaceRC(XACE_DECLARE_EXT_SECURE, SecurityDeclareExtSecure, NULL);
} /* SecurityExtensionSetup */
/* SecurityExtensionInit
*
@ -1916,7 +1915,6 @@ void
SecurityExtensionInit(INITARGS)
{
ExtensionEntry *extEntry;
int i;
SecurityAuthorizationResType =
CreateNewResourceType(SecurityDeleteAuthorization);
@ -1943,25 +1941,6 @@ SecurityExtensionInit(INITARGS)
EventSwapVector[SecurityEventBase + XSecurityAuthorizationRevoked] =
(EventSwapPtr)SwapSecurityAuthorizationRevokedEvent;
/* initialize untrusted proc vectors */
for (i = 0; i < 128; i++)
{
UntrustedProcVector[i] = ProcVector[i];
SwappedUntrustedProcVector[i] = SwappedProcVector[i];
}
/* make sure insecure extensions are not allowed */
for (i = 128; i < 256; i++)
{
if (!UntrustedProcVector[i])
{
UntrustedProcVector[i] = ProcBadRequest;
SwappedUntrustedProcVector[i] = ProcBadRequest;
}
}
SecurityLoadPropertyAccessList();
} /* SecurityExtensionInit */

View File

@ -86,46 +86,11 @@ typedef struct {
Bool valid; /* did anyone recognize it? if so, set to TRUE */
} SecurityValidateGroupInfoRec;
/* Proc vectors for untrusted clients, swapped and unswapped versions.
* These are the same as the normal proc vectors except that extensions
* that haven't declared themselves secure will have ProcBadRequest plugged
* in for their major opcode dispatcher. This prevents untrusted clients
* from guessing extension major opcodes and using the extension even though
* the extension can't be listed or queried.
*/
extern int (*UntrustedProcVector[256])(ClientPtr client);
extern int (*SwappedUntrustedProcVector[256])(ClientPtr client);
extern Bool SecurityCheckDeviceAccess(ClientPtr client, DeviceIntPtr dev,
Bool fromRequest);
extern void SecurityAudit(char *format, ...);
extern int XSecurityOptions(int argc, char **argv, int i);
/* Give this value or higher to the -audit option to get security messages */
#define SECURITY_AUDIT_LEVEL 4
extern void SecurityCensorImage(
ClientPtr client,
RegionPtr pVisibleRegion,
long widthBytesLine,
DrawablePtr pDraw,
int x, int y, int w, int h,
unsigned int format,
char * pBuf);
#define SecurityAllowOperation 0
#define SecurityIgnoreOperation 1
#define SecurityErrorOperation 2
extern char
SecurityCheckPropertyAccess(
ClientPtr client,
WindowPtr pWin,
ATOM propertyName,
Mask access_mode);
#define SECURITY_POLICY_FILE_VERSION "version-1"
extern char **SecurityGetSitePolicyStrings(int *n);

496
Xext/xace.c Normal file
View File

@ -0,0 +1,496 @@
/************************************************************
Author: Eamon Walsh <ewalsh@epoch.ncsc.mil>
Permission to use, copy, modify, distribute, and sell this software and its
documentation for any purpose is hereby granted without fee, provided that
this permission notice appear in supporting documentation. This permission
notice shall be included in all copies or substantial portions of the
Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
********************************************************/
#ifdef HAVE_DIX_CONFIG_H
#include <dix-config.h>
#endif
#include <stdarg.h>
#include "windowstr.h"
#include "scrnintstr.h"
#include "gcstruct.h"
#include "xacestr.h"
#include "modinit.h"
CallbackListPtr XaceHooks[XACE_NUM_HOOKS] = {0};
/* Proc vectors for untrusted clients, swapped and unswapped versions.
* These are the same as the normal proc vectors except that extensions
* that haven't declared themselves secure will have ProcBadRequest plugged
* in for their major opcode dispatcher. This prevents untrusted clients
* from guessing extension major opcodes and using the extension even though
* the extension can't be listed or queried.
*/
int (*UntrustedProcVector[256])(
ClientPtr /*client*/
);
int (*SwappedUntrustedProcVector[256])(
ClientPtr /*client*/
);
/* Entry point for hook functions. Called by Xserver.
*/
int XaceHook(int hook, ...)
{
pointer calldata; /* data passed to callback */
int *prv = NULL; /* points to return value from callback */
va_list ap; /* argument list */
va_start(ap, hook);
/* Marshal arguments for passing to callback.
* Each callback has its own case, which sets up a structure to hold
* the arguments and integer return parameter, or in some cases just
* sets calldata directly to a single argument (with no return result)
*/
switch (hook)
{
case XACE_CORE_DISPATCH: {
XaceCoreDispatchRec rec = {
va_arg(ap, ClientPtr),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_RESOURCE_ACCESS: {
XaceResourceAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, XID),
va_arg(ap, RESTYPE),
va_arg(ap, Mask),
va_arg(ap, pointer),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_DEVICE_ACCESS: {
XaceDeviceAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, DeviceIntPtr),
va_arg(ap, Bool),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_PROPERTY_ACCESS: {
XacePropertyAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, WindowPtr),
va_arg(ap, Atom),
va_arg(ap, Mask),
SecurityAllowOperation /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_DRAWABLE_ACCESS: {
XaceDrawableAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, DrawablePtr),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_MAP_ACCESS:
case XACE_BACKGRND_ACCESS: {
XaceMapAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, WindowPtr),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_EXT_DISPATCH:
case XACE_EXT_ACCESS: {
XaceExtAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, ExtensionEntry*),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_HOSTLIST_ACCESS: {
XaceHostlistAccessRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, Mask),
TRUE /* default allow */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_SITE_POLICY: {
XaceSitePolicyRec rec = {
va_arg(ap, char*),
va_arg(ap, int),
FALSE /* default unrecognized */
};
calldata = &rec;
prv = &rec.rval;
break;
}
case XACE_DECLARE_EXT_SECURE: {
XaceDeclareExtSecureRec rec = {
va_arg(ap, ExtensionEntry*),
va_arg(ap, Bool)
};
calldata = &rec;
break;
}
case XACE_AUTH_AVAIL: {
XaceAuthAvailRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, XID)
};
calldata = &rec;
break;
}
case XACE_KEY_AVAIL: {
XaceKeyAvailRec rec = {
va_arg(ap, xEventPtr),
va_arg(ap, DeviceIntPtr),
va_arg(ap, int)
};
calldata = &rec;
break;
}
case XACE_WINDOW_INIT: {
XaceWindowRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, WindowPtr)
};
calldata = &rec;
break;
}
case XACE_AUDIT_BEGIN: {
XaceAuditRec rec = {
va_arg(ap, ClientPtr),
0
};
calldata = &rec;
break;
}
case XACE_AUDIT_END: {
XaceAuditRec rec = {
va_arg(ap, ClientPtr),
va_arg(ap, int)
};
calldata = &rec;
break;
}
default: {
va_end(ap);
return 0; /* unimplemented hook number */
}
}
va_end(ap);
/* call callbacks and return result, if any. */
CallCallbacks(&XaceHooks[hook], calldata);
return prv ? *prv : 0;
}
static int
ProcXaceDispatch(ClientPtr client)
{
REQUEST(xReq);
switch (stuff->data)
{
default:
return BadRequest;
}
} /* ProcXaceDispatch */
static int
SProcXaceDispatch(ClientPtr client)
{
REQUEST(xReq);
switch (stuff->data)
{
default:
return BadRequest;
}
} /* SProcXaceDispatch */
/* XaceResetProc
*
* Arguments:
* extEntry is the extension information for the XACE extension.
*
* Returns: nothing.
*
* Side Effects:
* Performs any cleanup needed by XACE at server shutdown time.
*/
static void
XaceResetProc(ExtensionEntry *extEntry)
{
int i;
for (i=0; i<XACE_NUM_HOOKS; i++)
{
DeleteCallbackList(&XaceHooks[i]);
XaceHooks[i] = NULL;
}
} /* XaceResetProc */
static int
XaceCatchDispatchProc(ClientPtr client)
{
REQUEST(xReq);
int major = stuff->reqType;
if (!ProcVector[major])
return (BadRequest);
if (!XaceHook(XACE_CORE_DISPATCH, client))
return (BadAccess);
return client->swapped ?
(* SwappedProcVector[major])(client) :
(* ProcVector[major])(client);
}
static int
XaceCatchExtProc(ClientPtr client)
{
REQUEST(xReq);
int major = stuff->reqType;
ExtensionEntry *ext = GetExtensionEntry(major);
if (!ext || !ProcVector[major])
return (BadRequest);
if (!XaceHook(XACE_EXT_DISPATCH, client, ext))
return (BadRequest); /* pretend extension doesn't exist */
return client->swapped ?
(* SwappedProcVector[major])(client) :
(* ProcVector[major])(client);
}
/* SecurityClientStateCallback
*
* Arguments:
* pcbl is &ClientStateCallback.
* nullata is NULL.
* calldata is a pointer to a NewClientInfoRec (include/dixstruct.h)
* which contains information about client state changes.
*
* Returns: nothing.
*
* Side Effects:
*
* If a new client is connecting, its authorization ID is copied to
* client->authID. If this is a generated authorization, its reference
* count is bumped, its timer is cancelled if it was running, and its
* trustlevel is copied to TRUSTLEVEL(client).
*
* If a client is disconnecting and the client was using a generated
* authorization, the authorization's reference count is decremented, and
* if it is now zero, the timer for this authorization is started.
*/
static void
XaceClientStateCallback(
CallbackListPtr *pcbl,
pointer nulldata,
pointer calldata)
{
NewClientInfoRec *pci = (NewClientInfoRec *)calldata;
ClientPtr client = pci->client;
switch (client->clientState)
{
case ClientStateRunning:
{
client->requestVector = client->swapped ?
SwappedUntrustedProcVector : UntrustedProcVector;
break;
}
default: break;
}
} /* XaceClientStateCallback */
/* XaceExtensionInit
*
* Initialize the XACE Extension
*/
void XaceExtensionInit(INITARGS)
{
ExtensionEntry *extEntry;
int i;
if (!AddCallback(&ClientStateCallback, XaceClientStateCallback, NULL))
return;
extEntry = AddExtension(XACE_EXTENSION_NAME,
XaceNumberEvents, XaceNumberErrors,
ProcXaceDispatch, SProcXaceDispatch,
XaceResetProc, StandardMinorOpcode);
/* initialize dispatching intercept functions */
for (i = 0; i < 128; i++)
{
UntrustedProcVector[i] = XaceCatchDispatchProc;
SwappedUntrustedProcVector[i] = XaceCatchDispatchProc;
}
for (i = 128; i < 256; i++)
{
UntrustedProcVector[i] = XaceCatchExtProc;
SwappedUntrustedProcVector[i] = XaceCatchExtProc;
}
}
/* XaceCensorImage
*
* Called after pScreen->GetImage to prevent pieces or trusted windows from
* being returned in image data from an untrusted window.
*
* Arguments:
* client is the client doing the GetImage.
* pVisibleRegion is the visible region of the window.
* widthBytesLine is the width in bytes of one horizontal line in pBuf.
* pDraw is the source window.
* x, y, w, h is the rectangle of image data from pDraw in pBuf.
* format is the format of the image data in pBuf: ZPixmap or XYPixmap.
* pBuf is the image data.
*
* Returns: nothing.
*
* Side Effects:
* Any part of the rectangle (x, y, w, h) that is outside the visible
* region of the window will be destroyed (overwritten) in pBuf.
*/
void
XaceCensorImage(client, pVisibleRegion, widthBytesLine, pDraw, x, y, w, h,
format, pBuf)
ClientPtr client;
RegionPtr pVisibleRegion;
long widthBytesLine;
DrawablePtr pDraw;
int x, y, w, h;
unsigned int format;
char * pBuf;
{
ScreenPtr pScreen = pDraw->pScreen;
RegionRec imageRegion; /* region representing x,y,w,h */
RegionRec censorRegion; /* region to obliterate */
BoxRec imageBox;
int nRects;
imageBox.x1 = x;
imageBox.y1 = y;
imageBox.x2 = x + w;
imageBox.y2 = y + h;
REGION_INIT(pScreen, &imageRegion, &imageBox, 1);
REGION_NULL(pScreen, &censorRegion);
/* censorRegion = imageRegion - visibleRegion */
REGION_SUBTRACT(pScreen, &censorRegion, &imageRegion, pVisibleRegion);
nRects = REGION_NUM_RECTS(&censorRegion);
if (nRects > 0)
{ /* we have something to censor */
GCPtr pScratchGC = NULL;
PixmapPtr pPix = NULL;
xRectangle *pRects = NULL;
Bool failed = FALSE;
int depth = 1;
int bitsPerPixel = 1;
int i;
BoxPtr pBox;
/* convert region to list-of-rectangles for PolyFillRect */
pRects = (xRectangle *)ALLOCATE_LOCAL(nRects * sizeof(xRectangle *));
if (!pRects)
{
failed = TRUE;
goto failSafe;
}
for (pBox = REGION_RECTS(&censorRegion), i = 0;
i < nRects;
i++, pBox++)
{
pRects[i].x = pBox->x1;
pRects[i].y = pBox->y1 - imageBox.y1;
pRects[i].width = pBox->x2 - pBox->x1;
pRects[i].height = pBox->y2 - pBox->y1;
}
/* use pBuf as a fake pixmap */
if (format == ZPixmap)
{
depth = pDraw->depth;
bitsPerPixel = pDraw->bitsPerPixel;
}
pPix = GetScratchPixmapHeader(pDraw->pScreen, w, h,
depth, bitsPerPixel,
widthBytesLine, (pointer)pBuf);
if (!pPix)
{
failed = TRUE;
goto failSafe;
}
pScratchGC = GetScratchGC(depth, pPix->drawable.pScreen);
if (!pScratchGC)
{
failed = TRUE;
goto failSafe;
}
ValidateGC(&pPix->drawable, pScratchGC);
(* pScratchGC->ops->PolyFillRect)(&pPix->drawable,
pScratchGC, nRects, pRects);
failSafe:
if (failed)
{
/* Censoring was not completed above. To be safe, wipe out
* all the image data so that nothing trusted gets out.
*/
bzero(pBuf, (int)(widthBytesLine * h));
}
if (pRects) DEALLOCATE_LOCAL(pRects);
if (pScratchGC) FreeScratchGC(pScratchGC);
if (pPix) FreeScratchPixmapHeader(pPix);
}
REGION_UNINIT(pScreen, &imageRegion);
REGION_UNINIT(pScreen, &censorRegion);
} /* XaceCensorImage */

103
Xext/xace.h Normal file
View File

@ -0,0 +1,103 @@
/************************************************************
Author: Eamon Walsh <ewalsh@epoch.ncsc.mil>
Permission to use, copy, modify, distribute, and sell this software and its
documentation for any purpose is hereby granted without fee, provided that
this permission notice appear in supporting documentation. This permission
notice shall be included in all copies or substantial portions of the
Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
********************************************************/
#ifndef _XACE_H
#define _XACE_H
#define XACE_EXTENSION_NAME "XAccessControlExtension"
#define XACE_MAJOR_VERSION 1
#define XACE_MINOR_VERSION 0
#include "pixmap.h" /* for DrawablePtr */
#include "regionstr.h" /* for RegionPtr */
#define XaceNumberEvents 0
#define XaceNumberErrors 0
/* security hooks */
/* Constants used to identify the available security hooks
*/
#define XACE_CORE_DISPATCH 0
#define XACE_EXT_DISPATCH 1
#define XACE_RESOURCE_ACCESS 2
#define XACE_DEVICE_ACCESS 3
#define XACE_PROPERTY_ACCESS 4
#define XACE_DRAWABLE_ACCESS 5
#define XACE_MAP_ACCESS 6
#define XACE_BACKGRND_ACCESS 7
#define XACE_EXT_ACCESS 8
#define XACE_HOSTLIST_ACCESS 9
#define XACE_SITE_POLICY 10
#define XACE_DECLARE_EXT_SECURE 11
#define XACE_AUTH_AVAIL 12
#define XACE_KEY_AVAIL 13
#define XACE_WINDOW_INIT 14
#define XACE_AUDIT_BEGIN 15
#define XACE_AUDIT_END 16
#define XACE_NUM_HOOKS 17
extern CallbackListPtr XaceHooks[XACE_NUM_HOOKS];
/* Entry point for hook functions. Called by Xserver.
*/
extern int XaceHook(
int /*hook*/,
... /*appropriate args for hook*/
);
/* Register a callback for a given hook.
*/
#define XaceRegisterCallback(hook,callback,data) \
AddCallback(XaceHooks+(hook), callback, data)
/* Unregister an existing callback for a given hook.
*/
#define XaceDeleteCallback(hook,callback,data) \
DeleteCallback(XaceHooks+(hook), callback, data)
/* From the original Security extension...
*/
/* Hook return codes */
#define SecurityAllowOperation 0
#define SecurityIgnoreOperation 1
#define SecurityErrorOperation 2
/* Proc vectors for untrusted clients, swapped and unswapped versions.
* These are the same as the normal proc vectors except that extensions
* that haven't declared themselves secure will have ProcBadRequest plugged
* in for their major opcode dispatcher. This prevents untrusted clients
* from guessing extension major opcodes and using the extension even though
* the extension can't be listed or queried.
*/
extern int (*UntrustedProcVector[256])(ClientPtr client);
extern int (*SwappedUntrustedProcVector[256])(ClientPtr client);
extern void XaceCensorImage(
ClientPtr client,
RegionPtr pVisibleRegion,
long widthBytesLine,
DrawablePtr pDraw,
int x, int y, int w, int h,
unsigned int format,
char * pBuf
);
#endif /* _XACE_H */

135
Xext/xacestr.h Normal file
View File

@ -0,0 +1,135 @@
/************************************************************
Author: Eamon Walsh <ewalsh@epoch.ncsc.mil>
Permission to use, copy, modify, distribute, and sell this software and its
documentation for any purpose is hereby granted without fee, provided that
this permission notice appear in supporting documentation. This permission
notice shall be included in all copies or substantial portions of the
Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
********************************************************/
#ifndef _XACESTR_H
#define _XACESTR_H
#include <X11/Xdefs.h>
#include "dixstruct.h"
#include "resource.h"
#include "extnsionst.h"
#include "gcstruct.h"
#include "windowstr.h"
#include "inputstr.h"
#include "xace.h"
/* XACE_CORE_DISPATCH */
typedef struct {
ClientPtr client;
int rval;
} XaceCoreDispatchRec;
/* XACE_RESOURCE_ACCESS */
/* XACE_RESOURCE_CREATE */
typedef struct {
ClientPtr client;
XID id;
RESTYPE rtype;
Mask access_mode;
pointer res;
int rval;
} XaceResourceAccessRec;
/* XACE_DEVICE_ACCESS */
typedef struct {
ClientPtr client;
DeviceIntPtr dev;
Bool fromRequest;
int rval;
} XaceDeviceAccessRec;
/* XACE_PROPERTY_ACCESS */
typedef struct {
ClientPtr client;
WindowPtr pWin;
Atom propertyName;
Mask access_mode;
int rval;
} XacePropertyAccessRec;
/* XACE_DRAWABLE_ACCESS */
typedef struct {
ClientPtr client;
DrawablePtr pDraw;
int rval;
} XaceDrawableAccessRec;
/* XACE_MAP_ACCESS */
/* XACE_BACKGRND_ACCESS */
typedef struct {
ClientPtr client;
WindowPtr pWin;
int rval;
} XaceMapAccessRec;
/* XACE_EXT_DISPATCH_ACCESS */
/* XACE_EXT_ACCESS */
typedef struct {
ClientPtr client;
ExtensionEntry *ext;
int rval;
} XaceExtAccessRec;
/* XACE_HOSTLIST_ACCESS */
typedef struct {
ClientPtr client;
Mask access_mode;
int rval;
} XaceHostlistAccessRec;
/* XACE_SITE_POLICY */
typedef struct {
char *policyString;
int len;
int rval;
} XaceSitePolicyRec;
/* XACE_DECLARE_EXT_SECURE */
typedef struct {
ExtensionEntry *ext;
Bool secure;
} XaceDeclareExtSecureRec;
/* XACE_AUTH_AVAIL */
typedef struct {
ClientPtr client;
XID authId;
} XaceAuthAvailRec;
/* XACE_KEY_AVAIL */
typedef struct {
xEventPtr event;
DeviceIntPtr keybd;
int count;
} XaceKeyAvailRec;
/* XACE_WINDOW_INIT */
typedef struct {
ClientPtr client;
WindowPtr pWin;
} XaceWindowRec;
/* XACE_AUDIT_BEGIN */
/* XACE_AUDIT_END */
typedef struct {
ClientPtr client;
int requestResult;
} XaceAuditRec;
#endif /* _XACESTR_H */

View File

@ -413,11 +413,12 @@ AC_ARG_ENABLE(dri, AS_HELP_STRING([--enable-dri], [Build DRI extensio
AC_ARG_ENABLE(xinerama, AS_HELP_STRING([--disable-xinerama], [Build Xinerama extension (default: enabled)]), [XINERAMA=$enableval], [XINERAMA=yes])
AC_ARG_ENABLE(xf86vidmode, AS_HELP_STRING([--disable-xf86vidmode], [Build XF86VidMode extension (default: enabled)]), [XF86VIDMODE=$enableval], [XF86VIDMODE=yes])
AC_ARG_ENABLE(xf86misc, AS_HELP_STRING([--disable-xf86misc], [Build XF86Misc extension (default: enabled)]), [XF86MISC=$enableval], [XF86MISC=yes])
AC_ARG_ENABLE(xcsecurity, AS_HELP_STRING([--disable-xcsecurity], [Build Security extension (default: enabled)]), [XCSECURITY=$enableval], [XCSECURITY=yes])
AC_ARG_ENABLE(xace, AS_HELP_STRING([--disable-xace], [Build X-ACE extension (default: enabled)]), [XACE=$enableval], [XACE=yes])
AC_ARG_ENABLE(xcsecurity, AS_HELP_STRING([--disable-xcsecurity], [Build Security extension (default: enabled)]), [XCSECURITY=$enableval], [XCSECURITY=$XACE])
AC_ARG_ENABLE(appgroup, AS_HELP_STRING([--disable-appgroup], [Build XC-APPGROUP extension (default: enabled)]), [APPGROUP=$enableval], [APPGROUP=$XCSECURITY])
AC_ARG_ENABLE(xcalibrate, AS_HELP_STRING([--enable-xcalibrate], [Build XCalibrate extension (default: disabled)]), [XCALIBRATE=$enableval], [XCALIBRATE=no])
AC_ARG_ENABLE(tslib, AS_HELP_STRING([--enable-tslib], [Build kdrive tslib touchscreen support (default: disabled)]), [TSLIB=$enableval], [TSLIB=no])
AC_ARG_ENABLE(xevie, AS_HELP_STRING([--disable-xevie], [Build XEvIE extension (default: enabled)]), [XEVIE=$enableval], [XEVIE=yes])
AC_ARG_ENABLE(appgroup, AS_HELP_STRING([--disable-appgroup], [Build XC-APPGROUP extension (default: enabled)]), [APPGROUP=$enableval], [APPGROUP=yes])
AC_ARG_ENABLE(cup, AS_HELP_STRING([--disable-cup], [Build TOG-CUP extension (default: enabled)]), [CUP=$enableval], [CUP=yes])
AC_ARG_ENABLE(evi, AS_HELP_STRING([--disable-evi], [Build Extended-Visual-Information extension (default: enabled)]), [EVI=$enableval], [EVI=yes])
AC_ARG_ENABLE(multibuffer, AS_HELP_STRING([--enable-multibuffer], [Build Multibuffer extension (default: disabled)]), [MULTIBUFFER=$enableval], [MULTIBUFFER=no])
@ -622,8 +623,16 @@ if test "x$XINERAMA" = xyes; then
REQUIRED_MODULES="$REQUIRED_MODULES xineramaproto"
fi
AM_CONDITIONAL(XACE, [test "x$XACE" = xyes])
if test "x$XACE" = xyes; then
AC_DEFINE(XACE, 1, [Build X-ACE extension])
fi
AM_CONDITIONAL(XCSECURITY, [test "x$XCSECURITY" = xyes])
if test "x$XCSECURITY" = xyes; then
if test "x$XACE" != xyes; then
AC_MSG_ERROR([cannot build Security extension without X-ACE])
fi
AC_DEFINE(XCSECURITY, 1, [Build Security extension])
fi
@ -633,12 +642,11 @@ if test "x$XEVIE" = xyes; then
REQUIRED_MODULES="$REQUIRED_MODULES evieproto"
fi
if test "x$APPGROUP" = xyes && test "x$XCSECURITY" != xyes; then
AC_MSG_NOTICE([Disabling APPGROUP extension])
APPGROUP=no
fi
AM_CONDITIONAL(APPGROUP, [test "x$APPGROUP" = xyes])
if test "x$APPGROUP" = xyes; then
if test "x$XACE" != xyes || test "x$XCSECURITY" != xyes; then
AC_MSG_ERROR([cannot build APPGROUP extension without X-ACE and XC-SECURITY])
fi
AC_DEFINE(XAPPGROUP, 1, [Build APPGROUP extension])
fi

View File

@ -69,8 +69,8 @@ SOFTWARE.
#ifdef XKB
#include <X11/extensions/XKBsrv.h>
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
#include "dispatch.h"
@ -946,8 +946,8 @@ ProcSetModifierMapping(ClientPtr client)
}
}
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, keybd, TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, keybd, TRUE))
return BadAccess;
#endif
@ -1063,9 +1063,8 @@ ProcChangeKeyboardMapping(ClientPtr client)
client->errorValue = stuff->keySymsPerKeyCode;
return BadValue;
}
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, inputInfo.keyboard,
TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, inputInfo.keyboard, TRUE))
return BadAccess;
#endif
keysyms.minKeyCode = stuff->firstKeyCode;
@ -1211,8 +1210,8 @@ ProcChangeKeyboardControl (ClientPtr client)
vmask = stuff->mask;
if (client->req_len != (sizeof(xChangeKeyboardControlReq)>>2)+Ones(vmask))
return BadLength;
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, keybd, TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, keybd, TRUE))
return BadAccess;
#endif
vlist = (XID *)&stuff[1]; /* first word of values */
@ -1600,8 +1599,8 @@ ProcQueryKeymap(ClientPtr client)
rep.type = X_Reply;
rep.sequenceNumber = client->sequence;
rep.length = 2;
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, inputInfo.keyboard, TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, inputInfo.keyboard, TRUE))
{
bzero((char *)&rep.map[0], 32);
}

View File

@ -104,8 +104,8 @@ int ProcInitialConnection();
#include "panoramiX.h"
#include "panoramiXsrv.h"
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
#ifdef XAPPGROUP
#include "appgroup.h"
@ -451,7 +451,15 @@ Dispatch(void)
if (result > (maxBigRequestSize << 2))
result = BadLength;
else
#ifdef XACE
{
XaceHook(XACE_AUDIT_BEGIN, client);
result = (* client->requestVector[MAJOROP])(client);
XaceHook(XACE_AUDIT_END, client, result);
}
#else
result = (* client->requestVector[MAJOROP])(client);
#endif /* XACE */
if (result != Success)
{
@ -1099,11 +1107,10 @@ ProcConvertSelection(register ClientPtr client)
CurrentSelections[i].selection != stuff->selection) i++;
if ((i < NumCurrentSelections) &&
(CurrentSelections[i].window != None)
#ifdef XCSECURITY
&& (!client->CheckAccess ||
(* client->CheckAccess)(client, CurrentSelections[i].window,
RT_WINDOW, SecurityReadAccess,
CurrentSelections[i].pWin))
#ifdef XACE
&& XaceHook(XACE_RESOURCE_ACCESS, client,
CurrentSelections[i].window, RT_WINDOW,
SecurityReadAccess, CurrentSelections[i].pWin)
#endif
)
{
@ -2095,7 +2102,7 @@ DoGetImage(register ClientPtr client, int format, Drawable drawable,
Mask plane = 0;
char *pBuf;
xGetImageReply xgi;
#ifdef XCSECURITY
#ifdef XACE
RegionPtr pVisibleRegion = NULL;
#endif
@ -2201,9 +2208,9 @@ DoGetImage(register ClientPtr client, int format, Drawable drawable,
WriteReplyToClient(client, sizeof (xGetImageReply), &xgi);
}
#ifdef XCSECURITY
if (client->trustLevel != XSecurityClientTrusted &&
pDraw->type == DRAWABLE_WINDOW)
#ifdef XACE
if (pDraw->type == DRAWABLE_WINDOW &&
!XaceHook(XACE_DRAWABLE_ACCESS, client, pDraw))
{
pVisibleRegion = NotClippedByChildren((WindowPtr)pDraw);
if (pVisibleRegion)
@ -2231,9 +2238,9 @@ DoGetImage(register ClientPtr client, int format, Drawable drawable,
format,
planemask,
(pointer) pBuf);
#ifdef XCSECURITY
#ifdef XACE
if (pVisibleRegion)
SecurityCensorImage(client, pVisibleRegion, widthBytesLine,
XaceCensorImage(client, pVisibleRegion, widthBytesLine,
pDraw, x, y + linesDone, width,
nlines, format, pBuf);
#endif
@ -2272,9 +2279,9 @@ DoGetImage(register ClientPtr client, int format, Drawable drawable,
format,
plane,
(pointer)pBuf);
#ifdef XCSECURITY
#ifdef XACE
if (pVisibleRegion)
SecurityCensorImage(client, pVisibleRegion,
XaceCensorImage(client, pVisibleRegion,
widthBytesLine,
pDraw, x, y + linesDone, width,
nlines, format, pBuf);
@ -2300,7 +2307,7 @@ DoGetImage(register ClientPtr client, int format, Drawable drawable,
}
}
}
#ifdef XCSECURITY
#ifdef XACE
if (pVisibleRegion)
REGION_DESTROY(pDraw->pScreen, pVisibleRegion);
#endif
@ -3274,11 +3281,10 @@ ProcListHosts(register ClientPtr client)
/* REQUEST(xListHostsReq); */
REQUEST_SIZE_MATCH(xListHostsReq);
#ifdef XCSECURITY
#ifdef XACE
/* untrusted clients can't list hosts */
if (client->trustLevel != XSecurityClientTrusted)
if (!XaceHook(XACE_HOSTLIST_ACCESS, client, SecurityReadAccess))
{
SecurityAudit("client %d attempted to list hosts\n", client->index);
return BadAccess;
}
#endif
@ -3606,8 +3612,13 @@ CloseDownRetainedResources()
}
}
extern int clientPrivateLen;
extern unsigned *clientPrivateSizes;
extern unsigned totalClientSize;
void InitClient(ClientPtr client, int i, pointer ospriv)
{
bzero(client, totalClientSize);
client->index = i;
client->sequence = 0;
client->clientAsMask = ((Mask)i) << CLIENTOFFSET;
@ -3646,11 +3657,6 @@ void InitClient(ClientPtr client, int i, pointer ospriv)
}
#endif
client->replyBytesRemaining = 0;
#ifdef XCSECURITY
client->trustLevel = XSecurityClientTrusted;
client->CheckAccess = NULL;
client->authId = 0;
#endif
#ifdef XAPPGROUP
client->appgroup = NULL;
#endif
@ -3663,10 +3669,6 @@ void InitClient(ClientPtr client, int i, pointer ospriv)
#endif
}
extern int clientPrivateLen;
extern unsigned *clientPrivateSizes;
extern unsigned totalClientSize;
int
InitClientPrivates(ClientPtr client)
{
@ -3699,6 +3701,17 @@ InitClientPrivates(ClientPtr client)
else
ppriv->ptr = (pointer)NULL;
}
/* Allow registrants to initialize the serverClient devPrivates */
if (!client->index && ClientStateCallback)
{
NewClientInfoRec clientinfo;
clientinfo.client = client;
clientinfo.prefix = (xConnSetupPrefix *)NULL;
clientinfo.setup = (xConnSetup *) NULL;
CallCallbacks((&ClientStateCallback), (pointer)&clientinfo);
}
return 1;
}

View File

@ -95,8 +95,8 @@ Author: Adobe Systems Incorporated
#include "scrnintstr.h"
#define XK_LATIN1
#include <X11/keysymdef.h>
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
/*
@ -196,7 +196,7 @@ CompareISOLatin1Lowered(unsigned char *s1, int s1len,
return (int) c1 - (int) c2;
}
#ifdef XCSECURITY
#ifdef XACE
/* SecurityLookupWindow and SecurityLookupDrawable:
* Look up the window/drawable taking into account the client doing
@ -204,32 +204,16 @@ CompareISOLatin1Lowered(unsigned char *s1, int s1len,
* if it exists and the client is allowed access, else return NULL.
* Most Proc* functions should be calling these instead of
* LookupWindow and LookupDrawable, which do no access checks.
* XACE note: need to see if client->lastDrawableID can still be used here.
*/
_X_EXPORT WindowPtr
SecurityLookupWindow(XID rid, ClientPtr client, Mask access_mode)
{
WindowPtr pWin;
client->errorValue = rid;
if(rid == INVALID)
return NULL;
if (client->trustLevel != XSecurityClientTrusted)
return (WindowPtr)SecurityLookupIDByType(client, rid, RT_WINDOW, access_mode);
if (client->lastDrawableID == rid)
{
if (client->lastDrawable->type == DRAWABLE_WINDOW)
return ((WindowPtr) client->lastDrawable);
return (WindowPtr) NULL;
}
pWin = (WindowPtr)SecurityLookupIDByType(client, rid, RT_WINDOW, access_mode);
if (pWin && pWin->drawable.type == DRAWABLE_WINDOW) {
client->lastDrawable = (DrawablePtr) pWin;
client->lastDrawableID = rid;
client->lastGCID = INVALID;
client->lastGC = (GCPtr)NULL;
}
return pWin;
return (WindowPtr)SecurityLookupIDByType(client, rid, RT_WINDOW, access_mode);
}
@ -240,11 +224,6 @@ SecurityLookupDrawable(XID rid, ClientPtr client, Mask access_mode)
if(rid == INVALID)
return (pointer) NULL;
if (client->trustLevel != XSecurityClientTrusted)
return (DrawablePtr)SecurityLookupIDByClass(client, rid, RC_DRAWABLE,
access_mode);
if (client->lastDrawableID == rid)
return ((pointer) client->lastDrawable);
pDraw = (DrawablePtr)SecurityLookupIDByClass(client, rid, RC_DRAWABLE,
access_mode);
if (pDraw && (pDraw->type != UNDRAWABLE_WINDOW))
@ -268,7 +247,7 @@ LookupDrawable(XID rid, ClientPtr client)
return SecurityLookupDrawable(rid, client, SecurityUnknownAccess);
}
#else /* not XCSECURITY */
#else /* not XACE */
WindowPtr
LookupWindow(XID rid, ClientPtr client)
@ -310,7 +289,7 @@ LookupDrawable(XID rid, ClientPtr client)
return (pointer)NULL;
}
#endif /* XCSECURITY */
#endif /* XACE */
_X_EXPORT ClientPtr
LookupClient(XID rid, ClientPtr client)

View File

@ -135,8 +135,8 @@ of the copyright holder.
extern Bool XkbFilterEvents(ClientPtr, int, xEvent *);
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
#ifdef XEVIE
@ -2476,8 +2476,8 @@ CheckPassiveGrabsOnWindow(
(grab->confineTo->realized &&
BorderSizeNotEmpty(grab->confineTo))))
{
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(wClient(pWin), device, FALSE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, wClient(pWin), device, FALSE))
return FALSE;
#endif
#ifdef XKB
@ -2846,6 +2846,10 @@ drawable.id:0;
DeliverFocusedEvent(keybd, xE, sprite.win, count);
if (deactivateGrab)
(*keybd->DeactivateGrab)(keybd);
#ifdef XACE
XaceHook(XACE_KEY_AVAIL, xE, keybd, count);
#endif
}
#ifdef XKB
@ -3279,10 +3283,10 @@ EnterLeaveEvent(
{
xKeymapEvent ke;
#ifdef XCSECURITY
#ifdef XACE
ClientPtr client = grab ? rClient(grab)
: clients[CLIENT_ID(pWin->drawable.id)];
if (!SecurityCheckDeviceAccess(client, keybd, FALSE))
if (!XaceHook(XACE_DEVICE_ACCESS, client, keybd, FALSE))
{
bzero((char *)&ke.map[0], 31);
}
@ -3374,9 +3378,9 @@ FocusEvent(DeviceIntPtr dev, int type, int mode, int detail, register WindowPtr
((pWin->eventMask | wOtherEventMasks(pWin)) & KeymapStateMask))
{
xKeymapEvent ke;
#ifdef XCSECURITY
#ifdef XACE
ClientPtr client = clients[CLIENT_ID(pWin->drawable.id)];
if (!SecurityCheckDeviceAccess(client, dev, FALSE))
if (!XaceHook(XACE_DEVICE_ACCESS, client, dev, FALSE))
{
bzero((char *)&ke.map[0], 31);
}
@ -3645,8 +3649,8 @@ ProcSetInputFocus(client)
REQUEST(xSetInputFocusReq);
REQUEST_SIZE_MATCH(xSetInputFocusReq);
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, inputInfo.keyboard, TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, inputInfo.keyboard, TRUE))
return Success;
#endif
return SetInputFocus(client, inputInfo.keyboard, stuff->focus,
@ -3910,8 +3914,8 @@ ProcGrabKeyboard(ClientPtr client)
int result;
REQUEST_SIZE_MATCH(xGrabKeyboardReq);
#ifdef XCSECURITY
if (!SecurityCheckDeviceAccess(client, inputInfo.keyboard, TRUE))
#ifdef XACE
if (!XaceHook(XACE_DEVICE_ACCESS, client, inputInfo.keyboard, TRUE))
{
result = Success;
rep.status = AlreadyGrabbed;

View File

@ -59,8 +59,8 @@ SOFTWARE.
#include "gcstruct.h"
#include "scrnintstr.h"
#include "dispatch.h"
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
#define EXTENSION_BASE 128
@ -76,6 +76,39 @@ int lastEvent = EXTENSION_EVENT_BASE;
static int lastError = FirstExtensionError;
static unsigned int NumExtensions = 0;
extern int extensionPrivateLen;
extern unsigned *extensionPrivateSizes;
extern unsigned totalExtensionSize;
static void
InitExtensionPrivates(ExtensionEntry *ext)
{
register char *ptr;
DevUnion *ppriv;
register unsigned *sizes;
register unsigned size;
register int i;
if (totalExtensionSize == sizeof(ExtensionEntry))
ppriv = (DevUnion *)NULL;
else
ppriv = (DevUnion *)(ext + 1);
ext->devPrivates = ppriv;
sizes = extensionPrivateSizes;
ptr = (char *)(ppriv + extensionPrivateLen);
for (i = extensionPrivateLen; --i >= 0; ppriv++, sizes++)
{
if ( (size = *sizes) )
{
ppriv->ptr = (pointer)ptr;
ptr += size;
}
else
ppriv->ptr = (pointer)NULL;
}
}
_X_EXPORT ExtensionEntry *
AddExtension(char *name, int NumEvents, int NumErrors,
int (*MainProc)(ClientPtr c1),
@ -92,9 +125,11 @@ AddExtension(char *name, int NumEvents, int NumErrors,
(unsigned)(lastError + NumErrors > LAST_ERROR))
return((ExtensionEntry *) NULL);
ext = (ExtensionEntry *) xalloc(sizeof(ExtensionEntry));
ext = (ExtensionEntry *) xalloc(totalExtensionSize);
if (!ext)
return((ExtensionEntry *) NULL);
bzero(ext, totalExtensionSize);
InitExtensionPrivates(ext);
ext->name = (char *)xalloc(strlen(name) + 1);
ext->num_aliases = 0;
ext->aliases = (char **)NULL;
@ -144,9 +179,6 @@ AddExtension(char *name, int NumEvents, int NumErrors,
ext->errorBase = 0;
ext->errorLast = 0;
}
#ifdef XCSECURITY
ext->secure = FALSE;
#endif
return(ext);
}
@ -207,26 +239,27 @@ CheckExtension(const char *extname)
return NULL;
}
/*
* Added as part of Xace.
*/
ExtensionEntry *
GetExtensionEntry(int major)
{
if (major < EXTENSION_BASE)
return NULL;
major -= EXTENSION_BASE;
if (major >= NumExtensions)
return NULL;
return extensions[major];
}
_X_EXPORT void
DeclareExtensionSecurity(char *extname, Bool secure)
{
#ifdef XCSECURITY
#ifdef XACE
int i = FindExtension(extname, strlen(extname));
if (i >= 0)
{
int majorop = extensions[i]->base;
extensions[i]->secure = secure;
if (secure)
{
UntrustedProcVector[majorop] = ProcVector[majorop];
SwappedUntrustedProcVector[majorop] = SwappedProcVector[majorop];
}
else
{
UntrustedProcVector[majorop] = ProcBadRequest;
SwappedUntrustedProcVector[majorop] = ProcBadRequest;
}
}
XaceHook(XACE_DECLARE_EXT_SECURE, extensions[i], secure);
#endif
}
@ -304,10 +337,9 @@ ProcQueryExtension(ClientPtr client)
{
i = FindExtension((char *)&stuff[1], stuff->nbytes);
if (i < 0
#ifdef XCSECURITY
/* don't show insecure extensions to untrusted clients */
|| (client->trustLevel == XSecurityClientUntrusted &&
!extensions[i]->secure)
#ifdef XACE
/* call callbacks to find out whether to show extension */
|| !XaceHook(XACE_EXT_ACCESS, client, extensions[i])
#endif
)
reply.present = xFalse;
@ -344,10 +376,9 @@ ProcListExtensions(ClientPtr client)
for (i=0; i<NumExtensions; i++)
{
#ifdef XCSECURITY
/* don't show insecure extensions to untrusted clients */
if (client->trustLevel == XSecurityClientUntrusted &&
!extensions[i]->secure)
#ifdef XACE
/* call callbacks to find out whether to show extension */
if (!XaceHook(XACE_EXT_ACCESS, client, extensions[i]))
continue;
#endif
total_length += strlen(extensions[i]->name) + 1;
@ -362,9 +393,8 @@ ProcListExtensions(ClientPtr client)
for (i=0; i<NumExtensions; i++)
{
int len;
#ifdef XCSECURITY
if (client->trustLevel == XSecurityClientUntrusted &&
!extensions[i]->secure)
#ifdef XACE
if (!XaceHook(XACE_EXT_ACCESS, client, extensions[i]))
continue;
#endif
*bufptr++ = len = strlen(extensions[i]->name);

View File

@ -354,6 +354,7 @@ main(int argc, char *argv[], char *envp[])
InitAtoms();
InitEvents();
InitGlyphCaching();
ResetExtensionPrivates();
ResetClientPrivates();
ResetScreenPrivates();
ResetWindowPrivates();

View File

@ -42,6 +42,7 @@ from The Open Group.
#include "servermd.h"
#include "site.h"
#include "inputstr.h"
#include "extnsionst.h"
/*
* See the Wrappers and devPrivates section in "Definition of the
@ -49,6 +50,63 @@ from The Open Group.
* for information on how to use devPrivates.
*/
/*
* extension private machinery
*/
static int extensionPrivateCount;
int extensionPrivateLen;
unsigned *extensionPrivateSizes;
unsigned totalExtensionSize;
void
ResetExtensionPrivates()
{
extensionPrivateCount = 0;
extensionPrivateLen = 0;
xfree(extensionPrivateSizes);
extensionPrivateSizes = (unsigned *)NULL;
totalExtensionSize =
((sizeof(ExtensionEntry) + sizeof(long) - 1) / sizeof(long)) * sizeof(long);
}
_X_EXPORT int
AllocateExtensionPrivateIndex()
{
return extensionPrivateCount++;
}
_X_EXPORT Bool
AllocateExtensionPrivate(int index2, unsigned amount)
{
unsigned oldamount;
/* Round up sizes for proper alignment */
amount = ((amount + (sizeof(long) - 1)) / sizeof(long)) * sizeof(long);
if (index2 >= extensionPrivateLen)
{
unsigned *nsizes;
nsizes = (unsigned *)xrealloc(extensionPrivateSizes,
(index2 + 1) * sizeof(unsigned));
if (!nsizes)
return FALSE;
while (extensionPrivateLen <= index2)
{
nsizes[extensionPrivateLen++] = 0;
totalExtensionSize += sizeof(DevUnion);
}
extensionPrivateSizes = nsizes;
}
oldamount = extensionPrivateSizes[index2];
if (amount > oldamount)
{
extensionPrivateSizes[index2] = amount;
totalExtensionSize += (amount - oldamount);
}
return TRUE;
}
/*
* client private machinery
*/

View File

@ -58,8 +58,8 @@ SOFTWARE.
#include "dixstruct.h"
#include "dispatch.h"
#include "swaprep.h"
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
/*****************************************************************
@ -118,12 +118,12 @@ ProcRotateProperties(ClientPtr client)
return(BadAlloc);
for (i = 0; i < stuff->nAtoms; i++)
{
#ifdef XCSECURITY
char action = SecurityCheckPropertyAccess(client, pWin, atoms[i],
#ifdef XACE
char action = XaceHook(XACE_PROPERTY_ACCESS, client, pWin, atoms[i],
SecurityReadAccess|SecurityWriteAccess);
#endif
if (!ValidAtom(atoms[i])
#ifdef XCSECURITY
#ifdef XACE
|| (SecurityErrorOperation == action)
#endif
)
@ -132,7 +132,7 @@ ProcRotateProperties(ClientPtr client)
client->errorValue = atoms[i];
return BadAtom;
}
#ifdef XCSECURITY
#ifdef XACE
if (SecurityIgnoreOperation == action)
{
DEALLOCATE_LOCAL(props);
@ -233,8 +233,8 @@ ProcChangeProperty(ClientPtr client)
return(BadAtom);
}
#ifdef XCSECURITY
switch (SecurityCheckPropertyAccess(client, pWin, stuff->property,
#ifdef XACE
switch (XaceHook(XACE_PROPERTY_ACCESS, client, pWin, stuff->property,
SecurityWriteAccess))
{
case SecurityErrorOperation:
@ -501,13 +501,13 @@ ProcGetProperty(ClientPtr client)
if (!pProp)
return NullPropertyReply(client, None, 0, &reply);
#ifdef XCSECURITY
#ifdef XACE
{
Mask access_mode = SecurityReadAccess;
if (stuff->delete)
access_mode |= SecurityDestroyAccess;
switch(SecurityCheckPropertyAccess(client, pWin, stuff->property,
switch(XaceHook(XACE_PROPERTY_ACCESS, client, pWin, stuff->property,
access_mode))
{
case SecurityErrorOperation:
@ -663,8 +663,8 @@ ProcDeleteProperty(register ClientPtr client)
return (BadAtom);
}
#ifdef XCSECURITY
switch(SecurityCheckPropertyAccess(client, pWin, stuff->property,
#ifdef XACE
switch(XaceHook(XACE_PROPERTY_ACCESS, client, pWin, stuff->property,
SecurityDestroyAccess))
{
case SecurityErrorOperation:

View File

@ -120,6 +120,9 @@ Equipment Corporation.
#include "panoramiX.h"
#include "panoramiXsrv.h"
#endif
#ifdef XACE
#include "xace.h"
#endif
#include <assert.h>
static void RebuildTable(
@ -818,8 +821,6 @@ LegalNewID(XID id, register ClientPtr client)
!LookupIDByClass(id, RC_ANY)));
}
#ifdef XCSECURITY
/* SecurityLookupIDByType and SecurityLookupIDByClass:
* These are the heart of the resource ID security system. They take
* two additional arguments compared to the old LookupID functions:
@ -835,10 +836,6 @@ SecurityLookupIDByType(ClientPtr client, XID id, RESTYPE rtype, Mask mode)
register ResourcePtr res;
pointer retval = NULL;
assert(client == NullClient ||
(client->index <= currentMaxClients && clients[client->index] == client));
assert( (rtype & TypeMask) <= lastResourceType);
if (((cid = CLIENT_ID(id)) < MAXCLIENTS) &&
clientTable[cid].buckets)
{
@ -851,8 +848,11 @@ SecurityLookupIDByType(ClientPtr client, XID id, RESTYPE rtype, Mask mode)
break;
}
}
if (retval && client && client->CheckAccess)
retval = (* client->CheckAccess)(client, id, rtype, mode, retval);
#ifdef XACE
if (retval && client &&
!XaceHook(XACE_RESOURCE_ACCESS, client, id, rtype, mode, retval))
retval = NULL;
#endif
return retval;
}
@ -864,10 +864,6 @@ SecurityLookupIDByClass(ClientPtr client, XID id, RESTYPE classes, Mask mode)
register ResourcePtr res = NULL;
pointer retval = NULL;
assert(client == NullClient ||
(client->index <= currentMaxClients && clients[client->index] == client));
assert (classes >= lastResourceClass);
if (((cid = CLIENT_ID(id)) < MAXCLIENTS) &&
clientTable[cid].buckets)
{
@ -880,8 +876,11 @@ SecurityLookupIDByClass(ClientPtr client, XID id, RESTYPE classes, Mask mode)
break;
}
}
if (retval && client && client->CheckAccess)
retval = (* client->CheckAccess)(client, id, res->type, mode, retval);
#ifdef XACE
if (retval && client &&
!XaceHook(XACE_RESOURCE_ACCESS, client, id, res->type, mode, retval))
retval = NULL;
#endif
return retval;
}
@ -902,50 +901,3 @@ LookupIDByClass(XID id, RESTYPE classes)
return SecurityLookupIDByClass(NullClient, id, classes,
SecurityUnknownAccess);
}
#else /* not XCSECURITY */
/*
* LookupIDByType returns the object with the given id and type, else NULL.
*/
pointer
LookupIDByType(XID id, RESTYPE rtype)
{
int cid;
register ResourcePtr res;
if (((cid = CLIENT_ID(id)) < MAXCLIENTS) &&
clientTable[cid].buckets)
{
res = clientTable[cid].resources[Hash(cid, id)];
for (; res; res = res->next)
if ((res->id == id) && (res->type == rtype))
return res->value;
}
return (pointer)NULL;
}
/*
* LookupIDByClass returns the object with the given id and any one of the
* given classes, else NULL.
*/
pointer
LookupIDByClass(XID id, RESTYPE classes)
{
int cid;
register ResourcePtr res;
if (((cid = CLIENT_ID(id)) < MAXCLIENTS) &&
clientTable[cid].buckets)
{
res = clientTable[cid].resources[Hash(cid, id)];
for (; res; res = res->next)
if ((res->id == id) && (res->type & classes))
return res->value;
}
return (pointer)NULL;
}
#endif /* XCSECURITY */

View File

@ -126,8 +126,8 @@ Equipment Corporation.
#ifdef XAPPGROUP
#include "appgroup.h"
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
/******
@ -530,6 +530,10 @@ InitRootWindow(WindowPtr pWin)
/* We SHOULD check for an error value here XXX */
(*pScreen->ChangeWindowAttributes)(pWin, backFlag);
#ifdef XACE
XaceHook(XACE_WINDOW_INIT, serverClient, pWin);
#endif
MapWindow(pWin, serverClient);
}
@ -731,11 +735,11 @@ CreateWindow(Window wid, register WindowPtr pParent, int x, int y, unsigned w,
}
pWin->borderWidth = bw;
#ifdef XCSECURITY
#ifdef XACE
/* can't let untrusted clients have background None windows;
* they make it too easy to steal window contents
*/
if (client->trustLevel != XSecurityClientTrusted)
if (!XaceHook(XACE_BACKGRND_ACCESS, client, pWin))
{
pWin->backgroundState = BackgroundPixel;
pWin->background.pixel = 0;
@ -762,6 +766,10 @@ CreateWindow(Window wid, register WindowPtr pParent, int x, int y, unsigned w,
REGION_NULL(pScreen, &pWin->winSize);
REGION_NULL(pScreen, &pWin->borderSize);
#ifdef XACE
XaceHook(XACE_WINDOW_INIT, client, pWin);
#endif
pHead = RealChildHead(pParent);
if (pHead)
{
@ -1025,9 +1033,9 @@ ChangeWindowAttributes(register WindowPtr pWin, Mask vmask, XID *vlist, ClientPt
borderRelative = TRUE;
if (pixID == None)
{
#ifdef XCSECURITY
#ifdef XACE
/* can't let untrusted clients have background None windows */
if (client->trustLevel == XSecurityClientTrusted)
if (XaceHook(XACE_BACKGRND_ACCESS, client, pWin))
{
#endif
if (pWin->backgroundState == BackgroundPixmap)
@ -1036,7 +1044,7 @@ ChangeWindowAttributes(register WindowPtr pWin, Mask vmask, XID *vlist, ClientPt
MakeRootTile(pWin);
else
pWin->backgroundState = None;
#ifdef XCSECURITY
#ifdef XACE
}
else
{ /* didn't change the background to None, so don't tell ddx */
@ -2724,13 +2732,9 @@ MapWindow(register WindowPtr pWin, ClientPtr client)
if (pWin->mapped)
return(Success);
#ifdef XCSECURITY
/* don't let an untrusted client map a child-of-trusted-window, InputOnly
* window; too easy to steal device input
*/
if ( (client->trustLevel != XSecurityClientTrusted) &&
(pWin->drawable.class == InputOnly) &&
(wClient(pWin->parent)->trustLevel == XSecurityClientTrusted) )
#ifdef XACE
/* general check for permission to map window */
if (!XaceHook(XACE_MAP_ACCESS, client, pWin))
return Success;
#endif

View File

@ -125,7 +125,12 @@ extern void ShmRegisterFuncs(
ShmFuncsPtr funcs);
#endif
#ifdef XACE
extern void XaceExtensionInit(INITARGS);
#endif
#if 1
extern void SecurityExtensionSetup(INITARGS);
extern void SecurityExtensionInit(INITARGS);
#endif

View File

@ -162,7 +162,7 @@ _X_HIDDEN void *dixLookupTab[] = {
SYMFUNC(QueueWorkProc)
SYMFUNC(RegisterBlockAndWakeupHandlers)
SYMFUNC(RemoveBlockAndWakeupHandlers)
#ifdef XCSECURITY
#ifdef XACE
SYMFUNC(SecurityLookupDrawable)
SYMFUNC(SecurityLookupWindow)
#endif
@ -255,6 +255,8 @@ _X_HIDDEN void *dixLookupTab[] = {
SYMFUNC(GetScratchPixmapHeader)
SYMFUNC(FreeScratchPixmapHeader)
/* privates.c */
SYMFUNC(AllocateExtensionPrivate)
SYMFUNC(AllocateExtensionPrivateIndex)
SYMFUNC(AllocateClientPrivate)
SYMFUNC(AllocateClientPrivateIndex)
SYMFUNC(AllocateGCPrivate)
@ -282,10 +284,8 @@ _X_HIDDEN void *dixLookupTab[] = {
SYMFUNC(LookupIDByType)
SYMFUNC(LookupIDByClass)
SYMFUNC(LegalNewID)
#ifdef XCSECURITY
SYMFUNC(SecurityLookupIDByClass)
SYMFUNC(SecurityLookupIDByType)
#endif
SYMFUNC(FindClientResourcesByType)
SYMFUNC(FindAllClientResources)
SYMVAR(lastResourceType)

View File

@ -308,6 +308,9 @@
/* unaligned word accesses behave as expected */
#undef WORKING_UNALIGNED_INT
/* Build X-ACE extension */
#undef XACE
/* Support XCMisc extension */
#undef XCMISC

View File

@ -87,12 +87,9 @@ SOFTWARE.
((client->lastDrawableID == did) ? \
client->lastDrawable : (DrawablePtr)LookupDrawable(did, client))
#ifdef XCSECURITY
#ifdef XACE
#define SECURITY_VERIFY_DRAWABLE(pDraw, did, client, mode)\
if (client->lastDrawableID == did && !client->trustLevel)\
pDraw = client->lastDrawable;\
else \
{\
pDraw = (DrawablePtr) SecurityLookupIDByClass(client, did, \
RC_DRAWABLE, mode);\
@ -106,9 +103,6 @@ SOFTWARE.
}
#define SECURITY_VERIFY_GEOMETRABLE(pDraw, did, client, mode)\
if (client->lastDrawableID == did && !client->trustLevel)\
pDraw = client->lastDrawable;\
else \
{\
pDraw = (DrawablePtr) SecurityLookupIDByClass(client, did, \
RC_DRAWABLE, mode);\
@ -120,9 +114,6 @@ SOFTWARE.
}
#define SECURITY_VERIFY_GC(pGC, rid, client, mode)\
if (client->lastGCID == rid && !client->trustLevel)\
pGC = client->lastGC;\
else\
pGC = (GC *) SecurityLookupIDByType(client, rid, RT_GC, mode);\
if (!pGC)\
{\
@ -139,7 +130,7 @@ SOFTWARE.
#define VERIFY_GC(pGC, rid, client)\
SECURITY_VERIFY_GC(pGC, rid, client, SecurityUnknownAccess)
#else /* not XCSECURITY */
#else /* not XACE */
#define VERIFY_DRAWABLE(pDraw, did, client)\
if (client->lastDrawableID == did)\
@ -189,7 +180,7 @@ SOFTWARE.
#define SECURITY_VERIFY_GC(pGC, rid, client, mode)\
VERIFY_GC(pGC, rid, client)
#endif /* XCSECURITY */
#endif /* XACE */
/*
* We think that most hardware implementations of DBE will want
@ -384,7 +375,7 @@ extern int CompareISOLatin1Lowered(
unsigned char * /*b*/,
int blen);
#ifdef XCSECURITY
#ifdef XACE
extern WindowPtr SecurityLookupWindow(
XID /*rid*/,
@ -420,7 +411,7 @@ extern pointer LookupDrawable(
#define SecurityLookupDrawable(rid, client, access_mode) \
LookupDrawable(rid, client)
#endif /* XCSECURITY */
#endif /* XACE */
extern ClientPtr LookupClient(
XID /*rid*/,

View File

@ -128,16 +128,6 @@ typedef struct _Client {
int requestLogIndex;
#endif
unsigned long replyBytesRemaining;
#ifdef XCSECURITY
XID authId;
unsigned int trustLevel;
pointer (* CheckAccess)(
ClientPtr /*pClient*/,
XID /*id*/,
RESTYPE /*classes*/,
Mask /*access_mode*/,
pointer /*resourceval*/);
#endif
#ifdef XAPPGROUP
struct _AppGroupRec* appgroup;
#endif

View File

@ -58,6 +58,14 @@ extern Bool EnableDisableExtension(char *name, Bool enable);
extern void EnableDisableExtensionError(char *name, Bool enable);
extern void ResetExtensionPrivates(void);
extern int AllocateExtensionPrivateIndex(void);
extern Bool AllocateExtensionPrivate(
int /*index*/,
unsigned /*amount*/);
extern void InitExtensions(int argc, char **argv);
extern void InitVisualWrap(void);

View File

@ -48,6 +48,7 @@ SOFTWARE.
#ifndef EXTENSIONSTRUCT_H
#define EXTENSIONSTRUCT_H
#include "dix.h"
#include "misc.h"
#include "screenint.h"
#include "extension.h"
@ -68,9 +69,7 @@ typedef struct _ExtensionEntry {
pointer extPrivate;
unsigned short (* MinorOpcode)( /* called for errors */
ClientPtr /* client */);
#ifdef XCSECURITY
Bool secure; /* extension visible to untrusted clients? */
#endif
DevUnion *devPrivates;
} ExtensionEntry;
/*
@ -127,6 +126,7 @@ extern Bool AddExtensionAlias(
ExtensionEntry * /*extension*/);
extern ExtensionEntry *CheckExtension(const char *extname);
extern ExtensionEntry *GetExtensionEntry(int major);
extern ExtensionLookupProc LookupProc(
char* /*name*/,

View File

@ -225,8 +225,6 @@ extern pointer LookupClientResourceComplex(
#define SecurityWriteAccess (1<<1) /* changing the object */
#define SecurityDestroyAccess (1<<2) /* destroying the object */
#ifdef XCSECURITY
extern pointer SecurityLookupIDByType(
ClientPtr /*client*/,
XID /*id*/,
@ -239,15 +237,6 @@ extern pointer SecurityLookupIDByClass(
RESTYPE /*classes*/,
Mask /*access_mode*/);
#else /* not XCSECURITY */
#define SecurityLookupIDByType(client, id, rtype, access_mode) \
LookupIDByType(id, rtype)
#define SecurityLookupIDByClass(client, id, classes, access_mode) \
LookupIDByClass(id, classes)
#endif /* XCSECURITY */
extern void GetXIDRange(
int /*client*/,

View File

@ -241,6 +241,9 @@ typedef void (*InitExtension)(INITARGS);
#define _XAG_SERVER_
#include <X11/extensions/Xagstr.h>
#endif
#ifdef XACE
#include "xace.h"
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#include <X11/extensions/securstr.h>
@ -311,7 +314,11 @@ extern void DbeExtensionInit(INITARGS);
#ifdef XAPPGROUP
extern void XagExtensionInit(INITARGS);
#endif
#ifdef XACE
extern void XaceExtensionInit(INITARGS);
#endif
#ifdef XCSECURITY
extern void SecurityExtensionSetup(INITARGS);
extern void SecurityExtensionInit(INITARGS);
#endif
#ifdef XPRINT
@ -522,6 +529,9 @@ InitExtensions(argc, argv)
int argc;
char *argv[];
{
#ifdef XCSECURITY
SecurityExtensionSetup();
#endif
#ifdef PANORAMIX
# if !defined(PRINT_ONLY_SERVER) && !defined(NO_PANORAMIX)
if (!noPanoramiXExtension) PanoramiXExtensionInit();
@ -584,6 +594,9 @@ InitExtensions(argc, argv)
#ifdef XAPPGROUP
if (!noXagExtension) XagExtensionInit();
#endif
#ifdef XACE
XaceExtensionInit();
#endif
#ifdef XCSECURITY
if (!noSecurityExtension) SecurityExtensionInit();
#endif
@ -686,8 +699,11 @@ static ExtensionModule staticExtensions[] = {
#ifdef XAPPGROUP
{ XagExtensionInit, XAGNAME, &noXagExtension, NULL, NULL },
#endif
#ifdef XACE
{ XaceExtensionInit, XACE_EXTENSION_NAME, NULL, NULL, NULL },
#endif
#ifdef XCSECURITY
{ SecurityExtensionInit, SECURITY_EXTENSION_NAME, &noSecurityExtension, NULL, NULL },
{ SecurityExtensionInit, SECURITY_EXTENSION_NAME, &noSecurityExtension, SecurityExtensionSetup, NULL },
#endif
#ifdef XPRINT
{ XpExtensionInit, XP_PRINTNAME, NULL, NULL, NULL },

View File

@ -202,8 +202,8 @@ SOFTWARE.
#include "dixstruct.h"
#include "osdep.h"
#ifdef XCSECURITY
#include "securitysrv.h"
#ifdef XACE
#include "xace.h"
#endif
#ifndef PATH_MAX
@ -1386,15 +1386,6 @@ _X_EXPORT Bool LocalClient(ClientPtr client)
pointer addr;
register HOST *host;
#ifdef XCSECURITY
/* untrusted clients can't change host access */
if (client->trustLevel != XSecurityClientTrusted)
{
SecurityAudit("client %d attempted to change host access\n",
client->index);
return FALSE;
}
#endif
if (!_XSERVTransGetPeerAddr (((OsCommPtr)client->osPrivate)->trans_conn,
&notused, &alen, &from))
{
@ -1537,6 +1528,11 @@ AuthorizedClient(ClientPtr client)
{
if (!client || defeatAccessControl)
return TRUE;
#ifdef XACE
/* untrusted clients can't change host access */
if (!XaceHook(XACE_HOSTLIST_ACCESS, client, SecurityWriteAccess))
return FALSE;
#endif
return LocalClient(client);
}

View File

@ -148,6 +148,9 @@ extern __const__ int _nfiles;
#ifdef XAPPGROUP
#include "appgroup.h"
#endif
#ifdef XACE
#include "xace.h"
#endif
#ifdef XCSECURITY
#include "securitysrv.h"
#endif
@ -690,9 +693,8 @@ ClientAuthorized(ClientPtr client,
/* indicate to Xdmcp protocol that we've opened new client */
XdmcpOpenDisplay(priv->fd);
#endif /* XDMCP */
#ifdef XAPPGROUP
if (ClientStateCallback)
XagCallClientStateChange (client);
#ifdef XACE
XaceHook(XACE_AUTH_AVAIL, client, auth_id);
#endif
/* At this point, if the client is authorized to change the access control
* list, we should getpeername() information, and add the client to