24 #include <sys/types.h> 40 #include "../util/jitdump.h" 42 #define JIT_LANG "java" 49 return (pid_t)
syscall(__NR_gettid);
62 fd = open(
"/proc/self/exe", O_RDONLY);
66 sret = read(fd,
id,
sizeof(
id));
67 if (sret !=
sizeof(
id))
71 if (
id[0] != 0x7f ||
id[1] !=
'E' ||
id[2] !=
'L' ||
id[3] !=
'F')
74 sret = read(fd, &info,
sizeof(info));
75 if (sret !=
sizeof(info))
87 static inline uint64_t
90 #if defined(__i386__) || defined(__x86_64__) 91 unsigned int low, high;
93 asm volatile(
"rdtsc" :
"=a" (low),
"=d" (high));
95 return low | ((uint64_t)high) << 32;
101 #define NSEC_PER_SEC 1000000000 104 static inline uint64_t
107 return ((uint64_t) ts->tv_sec *
NSEC_PER_SEC) + ts->tv_nsec;
110 static inline uint64_t
136 localtime_r(&t, &tm);
138 base = getenv(
"JITDUMPDIR");
140 base = getenv(
"HOME");
144 strftime(str,
sizeof(str),
JIT_LANG"-jit-%Y%m%d", &tm);
150 if (errno != EEXIST) {
151 warn(
"jvmti: cannot create jit cache dir %s",
jit_path);
159 if (errno != EEXIST) {
160 warn(
"cannot create jit cache dir %s",
jit_path);
169 warn(
"cannot create jit cache dir %s",
jit_path);
181 pgsz = sysconf(_SC_PAGESIZE);
196 marker_addr = mmap(NULL, pgsz, PROT_READ|PROT_EXEC, MAP_PRIVATE, fd, 0);
208 pgsz = sysconf(_SC_PAGESIZE);
218 char *
str = getenv(
"JITDUMP_USE_ARCH_TIMESTAMP");
220 if (!str || !*str || !strcmp(str,
"0"))
240 warnx(
"jvmti: arch timestamp not supported");
242 warnx(
"jvmti: kernel does not support %d clock id",
perf_clk_id);
245 memset(&header, 0,
sizeof(header));
254 fd = open(dump_path, O_CREAT|O_TRUNC|O_RDWR, 0666);
262 warnx(
"jvmti: failed to create marker file");
266 fp = fdopen(fd,
"w+");
268 warn(
"jvmti: cannot create %s", dump_path);
273 warnx(
"jvmti: jitdump in %s", dump_path);
276 warn(
"get_e_machine failed\n");
283 header.
pid = getpid();
290 if (!fwrite(&header,
sizeof(header), 1, fp)) {
291 warn(
"jvmti: cannot write dumpfile header");
307 warnx(
"jvmti: invalid fd in close_agent");
316 if (!fwrite(&rec,
sizeof(rec), 1, fp))
330 uint64_t vma,
void const *code,
unsigned int const size)
332 static int code_generation = 1;
343 warnx(
"jvmti: invalid fd in write_native_code");
347 sym_len = strlen(sym) + 1;
373 ret = fwrite_unlocked(&rec,
sizeof(rec), 1, fp);
374 fwrite_unlocked(sym, sym_len, 1, fp);
377 fwrite_unlocked(code, size, 1, fp);
389 const char *
const * file_names)
392 size_t sret, len,
size, flen = 0;
404 warnx(
"jvmti: invalid fd in write_debug_info");
408 for (i = 0; i < nr_lines; ++i) {
409 flen += strlen(file_names[i]) + 1;
415 rec.
code_addr = (uint64_t)(uintptr_t)code;
435 sret = fwrite_unlocked(&rec,
sizeof(rec), 1, fp);
439 for (i = 0; i < nr_lines; i++) {
441 addr = (uint64_t)li[i].pc;
443 sret = fwrite_unlocked(&addr, len, 1, fp);
448 sret = fwrite_unlocked(&li[i].line_number, len, 1, fp);
453 sret = fwrite_unlocked(&li[i].
discrim, len, 1, fp);
457 sret = fwrite_unlocked(file_names[i], strlen(file_names[i]) + 1, 1, fp);
static uint64_t perf_get_timestamp(void)
#define JITDUMP_FLAGS_ARCH_TIMESTAMP
static void perf_close_marker_file(void)
static uint64_t timespec_to_ns(const struct timespec *ts)
#define JITHEADER_VERSION
static char jit_path[PATH_MAX]
static int debug_cache_init(void)
x86 movsq based memset() in arch/x86/lib/memset_64.S") MEMSET_FN(memset_erms
static pid_t gettid(void)
static int get_e_machine(struct jitheader *hdr)
int jvmti_write_debug_info(void *agent, uint64_t code, int nr_lines, jvmti_line_info_t *li, const char *const *file_names)
static int str(yyscan_t scanner, int token)
static uint64_t get_arch_timestamp(void)
int jvmti_close(void *agent)
static int perf_open_marker_file(int fd)
static int sym(yyscan_t scanner, int type, int config)
int jvmti_write_code(void *agent, char const *sym, uint64_t vma, void const *code, unsigned int const size)
static int use_arch_timestamp
static void init_arch_timestamp(void)
static void * marker_addr