int rtl88eu_download_fw(struct adapter *adapt) { struct dvobj_priv *dvobj = adapter_to_dvobj(adapt); struct device *device = dvobj_to_dev(dvobj); const struct firmware *fw; const char fw_name[] = "rtlwifi/rtl8188eufw.bin"; struct rtl92c_firmware_header *pfwheader = NULL; u8 *download_data, *fw_data; size_t download_size; unsigned int trailing_zeros_length; if (request_firmware(&fw, fw_name, device)) { dev_err(device, "Firmware %s not available\n", fw_name); return -ENOENT; } if (fw->size > FW_8188E_SIZE) { dev_err(device, "Firmware size exceed 0x%X. Check it.\n", FW_8188E_SIZE); release_firmware(fw); return -1; } trailing_zeros_length = (4 - fw->size % 4) % 4; fw_data = kmalloc(fw->size + trailing_zeros_length, GFP_KERNEL); if (!fw_data) { release_firmware(fw); return -ENOMEM; } memcpy(fw_data, fw->data, fw->size); memset(fw_data + fw->size, 0, trailing_zeros_length); pfwheader = (struct rtl92c_firmware_header *)fw_data; if (IS_FW_HEADER_EXIST(pfwheader)) { download_data = fw_data + 32; download_size = fw->size + trailing_zeros_length - 32; } else { download_data = fw_data; download_size = fw->size + trailing_zeros_length; } release_firmware(fw); if (usb_read8(adapt, REG_MCUFWDL) & RAM_DL_SEL) { usb_write8(adapt, REG_MCUFWDL, 0); rtl88e_firmware_selfreset(adapt); } _rtl88e_enable_fw_download(adapt, true); usb_write8(adapt, REG_MCUFWDL, usb_read8(adapt, REG_MCUFWDL) | FWDL_ChkSum_rpt); _rtl88e_write_fw(adapt, download_data, download_size); _rtl88e_enable_fw_download(adapt, false); kfree(fw_data); return _rtl88e_fw_free_to_go(adapt); }
static void hal_notch_filter_8188e(struct adapter *adapter, bool enable) { if (enable) { DBG_88E("Enable notch filter\n"); usb_write8(adapter, rOFDM0_RxDSP+1, usb_read8(adapter, rOFDM0_RxDSP+1) | BIT(1)); } else { DBG_88E("Disable notch filter\n"); usb_write8(adapter, rOFDM0_RxDSP+1, usb_read8(adapter, rOFDM0_RxDSP+1) & ~BIT(1)); } }
static void _rtl88e_enable_fw_download(struct adapter *adapt, bool enable) { u8 tmp; if (enable) { tmp = usb_read8(adapt, REG_MCUFWDL); usb_write8(adapt, REG_MCUFWDL, tmp | 0x01); tmp = usb_read8(adapt, REG_MCUFWDL + 2); usb_write8(adapt, REG_MCUFWDL + 2, tmp & 0xf7); } else { tmp = usb_read8(adapt, REG_MCUFWDL); usb_write8(adapt, REG_MCUFWDL, tmp & 0xfe); usb_write8(adapt, REG_MCUFWDL + 1, 0x00); } }
static void rtl88e_firmware_selfreset(struct adapter *adapt) { u8 u1b_tmp; u1b_tmp = usb_read8(adapt, REG_SYS_FUNC_EN+1); usb_write8(adapt, REG_SYS_FUNC_EN+1, (u1b_tmp & (~BIT(2)))); usb_write8(adapt, REG_SYS_FUNC_EN+1, (u1b_tmp | BIT(2))); }
void _8051Reset88E(struct adapter *padapter) { u8 u1bTmp; u1bTmp = usb_read8(padapter, REG_SYS_FUNC_EN+1); usb_write8(padapter, REG_SYS_FUNC_EN+1, u1bTmp&(~BIT(2))); usb_write8(padapter, REG_SYS_FUNC_EN+1, u1bTmp|(BIT(2))); DBG_88E("=====> _8051Reset88E(): 8051 reset success .\n"); }
/* Initialize GPIO setting registers */ static void dm_InitGPIOSetting(struct adapter *Adapter) { u8 tmp1byte; tmp1byte = usb_read8(Adapter, REG_GPIO_MUXCFG); tmp1byte &= (GPIOSEL_GPIO | ~GPIOSEL_ENBT); usb_write8(Adapter, REG_GPIO_MUXCFG, tmp1byte); }
/* Turn off LED according to LedPin specified. */ void SwLedOff(struct adapter *padapter, struct LED_871x *pLed) { u8 LedCfg; if (padapter->bSurpriseRemoved || padapter->bDriverStopped) goto exit; LedCfg = usb_read8(padapter, REG_LEDCFG2);/* 0x4E */ /* Open-drain arrangement for controlling the LED) */ LedCfg &= 0x90; /* Set to software control. */ usb_write8(padapter, REG_LEDCFG2, (LedCfg | BIT(3))); LedCfg = usb_read8(padapter, REG_MAC_PINMUX_CFG); LedCfg &= 0xFE; usb_write8(padapter, REG_MAC_PINMUX_CFG, LedCfg); exit: pLed->bLedOn = false; }
/* Turn on LED according to LedPin specified. */ void SwLedOn(struct adapter *padapter, struct LED_871x *pLed) { u8 LedCfg; if (padapter->bSurpriseRemoved || padapter->bDriverStopped) return; LedCfg = usb_read8(padapter, REG_LEDCFG2); usb_write8(padapter, REG_LEDCFG2, (LedCfg&0xf0) | BIT(5) | BIT(6)); /* SW control led0 on. */ pLed->bLedOn = true; }
static void _rtl88e_fw_page_write(struct adapter *adapt, u32 page, const u8 *buffer, u32 size) { u8 value8; u8 u8page = (u8)(page & 0x07); value8 = (usb_read8(adapt, REG_MCUFWDL + 2) & 0xF8) | u8page; usb_write8(adapt, (REG_MCUFWDL + 2), value8); _rtl88e_fw_block_write(adapt, buffer, size); }
void iol_mode_enable(struct adapter *padapter, u8 enable) { u8 reg_0xf0 = 0; if (enable) { /* Enable initial offload */ reg_0xf0 = usb_read8(padapter, REG_SYS_CFG); usb_write8(padapter, REG_SYS_CFG, reg_0xf0|SW_OFFLOAD_EN); if (!padapter->bFWReady) { DBG_88E("bFWReady == false call reset 8051...\n"); _8051Reset88E(padapter); } } else { /* disable initial offload */ reg_0xf0 = usb_read8(padapter, REG_SYS_CFG); usb_write8(padapter, REG_SYS_CFG, reg_0xf0 & ~SW_OFFLOAD_EN); } }
s32 iol_execute(struct adapter *padapter, u8 control) { s32 status = _FAIL; u8 reg_0x88 = 0; unsigned long start = 0; control = control&0x0f; reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0); usb_write8(padapter, REG_HMEBOX_E0, reg_0x88|control); start = jiffies; while ((reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0)) & control && jiffies_to_msecs(jiffies - start) < 1000) { udelay(5); } reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0); status = (reg_0x88 & control) ? _FAIL : _SUCCESS; if (reg_0x88 & control<<4) status = _FAIL; return status; }
s32 iol_execute(struct adapter *padapter, u8 control) { s32 status = _FAIL; u8 reg_0x88 = 0; u32 start = 0, passing_time = 0; control = control&0x0f; reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0); usb_write8(padapter, REG_HMEBOX_E0, reg_0x88|control); start = jiffies; while ((reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0)) & control && (passing_time = rtw_get_passing_time_ms(start)) < 1000) { ; } reg_0x88 = usb_read8(padapter, REG_HMEBOX_E0); status = (reg_0x88 & control) ? _FAIL : _SUCCESS; if (reg_0x88 & control<<4) status = _FAIL; return status; }
/* This routine deals with the Power Configuration CMDs parsing * for RTL8723/RTL8188E Series IC. */ u8 rtl88eu_pwrseqcmdparsing(struct adapter *padapter, u8 cut_vers, struct wl_pwr_cfg pwrseqcmd[]) { struct wl_pwr_cfg pwrcfgcmd = {0}; u8 poll_bit = false; u32 aryidx = 0; u8 value = 0; u32 offset = 0; u32 poll_count = 0; /* polling autoload done. */ u32 max_poll_count = 5000; do { pwrcfgcmd = pwrseqcmd[aryidx]; RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: offset(%#x) cut_msk(%#x)" " cmd(%#x)" "msk(%#x) value(%#x)\n", GET_PWR_CFG_OFFSET(pwrcfgcmd), GET_PWR_CFG_CUT_MASK(pwrcfgcmd), GET_PWR_CFG_CMD(pwrcfgcmd), GET_PWR_CFG_MASK(pwrcfgcmd), GET_PWR_CFG_VALUE(pwrcfgcmd))); /* Only Handle the command whose CUT is matched */ if (GET_PWR_CFG_CUT_MASK(pwrcfgcmd) & cut_vers) { switch (GET_PWR_CFG_CMD(pwrcfgcmd)) { case PWR_CMD_READ: RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: PWR_CMD_READ\n")); break; case PWR_CMD_WRITE: RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: PWR_CMD_WRITE\n")); offset = GET_PWR_CFG_OFFSET(pwrcfgcmd); /* Read the value from system register */ value = usb_read8(padapter, offset); value &= ~(GET_PWR_CFG_MASK(pwrcfgcmd)); value |= (GET_PWR_CFG_VALUE(pwrcfgcmd) & GET_PWR_CFG_MASK(pwrcfgcmd)); /* Write the value back to system register */ usb_write8(padapter, offset, value); break; case PWR_CMD_POLLING: RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: PWR_CMD_POLLING\n")); poll_bit = false; offset = GET_PWR_CFG_OFFSET(pwrcfgcmd); do { value = usb_read8(padapter, offset); value &= GET_PWR_CFG_MASK(pwrcfgcmd); if (value == (GET_PWR_CFG_VALUE(pwrcfgcmd) & GET_PWR_CFG_MASK(pwrcfgcmd))) poll_bit = true; else udelay(10); if (poll_count++ > max_poll_count) { DBG_88E("Fail to polling Offset[%#x]\n", offset); return false; } } while (!poll_bit); break; case PWR_CMD_DELAY: RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: PWR_CMD_DELAY\n")); if (GET_PWR_CFG_VALUE(pwrcfgcmd) == PWRSEQ_DELAY_US) udelay(GET_PWR_CFG_OFFSET(pwrcfgcmd)); else udelay(GET_PWR_CFG_OFFSET(pwrcfgcmd)*1000); break; case PWR_CMD_END: /* When this command is parsed, end the process */ RT_TRACE(_module_hal_init_c_, _drv_info_, ("rtl88eu_pwrseqcmdparsing: PWR_CMD_END\n")); return true; default: RT_TRACE(_module_hal_init_c_, _drv_err_, ("rtl88eu_pwrseqcmdparsing: Unknown CMD!!\n")); break; } } aryidx++;/* Add Array Index */ } while (1); return true; }
int proc_get_read_reg(char *page, char **start, off_t offset, int count, int *eof, void *data) { struct net_device *dev = data; struct adapter *padapter = (struct adapter *)rtw_netdev_priv(dev); int len = 0; if (proc_get_read_addr == 0xeeeeeeee) { *eof = 1; return len; } switch (proc_get_read_len) { case 1: len += snprintf(page + len, count - len, "usb_read8(0x%x)=0x%x\n", proc_get_read_addr, usb_read8(padapter, proc_get_read_addr)); break; case 2: len += snprintf(page + len, count - len, "usb_read16(0x%x)=0x%x\n", proc_get_read_addr, usb_read16(padapter, proc_get_read_addr)); break; case 4: len += snprintf(page + len, count - len, "usb_read32(0x%x)=0x%x\n", proc_get_read_addr, usb_read32(padapter, proc_get_read_addr)); break; default: len += snprintf(page + len, count - len, "error read length=%d\n", proc_get_read_len); break; } *eof = 1; return len; }