net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
/* SPDX-License-Identifier: GPL-2.0-only */
|
|
|
|
/* Copyright (c) 2021, Linaro Ltd <loic.poulain@linaro.org> */
|
|
|
|
|
|
|
|
#ifndef __WWAN_H
|
|
|
|
#define __WWAN_H
|
|
|
|
|
|
|
|
#include <linux/device.h>
|
|
|
|
#include <linux/kernel.h>
|
net: wwan: Allow WWAN drivers to provide blocking tx and poll function
At the moment, the WWAN core provides wwan_port_txon/off() to implement
blocking writes. The tx() port operation should not block, instead
wwan_port_txon/off() should be called when the TX queue is full or has
free space again.
However, in some cases it is not straightforward to make use of that
functionality. For example, the RPMSG API used by rpmsg_wwan_ctrl.c
does not provide any way to be notified when the TX queue has space
again. Instead, it only provides the following operations:
- rpmsg_send(): blocking write (wait until there is space)
- rpmsg_trysend(): non-blocking write (return error if no space)
- rpmsg_poll(): set poll flags depending on TX queue state
Generally that's totally sufficient for implementing a char device,
but it does not fit well to the currently provided WWAN port ops.
Most of the time, using the non-blocking rpmsg_trysend() in the
WWAN tx() port operation works just fine. However, with high-frequent
writes to the char device it is possible to trigger a situation
where this causes issues. For example, consider the following
(somewhat unrealistic) example:
# dd if=/dev/zero bs=1000 of=/dev/wwan0qmi0
dd: error writing '/dev/wwan0qmi0': Resource temporarily unavailable
1+0 records out
This fails immediately after writing the first record. It's likely
only a matter of time until this triggers issues for some real application
(e.g. ModemManager sending a lot of large QMI packets).
The rpmsg_char device does not have this problem, because it uses
rpmsg_trysend() and rpmsg_poll() to support non-blocking operations.
Make it possible to use the same in the RPMSG WWAN driver by adding
two new optional wwan_port_ops:
- tx_blocking(): send data blocking if allowed
- tx_poll(): set additional TX poll flags
This integrates nicely with the RPMSG API and does not require
any change in existing WWAN drivers.
With these changes, the dd example above blocks instead of exiting
with an error.
Cc: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: Stephan Gerhold <stephan@gerhold.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-06-19 01:36:11 +08:00
|
|
|
#include <linux/poll.h>
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
#include <linux/skbuff.h>
|
2021-06-12 16:20:56 +08:00
|
|
|
#include <linux/netlink.h>
|
2021-06-22 06:51:00 +08:00
|
|
|
#include <linux/netdevice.h>
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
|
|
|
|
/**
|
|
|
|
* enum wwan_port_type - WWAN port types
|
|
|
|
* @WWAN_PORT_AT: AT commands
|
|
|
|
* @WWAN_PORT_MBIM: Mobile Broadband Interface Model control
|
|
|
|
* @WWAN_PORT_QMI: Qcom modem/MSM interface for modem control
|
|
|
|
* @WWAN_PORT_QCDM: Qcom Modem diagnostic interface
|
|
|
|
* @WWAN_PORT_FIREHOSE: XML based command protocol
|
2021-06-08 12:02:34 +08:00
|
|
|
*
|
|
|
|
* @WWAN_PORT_MAX: Highest supported port types
|
|
|
|
* @WWAN_PORT_UNKNOWN: Special value to indicate an unknown port type
|
|
|
|
* @__WWAN_PORT_MAX: Internal use
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
*/
|
|
|
|
enum wwan_port_type {
|
|
|
|
WWAN_PORT_AT,
|
|
|
|
WWAN_PORT_MBIM,
|
|
|
|
WWAN_PORT_QMI,
|
|
|
|
WWAN_PORT_QCDM,
|
|
|
|
WWAN_PORT_FIREHOSE,
|
2021-06-08 12:02:34 +08:00
|
|
|
|
|
|
|
/* Add new port types above this line */
|
|
|
|
|
|
|
|
__WWAN_PORT_MAX,
|
|
|
|
WWAN_PORT_MAX = __WWAN_PORT_MAX - 1,
|
2021-05-11 22:42:22 +08:00
|
|
|
WWAN_PORT_UNKNOWN,
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
};
|
|
|
|
|
|
|
|
struct wwan_port;
|
|
|
|
|
|
|
|
/** struct wwan_port_ops - The WWAN port operations
|
|
|
|
* @start: The routine for starting the WWAN port device.
|
|
|
|
* @stop: The routine for stopping the WWAN port device.
|
net: wwan: Allow WWAN drivers to provide blocking tx and poll function
At the moment, the WWAN core provides wwan_port_txon/off() to implement
blocking writes. The tx() port operation should not block, instead
wwan_port_txon/off() should be called when the TX queue is full or has
free space again.
However, in some cases it is not straightforward to make use of that
functionality. For example, the RPMSG API used by rpmsg_wwan_ctrl.c
does not provide any way to be notified when the TX queue has space
again. Instead, it only provides the following operations:
- rpmsg_send(): blocking write (wait until there is space)
- rpmsg_trysend(): non-blocking write (return error if no space)
- rpmsg_poll(): set poll flags depending on TX queue state
Generally that's totally sufficient for implementing a char device,
but it does not fit well to the currently provided WWAN port ops.
Most of the time, using the non-blocking rpmsg_trysend() in the
WWAN tx() port operation works just fine. However, with high-frequent
writes to the char device it is possible to trigger a situation
where this causes issues. For example, consider the following
(somewhat unrealistic) example:
# dd if=/dev/zero bs=1000 of=/dev/wwan0qmi0
dd: error writing '/dev/wwan0qmi0': Resource temporarily unavailable
1+0 records out
This fails immediately after writing the first record. It's likely
only a matter of time until this triggers issues for some real application
(e.g. ModemManager sending a lot of large QMI packets).
The rpmsg_char device does not have this problem, because it uses
rpmsg_trysend() and rpmsg_poll() to support non-blocking operations.
Make it possible to use the same in the RPMSG WWAN driver by adding
two new optional wwan_port_ops:
- tx_blocking(): send data blocking if allowed
- tx_poll(): set additional TX poll flags
This integrates nicely with the RPMSG API and does not require
any change in existing WWAN drivers.
With these changes, the dd example above blocks instead of exiting
with an error.
Cc: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: Stephan Gerhold <stephan@gerhold.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-06-19 01:36:11 +08:00
|
|
|
* @tx: Non-blocking routine that sends WWAN port protocol data to the device.
|
|
|
|
* @tx_blocking: Optional blocking routine that sends WWAN port protocol data
|
|
|
|
* to the device.
|
|
|
|
* @tx_poll: Optional routine that sets additional TX poll flags.
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
*
|
|
|
|
* The wwan_port_ops structure contains a list of low-level operations
|
net: wwan: Allow WWAN drivers to provide blocking tx and poll function
At the moment, the WWAN core provides wwan_port_txon/off() to implement
blocking writes. The tx() port operation should not block, instead
wwan_port_txon/off() should be called when the TX queue is full or has
free space again.
However, in some cases it is not straightforward to make use of that
functionality. For example, the RPMSG API used by rpmsg_wwan_ctrl.c
does not provide any way to be notified when the TX queue has space
again. Instead, it only provides the following operations:
- rpmsg_send(): blocking write (wait until there is space)
- rpmsg_trysend(): non-blocking write (return error if no space)
- rpmsg_poll(): set poll flags depending on TX queue state
Generally that's totally sufficient for implementing a char device,
but it does not fit well to the currently provided WWAN port ops.
Most of the time, using the non-blocking rpmsg_trysend() in the
WWAN tx() port operation works just fine. However, with high-frequent
writes to the char device it is possible to trigger a situation
where this causes issues. For example, consider the following
(somewhat unrealistic) example:
# dd if=/dev/zero bs=1000 of=/dev/wwan0qmi0
dd: error writing '/dev/wwan0qmi0': Resource temporarily unavailable
1+0 records out
This fails immediately after writing the first record. It's likely
only a matter of time until this triggers issues for some real application
(e.g. ModemManager sending a lot of large QMI packets).
The rpmsg_char device does not have this problem, because it uses
rpmsg_trysend() and rpmsg_poll() to support non-blocking operations.
Make it possible to use the same in the RPMSG WWAN driver by adding
two new optional wwan_port_ops:
- tx_blocking(): send data blocking if allowed
- tx_poll(): set additional TX poll flags
This integrates nicely with the RPMSG API and does not require
any change in existing WWAN drivers.
With these changes, the dd example above blocks instead of exiting
with an error.
Cc: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: Stephan Gerhold <stephan@gerhold.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-06-19 01:36:11 +08:00
|
|
|
* that control a WWAN port device. All functions are mandatory unless specified.
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
*/
|
|
|
|
struct wwan_port_ops {
|
|
|
|
int (*start)(struct wwan_port *port);
|
|
|
|
void (*stop)(struct wwan_port *port);
|
|
|
|
int (*tx)(struct wwan_port *port, struct sk_buff *skb);
|
net: wwan: Allow WWAN drivers to provide blocking tx and poll function
At the moment, the WWAN core provides wwan_port_txon/off() to implement
blocking writes. The tx() port operation should not block, instead
wwan_port_txon/off() should be called when the TX queue is full or has
free space again.
However, in some cases it is not straightforward to make use of that
functionality. For example, the RPMSG API used by rpmsg_wwan_ctrl.c
does not provide any way to be notified when the TX queue has space
again. Instead, it only provides the following operations:
- rpmsg_send(): blocking write (wait until there is space)
- rpmsg_trysend(): non-blocking write (return error if no space)
- rpmsg_poll(): set poll flags depending on TX queue state
Generally that's totally sufficient for implementing a char device,
but it does not fit well to the currently provided WWAN port ops.
Most of the time, using the non-blocking rpmsg_trysend() in the
WWAN tx() port operation works just fine. However, with high-frequent
writes to the char device it is possible to trigger a situation
where this causes issues. For example, consider the following
(somewhat unrealistic) example:
# dd if=/dev/zero bs=1000 of=/dev/wwan0qmi0
dd: error writing '/dev/wwan0qmi0': Resource temporarily unavailable
1+0 records out
This fails immediately after writing the first record. It's likely
only a matter of time until this triggers issues for some real application
(e.g. ModemManager sending a lot of large QMI packets).
The rpmsg_char device does not have this problem, because it uses
rpmsg_trysend() and rpmsg_poll() to support non-blocking operations.
Make it possible to use the same in the RPMSG WWAN driver by adding
two new optional wwan_port_ops:
- tx_blocking(): send data blocking if allowed
- tx_poll(): set additional TX poll flags
This integrates nicely with the RPMSG API and does not require
any change in existing WWAN drivers.
With these changes, the dd example above blocks instead of exiting
with an error.
Cc: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: Stephan Gerhold <stephan@gerhold.net>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-06-19 01:36:11 +08:00
|
|
|
|
|
|
|
/* Optional operations */
|
|
|
|
int (*tx_blocking)(struct wwan_port *port, struct sk_buff *skb);
|
|
|
|
__poll_t (*tx_poll)(struct wwan_port *port, struct file *filp,
|
|
|
|
poll_table *wait);
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
};
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_create_port - Add a new WWAN port
|
|
|
|
* @parent: Device to use as parent and shared by all WWAN ports
|
|
|
|
* @type: WWAN port type
|
|
|
|
* @ops: WWAN port operations
|
|
|
|
* @drvdata: Pointer to caller driver data
|
|
|
|
*
|
|
|
|
* Allocate and register a new WWAN port. The port will be automatically exposed
|
|
|
|
* to user as a character device and attached to the right virtual WWAN device,
|
|
|
|
* based on the parent pointer. The parent pointer is the device shared by all
|
|
|
|
* components of a same WWAN modem (e.g. USB dev, PCI dev, MHI controller...).
|
|
|
|
*
|
|
|
|
* drvdata will be placed in the WWAN port device driver data and can be
|
|
|
|
* retrieved with wwan_port_get_drvdata().
|
|
|
|
*
|
|
|
|
* This function must be balanced with a call to wwan_remove_port().
|
|
|
|
*
|
|
|
|
* Returns a valid pointer to wwan_port on success or PTR_ERR on failure
|
|
|
|
*/
|
|
|
|
struct wwan_port *wwan_create_port(struct device *parent,
|
|
|
|
enum wwan_port_type type,
|
|
|
|
const struct wwan_port_ops *ops,
|
|
|
|
void *drvdata);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_remove_port - Remove a WWAN port
|
|
|
|
* @port: WWAN port to remove
|
|
|
|
*
|
|
|
|
* Remove a previously created port.
|
|
|
|
*/
|
|
|
|
void wwan_remove_port(struct wwan_port *port);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_port_rx - Receive data from the WWAN port
|
|
|
|
* @port: WWAN port for which data is received
|
|
|
|
* @skb: Pointer to the rx buffer
|
|
|
|
*
|
|
|
|
* A port driver calls this function upon data reception (MBIM, AT...).
|
|
|
|
*/
|
|
|
|
void wwan_port_rx(struct wwan_port *port, struct sk_buff *skb);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_port_txoff - Stop TX on WWAN port
|
|
|
|
* @port: WWAN port for which TX must be stopped
|
|
|
|
*
|
|
|
|
* Used for TX flow control, a port driver calls this function to indicate TX
|
|
|
|
* is temporary unavailable (e.g. due to ring buffer fullness).
|
|
|
|
*/
|
|
|
|
void wwan_port_txoff(struct wwan_port *port);
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_port_txon - Restart TX on WWAN port
|
|
|
|
* @port: WWAN port for which TX must be restarted
|
|
|
|
*
|
|
|
|
* Used for TX flow control, a port driver calls this function to indicate TX
|
|
|
|
* is available again.
|
|
|
|
*/
|
|
|
|
void wwan_port_txon(struct wwan_port *port);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* wwan_port_get_drvdata - Retrieve driver data from a WWAN port
|
|
|
|
* @port: Related WWAN port
|
|
|
|
*/
|
|
|
|
void *wwan_port_get_drvdata(struct wwan_port *port);
|
|
|
|
|
2021-06-22 06:51:00 +08:00
|
|
|
/**
|
|
|
|
* struct wwan_netdev_priv - WWAN core network device private data
|
|
|
|
* @link_id: WWAN device data link id
|
|
|
|
* @drv_priv: driver private data area, size is determined in &wwan_ops
|
|
|
|
*/
|
|
|
|
struct wwan_netdev_priv {
|
|
|
|
u32 link_id;
|
|
|
|
|
|
|
|
/* must be last */
|
|
|
|
u8 drv_priv[] __aligned(sizeof(void *));
|
|
|
|
};
|
|
|
|
|
|
|
|
static inline void *wwan_netdev_drvpriv(struct net_device *dev)
|
|
|
|
{
|
|
|
|
return ((struct wwan_netdev_priv *)netdev_priv(dev))->drv_priv;
|
|
|
|
}
|
|
|
|
|
2021-06-22 06:50:58 +08:00
|
|
|
/*
|
|
|
|
* Used to indicate that the WWAN core should not create a default network
|
|
|
|
* link.
|
|
|
|
*/
|
|
|
|
#define WWAN_NO_DEFAULT_LINK U32_MAX
|
|
|
|
|
2021-06-12 16:20:56 +08:00
|
|
|
/**
|
|
|
|
* struct wwan_ops - WWAN device ops
|
|
|
|
* @priv_size: size of private netdev data area
|
|
|
|
* @setup: set up a new netdev
|
|
|
|
* @newlink: register the new netdev
|
|
|
|
* @dellink: remove the given netdev
|
|
|
|
*/
|
|
|
|
struct wwan_ops {
|
|
|
|
unsigned int priv_size;
|
|
|
|
void (*setup)(struct net_device *dev);
|
|
|
|
int (*newlink)(void *ctxt, struct net_device *dev,
|
|
|
|
u32 if_id, struct netlink_ext_ack *extack);
|
|
|
|
void (*dellink)(void *ctxt, struct net_device *dev,
|
|
|
|
struct list_head *head);
|
|
|
|
};
|
|
|
|
|
|
|
|
int wwan_register_ops(struct device *parent, const struct wwan_ops *ops,
|
2021-06-22 06:50:58 +08:00
|
|
|
void *ctxt, u32 def_link_id);
|
2021-06-12 16:20:56 +08:00
|
|
|
|
|
|
|
void wwan_unregister_ops(struct device *parent);
|
|
|
|
|
net: Add a WWAN subsystem
This change introduces initial support for a WWAN framework. Given the
complexity and heterogeneity of existing WWAN hardwares and interfaces,
there is no strict definition of what a WWAN device is and how it should
be represented. It's often a collection of multiple devices that perform
the global WWAN feature (netdev, tty, chardev, etc).
One usual way to expose modem controls and configuration is via high
level protocols such as the well known AT command protocol, MBIM or
QMI. The USB modems started to expose them as character devices, and
user daemons such as ModemManager learnt to use them.
This initial version adds the concept of WWAN port, which is a logical
pipe to a modem control protocol. The protocols are rawly exposed to
user via character device, allowing straigthforward support in existing
tools (ModemManager, ofono...). The WWAN core takes care of the generic
part, including character device management, and relies on port driver
operations to receive/submit protocol data.
Since the different devices exposing protocols for a same WWAN hardware
do not necessarily know about each others (e.g. two different USB
interfaces, PCI/MHI channel devices...) and can be created/removed in
different orders, the WWAN core ensures that all WAN ports contributing
to the 'whole' WWAN feature are grouped under the same virtual WWAN
device, relying on the provided parent device (e.g. mhi controller,
USB device). It's a 'trick' I copied from Johannes's earlier WWAN
subsystem proposal.
This initial version is purposely minimalist, it's essentially moving
the generic part of the previously proposed mhi_wwan_ctrl driver inside
a common WWAN framework, but the implementation is open and flexible
enough to allow extension for further drivers.
Signed-off-by: Loic Poulain <loic.poulain@linaro.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
2021-04-16 16:36:33 +08:00
|
|
|
#endif /* __WWAN_H */
|