Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 6c26361e authored by florian@mickler.org's avatar florian@mickler.org Committed by John W. Linville
Browse files

enhance sysfs rfkill interface



This commit introduces two new sysfs knobs.

/sys/class/rfkill/rfkill[0-9]+/blocked_hw: (ro)
	hardblock kill state
/sys/class/rfkill/rfkill[0-9]+/blocked_sw: (rw)
	softblock kill state

Signed-off-by: default avatarFlorian Mickler <florian@mickler.org>
Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
parent 69c86373
Loading
Loading
Loading
Loading
+25 −0
Original line number Original line Diff line number Diff line
@@ -40,3 +40,28 @@ Description: Whether the soft blocked state is initialised from non-volatile
Values: 	A numeric value.
Values: 	A numeric value.
		0: false
		0: false
		1: true
		1: true


What:		/sys/class/rfkill/rfkill[0-9]+/blocked_hw
Date:		23-Feb-2010
KernelVersion	v2.6.34
Contact:	linux-wireless@vger.kernel.org
Description: 	Current hardblock state. This file is read only.
Values: 	A numeric value.
		0: inactive
			The transmitter is (potentially) active.
		1: active
			The transmitter is forced off by something outside of
			the driver's control.


What:		/sys/class/rfkill/rfkill[0-9]+/blocked_sw
Date:		23-Feb-2010
KernelVersion	v2.6.34
Contact:	linux-wireless@vger.kernel.org
Description:	Current softblock state. This file is read and write.
Values: 	A numeric value.
		0: inactive
			The transmitter is (potentially) active.
		1: active
			The transmitter is turned off by software.
+58 −0
Original line number Original line Diff line number Diff line
@@ -628,6 +628,61 @@ static ssize_t rfkill_persistent_show(struct device *dev,
	return sprintf(buf, "%d\n", rfkill->persistent);
	return sprintf(buf, "%d\n", rfkill->persistent);
}
}


static ssize_t rfkill_blocked_hw_show(struct device *dev,
				 struct device_attribute *attr,
				 char *buf)
{
	struct rfkill *rfkill = to_rfkill(dev);
	unsigned long flags;
	u32 state;

	spin_lock_irqsave(&rfkill->lock, flags);
	state = rfkill->state;
	spin_unlock_irqrestore(&rfkill->lock, flags);

	return sprintf(buf, "%d\n", (state & RFKILL_BLOCK_HW) ? 1 : 0 );
}

static ssize_t rfkill_blocked_sw_show(struct device *dev,
				 struct device_attribute *attr,
				 char *buf)
{
	struct rfkill *rfkill = to_rfkill(dev);
	unsigned long flags;
	u32 state;

	spin_lock_irqsave(&rfkill->lock, flags);
	state = rfkill->state;
	spin_unlock_irqrestore(&rfkill->lock, flags);

	return sprintf(buf, "%d\n", (state & RFKILL_BLOCK_SW) ? 1 : 0 );
}

static ssize_t rfkill_blocked_sw_store(struct device *dev,
				  struct device_attribute *attr,
				  const char *buf, size_t count)
{
	struct rfkill *rfkill = to_rfkill(dev);
	unsigned long state;
	int err;

	if (!capable(CAP_NET_ADMIN))
		return -EPERM;

	err = strict_strtoul(buf, 0, &state);
	if (err)
		return err;

	if (state > 1 )
		return -EINVAL;

	mutex_lock(&rfkill_global_mutex);
	rfkill_set_block(rfkill, state);
	mutex_unlock(&rfkill_global_mutex);

	return err ?: count;
}

static u8 user_state_from_blocked(unsigned long state)
static u8 user_state_from_blocked(unsigned long state)
{
{
	if (state & RFKILL_BLOCK_HW)
	if (state & RFKILL_BLOCK_HW)
@@ -700,6 +755,9 @@ static struct device_attribute rfkill_dev_attrs[] = {
	__ATTR(persistent, S_IRUGO, rfkill_persistent_show, NULL),
	__ATTR(persistent, S_IRUGO, rfkill_persistent_show, NULL),
	__ATTR(state, S_IRUGO|S_IWUSR, rfkill_state_show, rfkill_state_store),
	__ATTR(state, S_IRUGO|S_IWUSR, rfkill_state_show, rfkill_state_store),
	__ATTR(claim, S_IRUGO|S_IWUSR, rfkill_claim_show, rfkill_claim_store),
	__ATTR(claim, S_IRUGO|S_IWUSR, rfkill_claim_show, rfkill_claim_store),
	__ATTR(sw, S_IRUGO|S_IWUSR, rfkill_blocked_sw_show,
			rfkill_blocked_sw_store),
	__ATTR(hw, S_IRUGO, rfkill_blocked_hw_show, NULL),
	__ATTR_NULL
	__ATTR_NULL
};
};