int hw_atl_utils_fw_downld_dwords(struct aq_hw_s *self, u32 a, u32 *p, u32 cnt) { int err = 0; AQ_HW_WAIT_FOR(hw_atl_reg_glb_cpu_sem_get(self, HW_ATL_FW_SM_RAM) == 1U, 1U, 10000U); if (err < 0) { bool is_locked; hw_atl_reg_glb_cpu_sem_set(self, 1U, HW_ATL_FW_SM_RAM); is_locked = hw_atl_reg_glb_cpu_sem_get(self, HW_ATL_FW_SM_RAM); if (!is_locked) { err = -ETIMEDOUT; goto err_exit; } } aq_hw_write_reg(self, HW_ATL_MIF_ADDR, a); for (++cnt; --cnt && !err;) { aq_hw_write_reg(self, HW_ATL_MIF_CMD, 0x00008000U); if (IS_CHIP_FEATURE(REVISION_B1)) AQ_HW_WAIT_FOR(a != aq_hw_read_reg(self, HW_ATL_MIF_ADDR), 1, 1000U); else AQ_HW_WAIT_FOR(!(0x100 & aq_hw_read_reg(self, HW_ATL_MIF_CMD)), 1, 1000U); *(p++) = aq_hw_read_reg(self, HW_ATL_MIF_VAL); a += 4; } hw_atl_reg_glb_cpu_sem_set(self, 1U, HW_ATL_FW_SM_RAM); err_exit: return err; }
int hw_atl_utils_fw_upload_dwords(struct aq_hw_s *self, u32 a, u32 *p, u32 cnt) { int err = 0; bool is_locked; is_locked = hw_atl_reg_glb_cpu_sem_get(self, HW_ATL_FW_SM_RAM); if (!is_locked) { err = -ETIMEDOUT; goto err_exit; } if (IS_CHIP_FEATURE(REVISION_B1)) { u32 offset = 0; for (; offset < cnt; ++offset) { aq_hw_write_reg(self, 0x328, p[offset]); aq_hw_write_reg(self, 0x32C, (0x80000000 | (0xFFFF & (offset * 4)))); hw_atl_mcp_up_force_intr_set(self, 1); /* 1000 times by 10us = 10ms */ AQ_HW_WAIT_FOR((aq_hw_read_reg(self, 0x32C) & 0xF0000000) != 0x80000000, 10, 1000); } } else { u32 offset = 0; aq_hw_write_reg(self, 0x208, a); for (; offset < cnt; ++offset) { aq_hw_write_reg(self, 0x20C, p[offset]); aq_hw_write_reg(self, 0x200, 0xC000); AQ_HW_WAIT_FOR((aq_hw_read_reg(self, 0x200U) & 0x100) == 0, 10, 1000); } } hw_atl_reg_glb_cpu_sem_set(self, 1U, HW_ATL_FW_SM_RAM); err_exit: return err; }
void hw_atl_utils_mpi_read_stats(struct aq_hw_s *self, struct hw_aq_atl_utils_mbox *pmbox) { int err = 0; err = hw_atl_utils_fw_downld_dwords(self, self->mbox_addr, (u32 *)(void *)pmbox, sizeof(*pmbox) / sizeof(u32)); if (err < 0) goto err_exit; if (IS_CHIP_FEATURE(REVISION_A0)) { unsigned int mtu = 1514; pmbox->stats.ubrc = pmbox->stats.uprc * mtu; pmbox->stats.ubtc = pmbox->stats.uptc * mtu; } else { pmbox->stats.dpc = hw_atl_rpb_rx_dma_drop_pkt_cnt_get(self); } err_exit:; }
int hw_atl_utils_fw_rpc_call(struct aq_hw_s *self, unsigned int rpc_size) { int err = 0; struct aq_hw_atl_utils_fw_rpc_tid_s sw; if (!IS_CHIP_FEATURE(MIPS)) { err = -1; goto err_exit; } err = hw_atl_utils_fw_upload_dwords(self, self->rpc_addr, (u32 *)(void *)&self->rpc, (rpc_size + sizeof(u32) - sizeof(u8)) / sizeof(u32)); if (err < 0) goto err_exit; sw.tid = 0xFFFFU & (++self->rpc_tid); sw.len = (u16)rpc_size; aq_hw_write_reg(self, HW_ATL_RPC_CONTROL_ADR, sw.val); err_exit: return err; }
void hw_atl_utils_mpi_read_stats(struct aq_hw_s *self, struct hw_aq_atl_utils_mbox *pmbox) { int err = 0; err = hw_atl_utils_fw_downld_dwords(self, self->mbox_addr, (u32 *)(void *)pmbox, sizeof(*pmbox) / sizeof(u32)); if (err < 0) goto err_exit; if (IS_CHIP_FEATURE(REVISION_A0)) { unsigned int mtu = self->aq_nic_cfg ? self->aq_nic_cfg->mtu : 1514U; pmbox->stats.ubrc = pmbox->stats.uprc * mtu; pmbox->stats.ubtc = pmbox->stats.uptc * mtu; pmbox->stats.dpc = atomic_read(&self->dpc); } else { pmbox->stats.dpc = hw_atl_reg_rx_dma_stat_counter7get(self); } err_exit:; }