summaryrefslogtreecommitdiff
path: root/Xext/shm.c
diff options
context:
space:
mode:
authorEamon Walsh <ewalsh@tycho.nsa.gov>2007-10-17 15:00:54 -0400
committerEamon Walsh <ewalsh@moss-charon.epoch.ncsc.mil>2007-10-17 15:00:54 -0400
commitc3f7b862550fa8f46633162f83db8c27e46fc672 (patch)
treea8427c93c96af2bbf2133b07f2510ff31560e54d /Xext/shm.c
parentaf4dde0ac19ecec1d0ad988eb25b15401e7c6b36 (diff)
parentfeac0759522cbdc3e61ccfa373df735903c5cb27 (diff)
Merge branch 'master' into XACE-SELINUX
Conflicts: os/access.c
Diffstat (limited to 'Xext/shm.c')
-rw-r--r--Xext/shm.c98
1 files changed, 75 insertions, 23 deletions
diff --git a/Xext/shm.c b/Xext/shm.c
index 56a944be1..db3c2ec90 100644
--- a/Xext/shm.c
+++ b/Xext/shm.c
@@ -64,6 +64,33 @@ in this Software without prior written authorization from The Open Group.
#include <X11/extensions/shmstr.h>
#include <X11/Xfuncproto.h>
+/* Needed for Solaris cross-zone shared memory extension */
+#ifdef HAVE_SHMCTL64
+#include <sys/ipc_impl.h>
+#define SHMSTAT(id, buf) shmctl64(id, IPC_STAT64, buf)
+#define SHMSTAT_TYPE struct shmid_ds64
+#define SHMPERM_TYPE struct ipc_perm64
+#define SHM_PERM(buf) buf.shmx_perm
+#define SHM_SEGSZ(buf) buf.shmx_segsz
+#define SHMPERM_UID(p) p->ipcx_uid
+#define SHMPERM_CUID(p) p->ipcx_cuid
+#define SHMPERM_GID(p) p->ipcx_gid
+#define SHMPERM_CGID(p) p->ipcx_cgid
+#define SHMPERM_MODE(p) p->ipcx_mode
+#define SHMPERM_ZONEID(p) p->ipcx_zoneid
+#else
+#define SHMSTAT(id, buf) shmctl(id, IPC_STAT, buf)
+#define SHMSTAT_TYPE struct shmid_ds
+#define SHMPERM_TYPE struct ipc_perm
+#define SHM_PERM(buf) buf.shm_perm
+#define SHM_SEGSZ(buf) buf.shm_segsz
+#define SHMPERM_UID(p) p->uid
+#define SHMPERM_CUID(p) p->cuid
+#define SHMPERM_GID(p) p->gid
+#define SHMPERM_CGID(p) p->cgid
+#define SHMPERM_MODE(p) p->mode
+#endif
+
#ifdef PANORAMIX
#include "panoramiX.h"
#include "panoramiXsrv.h"
@@ -362,32 +389,57 @@ ProcShmQueryVersion(client)
* using the credentials from the client if available
*/
static int
-shm_access(ClientPtr client, struct ipc_perm *perm, int readonly)
+shm_access(ClientPtr client, SHMPERM_TYPE *perm, int readonly)
{
int uid, gid;
mode_t mask;
+ int uidset = 0, gidset = 0;
+ LocalClientCredRec *lcc;
+
+ if (GetLocalClientCreds(client, &lcc) != -1) {
- if (LocalClientCred(client, &uid, &gid) != -1) {
-
- /* User id 0 always gets access */
- if (uid == 0) {
- return 0;
+ if (lcc->fieldsSet & LCC_UID_SET) {
+ uid = lcc->euid;
+ uidset = 1;
+ }
+ if (lcc->fieldsSet & LCC_GID_SET) {
+ gid = lcc->egid;
+ gidset = 1;
}
- /* Check the owner */
- if (perm->uid == uid || perm->cuid == uid) {
- mask = S_IRUSR;
- if (!readonly) {
- mask |= S_IWUSR;
+
+#if defined(HAVE_GETZONEID) && defined(SHMPERM_ZONEID)
+ if ( ((lcc->fieldsSet & LCC_ZID_SET) == 0) || (lcc->zoneid == -1)
+ || (lcc->zoneid != SHMPERM_ZONEID(perm))) {
+ uidset = 0;
+ gidset = 0;
+ }
+#endif
+ FreeLocalClientCreds(lcc);
+
+ if (uidset) {
+ /* User id 0 always gets access */
+ if (uid == 0) {
+ return 0;
+ }
+ /* Check the owner */
+ if (SHMPERM_UID(perm) == uid || SHMPERM_CUID(perm) == uid) {
+ mask = S_IRUSR;
+ if (!readonly) {
+ mask |= S_IWUSR;
+ }
+ return (SHMPERM_MODE(perm) & mask) == mask ? 0 : -1;
}
- return (perm->mode & mask) == mask ? 0 : -1;
}
- /* Check the group */
- if (perm->gid == gid || perm->cgid == gid) {
- mask = S_IRGRP;
- if (!readonly) {
- mask |= S_IWGRP;
+
+ if (gidset) {
+ /* Check the group */
+ if (SHMPERM_GID(perm) == gid || SHMPERM_CGID(perm) == gid) {
+ mask = S_IRGRP;
+ if (!readonly) {
+ mask |= S_IWGRP;
+ }
+ return (SHMPERM_MODE(perm) & mask) == mask ? 0 : -1;
}
- return (perm->mode & mask) == mask ? 0 : -1;
}
}
/* Otherwise, check everyone else */
@@ -395,14 +447,14 @@ shm_access(ClientPtr client, struct ipc_perm *perm, int readonly)
if (!readonly) {
mask |= S_IWOTH;
}
- return (perm->mode & mask) == mask ? 0 : -1;
+ return (SHMPERM_MODE(perm) & mask) == mask ? 0 : -1;
}
static int
ProcShmAttach(client)
register ClientPtr client;
{
- struct shmid_ds buf;
+ SHMSTAT_TYPE buf;
ShmDescPtr shmdesc;
REQUEST(xShmAttachReq);
@@ -431,7 +483,7 @@ ProcShmAttach(client)
shmdesc->addr = shmat(stuff->shmid, 0,
stuff->readOnly ? SHM_RDONLY : 0);
if ((shmdesc->addr == ((char *)-1)) ||
- shmctl(stuff->shmid, IPC_STAT, &buf))
+ SHMSTAT(stuff->shmid, &buf))
{
xfree(shmdesc);
return BadAccess;
@@ -441,7 +493,7 @@ ProcShmAttach(client)
* do manual checking of access rights for the credentials
* of the client */
- if (shm_access(client, &(buf.shm_perm), stuff->readOnly) == -1) {
+ if (shm_access(client, &(SHM_PERM(buf)), stuff->readOnly) == -1) {
shmdt(shmdesc->addr);
xfree(shmdesc);
return BadAccess;
@@ -450,7 +502,7 @@ ProcShmAttach(client)
shmdesc->shmid = stuff->shmid;
shmdesc->refcnt = 1;
shmdesc->writable = !stuff->readOnly;
- shmdesc->size = buf.shm_segsz;
+ shmdesc->size = SHM_SEGSZ(buf);
shmdesc->next = Shmsegs;
Shmsegs = shmdesc;
}