Re: KKIS19990914.004b: ShareDream - shared memory - ipc vulnerability

Henrik Nordstrom (hno@hem.passagen.se)
Wed, 15 Sep 1999 01:57:57 +0200


This is a multi-part message in MIME format.

--------------33C58AFA3CE85E0572267A4
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit

Attached is a trivial Linux-2.2.12 patch wich adds add a procfs entry
for tuning the limit of shared memory allocable.

/proc/sys/kernel/shmmax Max number of shared memory pages

Attached is also a small hack for freeing unreferenced shared memory
pages and printing interesting details of available shared memory
segments (such as who created the segment, and when).

I am assuming others have made similar patches and tools before, but no
effective limit on shared memory exists in base Linux-2.2.12.

--
Henrik Nordstrom

Robert 'Shadow' Paj1k wrote:

[snip] > Raport title : Shared Memory DoS - IPC vulnerability (Linux > abuse as example) > Problem found by : Robert Pajak (shadow@security.kki.pl), > probably other ppl found that first - one of them is > lcamtuf, Solar Designer is probably other... [snip] > This is due to fact that shared memory segments can exist without > beeing bind with processes. To protect you should diable this > operations, or use Solar Designer's stack patch with limits set, > etc... [snip]

--------------33C58AFA3CE85E0572267A4 Content-Type: text/plain; charset=us-ascii; name="ipc_limit.patch" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="ipc_limit.patch"

--- linux/ipc/shm.c.orig Wed Sep 15 00:44:11 1999 +++ linux/ipc/shm.c Wed Sep 15 00:44:36 1999 @@ -68,6 +68,8 @@ return -1; } +int shmall = SHMALL; + /* * allocate new shmid_kernel and pgtable. protected by shm_segs[id] = NOID. */ @@ -79,7 +81,7 @@ if (size < SHMMIN) return -EINVAL; - if (shm_tot + numpages >= SHMALL) + if (shm_tot + numpages >= shmall) return -ENOSPC; for (id = 0; id < SHMMNI; id++) if (shm_segs[id] == IPC_UNUSED) { @@ -233,7 +235,7 @@ shminfo.shmmni = SHMMNI; shminfo.shmmax = shmmax; shminfo.shmmin = SHMMIN; - shminfo.shmall = SHMALL; + shminfo.shmall = shmall; shminfo.shmseg = SHMSEG; if(copy_to_user (buf, &shminfo, sizeof(struct shminfo))) goto out; --- linux/kernel/sysctl.c.orig Mon Aug 9 21:05:13 1999 +++ linux/kernel/sysctl.c Wed Sep 15 00:41:19 1999 @@ -47,6 +47,7 @@ #endif #ifdef CONFIG_SYSVIPC extern int shmmax; +extern int shmall; #endif #ifdef __sparc__ @@ -213,6 +214,8 @@ 0644, NULL, &proc_dointvec}, #ifdef CONFIG_SYSVIPC {KERN_SHMMAX, "shmmax", &shmmax, sizeof (int), + 0644, NULL, &proc_dointvec}, + {KERN_SHMMAX, "shmall", &shmall, sizeof (int), 0644, NULL, &proc_dointvec}, #endif #ifdef CONFIG_MAGIC_SYSRQ

--------------33C58AFA3CE85E0572267A4 Content-Type: text/plain; charset=us-ascii; name="free_shmem.c" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="free_shmem.c"

#include <stdio.h> #include <sys/ipc.h> #include <sys/shm.h> #include <time.h>

int main(void) { int i, id; struct shminfo shmi; struct shmid_ds sds;

shmctl(0, IPC_INFO, (void *)&shmi);

for(i=0; i<shmi.shmmni;i++) { if ((id = shmctl(i, SHM_STAT, &sds)) >= 0) { printf("SHM %d: size=%d cuid=%d cgid=%d cpid=%d lpid=%d uses=%d created %s", id, sds.shm_segsz, sds.shm_perm.cuid, sds.shm_perm.cgid, sds.shm_cpid, sds.shm_lpid, sds.shm_nattch, ctime(&sds.shm_ctime)); if (sds.shm_nattch == 0) { shmctl(id, IPC_RMID, NULL); printf("SHM segment %d freed\n", id); } } } return 0; }

--------------33C58AFA3CE85E0572267A4--

- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.rutgers.edu Please read the FAQ at http://www.tux.org/lkml/