iwlwifi: move the bus configuration to transport
All the bus configuration is now done in the transport allocation fucntion. Signed-off-by: Emmanuel Grumbach <emmanuel.grumbach@intel.com> Signed-off-by: Wey-Yi Guy <wey-yi.w.guy@intel.com>
This commit is contained in:
committed by
Wey-Yi Guy
parent
b52e7ea109
commit
a42a184458
@@ -148,7 +148,6 @@ struct iwl_bus_ops {
|
|||||||
* @shrd - pointer to iwl_shared which holds shared data from the upper layer
|
* @shrd - pointer to iwl_shared which holds shared data from the upper layer
|
||||||
* NB: for the time being this needs to be set by the upper layer since
|
* NB: for the time being this needs to be set by the upper layer since
|
||||||
* it allocates the shared data
|
* it allocates the shared data
|
||||||
* @irq - the irq number for the device
|
|
||||||
* @reg_lock - protect hw register access
|
* @reg_lock - protect hw register access
|
||||||
*/
|
*/
|
||||||
struct iwl_bus {
|
struct iwl_bus {
|
||||||
@@ -156,7 +155,6 @@ struct iwl_bus {
|
|||||||
const struct iwl_bus_ops *ops;
|
const struct iwl_bus_ops *ops;
|
||||||
struct iwl_shared *shrd;
|
struct iwl_shared *shrd;
|
||||||
|
|
||||||
unsigned int irq;
|
|
||||||
spinlock_t reg_lock;
|
spinlock_t reg_lock;
|
||||||
|
|
||||||
/* pointer to bus specific struct */
|
/* pointer to bus specific struct */
|
||||||
|
@@ -367,7 +367,6 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||||||
struct iwl_cfg *cfg = (struct iwl_cfg *)(ent->driver_data);
|
struct iwl_cfg *cfg = (struct iwl_cfg *)(ent->driver_data);
|
||||||
struct iwl_bus *bus;
|
struct iwl_bus *bus;
|
||||||
struct iwl_pci_bus *pci_bus;
|
struct iwl_pci_bus *pci_bus;
|
||||||
u16 pci_cmd;
|
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
bus = kzalloc(sizeof(*bus) + sizeof(*pci_bus), GFP_KERNEL);
|
bus = kzalloc(sizeof(*bus) + sizeof(*pci_bus), GFP_KERNEL);
|
||||||
@@ -382,7 +381,7 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||||||
dev_printk(KERN_ERR, &pdev->dev,
|
dev_printk(KERN_ERR, &pdev->dev,
|
||||||
"Couldn't allocate iwl_shared");
|
"Couldn't allocate iwl_shared");
|
||||||
err = -ENOMEM;
|
err = -ENOMEM;
|
||||||
goto out_no_pci;
|
goto out_free_bus;
|
||||||
}
|
}
|
||||||
|
|
||||||
bus->shrd->bus = bus;
|
bus->shrd->bus = bus;
|
||||||
@@ -391,82 +390,14 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||||||
|
|
||||||
pci_set_drvdata(pdev, bus);
|
pci_set_drvdata(pdev, bus);
|
||||||
|
|
||||||
/* W/A - seems to solve weird behavior. We need to remove this if we
|
|
||||||
* don't want to stay in L1 all the time. This wastes a lot of power */
|
|
||||||
pci_disable_link_state(pdev, PCIE_LINK_STATE_L0S | PCIE_LINK_STATE_L1 |
|
|
||||||
PCIE_LINK_STATE_CLKPM);
|
|
||||||
|
|
||||||
if (pci_enable_device(pdev)) {
|
|
||||||
err = -ENODEV;
|
|
||||||
goto out_no_pci;
|
|
||||||
}
|
|
||||||
|
|
||||||
pci_set_master(pdev);
|
|
||||||
|
|
||||||
err = pci_set_dma_mask(pdev, DMA_BIT_MASK(36));
|
|
||||||
if (!err)
|
|
||||||
err = pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(36));
|
|
||||||
if (err) {
|
|
||||||
err = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
|
|
||||||
if (!err)
|
|
||||||
err = pci_set_consistent_dma_mask(pdev,
|
|
||||||
DMA_BIT_MASK(32));
|
|
||||||
/* both attempts failed: */
|
|
||||||
if (err) {
|
|
||||||
dev_printk(KERN_ERR, bus->dev,
|
|
||||||
"No suitable DMA available.\n");
|
|
||||||
goto out_pci_disable_device;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
err = pci_request_regions(pdev, DRV_NAME);
|
|
||||||
if (err) {
|
|
||||||
dev_printk(KERN_ERR, bus->dev, "pci_request_regions failed");
|
|
||||||
goto out_pci_disable_device;
|
|
||||||
}
|
|
||||||
|
|
||||||
pci_bus->hw_base = pci_iomap(pdev, 0, 0);
|
|
||||||
if (!pci_bus->hw_base) {
|
|
||||||
dev_printk(KERN_ERR, bus->dev, "pci_iomap failed");
|
|
||||||
err = -ENODEV;
|
|
||||||
goto out_pci_release_regions;
|
|
||||||
}
|
|
||||||
|
|
||||||
dev_printk(KERN_INFO, &pdev->dev,
|
|
||||||
"pci_resource_len = 0x%08llx\n",
|
|
||||||
(unsigned long long) pci_resource_len(pdev, 0));
|
|
||||||
dev_printk(KERN_INFO, &pdev->dev,
|
|
||||||
"pci_resource_base = %p\n", pci_bus->hw_base);
|
|
||||||
|
|
||||||
dev_printk(KERN_INFO, &pdev->dev,
|
|
||||||
"HW Revision ID = 0x%X\n", pdev->revision);
|
|
||||||
|
|
||||||
/* We disable the RETRY_TIMEOUT register (0x41) to keep
|
|
||||||
* PCI Tx retries from interfering with C3 CPU state */
|
|
||||||
pci_write_config_byte(pdev, PCI_CFG_RETRY_TIMEOUT, 0x00);
|
|
||||||
|
|
||||||
err = pci_enable_msi(pdev);
|
|
||||||
if (err)
|
|
||||||
dev_printk(KERN_ERR, &pdev->dev,
|
|
||||||
"pci_enable_msi failed(0X%x)", err);
|
|
||||||
|
|
||||||
/* TODO: Move this away, not needed if not MSI */
|
|
||||||
/* enable rfkill interrupt: hw bug w/a */
|
|
||||||
pci_read_config_word(pdev, PCI_COMMAND, &pci_cmd);
|
|
||||||
if (pci_cmd & PCI_COMMAND_INTX_DISABLE) {
|
|
||||||
pci_cmd &= ~PCI_COMMAND_INTX_DISABLE;
|
|
||||||
pci_write_config_word(pdev, PCI_COMMAND, pci_cmd);
|
|
||||||
}
|
|
||||||
|
|
||||||
bus->dev = &pdev->dev;
|
bus->dev = &pdev->dev;
|
||||||
bus->irq = pdev->irq;
|
|
||||||
bus->ops = &bus_ops_pci;
|
bus->ops = &bus_ops_pci;
|
||||||
|
|
||||||
#ifdef CONFIG_IWLWIFI_IDI
|
#ifdef CONFIG_IWLWIFI_IDI
|
||||||
trans(bus) = iwl_trans_idi_alloc(bus->shrd, pdev, ent);
|
trans(bus) = iwl_trans_idi_alloc(bus->shrd, pdev, ent);
|
||||||
if (trans(bus) == NULL) {
|
if (trans(bus) == NULL) {
|
||||||
err = -ENOMEM;
|
err = -ENOMEM;
|
||||||
goto out_disable_msi;
|
goto out_free_bus;
|
||||||
}
|
}
|
||||||
|
|
||||||
err = iwl_probe(bus, &trans_ops_idi, cfg);
|
err = iwl_probe(bus, &trans_ops_idi, cfg);
|
||||||
@@ -474,26 +405,20 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
|||||||
trans(bus) = iwl_trans_pcie_alloc(bus->shrd, pdev, ent);
|
trans(bus) = iwl_trans_pcie_alloc(bus->shrd, pdev, ent);
|
||||||
if (trans(bus) == NULL) {
|
if (trans(bus) == NULL) {
|
||||||
err = -ENOMEM;
|
err = -ENOMEM;
|
||||||
goto out_disable_msi;
|
goto out_free_bus;
|
||||||
}
|
}
|
||||||
|
|
||||||
err = iwl_probe(bus, &trans_ops_pcie, cfg);
|
err = iwl_probe(bus, &trans_ops_pcie, cfg);
|
||||||
#endif
|
#endif
|
||||||
if (err)
|
if (err)
|
||||||
goto out_free_trans;
|
goto out_free_trans;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
out_free_trans:
|
out_free_trans:
|
||||||
iwl_trans_free(trans(bus));
|
iwl_trans_free(trans(bus));
|
||||||
out_disable_msi:
|
|
||||||
pci_disable_msi(pdev);
|
|
||||||
pci_iounmap(pdev, pci_bus->hw_base);
|
|
||||||
out_pci_release_regions:
|
|
||||||
pci_set_drvdata(pdev, NULL);
|
pci_set_drvdata(pdev, NULL);
|
||||||
pci_release_regions(pdev);
|
out_free_bus:
|
||||||
out_pci_disable_device:
|
|
||||||
pci_disable_device(pdev);
|
|
||||||
out_no_pci:
|
|
||||||
kfree(bus->shrd);
|
kfree(bus->shrd);
|
||||||
kfree(bus);
|
kfree(bus);
|
||||||
return err;
|
return err;
|
||||||
@@ -502,18 +427,12 @@ out_no_pci:
|
|||||||
static void __devexit iwl_pci_remove(struct pci_dev *pdev)
|
static void __devexit iwl_pci_remove(struct pci_dev *pdev)
|
||||||
{
|
{
|
||||||
struct iwl_bus *bus = pci_get_drvdata(pdev);
|
struct iwl_bus *bus = pci_get_drvdata(pdev);
|
||||||
struct iwl_pci_bus *pci_bus = IWL_BUS_GET_PCI_BUS(bus);
|
|
||||||
struct pci_dev *pci_dev = IWL_BUS_GET_PCI_DEV(bus);
|
|
||||||
struct iwl_shared *shrd = bus->shrd;
|
struct iwl_shared *shrd = bus->shrd;
|
||||||
|
|
||||||
iwl_remove(shrd->priv);
|
iwl_remove(shrd->priv);
|
||||||
iwl_trans_free(shrd->trans);
|
iwl_trans_free(shrd->trans);
|
||||||
|
|
||||||
pci_disable_msi(pci_dev);
|
pci_set_drvdata(pdev, NULL);
|
||||||
pci_iounmap(pci_dev, pci_bus->hw_base);
|
|
||||||
pci_release_regions(pci_dev);
|
|
||||||
pci_disable_device(pci_dev);
|
|
||||||
pci_set_drvdata(pci_dev, NULL);
|
|
||||||
|
|
||||||
kfree(bus->shrd);
|
kfree(bus->shrd);
|
||||||
kfree(bus);
|
kfree(bus);
|
||||||
|
@@ -211,6 +211,8 @@ struct iwl_tx_queue {
|
|||||||
* @txq_ctx_active_msk: what queue is active
|
* @txq_ctx_active_msk: what queue is active
|
||||||
* queue_stopped: tracks what queue is stopped
|
* queue_stopped: tracks what queue is stopped
|
||||||
* queue_stop_count: tracks what SW queue is stopped
|
* queue_stop_count: tracks what SW queue is stopped
|
||||||
|
* @pci_dev: basic pci-network driver stuff
|
||||||
|
* @hw_base: pci hardware address support
|
||||||
*/
|
*/
|
||||||
struct iwl_trans_pcie {
|
struct iwl_trans_pcie {
|
||||||
struct iwl_rx_queue rxq;
|
struct iwl_rx_queue rxq;
|
||||||
@@ -241,6 +243,10 @@ struct iwl_trans_pcie {
|
|||||||
#define IWL_MAX_HW_QUEUES 32
|
#define IWL_MAX_HW_QUEUES 32
|
||||||
unsigned long queue_stopped[BITS_TO_LONGS(IWL_MAX_HW_QUEUES)];
|
unsigned long queue_stopped[BITS_TO_LONGS(IWL_MAX_HW_QUEUES)];
|
||||||
atomic_t queue_stop_count[4];
|
atomic_t queue_stop_count[4];
|
||||||
|
|
||||||
|
/* PCI bus related data */
|
||||||
|
struct pci_dev *pci_dev;
|
||||||
|
void __iomem *hw_base;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define IWL_TRANS_GET_PCIE_TRANS(_iwl_trans) \
|
#define IWL_TRANS_GET_PCIE_TRANS(_iwl_trans) \
|
||||||
|
@@ -60,6 +60,8 @@
|
|||||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*
|
*
|
||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
#include <linux/pci.h>
|
||||||
|
#include <linux/pci-aspm.h>
|
||||||
#include <linux/interrupt.h>
|
#include <linux/interrupt.h>
|
||||||
#include <linux/debugfs.h>
|
#include <linux/debugfs.h>
|
||||||
#include <linux/bitops.h>
|
#include <linux/bitops.h>
|
||||||
@@ -1042,7 +1044,7 @@ static void iwl_trans_pcie_stop_device(struct iwl_trans *trans)
|
|||||||
spin_unlock_irqrestore(&trans->shrd->lock, flags);
|
spin_unlock_irqrestore(&trans->shrd->lock, flags);
|
||||||
|
|
||||||
/* wait to make sure we flush pending tasklet*/
|
/* wait to make sure we flush pending tasklet*/
|
||||||
synchronize_irq(bus(trans)->irq);
|
synchronize_irq(trans->irq);
|
||||||
tasklet_kill(&trans_pcie->irq_tasklet);
|
tasklet_kill(&trans_pcie->irq_tasklet);
|
||||||
|
|
||||||
/* stop and reset the on-board processor */
|
/* stop and reset the on-board processor */
|
||||||
@@ -1246,10 +1248,10 @@ static int iwl_trans_pcie_request_irq(struct iwl_trans *trans)
|
|||||||
|
|
||||||
iwl_alloc_isr_ict(trans);
|
iwl_alloc_isr_ict(trans);
|
||||||
|
|
||||||
err = request_irq(bus(trans)->irq, iwl_isr_ict, IRQF_SHARED,
|
err = request_irq(trans->irq, iwl_isr_ict, IRQF_SHARED,
|
||||||
DRV_NAME, trans);
|
DRV_NAME, trans);
|
||||||
if (err) {
|
if (err) {
|
||||||
IWL_ERR(trans, "Error allocating IRQ %d\n", bus(trans)->irq);
|
IWL_ERR(trans, "Error allocating IRQ %d\n", trans->irq);
|
||||||
iwl_free_isr_ict(trans);
|
iwl_free_isr_ict(trans);
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
@@ -1299,13 +1301,22 @@ static int iwl_trans_pcie_reclaim(struct iwl_trans *trans, int sta_id, int tid,
|
|||||||
|
|
||||||
static void iwl_trans_pcie_free(struct iwl_trans *trans)
|
static void iwl_trans_pcie_free(struct iwl_trans *trans)
|
||||||
{
|
{
|
||||||
|
struct iwl_trans_pcie *trans_pcie =
|
||||||
|
IWL_TRANS_GET_PCIE_TRANS(trans);
|
||||||
|
|
||||||
iwl_calib_free_results(trans);
|
iwl_calib_free_results(trans);
|
||||||
iwl_trans_pcie_tx_free(trans);
|
iwl_trans_pcie_tx_free(trans);
|
||||||
#ifndef CONFIG_IWLWIFI_IDI
|
#ifndef CONFIG_IWLWIFI_IDI
|
||||||
iwl_trans_pcie_rx_free(trans);
|
iwl_trans_pcie_rx_free(trans);
|
||||||
#endif
|
#endif
|
||||||
free_irq(bus(trans)->irq, trans);
|
free_irq(trans->irq, trans);
|
||||||
iwl_free_isr_ict(trans);
|
iwl_free_isr_ict(trans);
|
||||||
|
|
||||||
|
pci_disable_msi(trans_pcie->pci_dev);
|
||||||
|
pci_iounmap(trans_pcie->pci_dev, trans_pcie->hw_base);
|
||||||
|
pci_release_regions(trans_pcie->pci_dev);
|
||||||
|
pci_disable_device(trans_pcie->pci_dev);
|
||||||
|
|
||||||
trans->shrd->trans = NULL;
|
trans->shrd->trans = NULL;
|
||||||
kfree(trans);
|
kfree(trans);
|
||||||
}
|
}
|
||||||
@@ -1374,30 +1385,6 @@ static void iwl_trans_pcie_wake_any_queue(struct iwl_trans *trans,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const struct iwl_trans_ops trans_ops_pcie;
|
|
||||||
|
|
||||||
struct iwl_trans *iwl_trans_pcie_alloc(struct iwl_shared *shrd,
|
|
||||||
struct pci_dev *pdev,
|
|
||||||
const struct pci_device_id *ent)
|
|
||||||
{
|
|
||||||
struct iwl_trans_pcie *trans_pcie;
|
|
||||||
struct iwl_trans *iwl_trans = kzalloc(sizeof(struct iwl_trans) +
|
|
||||||
sizeof(struct iwl_trans_pcie),
|
|
||||||
GFP_KERNEL);
|
|
||||||
|
|
||||||
if (WARN_ON(!iwl_trans))
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
trans_pcie = IWL_TRANS_GET_PCIE_TRANS(iwl_trans);
|
|
||||||
|
|
||||||
iwl_trans->ops = &trans_ops_pcie;
|
|
||||||
iwl_trans->shrd = shrd;
|
|
||||||
trans_pcie->trans = iwl_trans;
|
|
||||||
spin_lock_init(&iwl_trans->hcmd_lock);
|
|
||||||
|
|
||||||
return iwl_trans;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void iwl_trans_pcie_stop_queue(struct iwl_trans *trans, int txq_id,
|
static void iwl_trans_pcie_stop_queue(struct iwl_trans *trans, int txq_id,
|
||||||
const char *msg)
|
const char *msg)
|
||||||
{
|
{
|
||||||
@@ -1949,3 +1936,129 @@ const struct iwl_trans_ops trans_ops_pcie = {
|
|||||||
.resume = iwl_trans_pcie_resume,
|
.resume = iwl_trans_pcie_resume,
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* TODO: remove this hack - will be possible when all the io{write/read} ops
|
||||||
|
* will be done through the transport
|
||||||
|
*/
|
||||||
|
struct iwl_pci_bus {
|
||||||
|
/* basic pci-network driver stuff */
|
||||||
|
struct pci_dev *pci_dev;
|
||||||
|
|
||||||
|
/* pci hardware address support */
|
||||||
|
void __iomem *hw_base;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define IWL_BUS_GET_PCI_BUS(_iwl_bus) \
|
||||||
|
((struct iwl_pci_bus *) ((_iwl_bus)->bus_specific))
|
||||||
|
|
||||||
|
/* PCI registers */
|
||||||
|
#define PCI_CFG_RETRY_TIMEOUT 0x041
|
||||||
|
|
||||||
|
struct iwl_trans *iwl_trans_pcie_alloc(struct iwl_shared *shrd,
|
||||||
|
struct pci_dev *pdev,
|
||||||
|
const struct pci_device_id *ent)
|
||||||
|
{
|
||||||
|
struct iwl_pci_bus *iwl_pci_bus = IWL_BUS_GET_PCI_BUS(shrd->bus);
|
||||||
|
struct iwl_trans_pcie *trans_pcie;
|
||||||
|
struct iwl_trans *trans;
|
||||||
|
u16 pci_cmd;
|
||||||
|
int err;
|
||||||
|
|
||||||
|
trans = kzalloc(sizeof(struct iwl_trans) +
|
||||||
|
sizeof(struct iwl_trans_pcie), GFP_KERNEL);
|
||||||
|
|
||||||
|
if (WARN_ON(!trans))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans);
|
||||||
|
|
||||||
|
trans->ops = &trans_ops_pcie;
|
||||||
|
trans->shrd = shrd;
|
||||||
|
trans_pcie->trans = trans;
|
||||||
|
spin_lock_init(&trans->hcmd_lock);
|
||||||
|
|
||||||
|
/* W/A - seems to solve weird behavior. We need to remove this if we
|
||||||
|
* don't want to stay in L1 all the time. This wastes a lot of power */
|
||||||
|
pci_disable_link_state(pdev, PCIE_LINK_STATE_L0S | PCIE_LINK_STATE_L1 |
|
||||||
|
PCIE_LINK_STATE_CLKPM);
|
||||||
|
|
||||||
|
if (pci_enable_device(pdev)) {
|
||||||
|
err = -ENODEV;
|
||||||
|
goto out_no_pci;
|
||||||
|
}
|
||||||
|
|
||||||
|
pci_set_master(pdev);
|
||||||
|
|
||||||
|
err = pci_set_dma_mask(pdev, DMA_BIT_MASK(36));
|
||||||
|
if (!err)
|
||||||
|
err = pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(36));
|
||||||
|
if (err) {
|
||||||
|
err = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
|
||||||
|
if (!err)
|
||||||
|
err = pci_set_consistent_dma_mask(pdev,
|
||||||
|
DMA_BIT_MASK(32));
|
||||||
|
/* both attempts failed: */
|
||||||
|
if (err) {
|
||||||
|
dev_printk(KERN_ERR, &pdev->dev,
|
||||||
|
"No suitable DMA available.\n");
|
||||||
|
goto out_pci_disable_device;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
err = pci_request_regions(pdev, DRV_NAME);
|
||||||
|
if (err) {
|
||||||
|
dev_printk(KERN_ERR, &pdev->dev, "pci_request_regions failed");
|
||||||
|
goto out_pci_disable_device;
|
||||||
|
}
|
||||||
|
|
||||||
|
trans_pcie->hw_base = pci_iomap(pdev, 0, 0);
|
||||||
|
if (!trans_pcie->hw_base) {
|
||||||
|
dev_printk(KERN_ERR, &pdev->dev, "pci_iomap failed");
|
||||||
|
err = -ENODEV;
|
||||||
|
goto out_pci_release_regions;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* TODO: remove this hack */
|
||||||
|
iwl_pci_bus->hw_base = trans_pcie->hw_base;
|
||||||
|
|
||||||
|
dev_printk(KERN_INFO, &pdev->dev,
|
||||||
|
"pci_resource_len = 0x%08llx\n",
|
||||||
|
(unsigned long long) pci_resource_len(pdev, 0));
|
||||||
|
dev_printk(KERN_INFO, &pdev->dev,
|
||||||
|
"pci_resource_base = %p\n", trans_pcie->hw_base);
|
||||||
|
|
||||||
|
dev_printk(KERN_INFO, &pdev->dev,
|
||||||
|
"HW Revision ID = 0x%X\n", pdev->revision);
|
||||||
|
|
||||||
|
/* We disable the RETRY_TIMEOUT register (0x41) to keep
|
||||||
|
* PCI Tx retries from interfering with C3 CPU state */
|
||||||
|
pci_write_config_byte(pdev, PCI_CFG_RETRY_TIMEOUT, 0x00);
|
||||||
|
|
||||||
|
err = pci_enable_msi(pdev);
|
||||||
|
if (err)
|
||||||
|
dev_printk(KERN_ERR, &pdev->dev,
|
||||||
|
"pci_enable_msi failed(0X%x)", err);
|
||||||
|
|
||||||
|
trans->dev = &pdev->dev;
|
||||||
|
trans->irq = pdev->irq;
|
||||||
|
trans_pcie->pci_dev = pdev;
|
||||||
|
|
||||||
|
/* TODO: Move this away, not needed if not MSI */
|
||||||
|
/* enable rfkill interrupt: hw bug w/a */
|
||||||
|
pci_read_config_word(pdev, PCI_COMMAND, &pci_cmd);
|
||||||
|
if (pci_cmd & PCI_COMMAND_INTX_DISABLE) {
|
||||||
|
pci_cmd &= ~PCI_COMMAND_INTX_DISABLE;
|
||||||
|
pci_write_config_word(pdev, PCI_COMMAND, pci_cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
return trans;
|
||||||
|
|
||||||
|
out_pci_release_regions:
|
||||||
|
pci_release_regions(pdev);
|
||||||
|
out_pci_disable_device:
|
||||||
|
pci_disable_device(pdev);
|
||||||
|
out_no_pci:
|
||||||
|
kfree(trans);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -228,6 +228,8 @@ struct iwl_calib_result {
|
|||||||
* @ops - pointer to iwl_trans_ops
|
* @ops - pointer to iwl_trans_ops
|
||||||
* @shrd - pointer to iwl_shared which holds shared data from the upper layer
|
* @shrd - pointer to iwl_shared which holds shared data from the upper layer
|
||||||
* @hcmd_lock: protects HCMD
|
* @hcmd_lock: protects HCMD
|
||||||
|
* @dev - pointer to struct device * that represents the device
|
||||||
|
* @irq - the irq number for the device
|
||||||
* @ucode_write_complete: indicates that the ucode has been copied.
|
* @ucode_write_complete: indicates that the ucode has been copied.
|
||||||
* @ucode_rt: run time ucode image
|
* @ucode_rt: run time ucode image
|
||||||
* @ucode_init: init ucode image
|
* @ucode_init: init ucode image
|
||||||
@@ -240,6 +242,9 @@ struct iwl_trans {
|
|||||||
struct iwl_shared *shrd;
|
struct iwl_shared *shrd;
|
||||||
spinlock_t hcmd_lock;
|
spinlock_t hcmd_lock;
|
||||||
|
|
||||||
|
struct device *dev;
|
||||||
|
unsigned int irq;
|
||||||
|
|
||||||
u8 ucode_write_complete; /* the image write is complete */
|
u8 ucode_write_complete; /* the image write is complete */
|
||||||
struct fw_img ucode_rt;
|
struct fw_img ucode_rt;
|
||||||
struct fw_img ucode_init;
|
struct fw_img ucode_init;
|
||||||
|
Reference in New Issue
Block a user