Received: by 2002:a05:6a10:5bc5:0:0:0:0 with SMTP id os5csp991220pxb; Tue, 26 Oct 2021 00:20:24 -0700 (PDT) X-Google-Smtp-Source: ABdhPJxSOmGQYW275eCR1WCUkqIS4gHrRN2cLfpgwtesCfJ1k5I5yk9AxXun1aFR3bpPDaypb/YM X-Received: by 2002:a17:90b:2354:: with SMTP id ms20mr3935641pjb.130.1635232824109; Tue, 26 Oct 2021 00:20:24 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1635232824; cv=none; d=google.com; s=arc-20160816; b=iKjOEIgIuzH6A86R+aHeHrvexpJwqozFHtOfJPZlmXB62gdujDdVk1OVUrNmrmL41D wxV/r+49WWrCuCVe3f6mmLbrGQX4bsytziB0NcMeSGL+1J9duZ6J0ckzPZrfjYf16EJu ghamNMvwAbnzzddYdEVqROrNHczHTW8zqOBkCGqE5YhXJpUHhXztT4P3XZLMlPot0iXI 319TD1TT1UWWv1HeUZICQG8gUEnaW28tyU6ICdi6+t3YUxjG4DRisZ2buAZQfhR1k0pv ohQ2TpH0Ikdu/4H73IUNj70gdpG4NkXA/Us4M7zMW8DLSZJhIaNMjmhjdPC0+oiYzMHZ oqRw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:cc:to:subject:message-id:date:from:in-reply-to :references:mime-version; bh=8qVyQe2fJcvVu4rwWNArN64jmUQrjVOWtiM22QUfv30=; b=uKpDt7u/o/9bauz8fjn6Zyza/1rKmsam/Sae3agrMs8RdbkqumRnkE8RFXOj+DDPNx +Rstx/5KydyxxRVHHciaOmaUevE5rT0vAZf9Tla9TLpW2Gp4s7OpbwBY+I7gjV08/4ke i/XN+9IADPtVxU5BA2AJkcQ9xsFIGTKNwengtBewEQNQ2/KqoM/QuM9cLyJ0khHzz/TO 8R6TUDDGHJu9H82XgVVKnJEci6tfBwkRr7s++8mBFpATkU762qxeb2NUYDv90yWulqkJ m9qCF0oDaD0crAjK7U2ptRT0QyXKVJi2JB7+Pe3/UK8XhbfFDCQvcIqIjprv9kyip1Tt YMpQ== ARC-Authentication-Results: i=1; mx.google.com; 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 Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id h7si6031859pfc.89.2021.10.26.00.20.10; Tue, 26 Oct 2021 00:20:24 -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; 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 Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S233706AbhJZGrH (ORCPT + 99 others); Tue, 26 Oct 2021 02:47:07 -0400 Received: from mail-ua1-f49.google.com ([209.85.222.49]:46958 "EHLO mail-ua1-f49.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231378AbhJZGrH (ORCPT ); Tue, 26 Oct 2021 02:47:07 -0400 Received: by mail-ua1-f49.google.com with SMTP id x3so7867884uar.13 for ; Mon, 25 Oct 2021 23:44:43 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:mime-version:references:in-reply-to:from:date :message-id:subject:to:cc; bh=8qVyQe2fJcvVu4rwWNArN64jmUQrjVOWtiM22QUfv30=; b=lCL0uQP4RkcnSLzYxRRiHl6wqeiB7e2MlUY5c13pnnCUZ3fyyu/P434OKHda9z3Tgq lQp0cykSinNfR7jDvUH3PD6Tp3UWoDI3IWaTTehI4NolxnVnz//wmlKU5pWc/3nFfJEP NqbKJkq6nrn7apxgIs5FGeX21iKhon5CzrwZ+FbXd0m4KnW4L9voDE9uIZAeGS09xmZv Nk8RRXy3B7w/3XJDY6tMxVs5+Ica38/W4RXSrBkB895BKXcPA5ynAgDKKuT6qHm7kZYR RCCV5DITR4ttGCS8U5a4sy63O5XQAJOtqEJ0aTS4B5ZjYX8Rl18a5gxeOQSJMolKei2Z HJNA== X-Gm-Message-State: AOAM530MeYHl0AuWFvJzs5n4NZO0tYRfmYFiKwgEtAtXFjxUi7LWLBqN UU2SwMZDfw2Kx8YjCPhFqUGsQ65pcMbvZQ== X-Received: by 2002:ab0:344e:: with SMTP id a14mr20767729uaq.63.1635230683300; Mon, 25 Oct 2021 23:44:43 -0700 (PDT) Received: from mail-ua1-f45.google.com (mail-ua1-f45.google.com. [209.85.222.45]) by smtp.gmail.com with ESMTPSA id m186sm4177340vsm.11.2021.10.25.23.44.42 for (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Mon, 25 Oct 2021 23:44:43 -0700 (PDT) Received: by mail-ua1-f45.google.com with SMTP id e5so20029263uam.11 for ; Mon, 25 Oct 2021 23:44:42 -0700 (PDT) X-Received: by 2002:a67:cb0a:: with SMTP id b10mr21049182vsl.9.1635230682605; Mon, 25 Oct 2021 23:44:42 -0700 (PDT) MIME-Version: 1.0 References: <830eda64-6e66-c61b-ceaa-57be87783b2c@w6rz.net> In-Reply-To: <830eda64-6e66-c61b-ceaa-57be87783b2c@w6rz.net> From: Geert Uytterhoeven Date: Tue, 26 Oct 2021 08:44:31 +0200 X-Gmail-Original-Message-ID: Message-ID: Subject: Re: Out-of-bounds access when hartid >= NR_CPUS To: re@w6rz.net Cc: Paul Walmsley , Palmer Dabbelt , Albert Ou , linux-riscv , Linux Kernel Mailing List Content-Type: text/plain; charset="UTF-8" Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Tue, Oct 26, 2021 at 2:37 AM Ron Economos wrote: > On 10/25/21 8:54 AM, Geert Uytterhoeven wrote: > > When booting a kernel with CONFIG_NR_CPUS=4 on Microchip PolarFire, > > the 4th CPU either fails to come online, or the system crashes. > > > > This happens because PolarFire has 5 CPU cores: hart 0 is an e51, > > and harts 1-4 are u54s, with the latter becoming CPUs 0-3 in Linux: > > - unused core has hartid 0 (sifive,e51), > > - processor 0 has hartid 1 (sifive,u74-mc), > > - processor 1 has hartid 2 (sifive,u74-mc), > > - processor 2 has hartid 3 (sifive,u74-mc), > > - processor 3 has hartid 4 (sifive,u74-mc). > > > > I assume the same issue is present on the SiFive fu540 and fu740 > > SoCs, but I don't have access to these. The issue is not present > > on StarFive JH7100, as processor 0 has hartid 1, and processor 1 has > > hartid 0. > > > > arch/riscv/kernel/cpu_ops.c has: > > > > void *__cpu_up_stack_pointer[NR_CPUS] __section(".data"); > > void *__cpu_up_task_pointer[NR_CPUS] __section(".data"); > > > > void cpu_update_secondary_bootdata(unsigned int cpuid, > > struct task_struct *tidle) > > { > > int hartid = cpuid_to_hartid_map(cpuid); > > > > /* Make sure tidle is updated */ > > smp_mb(); > > WRITE_ONCE(__cpu_up_stack_pointer[hartid], > > task_stack_page(tidle) + THREAD_SIZE); > > WRITE_ONCE(__cpu_up_task_pointer[hartid], tidle); > > > > The above two writes cause out-of-bound accesses beyond > > __cpu_up_{stack,pointer}_pointer[] if hartid >= CONFIG_NR_CPUS. > > > > } > > > > arch/riscv/kernel/smpboot.c:setup_smp(void) detects CPUs like this: > > > > for_each_of_cpu_node(dn) { > > hart = riscv_of_processor_hartid(dn); > > if (hart < 0) > > continue; > > > > if (hart == cpuid_to_hartid_map(0)) { > > BUG_ON(found_boot_cpu); > > found_boot_cpu = 1; > > early_map_cpu_to_node(0, of_node_to_nid(dn)); > > continue; > > } > > if (cpuid >= NR_CPUS) { > > pr_warn("Invalid cpuid [%d] for hartid [%d]\n", > > cpuid, hart); > > break; > > } > > > > cpuid_to_hartid_map(cpuid) = hart; > > early_map_cpu_to_node(cpuid, of_node_to_nid(dn)); > > cpuid++; > > } > > > > So cpuid >= CONFIG_NR_CPUS (too many CPU cores) is already rejected. > > > > How to fix this? > > > > We could skip hartids >= NR_CPUS, but that feels strange to me, as > > you need NR_CPUS to be larger (much larger if the first usable hartid > > is a large number) than the number of CPUs used. > The Ubuntu distro config for HiFive Unmatched set this to CONFIG_NR_CPUS=8. I know. Same for most defconfigs in Linux. But we do not tend to work around buffer overflows by changing config values. Besides, those configs will still experience the issue when run on e.g. an 8+1 core processor where the cores used by Linux have hartids 1-8. I noticed because I started with a starlight config with CONFIG_NR_CPUS=2 (which gave me only one core), changed that to CONFIG_NR_CPUS=4, and got a kernel that didn't boot at all (no output without earlycon).I know. Same for most defconfigs in Linux. But we do not tend to work around buffer overflows by changing config values. Besides, those configs will still experience the issue when run on e.g. an 8+1 core processor where the cores used by Linux have hartids 1-8. > > We could store the minimum hartid, and always subtract that when > > accessing __cpu_up_{stack,pointer}_pointer[] (also in > > arch/riscv/kernel/head.S), but that means unused cores cannot be in the > > middle of the hartid range. > > > > Are hartids guaranteed to be continuous? If not, we have no choice but > > to index __cpu_up_{stack,pointer}_pointer[] by cpuid instead, which > > needs a more expensive conversion in arch/riscv/kernel/head.S. https://riscv.org/wp-content/uploads/2017/05/riscv-privileged-v1.10.pdf says: Hart IDs might not necessarily be numbered contiguously in a multiprocessor system, but at least one hart must have a hart ID of zero. Which means indexing arrays by hart ID is a no-go? Gr{oetje,eeting}s, Geert -- Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert@linux-m68k.org In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that. -- Linus Torvalds