#include "event.h"
#include "symbol.h"
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include "debug.h"

static inline int is_anon_memory(const char *filename)
{
	return strcmp(filename, "//anon") == 0;
}

static int strcommon(const char *pathname, char *cwd, int cwdlen)
{
	int n = 0;

	while (n < cwdlen && pathname[n] == cwd[n])
		++n;

	return n;
}

void map__init(struct map *self, enum map_type type,
	       u64 start, u64 end, u64 pgoff, struct dso *dso)
{
	self->type     = type;
	self->start    = start;
	self->end      = end;
	self->pgoff    = pgoff;
	self->dso      = dso;
	self->map_ip   = map__map_ip;
	self->unmap_ip = map__unmap_ip;
	RB_CLEAR_NODE(&self->rb_node);
}

struct map *map__new(struct mmap_event *event, enum map_type type,
		     char *cwd, int cwdlen)
{
	struct map *self = malloc(sizeof(*self));

	if (self != NULL) {
		const char *filename = event->filename;
		char newfilename[PATH_MAX];
		struct dso *dso;
		int anon;

		if (cwd) {
			int n = strcommon(filename, cwd, cwdlen);

			if (n == cwdlen) {
				snprintf(newfilename, sizeof(newfilename),
					 ".%s", filename + n);
				filename = newfilename;
			}
		}

		anon = is_anon_memory(filename);

		if (anon) {
			snprintf(newfilename, sizeof(newfilename), "/tmp/perf-%d.map", event->pid);
			filename = newfilename;
		}

		dso = dsos__findnew(filename);
		if (dso == NULL)
			goto out_delete;

		map__init(self, type, event->start, event->start + event->len,
			  event->pgoff, dso);

		if (self->dso == vdso || anon)
			self->map_ip = self->unmap_ip = identity__map_ip;
	}
	return self;
out_delete:
	free(self);
	return NULL;
}

void map__delete(struct map *self)
{
	free(self);
}

void map__fixup_start(struct map *self)
{
	struct rb_root *symbols = &self->dso->symbols[self->type];
	struct rb_node *nd = rb_first(symbols);
	if (nd != NULL) {
		struct symbol *sym = rb_entry(nd, struct symbol, rb_node);
		self->start = sym->start;
	}
}

void map__fixup_end(struct map *self)
{
	struct rb_root *symbols = &self->dso->symbols[self->type];
	struct rb_node *nd = rb_last(symbols);
	if (nd != NULL) {
		struct symbol *sym = rb_entry(nd, struct symbol, rb_node);
		self->end = sym->end;
	}
}

#define DSO__DELETED "(deleted)"

struct symbol *map__find_symbol(struct map *self, u64 addr,
				symbol_filter_t filter)
{
	if (!dso__loaded(self->dso, self->type)) {
		int nr = dso__load(self->dso, self, filter);

		if (nr < 0) {
			if (self->dso->has_build_id) {
				char sbuild_id[BUILD_ID_SIZE * 2 + 1];

				build_id__sprintf(self->dso->build_id,
						  sizeof(self->dso->build_id),
						  sbuild_id);
				pr_warning("%s with build id %s not found",
					   self->dso->long_name, sbuild_id);
			} else
				pr_warning("Failed to open %s",
					   self->dso->long_name);
			pr_warning(", continuing without symbols\n");
			return NULL;
		} else if (nr == 0) {
			const char *name = self->dso->long_name;
			const size_t len = strlen(name);
			const size_t real_len = len - sizeof(DSO__DELETED);

			if (len > sizeof(DSO__DELETED) &&
			    strcmp(name + real_len + 1, DSO__DELETED) == 0) {
				pr_warning("%.*s was updated, restart the long running apps that use it!\n",
					   (int)real_len, name);
			} else {
				pr_warning("no symbols found in %s, maybe install a debug package?\n", name);
			}
			return NULL;
		}
	}

	return self->dso->find_symbol(self->dso, self->type, addr);
}

struct map *map__clone(struct map *self)
{
	struct map *map = malloc(sizeof(*self));

	if (!map)
		return NULL;

	memcpy(map, self, sizeof(*self));

	return map;
}

int map__overlap(struct map *l, struct map *r)
{
	if (l->start > r->start) {
		struct map *t = l;
		l = r;
		r = t;
	}

	if (l->end > r->start)
		return 1;

	return 0;
}

size_t map__fprintf(struct map *self, FILE *fp)
{
	return fprintf(fp, " %Lx-%Lx %Lx %s\n",
		       self->start, self->end, self->pgoff, self->dso->name);
}
