]> pilppa.org Git - linux-2.6-omap-h63xx.git/blobdiff - drivers/scsi/aic7xxx/aic7xxx_proc.c
Merge branch 'fixes-davem' of master.kernel.org:/pub/scm/linux/kernel/git/linville...
[linux-2.6-omap-h63xx.git] / drivers / scsi / aic7xxx / aic7xxx_proc.c
index 3802c91f0b07489a2dc3b04a01e9963880abaed8..99e5443e75352cecf9383c247b5d8107dfd109fe 100644 (file)
@@ -54,6 +54,47 @@ static void  ahc_dump_device_state(struct info_str *info,
 static int     ahc_proc_write_seeprom(struct ahc_softc *ahc,
                                       char *buffer, int length);
 
+/*
+ * Table of syncrates that don't follow the "divisible by 4"
+ * rule. This table will be expanded in future SCSI specs.
+ */
+static struct {
+       u_int period_factor;
+       u_int period;   /* in 100ths of ns */
+} scsi_syncrates[] = {
+       { 0x08, 625 },  /* FAST-160 */
+       { 0x09, 1250 }, /* FAST-80 */
+       { 0x0a, 2500 }, /* FAST-40 40MHz */
+       { 0x0b, 3030 }, /* FAST-40 33MHz */
+       { 0x0c, 5000 }  /* FAST-20 */
+};
+
+/*
+ * Return the frequency in kHz corresponding to the given
+ * sync period factor.
+ */
+static u_int
+ahc_calc_syncsrate(u_int period_factor)
+{
+       int i;
+
+       /* See if the period is in the "exception" table */
+       for (i = 0; i < ARRAY_SIZE(scsi_syncrates); i++) {
+
+               if (period_factor == scsi_syncrates[i].period_factor) {
+                       /* Period in kHz */
+                       return (100000000 / scsi_syncrates[i].period);
+               }
+       }
+
+       /*
+        * Wasn't in the table, so use the standard
+        * 4 times conversion.
+        */
+       return (10000000 / (period_factor * 4 * 10));
+}
+
+
 static void
 copy_mem_info(struct info_str *info, char *data, int len)
 {
@@ -106,7 +147,7 @@ ahc_format_transinfo(struct info_str *info, struct ahc_transinfo *tinfo)
         speed = 3300;
         freq = 0;
        if (tinfo->offset != 0) {
-               freq = aic_calc_syncsrate(tinfo->period);
+               freq = ahc_calc_syncsrate(tinfo->period);
                speed = freq;
        }
        speed *= (0x01 << tinfo->width);
@@ -141,7 +182,6 @@ ahc_dump_target_state(struct ahc_softc *ahc, struct info_str *info,
                      u_int our_id, char channel, u_int target_id,
                      u_int target_offset)
 {
-       struct  ahc_linux_target *targ;
        struct  scsi_target *starget;
        struct  ahc_initiator_tinfo *tinfo;
        struct  ahc_tmode_tstate *tstate;
@@ -157,7 +197,6 @@ ahc_dump_target_state(struct ahc_softc *ahc, struct info_str *info,
        starget = ahc->platform_data->starget[target_offset];
        if (!starget)
                return;
-       targ = scsi_transport_target_data(starget);
 
        copy_info(info, "\tGoal: ");
        ahc_format_transinfo(info, &tinfo->goal);
@@ -167,7 +206,7 @@ ahc_dump_target_state(struct ahc_softc *ahc, struct info_str *info,
        for (lun = 0; lun < AHC_NUM_LUNS; lun++) {
                struct scsi_device *sdev;
 
-               sdev = targ->sdev[lun];
+               sdev = scsi_device_lookup_by_target(starget, lun);
 
                if (sdev == NULL)
                        continue;
@@ -342,11 +381,11 @@ ahc_linux_proc_info(struct Scsi_Host *shost, char *buffer, char **start,
        }
        copy_info(&info, "\n");
 
-       max_targ = 15;
+       max_targ = 16;
        if ((ahc->features & (AHC_WIDE|AHC_TWIN)) == 0)
-               max_targ = 7;
+               max_targ = 8;
 
-       for (i = 0; i <= max_targ; i++) {
+       for (i = 0; i < max_targ; i++) {
                u_int our_id;
                u_int target_id;
                char channel;