aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/mvsas/mv_94xx.c
diff options
context:
space:
mode:
authorXiangliang Yu <yuxiangl@marvell.com>2011-05-24 10:36:02 -0400
committerJames Bottomley <JBottomley@Parallels.com>2011-07-26 02:36:11 -0400
commita4632aae8b662b1f32fe3fc558a813cd5c3daae6 (patch)
treea88ee045018877314d76b9cb99e3e837b78d5565 /drivers/scsi/mvsas/mv_94xx.c
parentb89e8f539ff8bcf2a1464578fa91cb96cc433fc3 (diff)
[SCSI] mvsas: Add new macros and functions
Add new macros: MVS_SOFT_RESET, MVS_HARD_RESET, MVS_PHY_TUNE, MVS_COMMAND_ACTIVE, EXP_BRCT_CHG, MVS_MAX_SG Add new member sg_width in struct mvs_chip_info Use macros rather than magic number Add new functions: mvs_fill_ssp_resp_iu, mvs_set_sense, mvs_94xx_clear_srs_irq, mvs_94xx_phy_set_link_rate Signed-off-by: Xiangliang Yu <yuxiangl@marvell.com> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
Diffstat (limited to 'drivers/scsi/mvsas/mv_94xx.c')
-rw-r--r--drivers/scsi/mvsas/mv_94xx.c80
1 files changed, 59 insertions, 21 deletions
diff --git a/drivers/scsi/mvsas/mv_94xx.c b/drivers/scsi/mvsas/mv_94xx.c
index 5b25f1b7fa52..a0ec4aaa24a2 100644
--- a/drivers/scsi/mvsas/mv_94xx.c
+++ b/drivers/scsi/mvsas/mv_94xx.c
@@ -389,7 +389,7 @@ static int __devinit mvs_94xx_init(struct mvs_info *mvi)
389 mvs_phy_hacks(mvi); 389 mvs_phy_hacks(mvi);
390 390
391 /* set LED blink when IO*/ 391 /* set LED blink when IO*/
392 mw32(MVS_PA_VSR_ADDR, 0x00000030); 392 mw32(MVS_PA_VSR_ADDR, VSR_PHY_ACT_LED);
393 tmp = mr32(MVS_PA_VSR_PORT); 393 tmp = mr32(MVS_PA_VSR_PORT);
394 tmp &= 0xFFFF00FF; 394 tmp &= 0xFFFF00FF;
395 tmp |= 0x00003300; 395 tmp |= 0x00003300;
@@ -419,7 +419,7 @@ static int __devinit mvs_94xx_init(struct mvs_info *mvi)
419 mvs_94xx_config_reg_from_hba(mvi, i); 419 mvs_94xx_config_reg_from_hba(mvi, i);
420 mvs_94xx_phy_enable(mvi, i); 420 mvs_94xx_phy_enable(mvi, i);
421 421
422 mvs_94xx_phy_reset(mvi, i, 1); 422 mvs_94xx_phy_reset(mvi, i, PHY_RST_HARD);
423 msleep(500); 423 msleep(500);
424 mvs_94xx_detect_porttype(mvi, i); 424 mvs_94xx_detect_porttype(mvi, i);
425 } 425 }
@@ -585,10 +585,48 @@ static irqreturn_t mvs_94xx_isr(struct mvs_info *mvi, int irq, u32 stat)
585static void mvs_94xx_command_active(struct mvs_info *mvi, u32 slot_idx) 585static void mvs_94xx_command_active(struct mvs_info *mvi, u32 slot_idx)
586{ 586{
587 u32 tmp; 587 u32 tmp;
588 mvs_cw32(mvi, 0x300 + (slot_idx >> 3), 1 << (slot_idx % 32)); 588 tmp = mvs_cr32(mvi, MVS_COMMAND_ACTIVE+(slot_idx >> 3));
589 do { 589 if (tmp && 1 << (slot_idx % 32)) {
590 tmp = mvs_cr32(mvi, 0x300 + (slot_idx >> 3)); 590 mv_printk("command active %08X, slot [%x].\n", tmp, slot_idx);
591 } while (tmp & 1 << (slot_idx % 32)); 591 mvs_cw32(mvi, MVS_COMMAND_ACTIVE + (slot_idx >> 3),
592 1 << (slot_idx % 32));
593 do {
594 tmp = mvs_cr32(mvi,
595 MVS_COMMAND_ACTIVE + (slot_idx >> 3));
596 } while (tmp & 1 << (slot_idx % 32));
597 }
598}
599
600void mvs_94xx_clear_srs_irq(struct mvs_info *mvi, u8 reg_set, u8 clear_all)
601{
602 void __iomem *regs = mvi->regs;
603 u32 tmp;
604
605 if (clear_all) {
606 tmp = mr32(MVS_INT_STAT_SRS_0);
607 if (tmp) {
608 mv_dprintk("check SRS 0 %08X.\n", tmp);
609 mw32(MVS_INT_STAT_SRS_0, tmp);
610 }
611 tmp = mr32(MVS_INT_STAT_SRS_1);
612 if (tmp) {
613 mv_dprintk("check SRS 1 %08X.\n", tmp);
614 mw32(MVS_INT_STAT_SRS_1, tmp);
615 }
616 } else {
617 if (reg_set > 31)
618 tmp = mr32(MVS_INT_STAT_SRS_1);
619 else
620 tmp = mr32(MVS_INT_STAT_SRS_0);
621
622 if (tmp & (1 << (reg_set % 32))) {
623 mv_dprintk("register set 0x%x was stopped.\n", reg_set);
624 if (reg_set > 31)
625 mw32(MVS_INT_STAT_SRS_1, 1 << (reg_set % 32));
626 else
627 mw32(MVS_INT_STAT_SRS_0, 1 << (reg_set % 32));
628 }
629 }
592} 630}
593 631
594static void mvs_94xx_issue_stop(struct mvs_info *mvi, enum mvs_port_type type, 632static void mvs_94xx_issue_stop(struct mvs_info *mvi, enum mvs_port_type type,
@@ -596,12 +634,10 @@ static void mvs_94xx_issue_stop(struct mvs_info *mvi, enum mvs_port_type type,
596{ 634{
597 void __iomem *regs = mvi->regs; 635 void __iomem *regs = mvi->regs;
598 u32 tmp; 636 u32 tmp;
637 mvs_94xx_clear_srs_irq(mvi, 0, 1);
599 638
600 if (type == PORT_TYPE_SATA) { 639 tmp = mr32(MVS_INT_STAT);
601 tmp = mr32(MVS_INT_STAT_SRS_0) | (1U << tfs); 640 mw32(MVS_INT_STAT, tmp | CINT_CI_STOP);
602 mw32(MVS_INT_STAT_SRS_0, tmp);
603 }
604 mw32(MVS_INT_STAT, CINT_CI_STOP);
605 tmp = mr32(MVS_PCS) | 0xFF00; 641 tmp = mr32(MVS_PCS) | 0xFF00;
606 mw32(MVS_PCS, tmp); 642 mw32(MVS_PCS, tmp);
607} 643}
@@ -794,7 +830,18 @@ static void mvs_94xx_fix_phy_info(struct mvs_info *mvi, int i,
794void mvs_94xx_phy_set_link_rate(struct mvs_info *mvi, u32 phy_id, 830void mvs_94xx_phy_set_link_rate(struct mvs_info *mvi, u32 phy_id,
795 struct sas_phy_linkrates *rates) 831 struct sas_phy_linkrates *rates)
796{ 832{
797 /* TODO */ 833 u32 lrmax = 0;
834 u32 tmp;
835
836 tmp = mvs_read_phy_ctl(mvi, phy_id);
837 lrmax = (rates->maximum_linkrate - SAS_LINK_RATE_1_5_GBPS) << 12;
838
839 if (lrmax) {
840 tmp &= ~(0x3 << 12);
841 tmp |= lrmax;
842 }
843 mvs_write_phy_ctl(mvi, phy_id, tmp);
844 mvs_94xx_phy_reset(mvi, phy_id, PHY_RST_HARD);
798} 845}
799 846
800static void mvs_94xx_clear_active_cmds(struct mvs_info *mvi) 847static void mvs_94xx_clear_active_cmds(struct mvs_info *mvi)
@@ -893,15 +940,6 @@ void mvs_94xx_fix_dma(struct mvs_info *mvi, u32 phy_mask,
893 } 940 }
894} 941}
895 942
896/*
897 * FIXME JEJB: temporary nop clear_srs_irq to make 94xx still work
898 * with 64xx fixes
899 */
900static void mvs_94xx_clear_srs_irq(struct mvs_info *mvi, u8 reg_set,
901 u8 clear_all)
902{
903}
904
905static void mvs_94xx_tune_interrupt(struct mvs_info *mvi, u32 time) 943static void mvs_94xx_tune_interrupt(struct mvs_info *mvi, u32 time)
906{ 944{
907 void __iomem *regs = mvi->regs; 945 void __iomem *regs = mvi->regs;