diff options
Diffstat (limited to 'c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c')
-rw-r--r-- | c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c | 190 |
1 files changed, 124 insertions, 66 deletions
diff --git a/c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c b/c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c index 764ab53eb1..c8f9b1c48d 100644 --- a/c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c +++ b/c/src/lib/libbsp/powerpc/ep1a/console/rsPMCQ1.c @@ -27,7 +27,7 @@ These functions are responsible for scanning for PMCQ1's and setting up the Motorola MC68360's if present. USAGE -call rsPMCQ1Init() to perform ba sic initialisation of the PMCQ1's. +call rsPMCQ1Init() to perform basic initialisation of the PMCQ1's. */ /* includes */ @@ -41,8 +41,8 @@ call rsPMCQ1Init() to perform ba sic initialisation of the PMCQ1's. #include "m68360.h" /* defines */ -#if 1 -#define DEBUG_360 +#if 0 +#define DEBUG_360 TRUE #endif /* Local data */ @@ -82,27 +82,61 @@ static unsigned char rsPMCQ1eeprom[] = void MsDelay(void) { - printk("."); + printk(".."); } void write8( int addr, int data ){ - out_8((void *)addr, (unsigned char)data); + out_8((volatile void *)addr, (unsigned char)data); + Processor_Synchronize(); } void write16( int addr, int data ) { - out_be16((void *)addr, (short)data ); + out_be16((volatile void *)addr, (short)data ); + Processor_Synchronize(); } void write32( int addr, int data ) { - out_be32((unsigned int *)addr, data ); + out_be32((volatile unsigned int *)addr, data ); + Processor_Synchronize(); } int read32( int addr){ - return in_be32((unsigned int *)addr); + int value = in_be32((volatile unsigned int *)addr); + Processor_Synchronize(); + return value; } +void rsPMCQ1_scc_On(const struct __rtems_irq_connect_data__ *ptr) +{ + +} + +void rsPMCQ1_scc_Off(const struct __rtems_irq_connect_data__ *ptr) +{ + +} + +int rsPMCQ1_scc_except_always_enabled(const struct __rtems_irq_connect_data__ *ptr) +{ + return TRUE; +} + + +void rsPMCQ1ShowIntrStatus(void ) +{ + unsigned long status; + unsigned long mask; + PPMCQ1BoardData boardData; + + for (boardData = pmcq1BoardData; boardData; boardData = boardData->pNext) + { + + status = PMCQ1_Read_EPLD(boardData->baseaddr, PMCQ1_INT_STATUS ); + mask = PMCQ1_Read_EPLD(boardData->baseaddr, PMCQ1_INT_MASK ); + printk("rsPMCQ1ShowIntrStatus: interrupt status 0x%x) 0x%x with mask: 0x%x\n", boardData->quiccInt, status, mask); + } +} -void rsPMCQ1_scc_nullFunc(void) {} /******************************************************************************* * rsPMCQ1Int - handle a PMCQ1 interrupt @@ -116,48 +150,57 @@ void rsPMCQ1_scc_nullFunc(void) {} void rsPMCQ1Int( void *ptr ) { unsigned long status; - unsigned long status1; + static unsigned long status1; unsigned long mask; uint32_t data; PPMCQ1BoardData boardData = ptr; + volatile unsigned long *hrdwr; + unsigned long value; status = PMCQ1_Read_EPLD(boardData->baseaddr, PMCQ1_INT_STATUS ); mask = PMCQ1_Read_EPLD(boardData->baseaddr, PMCQ1_INT_MASK ); - if (((mask & PMCQ1_INT_MASK_QUICC) == 0) && (status & PMCQ1_INT_STATUS_QUICC)) + + if (((mask & PMCQ1_INT_MASK_QUICC) == 0) && ((status & PMCQ1_INT_STATUS_QUICC) != 0 )) { /* If there is a handler call it otherwise mask the interrupt */ if (boardData->quiccInt) { boardData->quiccInt(boardData->quiccArg); } else { - *(volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_QUICC; + printk("No handler - Masking interrupt\n"); + hrdwr = (volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK); + value = (*hrdwr) | PMCQ1_INT_MASK_QUICC; + *hrdwr = value; } } if (((mask & PMCQ1_INT_MASK_MA) == 0) && (status & PMCQ1_INT_STATUS_MA)) { + /* If there is a handler call it otherwise mask the interrupt */ if (boardData->maInt) { boardData->maInt(boardData->maArg); - data = PMCQ1_Read_EPLD(boardData->baseaddr, PMCQ1_INT_STATUS ); - data &= (~PMCQ1_INT_STATUS_MA); + data = data & (~PMCQ1_INT_STATUS_MA); PMCQ1_Write_EPLD(boardData->baseaddr, PMCQ1_INT_STATUS, data ); - - } else { - *(volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_MA; + } else { + printk("No handler - Masking interrupt\n"); + hrdwr = (volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK); + value = (*hrdwr) | PMCQ1_INT_MASK_MA; + *hrdwr = value; } } RTEMS_COMPILER_MEMORY_BARRIER(); /* Clear Interrupt on QSPAN */ - *(volatile unsigned long *)(boardData->bridgeaddr + 0x600) = 0x00001000; + hrdwr = (volatile unsigned long *)(boardData->bridgeaddr + 0x600); + *hrdwr = 0x00001000; /* read back the status register to ensure that the pci write has completed */ - status1 = *(volatile unsigned long *)(boardData->bridgeaddr + 0x600); - RTEMS_COMPILER_MEMORY_BARRIER(); + status1 = *hrdwr; + RTEMS_COMPILER_MEMORY_BARRIER(); } @@ -175,8 +218,8 @@ unsigned int rsPMCQ1MaIntConnect ( unsigned long busNo, /* Pci Bus number of PMCQ1 */ unsigned long slotNo, /* Pci Slot number of PMCQ1 */ unsigned long funcNo, /* Pci Function number of PMCQ1 */ - FUNCION_PTR routine,/* interrupt routine */ - int arg /* argument to pass to interrupt routine */ + PMCQ1_FUNCTION_PTR routine,/* interrupt routine */ + void * arg /* argument to pass to interrupt routine */ ) { PPMCQ1BoardData boardData; @@ -231,7 +274,7 @@ unsigned int rsPMCQ1MaIntDisconnect( (boardData->funcNo == funcNo)) { boardData->maInt = NULL; - *(unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_MA; + *(volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_MA; status = RTEMS_SUCCESSFUL; break; } @@ -251,11 +294,11 @@ unsigned int rsPMCQ1MaIntDisconnect( */ unsigned int rsPMCQ1QuiccIntConnect( - unsigned long busNo, /* Pci Bus number of PMCQ1 */ - unsigned long slotNo, /* Pci Slot number of PMCQ1 */ - unsigned long funcNo, /* Pci Function number of PMCQ1 */ - FUNCION_PTR routine,/* interrupt routine */ - int arg /* argument to pass to interrupt routine */ + unsigned long busNo, /* Pci Bus number of PMCQ1 */ + unsigned long slotNo, /* Pci Slot number of PMCQ1 */ + unsigned long funcNo, /* Pci Function number of PMCQ1 */ + PMCQ1_FUNCTION_PTR routine, /* interrupt routine */ + void * arg /* argument to pass to interrupt routine */ ) { PPMCQ1BoardData boardData; @@ -300,7 +343,7 @@ unsigned int rsPMCQ1QuiccIntDisconnect( (boardData->funcNo == funcNo)) { boardData->quiccInt = NULL; - *(unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_QUICC; + *(volatile unsigned long *)(boardData->baseaddr + PMCQ1_INT_MASK) |= PMCQ1_INT_MASK_QUICC; status = RTEMS_SUCCESSFUL; break; } @@ -323,25 +366,22 @@ unsigned int rsPMCQ1Init(void) { int busNo; int slotNo; - unsigned int baseaddr = 0; - unsigned int bridgeaddr = 0; + uint32_t baseaddr = 0; + uint32_t bridgeaddr = 0; unsigned long pbti0_ctl; int i; unsigned char int_vector; int fun; - int temp; + uint32_t temp; PPMCQ1BoardData boardData; - rtems_irq_connect_data IrqData = {0, - rsPMCQ1Int, - rsPMCQ1_scc_nullFunc, - rsPMCQ1_scc_nullFunc, - rsPMCQ1_scc_nullFunc, - NULL}; + rtems_irq_connect_data *IrqData = NULL; if (rsPMCQ1Initialized) { + printk("rsPMCQ1Init: Already Initialized\n"); return RTEMS_SUCCESSFUL; - } + } + for (i=0;;i++){ if ( pci_find_device(PCI_VEN_ID_RADSTONE, PCI_DEV_ID_PMCQ1, i, &busNo, &slotNo, &fun) != 0 ) break; @@ -349,17 +389,17 @@ unsigned int rsPMCQ1Init(void) pci_read_config_dword(busNo, slotNo, 0, PCI_BASE_ADDRESS_2, &baseaddr); pci_read_config_dword(busNo, slotNo, 0, PCI_BASE_ADDRESS_0, &bridgeaddr); #ifdef DEBUG_360 - printk("PMCQ1 baseaddr 0x%08x bridgeaddr 0x%08x\n", baseaddr, bridgeaddr ); + printk("rsPMCQ1Init: PMCQ1 baseaddr 0x%08x bridgeaddr 0x%08x\n", baseaddr, bridgeaddr ); #endif /* Set function code to normal mode and enable window */ - pbti0_ctl = *(unsigned long *)(bridgeaddr + 0x100) & 0xff0fffff; + pbti0_ctl = (*(unsigned long *)(bridgeaddr + 0x100)) & 0xff0fffff; eieio(); - *(unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00500080; + *(volatile unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00500080; eieio(); /* Assert QBUS reset */ - *(unsigned long *)(bridgeaddr + 0x800) |= 0x00000080; + *(volatile unsigned long *)(bridgeaddr + 0x800) |= 0x00000080; eieio(); /* @@ -368,7 +408,7 @@ unsigned int rsPMCQ1Init(void) MsDelay(); /* Take QBUS out of reset */ - *(unsigned long *)(bridgeaddr + 0x800) &= ~0x00000080; + *(volatile unsigned long *)(bridgeaddr + 0x800) &= ~0x00000080; eieio(); MsDelay(); @@ -377,19 +417,19 @@ unsigned int rsPMCQ1Init(void) if (PMCQ1_Read_EPLD(baseaddr, PMCQ1_BUILD_OPTION) & PMCQ1_QUICC_FITTED) { #ifdef DEBUG_360 - printk(" Found QUICC busNo %d slotNo %d\n", busNo, slotNo); + printk("rsPMCQ1Init: Found QUICC busNo %d slotNo %d\n", busNo, slotNo); #endif /* Initialise MBAR (must use function code of 7) */ - *(unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00700080; + *(volatile unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00700080; eieio(); /* place internal 8K SRAM and registers at address 0x0 */ - *(unsigned long *)(baseaddr + Q1_360_MBAR) = 0x1; + *(volatile unsigned long *)(baseaddr + Q1_360_MBAR) = 0x1; eieio(); /* Set function code to normal mode */ - *(unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00500080; + *(volatile unsigned long *)(bridgeaddr + 0x100) = pbti0_ctl | 0x00500080; eieio(); /* Disable the SWT and perform basic initialisation */ @@ -425,15 +465,15 @@ unsigned int rsPMCQ1Init(void) */ pci_read_config_dword(busNo, slotNo, 0, PCI_BASE_ADDRESS_3, &temp); if (temp) { - *(unsigned long *)(bridgeaddr + 0x110) |= 0x00500880; + *(volatile unsigned long *)(bridgeaddr + 0x110) |= 0x00500880; } /* * Create descriptor structure for this card */ - if ((boardData = malloc(sizeof(struct _PMCQ1BoardData))) == NULL) + if ((boardData = calloc(1, sizeof(struct _PMCQ1BoardData))) == NULL) { - printk("Error Unable to allocate memory for _PMCQ1BoardData\n"); + printk("rsPMCQ1Init: Error Unable to allocate memory for _PMCQ1BoardData\n"); return(RTEMS_IO_ERROR); } @@ -446,6 +486,7 @@ unsigned int rsPMCQ1Init(void) boardData->quiccInt = NULL; boardData->maInt = NULL; pmcq1BoardData = boardData; + mc68360_scc_create_chip( boardData, int_vector ); /* @@ -453,11 +494,22 @@ unsigned int rsPMCQ1Init(void) */ pci_read_config_byte(busNo, slotNo, 0, 0x3c, &int_vector); #ifdef DEBUG_360 - printk("PMCQ1 int_vector %d\n", int_vector); + printk("rsPMCQ1Init: PMCQ1 int_vector %d\n", int_vector); #endif - IrqData.name = ((unsigned int)BSP_PCI_IRQ0 + int_vector); - IrqData.handle = boardData; - if (!BSP_install_rtems_shared_irq_handler (&IrqData)) { + + if ((IrqData = calloc( 1, sizeof(rtems_irq_connect_data) )) == NULL ) + { + printk("rsPMCQ1Init: Error Unable to allocate memory for rtems_irq_connect_data\n"); + return(RTEMS_IO_ERROR); + } + IrqData->name = ((unsigned int)BSP_PCI_IRQ0 + int_vector); + IrqData->hdl = rsPMCQ1Int; + IrqData->handle = boardData; + IrqData->on = rsPMCQ1_scc_On; + IrqData->off = rsPMCQ1_scc_Off; + IrqData->isOn = rsPMCQ1_scc_except_always_enabled; + + if (!BSP_install_rtems_shared_irq_handler (IrqData)) { printk("Error installing interrupt handler!\n"); rtems_fatal_error_occurred(1); } @@ -465,11 +517,10 @@ unsigned int rsPMCQ1Init(void) /* * Enable PMCQ1 Interrupts from QSPAN-II */ - - *(unsigned long *)(bridgeaddr + 0x600) = 0x00001000; + *(volatile unsigned long *)(bridgeaddr + 0x600) = 0x00001000; eieio(); - *(unsigned long *)(bridgeaddr + 0x604) |= 0x00001000; - + Processor_Synchronize(); + *(volatile unsigned long *)(bridgeaddr + 0x604) |= 0x00001000; eieio(); } @@ -512,9 +563,9 @@ unsigned int rsPMCQ1Commission( unsigned long busNo, unsigned long slotNo ) * A real PMCQ1 also has the sub vendor ID set up. */ if ((busNo == 0) && (slotNo == 1)) { - *(unsigned long *)rsPMCQ1eeprom = 0; + *(volatile unsigned long *)rsPMCQ1eeprom = 0; } else { - *(unsigned long *)rsPMCQ1eeprom = PCI_ID(PCI_VEN_ID_RADSTONE, PCI_DEV_ID_PMCQ1); + *(volatile unsigned long *)rsPMCQ1eeprom = PCI_ID(PCI_VEN_ID_RADSTONE, PCI_DEV_ID_PMCQ1); } for (i = 0; i < 23; i++) { @@ -558,20 +609,27 @@ unsigned int rsPMCQ1Commission( unsigned long busNo, unsigned long slotNo ) uint32_t PMCQ1_Read_EPLD( uint32_t base, uint32_t reg ) { - uint32_t data; + uint32_t data; + volatile uint32_t *ptr; - data = ( *((unsigned long *) (base + reg)) ); + Processor_Synchronize(); + ptr = (volatile uint32_t *)(base + reg); + data = *ptr ; #ifdef DEBUG_360 - printk("EPLD Read 0x%x: 0x%08x\n", reg + base, data ); + printk("EPLD Read 0x%x: 0x%08x\n", ptr, data ); #endif return data; } void PMCQ1_Write_EPLD( uint32_t base, uint32_t reg, uint32_t data ) { - *((unsigned long *) (base + reg)) = data; + volatile uint32_t *ptr; + + ptr = (volatile uint32_t *) (base + reg); + *ptr = data; + Processor_Synchronize(); #ifdef DEBUG_360 - printk("EPLD Write 0x%x: 0x%08x\n", reg+base, data ); + printk("EPLD Write 0x%x: 0x%08x\n", ptr, data ); #endif } |