Received: by 2002:a05:6902:102b:0:0:0:0 with SMTP id x11csp2258331ybt; Tue, 16 Jun 2020 00:58:17 -0700 (PDT) X-Google-Smtp-Source: ABdhPJwOCEI0TpJGMqZUHBGP8M+gv9Wf+jQ4Y9Wfz5yazNX1zxSlNXNZxGlaTTXDXHIk14R+eYxd X-Received: by 2002:a17:906:4310:: with SMTP id j16mr1508386ejm.511.1592294297560; Tue, 16 Jun 2020 00:58:17 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1592294297; cv=none; d=google.com; s=arc-20160816; b=wBsDgGwRf4265JDDh2aCexlXZnuUZlus8suqvMOPKdfxevdpcMZzwBeNrAwyiyvKVK 1F5RLGGKAgOlim09OGWB6OvLGU1CPD7QN0wunAvRlzU3XcKibYUjy7xmIRnDT/FRyl/v PdB4+cWcTIsG6/92du0GSVT+uJFKYIuLvFhZYY8XjoYN2f/Ot+emzHMnDLt+exo3teRP gWPdTXrnwOSuKtpLbCKH3nZbgnaVYEyq986xO420j5euBc1iiP9Z1v4ryk6zmcYj2Tmj pYYrUIWCTNlKXxiGnlT4EdYDKhVttazO0/GvF9QloEn4tF1xcOAS/7LP85UEZonx89QV QFKA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:references:in-reply-to:message-id:date :subject:cc:to:from:dkim-signature; bh=4qJjSzS3qsc/46vw3CAVyVPzMy5PIT8l5/oTWqdt8oo=; b=Dx7Ut38iTfwMTigAE30cEL0xsihOjbAIoM30pF2SfZhjmd0RGiJzNrjYbP6XTgzjx7 EAzGW/EyzSo73Z4JQGavU9Ki40q7cqfBSlAaRM6tbeYDs2CKSOo4v655VZSNsOZyWayB 4DK1DwLBOvjeZIMBp/4zmcfsMbuky5m9WgaCIFGL+f5XTzKg/r+iaZages6FbUNfgM/H 9QVJMP3L+uxPXzlI+kaFUPNlJe2V9t7mE2ald4weGm/ppv4nP3XuXqGVffTBpeztccag VSab2PRxpGd5hjOI+Ez/WF9KrGK/6vLESf5jF8/K9puVd/bqMfbUkzWxUMdNwgoqtJlK Ca2A== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@gmail.com header.s=20161025 header.b=HVStFhta; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id do11si14554823ejc.450.2020.06.16.00.57.55; Tue, 16 Jun 2020 00:58:17 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) client-ip=23.128.96.18; Authentication-Results: mx.google.com; dkim=pass header.i=@gmail.com header.s=20161025 header.b=HVStFhta; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726773AbgFPH4C (ORCPT + 99 others); Tue, 16 Jun 2020 03:56:02 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:57966 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726405AbgFPHz7 (ORCPT ); Tue, 16 Jun 2020 03:55:59 -0400 Received: from mail-pl1-x641.google.com (mail-pl1-x641.google.com [IPv6:2607:f8b0:4864:20::641]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 35CD6C03E96A for ; Tue, 16 Jun 2020 00:55:59 -0700 (PDT) Received: by mail-pl1-x641.google.com with SMTP id n9so8037246plk.1 for ; Tue, 16 Jun 2020 00:55:59 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=4qJjSzS3qsc/46vw3CAVyVPzMy5PIT8l5/oTWqdt8oo=; b=HVStFhtaoA2oLF72yHWaH/McQnIrOlDwaKg8cD6LXc1gm6z/rS8aECm4aW7xb5L79G SR8v1GrrjvToggZbmD1d9zSXOcnOCLfQXXXa8veQEc9f42hxhzx+iN9S8c7akoRoXVMc 0KX6grxPxdmn9fDmYiHahHxTIMTwBVaxmeiuQ7k4nU95/AiyqpMGGDDShKj7kD3hQ93W bWNIJhfap7tg48tWcNm9oysqFA59xleUGku8kKDhISjmlzTKlcktfup9ZrOPJxO3JN21 Ak+Y4vIL0E0g/3Rsg9W74pZqZa3AEhOqfrEi5FMzfGcFzCm6Pr/9DXTLTsXQg6ipAAoS rRHA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=4qJjSzS3qsc/46vw3CAVyVPzMy5PIT8l5/oTWqdt8oo=; b=ThgZg6geH9++cuDi37eXI/hqL+zxaYuE2+yB/zNiWaTcARNU4xYwGBFn4qdNYj60d3 QtbsI9poJrA7eUGsE1F9wA5BJGDHo+8bPaycRLXqJc8EAKS+soDwvO9w0dSDx0bnIq4B 0+MrudKeIKejesVCtF/lRrVYEuhuPE2xXnFjCKabVVJTLI+8+agUkeLMX8zzqGRQ3iCk P/xnH2cwySB4uSKhgB5PeyMIzH2dm1WGHVNtSViYToN0ANeqjYa4bYPkjpO5jSEyNNK4 oU/RNhpTsjojWNJyUc9gVzOG4TnvvpF1P7pj7mvnnWJiiRlxcbO0mwhNmE2qFK6mWtOA M9YA== X-Gm-Message-State: AOAM530iBFO6Zo9olUExLmZthNKstXBONZaXfybL6d3YbG55GPNh84Kn W4QXLDF+VAxQ/NLjgR/spQQ= X-Received: by 2002:a17:902:7204:: with SMTP id ba4mr1003927plb.250.1592294158483; Tue, 16 Jun 2020 00:55:58 -0700 (PDT) Received: from laptop.hsd1.wa.comcast.net ([2601:600:817f:a132:df3e:521d:99d5:710d]) by smtp.gmail.com with ESMTPSA id g6sm16168984pfb.164.2020.06.16.00.55.57 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 16 Jun 2020 00:55:58 -0700 (PDT) From: Andrei Vagin To: linux-arm-kernel@lists.infradead.org, Catalin Marinas , Will Deacon Cc: linux-kernel@vger.kernel.org, Vincenzo Frascino , Mark Rutland , Thomas Gleixner , Dmitry Safonov , Andrei Vagin Subject: [PATCH 3/6] arm64/vdso: Add time namespace page Date: Tue, 16 Jun 2020 00:55:42 -0700 Message-Id: <20200616075545.312684-4-avagin@gmail.com> X-Mailer: git-send-email 2.17.2 In-Reply-To: <20200616075545.312684-1-avagin@gmail.com> References: <20200616075545.312684-1-avagin@gmail.com> Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Allocate the time namespace page among VVAR pages. Provide __arch_get_timens_vdso_data() helper for VDSO code to get the code-relative position of VVARs on that special page. If a task belongs to a time namespace then the VVAR page which contains the system wide VDSO data is replaced with a namespace specific page which has the same layout as the VVAR page. That page has vdso_data->seq set to 1 to enforce the slow path and vdso_data->clock_mode set to VCLOCK_TIMENS to enforce the time namespace handling path. The extra check in the case that vdso_data->seq is odd, e.g. a concurrent update of the VDSO data is in progress, is not really affecting regular tasks which are not part of a time namespace as the task is spin waiting for the update to finish and vdso_data->seq to become even again. If a time namespace task hits that code path, it invokes the corresponding time getter function which retrieves the real VVAR page, reads host time and then adds the offset for the requested clock which is stored in the special VVAR page. Cc: Mark Rutland Reviewed-by: Vincenzo Frascino Reviewed-by: Dmitry Safonov Signed-off-by: Andrei Vagin --- arch/arm64/include/asm/vdso.h | 2 ++ .../include/asm/vdso/compat_gettimeofday.h | 12 ++++++++++++ arch/arm64/include/asm/vdso/gettimeofday.h | 8 ++++++++ arch/arm64/kernel/vdso.c | 19 ++++++++++++++++--- arch/arm64/kernel/vdso/vdso.lds.S | 5 ++++- arch/arm64/kernel/vdso32/vdso.lds.S | 5 ++++- include/vdso/datapage.h | 1 + 7 files changed, 47 insertions(+), 5 deletions(-) diff --git a/arch/arm64/include/asm/vdso.h b/arch/arm64/include/asm/vdso.h index 07468428fd29..f99dcb94b438 100644 --- a/arch/arm64/include/asm/vdso.h +++ b/arch/arm64/include/asm/vdso.h @@ -12,6 +12,8 @@ */ #define VDSO_LBASE 0x0 +#define __VVAR_PAGES 2 + #ifndef __ASSEMBLY__ #include diff --git a/arch/arm64/include/asm/vdso/compat_gettimeofday.h b/arch/arm64/include/asm/vdso/compat_gettimeofday.h index b6907ae78e53..b7c549d46d18 100644 --- a/arch/arm64/include/asm/vdso/compat_gettimeofday.h +++ b/arch/arm64/include/asm/vdso/compat_gettimeofday.h @@ -152,6 +152,18 @@ static __always_inline const struct vdso_data *__arch_get_vdso_data(void) return ret; } +#ifdef CONFIG_TIME_NS +static __always_inline const struct vdso_data *__arch_get_timens_vdso_data(void) +{ + const struct vdso_data *ret; + + /* See __arch_get_vdso_data(). */ + asm volatile("mov %0, %1" : "=r"(ret) : "r"(_timens_data)); + + return ret; +} +#endif + #endif /* !__ASSEMBLY__ */ #endif /* __ASM_VDSO_GETTIMEOFDAY_H */ diff --git a/arch/arm64/include/asm/vdso/gettimeofday.h b/arch/arm64/include/asm/vdso/gettimeofday.h index afba6ba332f8..cf39eae5eaaf 100644 --- a/arch/arm64/include/asm/vdso/gettimeofday.h +++ b/arch/arm64/include/asm/vdso/gettimeofday.h @@ -96,6 +96,14 @@ const struct vdso_data *__arch_get_vdso_data(void) return _vdso_data; } +#ifdef CONFIG_TIME_NS +static __always_inline +const struct vdso_data *__arch_get_timens_vdso_data(void) +{ + return _timens_data; +} +#endif + #endif /* !__ASSEMBLY__ */ #endif /* __ASM_VDSO_GETTIMEOFDAY_H */ diff --git a/arch/arm64/kernel/vdso.c b/arch/arm64/kernel/vdso.c index df4bb736d28a..14d5b7642b62 100644 --- a/arch/arm64/kernel/vdso.c +++ b/arch/arm64/kernel/vdso.c @@ -40,6 +40,12 @@ enum vdso_abi { #endif /* CONFIG_COMPAT_VDSO */ }; +enum vvar_pages { + VVAR_DATA_PAGE_OFFSET, + VVAR_TIMENS_PAGE_OFFSET, + VVAR_NR_PAGES, +}; + struct vdso_abi_info { const char *name; const char *vdso_code_start; @@ -126,6 +132,11 @@ static int __vdso_init(enum vdso_abi abi) } #ifdef CONFIG_TIME_NS +struct vdso_data *arch_get_vdso_data(void *vvar_page) +{ + return (struct vdso_data *)(vvar_page); +} + /* * The vvar page layout depends on whether a task belongs to the root or * non-root time namespace. Whenever a task changes its namespace, the VVAR @@ -175,9 +186,11 @@ static int __setup_additional_pages(enum vdso_abi abi, unsigned long gp_flags = 0; void *ret; + BUILD_BUG_ON(VVAR_NR_PAGES != __VVAR_PAGES); + vdso_text_len = vdso_info[abi].vdso_pages << PAGE_SHIFT; /* Be sure to map the data page */ - vdso_mapping_len = vdso_text_len + PAGE_SIZE; + vdso_mapping_len = vdso_text_len + VVAR_NR_PAGES * PAGE_SIZE; vdso_base = get_unmapped_area(NULL, 0, vdso_mapping_len, 0, 0); if (IS_ERR_VALUE(vdso_base)) { @@ -185,7 +198,7 @@ static int __setup_additional_pages(enum vdso_abi abi, goto up_fail; } - ret = _install_special_mapping(mm, vdso_base, PAGE_SIZE, + ret = _install_special_mapping(mm, vdso_base, VVAR_NR_PAGES * PAGE_SIZE, VM_READ|VM_MAYREAD|VM_PFNMAP, vdso_info[abi].dm); if (IS_ERR(ret)) @@ -194,7 +207,7 @@ static int __setup_additional_pages(enum vdso_abi abi, if (IS_ENABLED(CONFIG_ARM64_BTI_KERNEL) && system_supports_bti()) gp_flags = VM_ARM64_BTI; - vdso_base += PAGE_SIZE; + vdso_base += VVAR_NR_PAGES * PAGE_SIZE; mm->context.vdso = (void *)vdso_base; ret = _install_special_mapping(mm, vdso_base, vdso_text_len, VM_READ|VM_EXEC|gp_flags| diff --git a/arch/arm64/kernel/vdso/vdso.lds.S b/arch/arm64/kernel/vdso/vdso.lds.S index 7ad2d3a0cd48..d808ad31e01f 100644 --- a/arch/arm64/kernel/vdso/vdso.lds.S +++ b/arch/arm64/kernel/vdso/vdso.lds.S @@ -17,7 +17,10 @@ OUTPUT_ARCH(aarch64) SECTIONS { - PROVIDE(_vdso_data = . - PAGE_SIZE); + PROVIDE(_vdso_data = . - __VVAR_PAGES * PAGE_SIZE); +#ifdef CONFIG_TIME_NS + PROVIDE(_timens_data = _vdso_data + PAGE_SIZE); +#endif . = VDSO_LBASE + SIZEOF_HEADERS; .hash : { *(.hash) } :text diff --git a/arch/arm64/kernel/vdso32/vdso.lds.S b/arch/arm64/kernel/vdso32/vdso.lds.S index a3944927eaeb..06cc60a9630f 100644 --- a/arch/arm64/kernel/vdso32/vdso.lds.S +++ b/arch/arm64/kernel/vdso32/vdso.lds.S @@ -17,7 +17,10 @@ OUTPUT_ARCH(arm) SECTIONS { - PROVIDE_HIDDEN(_vdso_data = . - PAGE_SIZE); + PROVIDE_HIDDEN(_vdso_data = . - __VVAR_PAGES * PAGE_SIZE); +#ifdef CONFIG_TIME_NS + PROVIDE_HIDDEN(_timens_data = _vdso_data + PAGE_SIZE); +#endif . = VDSO_LBASE + SIZEOF_HEADERS; .hash : { *(.hash) } :text diff --git a/include/vdso/datapage.h b/include/vdso/datapage.h index 7955c56d6b3c..ee810cae4e1e 100644 --- a/include/vdso/datapage.h +++ b/include/vdso/datapage.h @@ -109,6 +109,7 @@ struct vdso_data { * relocation, and this is what we need. */ extern struct vdso_data _vdso_data[CS_BASES] __attribute__((visibility("hidden"))); +extern struct vdso_data _timens_data[CS_BASES] __attribute__((visibility("hidden"))); /* * The generic vDSO implementation requires that gettimeofday.h -- 2.24.1