/*
 * Blackfin performance counters
 *
 * Copyright 2011 Analog Devices Inc.
 *
 * Ripped from SuperH version:
 *
 *  Copyright (C) 2009  Paul Mundt
 *
 * Heavily based on the x86 and PowerPC implementations.
 *
 * x86:
 *  Copyright (C) 2008 Thomas Gleixner <tglx@linutronix.de>
 *  Copyright (C) 2008-2009 Red Hat, Inc., Ingo Molnar
 *  Copyright (C) 2009 Jaswinder Singh Rajput
 *  Copyright (C) 2009 Advanced Micro Devices, Inc., Robert Richter
 *  Copyright (C) 2008-2009 Red Hat, Inc., Peter Zijlstra
 *  Copyright (C) 2009 Intel Corporation, <markus.t.metzger@intel.com>
 *
 * ppc:
 *  Copyright 2008-2009 Paul Mackerras, IBM Corporation.
 *
 * Licensed under the GPL-2 or later.
 */

#include <linux/kernel.h>
#include <linux/export.h>
#include <linux/init.h>
#include <linux/perf_event.h>
#include <asm/bfin_pfmon.h>

/*
 * We have two counters, and each counter can support an event type.
 * The 'o' is PFCNTx=1 and 's' is PFCNTx=0
 *
 * 0x04 o pc invariant branches
 * 0x06 o mispredicted branches
 * 0x09 o predicted branches taken
 * 0x0B o EXCPT insn
 * 0x0C o CSYNC/SSYNC insn
 * 0x0D o Insns committed
 * 0x0E o Interrupts taken
 * 0x0F o Misaligned address exceptions
 * 0x80 o Code memory fetches stalled due to DMA
 * 0x83 o 64bit insn fetches delivered
 * 0x9A o data cache fills (bank a)
 * 0x9B o data cache fills (bank b)
 * 0x9C o data cache lines evicted (bank a)
 * 0x9D o data cache lines evicted (bank b)
 * 0x9E o data cache high priority fills
 * 0x9F o data cache low priority fills
 * 0x00 s loop 0 iterations
 * 0x01 s loop 1 iterations
 * 0x0A s CSYNC/SSYNC stalls
 * 0x10 s DAG read/after write hazards
 * 0x13 s RAW data hazards
 * 0x81 s code TAG stalls
 * 0x82 s code fill stalls
 * 0x90 s processor to memory stalls
 * 0x91 s data memory stalls not hidden by 0x90
 * 0x92 s data store buffer full stalls
 * 0x93 s data memory write buffer full stalls due to high->low priority
 * 0x95 s data memory fill buffer stalls
 * 0x96 s data TAG collision stalls
 * 0x97 s data collision stalls
 * 0x98 s data stalls
 * 0x99 s data stalls sent to processor
 */

static const int event_map[] = {
	/* use CYCLES cpu register */
	[PERF_COUNT_HW_CPU_CYCLES]          = -1,
	[PERF_COUNT_HW_INSTRUCTIONS]        = 0x0D,
	[PERF_COUNT_HW_CACHE_REFERENCES]    = -1,
	[PERF_COUNT_HW_CACHE_MISSES]        = 0x83,
	[PERF_COUNT_HW_BRANCH_INSTRUCTIONS] = 0x09,
	[PERF_COUNT_HW_BRANCH_MISSES]       = 0x06,
	[PERF_COUNT_HW_BUS_CYCLES]          = -1,
};

#define C(x)	PERF_COUNT_HW_CACHE_##x

static const int cache_events[PERF_COUNT_HW_CACHE_MAX]
                             [PERF_COUNT_HW_CACHE_OP_MAX]
                             [PERF_COUNT_HW_CACHE_RESULT_MAX] =
{
	[C(L1D)] = {	/* Data bank A */
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = 0,
			[C(RESULT_MISS)  ] = 0x9A,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = 0,
			[C(RESULT_MISS)  ] = 0,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = 0,
			[C(RESULT_MISS)  ] = 0,
		},
	},

	[C(L1I)] = {
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = 0,
			[C(RESULT_MISS)  ] = 0x83,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = 0,
			[C(RESULT_MISS)  ] = 0,
		},
	},

	[C(LL)] = {
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
	},

	[C(DTLB)] = {
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
	},

	[C(ITLB)] = {
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
	},

	[C(BPU)] = {
		[C(OP_READ)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_WRITE)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
		[C(OP_PREFETCH)] = {
			[C(RESULT_ACCESS)] = -1,
			[C(RESULT_MISS)  ] = -1,
		},
	},
};

const char *perf_pmu_name(void)
{
	return "bfin";
}
EXPORT_SYMBOL(perf_pmu_name);

int perf_num_counters(void)
{
	return ARRAY_SIZE(event_map);
}
EXPORT_SYMBOL(perf_num_counters);

static u64 bfin_pfmon_read(int idx)
{
	return bfin_read32(PFCNTR0 + (idx * 4));
}

static void bfin_pfmon_disable(struct hw_perf_event *hwc, int idx)
{
	bfin_write_PFCTL(bfin_read_PFCTL() & ~PFCEN(idx, PFCEN_MASK));
}

static void bfin_pfmon_enable(struct hw_perf_event *hwc, int idx)
{
	u32 val, mask;

	val = PFPWR;
	if (idx) {
		mask = ~(PFCNT1 | PFMON1 | PFCEN1 | PEMUSW1);
		/* The packed config is for event0, so shift it to event1 slots */
		val |= (hwc->config << (PFMON1_P - PFMON0_P));
		val |= (hwc->config & PFCNT0) << (PFCNT1_P - PFCNT0_P);
		bfin_write_PFCNTR1(0);
	} else {
		mask = ~(PFCNT0 | PFMON0 | PFCEN0 | PEMUSW0);
		val |= hwc->config;
		bfin_write_PFCNTR0(0);
	}

	bfin_write_PFCTL((bfin_read_PFCTL() & mask) | val);
}

static void bfin_pfmon_disable_all(void)
{
	bfin_write_PFCTL(bfin_read_PFCTL() & ~PFPWR);
}

static void bfin_pfmon_enable_all(void)
{
	bfin_write_PFCTL(bfin_read_PFCTL() | PFPWR);
}

struct cpu_hw_events {
	struct perf_event *events[MAX_HWEVENTS];
	unsigned long used_mask[BITS_TO_LONGS(MAX_HWEVENTS)];
};
DEFINE_PER_CPU(struct cpu_hw_events, cpu_hw_events);

static int hw_perf_cache_event(int config, int *evp)
{
	unsigned long type, op, result;
	int ev;

	/* unpack config */
	type = config & 0xff;
	op = (config >> 8) & 0xff;
	result = (config >> 16) & 0xff;

	if (type >= PERF_COUNT_HW_CACHE_MAX ||
	    op >= PERF_COUNT_HW_CACHE_OP_MAX ||
	    result >= PERF_COUNT_HW_CACHE_RESULT_MAX)
		return -EINVAL;

	ev = cache_events[type][op][result];
	if (ev == 0)
		return -EOPNOTSUPP;
	if (ev == -1)
		return -EINVAL;
	*evp = ev;
	return 0;
}

static void bfin_perf_event_update(struct perf_event *event,
				   struct hw_perf_event *hwc, int idx)
{
	u64 prev_raw_count, new_raw_count;
	s64 delta;
	int shift = 0;

	/*
	 * Depending on the counter configuration, they may or may not
	 * be chained, in which case the previous counter value can be
	 * updated underneath us if the lower-half overflows.
	 *
	 * Our tactic to handle this is to first atomically read and
	 * exchange a new raw count - then add that new-prev delta
	 * count to the generic counter atomically.
	 *
	 * As there is no interrupt associated with the overflow events,
	 * this is the simplest approach for maintaining consistency.
	 */
again:
	prev_raw_count = local64_read(&hwc->prev_count);
	new_raw_count = bfin_pfmon_read(idx);

	if (local64_cmpxchg(&hwc->prev_count, prev_raw_count,
			     new_raw_count) != prev_raw_count)
		goto again;

	/*
	 * Now we have the new raw value and have updated the prev
	 * timestamp already. We can now calculate the elapsed delta
	 * (counter-)time and add that to the generic counter.
	 *
	 * Careful, not all hw sign-extends above the physical width
	 * of the count.
	 */
	delta = (new_raw_count << shift) - (prev_raw_count << shift);
	delta >>= shift;

	local64_add(delta, &event->count);
}

static void bfin_pmu_stop(struct perf_event *event, int flags)
{
	struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
	struct hw_perf_event *hwc = &event->hw;
	int idx = hwc->idx;

	if (!(event->hw.state & PERF_HES_STOPPED)) {
		bfin_pfmon_disable(hwc, idx);
		cpuc->events[idx] = NULL;
		event->hw.state |= PERF_HES_STOPPED;
	}

	if ((flags & PERF_EF_UPDATE) && !(event->hw.state & PERF_HES_UPTODATE)) {
		bfin_perf_event_update(event, &event->hw, idx);
		event->hw.state |= PERF_HES_UPTODATE;
	}
}

static void bfin_pmu_start(struct perf_event *event, int flags)
{
	struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
	struct hw_perf_event *hwc = &event->hw;
	int idx = hwc->idx;

	if (WARN_ON_ONCE(idx == -1))
		return;

	if (flags & PERF_EF_RELOAD)
		WARN_ON_ONCE(!(event->hw.state & PERF_HES_UPTODATE));

	cpuc->events[idx] = event;
	event->hw.state = 0;
	bfin_pfmon_enable(hwc, idx);
}

static void bfin_pmu_del(struct perf_event *event, int flags)
{
	struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);

	bfin_pmu_stop(event, PERF_EF_UPDATE);
	__clear_bit(event->hw.idx, cpuc->used_mask);

	perf_event_update_userpage(event);
}

static int bfin_pmu_add(struct perf_event *event, int flags)
{
	struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
	struct hw_perf_event *hwc = &event->hw;
	int idx = hwc->idx;
	int ret = -EAGAIN;

	perf_pmu_disable(event->pmu);

	if (__test_and_set_bit(idx, cpuc->used_mask)) {
		idx = find_first_zero_bit(cpuc->used_mask, MAX_HWEVENTS);
		if (idx == MAX_HWEVENTS)
			goto out;

		__set_bit(idx, cpuc->used_mask);
		hwc->idx = idx;
	}

	bfin_pfmon_disable(hwc, idx);

	event->hw.state = PERF_HES_UPTODATE | PERF_HES_STOPPED;
	if (flags & PERF_EF_START)
		bfin_pmu_start(event, PERF_EF_RELOAD);

	perf_event_update_userpage(event);
	ret = 0;
out:
	perf_pmu_enable(event->pmu);
	return ret;
}

static void bfin_pmu_read(struct perf_event *event)
{
	bfin_perf_event_update(event, &event->hw, event->hw.idx);
}

static int bfin_pmu_event_init(struct perf_event *event)
{
	struct perf_event_attr *attr = &event->attr;
	struct hw_perf_event *hwc = &event->hw;
	int config = -1;
	int ret;

	if (attr->exclude_hv || attr->exclude_idle)
		return -EPERM;

	ret = 0;
	switch (attr->type) {
	case PERF_TYPE_RAW:
		config = PFMON(0, attr->config & PFMON_MASK) |
			PFCNT(0, !(attr->config & 0x100));
		break;
	case PERF_TYPE_HW_CACHE:
		ret = hw_perf_cache_event(attr->config, &config);
		break;
	case PERF_TYPE_HARDWARE:
		if (attr->config >= ARRAY_SIZE(event_map))
			return -EINVAL;

		config = event_map[attr->config];
		break;
	}

	if (config == -1)
		return -EINVAL;

	if (!attr->exclude_kernel)
		config |= PFCEN(0, PFCEN_ENABLE_SUPV);
	if (!attr->exclude_user)
		config |= PFCEN(0, PFCEN_ENABLE_USER);

	hwc->config |= config;

	return ret;
}

static void bfin_pmu_enable(struct pmu *pmu)
{
	struct cpu_hw_events *cpuc = this_cpu_ptr(&cpu_hw_events);
	struct perf_event *event;
	struct hw_perf_event *hwc;
	int i;

	for (i = 0; i < MAX_HWEVENTS; ++i) {
		event = cpuc->events[i];
		if (!event)
			continue;
		hwc = &event->hw;
		bfin_pfmon_enable(hwc, hwc->idx);
	}

	bfin_pfmon_enable_all();
}

static void bfin_pmu_disable(struct pmu *pmu)
{
	bfin_pfmon_disable_all();
}

static struct pmu pmu = {
	.pmu_enable  = bfin_pmu_enable,
	.pmu_disable = bfin_pmu_disable,
	.event_init  = bfin_pmu_event_init,
	.add         = bfin_pmu_add,
	.del         = bfin_pmu_del,
	.start       = bfin_pmu_start,
	.stop        = bfin_pmu_stop,
	.read        = bfin_pmu_read,
};

static int bfin_pmu_prepare_cpu(unsigned int cpu)
{
	struct cpu_hw_events *cpuhw = &per_cpu(cpu_hw_events, cpu);

	bfin_write_PFCTL(0);
	memset(cpuhw, 0, sizeof(struct cpu_hw_events));
	return 0;
}

static int __init bfin_pmu_init(void)
{
	int ret;

	/*
	 * All of the on-chip counters are "limited", in that they have
	 * no interrupts, and are therefore unable to do sampling without
	 * further work and timer assistance.
	 */
	pmu.capabilities |= PERF_PMU_CAP_NO_INTERRUPT;

	ret = perf_pmu_register(&pmu, "cpu", PERF_TYPE_RAW);
	if (!ret)
		cpuhp_setup_state(CPUHP_PERF_BFIN,"perf/bfin:starting",
				  bfin_pmu_prepare_cpu, NULL);
	return ret;
}
early_initcall(bfin_pmu_init);
