[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20250408233118.21452-6-ryazanov.s.a@gmail.com>
Date: Wed, 9 Apr 2025 02:31:17 +0300
From: Sergey Ryazanov <ryazanov.s.a@...il.com>
To: Loic Poulain <loic.poulain@....qualcomm.com>,
Johannes Berg <johannes@...solutions.net>
Cc: Andrew Lunn <andrew+netdev@...n.ch>,
Eric Dumazet <edumazet@...gle.com>,
"David S . Miller" <davem@...emloft.net>,
Jakub Kicinski <kuba@...nel.org>,
Paolo Abeni <pabeni@...hat.com>,
netdev@...r.kernel.org
Subject: [RFC PATCH 5/6] net: wwan: hwsim: refactor to support more port types
Just introduced WWAN NMEA port type needs a testing option. The WWAN HW
simulator was developed with the AT port type in mind and cannot be
easily extended. Refactor it now to make it capable to support more port
types.
No big functional changes, mostly renaming with a little code
rearrangement.
Signed-off-by: Sergey Ryazanov <ryazanov.s.a@...il.com>
---
drivers/net/wwan/wwan_hwsim.c | 73 ++++++++++++++++++++---------------
1 file changed, 41 insertions(+), 32 deletions(-)
diff --git a/drivers/net/wwan/wwan_hwsim.c b/drivers/net/wwan/wwan_hwsim.c
index b02befd1b6fb..20277ba88433 100644
--- a/drivers/net/wwan/wwan_hwsim.c
+++ b/drivers/net/wwan/wwan_hwsim.c
@@ -56,12 +56,16 @@ struct wwan_hwsim_port {
struct wwan_port *wwan;
struct work_struct del_work;
struct dentry *debugfs_topdir;
- enum { /* AT command parser state */
- AT_PARSER_WAIT_A,
- AT_PARSER_WAIT_T,
- AT_PARSER_WAIT_TERM,
- AT_PARSER_SKIP_LINE,
- } pstate;
+ union {
+ struct {
+ enum { /* AT command parser state */
+ AT_PARSER_WAIT_A,
+ AT_PARSER_WAIT_T,
+ AT_PARSER_WAIT_TERM,
+ AT_PARSER_SKIP_LINE,
+ } pstate;
+ } at_emul;
+ };
};
static const struct file_operations wwan_hwsim_debugfs_portdestroy_fops;
@@ -101,16 +105,16 @@ static const struct wwan_ops wwan_hwsim_wwan_rtnl_ops = {
.setup = wwan_hwsim_netdev_setup,
};
-static int wwan_hwsim_port_start(struct wwan_port *wport)
+static int wwan_hwsim_at_emul_start(struct wwan_port *wport)
{
struct wwan_hwsim_port *port = wwan_port_get_drvdata(wport);
- port->pstate = AT_PARSER_WAIT_A;
+ port->at_emul.pstate = AT_PARSER_WAIT_A;
return 0;
}
-static void wwan_hwsim_port_stop(struct wwan_port *wport)
+static void wwan_hwsim_at_emul_stop(struct wwan_port *wport)
{
}
@@ -120,7 +124,7 @@ static void wwan_hwsim_port_stop(struct wwan_port *wport)
*
* Be aware that this processor is not fully V.250 compliant.
*/
-static int wwan_hwsim_port_tx(struct wwan_port *wport, struct sk_buff *in)
+static int wwan_hwsim_at_emul_tx(struct wwan_port *wport, struct sk_buff *in)
{
struct wwan_hwsim_port *port = wwan_port_get_drvdata(wport);
struct sk_buff *out;
@@ -142,17 +146,17 @@ static int wwan_hwsim_port_tx(struct wwan_port *wport, struct sk_buff *in)
for (i = 0, s = 0; i < in->len; ++i) {
char c = in->data[i];
- if (port->pstate == AT_PARSER_WAIT_A) {
+ if (port->at_emul.pstate == AT_PARSER_WAIT_A) {
if (c == 'A' || c == 'a')
- port->pstate = AT_PARSER_WAIT_T;
+ port->at_emul.pstate = AT_PARSER_WAIT_T;
else if (c != '\n') /* Ignore formating char */
- port->pstate = AT_PARSER_SKIP_LINE;
- } else if (port->pstate == AT_PARSER_WAIT_T) {
+ port->at_emul.pstate = AT_PARSER_SKIP_LINE;
+ } else if (port->at_emul.pstate == AT_PARSER_WAIT_T) {
if (c == 'T' || c == 't')
- port->pstate = AT_PARSER_WAIT_TERM;
+ port->at_emul.pstate = AT_PARSER_WAIT_TERM;
else
- port->pstate = AT_PARSER_SKIP_LINE;
- } else if (port->pstate == AT_PARSER_WAIT_TERM) {
+ port->at_emul.pstate = AT_PARSER_SKIP_LINE;
+ } else if (port->at_emul.pstate == AT_PARSER_WAIT_TERM) {
if (c != '\r')
continue;
/* Consume the trailing formatting char as well */
@@ -162,11 +166,11 @@ static int wwan_hwsim_port_tx(struct wwan_port *wport, struct sk_buff *in)
skb_put_data(out, &in->data[s], n);/* Echo */
skb_put_data(out, "\r\nOK\r\n", 6);
s = i + 1;
- port->pstate = AT_PARSER_WAIT_A;
- } else if (port->pstate == AT_PARSER_SKIP_LINE) {
+ port->at_emul.pstate = AT_PARSER_WAIT_A;
+ } else if (port->at_emul.pstate == AT_PARSER_SKIP_LINE) {
if (c != '\r')
continue;
- port->pstate = AT_PARSER_WAIT_A;
+ port->at_emul.pstate = AT_PARSER_WAIT_A;
}
}
@@ -183,18 +187,25 @@ static int wwan_hwsim_port_tx(struct wwan_port *wport, struct sk_buff *in)
return 0;
}
-static const struct wwan_port_ops wwan_hwsim_port_ops = {
- .start = wwan_hwsim_port_start,
- .stop = wwan_hwsim_port_stop,
- .tx = wwan_hwsim_port_tx,
+static const struct wwan_port_ops wwan_hwsim_at_emul_port_ops = {
+ .start = wwan_hwsim_at_emul_start,
+ .stop = wwan_hwsim_at_emul_stop,
+ .tx = wwan_hwsim_at_emul_tx,
};
-static struct wwan_hwsim_port *wwan_hwsim_port_new(struct wwan_hwsim_dev *dev)
+static struct wwan_hwsim_port *wwan_hwsim_port_new(struct wwan_hwsim_dev *dev,
+ enum wwan_port_type type)
{
+ const struct wwan_port_ops *ops;
struct wwan_hwsim_port *port;
char name[0x10];
int err;
+ if (type == WWAN_PORT_AT)
+ ops = &wwan_hwsim_at_emul_port_ops;
+ else
+ return ERR_PTR(-EINVAL);
+
port = kzalloc(sizeof(*port), GFP_KERNEL);
if (!port)
return ERR_PTR(-ENOMEM);
@@ -205,9 +216,7 @@ static struct wwan_hwsim_port *wwan_hwsim_port_new(struct wwan_hwsim_dev *dev)
port->id = dev->port_idx++;
spin_unlock(&dev->ports_lock);
- port->wwan = wwan_create_port(&dev->dev, WWAN_PORT_AT,
- &wwan_hwsim_port_ops,
- NULL, port);
+ port->wwan = wwan_create_port(&dev->dev, type, ops, NULL, port);
if (IS_ERR(port->wwan)) {
err = PTR_ERR(port->wwan);
goto err_free_port;
@@ -392,7 +401,7 @@ static ssize_t wwan_hwsim_debugfs_portcreate_write(struct file *file,
struct wwan_hwsim_dev *dev = file->private_data;
struct wwan_hwsim_port *port;
- port = wwan_hwsim_port_new(dev);
+ port = wwan_hwsim_port_new(dev, WWAN_PORT_AT);
if (IS_ERR(port))
return PTR_ERR(port);
@@ -459,6 +468,8 @@ static int __init wwan_hwsim_init_devs(void)
int i, j;
for (i = 0; i < wwan_hwsim_devsnum; ++i) {
+ struct wwan_hwsim_port *port;
+
dev = wwan_hwsim_dev_new();
if (IS_ERR(dev))
return PTR_ERR(dev);
@@ -471,9 +482,7 @@ static int __init wwan_hwsim_init_devs(void)
* the simulator readiness time.
*/
for (j = 0; j < 2; ++j) {
- struct wwan_hwsim_port *port;
-
- port = wwan_hwsim_port_new(dev);
+ port = wwan_hwsim_port_new(dev, WWAN_PORT_AT);
if (IS_ERR(port))
return PTR_ERR(port);
--
2.45.3
Powered by blists - more mailing lists