static int rap__read(RIO *io, RIODesc *fd, ut8 *buf, int count) { RSocket *s = RIORAP_FD (fd); int ret, i = (int)count; ut8 tmp[5]; // XXX. if count is > RMT_MAX, just perform multiple queries if (count > RMT_MAX) { count = RMT_MAX; } // send tmp[0] = RMT_READ; r_write_be32 (tmp + 1, count); r_socket_write (s, tmp, 5); r_socket_flush (s); // recv ret = r_socket_read_block (s, tmp, 5); if (ret != 5 || tmp[0] != (RMT_READ | RMT_REPLY)) { eprintf ("rap__read: Unexpected rap read reply " "(%d=0x%02x) expected (%d=0x%02x)\n", ret, tmp[0], 2, (RMT_READ | RMT_REPLY)); return -1; } i = r_read_at_be32 (tmp, 1); if (i >count) { eprintf ("rap__read: Unexpected data size %d\n", i); return -1; } r_socket_read_block (s, buf, i); return count; }
static int rap__write(RIO *io, RIODesc *fd, const ut8 *buf, int count) { RSocket *s = RIORAP_FD (fd); ut8 *tmp; int ret; if (count < 1) { return count; } // TOOD: if count > RMT_MAX iterate ! if (count > RMT_MAX) { count = RMT_MAX; } if (!(tmp = (ut8 *)malloc (count + 5))) { eprintf ("rap__write: malloc failed\n"); return -1; } tmp[0] = RMT_WRITE; r_write_be32 (tmp + 1, count); memcpy (tmp + 5, buf, count); ret = r_socket_write (s, tmp, count + 5); r_socket_flush (s); if (r_socket_read (s, tmp, 5) != 5) { // TODO read_block? eprintf ("rap__write: error\n"); ret = -1; } else { ret = r_read_be32 (tmp + 1); if (!ret) { ret = -1; } } free (tmp); return ret; }
static int assemble(RAsm *a, RAsmOp *op, const char *buf) { const bool is_thumb = (a->bits == 16); int opsize; ut32 opcode; if (a->bits == 64) { if (!arm64ass (buf, a->pc, &opcode)) { return -1; } } else { opcode = armass_assemble (buf, a->pc, is_thumb); if (a->bits != 32 && a->bits != 16) { eprintf ("Error: ARM assembler only supports 16 or 32 bits\n"); return -1; } } if (opcode == UT32_MAX) { return -1; } if (is_thumb) { const int o = opcode >> 16; opsize = o > 0? 4: 2; //(o&0x80 && ((o&0xe0)==0xe0))? 4: 2; if (opsize == 4) { if (a->big_endian) { r_write_le32 (op->buf, opcode); } else { r_write_be32 (op->buf, opcode); } } else if (opsize == 2) { r_write_be16 (op->buf, opcode & UT16_MAX); } } else {
static int rap__system(RIO *io, RIODesc *fd, const char *command) { int ret, reslen = 0, cmdlen = 0; RSocket *s = RIORAP_FD (fd); unsigned int i, j = 0; char *ptr, *res, *str; ut8 buf[RMT_MAX]; buf[0] = RMT_CMD; i = strlen (command) + 1; if (i > RMT_MAX - 5) { eprintf ("Command too long\n"); return -1; } r_write_be32 (buf + 1, i); memcpy (buf + 5, command, i); r_socket_write (s, buf, i+5); r_socket_flush (s); /* read reverse cmds */ for (;;) { ret = r_socket_read_block (s, buf, 1); if (ret != 1) { return -1; } /* system back in the middle */ /* TODO: all pkt handlers should check for reverse queries */ if (buf[0] != RMT_CMD) { break; } // run io->cmdstr // return back the string buf[0] |= RMT_REPLY; memset (buf + 1, 0, 4); ret = r_socket_read_block (s, buf + 1, 4); cmdlen = r_read_at_be32 (buf, 1); if (cmdlen + 1 == 0) // check overflow cmdlen = 0; str = calloc (1, cmdlen + 1); ret = r_socket_read_block (s, (ut8*)str, cmdlen); eprintf ("RUN %d CMD(%s)\n", ret, str); if (str && *str) { res = io->cb_core_cmdstr (io->user, str); } else { res = strdup (""); } eprintf ("[%s]=>(%s)\n", str, res); reslen = strlen (res); free (str); r_write_be32 (buf + 1, reslen); memcpy (buf + 5, res, reslen); free (res); r_socket_write (s, buf, reslen + 5); r_socket_flush (s); } // read ret = r_socket_read_block (s, buf + 1, 4); if (ret != 4) { return -1; } if (buf[0] != (RMT_CMD | RMT_REPLY)) { eprintf ("Unexpected rap cmd reply\n"); return -1; } i = r_read_at_be32 (buf, 1); ret = 0; if (i > ST32_MAX) { eprintf ("Invalid length\n"); return -1; } ptr = (char *)calloc (1, i + 1); if (ptr) { int ir, tr = 0; do { ir = r_socket_read_block (s, (ut8*)ptr + tr, i - tr); if (ir < 1) break; tr += ir; } while (tr < i); // TODO: use io->cb_printf() with support for \x00 ptr[i] = 0; if (io->cb_printf) { io->cb_printf ("%s", ptr); j = i; } else { j = write (1, ptr, i); } free (ptr); } #if DEAD_CODE /* Clean */ if (ret > 0) { ret -= r_socket_read (s, (ut8*)buf, RMT_MAX); } #endif return i - j; }
R_API bool r_reg_set_value(RReg *reg, RRegItem *item, ut64 value) { int fits_in_arena; ut8 bytes[12]; ut8 *src = bytes; if (!item) { eprintf ("r_reg_set_value: item is NULL\n"); return false; } switch (item->size) { case 80: case 96: // long floating value r_reg_set_longdouble (reg, item, (long double)value); break; case 64: if (reg->big_endian) { r_write_be64 (src, value); } else { r_write_le64 (src, value); } break; case 32: if (reg->big_endian) { r_write_be32 (src, value); } else { r_write_le32 (src, value); } break; case 16: if (reg->big_endian) { r_write_be16 (src, value); } else { r_write_le16 (src, value); } break; case 8: r_write_ble8 (src, (ut8)(value & UT8_MAX)); break; case 1: if (value) { ut8 *buf = reg->regset[item->arena].arena->bytes + (item->offset / 8); int bit = (item->offset % 8); ut8 mask = (1 << bit); buf[0] = (buf[0] & (0xff ^ mask)) | mask; } else { int idx = item->offset / 8; RRegArena *arena = reg->regset[item->arena].arena; if (idx + item->size > arena->size) { eprintf ("RRegSetOverflow %d vs %d\n", idx + item->size, arena->size); return false; } ut8 *buf = arena->bytes + idx; int bit = item->offset % 8; ut8 mask = 0xff ^ (1 << bit); buf[0] = (buf[0] & mask) | 0; } return true; default: eprintf ("r_reg_set_value: Bit size %d not supported\n", item->size); return false; } fits_in_arena = (reg->regset[item->arena].arena->size - BITS2BYTES (item->offset) - BITS2BYTES (item->size)) >= 0; if (src && fits_in_arena) { r_mem_copybits (reg->regset[item->arena].arena->bytes + BITS2BYTES (item->offset), src, item->size); return true; } eprintf ("r_reg_set_value: Cannot set %s to 0x%" PFMT64x "\n", item->name, value); return false; }
R_API bool r_socket_rap_server_continue (RSocketRapServer *rap_s) { int i, whence, ret = true; ut64 offset; char *ptr = NULL; if (!rap_s || !rap_s->fd) return false; if (!r_socket_is_connected (rap_s->fd)) return false; r_socket_read_block (rap_s->fd, rap_s->buf, 1); ret = rap_s->buf[0]; switch (ret) { case RAP_RMT_OPEN: r_socket_read_block (rap_s->fd, &rap_s->buf[1], 2); r_socket_read_block (rap_s->fd, &rap_s->buf[3], (int)rap_s->buf[2]); rap_s->open (rap_s->user, (const char *)&rap_s->buf[3], (int)rap_s->buf[1], 0); rap_s->buf[0] = RAP_RMT_OPEN | RAP_RMT_REPLY; r_socket_write (rap_s->fd, rap_s->buf, 5); r_socket_flush (rap_s->fd); break; case RAP_RMT_READ: r_socket_read_block (rap_s->fd, &rap_s->buf[1], 4); i = r_read_be32 (&rap_s->buf[1]); if (i > RAP_RMT_MAX || i < 0) i = RAP_RMT_MAX; rap_s->read (rap_s->user, &rap_s->buf[5], i); rap_s->buf[0] = RAP_RMT_READ | RAP_RMT_REPLY; r_socket_write (rap_s->fd, rap_s->buf, i + 5); r_socket_flush (rap_s->fd); break; case RAP_RMT_WRITE: r_socket_read_block (rap_s->fd, rap_s->buf + 1, 4); i = r_read_be32 (rap_s->buf + 1); if (i > RAP_RMT_MAX || i < 0) { i = RAP_RMT_MAX; } r_socket_read_block (rap_s->fd, rap_s->buf + 5, i); int ret = rap_s->write (rap_s->user, rap_s->buf + 5, i); r_write_be32 (rap_s->buf + 1, ret); rap_s->buf[0] = RAP_RMT_WRITE | RAP_RMT_REPLY; r_socket_write (rap_s->fd, rap_s->buf, 5); r_socket_flush (rap_s->fd); break; case RAP_RMT_SEEK: r_socket_read_block (rap_s->fd, &rap_s->buf[1], 9); whence = rap_s->buf[1]; offset = r_read_be64 (rap_s->buf + 2); offset = rap_s->seek (rap_s->user, offset, whence); /* prepare reply */ rap_s->buf[0] = RAP_RMT_SEEK | RAP_RMT_REPLY; r_write_be64 (rap_s->buf + 1, offset); r_socket_write (rap_s->fd, rap_s->buf, 9); r_socket_flush (rap_s->fd); break; case RAP_RMT_CMD: r_socket_read_block (rap_s->fd, &rap_s->buf[1], 4); i = r_read_be32 (&rap_s->buf[1]); r_socket_read_block (rap_s->fd, &rap_s->buf[5], i); ptr = rap_s->cmd (rap_s->user, (const char *)&rap_s->buf[5]); i = (ptr)? strlen (ptr) + 1: 0; r_write_be32 (&rap_s->buf[1], i); rap_s->buf[0] = RAP_RMT_CMD | RAP_RMT_REPLY; r_socket_write (rap_s->fd, rap_s->buf, 5); if (i) r_socket_write (rap_s->fd, ptr, i); r_socket_flush (rap_s->fd); free (ptr); ptr = NULL; break; case RAP_RMT_CLOSE: r_socket_read_block (rap_s->fd, &rap_s->buf[1], 4); i = r_read_be32 (&rap_s->buf[1]); rap_s->close (rap_s->user, i); rap_s->buf[0] = RAP_RMT_CLOSE | RAP_RMT_REPLY; r_socket_write (rap_s->fd, rap_s->buf, 5); r_socket_flush (rap_s->fd); break; default: eprintf ("unknown command 0x%02x\n", \ (unsigned int)(unsigned char)rap_s->buf[0]); r_socket_close (rap_s->fd); ret = false; break; } return ret; }