Commit 96c55900 authored by Myron Stowe's avatar Myron Stowe Committed by Jesse Barnes

PCI: Pull PCI 'latency timer' setup up into the core

The 'latency timer' of PCI devices, both Type 0 and Type 1,
is setup in architecture-specific code [see: 'pcibios_set_master()'].
There are two approaches being taken by all the architectures - check
if the 'latency timer' is currently set between 16 and 255 and if not
bring it within bounds, or, do nothing (and then there is the
gratuitously different PA-RISC implementation).

There is nothing architecture-specific about PCI's 'latency timer' so
this patch pulls its setup functionality up into the PCI core by
creating a generic 'pcibios_set_master()' function using the '__weak'
attribute which can be used by all architectures as a default which,
if necessary, can then be over-ridden by architecture-specific code.

No functional change.
Signed-off-by: default avatarMyron Stowe <myron.stowe@redhat.com>
Signed-off-by: default avatarJesse Barnes <jbarnes@virtuousgeek.org>
parent 9cdce18d
...@@ -10,10 +10,6 @@ ...@@ -10,10 +10,6 @@
#define PCIBIOS_MIN_IO 0x00001000 #define PCIBIOS_MIN_IO 0x00001000
#define PCIBIOS_MIN_MEM 0x10000000 #define PCIBIOS_MIN_MEM 0x10000000
static inline void pcibios_set_master(struct pci_dev *dev)
{
/* No special bus mastering setup handling */
}
static inline void pcibios_penalize_isa_irq(int irq) static inline void pcibios_penalize_isa_irq(int irq)
{ {
/* We don't do dynamic PCI IRQ allocation */ /* We don't do dynamic PCI IRQ allocation */
......
...@@ -195,12 +195,6 @@ void __init pcibios_resource_survey(void) ...@@ -195,12 +195,6 @@ void __init pcibios_resource_survey(void)
pcibios_assign_resources(); pcibios_assign_resources();
} }
/*
* If we set up a device for bus mastering, we need to check the latency
* timer as certain crappy BIOSes forget to set it properly.
*/
unsigned int pcibios_max_latency = 255;
void pcibios_set_master(struct pci_dev *dev) void pcibios_set_master(struct pci_dev *dev)
{ {
u8 lat; u8 lat;
......
...@@ -26,8 +26,6 @@ extern unsigned int __nongpreldata pci_probe; ...@@ -26,8 +26,6 @@ extern unsigned int __nongpreldata pci_probe;
/* pci-frv.c */ /* pci-frv.c */
extern unsigned int pcibios_max_latency;
void pcibios_resource_survey(void); void pcibios_resource_survey(void);
/* pci-vdk.c */ /* pci-vdk.c */
......
...@@ -9,11 +9,6 @@ ...@@ -9,11 +9,6 @@
#define pcibios_assign_all_busses() 0 #define pcibios_assign_all_busses() 0
static inline void pcibios_set_master(struct pci_dev *dev)
{
/* No special bus mastering setup handling */
}
static inline void pcibios_penalize_isa_irq(int irq, int active) static inline void pcibios_penalize_isa_irq(int irq, int active)
{ {
/* We don't do dynamic PCI IRQ allocation */ /* We don't do dynamic PCI IRQ allocation */
......
...@@ -205,12 +205,6 @@ static int pcibios_enable_resources(struct pci_dev *dev, int mask) ...@@ -205,12 +205,6 @@ static int pcibios_enable_resources(struct pci_dev *dev, int mask)
return 0; return 0;
} }
/*
* If we set up a device for bus mastering, we need to check the latency
* timer as certain crappy BIOSes forget to set it properly.
*/
static unsigned int pcibios_max_latency = 255;
void pcibios_set_master(struct pci_dev *dev) void pcibios_set_master(struct pci_dev *dev)
{ {
u8 lat; u8 lat;
......
...@@ -213,12 +213,6 @@ void __init pcibios_resource_survey(void) ...@@ -213,12 +213,6 @@ void __init pcibios_resource_survey(void)
pcibios_allocate_resources(1); pcibios_allocate_resources(1);
} }
/*
* If we set up a device for bus mastering, we need to check the latency
* timer as certain crappy BIOSes forget to set it properly.
*/
unsigned int pcibios_max_latency = 255;
void pcibios_set_master(struct pci_dev *dev) void pcibios_set_master(struct pci_dev *dev)
{ {
u8 lat; u8 lat;
......
...@@ -31,8 +31,6 @@ extern unsigned int pci_probe; ...@@ -31,8 +31,6 @@ extern unsigned int pci_probe;
/* pci-asb2305.c */ /* pci-asb2305.c */
extern unsigned int pcibios_max_latency;
extern void pcibios_resource_survey(void); extern void pcibios_resource_survey(void);
/* pci.c */ /* pci.c */
......
...@@ -243,12 +243,6 @@ int pcibios_enable_device(struct pci_dev *dev, int mask) ...@@ -243,12 +243,6 @@ int pcibios_enable_device(struct pci_dev *dev, int mask)
return pci_enable_resources(dev, mask); return pci_enable_resources(dev, mask);
} }
/*
* If we set up a device for bus mastering, we need to check and set
* the latency timer as it may not be properly set.
*/
static unsigned int pcibios_max_latency = 255;
void pcibios_set_master(struct pci_dev *dev) void pcibios_set_master(struct pci_dev *dev)
{ {
u8 lat; u8 lat;
......
...@@ -44,8 +44,6 @@ enum pci_bf_sort_state { ...@@ -44,8 +44,6 @@ enum pci_bf_sort_state {
/* pci-i386.c */ /* pci-i386.c */
extern unsigned int pcibios_max_latency;
void pcibios_resource_survey(void); void pcibios_resource_survey(void);
void pcibios_set_cache_line_size(void); void pcibios_set_cache_line_size(void);
......
...@@ -254,12 +254,6 @@ void __init pcibios_resource_survey(void) ...@@ -254,12 +254,6 @@ void __init pcibios_resource_survey(void)
*/ */
fs_initcall(pcibios_assign_resources); fs_initcall(pcibios_assign_resources);
/*
* If we set up a device for bus mastering, we need to check the latency
* timer as certain crappy BIOSes forget to set it properly.
*/
unsigned int pcibios_max_latency = 255;
void pcibios_set_master(struct pci_dev *dev) void pcibios_set_master(struct pci_dev *dev)
{ {
u8 lat; u8 lat;
......
...@@ -88,6 +88,12 @@ enum pcie_bus_config_types pcie_bus_config = PCIE_BUS_TUNE_OFF; ...@@ -88,6 +88,12 @@ enum pcie_bus_config_types pcie_bus_config = PCIE_BUS_TUNE_OFF;
u8 pci_dfl_cache_line_size __devinitdata = L1_CACHE_BYTES >> 2; u8 pci_dfl_cache_line_size __devinitdata = L1_CACHE_BYTES >> 2;
u8 pci_cache_line_size; u8 pci_cache_line_size;
/*
* If we set up a device for bus mastering, we need to check the latency
* timer as certain BIOSes forget to set it properly.
*/
unsigned int pcibios_max_latency = 255;
/** /**
* pci_bus_max_busnr - returns maximum PCI bus number of given bus' children * pci_bus_max_busnr - returns maximum PCI bus number of given bus' children
* @bus: pointer to PCI bus structure to search * @bus: pointer to PCI bus structure to search
...@@ -2595,6 +2601,29 @@ static void __pci_set_master(struct pci_dev *dev, bool enable) ...@@ -2595,6 +2601,29 @@ static void __pci_set_master(struct pci_dev *dev, bool enable)
dev->is_busmaster = enable; dev->is_busmaster = enable;
} }
/**
* pcibios_set_master - enable PCI bus-mastering for device dev
* @dev: the PCI device to enable
*
* Enables PCI bus-mastering for the device. This is the default
* implementation. Architecture specific implementations can override
* this if necessary.
*/
void __weak pcibios_set_master(struct pci_dev *dev)
{
u8 lat;
pci_read_config_byte(dev, PCI_LATENCY_TIMER, &lat);
if (lat < 16)
lat = (64 <= pcibios_max_latency) ? 64 : pcibios_max_latency;
else if (lat > pcibios_max_latency)
lat = pcibios_max_latency;
else
return;
dev_printk(KERN_DEBUG, &dev->dev, "setting latency timer to %d\n", lat);
pci_write_config_byte(dev, PCI_LATENCY_TIMER, lat);
}
/** /**
* pci_set_master - enables bus-mastering for device dev * pci_set_master - enables bus-mastering for device dev
* @dev: the PCI device to enable * @dev: the PCI device to enable
......
...@@ -795,8 +795,11 @@ static inline int pci_is_managed(struct pci_dev *pdev) ...@@ -795,8 +795,11 @@ static inline int pci_is_managed(struct pci_dev *pdev)
} }
void pci_disable_device(struct pci_dev *dev); void pci_disable_device(struct pci_dev *dev);
extern unsigned int pcibios_max_latency;
void pci_set_master(struct pci_dev *dev); void pci_set_master(struct pci_dev *dev);
void pci_clear_master(struct pci_dev *dev); void pci_clear_master(struct pci_dev *dev);
int pci_set_pcie_reset_state(struct pci_dev *dev, enum pcie_reset_state state); int pci_set_pcie_reset_state(struct pci_dev *dev, enum pcie_reset_state state);
int pci_set_cacheline_size(struct pci_dev *dev); int pci_set_cacheline_size(struct pci_dev *dev);
#define HAVE_PCI_SET_MWI #define HAVE_PCI_SET_MWI
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment