--- a/net/wireless/sysfs.c +++ b/net/wireless/sysfs.c @@ -24,18 +24,35 @@ static inline struct cfg80211_registered return container_of(dev, struct cfg80211_registered_device, wiphy.dev); } -#define SHOW_FMT(name, fmt, member) \ +#define SHOW_FMT(name, fmt, member, mode) \ static ssize_t name ## _show(struct device *dev, \ struct device_attribute *attr, \ char *buf) \ { \ return sprintf(buf, fmt "\n", dev_to_rdev(dev)->member); \ } \ -static DEVICE_ATTR_RO(name) +static DEVICE_ATTR_##mode(name) -SHOW_FMT(index, "%d", wiphy_idx); -SHOW_FMT(macaddress, "%pM", wiphy.perm_addr); -SHOW_FMT(address_mask, "%pM", wiphy.addr_mask); +static ssize_t macaddress_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t len) +{ + u8 mac[ETH_ALEN]; + + if (!mac_pton(buf, mac)) + return -EINVAL; + + if (buf[3 * ETH_ALEN - 1] && buf[3 * ETH_ALEN - 1] != '\n') + return -EINVAL; + + memcpy(dev_to_rdev(dev)->wiphy.perm_addr, mac, ETH_ALEN); + + return strnlen(buf, len); +} + +SHOW_FMT(index, "%d", wiphy_idx, RO); +SHOW_FMT(macaddress, "%pM", wiphy.perm_addr, RW); +SHOW_FMT(address_mask, "%pM", wiphy.addr_mask, RO); static ssize_t name_show(struct device *dev, struct device_attribute *attr,