public inbox for passt-dev@passt.top
 help / color / mirror / code / Atom feed
From: Andrea Bolognani <abologna@redhat.com>
To: passt-dev@passt.top
Subject: [PATCH 4/5] qrap: Introduce machine-specific PCI address base
Date: Fri, 24 Feb 2023 19:49:48 +0100	[thread overview]
Message-ID: <20230224184949.518615-5-abologna@redhat.com> (raw)
In-Reply-To: <20230224184949.518615-1-abologna@redhat.com>

For pc machines, devices are placed directly on pci.0 with
addresses like

  bus=pci.0,addr=0xa

and in this case the existing code works correctly.

For q35 machines, however, a separate PCI bus is created for
each devices using a pcie-root-port, and the resulting
addresses look like

  bus=pci.9,addr=0x0

In this case, we need to treat PCI addresses as decimal, not
hexadecimal, both when parsing and generating them.

This issue has gone unnoticed for a long time because it only
shows up when enough PCI devices are present: for small
numbers, decimal and hexadecimal overlap, masking the issue.

Reported-by: Alona Paz <alkaplan@redhat.com>
Fixes: 5307faa05997 ("qrap: Strip network devices from command line, set them up according to machine")
Signed-off-by: Andrea Bolognani <abologna@redhat.com>
---
 qrap.c | 34 ++++++++++++++++++++++++----------
 1 file changed, 24 insertions(+), 10 deletions(-)

diff --git a/qrap.c b/qrap.c
index 3077944..27c12ed 100644
--- a/qrap.c
+++ b/qrap.c
@@ -77,6 +77,7 @@ static const struct drop_arg {
  * @template_post:	Suffix for device specification (last part of address)
  * @template_json:		Device prefix for when JSON is used
  * @template_json_post:	Device suffix for when JSON is used
+ * @base:		Base used for PCI addresses
  * @first:		First usable PCI address
  * @last:		Last usable PCI address
  */
@@ -87,6 +88,7 @@ static const struct pci_dev {
 	char *template_post;
 	char *template_json;
 	char *template_json_post;
+	int base;
 	int first;
 	int last;
 } pci_devs[] = {
@@ -94,19 +96,19 @@ static const struct pci_dev {
 		"pc-q35", "virtio-net-pci",
 		"bus=pci.", ",addr=0x0",
 		"\"bus\":\"pci.", ",\"addr\":\"0x0\"",
-		3, /* 2: hotplug bus */ 31
+		10, 3, /* 2: hotplug bus */ 31
 	},
 	{
 		"pc-", "virtio-net-pci",
 		"bus=pci.0,addr=0x", "",
 		"\"bus\":\"pci.0\",\"addr\":\"0x", "",
-		2, /* 1: ISA bridge */ 31
+		16, 2, /* 1: ISA bridge */ 31
 	},
 	{
 		"s390-ccw", "virtio-net-ccw",
 		"devno=fe.0.", "",
 		"\"devno\":\"fe.0.", "",
-		1, 16
+		16, 1, 16
 	},
 	{ 0 },
 };
@@ -264,7 +266,7 @@ int main(int argc, char **argv)
 			if (template) {
 				long n;
 
-				n = strtol(p + strlen(template), NULL, 16);
+				n = strtol(p + strlen(template), NULL, dev->base);
 				if (!errno)
 					addr_map |= (1 << n);
 			}
@@ -285,13 +287,25 @@ int main(int argc, char **argv)
 	if (has_dev) {
 		qemu_argv[qemu_argc++] = "-device";
 		if (!has_json) {
-			snprintf(dev_str, ARG_MAX,
-			         "%s,%s%x%s,netdev=hostnet0,x-txburst=4096",
-			         dev->name, dev->template, i, dev->template_post);
+			if (dev->base == 16) {
+				snprintf(dev_str, ARG_MAX,
+				         "%s,%s%x%s,netdev=hostnet0,x-txburst=4096",
+				         dev->name, dev->template, i, dev->template_post);
+			} else if (dev->base == 10) {
+				snprintf(dev_str, ARG_MAX,
+				         "%s,%s%d%s,netdev=hostnet0,x-txburst=4096",
+				         dev->name, dev->template, i, dev->template_post);
+			}
 		} else {
-			snprintf(dev_str, ARG_MAX,
-			         "{\"driver\":\"%s\",%s%x\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
-			         dev->name, dev->template_json, i, dev->template_json_post);
+			if (dev->base == 16) {
+				snprintf(dev_str, ARG_MAX,
+				         "{\"driver\":\"%s\",%s%x\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
+				         dev->name, dev->template_json, i, dev->template_json_post);
+			} else if (dev->base == 10) {
+				snprintf(dev_str, ARG_MAX,
+				         "{\"driver\":\"%s\",%s%d\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
+				         dev->name, dev->template_json, i, dev->template_json_post);
+			}
 		}
 		qemu_argv[qemu_argc++] = dev_str;
 	}
-- 
@@ -77,6 +77,7 @@ static const struct drop_arg {
  * @template_post:	Suffix for device specification (last part of address)
  * @template_json:		Device prefix for when JSON is used
  * @template_json_post:	Device suffix for when JSON is used
+ * @base:		Base used for PCI addresses
  * @first:		First usable PCI address
  * @last:		Last usable PCI address
  */
@@ -87,6 +88,7 @@ static const struct pci_dev {
 	char *template_post;
 	char *template_json;
 	char *template_json_post;
+	int base;
 	int first;
 	int last;
 } pci_devs[] = {
@@ -94,19 +96,19 @@ static const struct pci_dev {
 		"pc-q35", "virtio-net-pci",
 		"bus=pci.", ",addr=0x0",
 		"\"bus\":\"pci.", ",\"addr\":\"0x0\"",
-		3, /* 2: hotplug bus */ 31
+		10, 3, /* 2: hotplug bus */ 31
 	},
 	{
 		"pc-", "virtio-net-pci",
 		"bus=pci.0,addr=0x", "",
 		"\"bus\":\"pci.0\",\"addr\":\"0x", "",
-		2, /* 1: ISA bridge */ 31
+		16, 2, /* 1: ISA bridge */ 31
 	},
 	{
 		"s390-ccw", "virtio-net-ccw",
 		"devno=fe.0.", "",
 		"\"devno\":\"fe.0.", "",
-		1, 16
+		16, 1, 16
 	},
 	{ 0 },
 };
@@ -264,7 +266,7 @@ int main(int argc, char **argv)
 			if (template) {
 				long n;
 
-				n = strtol(p + strlen(template), NULL, 16);
+				n = strtol(p + strlen(template), NULL, dev->base);
 				if (!errno)
 					addr_map |= (1 << n);
 			}
@@ -285,13 +287,25 @@ int main(int argc, char **argv)
 	if (has_dev) {
 		qemu_argv[qemu_argc++] = "-device";
 		if (!has_json) {
-			snprintf(dev_str, ARG_MAX,
-			         "%s,%s%x%s,netdev=hostnet0,x-txburst=4096",
-			         dev->name, dev->template, i, dev->template_post);
+			if (dev->base == 16) {
+				snprintf(dev_str, ARG_MAX,
+				         "%s,%s%x%s,netdev=hostnet0,x-txburst=4096",
+				         dev->name, dev->template, i, dev->template_post);
+			} else if (dev->base == 10) {
+				snprintf(dev_str, ARG_MAX,
+				         "%s,%s%d%s,netdev=hostnet0,x-txburst=4096",
+				         dev->name, dev->template, i, dev->template_post);
+			}
 		} else {
-			snprintf(dev_str, ARG_MAX,
-			         "{\"driver\":\"%s\",%s%x\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
-			         dev->name, dev->template_json, i, dev->template_json_post);
+			if (dev->base == 16) {
+				snprintf(dev_str, ARG_MAX,
+				         "{\"driver\":\"%s\",%s%x\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
+				         dev->name, dev->template_json, i, dev->template_json_post);
+			} else if (dev->base == 10) {
+				snprintf(dev_str, ARG_MAX,
+				         "{\"driver\":\"%s\",%s%d\"%s,\"netdev\":\"hostnet0\",\"x-txburst\":4096}",
+				         dev->name, dev->template_json, i, dev->template_json_post);
+			}
 		}
 		qemu_argv[qemu_argc++] = dev_str;
 	}
-- 
2.39.2


  parent reply	other threads:[~2023-02-24 18:49 UTC|newest]

Thread overview: 15+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-02-24 18:49 [PATCH 0/5] qrap: Fix a number of issues Andrea Bolognani
2023-02-24 18:49 ` [PATCH 1/5] qrap: Fix limits for PCI addresses Andrea Bolognani
2023-02-26 23:54   ` David Gibson
2023-02-24 18:49 ` [PATCH 2/5] qrap: Fix support for pc machines Andrea Bolognani
2023-02-26 23:55   ` David Gibson
2023-02-24 18:49 ` [PATCH 3/5] qrap: Drop args in JSON format Andrea Bolognani
2023-02-26 23:56   ` David Gibson
2023-02-24 18:49 ` Andrea Bolognani [this message]
2023-02-26 23:58   ` [PATCH 4/5] qrap: Introduce machine-specific PCI address base David Gibson
2023-02-24 18:49 ` [PATCH 5/5] qrap: Generate -netdev as JSON Andrea Bolognani
2023-02-27  0:00   ` David Gibson
2023-02-24 19:36 ` [PATCH 0/5] qrap: Fix a number of issues Andrea Bolognani
2023-02-27 10:25   ` Stefano Brivio
2023-02-27 13:59     ` Andrea Bolognani
2023-02-27 21:54 ` Stefano Brivio

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20230224184949.518615-5-abologna@redhat.com \
    --to=abologna@redhat.com \
    --cc=passt-dev@passt.top \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://passt.top/passt

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for IMAP folder(s).