From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.0 required=3.0 tests=DKIMWL_WL_MED,DKIM_SIGNED, DKIM_VALID,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH,MAILING_LIST_MULTI, SIGNED_OFF_BY,SPF_PASS,URIBL_BLOCKED autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 933ABC282CC for ; Mon, 11 Feb 2019 05:18:40 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id 578F620855 for ; Mon, 11 Feb 2019 05:18:40 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=amacapital-net.20150623.gappssmtp.com header.i=@amacapital-net.20150623.gappssmtp.com header.b="xyuciNjk" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726896AbfBKFSj (ORCPT ); Mon, 11 Feb 2019 00:18:39 -0500 Received: from mail-pg1-f193.google.com ([209.85.215.193]:38250 "EHLO mail-pg1-f193.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726157AbfBKFSi (ORCPT ); Mon, 11 Feb 2019 00:18:38 -0500 Received: by mail-pg1-f193.google.com with SMTP id g189so4454144pgc.5 for ; Sun, 10 Feb 2019 21:18:37 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=amacapital-net.20150623.gappssmtp.com; s=20150623; h=mime-version:subject:from:in-reply-to:date:cc :content-transfer-encoding:message-id:references:to; bh=P/nz3ACoxpLDqb0eHS2Lbfh7g08M62jcwE0fE5p6slQ=; b=xyuciNjkFWciBsSx/is2lBM2iiUNDec2HmbyGj9VTUJYEYAUDuSAr19G2O+5RQXZja kDN98a6hx1onWzTw7CzmW+8qMZmYMnWAibmq/6o1dY+qqCj/M3v6KtlTjBFVdVkmnHU7 0aadpz2eqQLSu6Ist19NGgHJ/rqUS0wyDRkHsl/XcQorAL9QaroZvLPCNGCdzSNG0/sD jkdB1uk7FF3ixo/nUGKC57zIIWHDq+mUzpn29lf3AgAXtDae1qKETi1id1Y4c6r3ZFRG fr2FI8bBDK7khVD+ie9FEuGxSE6QU26XGV9pCOiVMG3MKav8TqVqSrNRJ0uvlV/Q4j8B o21Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:subject:from:in-reply-to:date:cc :content-transfer-encoding:message-id:references:to; bh=P/nz3ACoxpLDqb0eHS2Lbfh7g08M62jcwE0fE5p6slQ=; b=fwazTZ20cy9MPtItikRRZ7Zkr7sJ4zl5fJUr/qE+p7Pgar1BFtbV6eyhRoxfGxgZHE gfiN5HD3KiG0t7Q6YwccwUEN5U0Qd2k/uqB2f1EOvktdNkdB41inGoCfrTuk3DzxBR5a mxghDU77pdlU+CsL4RW5tkSTIm5XENur3MslGY6zIpyW0zPMaXHvK9C1mPynHBhUVlqL Bo1A+qFV9O9TzanHw9qlHbbcpezMGqsRG47WXwrWUEVV3aTdGsNtgwz48wRDJE3PNtMf 0asubPirDwRcngc0gEQNoRRzF/TMhn6SbBbS0F1C7J3USESYioS7xf4gW0m8lhFYlQQE zjnA== X-Gm-Message-State: AHQUAuYI8m09lzvfrKj1R/s4IfjiRLf5rU2uwv1DXcPhPAzaGeSm4DN+ eokQOvXYiOcTryoj8QL7UJoSjw== X-Google-Smtp-Source: AHgI3IZOahjUxu+t0qhpsn/mwzusbGjfiQw5XyvsSy/I2w+d8AyD7+Aa4/VTebWQOBBX1/tTqaH/jA== X-Received: by 2002:a63:61d8:: with SMTP id v207mr7347489pgb.308.1549862317394; Sun, 10 Feb 2019 21:18:37 -0800 (PST) Received: from ?IPv6:2601:646:c200:7429:5d4d:83bf:b51b:8718? ([2601:646:c200:7429:5d4d:83bf:b51b:8718]) by smtp.gmail.com with ESMTPSA id l11sm11539621pff.65.2019.02.10.21.18.35 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Sun, 10 Feb 2019 21:18:35 -0800 (PST) Content-Type: text/plain; charset=utf-8 Mime-Version: 1.0 (1.0) Subject: Re: [PATCH v2 05/20] x86/alternative: initializing temporary mm for patching From: Andy Lutomirski X-Mailer: iPhone Mail (16C101) In-Reply-To: <162C6C29-CD81-46FE-9A54-6ED05A93A9CB@gmail.com> Date: Sun, 10 Feb 2019 21:18:34 -0800 Cc: Rick Edgecombe , Andy Lutomirski , Ingo Molnar , LKML , X86 ML , "H. Peter Anvin" , Thomas Gleixner , Borislav Petkov , Dave Hansen , Peter Zijlstra , Damian Tometzki , linux-integrity , LSM List , Andrew Morton , Kernel Hardening , Linux-MM , Will Deacon , Ard Biesheuvel , Kristen Carlson Accardi , "Dock, Deneen T" , Kees Cook , Dave Hansen Content-Transfer-Encoding: quoted-printable Message-Id: <00649AE8-69C0-4CD2-A916-B8C8F0F5DAC3@amacapital.net> References: <20190129003422.9328-1-rick.p.edgecombe@intel.com> <20190129003422.9328-6-rick.p.edgecombe@intel.com> <162C6C29-CD81-46FE-9A54-6ED05A93A9CB@gmail.com> To: Nadav Amit Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Feb 10, 2019, at 4:39 PM, Nadav Amit wrote: >> On Jan 28, 2019, at 4:34 PM, Rick Edgecombe w= rote: >>=20 >> From: Nadav Amit >>=20 >> To prevent improper use of the PTEs that are used for text patching, we >> want to use a temporary mm struct. We initailize it by copying the init >> mm. >>=20 >> The address that will be used for patching is taken from the lower area >> that is usually used for the task memory. Doing so prevents the need to >> frequently synchronize the temporary-mm (e.g., when BPF programs are >> installed), since different PGDs are used for the task memory. >>=20 >> Finally, we randomize the address of the PTEs to harden against exploits >> that use these PTEs. >>=20 >> Cc: Kees Cook >> Cc: Dave Hansen >> Acked-by: Peter Zijlstra (Intel) >> Reviewed-by: Masami Hiramatsu >> Tested-by: Masami Hiramatsu >> Suggested-by: Andy Lutomirski >> Signed-off-by: Nadav Amit >> Signed-off-by: Rick Edgecombe >> --- >> arch/x86/include/asm/pgtable.h | 3 +++ >> arch/x86/include/asm/text-patching.h | 2 ++ >> arch/x86/kernel/alternative.c | 3 +++ >> arch/x86/mm/init_64.c | 36 ++++++++++++++++++++++++++++ >> init/main.c | 3 +++ >> 5 files changed, 47 insertions(+) >>=20 >> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtabl= e.h >> index 40616e805292..e8f630d9a2ed 100644 >> --- a/arch/x86/include/asm/pgtable.h >> +++ b/arch/x86/include/asm/pgtable.h >> @@ -1021,6 +1021,9 @@ static inline void __meminit init_trampoline_defaul= t(void) >> /* Default trampoline pgd value */ >> trampoline_pgd_entry =3D init_top_pgt[pgd_index(__PAGE_OFFSET)]; >> } >> + >> +void __init poking_init(void); >> + >> # ifdef CONFIG_RANDOMIZE_MEMORY >> void __meminit init_trampoline(void); >> # else >> diff --git a/arch/x86/include/asm/text-patching.h b/arch/x86/include/asm/= text-patching.h >> index f8fc8e86cf01..a75eed841eed 100644 >> --- a/arch/x86/include/asm/text-patching.h >> +++ b/arch/x86/include/asm/text-patching.h >> @@ -39,5 +39,7 @@ extern void *text_poke_kgdb(void *addr, const void *opc= ode, size_t len); >> extern int poke_int3_handler(struct pt_regs *regs); >> extern void *text_poke_bp(void *addr, const void *opcode, size_t len, voi= d *handler); >> extern int after_bootmem; >> +extern __ro_after_init struct mm_struct *poking_mm; >> +extern __ro_after_init unsigned long poking_addr; >>=20 >> #endif /* _ASM_X86_TEXT_PATCHING_H */ >> diff --git a/arch/x86/kernel/alternative.c b/arch/x86/kernel/alternative.= c >> index 12fddbc8c55b..ae05fbb50171 100644 >> --- a/arch/x86/kernel/alternative.c >> +++ b/arch/x86/kernel/alternative.c >> @@ -678,6 +678,9 @@ void *__init_or_module text_poke_early(void *addr, co= nst void *opcode, >> return addr; >> } >>=20 >> +__ro_after_init struct mm_struct *poking_mm; >> +__ro_after_init unsigned long poking_addr; >> + >> static void *__text_poke(void *addr, const void *opcode, size_t len) >> { >> unsigned long flags; >> diff --git a/arch/x86/mm/init_64.c b/arch/x86/mm/init_64.c >> index bccff68e3267..125c8c48aa24 100644 >> --- a/arch/x86/mm/init_64.c >> +++ b/arch/x86/mm/init_64.c >> @@ -53,6 +53,7 @@ >> #include >> #include >> #include >> +#include >>=20 >> #include "mm_internal.h" >>=20 >> @@ -1383,6 +1384,41 @@ unsigned long memory_block_size_bytes(void) >> return memory_block_size_probed; >> } >>=20 >> +/* >> + * Initialize an mm_struct to be used during poking and a pointer to be u= sed >> + * during patching. >> + */ >> +void __init poking_init(void) >> +{ >> + spinlock_t *ptl; >> + pte_t *ptep; >> + >> + poking_mm =3D copy_init_mm(); >> + BUG_ON(!poking_mm); >> + >> + /* >> + * Randomize the poking address, but make sure that the following pa= ge >> + * will be mapped at the same PMD. We need 2 pages, so find space fo= r 3, >> + * and adjust the address if the PMD ends after the first one. >> + */ >> + poking_addr =3D TASK_UNMAPPED_BASE; >> + if (IS_ENABLED(CONFIG_RANDOMIZE_BASE)) >> + poking_addr +=3D (kaslr_get_random_long("Poking") & PAGE_MASK) %= >> + (TASK_SIZE - TASK_UNMAPPED_BASE - 3 * PAGE_SIZE); >> + >> + if (((poking_addr + PAGE_SIZE) & ~PMD_MASK) =3D=3D 0) >> + poking_addr +=3D PAGE_SIZE; >=20 > Further thinking about it, I think that allocating the virtual address for= > poking from user address-range is problematic. The user can set watchpoint= s > on different addresses, cause some static-keys to be enabled/disabled, and= > monitor the signals to derandomize the poking address. >=20 Hmm, I hadn=E2=80=99t thought about watchpoints. I=E2=80=99m not sure how mu= ch we care about possible derandomization like this, but we certainly don=E2= =80=99t want to send signals or otherwise malfunction. > Andy, I think you were pushing this change. Can I go back to use a vmalloc= =E2=80=99d > address instead, or do you have a better solution? Hmm. If we use a vmalloc address, we have to make sure it=E2=80=99s not actu= ally allocated. I suppose we could allocate one once at boot and use that. W= e also have the problem that the usual APIs for handling =E2=80=9Cuser=E2=80= =9D addresses might assume they=E2=80=99re actually in the user range, altho= ugh this seems unlikely to be a problem in practice. More seriously, though= , the code that manipulates per-mm paging structures assumes that *all* of t= he structures up to the top level are per-mm, and, if we use anything less t= han a private pgd, this isn=E2=80=99t the case. > I prefer not to > save/restore DR7, of course. >=20 I suspect we may want to use the temporary mm concept for EFI, too, so we ma= y want to just suck it up and save/restore DR7. But only if a watchpoint is= in use, of course. I have an old patch I could dust off that tracks DR7 to m= ake things like this efficient.=