Search Linux Wireless

Re: [PATCH 3/5] ath10k: make warm reset a bit safer and faster

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 9 October 2014 10:22, Michal Kazior <michal.kazior@xxxxxxxxx> wrote:
> One of the problems with warm reset I've found is
> that it must be guaranteed that copy engine
> registers are not being accessed while being
> reset. Otherwise in worst case scenario the host
> may lock up.
>
> Instead of using sleeps and hoping the device is
> operational in some arbitrary timeframes use
> firmware indication register.
>
> As a side effect this makes driver
> boot/stop/recovery faster.
>
> Signed-off-by: Michal Kazior <michal.kazior@xxxxxxxxx>
[...]
> +static int ath10k_pci_warm_reset(struct ath10k *ar)
> +{
> +       int ret;
> +
> +       ath10k_dbg(ar, ATH10K_DBG_BOOT, "boot warm reset\n");
>
> -       /* debug */
> -       val = ath10k_pci_read32(ar, SOC_CORE_BASE_ADDRESS +
> -                               PCIE_INTR_CAUSE_ADDRESS);
> -       ath10k_dbg(ar, ATH10K_DBG_BOOT, "boot host cpu intr cause: 0x%08x\n",
> -                  val);
> +       spin_lock_bh(&ar->data_lock);
> +       ar->stats.fw_warm_reset_counter++;
> +       spin_unlock_bh(&ar->data_lock);
>
> -       val = ath10k_pci_read32(ar, SOC_CORE_BASE_ADDRESS +
> -                               CPU_INTR_ADDRESS);
> -       ath10k_dbg(ar, ATH10K_DBG_BOOT, "boot target cpu intr cause: 0x%08x\n",
> -                  val);
> +       ath10k_pci_irq_disable(ar);
>
> -       /* CPU warm reset */
> -       val = ath10k_pci_read32(ar, RTC_SOC_BASE_ADDRESS +
> -                               SOC_RESET_CONTROL_ADDRESS);
> -       ath10k_pci_write32(ar, RTC_SOC_BASE_ADDRESS + SOC_RESET_CONTROL_ADDRESS,
> -                          val | SOC_RESET_CONTROL_CPU_WARM_RST_MASK);
> +       /* Make sure the target CPU is not doing anything dangerous, e.g. if it
> +        * were to access copy engine while host performs copy engine reset
> +        * then it is possible for the device to confuse pci-e controller to
> +        * the point of bringing host system to a complete stop (i.e. hang).
> +        */
> +       ath10k_pci_warm_reset_si0(ar);
> +       ath10k_pci_warm_reset_cpu(ar);
> +       ath10k_pci_wait_for_target_init(ar);

Since warm_reset now calls wait_for_target_init (and thus can report a
target register dump on crash) and is called in pci_probe CE must be
initialized (which isn't the case in the code now). This can lead to
system crash on very early firmware crash during probing. Kudos to
Janusz for finding this out!

I'll respin a v2 later.


Michał
--
To unsubscribe from this list: send the line "unsubscribe linux-wireless" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html




[Index of Archives]     [Linux Host AP]     [ATH6KL]     [Linux Wireless Personal Area Network]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [Linux Kernel]     [IDE]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite Hiking]     [MIPS Linux]     [ARM Linux]     [Linux RAID]

  Powered by Linux