/*!- Initialize watchdog timer * */ LOCAL T_BOOT_TYPE cmnos_wdt_last_boot(void) { #if 0 if (HAL_WORD_REG_READ(MAGPIE_REG_RST_WDT_TIMER_CTRL_ADDR) & 0x80000000 ) return ENUM_WDT_BOOT; else return ENUM_COLD_BOOT; #endif #if defined(PROJECT_MAGPIE) if ( *((volatile uint32_t*)WATCH_DOG_MAGIC_PATTERN_ADDR) == WDT_MAGIC_PATTERN ) return ENUM_WDT_BOOT; else if ( *((volatile uint32_t*)WATCH_DOG_MAGIC_PATTERN_ADDR) == SUS_MAGIC_PATTERN ) return ENUM_SUSP_BOOT; else return ENUM_COLD_BOOT; #elif defined(PROJECT_K2) //if (HAL_WORD_REG_READ(MAGPIE_REG_RST_STATUS_ADDR) == WDT_MAGIC_PATTERN || HAL_WORD_REG_READ(MAGPIE_REG_RST_STATUS_ADDR) == SUS_MAGIC_PATTERN) if ( HAL_WORD_REG_READ(MAGPIE_REG_RST_STATUS_ADDR) == WDT_MAGIC_PATTERN ) return ENUM_WDT_BOOT; else if ( HAL_WORD_REG_READ(MAGPIE_REG_RST_STATUS_ADDR) == SUS_MAGIC_PATTERN ) return ENUM_SUSP_BOOT; else return ENUM_COLD_BOOT; #endif /* #if defined(PROJECT_MAGPIE) */ }
/*! eep read half word * * offset: is the offset address you want to do the read operation * * return: the data we read from eeprom */ LOCAL BOOLEAN cmnos_eeprom_read_hword(uint16_t offset, uint16_t *mData) { uint32_t mStsData; //uint16_t retryCnt = 1000; HAL_WORD_REG_READ(EEPROM_ADDR_BASE + offset*4); //while( retryCnt-- > 0 ) while(1) { mStsData = HAL_WORD_REG_READ((EEPROM_CTRL_BASE+H_EEPROM_STS_DATA)); if( (mStsData&(B_EEP_STS_STATE_BUSY | B_EEP_STS_IS_BUSY)) == 0 ) { *mData = (uint16_t)(mStsData & 0xffff); return TRUE; } // A_DELAY_USECS(100); } return FALSE; }
/*! eep write half word * * offset: is the offset address you want to do the write operation * data: is the data to write to eeprom * * return: TRUE/FALSE */ LOCAL BOOLEAN cmnos_eeprom_write_hword(uint16_t offset, uint16_t data) { /*! - Livy sugguest not use the retry, since it'll be huge retry count * so that, supposed that if the apb or pcie_rc is working fine, * we should always could see the NOT_BUSY, otherwise, * it should have something worng!, put a little delay in there, * * - debug string here will be noisy!! */ //uint16_t retryCnt = 1000; #if defined(PROJECT_MAGPIE) //gpio configuration, set GPIOs output to value set in output reg HAL_WORD_REG_WRITE((EEPROM_CTRL_BASE+0x4054), (HAL_WORD_REG_READ((EEPROM_CTRL_BASE+0x4054)) | 0x20000)); HAL_WORD_REG_WRITE((EEPROM_CTRL_BASE+0x4060), 0); HAL_WORD_REG_WRITE((EEPROM_CTRL_BASE+0x4064), 0); //GPIO3 always drive output HAL_WORD_REG_WRITE((EEPROM_CTRL_BASE+0x404c), 0xc0); //Set 0 on GPIO3 HAL_WORD_REG_WRITE((EEPROM_CTRL_BASE+0x4048), 0x0); #endif HAL_WORD_REG_WRITE(EEPROM_ADDR_BASE + offset*4, (uint32_t)data); //while( retryCnt-- > 0 ) while(1) { if( (HAL_WORD_REG_READ((EEPROM_CTRL_BASE+H_EEPROM_STS_DATA))&(B_EEP_STS_STATE_BUSY | B_EEP_STS_IS_BUSY)) == 0 ) { return(TRUE); } // A_DELAY_USECS(100); } return FALSE; }
/*!- Initialize eeprom, actually we link up the pcie_rc for accessing the eeprom in client card * */ LOCAL T_EEP_RET cmnos_eep_is_exist(void) { if( FALSE != eep_state ) { if( FALSE == eep_exist ) { uint16_t mData = HAL_WORD_REG_READ((EEPROM_CTRL_BASE+H_EEPROM_CTRL)); if( mData&B_EEP_CTRL_NOT_PRESENT ) return RET_NOT_EXIST; else if ( mData&B_EEP_CTRL_CORRUPT ) return RET_EEP_CORRUPT; else { eep_exist = TRUE; return RET_SUCCESS; } } else // already done the checking, fast response return RET_SUCCESS; } return RET_NOT_INIT; }
void app_start() { uint32_t rst_status; A_HOSTIF hostif; #if defined(PROJECT_MAGPIE) T_EEP_RET retEEP; #endif /* Zero BSS segment & dynamic memory section. */ init_mem(); #if defined(PROJECT_MAGPIE) fatal_exception_func(); #endif if( IS_FLASHBOOT() ) { athos_indirection_table_install(); DBG_MODULE_INSTALL(); A_CLOCK_INIT(SYSTEM_CLK); A_UART_INIT(); A_PRINTF_INIT(); A_DBG_INIT(); A_EEP_INIT(); A_TASKLET_INIT(); _indir_tbl.cmnos.timer._timer_init(); #if defined(PROJECT_K2) /* * WAR: these variable is not initialized when boot from flash * either re-enumeration or config them to default value = 0 would fix the issue */ u8UsbInterfaceAlternateSetting = u8UsbConfigValue = u8UsbInterfaceValue = 0; #endif } #ifdef ROM_VER_1_1 else A_EEP_INIT(); /*Required for 1_1*/ #endif #if defined(PROJECT_MAGPIE) retEEP = A_EEP_IS_EXIST(); bJumptoFlash = FALSE; if ( RET_SUCCESS == retEEP ) { bEepromExist = TRUE; } else { bEepromExist = FALSE; } #endif hostif = A_IS_HOST_PRESENT(); #if defined(PROJECT_MAGPIE) rst_status = *((volatile uint32_t*)WATCH_DOG_MAGIC_PATTERN_ADDR); #elif defined(PROJECT_K2) rst_status = HAL_WORD_REG_READ(MAGPIE_REG_RST_STATUS_ADDR); #endif /* #if defined(PROJECT_MAGPIE) */ A_PRINTF(" A_WDT_INIT()\n\r"); #if defined(PROJECT_K2) save_cmnos_printf = fw_cmnos_printf; #endif if( hostif == HIF_USB ) { #if defined(PROJECT_K2) #if MOVE_PRINT_TO_RAM save_cmnos_printf = _indir_tbl.cmnos.printf._printf; _indir_tbl.cmnos.printf._printf = fw_cmnos_printf; #endif _indir_tbl.cmnos.usb._usb_fw_task = _fw_usb_fw_task; _indir_tbl.cmnos.usb._usb_reset_fifo = _fw_usb_reset_fifo; #endif } if( rst_status == WDT_MAGIC_PATTERN ) { A_PRINTF(" ==>WDT reset<==\n"); #if defined(PROJECT_MAGPIE) reset_EP4_FIFO(); #endif *((volatile uint32_t*)WATCH_DOG_RESET_COUNTER_ADDR)+=1; } else if (rst_status == SUS_MAGIC_PATTERN) { A_PRINTF(" ==>warm start<==\n"); } else A_PRINTF(" ==>cold start<==\n"); #if defined(PROJECT_MAGPIE) *((volatile uint32_t*)WATCH_DOG_MAGIC_PATTERN_ADDR)=WDT_MAGIC_PATTERN; #elif defined(PROJECT_K2) HAL_WORD_REG_WRITE(MAGPIE_REG_RST_STATUS_ADDR, WDT_MAGIC_PATTERN); #endif /* #if defined(PROJECT_MAGPIE) */ /* intr enable would left for firmware */ /* athos_interrupt_init(); */ DBG_MODULE_INSTALL(); #if defined(PROJECT_K2) A_DBG_INIT(); #endif #if defined(PROJECT_K2) #if SYSTEM_MODULE_SFLASH SFLASH_MODULE_INSTALL(); A_SFLASH_INIT(); #endif #endif HIF_MODULE_INSTALL(); HTC_MODULE_INSTALL(); WMI_SERVICE_MODULE_INSTALL(); BUF_POOL_MODULE_INSTALL(); VBUF_MODULE_INSTALL(); VDESC_MODULE_INSTALL(); //init each module, should be put together.. A_PRINTF("ALLOCRAM start 0x%x size %d\n", ALLOCRAM_START, ALLOCRAM_SIZE); A_ALLOCRAM_INIT(ALLOCRAM_START, ALLOCRAM_SIZE); if( hostif == HIF_USB ) { _indir_tbl.hif._get_max_msg_len = _HIFusb_get_max_msg_len_patch; _indir_tbl.cmnos.usb._usb_reg_out = vUsb_Reg_Out_patch; _indir_tbl.hif._isr_handler = _HIFusb_isr_handler_patch; _indir_tbl.cmnos.usb._usb_set_configuration = bSet_configuration_patch; _indir_tbl.cmnos.usb._usb_status_in = vUsb_Status_In_patch; _indir_tbl.cmnos.usb._usb_get_descriptor = bGet_descriptor_patch; _indir_tbl.cmnos.usb._usb_standard_cmd = bStandardCommand_patch; _indir_tbl.usbfifo_api._init = _fw_usbfifo_init; #if defined(PROJECT_MAGPIE) _indir_tbl.cmnos.usb._usb_power_off = zfTurnOffPower_patch; _indir_tbl.cmnos.usb._usb_reset_fifo = zfResetUSBFIFO_patch; _indir_tbl.hif._start = _HIFusb_start_patch; _indir_tbl.htc._HTC_MsgRecvHandler = HTCMsgRecvHandler_patch; _indir_tbl.htc._HTC_ControlSvcProcessMsg = HTCControlSvcProcessMsg_patch; #endif if (!(USB_BYTE_REG_READ(ZM_MAIN_CTRL_OFFSET)&BIT6)) { vUSBFIFO_EP6Cfg_FS_patch(); } #ifdef FUSION_USB_ENABLE_TX_STREAM // For K2, enable tx stream mode A_PRINTF("Enable Tx Stream mode: 0x%x\r\n", USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)); // Patch for K2 USB STREAM mode USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, \ (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)&(~BIT0))); // disable down stream DMA mode USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, ((USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|BIT6))); #if SYSTEM_MODULE_HP_EP5 USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, ((USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|BIT8))); #endif #if SYSTEM_MODULE_HP_EP6 USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, ((USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|BIT9))); #endif USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|(BIT0))); // enable down stream DMA mode #endif #ifdef FUSION_USB_ENABLE_RX_STREAM // Patch for K2 USB STREAM mode USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, \ (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)&(~BIT1))); // disable upstream DMA mode USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, \ (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)&(~BIT3))); // enable upstream stream mode // K2, Set maximum IN transfer to 8K USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, \ (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)&(0xcf))); USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, \ (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|(0x20))); USB_WORD_REG_WRITE(ZM_SOC_USB_MODE_CTRL_OFFSET, (USB_WORD_REG_READ(ZM_SOC_USB_MODE_CTRL_OFFSET)|(BIT1))); // enable upstream DMA mode USB_WORD_REG_WRITE(ZM_SOC_USB_TIME_CTRL_OFFSET, 0xa0); // set stream mode timeout critirea #if defined(PROJECT_K2) /*0x10004020 is vaild in k2 but could be invaild in other chip*/ if ((HAL_WORD_REG_READ(0x10004020) & 0x2000) != 0) { /* disable stream mode for AR9270 */ USB_WORD_REG_WRITE(ZM_SOC_USB_MAX_AGGREGATE_OFFSET, 0); } else { /* enable stream mode for AR9271 */ USB_WORD_REG_WRITE(ZM_SOC_USB_MAX_AGGREGATE_OFFSET, 9); } #else USB_WORD_REG_WRITE(ZM_SOC_USB_MAX_AGGREGATE_OFFSET, 9); #endif #endif } #if defined(PROJECT_MAGPIE) && !defined(ROM_VER_1_1) else if (hostif == HIF_PCI ) hif_pci_patch_install(&_indir_tbl.hif); #endif A_PRINTF("USB mode: 0x%x\r\n", USB_WORD_REG_READ(0x100)); // patch the clock function if(1) { _indir_tbl.cmnos.clock._clock_init = cmnos_clock_init_patch; _indir_tbl.cmnos.clock._refclk_speed_get = cmnos_refclk_speed_get_patch; _indir_tbl.cmnos.clock._delay_us = cmnos_delay_us_patch; _indir_tbl.cmnos.clock._clock_tick = cmnos_tick_patch; _indir_tbl.cmnos.clock._milliseconds = cmnos_milliseconds_patch; //default clock, setup initial variable, SYSTEM_FREQ=40 A_CLOCK_INIT(SYSTEM_FREQ); } Magpie_init(); #if MAGPIE_ENABLE_WLAN == 1 HAL_WORD_REG_WRITE(MAGPIE_REG_RST_RESET_ADDR, (HAL_WORD_REG_READ(MAGPIE_REG_RST_RESET_ADDR)&(~(BIT10|BIT8|BIT7|BIT6)))); #if defined(PROJECT_MAGPIE) HAL_WORD_REG_WRITE(MAGPIE_REG_AHB_ARB_ADDR, (HAL_WORD_REG_READ(MAGPIE_REG_AHB_ARB_ADDR)|BIT1)); #endif wlan_pci_module_init(); wlan_pci_probe(); #endif A_PRINTF("Tgt running\n\r"); #if defined(PROJECT_MAGPIE) if(1) { A_PRINTF("======= Apply MISC Assert patch\n\r"); _assfail_ori = _indir_tbl.cmnos.misc._assfail; _indir_tbl.cmnos.misc._assfail = exception_reset; } change_magpie_clk(); #endif wlan_task(); //never return }
/*!- Initialize eeprom, actually we link up the pcie_rc for accessing the eeprom in client card * * Ryan - Add setup for PLL, refer to bug#37418 * * 5. clear PCIE_RC_PLL PCIE_PHY_SHIFT, PCIE_PHY, PCIE_RC rst bit * 6. clear PCIE_PLL bypass mode and PWD bit (BIT16 and BIT18) * 7. set bus master and memory space enable * 8. set app_ltssm_enable * * 200ns in each access * */ LOCAL void cmnos_eep_init(void) { uint32_t mStsData; volatile int32_t i = 10000; volatile reg_value = 0x0; #if defined(PROJECT_MAGPIE) if( TRUE != eep_state ) { DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x40; /* 5 */ #if defined(MAGPIE_FPGA) if (*(volatile uint32_t *)(WATCH_DOG_MAGIC_PATTERN_ADDR) == WDT_MAGIC_PATTERN ) { // fpga will hang since external pcie_rc is not able to reset, do a wdt check here, and avoid toching pcie_rc phy reset // not know will real chip have same issue, ryan // DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x41; /* // Paddu sugguest to remove these, since PCIE_RC's reset state is 1 already // HAL_WORD_REG_WRITE(MAGPIE_REG_RST_RESET_ADDR, \ (HAL_WORD_REG_READ(MAGPIE_REG_RST_RESET_ADDR)| \ (PCI_RC_PLL_RESET_BIT|PCI_RC_RESET_BIT))); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x42; */ HAL_WORD_REG_WRITE(MAGPIE_REG_RST_RESET_ADDR, \ (HAL_WORD_REG_READ(MAGPIE_REG_RST_RESET_ADDR)& \ (~(PCI_RC_PLL_RESET_BIT|PCI_RC_RESET_BIT)))); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); } else #endif { /* // Paddu sugguest to remove these, since PCIE_RC's reset state is 1 already // rom1.0 fix: looks like resetting the rc even already in reset state is fine // but this would fix the eeprom-less issue, when we do the 2n init */ /* asser the reset to pcie_rc */ DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x43; CMD_PCI_RC_RESET_ON(); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); /* dereset the reset */ DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x44; CMD_PCI_RC_RESET_CLR(); A_DELAY_USECS(500); } /*! * Ryan - clr MAGPIE_REG_AHB_ARB_ADDR, BIT1 is needed no mater FPGA or ASIC */ //#if defined(MAGPIE_FPGA) // workaround for FPGA, do we need to enable the PCIE_RC DMA just for accessing the EEPROM? //HAL_WORD_REG_WRITE(0x00050018, 0x6);, purpose is to enable pcie_rc access internal memory //HAL_WORD_REG_WRITE(MAGPIE_REG_AHB_ARB_ADDR, (HAL_WORD_REG_READ(MAGPIE_REG_AHB_ARB_ADDR)|(BIT1|BIT2))); DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x49; HAL_WORD_REG_WRITE(MAGPIE_REG_AHB_ARB_ADDR, (HAL_WORD_REG_READ(MAGPIE_REG_AHB_ARB_ADDR)|(BIT1))); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); //#endif /* 7.5. asser pcie_ep reset */ HAL_WORD_REG_WRITE(0x00040018, (HAL_WORD_REG_READ(0x00040018) & ~(0x1 << 2))); #if defined(MAGPIE_ASIC) /* PLL setup should be ASIC/DV specific */ /* 6. set PCIE_PLL in bypass mode, and get out of power-down, */ DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x50; HAL_WORD_REG_WRITE(MAGPIE_REG_PCIE_PLL_CONFIG_ADDR, \ (HAL_WORD_REG_READ(MAGPIE_REG_PCIE_PLL_CONFIG_ADDR)&(~(BIT16|BIT18)))); /* 100us delay wait for PCIE PLL stable */ A_DELAY_USECS(100); #endif /* 7. set bus master and memory space enable */ DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x45; HAL_WORD_REG_WRITE(0x00020004, (HAL_WORD_REG_READ(0x00020004)|(BIT1|BIT2))); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); /* 7.5. de-asser pcie_ep reset */ HAL_WORD_REG_WRITE(0x00040018, (HAL_WORD_REG_READ(0x00040018)|(0x1 << 2))); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); /* 8. set app_ltssm_enable */ DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x46; HAL_WORD_REG_WRITE(0x00040000, (HAL_WORD_REG_READ(0x00040000)|0xffc1)); /*! * Receive control (PCIE_RESET), * 0x40018, BIT0: LINK_UP, PHY Link up -PHY Link up/down indicator * in case the link up is not ready and we access the 0x14000000, * vmc will hang here */ /* poll 0x40018/bit0 (1000 times) until it turns to 1 */ while(i-->0) { reg_value = HAL_WORD_REG_READ(0x00040018); if( reg_value & BIT0 ) break; A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); } /* init fail, can't detect PCI_RC LINK UP, give up the init */ if( i<=0 ) { DEBUG_SYSTEM_STATE |= BIT26; goto ERR_DONE; } DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x47; HAL_WORD_REG_WRITE(0x14000004, (HAL_WORD_REG_READ(0x14000004)|0x116)); A_DELAY_USECS(PCIE_RC_ACCESS_DELAY); DEBUG_SYSTEM_STATE = (DEBUG_SYSTEM_STATE&(~0xff)) | 0x48; HAL_WORD_REG_WRITE(0x14000010, (HAL_WORD_REG_READ(0x14000010)|EEPROM_CTRL_BASE)); eep_state = TRUE; } #elif defined(PROJECT_K2) eep_state = TRUE; #endif /* End of #if defined(PROJECT_MAGPIE) */ if (TRUE == eep_state) { /* Read offset 1 location to determine if this EEPROM is protected somewhere */ HAL_WORD_REG_READ(EEPROM_ADDR_BASE + 4); while(1) { mStsData = HAL_WORD_REG_READ((EEPROM_CTRL_BASE+H_EEPROM_STS_DATA)); /* If this location is protected or EEPROM does not exist, return immediately */ if ( mStsData & (B_EEP_STS_PROTECTED | B_EEP_STS_DATA_NOT_EXIST) ) { eep_state = FALSE; break; } if ( ( mStsData & (B_EEP_STS_STATE_BUSY | B_EEP_STS_IS_BUSY) ) == 0 ) { if (mStsData & 0xffff) cmnos_eeprom_write_hword( (uint16_t)1, (uint16_t)0 ); break; } A_DELAY_USECS(100); } } ERR_DONE: } void cmnos_eep_module_install(struct eep_api *tbl) { tbl->_eep_init = cmnos_eep_init; tbl->_eep_read = cmnos_eep_read; tbl->_eep_write = cmnos_eep_write; tbl->_eep_is_exist = cmnos_eep_is_exist; }