On Tue, Apr 16, 2024 at 12:36:08PM +0300, Nadav Amit wrote: > > > > On 11 Apr 2024, at 19:05, Mike Rapoport <rppt@xxxxxxxxxx> wrote: > > > > @@ -2440,7 +2479,24 @@ static int post_relocation(struct module *mod, const struct load_info *info) > > add_kallsyms(mod, info); > > > > /* Arch-specific module finalizing. */ > > - return module_finalize(info->hdr, info->sechdrs, mod); > > + ret = module_finalize(info->hdr, info->sechdrs, mod); > > + if (ret) > > + return ret; > > + > > + for_each_mod_mem_type(type) { > > + struct module_memory *mem = &mod->mem[type]; > > + > > + if (mem->is_rox) { > > + if (!execmem_update_copy(mem->base, mem->rw_copy, > > + mem->size)) > > + return -ENOMEM; > > + > > + vfree(mem->rw_copy); > > + mem->rw_copy = NULL; > > + } > > + } > > + > > + return 0; > > } > > I might be missing something, but it seems a bit racy. > > IIUC, module_finalize() calls alternatives_smp_module_add(). At this > point, since you don’t hold the text_mutex, some might do text_poke(), > e.g., by enabling/disabling static-key, and the update would be > overwritten. No? Right :( Even worse, for UP case alternatives_smp_unlock() will "patch" still empty area. So I'm thinking about calling alternatives_smp_module_add() from an additional callback after the execmem_update_copy(). Does it make sense to you? -- Sincerely yours, Mike.