git: dad6e6fc1ea4 - main - Provide more precise error explanations for mmap(2) EINVAL errors.

From: Kirk McKusick <mckusick_at_FreeBSD.org>
Date: Thu, 19 Mar 2026 00:53:13 UTC
The branch main has been updated by mckusick:

URL: https://cgit.FreeBSD.org/src/commit/?id=dad6e6fc1ea4b737e9f1661ebd30da5d551e3d4a

commit dad6e6fc1ea4b737e9f1661ebd30da5d551e3d4a
Author:     Kirk McKusick <mckusick@FreeBSD.org>
AuthorDate: 2026-03-19 00:52:10 +0000
Commit:     Kirk McKusick <mckusick@FreeBSD.org>
CommitDate: 2026-03-19 00:52:10 +0000

    Provide more precise error explanations for mmap(2) EINVAL errors.
    
    Reviewed by:  kib
    Differential Revision: https://reviews.freebsd.org/D55888
    MFC-after:    1 week
    Sponsored by: Netflix
---
 sys/vm/vm_mmap.c | 36 +++++++++++++++++++++++-------------
 1 file changed, 23 insertions(+), 13 deletions(-)

diff --git a/sys/vm/vm_mmap.c b/sys/vm/vm_mmap.c
index cb5906440f56..8d71bce67d58 100644
--- a/sys/vm/vm_mmap.c
+++ b/sys/vm/vm_mmap.c
@@ -235,11 +235,15 @@ kern_mmap(struct thread *td, const struct mmap_req *mrp)
 	 * pos.
 	 */
 	if (!SV_CURPROC_FLAG(SV_AOUT)) {
-		if ((len == 0 && p->p_osrel >= P_OSREL_MAP_ANON) ||
-		    ((flags & MAP_ANON) != 0 && (fd != -1 || pos != 0))) {
-			return (EXTERROR(EINVAL,
-			    "offset %#jd not zero/fd %#jd not -1 for MAP_ANON",
-			    fd, pos));
+		if (len == 0 && p->p_osrel >= P_OSREL_MAP_ANON)
+			return (EXTERROR(EINVAL, "mapping with zero length"));
+		if ((flags & MAP_ANON) != 0) {
+			if (fd != -1)
+				return (EXTERROR(EINVAL,
+				    "fd %#jd not -1 for MAP_ANON", fd));
+			if (pos != 0)
+				return (EXTERROR(EINVAL,
+				    "offset %#jd not zero for MAP_ANON", pos));
 		}
 	} else {
 		if ((flags & MAP_ANON) != 0)
@@ -293,10 +297,14 @@ kern_mmap(struct thread *td, const struct mmap_req *mrp)
 
 	/* Ensure alignment is at least a page and fits in a pointer. */
 	align = flags & MAP_ALIGNMENT_MASK;
-	if (align != 0 && align != MAP_ALIGNED_SUPER &&
-	    (align >> MAP_ALIGNMENT_SHIFT >= sizeof(void *) * NBBY ||
-	    align >> MAP_ALIGNMENT_SHIFT < PAGE_SHIFT)) {
-		return (EXTERROR(EINVAL, "bad alignment %#jx", align));
+	if (align != 0 && align != MAP_ALIGNED_SUPER) {
+		if (align >> MAP_ALIGNMENT_SHIFT >= sizeof(void *) * NBBY)
+			return (EXTERROR(EINVAL, "bad alignment %#jx >= %#jx",
+			    align >> MAP_ALIGNMENT_SHIFT,
+			    sizeof(void *) * NBBY));
+		else if (align >> MAP_ALIGNMENT_SHIFT < PAGE_SHIFT)
+			return (EXTERROR(EINVAL, "bad alignment %#jx < %#jx",
+			    align >> MAP_ALIGNMENT_SHIFT, PAGE_SHIFT));
 	}
 
 	/*
@@ -312,15 +320,17 @@ kern_mmap(struct thread *td, const struct mmap_req *mrp)
 		addr -= pageoff;
 		if ((addr & PAGE_MASK) != 0) {
 			return (EXTERROR(EINVAL,
-			    "fixed mapping at %#jx not aligned", addr));
+			    "fixed mapping at %#jx not page aligned %#jx", addr,
+			    PAGE_SIZE));
 		}
 
 		/* Address range must be all in user VM space. */
 		if (!vm_map_range_valid(&vms->vm_map, addr, addr + size)) {
-			EXTERROR(EINVAL, "mapping outside vm_map");
-			return (EINVAL);
+			return (EXTERROR(EINVAL,
+			    "mapping %#jx-%#jx outside vm_map", addr,
+			    addr + size));
 		}
-		if (flags & MAP_32BIT && addr + size > MAP_32BIT_MAX_ADDR) {
+		if ((flags & MAP_32BIT) && addr + size > MAP_32BIT_MAX_ADDR) {
 			return (EXTERROR(EINVAL,
 		    "fixed 32bit mapping of [%#jx %#jx] does not fit into 4G",
 			    addr, addr + size));