int load_track_handler(const char *path, const char *types, lo_arg ** argv, int argc, void *data, void *user_data) { /* example showing pulling the argument values out of the argv array */ printf("%s <- deck:%i path:%s artist:%s title:%s\n", path, argv[0]->i, &argv[1]->s, &argv[2]->s, &argv[3]->s); fflush(stdout); int d; struct deck *de; struct record *r; d = argv[0]->i; de = &osc_deck[d]; r = malloc(sizeof *r); if (r == NULL) { perror("malloc"); return -1; } r->pathname = strdup(&argv[1]->s); r->artist = strdup(&argv[2]->s); r->title = strdup(&argv[3]->s); r = library_add(osc_library, r); if (r == NULL) { /* FIXME: memory leak, need to do record_clear(r) */ return -1; } deck_load(&osc_deck[d], r); return 0; }
struct libref *elf_read_main_binary(struct task *task, int was_attached) { char fname[PATH_MAX]; int ret; char *filename; struct mt_elf mte = { }; unsigned long entry; unsigned long base; struct libref *libref; filename = pid2name(task->pid); if (!filename) return NULL; libref = libref_new(LIBTYPE_MAIN); if (libref == NULL) goto fail1; ret = readlink(filename, fname, sizeof(fname) - 1); if (ret == -1) goto fail2; fname[ret] = 0; free(filename); libref_set_filename(libref, fname); if (elf_read(&mte, task, fname) == -1) goto fail3; task->is_64bit = is_64bit(&mte); if (process_get_entry(task, &entry, &base) < 0) { fprintf(stderr, "Couldn't find process entry of %s\n", filename); goto fail3; } mte.bias = entry - mte.ehdr.e_entry - mte.vstart; mte.entry_addr = entry; if (elf_lib_init(&mte, task, libref)) goto fail3; close_elf(&mte); report_attach(task, was_attached); library_add(task, libref); if (!mte.interp) return libref; struct mt_elf mte_ld = { }; if (copy_str_from_proc(task, ARCH_ADDR_T(mte.bias + mte.interp - mte.vstart), fname, sizeof(fname)) == -1) { fprintf(stderr, "fatal error: cannot get loader name for pid=%d\n", task->pid); abort(); } if (!elf_read(&mte_ld, task, fname)) { struct libref *libref; libref = libref_new(LIBTYPE_LOADER); if (libref == NULL) goto fail4; libref_set_filename(libref, fname); mte_ld.bias = base; mte_ld.entry_addr = base + mte_ld.ehdr.e_entry - mte.vstart; ret = elf_lib_init(&mte_ld, task, libref); if (!ret) { library_add(task, libref); if (linkmap_init(task, ARCH_ADDR_T(mte.bias + mte.dyn - mte.vstart))) { arch_addr_t addr = find_solib_break(&mte_ld); if (!addr) addr = ARCH_ADDR_T(entry); struct entry_breakpoint *entry_bp = (void *)breakpoint_new_ext(task, addr, NULL, 0, sizeof(*entry_bp) - sizeof(entry_bp->breakpoint)); if (!entry_bp) fprintf(stderr, "Couldn't initialize entry breakpoint for PID %d.\n" "Tracing events may be missed.\n", task->pid ); else { entry_bp->breakpoint.on_hit = entry_breakpoint_on_hit; entry_bp->breakpoint.locked = 1; entry_bp->dyn_addr = ARCH_ADDR_T(mte.bias + mte.dyn - mte.vstart); breakpoint_enable(task, &entry_bp->breakpoint); } } } else { fprintf(stderr, "Couldn't read dynamic loader `%s` for PID %d.\n" "Tracing events may be missed.\n", fname, task->pid ); } fail4: close_elf(&mte_ld); } else { fprintf(stderr, "Couldn't open dynamic loader `%s` for PID %d.\n" "Tracing events may be missed.\n", fname, task->pid ); } return libref; fail3: close_elf(&mte); fail2: libref_delete(libref); fail1: free(filename); return libref; }