Received: by 2002:a05:7412:31a9:b0:e2:908c:2ebd with SMTP id et41csp3270024rdb; Wed, 13 Sep 2023 07:18:23 -0700 (PDT) X-Google-Smtp-Source: AGHT+IHaWNZHzFjoGfYGblxWTwDoQJfYJImU35YGh5vkZvBY+b9nrfRVg5b4n8Mu10t9C2uKAH7o X-Received: by 2002:a17:902:e74c:b0:1b8:8702:1e7c with SMTP id p12-20020a170902e74c00b001b887021e7cmr7390928plf.33.1694614703307; Wed, 13 Sep 2023 07:18:23 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1694614703; cv=none; d=google.com; s=arc-20160816; b=uvZuL1RY+LGX6OT7qFj+WIESgqJz5PvKHquBktIBN4tZGqQ2JV+vwVGxDCulnaWpEF VpjzqyeydmAY9H8u0JjPf6kpJZeT1kyR7kAYRHY19wU7hz+KQuoKdMxawFjTpMPFrnZE bgXQKYaOB73DVSHNk8qBVpRwtAEzwKLXB21lhWTDQWZvblRorYHVeUMp4A8UnIeW2TmO Yu7G03RQPJN+oB9ywMSNyIqE1DD0GeXKE0OdCPuoF4Z6dEzqaWu/tC+zSd+f4fmsGsyS gQO/HLZ9K1VNoyzVCNqK2Yh6Jm5sGd87PAJVBxaQ/JjThu9Dib9eHK+CExYkTpFliNEo TDXQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:mime-version:references:message-id:in-reply-to :subject:cc:to:from:date:dkim-signature; bh=amC0mEPfIpFvxI4FqNd6nuzQjjYXozYM6Q1rYkJpl2c=; fh=vzs4DM2mWD8PfpMGlWsS6C5YnjZxZOklMqe3c3BEG2k=; b=rVWx+vM+y/Z6Q4dSKYAFxnF4w14SqJfmDUu22TwHOiyxfA5AJCrzOuhMKIanKShQfo ezCJYHkcfMU21+Tdo4AhUulFEO90K715DQ37A268FGHbZXdkJohu/I26jb8jcz2Uy4XN UhqBpeQKfbhcWKd4hxa2OKvbWWi7vaizoGGu1lHXUsiOCwxL6e8bWclTxvWRfgiylUR7 fnraAKoNW3Ucxh8CWmIchPvzorBM1VNyAdlkxjhY/vRDRPW7HmErqG02ApqGWe+UFiCq 8E4VeRUMZcf3eJecZB/ckkxmtfu33yoW5WXigbc55IJySgBU3W7HjR8MfMYw3Izc9huc Hs7g== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b="BLiT/Ked"; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.34 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Return-Path: Received: from howler.vger.email (howler.vger.email. [23.128.96.34]) by mx.google.com with ESMTPS id r9-20020a170902be0900b001b9d9b01303si3702532pls.628.2023.09.13.07.18.22 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 13 Sep 2023 07:18:23 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.34 as permitted sender) client-ip=23.128.96.34; Authentication-Results: mx.google.com; dkim=pass header.i=@intel.com header.s=Intel header.b="BLiT/Ked"; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.34 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=intel.com Received: from out1.vger.email (depot.vger.email [IPv6:2620:137:e000::3:0]) by howler.vger.email (Postfix) with ESMTP id 4239083F0296; Tue, 12 Sep 2023 05:24:21 -0700 (PDT) X-Virus-Status: Clean X-Virus-Scanned: clamav-milter 0.103.10 at howler.vger.email Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S235102AbjILMYT (ORCPT + 99 others); Tue, 12 Sep 2023 08:24:19 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:58780 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S234663AbjILMYR (ORCPT ); Tue, 12 Sep 2023 08:24:17 -0400 Received: from mgamail.intel.com (mgamail.intel.com [192.55.52.93]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 4EBC110D3; Tue, 12 Sep 2023 05:24:13 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1694521453; x=1726057453; h=date:from:to:cc:subject:in-reply-to:message-id: references:mime-version; bh=PZ3ZOuKlWKIA/NPSNRLsnK9MoIK3kPL++X5vnjv5+to=; b=BLiT/KedA0TikHrxWSml/z9/H4qcRU6OG0hWgd1VkdJ/DNaRBj0WcdRL igI1SC1J7y9me1HyuSPzUWnMcjCECI7sCyfygwwc0VfuNZxp7iOsmi68x e+ZsLEXyAnNkILR9ZnJlnQkP3ES668N+q3bVn7PgU3Bd1e5UuaEGlJMpu TzDBCXgA510oA9B0vqDwof7Pkzi5Tkud9RjRFZlLwtGxjK9eTpskYU2rB 6OAOeVptgc+h6KrrUhMoT6mOKGuoy9hy1KDkzrAsdCVXPbig1bsZ+WzAp fJOKugUQBvxro3XaP6+pM3NLoD2SSL5yKiHrt9jh1oeWpcIfaV+IqFT4M g==; X-IronPort-AV: E=McAfee;i="6600,9927,10830"; a="375688311" X-IronPort-AV: E=Sophos;i="6.02,139,1688454000"; d="scan'208";a="375688311" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga102.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 12 Sep 2023 05:24:10 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=McAfee;i="6600,9927,10830"; a="778772987" X-IronPort-AV: E=Sophos;i="6.02,139,1688454000"; d="scan'208";a="778772987" Received: from npejicx-mobl.ger.corp.intel.com ([10.251.217.90]) by orsmga001-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 12 Sep 2023 05:24:06 -0700 Date: Tue, 12 Sep 2023 15:24:04 +0300 (EEST) From: =?ISO-8859-15?Q?Ilpo_J=E4rvinen?= To: Tony Lindgren cc: Greg Kroah-Hartman , Jiri Slaby , Andy Shevchenko , Dhruva Gole , John Ogness , Johan Hovold , Sebastian Andrzej Siewior , Vignesh Raghavendra , LKML , linux-serial Subject: Re: [PATCH v2 2/3] serial: core: Add support for DEVNAME:0.0 style naming for kernel console In-Reply-To: <20230912110350.14482-3-tony@atomide.com> Message-ID: References: <20230912110350.14482-1-tony@atomide.com> <20230912110350.14482-3-tony@atomide.com> MIME-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org X-Greylist: Sender passed SPF test, not delayed by milter-greylist-4.6.4 (howler.vger.email [0.0.0.0]); Tue, 12 Sep 2023 05:24:21 -0700 (PDT) On Tue, 12 Sep 2023, Tony Lindgren wrote: > We can now add hardware based addressing to serial ports. Starting with > commit 84a9582fd203 ("serial: core: Start managing serial controllers to > enable runtime PM"), and all the related fixes to this commit, the serial > core now knows to which serial port controller the ports are connected. > > The serial ports can be addressed with DEVNAME:0.0 style naming. The names > are something like 00:04:0.0 for a serial port on qemu, and something like > 2800000.serial:0.0 on platform device using systems like ARM64 for example. > > The DEVNAME is the unique serial port hardware controller device name, AKA > the name for port->dev. The 0.0 are the serial core controller id and port > id. > > Typically 0.0 are used for each controller and port instance unless the > serial port hardware controller has multiple controllers or ports. > > Using DEVNAME:0.0 style naming actually solves two long term issues for > addressing the serial ports: > > 1. According to Andy Shevchenko, using DEVNAME:0.0 style naming fixes an > issue where depending on the BIOS settings, the kernel serial port ttyS > instance number may change if HSUART is enabled > > 2. Device tree using architectures no longer necessarily need to specify > aliases to find a specific serial port, and we can just allocate the > ttyS instance numbers dynamically in whatever probe order > > To do this, we need a custom init time parser for the console= command > line option as printk already handles parsing it with console_setup(). > Also early_param() gets handled by console_setup() if "console" and > "earlycon" are used. > > Signed-off-by: Tony Lindgren > --- > drivers/tty/serial/Makefile | 3 + > drivers/tty/serial/serial_base.h | 11 +++ > drivers/tty/serial/serial_base_con.c | 133 +++++++++++++++++++++++++++ > drivers/tty/serial/serial_core.c | 4 + > 4 files changed, 151 insertions(+) > create mode 100644 drivers/tty/serial/serial_base_con.c > > diff --git a/drivers/tty/serial/Makefile b/drivers/tty/serial/Makefile > --- a/drivers/tty/serial/Makefile > +++ b/drivers/tty/serial/Makefile > @@ -3,6 +3,9 @@ > # Makefile for the kernel serial device drivers. > # > > +# Parse kernel command line consoles before the serial drivers probe > +obj-$(CONFIG_SERIAL_CORE_CONSOLE) += serial_base_con.o > + > obj-$(CONFIG_SERIAL_CORE) += serial_base.o > serial_base-y := serial_core.o serial_base_bus.o serial_ctrl.o serial_port.o > > diff --git a/drivers/tty/serial/serial_base.h b/drivers/tty/serial/serial_base.h > --- a/drivers/tty/serial/serial_base.h > +++ b/drivers/tty/serial/serial_base.h > @@ -45,3 +45,14 @@ void serial_ctrl_unregister_port(struct uart_driver *drv, struct uart_port *port > > int serial_core_register_port(struct uart_driver *drv, struct uart_port *port); > void serial_core_unregister_port(struct uart_driver *drv, struct uart_port *port); > + > +#ifdef CONFIG_SERIAL_CORE_CONSOLE > +int serial_base_add_preferred_console(struct uart_driver *drv, > + struct uart_port *port); > +#else > +static inline int serial_base_add_preferred_console(struct uart_driver *drv, > + struct uart_port *port) > +{ > + return 0; > +} > +#endif > diff --git a/drivers/tty/serial/serial_base_con.c b/drivers/tty/serial/serial_base_con.c > new file mode 100644 > --- /dev/null > +++ b/drivers/tty/serial/serial_base_con.c > @@ -0,0 +1,133 @@ > +// SPDX-License-Identifier: GPL-2.0+ > +/* > + * Serial base console options handling > + * > + * Copyright (C) 2023 Texas Instruments Incorporated - https://www.ti.com/ > + * Author: Tony Lindgren > + */ > + > +#include > +#include > +#include > +#include > +#include > + > +#include "serial_base.h" > + > +static LIST_HEAD(serial_base_consoles); > + > +struct serial_base_console { > + struct list_head node; > + char *name; Can't this be const char as too? -- i. > + char *opt; > +}; > + > +/* > + * Adds a preferred console for a serial port if console=DEVNAME:0.0 > + * style addressing is used for the kernel command line. Translates > + * from DEVNAME:0.0 to port->dev_name such as ttyS. Duplicates are > + * ignored by add_preferred_console(). > + */ > +int serial_base_add_preferred_console(struct uart_driver *drv, > + struct uart_port *port) > +{ > + struct serial_base_console *entry; > + char *port_match; > + > + port_match = kasprintf(GFP_KERNEL, "%s:%i.%i", dev_name(port->dev), > + port->ctrl_id, port->port_id); > + if (!port_match) > + return -ENOMEM; > + > + list_for_each_entry(entry, &serial_base_consoles, node) { > + if (!strcmp(port_match, entry->name)) { > + add_preferred_console(drv->dev_name, port->line, > + entry->opt); > + break; > + } > + } > + > + kfree(port_match); > + > + return 0; > +} > +EXPORT_SYMBOL_GPL(serial_base_add_preferred_console); > + > +/* Adds a command line console to the list of consoles for driver probe time */ > +static int __init serial_base_add_con(char *name, char *opt) > +{ > + struct serial_base_console *con; > + > + con = kzalloc(sizeof(*con), GFP_KERNEL); > + if (!con) > + return -ENOMEM; > + > + con->name = kstrdup(name, GFP_KERNEL); > + if (!con->name) > + goto free_con; > + > + if (opt) { > + con->opt = kstrdup(opt, GFP_KERNEL); > + if (!con->name) > + goto free_name; > + } > + > + list_add_tail(&con->node, &serial_base_consoles); > + > + return 0; > + > +free_name: > + kfree(con->name); > + > +free_con: > + kfree(con); > + > + return -ENOMEM; > +} > + > +/* Parse console name and options */ > +static int __init serial_base_parse_one(char *param, char *val, > + const char *unused, void *arg) > +{ > + char *opt; > + > + if (strcmp(param, "console")) > + return 0; > + > + if (!val) > + return 0; > + > + opt = strchr(val, ','); > + if (opt) { > + opt[0] = '\0'; > + opt++; > + } > + > + if (!strlen(val)) > + return 0; > + > + return serial_base_add_con(val, opt); > +} > + > +/* > + * The "console=" option is handled by console_setup() in printk. We can't use > + * early_param() as do_early_param() checks for "console" and "earlycon" options > + * so console_setup() potentially handles console also early. Use parse_args(). > + */ > +static int __init serial_base_opts_init(void) > +{ > + char *command_line; > + > + command_line = kstrdup(boot_command_line, GFP_KERNEL); > + if (!command_line) > + return -ENOMEM; > + > + parse_args("Setting serial core console", command_line, > + NULL, 0, -1, -1, NULL, serial_base_parse_one); > + > + kfree(command_line); > + > + return 0; > +} > + > +arch_initcall(serial_base_opts_init); > diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c > --- a/drivers/tty/serial/serial_core.c > +++ b/drivers/tty/serial/serial_core.c > @@ -3358,6 +3358,10 @@ int serial_core_register_port(struct uart_driver *drv, struct uart_port *port) > if (ret) > goto err_unregister_ctrl_dev; > > + ret = serial_base_add_preferred_console(drv, port); > + if (ret) > + goto err_unregister_port_dev; > + > ret = serial_core_add_one_port(drv, port); > if (ret) > goto err_unregister_port_dev; >