Received: by 2002:a05:6358:d09b:b0:dc:cd0c:909e with SMTP id jc27csp4917194rwb; Sun, 4 Dec 2022 10:29:48 -0800 (PST) X-Google-Smtp-Source: AA0mqf7KF3oYv9Ot/51/r1PzSUcG+lkD7ybjWZ4B99nqsoHlPwns34YBjRyIBDrJ8qMPVl2ZnUqa X-Received: by 2002:a17:906:a157:b0:7a5:7e25:5b11 with SMTP id bu23-20020a170906a15700b007a57e255b11mr1271255ejb.254.1670178588542; Sun, 04 Dec 2022 10:29:48 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1670178588; cv=none; d=google.com; s=arc-20160816; b=PlXiZXg8NYnQ5lU8vzEI4pRWp11iUWFQ+JYeB+13Cr/4rTRjTs5K4X31/ywBluOnUt M3UkiUs/nna590aeZQHIJHVARSGFqPKoieryzZCUuaYOiN5YchHItL7vmZKRvnftRHuE eQkqhH2p5aDsaRoI7iC7wYeqYnf3pt5/sOZt34ZKJKYY2ATdvmk7ql0xNR9Jo4EkwJfp bjspLLMc60JM923GQ3vsMQyHazXfn8u97TkyMk9BNhrzjV18EntwXB+liwHsuUHT3xFY GRJY8dlncoTtdI4nSf95Iw6+cBDNQdfNhUCkjTA5RgLGZMuXMsI8yXUFBBS0+XK0vFRw EC0A== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:user-agent:in-reply-to:content-disposition :mime-version:references:message-id:subject:cc:to:from:date :dkim-signature; bh=y7n0hCnLGy1zh+SrdpqxlWp8vDHcKpVOgMWTyUVHEaQ=; b=E0+SGEjTM4cYkNKll86Z4msqXyZEOFTgOAzpqucs3csNVEiz0k8Ah9z9PxINZcjErj 3Uxj882lVeZHOmobv5QZOBa25gL0LD5mTEVuaMpI7sJ6w688/xIaeo9VOa9H4DLnFZ1/ Oe1zIc6L9yAYNIlnLhNzepieAJSXNZtLKmMrR6T1pW3JQFrvH+oeyzf6fNuWb5f58ukl F/2WvOJIlQ5JiX0iWtjGUVYiMhHCRLxG0yoKgh+wskM1ElhmjzkzIxUe2Swnq/2jDa6n Jnf4YMsqYd7FReQCNpU7KEF+TBC7qDQCRwW6ttycauXOaHVl3Z9UudEu7piVWvyVGVxz KcBw== ARC-Authentication-Results: i=1; mx.google.com; dkim=fail header.i=@treblig.org header.s=bytemarkmx header.b=A0wRDCpB; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id y3-20020a50eb83000000b00461f9648c7dsi2186158edr.422.2022.12.04.10.29.26; Sun, 04 Dec 2022 10:29:48 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=fail header.i=@treblig.org header.s=bytemarkmx header.b=A0wRDCpB; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230184AbiLDSFc (ORCPT + 84 others); Sun, 4 Dec 2022 13:05:32 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:51806 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S230042AbiLDSFa (ORCPT ); Sun, 4 Dec 2022 13:05:30 -0500 Received: from mx.treblig.org (mx.treblig.org [46.43.15.161]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 63733DECF; Sun, 4 Dec 2022 10:05:29 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=treblig.org ; s=bytemarkmx; h=In-Reply-To:Content-Type:MIME-Version:References:Message-ID :Subject:Cc:To:From:Date:Sender:Reply-To:Content-Transfer-Encoding:Content-ID :Content-Description:Resent-Date:Resent-From:Resent-Sender:Resent-To: Resent-Cc:Resent-Message-ID:List-Id:List-Help:List-Unsubscribe:List-Subscribe :List-Post:List-Owner:List-Archive; bh=y7n0hCnLGy1zh+SrdpqxlWp8vDHcKpVOgMWTyUVHEaQ=; b=A0wRDCpBFBt2mvSCaPYoSuQcDN f4aaXk7mu1f+GHWPClZ9jdgaDwmwCuXkI1ApIeFXaEbPbPK/GZZLJ/Y5BOqixCD5OtV3pk4wM1WbN MjLtH98IEOFFlw43yueO0Df4gFwGrQ1PmS2tBNobhLGAiwNViNJqKptN1OWXiwoFI+sk97L681aP9 lUEaQ9RyUF1mulgo3Mcmip8YPYu4jC7Irq/q/QTbIn9i7rb6hFueWUZpUv4aDn5GMxaKV55QWgS5X WhvGUoE9ktjMC5IENU0wefbFz5v9pM1jXBjUWukP+gzsHtKY5wkJ3PAtzg9K2WYjNmK42mgwGBn47 KPOxGklg==; Received: from dg by mx.treblig.org with local (Exim 4.94.2) (envelope-from ) id 1p1tMf-00534x-B2; Sun, 04 Dec 2022 18:05:21 +0000 Date: Sun, 4 Dec 2022 18:05:21 +0000 From: "Dr. David Alan Gilbert" To: Wedson Almeida Filho Cc: ojeda@kernel.org, Alex Gaynor , Boqun Feng , Gary Guo , =?iso-8859-1?Q?Bj=F6rn?= Roy Baron , rust-for-linux@vger.kernel.org, linux-kernel@vger.kernel.org, patches@lists.linux.dev, Adam Bratschi-Kaye Subject: Re: [PATCH v2 20/28] rust: str: add `Formatter` type Message-ID: References: <20221202161502.385525-1-ojeda@kernel.org> <20221202161502.385525-21-ojeda@kernel.org> MIME-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Disposition: inline In-Reply-To: X-Chocolate: 70 percent or better cocoa solids preferably X-Operating-System: Linux/5.10.0-12-amd64 (x86_64) X-Uptime: 17:58:55 up 268 days, 4:24, 1 user, load average: 0.18, 0.09, 0.03 User-Agent: Mutt/2.0.5 (2021-01-21) X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,SPF_HELO_NONE,SPF_PASS autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org * Wedson Almeida Filho (wedsonaf@gmail.com) wrote: > On Sun, 4 Dec 2022 at 15:41, Dr. David Alan Gilbert wrote: > > > > * ojeda@kernel.org (ojeda@kernel.org) wrote: > > > From: Wedson Almeida Filho > > > > > > Add the `Formatter` type, which leverages `RawFormatter`, > > > but fails if callers attempt to write more than will fit > > > in the buffer. > > > > > > In order to so, implement the `RawFormatter::from_buffer()` > > > constructor as well. > > > > > > Co-developed-by: Adam Bratschi-Kaye > > > Signed-off-by: Adam Bratschi-Kaye > > > Signed-off-by: Wedson Almeida Filho > > > Reviewed-by: Gary Guo > > > [Reworded, adapted for upstream and applied latest changes] > > > Signed-off-by: Miguel Ojeda > > > --- > > > rust/kernel/str.rs | 57 ++++++++++++++++++++++++++++++++++++++++++++++ > > > 1 file changed, 57 insertions(+) > > > > > > diff --git a/rust/kernel/str.rs b/rust/kernel/str.rs > > > index a995db36486f..ce207d1b3d2a 100644 > > > --- a/rust/kernel/str.rs > > > +++ b/rust/kernel/str.rs > > > @@ -406,6 +406,23 @@ impl RawFormatter { > > > } > > > } > > > > > > + /// Creates a new instance of [`RawFormatter`] with the given buffer. > > > + /// > > > + /// # Safety > > > + /// > > > + /// The memory region starting at `buf` and extending for `len` bytes must be valid for writes > > > + /// for the lifetime of the returned [`RawFormatter`]. > > > + pub(crate) unsafe fn from_buffer(buf: *mut u8, len: usize) -> Self { > > > + let pos = buf as usize; > > > + // INVARIANT: We ensure that `end` is never less then `buf`, and the safety requirements > > > + // guarantees that the memory region is valid for writes. > > > + Self { > > > + pos, > > > + beg: pos, > > > + end: pos.saturating_add(len), > > > + } > > > + } > > > + > > > /// Returns the current insert position. > > > /// > > > /// N.B. It may point to invalid memory. > > > @@ -439,3 +456,43 @@ impl fmt::Write for RawFormatter { > > > Ok(()) > > > } > > > } > > > + > > > +/// Allows formatting of [`fmt::Arguments`] into a raw buffer. > > > +/// > > > +/// Fails if callers attempt to write more than will fit in the buffer. > > > +pub(crate) struct Formatter(RawFormatter); > > Here we mention that `Formatter` fails if callers attempt to write > more than will fit in the buffer. > > This is in contrast with `RawFormatter`, which doesn't fail in such > cases. There's also a comment there explaining it (not visible in this > patch because it's already there), but I reproduce below: > > /// Allows formatting of [`fmt::Arguments`] into a raw buffer. > /// > /// It does not fail if callers write past the end of the buffer so > that they can calculate the > /// size required to fit everything. > /// > /// # Invariants > /// > /// The memory region between `pos` (inclusive) and `end` (exclusive) > is valid for writes if `pos` > /// is less than `end`. > pub(crate) struct RawFormatter { > > `RawFormatter` is used to implement the "%pA" printf specifier, which > requires this behaviour. > > > > + > > > +impl Formatter { > > > + /// Creates a new instance of [`Formatter`] with the given buffer. > > > + /// > > > + /// # Safety > > > + /// > > > + /// The memory region starting at `buf` and extending for `len` bytes must be valid for writes > > > + /// for the lifetime of the returned [`Formatter`]. > > > + #[allow(dead_code)] > > > + pub(crate) unsafe fn from_buffer(buf: *mut u8, len: usize) -> Self { > > > + // SAFETY: The safety requirements of this function satisfy those of the callee. > > > + Self(unsafe { RawFormatter::from_buffer(buf, len) }) > > > + } > > > +} > > > + > > > +impl Deref for Formatter { > > > + type Target = RawFormatter; > > > + > > > + fn deref(&self) -> &Self::Target { > > > + &self.0 > > > + } > > > +} > > > + > > > +impl fmt::Write for Formatter { > > > + fn write_str(&mut self, s: &str) -> fmt::Result { > > > + self.0.write_str(s)?; > > > + > > > + // Fail the request if we go past the end of the buffer. > > > > Reading this for the first time, I'm surprised by this, perhaps a > > bit more comment is needed? I was expecting that nothing would > > let pos pass end. > > Given the comments I highlight above, do you think we still need more? > > (My impression is that you're reading this without the context I tried > to explain above, and this context may perhaps be sufficient.) Thanks for the pointer; I guess I find it trickier when I can't see the type in self.0 to immediately see it's RawFormatter, and 'Raw' is abstract enough to need to go hunt to see it's behaviour. With that context, I wouldn't object to what's there, but how about something like: // RawFormatter (self.0) still updates pos if the buffer // is too small, but doesn't fail - we want to fail the request. Dave > Thanks, > -Wedson -- -----Open up your eyes, open up your mind, open up your code ------- / Dr. David Alan Gilbert | Running GNU/Linux | Happy \ \ dave @ treblig.org | | In Hex / \ _________________________|_____ http://www.treblig.org |_______/