// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (C) 2018-2020 Oplus. All rights reserved.
 */

#include <linux/module.h>
#include <linux/proc_fs.h>
#include <linux/slab.h>
#include <linux/seq_file.h>
#include <linux/of_gpio.h>
#include <linux/platform_device.h>
#include <linux/gpio.h>
#include <linux/uaccess.h>

#define SIM_DETECT_NAME "sim_detect"

/**for sim_detect log**/
#define SIMDETECT_ERR(a, arg...)  pr_err("[sim_detect]:" a, ##arg)

/**sim_detect log end**/


#define MODEM_DETECT_CMD 55

static struct of_device_id sim_detect_id[] = {
	{.compatible = "oplus, sim_detect", },
	{},
};

struct sim_detect_data {
	struct platform_device *pdev;
	int sim_detect;
};

#ifdef CONFIG_OEM_QMI
extern int oem_qmi_common_req(u32 cmd_type, const char *req_data, u32 req_len,
	char *resp_data, u32 resp_len);
#else
static int oem_qmi_common_req(u32 cmd_type, const char *req_data, u32 req_len,
	char *resp_data, u32 resp_len) {
	return -1;
}
#endif

static ssize_t proc_sim_detect_read(struct file *file,
                                    char __user *user_buf, size_t count, loff_t *ppos)
{
	int ret = 0;
	char page[25] = {0};
	int sim_detect_value = -1;
	struct sim_detect_data *sim_detect_data = PDE_DATA(file_inode(file));

	if (!sim_detect_data)
		return 0;

	if (sim_detect_data->sim_detect >= 0) {
		sim_detect_value = gpio_get_value(sim_detect_data->sim_detect);

	} else {
		char resp_data[8] = {0};
		if (oem_qmi_common_req(MODEM_DETECT_CMD, NULL, 0, resp_data, 8)) {
			SIMDETECT_ERR("failed to read status from modem\n");
		} else {
			sim_detect_value = resp_data[0];
		}
	}

	SIMDETECT_ERR("sim_detect_value:%d\n", sim_detect_value);

	ret = snprintf(page, sizeof(page) - 1, "%d\n", sim_detect_value);
	ret = simple_read_from_buffer(user_buf, count, ppos, page, strlen(page));

	return ret;
}


static const struct file_operations sim_detect_ops = {
	.read  = proc_sim_detect_read,
	.open  = simple_open,
	.owner = THIS_MODULE,
};

static int sim_card_detect_init(struct sim_detect_data *sim_detect_data)
{
	int ret = 0;
	struct device_node *np = NULL;
	struct proc_dir_entry *p = NULL;

	np = sim_detect_data->pdev->dev.of_node;
	sim_detect_data->sim_detect = of_get_named_gpio(np, "Hw,sim_det", 0);

	if (sim_detect_data->sim_detect < 0) {
		const char *out_string;
		SIMDETECT_ERR("sim detect gpio not specified\n");
		if (of_property_read_string(np, "Hw,sim_det", &out_string)
			|| strcmp(out_string, "modem_det")) {
			SIMDETECT_ERR("modem det not specified\n");
			ret = -1;
			goto err;
		}
	}

	p = proc_create_data("sim_detect", 0644, NULL, &sim_detect_ops,
                         sim_detect_data);
	if (!p) {
		SIMDETECT_ERR("proc create sim detect failed\n");
		ret = -1;
		goto err;
	}
err:
	return ret;
}

static int sim_detect_probe(struct platform_device *pdev)
{
	int ret = 0;
	struct sim_detect_data *sim_detect_data = NULL;

	SIMDETECT_ERR("sim_detect_probe enter\n");
	sim_detect_data = devm_kzalloc(&pdev->dev, sizeof(struct sim_detect_data), GFP_KERNEL);

	if (IS_ERR_OR_NULL(sim_detect_data)) {
		SIMDETECT_ERR("sim_detect_data kzalloc failed\n");
		ret = -ENOMEM;
		return ret;
	}

	/*parse_dts*/
	sim_detect_data->pdev = pdev;

	sim_card_detect_init(sim_detect_data);

	platform_set_drvdata(pdev, sim_detect_data);

	return ret;
}

static int sim_detect_remove(struct platform_device *pdev)
{
	struct sim_detect_data *sim_detect_data = platform_get_drvdata(pdev);

	if (sim_detect_data) {
		remove_proc_entry(SIM_DETECT_NAME, NULL);
	}
	return 0;
}

static struct platform_driver sim_detect_platform_driver = {
	.probe = sim_detect_probe,
	.remove = sim_detect_remove,
	.driver = {
		.name = SIM_DETECT_NAME,
		.of_match_table = sim_detect_id,
	},
};

module_platform_driver(sim_detect_platform_driver);

MODULE_DESCRIPTION("sim_detect");
MODULE_LICENSE("GPL v2");
MODULE_AUTHOR("Qicai.gu <qicai.gu>");
