> Date: Sat, 16 Aug 2025 15:19:26 +0200 > From: Martin Pieuchot <m...@grenadille.net> > > On 16/08/25(Sat) 14:41, Mark Kettenis wrote: > > > Date: Fri, 15 Aug 2025 15:53:25 +0200 > > > From: Martin Pieuchot <m...@grenadille.net> > > > > > > On 15/08/25(Fri) 15:45, Mark Kettenis wrote: > > > > > Date: Fri, 15 Aug 2025 14:06:06 +0200 > > > > > From: Martin Pieuchot <m...@grenadille.net> > > > > > > > > > > On 15/08/25(Fri) 13:17, Mark Kettenis wrote: > > > > > > > Date: Fri, 15 Aug 2025 11:51:18 +0200 > > > > > > > From: Martin Pieuchot <m...@grenadille.net> > > > > > > > > > > > > > > On 15/08/25(Fri) 09:39, Miod Vallat wrote: > > > > > > > > > Please don't. Keeping that page read-only is important for > > > > > > > > > security. > > > > > > > > > Maybe if nobody cares about the amd64 and i386 pmaps we > > > > > > > > > should just > > > > > > > > > delete those architectures? > > > > > > > > > > > > > > > > But remember, because the end argument was wrong (sz instead of > > > > > > > > va + > > > > > > > > sz), this call did *nothing*. > > > > > > > > > > > > > > > > At least the commented out code will be correct now. > > > > > > > > > > > > > > Exactly. Since you committed this code Mark it does nothing. > > > > > > > That's > > > > > > > what I said in the original report it's dead code. > > > > > > > > > > > > The original code (before I "broke" it) did an unmap of the memory. > > > > > > BTW that means we need to fix the comment. > > > > > > > > > > Indeed. I'd be glad if you could do that when enable the > > > > > uvm_map_protect() > > > > > call. > > > > > > > > ok? > > > > > > Would you please integrate the proper refcount & error handling I fixed in > > > my diff? > > > > I'm not sure the refcount and error handling in your diff makes sense. > > I'm not sure the current refcount and error handling makes sense > > either. > > All I want is correct code. This code has already been copied and it > took dv@ and I some iteration to get the refcount correct in vmm(4). > The diff I produced might not be needed but is similar to what we have > there and can be copied. > > > This sigobject is a permanent uvm object that is never going to be > > freed. It gets created the first time we do an exec. And if for some > > reason we fail to create it you won't be able to exec anything. Not > > even init(8)! > > Sure, I'm fine with a panic. > > > So I think it makes more sense to simply panic if that uvm_map() call > > fails. Not sure what to do with the uvm_map_protect() call. That > > call should never fail. And even if it does fail, the kernel will > > work just fine. So I'm inclined to leave it without an error check. > > Can we print a message in such case? I dislike silent failures. > > > At that point the reference counting should be really simple. The > > uao_create() call already gives us a reference. And since we no > > longer unmap the object we don't need another one. So we can actually > > drop the uao_reference() call that we have right now. > > Right. > > > I would rather make those changes in a separate commit though. > > Go for it.
So here is the diff I was thinking about. This fixes the reference count and turns failures into panic. I also removed the "r" variable since it was pointless and doing so results in more readable code. The comment gets adjusted again since we no longer explicitly "add a permanent reference". ok? Index: kern/kern_exec.c =================================================================== RCS file: /cvs/src/sys/kern/kern_exec.c,v retrieving revision 1.267 diff -u -p -r1.267 kern_exec.c --- kern/kern_exec.c 23 Aug 2025 16:12:52 -0000 1.267 +++ kern/kern_exec.c 23 Aug 2025 16:51:39 -0000 @@ -860,12 +860,12 @@ exec_sigcode_map(struct process *pr) /* * If we don't have a sigobject yet, create one. * - * sigobject is an anonymous memory object (just like SYSV shared - * memory) that we keep a permanent reference to and that we map - * in all processes that need this sigcode. The creation is simple, - * we create an object, add a permanent reference to it, map it in - * kernel space, copy out the sigcode to it and map it PROT_READ - * such that the coredump code can write it out into core dumps. + * sigobject is an anonymous memory object (just like SYSV + * shared memory) that we keep a permanent reference to and + * that we map in all processes that need this sigcode. The + * creation is simple, we create an object, map it in kernel + * space, copy out the sigcode to it and map it PROT_READ such + * that the coredump code can write it out into core dumps. * Then we map it with PROT_EXEC into the process just the way * sys_mmap would map it. */ @@ -874,17 +874,13 @@ exec_sigcode_map(struct process *pr) extern u_char sigfill[]; size_t off, left; vaddr_t va; - int r; - sigobject = uao_create(sz, 0); - uao_reference(sigobject); /* permanent reference */ + sigobject = uao_create(sz, 0); /* permanent reference */ - if ((r = uvm_map(kernel_map, &va, round_page(sz), sigobject, - 0, 0, UVM_MAPFLAG(PROT_READ | PROT_WRITE, PROT_READ | PROT_WRITE, - MAP_INHERIT_SHARE, MADV_RANDOM, 0)))) { - uao_detach(sigobject); - return (ENOMEM); - } + if (uvm_map(kernel_map, &va, round_page(sz), sigobject, 0, 0, + UVM_MAPFLAG(PROT_READ | PROT_WRITE, PROT_READ | PROT_WRITE, + MAP_INHERIT_SHARE, MADV_RANDOM, 0))) + panic("can't map sigobject"); for (off = 0, left = round_page(sz); left != 0; off += sigfillsiz) { @@ -894,8 +890,10 @@ exec_sigcode_map(struct process *pr) } memcpy((caddr_t)va, sigcode, sz); - (void) uvm_map_protect(kernel_map, va, round_page(va + sz), - PROT_READ, 0, FALSE, FALSE); + if (uvm_map_protect(kernel_map, va, round_page(va + sz), + PROT_READ, 0, FALSE, FALSE)) + panic("can't write-protect sigobject"); + sigcode_va = va; sigcode_sz = round_page(sz); }