static inline int sd_rw_cmd(struct mmc_command *cmd) { return mmc_op_multi(cmd->opcode) || (cmd->opcode == MMC_READ_SINGLE_BLOCK) || (cmd->opcode == MMC_WRITE_BLOCK); }
static void sd_request(struct work_struct *work) { struct realtek_pci_sdmmc *host = container_of(work, struct realtek_pci_sdmmc, work); struct rtsx_pcr *pcr = host->pcr; struct mmc_host *mmc = host->mmc; struct mmc_request *mrq = host->mrq; struct mmc_command *cmd = mrq->cmd; struct mmc_data *data = mrq->data; unsigned int data_size = 0; int err; if (host->eject) { cmd->error = -ENOMEDIUM; goto finish; } err = rtsx_pci_card_exclusive_check(host->pcr, RTSX_SD_CARD); if (err) { cmd->error = err; goto finish; } mutex_lock(&pcr->pcr_mutex); rtsx_pci_start_run(pcr); rtsx_pci_switch_clock(pcr, host->clock, host->ssc_depth, host->initial_mode, host->double_clk, host->vpclk); rtsx_pci_write_register(pcr, CARD_SELECT, 0x07, SD_MOD_SEL); rtsx_pci_write_register(pcr, CARD_SHARE_MODE, CARD_SHARE_MASK, CARD_SHARE_48_SD); mutex_lock(&host->host_mutex); host->mrq = mrq; mutex_unlock(&host->host_mutex); if (mrq->data) data_size = data->blocks * data->blksz; if (!data_size || sd_rw_cmd(cmd)) { sd_send_cmd_get_rsp(host, cmd); if (!cmd->error && data_size) { sd_rw_multi(host, mrq); if (!host->using_cookie) sdmmc_post_req(host->mmc, host->mrq, 0); if (mmc_op_multi(cmd->opcode) && mrq->stop) sd_send_cmd_get_rsp(host, mrq->stop); } } else { sd_normal_rw(host, mrq); } if (mrq->data) { if (cmd->error || data->error) data->bytes_xfered = 0; else data->bytes_xfered = data->blocks * data->blksz; } mutex_unlock(&pcr->pcr_mutex); finish: if (cmd->error) dev_dbg(sdmmc_dev(host), "cmd->error = %d\n", cmd->error); mutex_lock(&host->host_mutex); host->mrq = NULL; mutex_unlock(&host->host_mutex); mmc_request_done(mmc, mrq); }
static void sdmmc_request(struct mmc_host *mmc, struct mmc_request *mrq) { struct realtek_pci_sdmmc *host = mmc_priv(mmc); struct rtsx_pcr *pcr = host->pcr; struct mmc_command *cmd = mrq->cmd; struct mmc_data *data = mrq->data; unsigned int data_size = 0; if (host->eject) { cmd->error = -ENOMEDIUM; goto finish; } mutex_lock(&pcr->pcr_mutex); rtsx_pci_start_run(pcr); rtsx_pci_switch_clock(pcr, host->clock, host->ssc_depth, host->initial_mode, host->double_clk, host->vpclk); rtsx_pci_write_register(pcr, CARD_SELECT, 0x07, SD_MOD_SEL); rtsx_pci_write_register(pcr, CARD_SHARE_MODE, CARD_SHARE_MASK, CARD_SHARE_48_SD); mutex_lock(&host->host_mutex); host->mrq = mrq; mutex_unlock(&host->host_mutex); if (mrq->data) data_size = data->blocks * data->blksz; if (!data_size || mmc_op_multi(cmd->opcode) || (cmd->opcode == MMC_READ_SINGLE_BLOCK) || (cmd->opcode == MMC_WRITE_BLOCK)) { sd_send_cmd_get_rsp(host, cmd); if (!cmd->error && data_size) { sd_rw_multi(host, mrq); if (mmc_op_multi(cmd->opcode) && mrq->stop) sd_send_cmd_get_rsp(host, mrq->stop); } } else { sd_normal_rw(host, mrq); } if (mrq->data) { if (cmd->error || data->error) data->bytes_xfered = 0; else data->bytes_xfered = data->blocks * data->blksz; } mutex_unlock(&pcr->pcr_mutex); finish: if (cmd->error) dev_dbg(sdmmc_dev(host), "cmd->error = %d\n", cmd->error); mutex_lock(&host->host_mutex); host->mrq = NULL; mutex_unlock(&host->host_mutex); mmc_request_done(mmc, mrq); }