/*
 * jvmti_agent.c: JVMTI agent interface
 *
 * Adapted from the Oprofile code in opagent.c:
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 * Copyright 2007 OProfile authors
 * Jens Wilke
 * Daniel Hansel
 * Copyright IBM Corporation 2007
 */
#include <sys/types.h>
#include <sys/stat.h> /* for mkdir() */
#include <stdio.h>
#include <errno.h>
#include <string.h>
#include <stdlib.h>
#include <stdint.h>
#include <limits.h>
#include <fcntl.h>
#include <unistd.h>
#include <time.h>
#include <sys/mman.h>
#include <syscall.h> /* for gettid() */
#include <err.h>

#include "jvmti_agent.h"
#include "../util/jitdump.h"

#define JIT_LANG "java"

static char jit_path[PATH_MAX];
static void *marker_addr;

static inline pid_t gettid(void)
{
	return (pid_t)syscall(__NR_gettid);
}

static int get_e_machine(struct jitheader *hdr)
{
	ssize_t sret;
	char id[16];
	int fd, ret = -1;
	struct {
		uint16_t e_type;
		uint16_t e_machine;
	} info;

	fd = open("/proc/self/exe", O_RDONLY);
	if (fd == -1)
		return -1;

	sret = read(fd, id, sizeof(id));
	if (sret != sizeof(id))
		goto error;

	/* check ELF signature */
	if (id[0] != 0x7f || id[1] != 'E' || id[2] != 'L' || id[3] != 'F')
		goto error;

	sret = read(fd, &info, sizeof(info));
	if (sret != sizeof(info))
		goto error;

	hdr->elf_mach = info.e_machine;
	ret = 0;
error:
	close(fd);
	return ret;
}

static int use_arch_timestamp;

static inline uint64_t
get_arch_timestamp(void)
{
#if defined(__i386__) || defined(__x86_64__)
	unsigned int low, high;

	asm volatile("rdtsc" : "=a" (low), "=d" (high));

	return low | ((uint64_t)high) << 32;
#else
	return 0;
#endif
}

#define NSEC_PER_SEC	1000000000
static int perf_clk_id = CLOCK_MONOTONIC;

static inline uint64_t
timespec_to_ns(const struct timespec *ts)
{
        return ((uint64_t) ts->tv_sec * NSEC_PER_SEC) + ts->tv_nsec;
}

static inline uint64_t
perf_get_timestamp(void)
{
	struct timespec ts;
	int ret;

	if (use_arch_timestamp)
		return get_arch_timestamp();

	ret = clock_gettime(perf_clk_id, &ts);
	if (ret)
		return 0;

	return timespec_to_ns(&ts);
}

static int
debug_cache_init(void)
{
	char str[32];
	char *base, *p;
	struct tm tm;
	time_t t;
	int ret;

	time(&t);
	localtime_r(&t, &tm);

	base = getenv("JITDUMPDIR");
	if (!base)
		base = getenv("HOME");
	if (!base)
		base = ".";

	strftime(str, sizeof(str), JIT_LANG"-jit-%Y%m%d", &tm);

	snprintf(jit_path, PATH_MAX - 1, "%s/.debug/", base);

	ret = mkdir(jit_path, 0755);
	if (ret == -1) {
		if (errno != EEXIST) {
			warn("jvmti: cannot create jit cache dir %s", jit_path);
			return -1;
		}
	}

	snprintf(jit_path, PATH_MAX - 1, "%s/.debug/jit", base);
	ret = mkdir(jit_path, 0755);
	if (ret == -1) {
		if (errno != EEXIST) {
			warn("cannot create jit cache dir %s", jit_path);
			return -1;
		}
	}

	snprintf(jit_path, PATH_MAX - 1, "%s/.debug/jit/%s.XXXXXXXX", base, str);

	p = mkdtemp(jit_path);
	if (p != jit_path) {
		warn("cannot create jit cache dir %s", jit_path);
		return -1;
	}

	return 0;
}

static int
perf_open_marker_file(int fd)
{
	long pgsz;

	pgsz = sysconf(_SC_PAGESIZE);
	if (pgsz == -1)
		return -1;

	/*
	 * we mmap the jitdump to create an MMAP RECORD in perf.data file.
	 * The mmap is captured either live (perf record running when we mmap)
	 * or  in deferred mode, via /proc/PID/maps
	 * the MMAP record is used as a marker of a jitdump file for more meta
	 * data info about the jitted code. Perf report/annotate detect this
	 * special filename and process the jitdump file.
	 *
	 * mapping must be PROT_EXEC to ensure it is captured by perf record
	 * even when not using -d option
	 */
	marker_addr = mmap(NULL, pgsz, PROT_READ|PROT_EXEC, MAP_PRIVATE, fd, 0);
	return (marker_addr == MAP_FAILED) ? -1 : 0;
}

static void
perf_close_marker_file(void)
{
	long pgsz;

	if (!marker_addr)
		return;

	pgsz = sysconf(_SC_PAGESIZE);
	if (pgsz == -1)
		return;

	munmap(marker_addr, pgsz);
}

static void
init_arch_timestamp(void)
{
	char *str = getenv("JITDUMP_USE_ARCH_TIMESTAMP");

	if (!str || !*str || !strcmp(str, "0"))
		return;

	use_arch_timestamp = 1;
}

void *jvmti_open(void)
{
	char dump_path[PATH_MAX];
	struct jitheader header;
	int fd;
	FILE *fp;

	init_arch_timestamp();

	/*
	 * check if clockid is supported
	 */
	if (!perf_get_timestamp()) {
		if (use_arch_timestamp)
			warnx("jvmti: arch timestamp not supported");
		else
			warnx("jvmti: kernel does not support %d clock id", perf_clk_id);
	}

	memset(&header, 0, sizeof(header));

	debug_cache_init();

	/*
	 * jitdump file name
	 */
	snprintf(dump_path, PATH_MAX, "%s/jit-%i.dump", jit_path, getpid());

	fd = open(dump_path, O_CREAT|O_TRUNC|O_RDWR, 0666);
	if (fd == -1)
		return NULL;

	/*
	 * create perf.data maker for the jitdump file
	 */
	if (perf_open_marker_file(fd)) {
		warnx("jvmti: failed to create marker file");
		return NULL;
	}

	fp = fdopen(fd, "w+");
	if (!fp) {
		warn("jvmti: cannot create %s", dump_path);
		close(fd);
		goto error;
	}

	warnx("jvmti: jitdump in %s", dump_path);

	if (get_e_machine(&header)) {
		warn("get_e_machine failed\n");
		goto error;
	}

	header.magic      = JITHEADER_MAGIC;
	header.version    = JITHEADER_VERSION;
	header.total_size = sizeof(header);
	header.pid        = getpid();

	header.timestamp = perf_get_timestamp();

	if (use_arch_timestamp)
		header.flags |= JITDUMP_FLAGS_ARCH_TIMESTAMP;

	if (!fwrite(&header, sizeof(header), 1, fp)) {
		warn("jvmti: cannot write dumpfile header");
		goto error;
	}
	return fp;
error:
	fclose(fp);
	return NULL;
}

int
jvmti_close(void *agent)
{
	struct jr_code_close rec;
	FILE *fp = agent;

	if (!fp) {
		warnx("jvmti: invalid fd in close_agent");
		return -1;
	}

	rec.p.id = JIT_CODE_CLOSE;
	rec.p.total_size = sizeof(rec);

	rec.p.timestamp = perf_get_timestamp();

	if (!fwrite(&rec, sizeof(rec), 1, fp))
		return -1;

	fclose(fp);

	fp = NULL;

	perf_close_marker_file();

	return 0;
}

int
jvmti_write_code(void *agent, char const *sym,
	uint64_t vma, void const *code, unsigned int const size)
{
	static int code_generation = 1;
	struct jr_code_load rec;
	size_t sym_len;
	FILE *fp = agent;
	int ret = -1;

	/* don't care about 0 length function, no samples */
	if (size == 0)
		return 0;

	if (!fp) {
		warnx("jvmti: invalid fd in write_native_code");
		return -1;
	}

	sym_len = strlen(sym) + 1;

	rec.p.id           = JIT_CODE_LOAD;
	rec.p.total_size   = sizeof(rec) + sym_len;
	rec.p.timestamp    = perf_get_timestamp();

	rec.code_size  = size;
	rec.vma        = vma;
	rec.code_addr  = vma;
	rec.pid	       = getpid();
	rec.tid	       = gettid();

	if (code)
		rec.p.total_size += size;

	/*
	 * If JVM is multi-threaded, nultiple concurrent calls to agent
	 * may be possible, so protect file writes
	 */
	flockfile(fp);

	/*
	 * get code index inside lock to avoid race condition
	 */
	rec.code_index = code_generation++;

	ret = fwrite_unlocked(&rec, sizeof(rec), 1, fp);
	fwrite_unlocked(sym, sym_len, 1, fp);

	if (code)
		fwrite_unlocked(code, size, 1, fp);

	funlockfile(fp);

	ret = 0;

	return ret;
}

int
jvmti_write_debug_info(void *agent, uint64_t code, const char *file,
		       jvmti_line_info_t *li, int nr_lines)
{
	struct jr_code_debug_info rec;
	size_t sret, len, size, flen;
	uint64_t addr;
	const char *fn = file;
	FILE *fp = agent;
	int i;

	/*
	 * no entry to write
	 */
	if (!nr_lines)
		return 0;

	if (!fp) {
		warnx("jvmti: invalid fd in write_debug_info");
		return -1;
	}

	flen = strlen(file) + 1;

	rec.p.id        = JIT_CODE_DEBUG_INFO;
	size            = sizeof(rec);
	rec.p.timestamp = perf_get_timestamp();
	rec.code_addr   = (uint64_t)(uintptr_t)code;
	rec.nr_entry    = nr_lines;

	/*
	 * on disk source line info layout:
	 * uint64_t : addr
	 * int      : line number
	 * int      : column discriminator
	 * file[]   : source file name
	 */
	size += nr_lines * sizeof(struct debug_entry);
	size += flen * nr_lines;
	rec.p.total_size = size;

	/*
	 * If JVM is multi-threaded, nultiple concurrent calls to agent
	 * may be possible, so protect file writes
	 */
	flockfile(fp);

	sret = fwrite_unlocked(&rec, sizeof(rec), 1, fp);
	if (sret != 1)
		goto error;

	for (i = 0; i < nr_lines; i++) {

		addr = (uint64_t)li[i].pc;
		len  = sizeof(addr);
		sret = fwrite_unlocked(&addr, len, 1, fp);
		if (sret != 1)
			goto error;

		len  = sizeof(li[0].line_number);
		sret = fwrite_unlocked(&li[i].line_number, len, 1, fp);
		if (sret != 1)
			goto error;

		len  = sizeof(li[0].discrim);
		sret = fwrite_unlocked(&li[i].discrim, len, 1, fp);
		if (sret != 1)
			goto error;

		sret = fwrite_unlocked(fn, flen, 1, fp);
		if (sret != 1)
			goto error;
	}
	funlockfile(fp);
	return 0;
error:
	funlockfile(fp);
	return -1;
}
