/******************************************************************************
 *
 * This file is provided under a dual BSD/GPLv2 license.  When using or
 * redistributing this file, you may do so under either license.
 *
 * GPL LICENSE SUMMARY
 *
 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
 * Copyright(c) 2013 - 2015 Intel Mobile Communications GmbH
 * Copyright(c) 2016 - 2017 Intel Deutschland GmbH
 * Copyright(c) 2018        Intel Corporation
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of version 2 of the GNU General Public License as
 * published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License for more details.
 *
 * The full GNU General Public License is included in this distribution
 * in the file called COPYING.
 *
 * Contact Information:
 *  Intel Linux Wireless <linuxwifi@intel.com>
 * Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
 *
 * BSD LICENSE
 *
 * Copyright(c) 2012 - 2014 Intel Corporation. All rights reserved.
 * Copyright(c) 2013 - 2015 Intel Mobile Communications GmbH
 * Copyright(c) 2016 - 2017 Intel Deutschland GmbH
 * Copyright(c) 2018        Intel Corporation
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 *  * Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *  * Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *  * Neither the name Intel Corporation nor the names of its
 *    contributors may be used to endorse or promote products derived
 *    from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 *
 *****************************************************************************/
#include "iwl-drv.h"
#include "runtime.h"
#include "fw/api/commands.h"

void iwl_free_fw_paging(struct iwl_fw_runtime *fwrt)
{
	int i;

	if (!fwrt->fw_paging_db[0].fw_paging_block)
		return;

	for (i = 0; i < NUM_OF_FW_PAGING_BLOCKS; i++) {
		struct iwl_fw_paging *paging = &fwrt->fw_paging_db[i];

		if (!paging->fw_paging_block) {
			IWL_DEBUG_FW(fwrt,
				     "Paging: block %d already freed, continue to next page\n",
				     i);

			continue;
		}
		dma_unmap_page(fwrt->trans->dev, paging->fw_paging_phys,
			       paging->fw_paging_size, DMA_BIDIRECTIONAL);

		__free_pages(paging->fw_paging_block,
			     get_order(paging->fw_paging_size));
		paging->fw_paging_block = NULL;
	}
	kfree(fwrt->trans->paging_download_buf);
	fwrt->trans->paging_download_buf = NULL;
	fwrt->trans->paging_db = NULL;

	memset(fwrt->fw_paging_db, 0, sizeof(fwrt->fw_paging_db));
}
IWL_EXPORT_SYMBOL(iwl_free_fw_paging);

static int iwl_alloc_fw_paging_mem(struct iwl_fw_runtime *fwrt,
				   const struct fw_img *image)
{
	struct page *block;
	dma_addr_t phys = 0;
	int blk_idx, order, num_of_pages, size, dma_enabled;

	if (fwrt->fw_paging_db[0].fw_paging_block)
		return 0;

	dma_enabled = is_device_dma_capable(fwrt->trans->dev);

	/* ensure BLOCK_2_EXP_SIZE is power of 2 of PAGING_BLOCK_SIZE */
	BUILD_BUG_ON(BIT(BLOCK_2_EXP_SIZE) != PAGING_BLOCK_SIZE);

	num_of_pages = image->paging_mem_size / FW_PAGING_SIZE;
	fwrt->num_of_paging_blk =
		DIV_ROUND_UP(num_of_pages, NUM_OF_PAGE_PER_GROUP);
	fwrt->num_of_pages_in_last_blk =
		num_of_pages -
		NUM_OF_PAGE_PER_GROUP * (fwrt->num_of_paging_blk - 1);

	IWL_DEBUG_FW(fwrt,
		     "Paging: allocating mem for %d paging blocks, each block holds 8 pages, last block holds %d pages\n",
		     fwrt->num_of_paging_blk,
		     fwrt->num_of_pages_in_last_blk);

	/*
	 * Allocate CSS and paging blocks in dram.
	 */
	for (blk_idx = 0; blk_idx < fwrt->num_of_paging_blk + 1; blk_idx++) {
		/* For CSS allocate 4KB, for others PAGING_BLOCK_SIZE (32K) */
		size = blk_idx ? PAGING_BLOCK_SIZE : FW_PAGING_SIZE;
		order = get_order(size);
		block = alloc_pages(GFP_KERNEL, order);
		if (!block) {
			/* free all the previous pages since we failed */
			iwl_free_fw_paging(fwrt);
			return -ENOMEM;
		}

		fwrt->fw_paging_db[blk_idx].fw_paging_block = block;
		fwrt->fw_paging_db[blk_idx].fw_paging_size = size;

		if (dma_enabled) {
			phys = dma_map_page(fwrt->trans->dev, block, 0,
					    PAGE_SIZE << order,
					    DMA_BIDIRECTIONAL);
			if (dma_mapping_error(fwrt->trans->dev, phys)) {
				/*
				 * free the previous pages and the current one
				 * since we failed to map_page.
				 */
				iwl_free_fw_paging(fwrt);
				return -ENOMEM;
			}
			fwrt->fw_paging_db[blk_idx].fw_paging_phys = phys;
		} else {
			fwrt->fw_paging_db[blk_idx].fw_paging_phys =
				PAGING_ADDR_SIG |
				blk_idx << BLOCK_2_EXP_SIZE;
		}

		if (!blk_idx)
			IWL_DEBUG_FW(fwrt,
				     "Paging: allocated 4K(CSS) bytes (order %d) for firmware paging.\n",
				     order);
		else
			IWL_DEBUG_FW(fwrt,
				     "Paging: allocated 32K bytes (order %d) for firmware paging.\n",
				     order);
	}

	return 0;
}

static int iwl_fill_paging_mem(struct iwl_fw_runtime *fwrt,
			       const struct fw_img *image)
{
	int sec_idx, idx, ret;
	u32 offset = 0;

	/*
	 * find where is the paging image start point:
	 * if CPU2 exist and it's in paging format, then the image looks like:
	 * CPU1 sections (2 or more)
	 * CPU1_CPU2_SEPARATOR_SECTION delimiter - separate between CPU1 to CPU2
	 * CPU2 sections (not paged)
	 * PAGING_SEPARATOR_SECTION delimiter - separate between CPU2
	 * non paged to CPU2 paging sec
	 * CPU2 paging CSS
	 * CPU2 paging image (including instruction and data)
	 */
	for (sec_idx = 0; sec_idx < image->num_sec; sec_idx++) {
		if (image->sec[sec_idx].offset == PAGING_SEPARATOR_SECTION) {
			sec_idx++;
			break;
		}
	}

	/*
	 * If paging is enabled there should be at least 2 more sections left
	 * (one for CSS and one for Paging data)
	 */
	if (sec_idx >= image->num_sec - 1) {
		IWL_ERR(fwrt, "Paging: Missing CSS and/or paging sections\n");
		ret = -EINVAL;
		goto err;
	}

	/* copy the CSS block to the dram */
	IWL_DEBUG_FW(fwrt, "Paging: load paging CSS to FW, sec = %d\n",
		     sec_idx);

	if (image->sec[sec_idx].len > fwrt->fw_paging_db[0].fw_paging_size) {
		IWL_ERR(fwrt, "CSS block is larger than paging size\n");
		ret = -EINVAL;
		goto err;
	}

	memcpy(page_address(fwrt->fw_paging_db[0].fw_paging_block),
	       image->sec[sec_idx].data,
	       image->sec[sec_idx].len);
	dma_sync_single_for_device(fwrt->trans->dev,
				   fwrt->fw_paging_db[0].fw_paging_phys,
				   fwrt->fw_paging_db[0].fw_paging_size,
				   DMA_BIDIRECTIONAL);

	IWL_DEBUG_FW(fwrt,
		     "Paging: copied %d CSS bytes to first block\n",
		     fwrt->fw_paging_db[0].fw_paging_size);

	sec_idx++;

	/*
	 * copy the paging blocks to the dram
	 * loop index start from 1 since that CSS block already copied to dram
	 * and CSS index is 0.
	 * loop stop at num_of_paging_blk since that last block is not full.
	 */
	for (idx = 1; idx < fwrt->num_of_paging_blk; idx++) {
		struct iwl_fw_paging *block = &fwrt->fw_paging_db[idx];

		if (block->fw_paging_size > image->sec[sec_idx].len - offset) {
			IWL_ERR(fwrt,
				"Paging: paging size is larger than remaining data in block %d\n",
				idx);
			ret = -EINVAL;
			goto err;
		}

		memcpy(page_address(block->fw_paging_block),
		       image->sec[sec_idx].data + offset,
		       block->fw_paging_size);
		dma_sync_single_for_device(fwrt->trans->dev,
					   block->fw_paging_phys,
					   block->fw_paging_size,
					   DMA_BIDIRECTIONAL);

		IWL_DEBUG_FW(fwrt,
			     "Paging: copied %d paging bytes to block %d\n",
			     block->fw_paging_size, idx);

		offset += block->fw_paging_size;

		if (offset > image->sec[sec_idx].len) {
			IWL_ERR(fwrt,
				"Paging: offset goes over section size\n");
			ret = -EINVAL;
			goto err;
		}
	}

	/* copy the last paging block */
	if (fwrt->num_of_pages_in_last_blk > 0) {
		struct iwl_fw_paging *block = &fwrt->fw_paging_db[idx];

		if (image->sec[sec_idx].len - offset > block->fw_paging_size) {
			IWL_ERR(fwrt,
				"Paging: last block is larger than paging size\n");
			ret = -EINVAL;
			goto err;
		}

		memcpy(page_address(block->fw_paging_block),
		       image->sec[sec_idx].data + offset,
		       image->sec[sec_idx].len - offset);
		dma_sync_single_for_device(fwrt->trans->dev,
					   block->fw_paging_phys,
					   block->fw_paging_size,
					   DMA_BIDIRECTIONAL);

		IWL_DEBUG_FW(fwrt,
			     "Paging: copied %d pages in the last block %d\n",
			     fwrt->num_of_pages_in_last_blk, idx);
	}

	return 0;

err:
	iwl_free_fw_paging(fwrt);
	return ret;
}

static int iwl_save_fw_paging(struct iwl_fw_runtime *fwrt,
			      const struct fw_img *fw)
{
	int ret;

	ret = iwl_alloc_fw_paging_mem(fwrt, fw);
	if (ret)
		return ret;

	return iwl_fill_paging_mem(fwrt, fw);
}

/* send paging cmd to FW in case CPU2 has paging image */
static int iwl_send_paging_cmd(struct iwl_fw_runtime *fwrt,
			       const struct fw_img *fw)
{
	struct iwl_fw_paging_cmd paging_cmd = {
		.flags = cpu_to_le32(PAGING_CMD_IS_SECURED |
				     PAGING_CMD_IS_ENABLED |
				     (fwrt->num_of_pages_in_last_blk <<
				      PAGING_CMD_NUM_OF_PAGES_IN_LAST_GRP_POS)),
		.block_size = cpu_to_le32(BLOCK_2_EXP_SIZE),
		.block_num = cpu_to_le32(fwrt->num_of_paging_blk),
	};
	struct iwl_host_cmd hcmd = {
		.id = iwl_cmd_id(FW_PAGING_BLOCK_CMD, IWL_ALWAYS_LONG_GROUP, 0),
		.len = { sizeof(paging_cmd), },
		.data = { &paging_cmd, },
	};
	int blk_idx;

	/* loop for for all paging blocks + CSS block */
	for (blk_idx = 0; blk_idx < fwrt->num_of_paging_blk + 1; blk_idx++) {
		dma_addr_t addr = fwrt->fw_paging_db[blk_idx].fw_paging_phys;
		__le32 phy_addr;

		addr = addr >> PAGE_2_EXP_SIZE;
		phy_addr = cpu_to_le32(addr);
		paging_cmd.device_phy_addr[blk_idx] = phy_addr;
	}

	return iwl_trans_send_cmd(fwrt->trans, &hcmd);
}

/*
 * Send paging item cmd to FW in case CPU2 has paging image
 */
static int iwl_trans_get_paging_item(struct iwl_fw_runtime *fwrt)
{
	int ret;
	struct iwl_fw_get_item_cmd fw_get_item_cmd = {
		.item_id = cpu_to_le32(IWL_FW_ITEM_ID_PAGING),
	};
	struct iwl_fw_get_item_resp *item_resp;
	struct iwl_host_cmd cmd = {
		.id = iwl_cmd_id(FW_GET_ITEM_CMD, IWL_ALWAYS_LONG_GROUP, 0),
		.flags = CMD_WANT_SKB | CMD_SEND_IN_RFKILL,
		.data = { &fw_get_item_cmd, },
		.len = { sizeof(fw_get_item_cmd), },
	};

	ret = iwl_trans_send_cmd(fwrt->trans, &cmd);
	if (ret) {
		IWL_ERR(fwrt,
			"Paging: Failed to send FW_GET_ITEM_CMD cmd (err = %d)\n",
			ret);
		return ret;
	}

	item_resp = (void *)((struct iwl_rx_packet *)cmd.resp_pkt)->data;
	if (item_resp->item_id != cpu_to_le32(IWL_FW_ITEM_ID_PAGING)) {
		IWL_ERR(fwrt,
			"Paging: got wrong item in FW_GET_ITEM_CMD resp (item_id = %u)\n",
			le32_to_cpu(item_resp->item_id));
		ret = -EIO;
		goto exit;
	}

	/* Add an extra page for headers */
	fwrt->trans->paging_download_buf = kzalloc(PAGING_BLOCK_SIZE +
						  FW_PAGING_SIZE,
						  GFP_KERNEL);
	if (!fwrt->trans->paging_download_buf) {
		ret = -ENOMEM;
		goto exit;
	}
	fwrt->trans->paging_req_addr = le32_to_cpu(item_resp->item_val);
	fwrt->trans->paging_db = fwrt->fw_paging_db;
	IWL_DEBUG_FW(fwrt,
		     "Paging: got paging request address (paging_req_addr 0x%08x)\n",
		     fwrt->trans->paging_req_addr);

exit:
	iwl_free_resp(&cmd);

	return ret;
}

int iwl_init_paging(struct iwl_fw_runtime *fwrt, enum iwl_ucode_type type)
{
	const struct fw_img *fw = &fwrt->fw->img[type];
	int ret;

	if (fwrt->trans->cfg->gen2)
		return 0;

	/*
	 * Configure and operate fw paging mechanism.
	 * The driver configures the paging flow only once.
	 * The CPU2 paging image is included in the IWL_UCODE_INIT image.
	 */
	if (!fw->paging_mem_size)
		return 0;

	/*
	 * When dma is not enabled, the driver needs to copy / write
	 * the downloaded / uploaded page to / from the smem.
	 * This gets the location of the place were the pages are
	 * stored.
	 */
	if (!is_device_dma_capable(fwrt->trans->dev)) {
		ret = iwl_trans_get_paging_item(fwrt);
		if (ret) {
			IWL_ERR(fwrt, "failed to get FW paging item\n");
			return ret;
		}
	}

	ret = iwl_save_fw_paging(fwrt, fw);
	if (ret) {
		IWL_ERR(fwrt, "failed to save the FW paging image\n");
		return ret;
	}

	ret = iwl_send_paging_cmd(fwrt, fw);
	if (ret) {
		IWL_ERR(fwrt, "failed to send the paging cmd\n");
		iwl_free_fw_paging(fwrt);
		return ret;
	}

	return 0;
}
IWL_EXPORT_SYMBOL(iwl_init_paging);
