Commit 772137b4 authored by Jody McIntyre's avatar Jody McIntyre

Adds a disable_irm option to ieee1394.ko which disables all Isochronous
Resource Manager functionality, useful to work around certain problems,
e.g. iPod detection.
Signed-off-by: default avatarJody McIntyre <scjody@modernduck.com>
parent 130c2a5f
...@@ -77,6 +77,30 @@ extern const char *hpsb_speedto_str[]; ...@@ -77,6 +77,30 @@ extern const char *hpsb_speedto_str[];
#define SELFID_PORT_NONE 0x0 #define SELFID_PORT_NONE 0x0
/* 1394a PHY bitmasks */
#define PHY_00_PHYSICAL_ID 0xFC
#define PHY_00_R 0x02 /* Root */
#define PHY_00_PS 0x01 /* Power Status*/
#define PHY_01_RHB 0x80 /* Root Hold-Off */
#define PHY_01_IBR 0x80 /* Initiate Bus Reset */
#define PHY_01_GAP_COUNT 0x3F
#define PHY_02_EXTENDED 0xE0 /* 0x7 for 1394a-compliant PHY */
#define PHY_02_TOTAL_PORTS 0x1F
#define PHY_03_MAX_SPEED 0xE0
#define PHY_03_DELAY 0x0F
#define PHY_04_LCTRL 0x80 /* Link Active Report Control */
#define PHY_04_CONTENDER 0x40
#define PHY_04_JITTER 0x38
#define PHY_04_PWR_CLASS 0x07 /* Power Class */
#define PHY_05_WATCHDOG 0x80
#define PHY_05_ISBR 0x40 /* Initiate Short Bus Reset */
#define PHY_05_LOOP 0x20 /* Loop Detect */
#define PHY_05_PWR_FAIL 0x10 /* Cable Power Failure Detect */
#define PHY_05_TIMEOUT 0x08 /* Arbitration State Machine Timeout */
#define PHY_05_PORT_EVENT 0x04 /* Port Event Detect */
#define PHY_05_ENAB_ACCEL 0x02 /* Enable Arbitration Acceleration */
#define PHY_05_ENAB_MULTI 0x01 /* Ena. Multispeed Packet Concatenation */
#include <asm/byteorder.h> #include <asm/byteorder.h>
#ifdef __BIG_ENDIAN_BITFIELD #ifdef __BIG_ENDIAN_BITFIELD
......
...@@ -56,6 +56,12 @@ static int disable_nodemgr = 0; ...@@ -56,6 +56,12 @@ static int disable_nodemgr = 0;
module_param(disable_nodemgr, int, 0444); module_param(disable_nodemgr, int, 0444);
MODULE_PARM_DESC(disable_nodemgr, "Disable nodemgr functionality."); MODULE_PARM_DESC(disable_nodemgr, "Disable nodemgr functionality.");
/* Disable Isochronous Resource Manager functionality */
int hpsb_disable_irm = 0;
module_param_named(disable_irm, hpsb_disable_irm, bool, 0);
MODULE_PARM_DESC(disable_irm,
"Disable Isochronous Resource Manager functionality.");
/* We are GPL, so treat us special */ /* We are GPL, so treat us special */
MODULE_LICENSE("GPL"); MODULE_LICENSE("GPL");
...@@ -1129,10 +1135,19 @@ static int __init ieee1394_init(void) ...@@ -1129,10 +1135,19 @@ static int __init ieee1394_init(void)
} }
if (disable_nodemgr) { if (disable_nodemgr) {
HPSB_INFO("nodemgr functionality disabled"); HPSB_INFO("nodemgr and IRM functionality disabled");
/* We shouldn't contend for IRM with nodemgr disabled, since
nodemgr implements functionality required of ieee1394a-2000
IRMs */
hpsb_disable_irm = 1;
return 0; return 0;
} }
if (hpsb_disable_irm) {
HPSB_INFO("IRM functionality disabled");
}
ret = init_ieee1394_nodemgr(); ret = init_ieee1394_nodemgr();
if (ret < 0) { if (ret < 0) {
HPSB_INFO("init nodemgr failed"); HPSB_INFO("init nodemgr failed");
...@@ -1219,6 +1234,7 @@ EXPORT_SYMBOL(hpsb_selfid_received); ...@@ -1219,6 +1234,7 @@ EXPORT_SYMBOL(hpsb_selfid_received);
EXPORT_SYMBOL(hpsb_selfid_complete); EXPORT_SYMBOL(hpsb_selfid_complete);
EXPORT_SYMBOL(hpsb_packet_sent); EXPORT_SYMBOL(hpsb_packet_sent);
EXPORT_SYMBOL(hpsb_packet_received); EXPORT_SYMBOL(hpsb_packet_received);
EXPORT_SYMBOL_GPL(hpsb_disable_irm);
/** ieee1394_transactions.c **/ /** ieee1394_transactions.c **/
EXPORT_SYMBOL(hpsb_get_tlabel); EXPORT_SYMBOL(hpsb_get_tlabel);
......
...@@ -218,6 +218,7 @@ static inline unsigned char ieee1394_file_to_instance(struct file *file) ...@@ -218,6 +218,7 @@ static inline unsigned char ieee1394_file_to_instance(struct file *file)
return file->f_dentry->d_inode->i_cindex; return file->f_dentry->d_inode->i_cindex;
} }
extern int hpsb_disable_irm;
/* Our sysfs bus entry */ /* Our sysfs bus entry */
extern struct bus_type ieee1394_bus_type; extern struct bus_type ieee1394_bus_type;
......
...@@ -23,6 +23,7 @@ ...@@ -23,6 +23,7 @@
#include "ieee1394_types.h" #include "ieee1394_types.h"
#include "ieee1394.h" #include "ieee1394.h"
#include "ieee1394_core.h"
#include "hosts.h" #include "hosts.h"
#include "ieee1394_transactions.h" #include "ieee1394_transactions.h"
#include "highlevel.h" #include "highlevel.h"
...@@ -1464,7 +1465,7 @@ static int nodemgr_check_irm_capability(struct hpsb_host *host, int cycles) ...@@ -1464,7 +1465,7 @@ static int nodemgr_check_irm_capability(struct hpsb_host *host, int cycles)
quadlet_t bc; quadlet_t bc;
int status; int status;
if (host->is_irm) if (hpsb_disable_irm || host->is_irm)
return 1; return 1;
status = hpsb_read(host, LOCAL_BUS | (host->irm_id), status = hpsb_read(host, LOCAL_BUS | (host->irm_id),
......
...@@ -482,7 +482,9 @@ static void ohci_initialize(struct ti_ohci *ohci) ...@@ -482,7 +482,9 @@ static void ohci_initialize(struct ti_ohci *ohci)
/* Put some defaults to these undefined bus options */ /* Put some defaults to these undefined bus options */
buf = reg_read(ohci, OHCI1394_BusOptions); buf = reg_read(ohci, OHCI1394_BusOptions);
buf |= 0xE0000000; /* Enable IRMC, CMC and ISC */ buf |= 0x60000000; /* Enable CMC and ISC */
if (!hpsb_disable_irm)
buf |= 0x80000000; /* Enable IRMC */
buf &= ~0x00ff0000; /* XXX: Set cyc_clk_acc to zero for now */ buf &= ~0x00ff0000; /* XXX: Set cyc_clk_acc to zero for now */
buf &= ~0x18000000; /* Disable PMC and BMC */ buf &= ~0x18000000; /* Disable PMC and BMC */
reg_write(ohci, OHCI1394_BusOptions, buf); reg_write(ohci, OHCI1394_BusOptions, buf);
...@@ -497,10 +499,12 @@ static void ohci_initialize(struct ti_ohci *ohci) ...@@ -497,10 +499,12 @@ static void ohci_initialize(struct ti_ohci *ohci)
reg_write(ohci, OHCI1394_LinkControlClear, 0xffffffff); reg_write(ohci, OHCI1394_LinkControlClear, 0xffffffff);
/* Enable cycle timer and cycle master and set the IRM /* Enable cycle timer and cycle master and set the IRM
* contender bit in our self ID packets. */ * contender bit in our self ID packets if appropriate. */
reg_write(ohci, OHCI1394_LinkControlSet, OHCI1394_LinkControl_CycleTimerEnable | reg_write(ohci, OHCI1394_LinkControlSet,
OHCI1394_LinkControl_CycleTimerEnable |
OHCI1394_LinkControl_CycleMaster); OHCI1394_LinkControl_CycleMaster);
set_phy_reg_mask(ohci, 4, 0xc0); set_phy_reg_mask(ohci, 4, PHY_04_LCTRL |
(hpsb_disable_irm ? 0 : PHY_04_CONTENDER));
/* Set up self-id dma buffer */ /* Set up self-id dma buffer */
reg_write(ohci, OHCI1394_SelfIDBuffer, ohci->selfid_buf_bus); reg_write(ohci, OHCI1394_SelfIDBuffer, ohci->selfid_buf_bus);
......
...@@ -384,7 +384,8 @@ static quadlet_t generate_own_selfid(struct ti_lynx *lynx, ...@@ -384,7 +384,8 @@ static quadlet_t generate_own_selfid(struct ti_lynx *lynx,
lsid = 0x80400000 | ((phyreg[0] & 0xfc) << 22); lsid = 0x80400000 | ((phyreg[0] & 0xfc) << 22);
lsid |= (phyreg[1] & 0x3f) << 16; /* gap count */ lsid |= (phyreg[1] & 0x3f) << 16; /* gap count */
lsid |= (phyreg[2] & 0xc0) << 8; /* max speed */ lsid |= (phyreg[2] & 0xc0) << 8; /* max speed */
lsid |= (phyreg[6] & 0x01) << 11; /* contender (phy dependent) */ if (!hpsb_disable_irm)
lsid |= (phyreg[6] & 0x01) << 11; /* contender (phy dependent) */
/* lsid |= 1 << 11; *//* set contender (hack) */ /* lsid |= 1 << 11; *//* set contender (hack) */
lsid |= (phyreg[6] & 0x10) >> 3; /* initiated reset */ lsid |= (phyreg[6] & 0x10) >> 3; /* initiated reset */
...@@ -1779,21 +1780,27 @@ static int __devinit add_card(struct pci_dev *dev, ...@@ -1779,21 +1780,27 @@ static int __devinit add_card(struct pci_dev *dev,
| LINK_CONTROL_TX_ASYNC_EN | LINK_CONTROL_RX_ASYNC_EN | LINK_CONTROL_TX_ASYNC_EN | LINK_CONTROL_RX_ASYNC_EN
| LINK_CONTROL_RESET_TX | LINK_CONTROL_RESET_RX); | LINK_CONTROL_RESET_TX | LINK_CONTROL_RESET_RX);
if (!lynx->phyic.reg_1394a) { if (!lynx->phyic.reg_1394a) {
/* attempt to enable contender bit -FIXME- would this work if (!hpsb_disable_irm) {
* elsewhere? */ /* attempt to enable contender bit -FIXME- would this
reg_set_bits(lynx, GPIO_CTRL_A, 0x1); * work elsewhere? */
reg_write(lynx, GPIO_DATA_BASE + 0x3c, 0x1); reg_set_bits(lynx, GPIO_CTRL_A, 0x1);
} else { reg_write(lynx, GPIO_DATA_BASE + 0x3c, 0x1);
/* set the contender and LCtrl bit in the extended PHY register }
* set. (Should check that bis 0,1,2 (=0xE0) is set } else {
* in register 2?) /* set the contender (if appropriate) and LCtrl bit in the
*/ * extended PHY register set. (Should check that PHY_02_EXTENDED
i = get_phy_reg(lynx, 4); * is set in register 2?)
if (i != -1) set_phy_reg(lynx, 4, i | 0xc0); */
} i = get_phy_reg(lynx, 4);
i |= PHY_04_LCTRL;
if (hpsb_disable_irm)
i &= !PHY_04_CONTENDER;
else
i |= PHY_04_CONTENDER;
if (i != -1) set_phy_reg(lynx, 4, i);
}
if (!skip_eeprom) if (!skip_eeprom)
{ {
i2c_adapter = bit_ops; i2c_adapter = bit_ops;
......
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