DragonFlyBSD Kernel Audit
DF-0095 / fix.diff
← back to finding ↓ download raw
diff --git a/sys/kern/sysv_shm.c b/sys/kern/sysv_shm.c
--- a/sys/kern/sysv_shm.c
+++ b/sys/kern/sysv_shm.c
@@ -239,7 +239,7 @@
 		error = EINVAL;
 		goto done;
 	}
-	for (i = 0; i < shminfo.shmseg; i++, shmmap_s++) {
+	for (i = 0; i < imin(shminfo.shmseg, SHMMNI); i++, shmmap_s++) {
 		if (shmmap_s->shmid != -1 &&
 		    shmmap_s->va == (vm_offset_t)uap->shmaddr)
 			break;
@@ -281,9 +281,9 @@
 again:
 	shmmap_s = (struct shmmap_state *)p->p_vmspace->vm_shm;
 	if (shmmap_s == NULL) {
-		size = shminfo.shmseg * sizeof(struct shmmap_state);
+		size = SHMMNI * sizeof(struct shmmap_state);
 		shmmap_s = kmalloc(size, M_SHM, M_WAITOK);
-		for (i = 0; i < shminfo.shmseg; i++) {
+		for (i = 0; i < imin(shminfo.shmseg, SHMMNI); i++) {
 			shmmap_s[i].shmid = -1;
 			shmmap_s[i].reserved = 0;
 		}
@@ -309,14 +309,14 @@
 	 * interrupted by blocking operations.  The shmmap_s reservation
 	 * will be cleared upon completion or error.
 	 */
-	for (i = 0; i < shminfo.shmseg; i++) {
+	for (i = 0; i < imin(shminfo.shmseg, SHMMNI); i++) {
 		if (shmmap_s->shmid == -1 && shmmap_s->reserved == 0) {
 			shmmap_s->reserved = 1;
 			break;
 		}
 		shmmap_s++;
 	}
-	if (i >= shminfo.shmseg) {
+	if (i >= imin(shminfo.shmseg, SHMMNI)) {
 		error = EMFILE;
 		goto done;
 	}
@@ -651,11 +651,11 @@
 	int i;
 
 	lwkt_gettoken(&shm_token);
-	size = shminfo.shmseg * sizeof(struct shmmap_state);
+	size = SHMMNI * sizeof(struct shmmap_state);
 	shmmap_s = kmalloc(size, M_SHM, M_WAITOK);
 	bcopy((caddr_t)p1->p_vmspace->vm_shm, (caddr_t)shmmap_s, size);
 	p2->p_vmspace->vm_shm = (caddr_t)shmmap_s;
-	for (i = 0; i < shminfo.shmseg; i++, shmmap_s++) {
+	for (i = 0; i < imin(shminfo.shmseg, SHMMNI); i++, shmmap_s++) {
 		if (shmmap_s->shmid != -1)
 			shmsegs[IPCID_TO_IX(shmmap_s->shmid)].shm_nattch++;
 	}
@@ -671,7 +671,7 @@
 	if ((base = (struct shmmap_state *)vm->vm_shm) != NULL) {
 		vm->vm_shm = NULL;
 		lwkt_gettoken(&shm_token);
-		for (i = 0, shm = base; i < shminfo.shmseg; i++, shm++) {
+		for (i = 0, shm = base; i < imin(shminfo.shmseg, SHMMNI); i++, shm++) {
 			if (shm->shmid != -1)
 				shm_delete_mapping(vm, shm);
 		}