From patchwork Fri Aug 2 19:02:27 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Michael Jeanson X-Patchwork-Id: 1968486 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=efficios.com header.i=@efficios.com header.a=rsa-sha256 header.s=smtpout1 header.b=ZnqOjMsj; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=sourceware.org (client-ip=2620:52:3:1:0:246e:9693:128c; helo=server2.sourceware.org; envelope-from=libc-alpha-bounces~incoming=patchwork.ozlabs.org@sourceware.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [IPv6:2620:52:3:1:0:246e:9693:128c]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4WbFfq4L6Rz1yZl for ; Sat, 3 Aug 2024 05:06:11 +1000 (AEST) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id DCDFD384F02C for ; Fri, 2 Aug 2024 19:06:09 +0000 (GMT) X-Original-To: libc-alpha@sourceware.org Delivered-To: libc-alpha@sourceware.org Received: from smtpout.efficios.com (smtpout.efficios.com [IPv6:2607:5300:203:b2ee::31e5]) by sourceware.org (Postfix) with ESMTPS id C4CF43858428 for ; Fri, 2 Aug 2024 19:03:00 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org C4CF43858428 Authentication-Results: sourceware.org; dmarc=pass (p=none dis=none) header.from=efficios.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=efficios.com ARC-Filter: OpenARC Filter v1.0.0 sourceware.org C4CF43858428 Authentication-Results: server2.sourceware.org; arc=none smtp.remote-ip=2607:5300:203:b2ee::31e5 ARC-Seal: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1722625385; cv=none; b=sVLUMbGDA+LfpRvhQcqWFCShp7/ImNY3mvcu8jC5KRDFLuVQTo+3q5KrJBxjfbQXcfwU+oHsZUboFo2S8wMG2sMjOgbxcQmZzEsucVJxkP+r/lozK3Y24J7mgoZtleH9IgsKpcCviP4HVeCS/mAiT83dcN69m8oHk28MZAx6MB4= ARC-Message-Signature: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1722625385; c=relaxed/simple; bh=9I69ZhxQgSZGk0+qDJvi35BijcyLoLfcB/gboc8B98c=; h=DKIM-Signature:From:To:Subject:Date:Message-Id:MIME-Version; b=FQiYqzdOQQsrZ9beDlXUTH1dw/44mskSnupy8hIf+1bu36hLpB40gBp0f3UBmn6wbbjIfTnknOu0BWIrU6aHtQlgsSKT7FFp+fVVt3/iX/vfdfugsd2hyoicCkOk0aNSLonUGakcPa1lpcaBTxU0Z6sW4ir99U+tjEXqXWZMkXk= ARC-Authentication-Results: i=1; server2.sourceware.org DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=efficios.com; s=smtpout1; t=1722625380; bh=9I69ZhxQgSZGk0+qDJvi35BijcyLoLfcB/gboc8B98c=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ZnqOjMsjy3QRBmXfGF0VMyJT1NAYQCBC9yUduECLZXmul4wt48CG01F1pcvqvouxh YAr1CEvoK0rDNuiGvR4oA5kexbIsH4QcbImbDioxmjqFisBsAlHGoMW00PfmB0lYSY Ds3NIxRm/CZ/XVhPs/IXMG7EOVqfzZVGC9+/MhHGCMF4sIEyMWy9Z8fGSP09DlDP5y SjmGsyW2KDA++Ey15Q1JXZEIWhCNQuG+6ItHCQmwWqziHMq+gDDoMnQ9lFyTAsC1sI OVuuo+XcyYY2DipxxUVaa4AabgasFLVvfBUfP7INvNwt0Se9ptn6RGCRBDqf8QW+w8 sCO2cBESoKp/g== Received: from mj-deb12-aarch64-glibc.internal.efficios.com (192-222-143-198.qc.cable.ebox.net [192.222.143.198]) by smtpout.efficios.com (Postfix) with ESMTPSA id 4WbFb832TRz1Fl3; Fri, 2 Aug 2024 15:03:00 -0400 (EDT) From: Michael Jeanson To: libc-alpha@sourceware.org Cc: Michael Jeanson , Florian Weimer , Carlos O'Donell , DJ Delorie , Mathieu Desnoyers Subject: [PATCH RFC v11 14/17] nptl: Introduce RSEQ_GETMEM_VOLATILE and RSEQ_SETMEM Date: Fri, 2 Aug 2024 15:02:27 -0400 Message-Id: <20240801-rseq-abi-v11-split-v11-14-b7bbc0138bfd@efficios.com> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20240801-rseq-abi-v11-split-v11-0-b7bbc0138bfd@efficios.com> References: <20240801-rseq-abi-v11-split-v11-0-b7bbc0138bfd@efficios.com> MIME-Version: 1.0 X-Spam-Status: No, score=-12.0 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, SPF_HELO_NONE, SPF_PASS, TXREP autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: libc-alpha@sourceware.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Libc-alpha mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: libc-alpha-bounces~incoming=patchwork.ozlabs.org@sourceware.org This will be used to access and write to the rseq area in the extra TLS block. Signed-off-by: Michael Jeanson --- sysdeps/i386/nptl/tcb-access.h | 61 ++++++++++++++++++++++++++++++++++++++++ sysdeps/nptl/tcb-access.h | 5 ++++ sysdeps/x86_64/nptl/tcb-access.h | 61 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 127 insertions(+) diff --git a/sysdeps/i386/nptl/tcb-access.h b/sysdeps/i386/nptl/tcb-access.h index 4b6221e103..eb40906c48 100644 --- a/sysdeps/i386/nptl/tcb-access.h +++ b/sysdeps/i386/nptl/tcb-access.h @@ -123,3 +123,64 @@ "i" (offsetof (struct pthread, member)), \ "r" (idx)); \ }}) + + +#if IS_IN (rtld) +/* Use the hidden symbol in ld.so. */ +# define rseq_offset_sym _rseq_offset +#else +# define rseq_offset_sym __rseq_offset +#endif + +/* Read member of the RSEQ area directly. */ +#define RSEQ_GETMEM_VOLATILE(descr, member) \ + ({ __typeof (descr->member) __value; \ + _Static_assert (sizeof (__value) == 1 \ + || sizeof (__value) == 4 \ + || sizeof (__value) == 8, \ + "size of per-thread data"); \ + if (sizeof (__value) == 1) \ + asm volatile ("movb %%gs:%P2(%3),%b0" \ + : "=q" (__value) \ + : "0" (0), "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else if (sizeof (__value) == 4) \ + asm volatile ("movl %%gs:%P1(%2),%0" \ + : "=r" (__value) \ + : "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else /* 8 */ \ + { \ + asm volatile ("movl %%gs:%P1(%2),%%eax\n\t" \ + "movl %%gs:4+%P1(%2),%%edx" \ + : "=&A" (__value) \ + : "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + } \ + __value; }) + +/* Set member of the RSEQ area directly. */ +#define RSEQ_SETMEM(descr, member, value) \ + ({ \ + _Static_assert (sizeof (descr->member) == 1 \ + || sizeof (descr->member) == 4 \ + || sizeof (descr->member) == 8, \ + "size of per-thread data"); \ + if (sizeof (descr->member) == 1) \ + asm volatile ("movb %b0,%%gs:%P1(%2)" : \ + : "iq" (value), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else if (sizeof (descr->member) == 4) \ + asm volatile ("movl %0,%%gs:%P1(%2)" : \ + : "ir" (value), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else /* 8 */ \ + { \ + asm volatile ("movl %%eax,%%gs:%P1(%2)\n\t" \ + "movl %%edx,%%gs:4+%P1(%2)" : \ + : "A" ((uint64_t) cast_to_integer (value)), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + }}) diff --git a/sysdeps/nptl/tcb-access.h b/sysdeps/nptl/tcb-access.h index 600433766f..9532f30022 100644 --- a/sysdeps/nptl/tcb-access.h +++ b/sysdeps/nptl/tcb-access.h @@ -30,3 +30,8 @@ descr->member = (value) #define THREAD_SETMEM_NC(descr, member, idx, value) \ descr->member[idx] = (value) + +#define RSEQ_GETMEM_VOLATILE(descr, member) \ + THREAD_GETMEM_VOLATILE(descr, member) +#define RSEQ_SETMEM(descr, member, value) \ + THREAD_SETMEM(descr, member, value) diff --git a/sysdeps/x86_64/nptl/tcb-access.h b/sysdeps/x86_64/nptl/tcb-access.h index d35948f111..2edead755e 100644 --- a/sysdeps/x86_64/nptl/tcb-access.h +++ b/sysdeps/x86_64/nptl/tcb-access.h @@ -130,3 +130,64 @@ "i" (offsetof (struct pthread, member[0])), \ "r" (idx)); \ }}) + +#if IS_IN (rtld) +/* Use the hidden symbol in ld.so. */ +# define rseq_offset_sym _rseq_offset +#else +# define rseq_offset_sym __rseq_offset +#endif + +/* Read member of the RSEQ area directly. */ +# define RSEQ_GETMEM_VOLATILE(descr, member) \ + ({ __typeof (descr->member) __value; \ + _Static_assert (sizeof (__value) == 1 \ + || sizeof (__value) == 4 \ + || sizeof (__value) == 8, \ + "size of per-thread data"); \ + if (sizeof (__value) == 1) \ + asm volatile ("movb %%fs:%P2(%q3),%b0" \ + : "=q" (__value) \ + : "0" (0), "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else if (sizeof (__value) == 4) \ + asm volatile ("movl %%fs:%P1(%q2),%0" \ + : "=r" (__value) \ + : "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else /* 8 */ \ + { \ + asm volatile ("movq %%fs:%P1(%q2),%q0" \ + : "=r" (__value) \ + : "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + } \ + __value; }) + +/* Set member of the RSEQ area directly. */ +# define RSEQ_SETMEM(descr, member, value) \ + ({ \ + _Static_assert (sizeof (descr->member) == 1 \ + || sizeof (descr->member) == 4 \ + || sizeof (descr->member) == 8, \ + "size of per-thread data"); \ + if (sizeof (descr->member) == 1) \ + asm volatile ("movb %b0,%%fs:%P1(%q2)" : \ + : "iq" (value), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else if (sizeof (descr->member) == 4) \ + asm volatile ("movl %0,%%fs:%P1(%q2)" : \ + : IMM_MODE (value), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + else /* 8 */ \ + { \ + /* Since movq takes a signed 32-bit immediate or a register source \ + operand, use "er" constraint for 32-bit signed integer constant \ + or register. */ \ + asm volatile ("movq %q0,%%fs:%P1(%q2)" : \ + : "er" ((uint64_t) cast_to_integer (value)), \ + "i" (offsetof (struct rseq_area, member)), \ + "r" (rseq_offset_sym)); \ + }})