/* Copyright (c) 2012, 2014-2016, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
 * only version 2 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.
 *
 */

#define pr_fmt(fmt) "%s: " fmt, __func__

#include <linux/module.h>
#include <linux/clocksource.h>
#include <linux/clockchips.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/irq.h>
#include <linux/interrupt.h>
#include <linux/cpu.h>
#include <soc/qcom/event_timer.h>

/**
 * struct event_timer_info - basic event timer structure
 * @node: timerqueue node to track time ordered data structure
 *        of event timers
 * @notify: irq affinity notifier.
 * @timer: hrtimer created for this event.
 * @function : callback function for event timer.
 * @data : callback data for event timer.
 * @irq: irq number for which event timer is created.
 * @cpu: event timer associated cpu.
 */
struct event_timer_info {
	struct timerqueue_node node;
	struct irq_affinity_notify notify;
	void (*function)(void *);
	void *data;
	int irq;
	int cpu;
};

struct hrtimer_info {
	struct hrtimer event_hrtimer;
	bool timer_initialized;
};

static DEFINE_PER_CPU(struct hrtimer_info, per_cpu_hrtimer);

static DEFINE_PER_CPU(struct timerqueue_head, timer_head) = {
	.head = RB_ROOT,
	.next = NULL,
};

static DEFINE_SPINLOCK(event_timer_lock);
static DEFINE_SPINLOCK(event_setup_lock);

static void create_timer_smp(void *data);
static void setup_event_hrtimer(struct event_timer_info *event);
static enum hrtimer_restart event_hrtimer_cb(struct hrtimer *hrtimer);
static void irq_affinity_change_notifier(struct irq_affinity_notify *notify,
						const cpumask_t *new_cpu_mask);
static void irq_affinity_release(struct kref *ref);

static int msm_event_debug_mask;
module_param_named(debug_mask, msm_event_debug_mask, int, 0664);

enum {
	MSM_EVENT_TIMER_DEBUG = 1U << 0,
};

/**
 * add_event_timer() : Add a wakeup event. Intended to be called
 *                     by clients once. Returns a handle to be used
 *                     for future transactions.
 * @irq: event associated irq number.
 * @function : The callback function will be called when event
 *             timer expires.
 * @data: callback data provided by client.
 */
struct event_timer_info *add_event_timer(uint32_t irq,
				void (*function)(void *), void *data)
{
	struct event_timer_info *event_info =
			kzalloc(sizeof(struct event_timer_info), GFP_KERNEL);

	if (!event_info)
		return NULL;

	event_info->function = function;
	event_info->data = data;

	if (irq) {
		struct irq_desc *desc = irq_to_desc(irq);
		struct cpumask *mask = desc->irq_common_data.affinity;

		get_online_cpus();
		event_info->cpu = cpumask_any_and(mask, cpu_online_mask);
		if (event_info->cpu >= nr_cpu_ids)
			event_info->cpu = cpumask_first(cpu_online_mask);

		event_info->notify.notify = irq_affinity_change_notifier;
		event_info->notify.release = irq_affinity_release;
		irq_set_affinity_notifier(irq, &event_info->notify);
		put_online_cpus();
	}

	/* Init rb node and hr timer */
	timerqueue_init(&event_info->node);
	pr_debug("New Event Added. Event %p(on cpu%d). irq %d.\n",
					event_info, event_info->cpu, irq);

	return event_info;
}
EXPORT_SYMBOL(add_event_timer);

/**
 * is_event_next(): Helper function to check if the event is the next
 *                  expiring event
 * @event : handle to the event to be checked.
 */
static bool is_event_next(struct event_timer_info *event)
{
	struct event_timer_info *next_event;
	struct timerqueue_node *next;
	bool ret = false;

	next = timerqueue_getnext(&per_cpu(timer_head, event->cpu));
	if (!next)
		goto exit_is_next_event;

	next_event = container_of(next, struct event_timer_info, node);
	if (!next_event)
		goto exit_is_next_event;

	if (next_event == event)
		ret = true;

exit_is_next_event:
	return ret;
}

/**
 * is_event_active(): Helper function to check if the timer for a given event
 *                    has been started.
 * @event : handle to the event to be checked.
 */
static bool is_event_active(struct event_timer_info *event)
{
	struct timerqueue_node *next;
	struct event_timer_info *next_event;
	bool ret = false;

	for (next = timerqueue_getnext(&per_cpu(timer_head, event->cpu)); next;
			next = timerqueue_iterate_next(next)) {
		next_event = container_of(next, struct event_timer_info, node);

		if (event == next_event) {
			ret = true;
			break;
		}
	}
	return ret;
}

/**
 * create_hrtimer(): Helper function to setup hrtimer.
 */
static void create_hrtimer(struct event_timer_info *event)

{
	bool timer_initialized = per_cpu(per_cpu_hrtimer.timer_initialized,
								event->cpu);
	struct hrtimer *event_hrtimer = &per_cpu(per_cpu_hrtimer.event_hrtimer,
								event->cpu);

	if (!timer_initialized) {
		hrtimer_init(event_hrtimer, CLOCK_MONOTONIC,
						HRTIMER_MODE_ABS_PINNED);
		per_cpu(per_cpu_hrtimer.timer_initialized, event->cpu) = true;
	}

	event_hrtimer->function = event_hrtimer_cb;
	hrtimer_start(event_hrtimer, event->node.expires,
					HRTIMER_MODE_ABS_PINNED);
}

/**
 * event_hrtimer_cb() : Callback function for hr timer.
 *                      Make the client CB from here and remove the event
 *                      from the time ordered queue.
 */
static enum hrtimer_restart event_hrtimer_cb(struct hrtimer *hrtimer)
{
	struct event_timer_info *event;
	struct timerqueue_node *next;
	unsigned long flags;
	int cpu;

	spin_lock_irqsave(&event_timer_lock, flags);
	cpu = smp_processor_id();
	next = timerqueue_getnext(&per_cpu(timer_head, cpu));

	while (next && (ktime_to_ns(next->expires)
		<= ktime_to_ns(hrtimer->node.expires))) {
		event = container_of(next, struct event_timer_info, node);
		if (!event)
			goto hrtimer_cb_exit;

		WARN_ON_ONCE(event->cpu != cpu);

		if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
			pr_debug("Deleting event %p @ %lu(on cpu%d)\n", event,
				(unsigned long)ktime_to_ns(next->expires), cpu);

		timerqueue_del(&per_cpu(timer_head, cpu), &event->node);

		if (event->function)
			event->function(event->data);

		next = timerqueue_getnext(&per_cpu(timer_head, cpu));
	}

	if (next) {
		event = container_of(next, struct event_timer_info, node);
		create_hrtimer(event);
	}
hrtimer_cb_exit:
	spin_unlock_irqrestore(&event_timer_lock, flags);
	return HRTIMER_NORESTART;
}

/**
 * create_timer_smp(): Helper function used setting up timer on CPUs.
 */
static void create_timer_smp(void *data)
{
	unsigned long flags;
	struct event_timer_info *event =
		(struct event_timer_info *)data;
	struct timerqueue_node *next;

	spin_lock_irqsave(&event_timer_lock, flags);

	if (is_event_active(event))
		timerqueue_del(&per_cpu(timer_head, event->cpu), &event->node);

	next = timerqueue_getnext(&per_cpu(timer_head, event->cpu));
	timerqueue_add(&per_cpu(timer_head, event->cpu), &event->node);

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("Adding Event %p(on cpu%d) for %lu\n", event,
		event->cpu,
		(unsigned long)ktime_to_ns(event->node.expires));

	if (!next || (next && (ktime_to_ns(event->node.expires) <
						ktime_to_ns(next->expires)))) {
		if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
			pr_debug("Setting timer for %lu(on cpu%d)\n",
			(unsigned long)ktime_to_ns(event->node.expires),
			event->cpu);

		create_hrtimer(event);
	}
	spin_unlock_irqrestore(&event_timer_lock, flags);
}

/**
 *  setup_timer() : Helper function to setup timer on primary
 *                  core during hrtimer callback.
 *  @event: event handle causing the wakeup.
 */
static void setup_event_hrtimer(struct event_timer_info *event)
{
	smp_call_function_single(event->cpu, create_timer_smp, event, 1);
}

static void irq_affinity_release(struct kref *ref)
{
	struct event_timer_info *event;
	struct irq_affinity_notify *notify =
			container_of(ref, struct irq_affinity_notify, kref);

	event = container_of(notify, struct event_timer_info, notify);
	pr_debug("event = %p\n", event);
}

static void irq_affinity_change_notifier(struct irq_affinity_notify *notify,
						const cpumask_t *mask_val)
{
	struct event_timer_info *event;
	unsigned long flags;
	unsigned int irq;
	int old_cpu = -EINVAL, new_cpu = -EINVAL;
	bool next_event = false;

	event = container_of(notify, struct event_timer_info, notify);
	irq = notify->irq;

	if (!event)
		return;

	/*
	 * This logic is inline with irq-gic.c for finding
	 * the next affinity CPU.
	 */
	new_cpu = cpumask_any_and(mask_val, cpu_online_mask);
	if (new_cpu >= nr_cpu_ids)
		return;

	old_cpu = event->cpu;

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("irq %d, event %p, old_cpu(%d)->new_cpu(%d).\n",
						irq, event, old_cpu, new_cpu);

	/* No change in IRQ affinity */
	if (old_cpu == new_cpu)
		return;

	spin_lock_irqsave(&event_timer_lock, flags);

	/* If the event is not active OR
	 * If it is the next event
	 * and the timer is already in callback
	 * Just reset cpu and return
	 */
	if (!is_event_active(event) ||
		(is_event_next(event) &&
		(hrtimer_try_to_cancel(&per_cpu(per_cpu_hrtimer.event_hrtimer,
						old_cpu)) < 0))) {
		event->cpu = new_cpu;
		spin_unlock_irqrestore(&event_timer_lock, flags);
		if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
			pr_debug("Event:%p is not active or in callback\n",
					event);
		return;
	}

	/* Update the flag based on EVENT is next are not */
	if (is_event_next(event))
		next_event = true;

	event->cpu = new_cpu;

	/*
	 * We are here either because hrtimer was active or event is not next
	 * Delete the event from the timer queue anyway
	 */
	timerqueue_del(&per_cpu(timer_head, old_cpu), &event->node);

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("Event:%p is in the list\n", event);

	spin_unlock_irqrestore(&event_timer_lock, flags);

	/*
	 * Migrating event timer to a new CPU is automatically
	 * taken care. Since we have already modify the event->cpu
	 * with new CPU.
	 *
	 * Typical cases are
	 *
	 * 1)
	 *		C0			C1
	 *		|			^
	 *	-----------------		|
	 *	|	|	|		|
	 *	E1	E2	E3		|
	 *		|(migrating)		|
	 *		-------------------------
	 *
	 * 2)
	 *		C0			C1
	 *		|			^
	 *	----------------		|
	 *	|	|	|		|
	 *	E1	E2	E3		|
	 *	|(migrating)			|
	 *	---------------------------------
	 *
	 * Here after moving the E1 to C1. Need to start
	 * E2 on C0.
	 */
	spin_lock(&event_setup_lock);
	/* Setup event timer on new cpu*/
	setup_event_hrtimer(event);

	/* Setup event on the old cpu*/
	if (next_event) {
		struct timerqueue_node *next;

		next = timerqueue_getnext(&per_cpu(timer_head, old_cpu));
		if (next) {
			event = container_of(next,
					struct event_timer_info, node);
			setup_event_hrtimer(event);
		}
	}
	spin_unlock(&event_setup_lock);
}

/**
 * activate_event_timer() : Set the expiration time for an event in absolute
 *                           ktime. This is a oneshot event timer, clients
 *                           should call this again to set another expiration.
 *  @event : event handle.
 *  @event_time : event time in absolute ktime.
 */
void activate_event_timer(struct event_timer_info *event, ktime_t event_time)
{
	if (!event)
		return;

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("Adding event %p timer @ %lu(on cpu%d)\n", event,
				(unsigned long)ktime_to_us(event_time),
				event->cpu);

	spin_lock(&event_setup_lock);
	event->node.expires = event_time;
	/* Start hrtimer and add event to rb tree */
	setup_event_hrtimer(event);
	spin_unlock(&event_setup_lock);
}
EXPORT_SYMBOL(activate_event_timer);

/**
 * deactivate_event_timer() : Deactivate an event timer, this removes the event
 *				from the time ordered queue of event timers.
 * @event: event handle.
 */
void deactivate_event_timer(struct event_timer_info *event)
{
	unsigned long flags;

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("Deactivate timer\n");

	spin_lock_irqsave(&event_timer_lock, flags);
	if (is_event_active(event)) {
		if (is_event_next(event))
			hrtimer_try_to_cancel(&per_cpu(
				per_cpu_hrtimer.event_hrtimer, event->cpu));

		timerqueue_del(&per_cpu(timer_head, event->cpu), &event->node);
	}
	spin_unlock_irqrestore(&event_timer_lock, flags);
}

/**
 * destroy_event_timer() : Free the event info data structure allocated during
 *                         add_event_timer().
 * @event: event handle.
 */
void destroy_event_timer(struct event_timer_info *event)
{
	unsigned long flags;

	spin_lock_irqsave(&event_timer_lock, flags);
	if (is_event_active(event)) {
		if (is_event_next(event))
			hrtimer_try_to_cancel(&per_cpu(
				per_cpu_hrtimer.event_hrtimer, event->cpu));

		timerqueue_del(&per_cpu(timer_head, event->cpu), &event->node);
	}
	spin_unlock_irqrestore(&event_timer_lock, flags);
	kfree(event);
}
EXPORT_SYMBOL(destroy_event_timer);

/**
 * get_next_event_timer() - Get the next wakeup event. Returns
 *                          a ktime value of the next expiring event.
 */
ktime_t get_next_event_time(int cpu)
{
	unsigned long flags;
	struct timerqueue_node *next;
	struct event_timer_info *event;
	ktime_t next_event = ns_to_ktime(0);

	spin_lock_irqsave(&event_timer_lock, flags);
	next = timerqueue_getnext(&per_cpu(timer_head, cpu));
	event = container_of(next, struct event_timer_info, node);
	spin_unlock_irqrestore(&event_timer_lock, flags);

	if (!next || event->cpu != cpu)
		return next_event;

	next_event = hrtimer_get_remaining(
				&per_cpu(per_cpu_hrtimer.event_hrtimer, cpu));

	if (msm_event_debug_mask && MSM_EVENT_TIMER_DEBUG)
		pr_debug("Next Event %lu(on cpu%d)\n",
			(unsigned long)ktime_to_us(next_event), cpu);

	return next_event;
}
