]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
iwlwifi: pcie: add fake RF-kill to debugfs
authorJohannes Berg <johannes.berg@intel.com>
Tue, 25 Apr 2017 07:58:25 +0000 (09:58 +0200)
committerLuca Coelho <luciano.coelho@intel.com>
Thu, 22 Jun 2017 21:13:01 +0000 (00:13 +0300)
In order to debug "hardware" RF-kill flows, add a low-level hook to
allow changing the "hardware" RF-kill from debugfs.

Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Signed-off-by: Luca Coelho <luciano.coelho@intel.com>
drivers/net/wireless/intel/iwlwifi/pcie/internal.h
drivers/net/wireless/intel/iwlwifi/pcie/rx.c
drivers/net/wireless/intel/iwlwifi/pcie/trans.c

index 4b7be7ba978021c7f300bf7be6147a5ac6f3884f..17bd9561448397cabf1472652cc9b95e65628913 100644 (file)
@@ -404,6 +404,7 @@ struct iwl_trans_pcie {
        int ict_index;
        bool use_ict;
        bool is_down;
+       bool debug_rfkill;
        struct isr_statistics isr_stats;
 
        spinlock_t irq_lock;
@@ -675,6 +676,8 @@ static inline void iwl_enable_rfkill_int(struct iwl_trans *trans)
        }
 }
 
+void iwl_pcie_handle_rfkill_irq(struct iwl_trans *trans);
+
 static inline void iwl_wake_queue(struct iwl_trans *trans,
                                  struct iwl_txq *txq)
 {
@@ -713,7 +716,12 @@ static inline u8 get_cmd_index(struct iwl_txq *q, u32 index)
 
 static inline bool iwl_is_rfkill_set(struct iwl_trans *trans)
 {
-       lockdep_assert_held(&IWL_TRANS_GET_PCIE_TRANS(trans)->mutex);
+       struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
+
+       lockdep_assert_held(&trans_pcie->mutex);
+
+       if (trans_pcie->debug_rfkill)
+               return true;
 
        return !(iwl_read32(trans, CSR_GP_CNTRL) &
                CSR_GP_CNTRL_REG_FLAG_HW_RF_KILL_SW);
index c27d6f711abf70a12ee842332cde026d63dc7581..b6b04e72521e429d68e1b4ccba6af0f781625980 100644 (file)
@@ -1509,7 +1509,7 @@ static u32 iwl_pcie_int_cause_ict(struct iwl_trans *trans)
        return inta;
 }
 
-static void iwl_pcie_handle_rfkill_irq(struct iwl_trans *trans)
+void iwl_pcie_handle_rfkill_irq(struct iwl_trans *trans)
 {
        struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
        struct isr_statistics *isr_stats = &trans_pcie->isr_stats;
index a3c5d3b195ada5cd38399c4bc26c3035aeac5db2..6c4f8e377fb905036f0cd539b673d79373c2cf04 100644 (file)
@@ -2461,11 +2461,50 @@ static ssize_t iwl_dbgfs_fh_reg_read(struct file *file,
        return ret;
 }
 
+static ssize_t iwl_dbgfs_rfkill_read(struct file *file,
+                                    char __user *user_buf,
+                                    size_t count, loff_t *ppos)
+{
+       struct iwl_trans *trans = file->private_data;
+       struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
+       char buf[100];
+       int pos;
+
+       pos = scnprintf(buf, sizeof(buf), "debug: %d\nhw: %d\n",
+                       trans_pcie->debug_rfkill,
+                       !(iwl_read32(trans, CSR_GP_CNTRL) &
+                               CSR_GP_CNTRL_REG_FLAG_HW_RF_KILL_SW));
+
+       return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
+}
+
+static ssize_t iwl_dbgfs_rfkill_write(struct file *file,
+                                     const char __user *user_buf,
+                                     size_t count, loff_t *ppos)
+{
+       struct iwl_trans *trans = file->private_data;
+       struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
+       bool old = trans_pcie->debug_rfkill;
+       int ret;
+
+       ret = kstrtobool_from_user(user_buf, count, &trans_pcie->debug_rfkill);
+       if (ret)
+               return ret;
+       if (old == trans_pcie->debug_rfkill)
+               return count;
+       IWL_WARN(trans, "changing debug rfkill %d->%d\n",
+                old, trans_pcie->debug_rfkill);
+       iwl_pcie_handle_rfkill_irq(trans);
+
+       return count;
+}
+
 DEBUGFS_READ_WRITE_FILE_OPS(interrupt);
 DEBUGFS_READ_FILE_OPS(fh_reg);
 DEBUGFS_READ_FILE_OPS(rx_queue);
 DEBUGFS_READ_FILE_OPS(tx_queue);
 DEBUGFS_WRITE_FILE_OPS(csr);
+DEBUGFS_READ_WRITE_FILE_OPS(rfkill);
 
 /* Create the debugfs files and directories */
 int iwl_trans_pcie_dbgfs_register(struct iwl_trans *trans)
@@ -2477,6 +2516,7 @@ int iwl_trans_pcie_dbgfs_register(struct iwl_trans *trans)
        DEBUGFS_ADD_FILE(interrupt, dir, S_IWUSR | S_IRUSR);
        DEBUGFS_ADD_FILE(csr, dir, S_IWUSR);
        DEBUGFS_ADD_FILE(fh_reg, dir, S_IRUSR);
+       DEBUGFS_ADD_FILE(rfkill, dir, S_IWUSR | S_IRUSR);
        return 0;
 
 err: