static int mwifiex_sdio_host_to_card(struct mwifiex_adapter *adapter, u8 type, struct sk_buff *skb, struct mwifiex_tx_param *tx_param) { struct sdio_mmc_card *card = adapter->card; int ret; u32 buf_block_len; u32 blk_size; u8 port = CTRL_PORT; u8 *payload = (u8 *)skb->data; u32 pkt_len = skb->len; blk_size = MWIFIEX_SDIO_BLOCK_SIZE; buf_block_len = (pkt_len + blk_size - 1) / blk_size; *(u16 *) &payload[0] = (u16) pkt_len; *(u16 *) &payload[2] = type; if (type == MWIFIEX_TYPE_DATA) { ret = mwifiex_get_wr_port_data(adapter, &port); if (ret) { dev_err(adapter->dev, "%s: no wr_port available\n", __func__); return ret; } } else { adapter->cmd_sent = true; if (pkt_len <= INTF_HEADER_LEN || pkt_len > MWIFIEX_UPLD_SIZE) dev_err(adapter->dev, "%s: payload=%p, nb=%d\n", __func__, payload, pkt_len); } pkt_len = buf_block_len * blk_size; if (tx_param) ret = mwifiex_host_to_card_mp_aggr(adapter, payload, pkt_len, port, tx_param->next_pkt_len ); else ret = mwifiex_host_to_card_mp_aggr(adapter, payload, pkt_len, port, 0); if (ret) { if (type == MWIFIEX_TYPE_CMD) adapter->cmd_sent = false; if (type == MWIFIEX_TYPE_DATA) adapter->data_sent = false; } else { if (type == MWIFIEX_TYPE_DATA) { if (!(card->mp_wr_bitmap & (1 << card->curr_wr_port))) adapter->data_sent = true; else adapter->data_sent = false; } } return ret; }
/* * This function downloads data from driver to card. * * Both commands and data packets are transferred to the card by this * function. * * This function adds the SDIO specific header to the front of the buffer * before transferring. The header contains the length of the packet and * the type. The firmware handles the packets based upon this set type. */ static int mwifiex_sdio_host_to_card(struct mwifiex_adapter *adapter, u8 type, u8 *payload, u32 pkt_len, struct mwifiex_tx_param *tx_param) { struct sdio_mmc_card *card = adapter->card; int ret; u32 buf_block_len; u32 blk_size; u8 port = CTRL_PORT; /* Allocate buffer and copy payload */ blk_size = MWIFIEX_SDIO_BLOCK_SIZE; buf_block_len = (pkt_len + blk_size - 1) / blk_size; *(__le16 *)&payload[0] = cpu_to_le16((u16)pkt_len); *(__le16 *)&payload[2] = cpu_to_le16(type); /* * This is SDIO specific header * u16 length, * u16 type (MWIFIEX_TYPE_DATA = 0, MWIFIEX_TYPE_CMD = 1, * MWIFIEX_TYPE_EVENT = 3) */ if (type == MWIFIEX_TYPE_DATA) { ret = mwifiex_get_wr_port_data(adapter, &port); if (ret) { dev_err(adapter->dev, "%s: no wr_port available\n", __func__); return ret; } } else { adapter->cmd_sent = true; /* Type must be MWIFIEX_TYPE_CMD */ if (pkt_len <= INTF_HEADER_LEN || pkt_len > MWIFIEX_UPLD_SIZE) dev_err(adapter->dev, "%s: payload=%p, nb=%d\n", __func__, payload, pkt_len); } /* Transfer data to card */ pkt_len = buf_block_len * blk_size; if (tx_param) ret = mwifiex_host_to_card_mp_aggr(adapter, payload, pkt_len, port, tx_param->next_pkt_len); else ret = mwifiex_host_to_card_mp_aggr(adapter, payload, pkt_len, port, 0); if (ret) { if (type == MWIFIEX_TYPE_CMD) adapter->cmd_sent = false; if (type == MWIFIEX_TYPE_DATA) adapter->data_sent = false; } else { if (type == MWIFIEX_TYPE_DATA) { if (!(card->mp_wr_bitmap & (1 << card->curr_wr_port))) adapter->data_sent = true; else adapter->data_sent = false; } } return ret; }