aboutsummaryrefslogtreecommitdiff
path: root/drivers/net/ibm_newemac/tah.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/ibm_newemac/tah.c')
-rw-r--r--drivers/net/ibm_newemac/tah.c79
1 files changed, 79 insertions, 0 deletions
diff --git a/drivers/net/ibm_newemac/tah.c b/drivers/net/ibm_newemac/tah.c
index 8d31b4a2c91..4ed836a8d82 100644
--- a/drivers/net/ibm_newemac/tah.c
+++ b/drivers/net/ibm_newemac/tah.c
@@ -49,6 +49,7 @@ void tah_reset(struct of_device *ofdev)
struct tah_instance *dev = dev_get_drvdata(&ofdev->dev);
struct tah_regs __iomem *p = dev->base;
int n;
+ u32 ss_arr[] = TAH_SS_DEFAULT;
/* Reset TAH */
out_be32(&p->mr, TAH_MR_SR);
@@ -63,6 +64,16 @@ void tah_reset(struct of_device *ofdev)
out_be32(&p->mr,
TAH_MR_CVR | TAH_MR_ST_256 | TAH_MR_TFS_10KB | TAH_MR_DTFP |
TAH_MR_DIG);
+
+ /* Re-initialize SSRx values */
+ for (n=0; n < TAH_NO_SSR; n++) {
+ dev->ss_order[n] = n;
+ }
+
+ for (n=0; n < TAH_NO_SSR; n++) {
+ tah_set_ssr(ofdev, n, ss_arr[n]);
+ }
+
}
int tah_get_regs_len(struct of_device *ofdev)
@@ -86,6 +97,74 @@ void *tah_dump_regs(struct of_device *ofdev, void *buf)
return regs + 1;
}
+void tah_set_ssr(struct of_device *ofdev, int index, int seg_size)
+{
+ struct tah_instance *dev = dev_get_drvdata(&ofdev->dev);
+ struct tah_regs __iomem *p = dev->base;
+ u32 ssr_tmp[TAH_NO_SSR];
+ int i = 0;
+ int j = 0;
+ u32 tmp_val;
+
+ if ((index < 0) || (index > 5)) return;
+ mutex_lock(&dev->lock);
+ /* TAH segment size reg defines the number of half words */
+ out_be32(&p->ssr0 + index, SS_2_TAH_SSR(seg_size >> 1));
+ dev->ss_array[index] = seg_size & 0x3ffe;
+
+ /*
+ * Sort the TAH_SSRx values and store the index in
+ * ss_order array in high-to-low order
+ */
+ for (i=0; i < TAH_NO_SSR; i++) {
+ ssr_tmp[i] = dev->ss_array[i];
+ dev->ss_order[i] = i;
+ }
+ /* Simple bubble short */
+ for (i =0; i < (TAH_NO_SSR-1); i++)
+ for (j = i+1; j < TAH_NO_SSR; j++) {
+ if (ssr_tmp[i] < ssr_tmp[j]) {
+ /* Swap ssr_tmp[] values */
+ tmp_val = ssr_tmp[i];
+ ssr_tmp[i] = ssr_tmp[j];
+ ssr_tmp[j] = tmp_val;
+ /* Swap order array values */
+ tmp_val = dev->ss_order[i];
+ dev->ss_order[i] = dev->ss_order[j];
+ dev->ss_order[j] = tmp_val;
+ }
+ }
+#if 0
+ printk(KERN_DEBUG "%s: Setting TAH_SSR%d[SS] to %d\n",
+ ofdev->node->full_name, index,
+ TAH_SSR_2_SS(in_be32(&p->ssr0+index)));
+ printk("SSRx array: ");
+ for (i = 0; i < TAH_NO_SSR; i++)
+ printk("%d ", ssr_tmp[i]);
+ printk("\n");
+
+ printk("SSRx order: ");
+ for (i = 0; i < TAH_NO_SSR; i++)
+ printk("%d ", dev->ss_order[i]);
+ printk("\n");
+#endif
+ mutex_unlock(&dev->lock);
+}
+
+u32 tah_get_ssr(struct of_device *ofdev, int index)
+{
+ struct tah_instance *dev = dev_get_drvdata(&ofdev->dev);
+ struct tah_regs __iomem *p = dev->base;
+ u32 ret = 0;
+
+ if ((index < 0) || (index > 5)) return 0;
+ mutex_lock(&dev->lock);
+ ret = (in_be32(&p->ssr0 + index));
+ mutex_unlock(&dev->lock);
+
+ return ret;
+}
+
static int __devinit tah_probe(struct of_device *ofdev,
const struct of_device_id *match)
{