Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 104601
b: refs/heads/master
c: 3faefc8
h: refs/heads/master
i:
  104599: 5aef54b
v: v3
  • Loading branch information
Nate Case authored and Greg Kroah-Hartman committed Jul 21, 2008
1 parent e21ecc8 commit 99d96f5
Show file tree
Hide file tree
Showing 4 changed files with 105 additions and 19 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 6d243e5c76b632a94d54cac2fe7fe8c0b41cd482
refs/heads/master: 3faefc88c1a32b0b4a00b9089fab5d917996b16c
67 changes: 53 additions & 14 deletions trunk/drivers/usb/host/isp1760-hcd.c
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ struct isp1760_hcd {
unsigned i_thresh;
unsigned long reset_done;
unsigned long next_statechange;
unsigned int devflags;
};

static inline struct isp1760_hcd *hcd_to_priv(struct usb_hcd *hcd)
Expand Down Expand Up @@ -378,9 +379,31 @@ static int isp1760_hc_setup(struct usb_hcd *hcd)
{
struct isp1760_hcd *priv = hcd_to_priv(hcd);
int result;
u32 scratch;
u32 scratch, hwmode;

/* Setup HW Mode Control: This assumes a level active-low interrupt */
hwmode = HW_DATA_BUS_32BIT;

if (priv->devflags & ISP1760_FLAG_BUS_WIDTH_16)
hwmode &= ~HW_DATA_BUS_32BIT;
if (priv->devflags & ISP1760_FLAG_ANALOG_OC)
hwmode |= HW_ANA_DIGI_OC;
if (priv->devflags & ISP1760_FLAG_DACK_POL_HIGH)
hwmode |= HW_DACK_POL_HIGH;
if (priv->devflags & ISP1760_FLAG_DREQ_POL_HIGH)
hwmode |= HW_DREQ_POL_HIGH;

/*
* We have to set this first in case we're in 16-bit mode.
* Write it twice to ensure correct upper bits if switching
* to 16-bit mode.
*/
isp1760_writel(hwmode, hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(hwmode, hcd->regs + HC_HW_MODE_CTRL);

isp1760_writel(0xdeadbabe, hcd->regs + HC_SCRATCH_REG);
/* Change bus pattern */
scratch = isp1760_readl(hcd->regs + HC_CHIP_ID_REG);
scratch = isp1760_readl(hcd->regs + HC_SCRATCH_REG);
if (scratch != 0xdeadbabe) {
printk(KERN_ERR "ISP1760: Scratch test failed.\n");
Expand All @@ -403,17 +426,29 @@ static int isp1760_hc_setup(struct usb_hcd *hcd)

/* Step 11 passed */

isp1760_writel(INTERRUPT_ENABLE_MASK, hcd->regs + HC_INTERRUPT_REG);
isp1760_writel(INTERRUPT_ENABLE_MASK, hcd->regs + HC_INTERRUPT_ENABLE);
isp1760_info(priv, "bus width: %d, oc: %s\n",
(priv->devflags & ISP1760_FLAG_BUS_WIDTH_16) ?
16 : 32, (priv->devflags & ISP1760_FLAG_ANALOG_OC) ?
"analog" : "digital");

/* ATL reset */
scratch = isp1760_readl(hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(scratch | ALL_ATX_RESET, hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(hwmode | ALL_ATX_RESET, hcd->regs + HC_HW_MODE_CTRL);
mdelay(10);
isp1760_writel(scratch, hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(hwmode, hcd->regs + HC_HW_MODE_CTRL);

isp1760_writel(PORT1_POWER | PORT1_INIT2, hcd->regs + HC_PORT1_CTRL);
mdelay(10);
isp1760_writel(INTERRUPT_ENABLE_MASK, hcd->regs + HC_INTERRUPT_REG);
isp1760_writel(INTERRUPT_ENABLE_MASK, hcd->regs + HC_INTERRUPT_ENABLE);

/*
* PORT 1 Control register of the ISP1760 is the OTG control
* register on ISP1761.
*/
if (!(priv->devflags & ISP1760_FLAG_ISP1761) &&
!(priv->devflags & ISP1760_FLAG_PORT1_DIS)) {
isp1760_writel(PORT1_POWER | PORT1_INIT2,
hcd->regs + HC_PORT1_CTRL);
mdelay(10);
}

priv->hcs_params = isp1760_readl(hcd->regs + HC_HCSPARAMS);

Expand Down Expand Up @@ -453,8 +488,7 @@ static int isp1760_run(struct usb_hcd *hcd)
hcd->state = HC_STATE_RUNNING;
isp1760_enable_interrupts(hcd);
temp = isp1760_readl(hcd->regs + HC_HW_MODE_CTRL);
temp |= FINAL_HW_CONFIG;
isp1760_writel(temp, hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(temp | HW_GLOBAL_INTR_EN, hcd->regs + HC_HW_MODE_CTRL);

command = isp1760_readl(hcd->regs + HC_USBCMD);
command &= ~(CMD_LRESET|CMD_RESET);
Expand Down Expand Up @@ -2112,6 +2146,7 @@ static int isp1760_get_frame(struct usb_hcd *hcd)
static void isp1760_stop(struct usb_hcd *hcd)
{
struct isp1760_hcd *priv = hcd_to_priv(hcd);
u32 temp;

isp1760_hub_control(hcd, ClearPortFeature, USB_PORT_FEAT_POWER, 1,
NULL, 0);
Expand All @@ -2120,18 +2155,20 @@ static void isp1760_stop(struct usb_hcd *hcd)
spin_lock_irq(&priv->lock);
ehci_reset(priv);
/* Disable IRQ */
isp1760_writel(HW_DATA_BUS_32BIT, hcd->regs + HC_HW_MODE_CTRL);
temp = isp1760_readl(hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(temp &= ~HW_GLOBAL_INTR_EN, hcd->regs + HC_HW_MODE_CTRL);
spin_unlock_irq(&priv->lock);

isp1760_writel(0, hcd->regs + HC_CONFIGFLAG);
}

static void isp1760_shutdown(struct usb_hcd *hcd)
{
u32 command;
u32 command, temp;

isp1760_stop(hcd);
isp1760_writel(HW_DATA_BUS_32BIT, hcd->regs + HC_HW_MODE_CTRL);
temp = isp1760_readl(hcd->regs + HC_HW_MODE_CTRL);
isp1760_writel(temp &= ~HW_GLOBAL_INTR_EN, hcd->regs + HC_HW_MODE_CTRL);

command = isp1760_readl(hcd->regs + HC_USBCMD);
command &= ~CMD_RUN;
Expand Down Expand Up @@ -2183,7 +2220,8 @@ void deinit_kmem_cache(void)
}

struct usb_hcd *isp1760_register(u64 res_start, u64 res_len, int irq,
u64 irqflags, struct device *dev, const char *busname)
u64 irqflags, struct device *dev, const char *busname,
unsigned int devflags)
{
struct usb_hcd *hcd;
struct isp1760_hcd *priv;
Expand All @@ -2200,6 +2238,7 @@ struct usb_hcd *isp1760_register(u64 res_start, u64 res_len, int irq,
return ERR_PTR(-ENOMEM);

priv = hcd_to_priv(hcd);
priv->devflags = devflags;
init_memory(priv);
hcd->regs = ioremap(res_start, res_len);
if (!hcd->regs) {
Expand Down
20 changes: 18 additions & 2 deletions trunk/drivers/usb/host/isp1760-hcd.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@

/* exports for if */
struct usb_hcd *isp1760_register(u64 res_start, u64 res_len, int irq,
u64 irqflags, struct device *dev, const char *busname);
u64 irqflags, struct device *dev, const char *busname,
unsigned int devflags);
int init_kmem_once(void);
void deinit_kmem_cache(void);

Expand Down Expand Up @@ -31,6 +32,7 @@ void deinit_kmem_cache(void);
/* Configuration Register */
#define HC_HW_MODE_CTRL 0x300
#define ALL_ATX_RESET (1 << 31)
#define HW_ANA_DIGI_OC (1 << 15)
#define HW_DATA_BUS_32BIT (1 << 8)
#define HW_DACK_POL_HIGH (1 << 6)
#define HW_DREQ_POL_HIGH (1 << 5)
Expand All @@ -56,13 +58,14 @@ void deinit_kmem_cache(void);
#define PORT1_POWER (3 << 3)
#define PORT1_INIT1 (1 << 7)
#define PORT1_INIT2 (1 << 23)
#define HW_OTG_CTRL_SET 0x374
#define HW_OTG_CTRL_CLR 0x376

/* Interrupt Register */
#define HC_INTERRUPT_REG 0x310

#define HC_INTERRUPT_ENABLE 0x314
#define INTERRUPT_ENABLE_MASK (HC_INTL_INT | HC_ATL_INT | HC_EOT_INT)
#define FINAL_HW_CONFIG (HW_GLOBAL_INTR_EN | HW_DATA_BUS_32BIT)

#define HC_ISO_INT (1 << 9)
#define HC_ATL_INT (1 << 8)
Expand Down Expand Up @@ -122,6 +125,19 @@ typedef void (packet_enqueue)(struct usb_hcd *hcd, struct isp1760_qh *qh,
#define isp1760_err(priv, fmt, args...) \
dev_err(priv_to_hcd(priv)->self.controller, fmt, ##args)

/*
* Device flags that can vary from board to board. All of these
* indicate the most "atypical" case, so that a devflags of 0 is
* a sane default configuration.
*/
#define ISP1760_FLAG_PORT1_DIS 0x00000001 /* Port 1 disabled */
#define ISP1760_FLAG_BUS_WIDTH_16 0x00000002 /* 16-bit data bus width */
#define ISP1760_FLAG_OTG_EN 0x00000004 /* Port 1 supports OTG */
#define ISP1760_FLAG_ANALOG_OC 0x00000008 /* Analog overcurrent */
#define ISP1760_FLAG_DACK_POL_HIGH 0x00000010 /* DACK active high */
#define ISP1760_FLAG_DREQ_POL_HIGH 0x00000020 /* DREQ active high */
#define ISP1760_FLAG_ISP1761 0x00000040 /* Chip is ISP1761 */

/* chip memory management */
struct memory_chunk {
unsigned int start;
Expand Down
35 changes: 33 additions & 2 deletions trunk/drivers/usb/host/isp1760-if.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,8 @@ static int of_isp1760_probe(struct of_device *dev,
int virq;
u64 res_len;
int ret;
const unsigned int *prop;
unsigned int devflags = 0;

ret = of_address_to_resource(dp, 0, &memory);
if (ret)
Expand All @@ -55,8 +57,32 @@ static int of_isp1760_probe(struct of_device *dev,
virq = irq_create_of_mapping(oirq.controller, oirq.specifier,
oirq.size);

if (of_device_is_compatible(dp, "nxp,usb-isp1761"))
devflags |= ISP1760_FLAG_ISP1761;

if (of_get_property(dp, "port1-disable", NULL) != NULL)
devflags |= ISP1760_FLAG_PORT1_DIS;

/* Some systems wire up only 16 of the 32 data lines */
prop = of_get_property(dp, "bus-width", NULL);
if (prop && *prop == 16)
devflags |= ISP1760_FLAG_BUS_WIDTH_16;

if (of_get_property(dp, "port1-otg", NULL) != NULL)
devflags |= ISP1760_FLAG_OTG_EN;

if (of_get_property(dp, "analog-oc", NULL) != NULL)
devflags |= ISP1760_FLAG_ANALOG_OC;

if (of_get_property(dp, "dack-polarity", NULL) != NULL)
devflags |= ISP1760_FLAG_DACK_POL_HIGH;

if (of_get_property(dp, "dreq-polarity", NULL) != NULL)
devflags |= ISP1760_FLAG_DREQ_POL_HIGH;

hcd = isp1760_register(memory.start, res_len, virq,
IRQF_SHARED | IRQF_DISABLED, &dev->dev, dev_name(&dev->dev));
IRQF_SHARED | IRQF_DISABLED, &dev->dev, dev_name(&dev->dev),
devflags);
if (IS_ERR(hcd)) {
ret = PTR_ERR(hcd);
goto release_reg;
Expand Down Expand Up @@ -87,6 +113,9 @@ static struct of_device_id of_isp1760_match[] = {
{
.compatible = "nxp,usb-isp1760",
},
{
.compatible = "nxp,usb-isp1761",
},
{ },
};
MODULE_DEVICE_TABLE(of, of_isp1760_match);
Expand Down Expand Up @@ -116,6 +145,7 @@ static int __devinit isp1761_pci_probe(struct pci_dev *dev,
int length;
int status = 1;
struct usb_hcd *hcd;
unsigned int devflags = 0;

if (usb_disabled())
return -ENODEV;
Expand Down Expand Up @@ -200,7 +230,8 @@ static int __devinit isp1761_pci_probe(struct pci_dev *dev,

dev->dev.dma_mask = NULL;
hcd = isp1760_register(pci_mem_phy0, length, dev->irq,
IRQF_SHARED | IRQF_DISABLED, &dev->dev, dev_name(&dev->dev));
IRQF_SHARED | IRQF_DISABLED, &dev->dev, dev_name(&dev->dev),
devflags);
pci_set_drvdata(dev, hcd);
if (!hcd)
return 0;
Expand Down

0 comments on commit 99d96f5

Please sign in to comment.