On 03/31/2013 12:18 PM, Werner Almesberger wrote:
> This makes documented use of "struct ieee802154_mlme_ops" follow current
> use, in which some operations are regularly left out, making them NULL.
> Since the calls do not check for NULL, any attempted use causes an oops.
>
> This patch makes the following operations optional and returns EINVAL
> if their use is attempted: assoc_req, assoc_resp, disassoc_req,
> start_req, and scan_req.
>
> The following operations are still required: get_phy, get_pan_id,
> get_short_addr, and get_dsn.
>
> I didn't touch the remaining get_bsn because it is currently not
> called anywhere.

Maybe make it clear that this fixes a current oops in the kernel. Maybe
some text like the following:

Make nl-mac.c check for NULL before calling the following functions:
    assoc_req,
    assoc_resp,
    disassoc_req,
    start_req,
    scan_req.

This fixes a current oops where those functions are called but not
implemented.

<then additional text>

The patch looks good.


> Signed-off-by: Werner Almesberger <wer...@almesberger.net>
> ---
>  Documentation/networking/ieee802154.txt |    5 +++--
>  include/net/ieee802154_netdev.h         |    4 ++++
>  net/ieee802154/nl-mac.c                 |   10 ++++++++++
>  3 files changed, 17 insertions(+), 2 deletions(-)
>
> diff --git a/Documentation/networking/ieee802154.txt 
> b/Documentation/networking/ieee802154.txt
> index 703cf43..67a9cb2 100644
> --- a/Documentation/networking/ieee802154.txt
> +++ b/Documentation/networking/ieee802154.txt
> @@ -71,8 +71,9 @@ submits skb to qdisc), so if you need something from that 
> cb later, you should
>  store info in the skb->data on your own.
>  
>  To hook the MLME interface you have to populate the ml_priv field of your
> -net_device with a pointer to struct ieee802154_mlme_ops instance. All fields 
> are
> -required.
> +net_device with a pointer to struct ieee802154_mlme_ops instance. The fields
> +assoc_req, assoc_resp, disassoc_req, start_req, and scan_req are optional.
> +All other fields are required.
>  
>  We provide an example of simple HardMAC driver at 
> drivers/ieee802154/fakehard.c
>  
> diff --git a/include/net/ieee802154_netdev.h b/include/net/ieee802154_netdev.h
> index d104c88..b9cb33d 100644
> --- a/include/net/ieee802154_netdev.h
> +++ b/include/net/ieee802154_netdev.h
> @@ -85,6 +85,8 @@ struct wpan_phy;
>   * Use wpan_wpy_put to put that reference.
>   */
>  struct ieee802154_mlme_ops {
> +     /* The following fields are optional (can be NULL). */
> +
>       int (*assoc_req)(struct net_device *dev,
>                       struct ieee802154_addr *addr,
>                       u8 channel, u8 page, u8 cap);
> @@ -101,6 +103,8 @@ struct ieee802154_mlme_ops {
>       int (*scan_req)(struct net_device *dev,
>                       u8 type, u32 channels, u8 page, u8 duration);
>  
> +     /* The fields below are required. */
> +
>       struct wpan_phy *(*get_phy)(const struct net_device *dev);
>  
>       /*
> diff --git a/net/ieee802154/nl-mac.c b/net/ieee802154/nl-mac.c
> index 96bb08a..ca49e65 100644
> --- a/net/ieee802154/nl-mac.c
> +++ b/net/ieee802154/nl-mac.c
> @@ -327,6 +327,8 @@ static int ieee802154_associate_req(struct sk_buff *skb,
>       dev = ieee802154_nl_get_dev(info);
>       if (!dev)
>               return -ENODEV;
> +     if (!ieee802154_mlme_ops(dev)->assoc_req)
> +             return -EINVAL;
>  
>       if (info->attrs[IEEE802154_ATTR_COORD_HW_ADDR]) {
>               addr.addr_type = IEEE802154_ADDR_LONG;
> @@ -369,6 +371,8 @@ static int ieee802154_associate_resp(struct sk_buff *skb,
>       dev = ieee802154_nl_get_dev(info);
>       if (!dev)
>               return -ENODEV;
> +     if (!ieee802154_mlme_ops(dev)->assoc_resp)
> +             return -EINVAL;
>  
>       addr.addr_type = IEEE802154_ADDR_LONG;
>       nla_memcpy(addr.hwaddr, info->attrs[IEEE802154_ATTR_DEST_HW_ADDR],
> @@ -399,6 +403,8 @@ static int ieee802154_disassociate_req(struct sk_buff 
> *skb,
>       dev = ieee802154_nl_get_dev(info);
>       if (!dev)
>               return -ENODEV;
> +     if (!ieee802154_mlme_ops(dev)->disassoc_req)
> +             return -EINVAL;
>  
>       if (info->attrs[IEEE802154_ATTR_DEST_HW_ADDR]) {
>               addr.addr_type = IEEE802154_ADDR_LONG;
> @@ -448,6 +454,8 @@ static int ieee802154_start_req(struct sk_buff *skb, 
> struct genl_info *info)
>       dev = ieee802154_nl_get_dev(info);
>       if (!dev)
>               return -ENODEV;
> +     if (!ieee802154_mlme_ops(dev)->start_req)
> +             return -EINVAL;
>  
>       addr.addr_type = IEEE802154_ADDR_SHORT;
>       addr.short_addr = nla_get_u16(
> @@ -497,6 +505,8 @@ static int ieee802154_scan_req(struct sk_buff *skb, 
> struct genl_info *info)
>       dev = ieee802154_nl_get_dev(info);
>       if (!dev)
>               return -ENODEV;
> +     if (!ieee802154_mlme_ops(dev)->scan_req)
> +             return -EINVAL;
>  
>       type = nla_get_u8(info->attrs[IEEE802154_ATTR_SCAN_TYPE]);
>       channels = nla_get_u32(info->attrs[IEEE802154_ATTR_CHANNELS]);


------------------------------------------------------------------------------
Minimize network downtime and maximize team effectiveness.
Reduce network management and security costs.Learn how to hire 
the most talented Cisco Certified professionals. Visit the 
Employer Resources Portal
http://www.cisco.com/web/learning/employer_resources/index.html
_______________________________________________
Linux-zigbee-devel mailing list
Linux-zigbee-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/linux-zigbee-devel

Reply via email to