[linux-yocto] [PATCH 11/18] arch/arm/mach-axxia: added support for ncr_read/ncr_write() to access PCIe/SRIO SerDes Config in 0x115 node
Charlie Paul
cpaul.windriver at gmail.com
Tue Feb 18 09:26:41 PST 2014
From: SangeethaRao <sangeetha.rao at lsi.com>
Signed-off-by: SangeethaRao <sangeetha.rao at lsi.com>
---
arch/arm/mach-axxia/ncr.c | 133 +++++++++++++++++++++++++++++++++++++++++----
1 file changed, 122 insertions(+), 11 deletions(-)
diff --git a/arch/arm/mach-axxia/ncr.c b/arch/arm/mach-axxia/ncr.c
index 58b959a..4112038 100644
--- a/arch/arm/mach-axxia/ncr.c
+++ b/arch/arm/mach-axxia/ncr.c
@@ -224,7 +224,7 @@ ncr_read(unsigned long region, unsigned long address, int number,
if (0 != ncr_lock(LOCK_DOMAIN))
return -1;
- if (NCP_NODE_ID(region) != 0x0153) {
+ if ((NCP_NODE_ID(region) != 0x0153) && (NCP_NODE_ID(region) != 0x115)) {
/*
Set up the read command.
*/
@@ -274,6 +274,7 @@ ncr_read(unsigned long region, unsigned long address, int number,
*((unsigned long *) buffer) =
ncr_register_read((unsigned *) address);
address += 4;
+ buffer += 4;
number -= 4;
}
@@ -284,17 +285,76 @@ ncr_read(unsigned long region, unsigned long address, int number,
}
} else {
#ifdef APB2SER_PHY_PHYS_ADDRESS
- void __iomem *targ_address = apb2ser0_address +
+ if (NCP_NODE_ID(region) != 0x115) {
+ void __iomem *targ_address = apb2ser0_address +
(address & (~0x3));
- /*
- Copy data words to the buffer.
- */
+ /*
+ * Copy data words to the buffer.
+ */
+
+ while (4 <= number) {
+ *((unsigned long *) buffer) =
+ *((unsigned long *) targ_address);
+ targ_address += 4;
+ number -= 4;
+ }
+ } else {
+ void __iomem *base;
+ if (0xffff < address) {
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+
+ switch (NCP_TARGET_ID(region)) {
+ case 0:
+ base = (apb2ser0_address + 0x1e0);
+ break;
+ case 1:
+ base = (apb2ser0_address + 0x1f0);
+ break;
+ case 2:
+ base = (apb2ser0_address + 0x200);
+ break;
+ case 3:
+ base = (apb2ser0_address + 0x210);
+ break;
+ case 4:
+ base = (apb2ser0_address + 0x220);
+ break;
+ case 5:
+ base = (apb2ser0_address + 0x230);
+ break;
+ default:
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+ if ((NCP_TARGET_ID(region) == 0x1) ||
+ (NCP_TARGET_ID(region) == 0x4)) {
+ writel((0x84c00000 + address), (base + 4));
+ } else {
+ writel((0x85400000 + address), (base + 4));
+ }
+ do {
+ --wfc_timeout;
+ *((unsigned long *) buffer) =
+ readl(base + 4);
+ } while (0 != (*((unsigned long *) buffer) & 0x80000000)
+ && 0 < wfc_timeout);
+
+ if (0 == wfc_timeout) {
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+
+ if ((NCP_TARGET_ID(region) == 0x1) ||
+ (NCP_TARGET_ID(region) == 0x4)) {
+ *((unsigned short *) buffer) =
+ readl(base + 8);
+ } else {
+ *((unsigned long *) buffer) =
+ readl(base + 8);
+ }
- while (4 <= number) {
- *((unsigned long *) buffer) =
- *((unsigned long *) targ_address);
- targ_address += 4;
- number -= 4;
}
#else
ncr_unlock(LOCK_DOMAIN);
@@ -335,7 +395,7 @@ ncr_write(unsigned long region, unsigned long address, int number,
if (0 != ncr_lock(LOCK_DOMAIN))
return -1;
- if (NCP_NODE_ID(region) != 0x0153) {
+ if ((NCP_NODE_ID(region) != 0x0153) && (NCP_NODE_ID(region) != 0x115)) {
/*
Set up the write.
*/
@@ -416,6 +476,7 @@ ncr_write(unsigned long region, unsigned long address, int number,
}
} else {
#ifdef APB2SER_PHY_PHYS_ADDRESS
+ if (NCP_NODE_ID(region) != 0x115) {
void __iomem *targ_address = apb2ser0_address +
(address & (~0x3));
/*
@@ -428,6 +489,56 @@ ncr_write(unsigned long region, unsigned long address, int number,
targ_address += 4;
number -= 4;
}
+ } else {
+ void __iomem *base;
+ if (0xffff < address) {
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+
+ switch (NCP_TARGET_ID(region)) {
+ case 0:
+ base = (apb2ser0_address + 0x1e0);
+ break;
+ case 1:
+ base = (apb2ser0_address + 0x1f0);
+ break;
+ case 2:
+ base = (apb2ser0_address + 0x200);
+ break;
+ case 3:
+ base = (apb2ser0_address + 0x210);
+ break;
+ case 4:
+ base = (apb2ser0_address + 0x220);
+ break;
+ case 5:
+ base = (apb2ser0_address + 0x230);
+ break;
+ default:
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+ if ((NCP_TARGET_ID(region) == 0x1) ||
+ (NCP_TARGET_ID(region) == 0x4)) {
+ writel(*((unsigned short *) buffer), base);
+ writel((0xc4c00000 + address), (base + 4));
+ } else {
+ writel(*((unsigned long *) buffer), base);
+ writel((0xc5400000 + address), (base + 4));
+ }
+ do {
+ --wfc_timeout;
+ *((unsigned long *) buffer) =
+ readl(base + 4);
+ } while (0 != (*((unsigned long *) buffer) & 0x80000000)
+ && 0 < wfc_timeout);
+
+ if (0 == wfc_timeout) {
+ ncr_unlock(LOCK_DOMAIN);
+ return -1;
+ }
+ }
#else
ncr_unlock(LOCK_DOMAIN);
return -1;
--
1.7.9.5
More information about the linux-yocto
mailing list