rfkill: rewrite
[deliverable/linux.git] / drivers / net / wireless / iwlwifi / iwl-rfkill.c
index 65605ad44e4b0c06e16ccd3141a03190003d4c7e..13149936fd26d674c04c2d9f53a136c36753a6a5 100644 (file)
 #include "iwl-core.h"
 
 /* software rf-kill from user */
-static int iwl_rfkill_soft_rf_kill(void *data, enum rfkill_state state)
+static int iwl_rfkill_soft_rf_kill(void *data, bool blocked)
 {
        struct iwl_priv *priv = data;
-       int err = 0;
 
        if (!priv->rfkill)
-               return 0;
+               return -EINVAL;
 
        if (test_bit(STATUS_EXIT_PENDING, &priv->status))
                return 0;
 
-       IWL_DEBUG_RF_KILL(priv, "we received soft RFKILL set to state %d\n", state);
+       IWL_DEBUG_RF_KILL(priv, "received soft RFKILL: block=%d\n", blocked);
+
        mutex_lock(&priv->mutex);
 
-       switch (state) {
-       case RFKILL_STATE_UNBLOCKED:
-               if (iwl_is_rfkill_hw(priv)) {
-                       err = -EBUSY;
-                       goto out_unlock;
-               }
+       if (iwl_is_rfkill_hw(priv))
+               goto out_unlock;
+
+       if (!blocked)
                iwl_radio_kill_sw_enable_radio(priv);
-               break;
-       case RFKILL_STATE_SOFT_BLOCKED:
+       else
                iwl_radio_kill_sw_disable_radio(priv);
-               break;
-       default:
-               IWL_WARN(priv, "we received unexpected RFKILL state %d\n",
-                       state);
-               break;
-       }
+
 out_unlock:
        mutex_unlock(&priv->mutex);
-
-       return err;
+       return 0;
 }
 
+static const struct rfkill_ops iwl_rfkill_ops = {
+       .set_block = iwl_rfkill_soft_rf_kill,
+};
+
 int iwl_rfkill_init(struct iwl_priv *priv)
 {
        struct device *device = wiphy_dev(priv->hw->wiphy);
@@ -80,21 +75,16 @@ int iwl_rfkill_init(struct iwl_priv *priv)
        BUG_ON(device == NULL);
 
        IWL_DEBUG_RF_KILL(priv, "Initializing RFKILL.\n");
-       priv->rfkill = rfkill_allocate(device, RFKILL_TYPE_WLAN);
+       priv->rfkill = rfkill_alloc(priv->cfg->name,
+                                   device,
+                                   RFKILL_TYPE_WLAN,
+                                   &iwl_rfkill_ops, priv);
        if (!priv->rfkill) {
                IWL_ERR(priv, "Unable to allocate RFKILL device.\n");
                ret = -ENOMEM;
                goto error;
        }
 
-       priv->rfkill->name = priv->cfg->name;
-       priv->rfkill->data = priv;
-       priv->rfkill->state = RFKILL_STATE_UNBLOCKED;
-       priv->rfkill->toggle_radio = iwl_rfkill_soft_rf_kill;
-
-       priv->rfkill->dev.class->suspend = NULL;
-       priv->rfkill->dev.class->resume = NULL;
-
        ret = rfkill_register(priv->rfkill);
        if (ret) {
                IWL_ERR(priv, "Unable to register RFKILL: %d\n", ret);
@@ -102,11 +92,10 @@ int iwl_rfkill_init(struct iwl_priv *priv)
        }
 
        IWL_DEBUG_RF_KILL(priv, "RFKILL initialization complete.\n");
-       return ret;
+       return 0;
 
 free_rfkill:
-       if (priv->rfkill != NULL)
-               rfkill_free(priv->rfkill);
+       rfkill_destroy(priv->rfkill);
        priv->rfkill = NULL;
 
 error:
@@ -118,8 +107,10 @@ EXPORT_SYMBOL(iwl_rfkill_init);
 void iwl_rfkill_unregister(struct iwl_priv *priv)
 {
 
-       if (priv->rfkill)
+       if (priv->rfkill) {
                rfkill_unregister(priv->rfkill);
+               rfkill_destroy(priv->rfkill);
+       }
 
        priv->rfkill = NULL;
 }
@@ -131,14 +122,10 @@ void iwl_rfkill_set_hw_state(struct iwl_priv *priv)
        if (!priv->rfkill)
                return;
 
-       if (iwl_is_rfkill_hw(priv)) {
-               rfkill_force_state(priv->rfkill, RFKILL_STATE_HARD_BLOCKED);
-               return;
-       }
-
-       if (!iwl_is_rfkill_sw(priv))
-               rfkill_force_state(priv->rfkill, RFKILL_STATE_UNBLOCKED);
+       if (rfkill_set_hw_state(priv->rfkill,
+                               !!iwl_is_rfkill_hw(priv)))
+               iwl_radio_kill_sw_disable_radio(priv);
        else
-               rfkill_force_state(priv->rfkill, RFKILL_STATE_SOFT_BLOCKED);
+               iwl_radio_kill_sw_enable_radio(priv);
 }
 EXPORT_SYMBOL(iwl_rfkill_set_hw_state);
This page took 0.028407 seconds and 5 git commands to generate.