From patchwork Wed Jul 17 08:14:31 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Alan Hayward X-Patchwork-Id: 33724 Received: (qmail 63873 invoked by alias); 17 Jul 2019 08:14:47 -0000 Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org Delivered-To: mailing list gdb-patches@sourceware.org Received: (qmail 63864 invoked by uid 89); 17 Jul 2019 08:14:47 -0000 Authentication-Results: sourceware.org; auth=none X-Spam-SWARE-Status: No, score=-24.0 required=5.0 tests=AWL, BAYES_00, GIT_PATCH_0, GIT_PATCH_1, GIT_PATCH_2, GIT_PATCH_3, RCVD_IN_DNSWL_NONE, SPF_HELO_PASS, SPF_PASS autolearn=ham version=3.3.1 spammy=apple, Apple, authentication X-HELO: EUR01-HE1-obe.outbound.protection.outlook.com Received: from mail-eopbgr130041.outbound.protection.outlook.com (HELO EUR01-HE1-obe.outbound.protection.outlook.com) (40.107.13.41) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Wed, 17 Jul 2019 08:14:44 +0000 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=armh.onmicrosoft.com; s=selector2-armh-onmicrosoft-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=20scTawldTDw1RoBfKZYiGDFVeFLHbxg97nPCvD5mP0=; b=ITlDw5zfepNaR60qVRazxQN1M1fKp1y3tJiyohg5B0vBCD+9uUA9zr/Z8CF8aJpF1duP9HmhllMfP9Bgv6Sa5mrwu71D4HP0Xv6TNJpQg+7Vc2WhFkoYGHWB6Sm7wYlX8PV/9J0qnYXXEZdnTj2fvfIm7155QZIWYiI3mK7EwdE= Received: from AM6PR08CA0045.eurprd08.prod.outlook.com (2603:10a6:20b:c0::33) by AM0PR08MB4946.eurprd08.prod.outlook.com (2603:10a6:208:165::13) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.2073.14; Wed, 17 Jul 2019 08:14:40 +0000 Received: from AM5EUR03FT023.eop-EUR03.prod.protection.outlook.com (2a01:111:f400:7e08::205) by AM6PR08CA0045.outlook.office365.com (2603:10a6:20b:c0::33) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384) id 15.20.2073.14 via Frontend Transport; Wed, 17 Jul 2019 08:14:39 +0000 Authentication-Results: spf=temperror (sender IP is 63.35.35.123) smtp.mailfrom=arm.com; sourceware.org; dkim=pass (signature was verified) header.d=armh.onmicrosoft.com; sourceware.org; dmarc=temperror action=none header.from=arm.com; Received-SPF: TempError (protection.outlook.com: error in processing during lookup of arm.com: DNS Timeout) Received: from 64aa7808-outbound-1.mta.getcheckrecipient.com (63.35.35.123) by AM5EUR03FT023.mail.protection.outlook.com (10.152.16.169) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384) id 15.20.2052.18 via Frontend Transport; Wed, 17 Jul 2019 08:14:38 +0000 Received: ("Tessian outbound cb57de15885d:v24"); Wed, 17 Jul 2019 08:14:38 +0000 X-CheckRecipientChecked: true X-CR-MTA-CID: 580754d99aa2c863 X-CR-MTA-TID: 64aa7808 Received: from 5ce1e319f69b.2 (cr-mta-lb-1.cr-mta-net [104.47.6.59]) by 64aa7808-outbound-1.mta.getcheckrecipient.com id 1520B922-4170-478F-A69C-402DFDBF3578.1; Wed, 17 Jul 2019 08:14:33 +0000 Received: from EUR02-VE1-obe.outbound.protection.outlook.com (mail-ve1eur02lp2059.outbound.protection.outlook.com [104.47.6.59]) by 64aa7808-outbound-1.mta.getcheckrecipient.com with ESMTPS id 5ce1e319f69b.2 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384); Wed, 17 Jul 2019 08:14:33 +0000 ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=YoyRd4sqRcNUZO9DE71EQZA+f5S8tHOTTbMQDZVRjNj6wbeFReczi2s3wl6Pa6DOAL98lc9oIdt0A7pq9sapocze8S0v+9IW8lo4EaRcPKJEGGG7sWcNOjWxNHlgEjpaNX5ITGWI+DkALlbXD0cwiSx6Vq+vcG8nFacvgAAf0sMheG8RvEcT9oqEyuvOb1LboH2oUKBDnsrsTDMwfkbru4zP/SXZLM0UJd9jblw74RSyMQUcGCC0ytev4oKB4Kt0lUvQOVehP6nBIZhZmLuTMyPflSGEct6piOuQCNYpC9O2PTfzwRzmiCBnQBPZzqoomdlzWO45VBdz0VnmKfYTDw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=20scTawldTDw1RoBfKZYiGDFVeFLHbxg97nPCvD5mP0=; b=N3z1aUFcfFHxm08iNH2ccB3vNJIp+t6fm9GJtUaq8yUdhp8VVmMDEb0UX4wnW1g6yzFCv5Z3Nks2R61fWqekdQjeJuuA54NiRB9QHwWyKRiDv4JsGbYTwy41u7hunepKNAASuuvUSAAPKh2sDj3G+qskoOTsXrvpOXCOeVNwfooJpzgQzz14mTu5c6K9IR1jwaG0CRX5srvrxOfkMHXWWzskQx3afqQ4KyKqbQyI8cRm42XTpvt3fvdZH9PjK01ETflLxlo0ZESYPOt/OY/t2TO25U0HTZdVIsHO/B0Crc6L7A4ho/Uc2agjIiDe9YYlBCiPUtDPaftcbpcHcnfNOQ== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=arm.com; dmarc=pass action=none header.from=arm.com; dkim=pass header.d=arm.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=armh.onmicrosoft.com; s=selector2-armh-onmicrosoft-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=20scTawldTDw1RoBfKZYiGDFVeFLHbxg97nPCvD5mP0=; b=ITlDw5zfepNaR60qVRazxQN1M1fKp1y3tJiyohg5B0vBCD+9uUA9zr/Z8CF8aJpF1duP9HmhllMfP9Bgv6Sa5mrwu71D4HP0Xv6TNJpQg+7Vc2WhFkoYGHWB6Sm7wYlX8PV/9J0qnYXXEZdnTj2fvfIm7155QZIWYiI3mK7EwdE= Received: from DB6PR0802MB2133.eurprd08.prod.outlook.com (10.172.227.22) by DB6PR0802MB2598.eurprd08.prod.outlook.com (10.172.246.148) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.2073.14; Wed, 17 Jul 2019 08:14:32 +0000 Received: from DB6PR0802MB2133.eurprd08.prod.outlook.com ([fe80::5ce5:cf42:42dd:eda1]) by DB6PR0802MB2133.eurprd08.prod.outlook.com ([fe80::5ce5:cf42:42dd:eda1%6]) with mapi id 15.20.2073.015; Wed, 17 Jul 2019 08:14:32 +0000 From: Alan Hayward To: "gdb-patches@sourceware.org" CC: nd , Alan Hayward Subject: [PATCH] AArch64 pauth: Indicate unmasked addresses in backtrace Date: Wed, 17 Jul 2019 08:14:31 +0000 Message-ID: <20190717081336.68835-1-alan.hayward@arm.com> Authentication-Results-Original: spf=none (sender IP is ) smtp.mailfrom=Alan.Hayward@arm.com; X-Microsoft-Antispam-Untrusted: BCL:0; PCL:0; RULEID:(2390118)(7020095)(4652040)(8989299)(4534185)(4627221)(201703031133081)(201702281549075)(8990200)(5600148)(711020)(4605104)(1401327)(4618075)(2017052603328)(7193020); SRVR:DB6PR0802MB2598; x-checkrecipientrouted: true x-ms-oob-tlc-oobclassifiers: OLM:6108;OLM:6108; X-Forefront-Antispam-Report-Untrusted: SFV:NSPM; SFS:(10009020)(979002)(4636009)(366004)(346002)(39860400002)(376002)(396003)(136003)(189003)(199004)(478600001)(2351001)(316002)(71190400001)(8676002)(71200400001)(14454004)(1076003)(54906003)(4326008)(99286004)(3846002)(6116002)(25786009)(7736002)(305945005)(36756003)(6436002)(66066001)(52116002)(8936002)(5660300002)(81156014)(81166006)(50226002)(66446008)(476003)(66556008)(2501003)(26005)(102836004)(2616005)(64756008)(386003)(486006)(66946007)(44832011)(66476007)(2906002)(6486002)(186003)(68736007)(256004)(14444005)(5640700003)(53936002)(6512007)(6506007)(6916009)(86362001)(969003)(989001)(999001)(1009001)(1019001); DIR:OUT; SFP:1101; SCL:1; SRVR:DB6PR0802MB2598; H:DB6PR0802MB2133.eurprd08.prod.outlook.com; FPR:; SPF:None; LANG:en; PTR:InfoNoRecords; MX:1; A:1; received-spf: None (protection.outlook.com: arm.com does not designate permitted sender hosts) X-MS-Exchange-SenderADCheck: 1 X-Microsoft-Antispam-Message-Info-Original: BIfstftmofpQVwLEz1OeTCnEzcm5uGKblBdex/u0OkELNnMLVwyrJXj/HKjmig5Ago6uNqlNGzgE+XiEYycTt/Vz1fq1TSh2UnY6yJ2FK++gKPG9Dh4g3NfisaBj9Wn+9T8J18MaF+uI/HPShUZC+wlhOyEEouUAXagUAq73XSbeNj1IZRHAgaAxAw90oI7gQ2rVthkv7nUQsCYtE+jr4o90O1uwOQwI2XHK32VGWqqxbVloa9T5zqGiVgnjzGnsQFSxTWZxncj41yK0nHtqesaYfipcL9RsMzkY7/ANVWSSxKjDNgz3K5aA2q0ZqMLf30HOyV9XSxIv5tiPi4ZOF5/MPuFIy/q0Mjgo/jw9awrKunqD15h1ipZjGdBubvleGmE7nSAqxr/mXHWkc0daAOnsuTAkjNbsdLLvBsdaFoY= MIME-Version: 1.0 Original-Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=Alan.Hayward@arm.com; Return-Path: Alan.Hayward@arm.com X-MS-Exchange-Transport-CrossTenantHeadersStripped: AM5EUR03FT023.eop-EUR03.prod.protection.outlook.com X-MS-Office365-Filtering-Correlation-Id-Prvs: 153849c6-f6b3-40e6-fda3-08d70a8ecbd5 X-IsSubscribed: yes Armv8.3-a Pointer Authentication causes the function return address to be obfuscated on entry to some functions. GDB must unmask the link register in order to produce a backtrace. The following patch adds markers of to the bracktrace, to indicate which addresses needed unmasking. For example, consider the following backtrace: (gdb) bt 0 0x0000000000400490 in puts@plt () 1 0x00000000004005dc in foo ("hello") at cbreak-lib.c:6 2 0x0000000000400604 in bar () at cbreak-lib.c:12 3 0x0000000000400620 in barbar () at cbreak.c:17 4 0x00000000004005b4 in main () at cbreak-3.c:10 The functions in the cbreak-lib use pointer auth, obfuscating the return address to the previous function. The caused the addresses of bar and barbar to require unmasking in order to unwind the backtrace. Alternatively, I considered replacing with a single chracter, such as * for brevity reasons, but felt this would be non obvious for the user. An extra bool is added alongside the prev_pc in the frame struture. At the point at which the link register is unmasked, the AArch64 port calls into frame to sets the bool. This seemed the most efficient way of doing it. aarch64_frame_unmask_address is designed to work for any address, however at the momoment it is only used for the link address. An extra default parameter is added to ensure it only caches for the link register. I expect this will potentially cause issues with some tests in the testsuite when Armv8.3 pointer authentication is used. This should be fixed up in the the future once real hardware is available for full testsuite testing. 2019-07-17 Alan Hayward * NEWS: Expand the Pointer Authentication entry. * aarch64-tdep.c (aarch64_frame_unmask_address): Mark frame if unmasking link register. * frame.c (struct frame_info): Add masked variable. (frame_set_previous_pc_masked) (frame_get_pc_masked): New function. * frame.h (frame_set_previous_pc_masked) (frame_get_pc_masked): New declaration. * stack.c (print_frame): Check for masked pc. --- gdb/NEWS | 3 ++- gdb/aarch64-tdep.c | 12 +++++++++--- gdb/frame.c | 17 +++++++++++++++++ gdb/frame.h | 9 +++++++++ gdb/stack.c | 6 +++++- 5 files changed, 42 insertions(+), 5 deletions(-) diff --git a/gdb/NEWS b/gdb/NEWS index 4e479bf738..cea88491bd 100644 --- a/gdb/NEWS +++ b/gdb/NEWS @@ -16,7 +16,8 @@ architectures require kernel changes. TLS is not yet supported for amd64 and i386 process core dumps. -* Support for Pointer Authentication on AArch64 Linux. +* Support for Pointer Authentication on AArch64 Linux. Return addresses that + required unmasking are shown in the backtrace with the postfix . * Two new convenience functions $_cimag and $_creal that extract the imaginary and real parts respectively from complex numbers. diff --git a/gdb/aarch64-tdep.c b/gdb/aarch64-tdep.c index e23cc3f956..eaac7960ec 100644 --- a/gdb/aarch64-tdep.c +++ b/gdb/aarch64-tdep.c @@ -251,12 +251,13 @@ class instruction_reader : public abstract_instruction_reader } // namespace /* If address signing is enabled, mask off the signature bits from ADDR, using - the register values in THIS_FRAME. */ + the register values in THIS_FRAME. IS_LR indicates if ADDR is from the link + register for the current frame. */ static CORE_ADDR aarch64_frame_unmask_address (struct gdbarch_tdep *tdep, - struct frame_info *this_frame, - CORE_ADDR addr) + struct frame_info *this_frame, CORE_ADDR addr, + bool is_lr = true) { if (tdep->has_pauth () && frame_unwind_register_unsigned (this_frame, @@ -265,6 +266,11 @@ aarch64_frame_unmask_address (struct gdbarch_tdep *tdep, int cmask_num = AARCH64_PAUTH_CMASK_REGNUM (tdep->pauth_reg_base); CORE_ADDR cmask = frame_unwind_register_unsigned (this_frame, cmask_num); addr = addr & ~cmask; + + /* If addr was taken from the Link Register, then record this in the + frame. */ + if (is_lr) + frame_set_previous_pc_masked (this_frame); } return addr; diff --git a/gdb/frame.c b/gdb/frame.c index 84e0397db9..b7bb44986e 100644 --- a/gdb/frame.c +++ b/gdb/frame.c @@ -124,6 +124,8 @@ struct frame_info struct { enum cached_copy_status status; CORE_ADDR value; + /* Did VALUE require unmasking when being read. */ + bool masked; } prev_pc; /* Cached copy of the previous frame's function address. */ @@ -161,6 +163,21 @@ struct frame_info const char *stop_string; }; +/* See frame.h. */ + +void +frame_set_previous_pc_masked (struct frame_info *frame) +{ + frame->prev_pc.masked = true; +} + +/* See frame.h. */ + +bool frame_get_pc_masked (struct frame_info *frame) +{ + return frame->next->prev_pc.masked; +} + /* A frame stash used to speed up frame lookups. Create a hash table to stash frames previously accessed from the frame cache for quicker subsequent retrieval. The hash table is emptied whenever diff --git a/gdb/frame.h b/gdb/frame.h index a79eeeeab1..61c12ec0b2 100644 --- a/gdb/frame.h +++ b/gdb/frame.h @@ -930,4 +930,13 @@ extern const gdb::option::option_def set_backtrace_option_defs[2]; /* The values behind the global "set backtrace ..." settings. */ extern set_backtrace_options user_set_backtrace_options; +/* Mark that the PC value is masked for the previous frame. */ + +extern void frame_set_previous_pc_masked (struct frame_info *frame); + +/* Get whether the PC value is masked for the given frame. */ + +extern bool frame_get_pc_masked (struct frame_info *frame); + + #endif /* !defined (FRAME_H) */ diff --git a/gdb/stack.c b/gdb/stack.c index 9b1d1a6856..cef1c29a82 100644 --- a/gdb/stack.c +++ b/gdb/stack.c @@ -1254,7 +1254,11 @@ print_frame (const frame_print_options &fp_opts, { annotate_frame_address (); if (pc_p) - uiout->field_core_addr ("addr", gdbarch, pc); + { + uiout->field_core_addr ("addr", gdbarch, pc); + if (frame_get_pc_masked (frame)) + uiout->text (""); + } else uiout->field_string ("addr", "", ui_out_style_kind::ADDRESS);