// SPDX-FileCopyrightText: 2009-2021 pancake // SPDX-License-Identifier: LGPL-3.0-only #include #include #include #include #include "../core_private.h" struct open_list_ascii_data_t { RzPrint *p; int fdsz; }; static bool core_bin_reload(RzCore *r, const char *file, ut64 baseaddr) { RzCoreFile *cf = rz_core_file_cur(r); if (!cf) { return false; } RzBinFile *obf = rz_bin_file_find_by_fd(r->bin, cf->fd); if (!obf) { return false; } RzBinFile *nbf = rz_bin_reload(r->bin, obf, baseaddr); if (!nbf) { return false; } rz_core_bin_apply_all_info(r, nbf); return true; } static bool init_desc_list_visual_cb(void *user, void *data, ut32 id) { struct open_list_ascii_data_t *u = (struct open_list_ascii_data_t *)user; RzIODesc *desc = (RzIODesc *)data; ut64 sz = rz_io_desc_size(desc); if (sz > u->fdsz) { u->fdsz = sz; } return true; } static bool desc_list_visual_cb(void *user, void *data, ut32 id) { struct open_list_ascii_data_t *u = (struct open_list_ascii_data_t *)user; RzPrint *p = u->p; RzIODesc *desc = (RzIODesc *)data; ut64 sz = rz_io_desc_size(desc); rz_cons_printf("%2d %c %s 0x%08" PFMT64x " ", desc->fd, (desc->io && (desc->io->desc == desc)) ? '*' : '-', rz_str_rwx_i(desc->perm), sz); int flags = p->flags; p->flags &= ~RZ_PRINT_FLAGS_HEADER; rz_print_progressbar(p, sz * 100 / u->fdsz, rz_cons_get_size(NULL) - 40); p->flags = flags; rz_cons_printf(" %s\n", desc->uri); return true; } static bool desc_list_quiet_cb(void *user, void *data, ut32 id) { RzPrint *p = (RzPrint *)user; RzIODesc *desc = (RzIODesc *)data; p->cb_printf("%d\n", desc->fd); return true; } static bool desc_list_cb(void *user, void *data, ut32 id) { RzPrint *p = (RzPrint *)user; RzIODesc *desc = (RzIODesc *)data; p->cb_printf("%2d %c %s 0x%08" PFMT64x " %s\n", desc->fd, (desc->io && (desc->io->desc == desc)) ? '*' : '-', rz_str_rwx_i(desc->perm), rz_io_desc_size(desc), desc->uri); return true; } static bool desc_list_json_cb(void *user, void *data, ut32 id) { PJ *pj = (PJ *)user; RzIODesc *desc = (RzIODesc *)data; // TODO: from is always 0? See librz/core/file.c:945 ut64 from = 0LL; pj_o(pj); pj_kb(pj, "raised", desc->io && (desc->io->desc == desc)); pj_kN(pj, "fd", desc->fd); pj_ks(pj, "uri", desc->uri); pj_kn(pj, "from", from); pj_kb(pj, "writable", desc->perm & RZ_PERM_W); pj_kN(pj, "size", rz_io_desc_size(desc)); pj_end(pj); return true; } static bool desc_list_table_cb(void *user, void *data, ut32 id) { RzTable *t = (RzTable *)user; RzIODesc *desc = (RzIODesc *)data; rz_table_add_rowf(t, "dbsXs", desc->fd, desc->io && (desc->io->desc == desc), rz_str_rwx_i(desc->perm), rz_io_desc_size(desc), desc->uri); return true; } RZ_IPI RzCmdStatus rz_open_close_handler(RzCore *core, int argc, const char **argv) { if (!rz_num_is_valid_input(NULL, argv[1])) { RZ_LOG_ERROR("Invalid fd: %s\n", argv[1]); return RZ_CMD_STATUS_ERROR; } int fd = (int)rz_num_math(NULL, argv[1]); if (!rz_core_file_close_fd(core, fd)) { RZ_LOG_ERROR("Unable to find file descriptor %d\n", fd); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_close_all_handler(RzCore *core, int argc, const char **argv) { rz_core_file_close_fd(core, -1); rz_io_close_all(core->io); rz_bin_file_delete_all(core->bin); // TODO: Move to a-- ? rz_analysis_purge(core->analysis); // TODO: Move to f-- ? rz_flag_unset_all(core->flags); RZ_LOG_INFO("Close all files\n"); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_list_ascii_handler(RzCore *core, int argc, const char **argv) { struct open_list_ascii_data_t data = { 0 }; data.p = core->print; data.fdsz = 0; rz_id_storage_foreach(core->io->files, init_desc_list_visual_cb, &data); rz_id_storage_foreach(core->io->files, desc_list_visual_cb, &data); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_arch_bits_handler(RzCore *core, int argc, const char **argv) { const char *filename = argc > 3 ? argv[3] : NULL; ut16 bits = rz_num_math(core->num, argv[2]); const char *arch = argv[1]; int res = rz_core_bin_set_arch_bits(core, filename, arch, bits); return res ? RZ_CMD_STATUS_OK : RZ_CMD_STATUS_ERROR; } RZ_IPI RzCmdStatus rz_open_use_handler(RzCore *core, int argc, const char **argv) { RzListIter *iter = NULL; RzCoreFile *f; int fdnum = rz_num_math(NULL, argv[1]); rz_list_foreach (core->files, iter, f) { if (f->fd == fdnum) { core->file = f; rz_io_use_fd(core->io, fdnum); RzBinFile *bf = rz_bin_file_find_by_fd(core->bin, fdnum); if (!bf) { RZ_LOG_ERROR("Could not find binfile with fd %d\n", fdnum); return RZ_CMD_STATUS_ERROR; } rz_core_bin_raise(core, bf->id); rz_core_block_read(core); RZ_LOG_INFO("Switched to fd %d (%s)\n", fdnum, bf->file); return RZ_CMD_STATUS_OK; } } RZ_LOG_ERROR("Could not find any opened file with fd %d\n", fdnum); return RZ_CMD_STATUS_ERROR; } static RzCmdStatus prioritize_file(RzCore *core, int fd) { if (fd <= 0) { RZ_LOG_ERROR("Wrong file descriptor %d\n", fd); return RZ_CMD_STATUS_ERROR; } int curfd = rz_io_fd_get_current(core->io); if (fd == curfd) { return RZ_CMD_STATUS_OK; } if (!rz_io_use_fd(core->io, fd)) { RZ_LOG_ERROR("Could not use IO fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } rz_core_block_read(core); RzBinFile *bf = rz_bin_file_find_by_fd(core->bin, fd); if (bf && !rz_core_bin_raise(core, bf->id)) { RZ_LOG_ERROR("Could not use bin id %d\n", bf->id); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_prioritize_handler(RzCore *core, int argc, const char **argv) { int fd = atoi(argv[1]); return prioritize_file(core, fd); } RZ_IPI RzCmdStatus rz_open_prioritize_next_handler(RzCore *core, int argc, const char **argv) { int fd = rz_io_fd_get_next(core->io, rz_io_fd_get_current(core->io)); return prioritize_file(core, fd); } RZ_IPI RzCmdStatus rz_open_prioritize_prev_handler(RzCore *core, int argc, const char **argv) { int fd = rz_io_fd_get_prev(core->io, rz_io_fd_get_current(core->io)); return prioritize_file(core, fd); } RZ_IPI RzCmdStatus rz_open_prioritize_next_rotate_handler(RzCore *core, int argc, const char **argv) { int fd = rz_io_fd_get_next(core->io, rz_io_fd_get_current(core->io)); if (fd == -1) { fd = rz_io_fd_get_lowest(core->io); } return prioritize_file(core, fd) ? RZ_CMD_STATUS_OK : RZ_CMD_STATUS_ERROR; } RZ_IPI RzCmdStatus rz_open_maps_remove_handler(RzCore *core, int argc, const char **argv) { if (!rz_num_is_valid_input(NULL, argv[1])) { RZ_LOG_ERROR("Invalid map id '%s'\n", argv[1]); return RZ_CMD_STATUS_ERROR; } ut32 map_id = rz_num_math(NULL, argv[1]); if (!rz_io_map_del(core->io, map_id)) { RZ_LOG_ERROR("Could not delete IO map %d\n", map_id); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_remove_all_handler(RzCore *core, int argc, const char **argv) { rz_io_map_reset(core->io); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_list_ascii_handler(RzCore *core, int argc, const char **argv) { RzList *list = rz_list_newf((RzListFree)rz_listinfo_free); if (!list) { return RZ_CMD_STATUS_ERROR; } void **it; RzPVector *maps = rz_io_maps(core->io); rz_pvector_foreach_prev(maps, it) { RzIOMap *map = *it; char temp[32]; rz_strf(temp, "%d", map->fd); RzListInfo *info = rz_listinfo_new(map->name, map->itv, map->itv, map->perm, temp); if (!info) { break; } rz_list_append(list, info); } RzTable *table = rz_core_table(core); rz_table_visual_list(table, list, core->offset, core->blocksize, rz_cons_get_size(NULL), rz_config_get_i(core->config, "scr.color")); char *tablestr = rz_table_tostring(table); rz_cons_printf("%s", tablestr); rz_table_free(table); rz_list_free(list); free(tablestr); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_all_fd_handler(RzCore *core, int argc, const char **argv) { ut32 fd = argc > 1 ? rz_num_math(NULL, argv[1]) : rz_io_fd_get_current(core->io); RzIODesc *desc = rz_io_desc_get(core->io, fd); if (!desc) { RZ_LOG_ERROR("Could not find any file descriptor with fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } RzIOMap *map = rz_io_map_add(core->io, fd, desc->perm, 0, 0, UT64_MAX); if (!map) { RZ_LOG_ERROR("Could not create a IO map for file descriptor %d\n", fd); return RZ_CMD_STATUS_ERROR; } rz_io_map_set_name(map, desc->name); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_relocate_handler(RzCore *core, int argc, const char **argv) { if (!rz_num_is_valid_input(NULL, argv[1])) { RZ_LOG_ERROR("Invalid map id '%s'\n", argv[1]); return RZ_CMD_STATUS_ERROR; } if (!rz_num_is_valid_input(core->num, argv[2])) { RZ_LOG_ERROR("Invalid address '%s'\n", argv[2]); return RZ_CMD_STATUS_ERROR; } ut32 map_id = (ut32)rz_num_math(NULL, argv[1]); ut64 addr = rz_num_math(core->num, argv[2]); if (!rz_io_map_remap(core->io, map_id, addr)) { RZ_LOG_ERROR("Could not relocate map with id %d to %" PFMT64x "\n", map_id, addr); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_relocate_current_handler(RzCore *core, int argc, const char **argv) { if (!rz_num_is_valid_input(core->num, argv[1])) { RZ_LOG_ERROR("Invalid address '%s'\n", argv[1]); return RZ_CMD_STATUS_ERROR; } RzIOMap *map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Could not find any IO map at current offset\n"); return RZ_CMD_STATUS_ERROR; } ut64 addr = rz_num_math(core->num, argv[1]); if (!rz_io_map_remap(core->io, map->id, addr)) { RZ_LOG_ERROR("Could not relocate map with id %d to %" PFMT64x "\n", map->id, addr); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_resize_handler(RzCore *core, int argc, const char **argv) { if (!rz_num_is_valid_input(NULL, argv[1])) { RZ_LOG_ERROR("Invalid map id '%s'\n", argv[1]); return RZ_CMD_STATUS_ERROR; } if (!rz_num_is_valid_input(core->num, argv[2])) { RZ_LOG_ERROR("Invalid size '%s'\n", argv[2]); return RZ_CMD_STATUS_ERROR; } ut32 map_id = (ut32)rz_num_math(NULL, argv[1]); ut64 size = rz_num_math(core->num, argv[2]); if (!rz_io_map_resize(core->io, map_id, size)) { RZ_LOG_ERROR("Could not resize map with id %d to %" PFMT64x "\n", map_id, size); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_prioritize_handler(RzCore *core, int argc, const char **argv) { ut32 id = (ut32)rz_num_math(core->num, argv[1]); if (!rz_io_map_exists_for_id(core->io, id)) { RZ_LOG_ERROR("Cannot find any map with mapid %d\n", id); return RZ_CMD_STATUS_ERROR; } rz_io_map_priorize(core->io, id); rz_core_block_read(core); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_prioritize_binid_handler(RzCore *core, int argc, const char **argv) { ut32 id = (ut32)rz_num_math(core->num, argv[1]); if (!rz_bin_file_set_cur_by_id(core->bin, id)) { RZ_LOG_ERROR("Cannot prioritize bin with fd %d\n", id); return RZ_CMD_STATUS_ERROR; } RzListIter *it; RzCoreFile *file = NULL; rz_list_foreach (core->files, it, file) { void **binfile; rz_pvector_foreach (&file->binfiles, binfile) { RzBinFile *bf = *binfile; if (bf->id == id) { void **map; rz_pvector_foreach (&file->maps, map) { RzIOMap *m = *map; rz_io_map_priorize(core->io, m->id); } } } } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_deprioritize_handler(RzCore *core, int argc, const char **argv) { ut32 id = (ut32)rz_num_math(core->num, argv[1]); if (!rz_io_map_exists_for_id(core->io, id)) { RZ_LOG_ERROR("Cannot find any map with mapid %d\n", id); return RZ_CMD_STATUS_ERROR; } rz_io_map_depriorize(core->io, id); rz_core_block_read(core); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_prioritize_fd_handler(RzCore *core, int argc, const char **argv) { int fd = (int)rz_num_math(core->num, argv[1]); if (!rz_io_map_priorize_for_fd(core->io, fd)) { RZ_LOG_ERROR("Cannot prioritize any map for fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_name_handler(RzCore *core, int argc, const char **argv) { RzIOMap *map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Cannot find any map at address %" PFMT64x "d\n", core->offset); return RZ_CMD_STATUS_ERROR; } rz_io_map_set_name(map, argv[1]); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_name_del_handler(RzCore *core, int argc, const char **argv) { RzIOMap *map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Cannot find any map at address %" PFMT64x "\n", core->offset); return RZ_CMD_STATUS_ERROR; } rz_io_map_del_name(map); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_name_id_handler(RzCore *core, int argc, const char **argv) { ut32 id = rz_num_math(core->num, argv[1]); RzIOMap *map = rz_io_map_resolve(core->io, id); if (!map) { RZ_LOG_ERROR("Cannot find any map with id %d\n", id); return RZ_CMD_STATUS_ERROR; } rz_io_map_set_name(map, argv[2]); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_name_id_del_handler(RzCore *core, int argc, const char **argv) { ut32 id = rz_num_math(core->num, argv[1]); RzIOMap *map = rz_io_map_resolve(core->io, id); if (!map) { RZ_LOG_ERROR("Cannot find any map with id %d\n", id); return RZ_CMD_STATUS_ERROR; } rz_io_map_del_name(map); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_map_fd_handler(RzCore *core, int argc, const char **argv) { ut32 fd = argc > 1 ? rz_num_math(NULL, argv[1]) : rz_io_fd_get_current(core->io); RzIODesc *desc = rz_io_desc_get(core->io, fd); if (!desc) { RZ_LOG_ERROR("Cannot find any descriptor with fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } ut64 size = rz_io_desc_size(desc); RzIOMap *map = rz_io_map_add(core->io, fd, desc->perm, 0, 0, size); if (!map) { RZ_LOG_ERROR("Cannot create new map for fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } rz_io_map_set_name(map, desc->name); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_flags_handler(RzCore *core, int argc, const char **argv) { int perm = rz_str_rwx(argv[1]); RzIOMap *map = NULL; if (argc > 2) { ut32 id = rz_num_math(NULL, argv[2]); map = rz_io_map_resolve(core->io, id); if (!map) { RZ_LOG_ERROR("Cannot find any map with id %d\n", id); return RZ_CMD_STATUS_ERROR; } } else { map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Cannot find any map at the current address %" PFMT64x "\n", core->offset); return RZ_CMD_STATUS_ERROR; } } map->perm = perm; return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_flags_global_handler(RzCore *core, int argc, const char **argv) { const char *arg = argv[1]; enum mode { ADD, DEL, SET, } mode = SET; if (arg[0] == '+') { mode = ADD; arg++; } else if (arg[0] == '-') { mode = DEL; arg++; } int perm = rz_str_rwx(arg); RzPVector *maps = rz_io_maps(core->io); void **it; rz_pvector_foreach (maps, it) { RzIOMap *map = *it; switch (mode) { case ADD: map->perm |= perm; break; case DEL: map->perm &= ~perm; break; case SET: map->perm = perm; break; } } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_map_handler(RzCore *core, int argc, const char **argv) { int fd = (int)rz_num_math(NULL, argv[1]); if (fd < 3) { RZ_LOG_ERROR("Wrong fd, it must be greather than 3\n"); return RZ_CMD_STATUS_ERROR; } ut64 vaddr = rz_num_math(core->num, argv[2]); ut64 size = argc > 3 ? rz_num_math(core->num, argv[3]) : rz_io_fd_size(core->io, fd); ut64 paddr = argc > 4 ? rz_num_math(core->num, argv[4]) : 0; int rwx = argc > 5 ? rz_str_rwx(argv[5]) : 0; const char *name = argc > 6 ? argv[6] : ""; if (argc <= 5) { RzIODesc *desc = rz_io_desc_get(core->io, fd); if (!desc) { RZ_LOG_ERROR("Could not determine any opened file with fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } rwx = desc->perm; } RzIOMap *map = rz_io_map_add(core->io, fd, rwx, paddr, vaddr, size); if (!map) { RZ_LOG_ERROR("Could not create new map for fd %d at vaddr %" PFMT64x "\n", fd, vaddr); return RZ_CMD_STATUS_ERROR; } rz_io_map_set_name(map, name); return RZ_CMD_STATUS_OK; } static void open_maps_show(RzCore *core, RzCmdStateOutput *state, RzIOMap *map, bool seek_inside) { switch (state->mode) { case RZ_OUTPUT_MODE_QUIET: rz_cons_printf("%d %d\n", map->fd, map->id); break; case RZ_OUTPUT_MODE_QUIETEST: rz_cons_printf("0x%08" PFMT64x "\n", rz_io_map_get_from(map)); break; case RZ_OUTPUT_MODE_JSON: pj_o(state->d.pj); pj_ki(state->d.pj, "map", map->id); pj_ki(state->d.pj, "fd", map->fd); pj_kn(state->d.pj, "delta", map->delta); pj_kn(state->d.pj, "from", rz_io_map_get_from(map)); pj_kn(state->d.pj, "to", rz_itv_end(map->itv)); pj_ks(state->d.pj, "perm", rz_str_rwx_i(map->perm)); pj_ks(state->d.pj, "name", rz_str_get(map->name)); pj_end(state->d.pj); break; case RZ_OUTPUT_MODE_TABLE: rz_table_add_rowf(state->d.t, "ddxxxxxss", map->id, map->fd, map->delta, map->delta + rz_itv_size(map->itv), rz_itv_size(map->itv), rz_io_map_get_from(map), rz_itv_end(map->itv), rz_str_rwx_i(map->perm), rz_str_get(map->name)); break; default: rz_cons_printf("%2d fd: %i +0x%08" PFMT64x " 0x%08" PFMT64x " %c 0x%08" PFMT64x " %s %s\n", map->id, map->fd, map->delta, rz_io_map_get_from(map), seek_inside ? '*' : '-', rz_io_map_get_to(map), rz_str_rwx_i(map->perm), rz_str_get(map->name)); break; } } static void open_maps_list(RzCore *core, RzCmdStateOutput *state, int fd) { RzPVector *maps = rz_io_maps(core->io); void **it; rz_cmd_state_output_array_start(state); rz_cmd_state_output_set_columnsf(state, "ddxxxxxss", "id", "fd", "pa", "pa_end", "size", "va", "va_end", "perm", "name"); if (state->mode == RZ_OUTPUT_MODE_TABLE) { state->d.t->showFancy = true; } RzIOMap *at_seek = NULL; if (state->mode == RZ_OUTPUT_MODE_STANDARD) { at_seek = rz_io_map_get(core->io, core->offset); } rz_pvector_foreach (maps, it) { RzIOMap *map = *it; if (fd >= 0 && map->fd != fd) { continue; } open_maps_show(core, state, map, map == at_seek); } rz_cmd_state_output_array_end(state); } RZ_IPI RzCmdStatus rz_open_maps_list_handler(RzCore *core, int argc, const char **argv, RzCmdStateOutput *state) { int fd = argc > 1 ? rz_num_math(NULL, argv[1]) : -1; open_maps_list(core, state, fd); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_maps_list_cur_handler(RzCore *core, int argc, const char **argv, RzCmdStateOutput *state) { RzIOMap *map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Cannot find any map at the current address %" PFMT64x "\n", core->offset); return RZ_CMD_STATUS_ERROR; } rz_cmd_state_output_set_columnsf(state, "ddxxxxxss", "id", "fd", "pa", "pa_end", "va", "va_end", "perm", "name"); if (state->mode == RZ_OUTPUT_MODE_TABLE) { state->d.t->showFancy = true; } open_maps_show(core, state, map, false); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_select_id_handler(RzCore *core, int argc, const char **argv) { ut32 id = (ut32)rz_num_math(NULL, argv[1]); if (!rz_core_bin_raise(core, id)) { RZ_LOG_ERROR("Could not select binary file with id %d\n", id); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_select_fd_handler(RzCore *core, int argc, const char **argv) { ut32 fd = rz_num_math(NULL, argv[1]); RzBinFile *bf = rz_bin_file_find_by_fd(core->bin, fd); if (!bf) { RZ_LOG_ERROR("Could not find any binary file for fd %d.\n", fd); return RZ_CMD_STATUS_ERROR; } if (!rz_core_bin_raise(core, bf->id)) { RZ_LOG_ERROR("core: Could not select the binary file for fd %d.\n", fd); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_del_handler(RzCore *core, int argc, const char **argv) { ut32 id = (ut32)rz_num_math(NULL, argv[1]); RzBinFile *bf = rz_bin_file_find_by_id(core->bin, id); if (!bf) { RZ_LOG_ERROR("Could not find any binary file with id %d.\n", id); return RZ_CMD_STATUS_ERROR; } if (!rz_core_binfiles_delete(core, bf)) { RZ_LOG_ERROR("Could not delete binary file with id %d\n", id); return RZ_CMD_STATUS_ERROR; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_del_all_handler(RzCore *core, int argc, const char **argv) { rz_bin_file_delete_all(core->bin); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_list_handler(RzCore *core, int argc, const char **argv, RzCmdStateOutput *state) { rz_core_binfiles_print(core, state); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_show_handler(RzCore *core, int argc, const char **argv) { RzBinFile *bf = rz_bin_file_at(core->bin, core->offset); if (bf) { rz_cons_printf("%d\n", bf->id); } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_list_ascii_handler(RzCore *core, int argc, const char **argv) { RzBin *bin = core->bin; if (!bin) { return RZ_CMD_STATUS_ERROR; } RzList *list = rz_list_newf((RzListFree)rz_listinfo_free); if (!list) { return RZ_CMD_STATUS_ERROR; } RzListIter *iter; RzBinFile *bf = NULL; rz_list_foreach (bin->binfiles, iter, bf) { char temp[64]; RzInterval inter = (RzInterval){ bf->o->opts.baseaddr, bf->o->size }; RzListInfo *info = rz_listinfo_new(bf->file, inter, inter, -1, sdb_itoa(bf->fd, temp, 10)); if (!info) { break; } rz_list_append(list, info); } RzTable *table = rz_core_table(core); rz_table_visual_list(table, list, core->offset, core->blocksize, rz_cons_get_size(NULL), rz_config_get_i(core->config, "scr.color")); char *table_text = rz_table_tostring(table); rz_cons_printf("\n%s\n", table_text); rz_free(table_text); rz_table_free(table); rz_list_free(list); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_add_handler(RzCore *core, int argc, const char **argv) { ut64 loadaddr = rz_num_math(core->num, argv[1]); int fd = rz_io_fd_get_current(core->io); RzIODesc *desc = rz_io_desc_get(core->io, fd); if (!desc) { RZ_LOG_ERROR("Could not determine any opened file with fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } RzBinOptions opt; opt.sz = 1024 * 1024 * 1; rz_core_bin_options_init(core, &opt, desc->fd, core->offset, loadaddr); RzBinFile *bf = rz_bin_open_io(core->bin, &opt); rz_core_bin_apply_all_info(core, bf); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_file_handler(RzCore *core, int argc, const char **argv) { int saved_fd = rz_io_fd_get_current(core->io); RzList *files = rz_list_newf(NULL); RzListIter *iter; RzIODesc *desc = NULL; if (argc > 1) { desc = rz_io_open(core->io, argv[1], RZ_PERM_R, 0); if (!desc) { RZ_LOG_ERROR("Could not open file %s\n", argv[1]); rz_list_free(files); return RZ_CMD_STATUS_ERROR; } rz_list_append(files, (void *)(size_t)desc->fd); } else { RzList *ofiles = rz_id_storage_list(core->io->files); RzIODesc *desc; rz_list_foreach (ofiles, iter, desc) { rz_list_append(files, (void *)(size_t)desc->fd); } } void *_fd; rz_list_foreach (files, iter, _fd) { RzBinOptions opt; int fd = (size_t)_fd; rz_core_bin_options_init(core, &opt, fd, core->offset, 0); RzBinFile *bf = rz_bin_open_io(core->bin, &opt); rz_core_bin_apply_all_info(core, bf); } rz_list_free(files); rz_io_desc_close(desc); rz_io_use_fd(core->io, saved_fd); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_rebase_handler(RzCore *core, int argc, const char **argv) { rz_core_bin_rebase(core, rz_num_math(core->num, argv[1])); rz_core_bin_apply_all_info(core, rz_bin_cur(core->bin)); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_binary_reload_handler(RzCore *core, int argc, const char **argv) { // XXX: this will reload the bin using the buffer. // An assumption is made that assumes there is an underlying // plugin that will be used to load the bin (e.g. malloc://) // TODO: Might be nice to reload a bin at a specified offset? core_bin_reload(core, NULL, rz_num_math(core->num, argv[1])); rz_core_block_read(core); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_handler(RzCore *core, int argc, const char **argv) { ut64 addr = argc > 2 ? rz_num_math(core->num, argv[2]) : 0; int perms = argc > 3 ? rz_str_rwx(argv[3]) : RZ_PERM_R; return bool2status(rz_core_file_open_load(core, argv[1], addr, perms, false)); } RZ_IPI RzCmdStatus rz_open_write_handler(RzCore *core, int argc, const char **argv) { ut64 addr = argc > 2 ? rz_num_math(core->num, argv[2]) : 0; int perms = argc > 3 ? rz_str_rwx(argv[3]) : RZ_PERM_RW; return bool2status(rz_core_file_open_load(core, argv[1], addr, perms, true)); } RZ_IPI RzCmdStatus rz_open_list_handler(RzCore *core, int argc, const char **argv, RzCmdStateOutput *state) { rz_cmd_state_output_array_start(state); rz_cmd_state_output_set_columnsf(state, "dbsXs", "fd", "raised", "perm", "size", "uri"); switch (state->mode) { case RZ_OUTPUT_MODE_STANDARD: rz_id_storage_foreach(core->io->files, desc_list_cb, core->print); break; case RZ_OUTPUT_MODE_JSON: rz_id_storage_foreach(core->io->files, desc_list_json_cb, state->d.pj); break; case RZ_OUTPUT_MODE_TABLE: rz_id_storage_foreach(core->io->files, desc_list_table_cb, state->d.t); break; case RZ_OUTPUT_MODE_QUIET: rz_id_storage_foreach(core->io->files, desc_list_quiet_cb, core->print); break; default: break; } rz_cmd_state_output_array_end(state); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_show_current_handler(RzCore *core, int argc, const char **argv, RzCmdStateOutput *state) { RzIOMap *map = rz_io_map_get(core->io, core->offset); if (!map) { RZ_LOG_ERROR("Could not find any map at current address %" PFMT64x ".\n", core->offset); return RZ_CMD_STATUS_ERROR; } RzIODesc *desc = rz_io_desc_get(core->io, map->fd); if (!desc) { RZ_LOG_ERROR("Could not find file for map fd %d.\n", map->fd); return RZ_CMD_STATUS_ERROR; } rz_cmd_state_output_set_columnsf(state, "dbsXs", "fd", "raised", "perm", "size", "uri"); switch (state->mode) { case RZ_OUTPUT_MODE_STANDARD: desc_list_cb(core->print, desc, 0); break; case RZ_OUTPUT_MODE_JSON: desc_list_json_cb(state->d.pj, desc, 0); break; case RZ_OUTPUT_MODE_TABLE: desc_list_table_cb(state->d.t, desc, 0); break; case RZ_OUTPUT_MODE_QUIET: desc_list_quiet_cb(core->print, desc, 0); break; default: break; } return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_exchange_handler(RzCore *core, int argc, const char **argv) { int fd = (int)rz_num_math(NULL, argv[1]); int fdx = (int)rz_num_math(NULL, argv[2]); if ((fdx == -1) || (fd == -1) || (fdx == fd)) { RZ_LOG_ERROR("Could not exchange file descriptor %d and %d.\n", fd, fdx); return RZ_CMD_STATUS_ERROR; } rz_io_desc_exchange(core->io, fd, fdx); rz_core_block_read(core); return RZ_CMD_STATUS_OK; } static RzCmdStatus open_core_file(RzCore *core, const char *filename) { if (core->tasks.current_task != core->tasks.main_task) { RZ_LOG_ERROR("This command can only be executed on the main task!\n"); return RZ_CMD_STATUS_ERROR; } rz_core_task_sync_end(&core->tasks); rz_core_fini(core); rz_core_init(core); rz_core_task_sync_begin(&core->tasks); if (!rz_core_file_open(core, filename, RZ_PERM_R, 0)) { RZ_LOG_ERROR("Cannot open file '%s'\n", filename); return RZ_CMD_STATUS_ERROR; } ut64 baddr = rz_config_get_i(core->config, "bin.baddr"); return bool2status(rz_core_bin_load(core, NULL, baddr)); } RZ_IPI RzCmdStatus rz_open_core_file_handler(RzCore *core, int argc, const char **argv) { return open_core_file(core, argv[1]); } RZ_IPI RzCmdStatus rz_open_malloc_handler(RzCore *core, int argc, const char **argv) { int len = (int)rz_num_math(core->num, argv[1]); if (len < 0) { RZ_LOG_ERROR("Invalid length %d.\n", len); return RZ_CMD_STATUS_ERROR; } RzCmdStatus res = RZ_CMD_STATUS_ERROR; ut8 *data = RZ_NEWS(ut8, len); if (!data) { return RZ_CMD_STATUS_ERROR; } if (!rz_io_read_at(core->io, core->offset, data, len)) { RZ_LOG_ERROR("Cannot read %d bytes from current offset.\n", len); goto err; } char uri[100]; rz_strf(uri, "malloc://%d", len); RzCoreFile *cfile = rz_core_file_open(core, uri, RZ_PERM_RWX, 0); if (!cfile) { RZ_LOG_ERROR("Cannot open '%s'.\n", uri); goto err; } if (!rz_core_bin_load(core, uri, 0)) { RZ_LOG_ERROR("Cannot load binary info of '%s'.\n", uri); goto err; } RzIODesc *desc = rz_io_desc_get(core->io, cfile->fd); rz_warn_if_fail(desc); rz_io_desc_write_at(desc, 0, data, len); res = RZ_CMD_STATUS_OK; err: free(data); return res; } static RzCmdStatus open_nobin_file(RzCore *core, const char *uri, ut64 addr, int perms) { if (!strcmp(uri, "=")) { uri = "malloc://512"; } RzIODesc *desc = rz_io_open_at(core->io, uri, perms, 0644, addr, NULL); if (!desc || desc->fd == -1) { RZ_LOG_ERROR("Cannot open '%s' at %" PFMT64x ".\n", uri, addr); return RZ_CMD_STATUS_ERROR; } core->num->value = desc->fd; rz_core_block_read(core); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_open_nobin_handler(RzCore *core, int argc, const char **argv) { ut64 addr = argc > 2 ? rz_num_math(core->num, argv[2]) : 0; int perms = argc > 3 ? rz_str_rwx(argv[3]) : RZ_PERM_R; return open_nobin_file(core, argv[1], addr, perms); } RZ_IPI RzCmdStatus rz_open_nobin_write_handler(RzCore *core, int argc, const char **argv) { ut64 addr = argc > 2 ? rz_num_math(core->num, argv[2]) : 0; int perms = argc > 3 ? rz_str_rwx(argv[3]) : RZ_PERM_RW; return open_nobin_file(core, argv[1], addr, perms); } RZ_IPI RzCmdStatus rz_reopen_handler(RzCore *core, int argc, const char **argv) { int fd; if (argc > 1) { fd = (int)rz_num_math(NULL, argv[1]); if (fd < 0) { RZ_LOG_ERROR("Invalid negative fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } } else { if (!core->io || !core->io->desc) { RZ_LOG_ERROR("Cannot find current file.\n"); return RZ_CMD_STATUS_ERROR; } fd = core->io->desc->fd; } rz_core_io_file_open(core, fd); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_write_handler(RzCore *core, int argc, const char **argv) { int fd; int perms = RZ_PERM_RW; if (argc > 1) { fd = (int)rz_num_math(NULL, argv[1]); if (fd < 0) { RZ_LOG_ERROR("Invalid negative fd %d\n", fd); return RZ_CMD_STATUS_ERROR; } } else { if (!core->io || !core->io->desc) { RZ_LOG_ERROR("Cannot find current file.\n"); return RZ_CMD_STATUS_ERROR; } fd = core->io->desc->fd; perms |= core->io->desc->perm; } rz_core_io_file_reopen(core, fd, perms); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_binary_handler(RzCore *core, int argc, const char **argv) { return bool2status(rz_core_file_reopen(core, argv[1], 0, 2)); } RZ_IPI RzCmdStatus rz_reopen_core_handler(RzCore *core, int argc, const char **argv) { if (!core->io || !core->io->desc) { RZ_LOG_ERROR("Could not find current file\n"); return RZ_CMD_STATUS_ERROR; } return open_core_file(core, core->io->desc->uri); } RZ_IPI RzCmdStatus rz_reopen_debug_handler(RzCore *core, int argc, const char **argv) { // TODO: this is bad as we force ourselves to convert arguments to strings. // There should be an API to reopen a file in debug mode and directly // pass args to it. char **args = RZ_NEWS(char *, argc - 1); int i; for (i = 1; i < argc; i++) { char *t = rz_cmd_escape_arg(argv[i], RZ_CMD_ESCAPE_DOUBLE_QUOTED_ARG); args[i - 1] = rz_str_newf("\"%s\"", t); free(t); } char *args_str = rz_str_array_join((const char **)args, argc - 1, " "); for (i = 0; i < argc - 1; i++) { free(args[i]); } free(args); rz_core_file_reopen_debug(core, args_str); free(args_str); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_debug_file_handler(RzCore *core, int argc, const char **argv) { const char *uri = argv[1]; ut64 addr = argc > 2 ? rz_num_math(core->num, argv[2]) : 0; rz_core_file_reopen_remote_debug(core, uri, addr); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_debug_rzrun_handler(RzCore *core, int argc, const char **argv) { char *file = rz_file_temp("rz-run"); char *s = strdup(argv[1]); rz_config_set(core->config, "dbg.profile", file); rz_str_replace_char(s, ',', '\n'); rz_file_dump(file, (const ut8 *)s, strlen(s), 0); rz_file_dump(file, (const ut8 *)"\n", 1, 1); free(s); free(file); rz_core_file_reopen_debug(core, ""); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_malloc_handler(RzCore *core, int argc, const char **argv) { rz_core_file_reopen_in_malloc(core); return RZ_CMD_STATUS_OK; } RZ_IPI RzCmdStatus rz_reopen_nobin_handler(RzCore *core, int argc, const char **argv) { return bool2status(rz_core_file_reopen(core, NULL, 0, 0)); } RZ_IPI RzCmdStatus rz_reopen_nobin_write_handler(RzCore *core, int argc, const char **argv) { return bool2status(rz_core_file_reopen(core, NULL, RZ_PERM_RW, 0)); } static RzCmdStatus reopen_nobin_headers(RzCore *core, int add_perms) { RzIODesc *desc = rz_io_desc_get(core->io, core->file->fd); if (!desc) { RZ_LOG_ERROR("Could not find current file.\n"); return RZ_CMD_STATUS_ERROR; } int perms = core->io->desc->perm | add_perms; char *fname = strdup(desc->name); if (!fname) { return RZ_CMD_STATUS_ERROR; } if (!rz_core_bin_load_structs(core, fname)) { RZ_LOG_WARN("Could not load file format information for '%s'.\n", fname); } bool res = rz_core_file_reopen(core, fname, perms, 0); free(fname); return bool2status(res); } RZ_IPI RzCmdStatus rz_reopen_nobin_headers_handler(RzCore *core, int argc, const char **argv) { return reopen_nobin_headers(core, 0); } RZ_IPI RzCmdStatus rz_reopen_nobin_write_headers_handler(RzCore *core, int argc, const char **argv) { return reopen_nobin_headers(core, RZ_PERM_RW); }