aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/firewire/ohci.c
diff options
context:
space:
mode:
authorStefan Richter <stefanr@s5r6.in-berlin.de>2010-07-08 10:09:06 -0400
committerStefan Richter <stefanr@s5r6.in-berlin.de>2010-07-13 03:58:27 -0400
commit02d37bed188c500ee7afb0a2dc6b65a80704c58e (patch)
treea019891672a1505e35eb15fa2621caffecff2c80 /drivers/firewire/ohci.c
parent8b4f70ba4967cae90d128857af1382026a24230a (diff)
firewire: core: integrate software-forced bus resets with bus management
Bus resets which are triggered - by the kernel drivers after updates of the local nodes' config ROM, - by userspace software via ioctl shall be deferred until after >=2 seconds after the last bus reset. If multiple modifications of the local nodes' config ROM happen in a row, only a single bus reset should happen after them. When the local node's link goes from inactive to active or vice versa, and at the two occasions of bus resets mentioned above --- and if the current gap count differs from 63 --- the bus reset should be preceded by a PHY configuration packet that reaffirms the gap count. Otherwise a bus manager would have to reset the bus again right after that. This is necessary to promote bus stability, e.g. leave grace periods for allocations and reallocations of isochronous channels and bandwidth, SBP-2 reconnections etc.; see IEEE 1394 clause 8.2.1. This change implements all of the above by moving bus reset initiation into a delayed work (except for bus resets which are triggered by the bus manager workqueue job and are performed there immediately). It comes with a necessary addition to the card driver methods that allows to get the current gap count from PHY registers. Signed-off-by: Stefan Richter <stefanr@s5r6.in-berlin.de>
Diffstat (limited to 'drivers/firewire/ohci.c')
-rw-r--r--drivers/firewire/ohci.c53
1 files changed, 38 insertions, 15 deletions
diff --git a/drivers/firewire/ohci.c b/drivers/firewire/ohci.c
index a4bbf3dadf58..bb6a92bc9e6a 100644
--- a/drivers/firewire/ohci.c
+++ b/drivers/firewire/ohci.c
@@ -34,6 +34,7 @@
34#include <linux/mm.h> 34#include <linux/mm.h>
35#include <linux/module.h> 35#include <linux/module.h>
36#include <linux/moduleparam.h> 36#include <linux/moduleparam.h>
37#include <linux/mutex.h>
37#include <linux/pci.h> 38#include <linux/pci.h>
38#include <linux/pci_ids.h> 39#include <linux/pci_ids.h>
39#include <linux/spinlock.h> 40#include <linux/spinlock.h>
@@ -182,6 +183,8 @@ struct fw_ohci {
182 */ 183 */
183 spinlock_t lock; 184 spinlock_t lock;
184 185
186 struct mutex phy_reg_mutex;
187
185 struct ar_context ar_request_ctx; 188 struct ar_context ar_request_ctx;
186 struct ar_context ar_response_ctx; 189 struct ar_context ar_response_ctx;
187 struct context at_request_ctx; 190 struct context at_request_ctx;
@@ -517,13 +520,10 @@ static int write_phy_reg(const struct fw_ohci *ohci, int addr, u32 val)
517 return -EBUSY; 520 return -EBUSY;
518} 521}
519 522
520static int ohci_update_phy_reg(struct fw_card *card, int addr, 523static int update_phy_reg(struct fw_ohci *ohci, int addr,
521 int clear_bits, int set_bits) 524 int clear_bits, int set_bits)
522{ 525{
523 struct fw_ohci *ohci = fw_ohci(card); 526 int ret = read_phy_reg(ohci, addr);
524 int ret;
525
526 ret = read_phy_reg(ohci, addr);
527 if (ret < 0) 527 if (ret < 0)
528 return ret; 528 return ret;
529 529
@@ -541,13 +541,38 @@ static int read_paged_phy_reg(struct fw_ohci *ohci, int page, int addr)
541{ 541{
542 int ret; 542 int ret;
543 543
544 ret = ohci_update_phy_reg(&ohci->card, 7, PHY_PAGE_SELECT, page << 5); 544 ret = update_phy_reg(ohci, 7, PHY_PAGE_SELECT, page << 5);
545 if (ret < 0) 545 if (ret < 0)
546 return ret; 546 return ret;
547 547
548 return read_phy_reg(ohci, addr); 548 return read_phy_reg(ohci, addr);
549} 549}
550 550
551static int ohci_read_phy_reg(struct fw_card *card, int addr)
552{
553 struct fw_ohci *ohci = fw_ohci(card);
554 int ret;
555
556 mutex_lock(&ohci->phy_reg_mutex);
557 ret = read_phy_reg(ohci, addr);
558 mutex_unlock(&ohci->phy_reg_mutex);
559
560 return ret;
561}
562
563static int ohci_update_phy_reg(struct fw_card *card, int addr,
564 int clear_bits, int set_bits)
565{
566 struct fw_ohci *ohci = fw_ohci(card);
567 int ret;
568
569 mutex_lock(&ohci->phy_reg_mutex);
570 ret = update_phy_reg(ohci, addr, clear_bits, set_bits);
571 mutex_unlock(&ohci->phy_reg_mutex);
572
573 return ret;
574}
575
551static int ar_context_add_page(struct ar_context *ctx) 576static int ar_context_add_page(struct ar_context *ctx)
552{ 577{
553 struct device *dev = ctx->ohci->card.device; 578 struct device *dev = ctx->ohci->card.device;
@@ -1676,7 +1701,7 @@ static int configure_1394a_enhancements(struct fw_ohci *ohci)
1676 clear = PHY_ENABLE_ACCEL | PHY_ENABLE_MULTI; 1701 clear = PHY_ENABLE_ACCEL | PHY_ENABLE_MULTI;
1677 set = 0; 1702 set = 0;
1678 } 1703 }
1679 ret = ohci_update_phy_reg(&ohci->card, 5, clear, set); 1704 ret = update_phy_reg(ohci, 5, clear, set);
1680 if (ret < 0) 1705 if (ret < 0)
1681 return ret; 1706 return ret;
1682 1707
@@ -1856,12 +1881,8 @@ static int ohci_enable(struct fw_card *card,
1856 OHCI1394_HCControl_BIBimageValid); 1881 OHCI1394_HCControl_BIBimageValid);
1857 flush_writes(ohci); 1882 flush_writes(ohci);
1858 1883
1859 /* 1884 /* We are ready to go, reset bus to finish initialization. */
1860 * We are ready to go, initiate bus reset to finish the 1885 fw_schedule_bus_reset(&ohci->card, false, true);
1861 * initialization.
1862 */
1863
1864 fw_core_initiate_bus_reset(&ohci->card, 1);
1865 1886
1866 return 0; 1887 return 0;
1867} 1888}
@@ -1936,7 +1957,7 @@ static int ohci_set_config_rom(struct fw_card *card,
1936 * takes effect. 1957 * takes effect.
1937 */ 1958 */
1938 if (ret == 0) 1959 if (ret == 0)
1939 fw_core_initiate_bus_reset(&ohci->card, 1); 1960 fw_schedule_bus_reset(&ohci->card, true, true);
1940 else 1961 else
1941 dma_free_coherent(ohci->card.device, CONFIG_ROM_SIZE, 1962 dma_free_coherent(ohci->card.device, CONFIG_ROM_SIZE,
1942 next_config_rom, next_config_rom_bus); 1963 next_config_rom, next_config_rom_bus);
@@ -2570,6 +2591,7 @@ static int ohci_queue_iso(struct fw_iso_context *base,
2570 2591
2571static const struct fw_card_driver ohci_driver = { 2592static const struct fw_card_driver ohci_driver = {
2572 .enable = ohci_enable, 2593 .enable = ohci_enable,
2594 .read_phy_reg = ohci_read_phy_reg,
2573 .update_phy_reg = ohci_update_phy_reg, 2595 .update_phy_reg = ohci_update_phy_reg,
2574 .set_config_rom = ohci_set_config_rom, 2596 .set_config_rom = ohci_set_config_rom,
2575 .send_request = ohci_send_request, 2597 .send_request = ohci_send_request,
@@ -2645,6 +2667,7 @@ static int __devinit pci_probe(struct pci_dev *dev,
2645 pci_set_drvdata(dev, ohci); 2667 pci_set_drvdata(dev, ohci);
2646 2668
2647 spin_lock_init(&ohci->lock); 2669 spin_lock_init(&ohci->lock);
2670 mutex_init(&ohci->phy_reg_mutex);
2648 2671
2649 tasklet_init(&ohci->bus_reset_tasklet, 2672 tasklet_init(&ohci->bus_reset_tasklet,
2650 bus_reset_tasklet, (unsigned long)ohci); 2673 bus_reset_tasklet, (unsigned long)ohci);