// SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note
/*
 * Copyright (c) 2023 MediaTek Inc.
 */

#include <mali_kbase.h>
#include <linux/delay.h>
#include "mtk_dtv_gpu_utility.h"
#include "mali_kbase_platform_mtk_dtv.h"
#include "mali_kbase_platform_mtk_dtv_mt5873_reg.h"

#ifdef CONFIG_DEBUG_FS

static void update_frequency(u32 frequency)
{
	mali_gpu_clock = frequency;
	/* set GPU clock */
	SET_REG(GPUBRDGPLL, pd_gpubrdgpll, 0x0);
	SET_REG(GPUBRDGPLL, gc_gpubrdgpll_loopdiv_second, (frequency/GPU_CLOCK_STEP));
	udelay(1);
}

static ssize_t gpu_clock_read(struct file *filp, char __user *ubuf, size_t cnt, loff_t *ppos)
{
	char buf[64];
	int r;

	r = snprintf(buf, 64, "%u\n", mali_gpu_clock);

	if ((r < 0) || (r >= sizeof(buf)))
		return 0;

	return simple_read_from_buffer(ubuf, cnt, ppos, buf, r);
}

static ssize_t gpu_clock_write(struct file *filp, const char __user *ubuf, size_t cnt, loff_t *ppos)
{
	int ret;
	char buffer[32];
	unsigned long val;

	if (cnt >= sizeof(buffer))
		return -ENOMEM;

	if (copy_from_user(&buffer[0], ubuf, cnt))
		return -EFAULT;

	buffer[cnt] = '\0';
	ret = kstrtoul(&buffer[0], 10, &val);

	if (ret != 0)
		return -EINVAL;

	if (mali_debug_property == MALI_DEBUG_PROPERTY_PASSWORD)
		update_frequency(val);

	return cnt;
}

static const struct file_operations kbasep_gpu_clock_debugfs_fops = {
	.read = gpu_clock_read,
	.write = gpu_clock_write,
};

/*
 *  Initialize debugfs entry for gpu clock
 */
void kbasep_gpu_clock_debugfs_init(struct kbase_device *kbdev)
{
	debugfs_create_file("gpu_clock", 0644,
		kbdev->mali_debugfs_directory, NULL,
		&kbasep_gpu_clock_debugfs_fops);
}

#else
/*
 * Stub functions for when debugfs is disabled
 */
void kbasep_gpu_clock_debugfs_init(struct kbase_device *kbdev)
{

}
#endif
