String/Hex-Search 1/9: Add hexadecimal number helpers, doxygen and type annotations.
Part 1/9. Likely won't build in between parts. Co-authored-by: wargio <deroad@kumo.xn--q9jyb4c>
This commit is contained in:
parent
9f1ac64d87
commit
6d10861ace
6 changed files with 375 additions and 41 deletions
|
|
@ -32,13 +32,13 @@ static bool rz_debug_dmp_init(RzDebug *dbg, void **user) {
|
|||
DmpCtx *ctx = dbg->plugin_data;
|
||||
ctx->bf = core->bin->cur;
|
||||
|
||||
int ret = rz_hex_str2bin(core->bin->cur->o->regstate, NULL);
|
||||
ctx->context = malloc(ret);
|
||||
ctx->context = malloc((strlen(core->bin->cur->o->regstate) / 2) + 1);
|
||||
if (!ctx->context) {
|
||||
return false;
|
||||
}
|
||||
ctx->context_sz = ret;
|
||||
rz_hex_str2bin(core->bin->cur->o->regstate, ctx->context);
|
||||
int size = rz_hex_str2bin(core->bin->cur->o->regstate, ctx->context);
|
||||
size *= size < 0 ? -1 : 1;
|
||||
ctx->context_sz = size;
|
||||
|
||||
ut32 MachineImageType = 0; // Windows Architecture (IMAGE_FILE_MACHINE)
|
||||
ut32 MinorVersion = 0; // Windows Version
|
||||
|
|
|
|||
|
|
@ -8,12 +8,15 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
RZ_API int rz_hex_pair2bin(const char *arg);
|
||||
RZ_API int rz_hex_str2binmask(const char *in, ut8 *out, ut8 *mask);
|
||||
RZ_API int rz_hex_str2bin(const char *in, ut8 *out);
|
||||
RZ_API int rz_hex_str2bin_msb(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out);
|
||||
RZ_API size_t rz_hex_str2bin_mask(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out, RZ_NULLABLE RZ_OUT ut8 *mask, bool lsb_extend);
|
||||
RZ_API int rz_hex_str2bin(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out);
|
||||
RZ_API int rz_hex_bin2str(const ut8 *in, int len, char *out);
|
||||
RZ_API void rz_hex_ut2st_str(const ut32 in, RZ_INOUT char *out, const int len);
|
||||
RZ_API char *rz_hex_bin2strdup(const ut8 *in, int len);
|
||||
RZ_API bool rz_hex_to_byte(ut8 *val, ut8 c);
|
||||
RZ_API ut8 rz_hex_digit_to_byte(const char c);
|
||||
RZ_API ut16 rz_hex_digit_pair_to_byte(const char *c);
|
||||
RZ_API int rz_hex_str_is_valid(const char *s, bool allow_prefix);
|
||||
RZ_API st64 rz_hex_bin_truncate(ut64 in, int n);
|
||||
RZ_API char *rz_hex_from_c(const char *code);
|
||||
|
|
|
|||
|
|
@ -303,12 +303,13 @@ static int rasm_disasm(RzAsmState *as, ut64 addr, const char *buf, int len, int
|
|||
clen = len; // XXX
|
||||
data = (ut8 *)buf;
|
||||
} else {
|
||||
clen = rz_hex_str2bin(buf, NULL);
|
||||
if ((int)clen < 1 || !(data = malloc(clen))) {
|
||||
if (!(data = malloc((strlen(buf) / 2) + 1))) {
|
||||
ret = 0;
|
||||
goto beach;
|
||||
}
|
||||
rz_hex_str2bin(buf, data);
|
||||
clen = rz_hex_str2bin(buf, data);
|
||||
// Odd number of nibbles case.
|
||||
clen *= clen < 0 ? -1 : 1;
|
||||
len = clen;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -189,7 +189,7 @@ RZ_API RzSearchKeyword *rz_search_keyword_new_hexmask(const char *kwstr, const c
|
|||
kw = malloc(len + 4);
|
||||
bm = malloc(len + 4);
|
||||
if (kw != NULL && bm != NULL) {
|
||||
len = rz_hex_str2binmask(kwstr, (ut8 *)kw, (ut8 *)bm);
|
||||
len = rz_hex_str2bin_mask(kwstr, (ut8 *)kw, (ut8 *)bm, true);
|
||||
if (len < 0) {
|
||||
len = -len - 1;
|
||||
}
|
||||
|
|
|
|||
251
librz/util/hex.c
251
librz/util/hex.c
|
|
@ -6,6 +6,78 @@
|
|||
#include <stdio.h>
|
||||
#include <ctype.h>
|
||||
|
||||
/**
|
||||
* \brief Returns the byte value for a hexadecimal nibble.
|
||||
*
|
||||
* \param The hexadecimal nibble to get the raw byte value for.
|
||||
*
|
||||
* \param The byte value of the nibble.
|
||||
* Or UT8_MAX if the nibble is no hexadecimal character.
|
||||
*
|
||||
* \return The byte value of the hex digit.
|
||||
* Or UT8_MAX if the character was not a hexadecimal character.
|
||||
*
|
||||
* Example:
|
||||
* ```c
|
||||
* assert(rz_hex_nibble_to_byte('1') == 1);
|
||||
* assert(rz_hex_nibble_to_byte('A') == 10);
|
||||
* assert(rz_hex_nibble_to_byte('b') == 11);
|
||||
* assert(rz_hex_nibble_to_byte('S') == UT8_MAX);
|
||||
* assert(rz_hex_nibble_to_byte('\0') == UT8_MAX);
|
||||
* ```
|
||||
*/
|
||||
RZ_API ut8 rz_hex_digit_to_byte(const char c) {
|
||||
if (!isxdigit(c)) {
|
||||
return UT8_MAX;
|
||||
}
|
||||
// Check an ASCII table for this.
|
||||
// Bit 6 indicates if it is A-F or a-f.
|
||||
ut8 byte = (c & 0x40) ? 9 : 0;
|
||||
// Bit 3-0 are the same bits for upper and lower case A-F.
|
||||
// And 'a' & 0xf == 1, so 9 + 1 == 10.
|
||||
byte += (c & 0xf);
|
||||
return byte;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Returns the byte value for a hexadecimal nibble pair.
|
||||
* It stops parsing at the first non hex digit.
|
||||
*
|
||||
* \param The string to parse as hex digit pair.
|
||||
*
|
||||
* \return The byte value of the nibble pair.
|
||||
* Or UT16_MAX if the first nibble is no hexadecimal character.
|
||||
*
|
||||
* Example:
|
||||
* ```c
|
||||
* assert(rz_hex_nibble_pair_to_byte("1") == 1);
|
||||
* assert(rz_hex_nibble_pair_to_byte("11") == 17);
|
||||
* assert(rz_hex_nibble_pair_to_byte("fe") == 254);
|
||||
*
|
||||
* assert(rz_hex_nibble_pair_to_byte("ff01") == 255);
|
||||
* assert(rz_hex_nibble_pair_to_byte("F@") == 15);
|
||||
* assert(rz_hex_nibble_pair_to_byte("p1") == UT16_MAX);
|
||||
* assert(rz_hex_nibble_pair_to_byte("") == UT16_MAX);
|
||||
* ```
|
||||
*/
|
||||
RZ_API ut16 rz_hex_digit_pair_to_byte(const char *npair) {
|
||||
if (!isxdigit(npair[0])) {
|
||||
return UT16_MAX;
|
||||
}
|
||||
ut8 n0 = rz_hex_digit_to_byte(npair[0]);
|
||||
if (n0 == UT8_MAX) {
|
||||
return UT16_MAX;
|
||||
}
|
||||
if (!isxdigit(npair[1])) {
|
||||
return n0;
|
||||
}
|
||||
ut8 n1 = rz_hex_digit_to_byte(npair[1]);
|
||||
if (n1 == UT8_MAX) {
|
||||
return UT16_MAX;
|
||||
}
|
||||
return (n0 << 4 | n1);
|
||||
}
|
||||
|
||||
/* int c = 0; ret = hex_to_byte(&c, 'c'); */
|
||||
RZ_API bool rz_hex_to_byte(ut8 *val, ut8 c) {
|
||||
if (IS_DIGIT(c)) {
|
||||
|
|
@ -437,16 +509,76 @@ RZ_API char *rz_hex_bin2strdup(const ut8 *in, int len) {
|
|||
}
|
||||
|
||||
/**
|
||||
* \brief Convert an input string \p in into the binary form in \p out
|
||||
* \brief Convert an input string \p in into the binary form in \p out.
|
||||
* For odd number of nibbles, the MSB side is extended with a 0 nibble.
|
||||
*
|
||||
* If \p in contains non-hexadecimal digits, the result is undefined.
|
||||
*
|
||||
* Convert an input string in the hexadecimal form (e.g. "41424344") into the
|
||||
* raw binary form (e.g. "ABCD")
|
||||
* raw binary form (e.g. "\x41\x42\x43\x44" or "ABCD").
|
||||
*
|
||||
* Note: If an odd number of nibbles is given, the buffer is extended on the side of the MSB with a 0 nibble.
|
||||
* So, "444" becomes "\x04\x44".
|
||||
* Use rz_hex_str2bin() if you need to extend it on the LSB side.
|
||||
*
|
||||
* \param in Input string in hexadecimal form. An optional "0x" prefix may be present.
|
||||
* \param out Output buffer having at least strlen(in) / 2 bytes available
|
||||
* \return number of bytes written into \p out
|
||||
* \return Number of bytes written into \p out. The number is negative if an odd number of nibbles was parsed.
|
||||
*/
|
||||
RZ_API int rz_hex_str2bin(const char *in, ut8 *out) {
|
||||
RZ_API int rz_hex_str2bin_msb(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out) {
|
||||
rz_return_val_if_fail(in && out, 0);
|
||||
|
||||
if (!in[0]) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
size_t i = 0, j = 0;
|
||||
if (in[0] == '0' && in[1] == 'x') {
|
||||
i += 2;
|
||||
}
|
||||
|
||||
ut16 byte = 0;
|
||||
size_t nibbles = rz_str_ansi_len(in + i);
|
||||
|
||||
bool odd_nibble = (nibbles % 2) == 1;
|
||||
if (odd_nibble) {
|
||||
byte = rz_hex_digit_to_byte(in[i]);
|
||||
if (byte >= UT8_MAX) {
|
||||
return 0;
|
||||
}
|
||||
out[j] = byte;
|
||||
i++;
|
||||
j++;
|
||||
}
|
||||
|
||||
for (byte = rz_hex_digit_pair_to_byte(in + i); i < strlen(in) && byte <= UT8_MAX; j++, i += 2, byte = rz_hex_digit_pair_to_byte(in + i)) {
|
||||
out[j] = byte;
|
||||
}
|
||||
|
||||
return odd_nibble ? -j : j;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Convert an input string \p in into the binary form in \p out
|
||||
* For odd number of nibbles, the LSB side is extended with a 0 nibble.
|
||||
*
|
||||
* If \p in contains non-hexadecimal digits, the result is undefined.
|
||||
*
|
||||
* Convert an input string in the hexadecimal form (e.g. "41424344") into the
|
||||
* raw binary form (e.g. "\x41\x42\x43\x44" or "ABCD").
|
||||
*
|
||||
* Note: If an odd number of nibbles is given, the buffer is extended on the side of the LSB with a 0 nibble.
|
||||
* So, "444" becomes "\x44\x40".
|
||||
* Use rz_hex_str2bin_msb() if you need to extend it on the MSB side.
|
||||
*
|
||||
* \param in Input string in hexadecimal form. An optional "0x" prefix may be present.
|
||||
* \param out Output buffer having at least (strlen(in) / 2) + 1 bytes available.
|
||||
*
|
||||
* \return Number of bytes written into \p out. The number is negative if an odd number of nibbles was parsed.
|
||||
*/
|
||||
RZ_API int rz_hex_str2bin(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out) {
|
||||
rz_return_val_if_fail(in && out, 0);
|
||||
|
||||
long nibbles = 0;
|
||||
|
||||
while (in && *in) {
|
||||
|
|
@ -492,39 +624,98 @@ RZ_API int rz_hex_str2bin(const char *in, ut8 *out) {
|
|||
return nibbles / 2;
|
||||
}
|
||||
|
||||
RZ_API int rz_hex_str2binmask(const char *in, ut8 *out, ut8 *mask) {
|
||||
ut8 *ptr;
|
||||
int len, ilen = strlen(in) + 1;
|
||||
int has_nibble = 0;
|
||||
memcpy(out, in, ilen);
|
||||
for (ptr = out; *ptr; ptr++) {
|
||||
if (*ptr == '.') {
|
||||
*ptr = '0';
|
||||
/**
|
||||
* \brief Transforms an input hex string to its byte array eqivalent and a mask for it.
|
||||
* The hex string is allowed to contain '.' characters as wildcard.
|
||||
* Wildcards in \p in are set to '0' in the mask and \p out.
|
||||
* It stops at the first invalid character and returns.
|
||||
*
|
||||
* If \p in contains non-hexadecimal digits, the result is undefined.
|
||||
*
|
||||
* The input string may be prefixed with a "0x".
|
||||
*
|
||||
* \param in The hex string to parse and transform.
|
||||
* \param out The output buffer. It must be the same size as \p strlen(in) / 2.
|
||||
* \param mask The output buffer for the mask. It must be the same size as \p out.
|
||||
* Can be NULL, if no mask is required.
|
||||
* \param lsb_extend If set and \p in has an odd number hex digits,
|
||||
* it extends the byte buffer with a wildcard nibble at the LSB (right) side.
|
||||
* If unset and with an odd digit count, it extends on the MSB (left) side.
|
||||
*
|
||||
* \return The number of bytes written to \p out and \p mask. In case of failure it returns less then 0.
|
||||
* Note: In case of failure the content of \p out and \p mask are undefined.
|
||||
*
|
||||
* Example:
|
||||
* ```c
|
||||
* rz_hex_str2bin_mask("ffe4", out, mask, false);
|
||||
* assert_mem_eq(out, { 0xff, 0xe4 });
|
||||
* assert_mem_eq(mask, { 0xff, 0xff });
|
||||
*
|
||||
* rz_hex_str2bin_mask("ff.4", out, mask, false);
|
||||
* assert_mem_eq(out, { 0xff, 0x04 });
|
||||
* assert_mem_eq(mask, { 0xff, 0x0f });
|
||||
*
|
||||
* // Extend on MSB side
|
||||
* rz_hex_str2bin_mask("ffee4", out, mask, false);
|
||||
* assert_mem_eq(out, { 0x0f, 0xfe, 0xe4 });
|
||||
* assert_mem_eq(mask, { 0x0f, 0xff, 0xff });
|
||||
*
|
||||
* // Extend on LSB side
|
||||
* rz_hex_str2bin_mask("ee4", out, mask, true);
|
||||
* assert_mem_eq(out, { 0xee, 0x40 });
|
||||
* assert_mem_eq(mask, { 0xff, 0xf0 });
|
||||
* ```
|
||||
*/
|
||||
RZ_API size_t rz_hex_str2bin_mask(RZ_NONNULL const char *in, RZ_NONNULL RZ_OUT ut8 *out, RZ_NULLABLE RZ_OUT ut8 *mask, bool lsb_extend) {
|
||||
rz_return_val_if_fail(in && out, 0);
|
||||
|
||||
if (in[0] == '\0') {
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *in_cpy = strdup(in);
|
||||
for (size_t i = 0; in_cpy[i]; ++i) {
|
||||
if (in_cpy[i] == '.') {
|
||||
in_cpy[i] = '0';
|
||||
}
|
||||
}
|
||||
len = rz_hex_str2bin((char *)out, out);
|
||||
if (len < 0) {
|
||||
has_nibble = 1;
|
||||
len = -(len + 1);
|
||||
|
||||
int bytes_copied;
|
||||
if (lsb_extend) {
|
||||
bytes_copied = rz_hex_str2bin(in_cpy, out);
|
||||
} else {
|
||||
bytes_copied = rz_hex_str2bin_msb(in_cpy, out);
|
||||
}
|
||||
if (len != -1) {
|
||||
memcpy(mask, in, ilen);
|
||||
if (has_nibble) {
|
||||
memcpy(mask + ilen, "f0", 3);
|
||||
size_t ret = bytes_copied < 0 ? -bytes_copied : bytes_copied;
|
||||
|
||||
if (!mask) {
|
||||
free(in_cpy);
|
||||
return ret;
|
||||
}
|
||||
bool odd_nibbles = bytes_copied < 0;
|
||||
for (size_t i = 0; i < ret; ++i) {
|
||||
int low_offset = (i * 2);
|
||||
int high_offset = (i * 2) + 1;
|
||||
char low_digit;
|
||||
char high_digit;
|
||||
if (odd_nibbles && (i == 0 || i == (ret - 1))) {
|
||||
low_digit = (i == 0 && !lsb_extend) ? '.' : in[low_offset];
|
||||
high_digit = (i == ret - 1) && lsb_extend ? '.' : in[high_offset - 1];
|
||||
} else {
|
||||
low_digit = in[low_offset];
|
||||
high_digit = in[high_offset];
|
||||
}
|
||||
for (ptr = mask; *ptr; ptr++) {
|
||||
if (IS_HEXCHAR(*ptr)) {
|
||||
*ptr = 'f';
|
||||
} else if (*ptr == '.') {
|
||||
*ptr = '0';
|
||||
}
|
||||
|
||||
mask[i] = 0x00;
|
||||
if (low_digit != '.') {
|
||||
mask[i] |= 0xf0;
|
||||
}
|
||||
len = rz_hex_str2bin((char *)mask, mask);
|
||||
if (len < 0) {
|
||||
len++;
|
||||
if (high_digit != '.') {
|
||||
mask[i] |= 0x0f;
|
||||
}
|
||||
}
|
||||
return len;
|
||||
free(in_cpy);
|
||||
return ret;
|
||||
}
|
||||
|
||||
RZ_API st64 rz_hex_bin_truncate(ut64 in, int n) {
|
||||
|
|
|
|||
|
|
@ -157,24 +157,163 @@ bool test_rz_hex_no_code() {
|
|||
}
|
||||
|
||||
bool test_rz_str2bin(void) {
|
||||
ut8 *buf = malloc(100);
|
||||
ut8 *buf = calloc(100, sizeof(ut8));
|
||||
mu_assert_eq(rz_hex_str2bin("", buf), 0, "0 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"", 0, "'0' has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin("41424344", buf), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "ABCD has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin("0x41424344", buf), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "ABCD has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin("616263646566", buf), 6, "6 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"abcdef", 6, "abcdef has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin("61626364656", buf), -6, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"abcde\x60", 6, "abcdef has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin("61", buf), 1, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"a", 1, "a has been written");
|
||||
free(buf);
|
||||
mu_end;
|
||||
}
|
||||
|
||||
bool test_rz_str2bin_msb(void) {
|
||||
ut8 *buf = calloc(100, sizeof(ut8));
|
||||
mu_assert_eq(rz_hex_str2bin_msb("", buf), 0, "0 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"", 0, "'0' has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("61", buf), 1, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"a", 1, "a has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("41424344", buf), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "ABCD has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("0x41424344", buf), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "ABCD has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("616263646566", buf), 6, "6 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"abcdef", 6, "abcdef has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("61626364656", buf), -6, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x06\x16\x26\x36\x46\x56", 6, "abcdef has been written");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_msb("0x61626364656", buf), -6, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x06\x16\x26\x36\x46\x56", 6, "abcdef has been written");
|
||||
free(buf);
|
||||
mu_end;
|
||||
}
|
||||
|
||||
bool test_rz_str2bin_mask(void) {
|
||||
ut8 *buf = calloc(100, sizeof(ut8));
|
||||
ut8 *mask = calloc(100, sizeof(ut8));
|
||||
mu_assert_eq(rz_hex_str2bin_mask("", buf, mask, false), 0, "0 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"", 0, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"", 0, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("41424344", buf, mask, false), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff\xff\xff\xff", 4, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask(".14.", buf, mask, false), 2, "2 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x01\x40", 2, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\x0f\xf0", 2, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("0140", buf, mask, false), 2, "2 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x01\x40", 2, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff\xff", 2, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("0x41424344", buf, mask, false), 4, "4 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"ABCD", 4, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff\xff\xff\xff", 4, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("616263646566", buf, mask, false), 6, "6 bytes are written");
|
||||
mu_assert_memeq(buf, (ut8 *)"abcdef", 6, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff\xff\xff\xff\xff\xff", 6, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("61626364656", buf, mask, true), 6, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"abcde\x60", 6, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff\xff\xff\xff\xff\xf0", 6, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("61626364656", buf, mask, false), 6, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x06\x16\x26\x36\x46\x56", 6, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\x0f\xff\xff\xff\xff\xff", 6, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("6", buf, mask, true), 1, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x60", 1, "Mem mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xf0", 1, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("6", buf, mask, false), 1, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x06", 1, "Mem mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\x0f", 1, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("61", buf, mask, false), 1, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"a", 1, "Buffer mismatch");
|
||||
mu_assert_memeq(mask, (ut8 *)"\xff", 1, "Mask doesn't match");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("ffffffffff", buf, NULL, false), 5, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\xff\xff\xff\xff\xff", 5, "Buffer mismatch");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("fffffffff", buf, NULL, false), 5, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x0f\xff\xff\xff\xff", 5, "Buffer mismatch");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("0xffffffffff", buf, NULL, false), 5, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\xff\xff\xff\xff\xff", 5, "Buffer mismatch");
|
||||
|
||||
mu_assert_eq(rz_hex_str2bin_mask("0xfffffffff", buf, NULL, false), 5, "error should be returned");
|
||||
mu_assert_memeq(buf, (ut8 *)"\x0f\xff\xff\xff\xff", 5, "Buffer mismatch");
|
||||
free(mask);
|
||||
free(buf);
|
||||
mu_end;
|
||||
}
|
||||
|
||||
bool test_rz_hex_nibble_to_byte(void) {
|
||||
mu_assert_eq(rz_hex_digit_to_byte('/'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('0'), 0, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('1'), 1, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('8'), 8, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('9'), 9, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte(':'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('@'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('A'), 10, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('B'), 11, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('E'), 14, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('F'), 15, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('G'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('`'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('a'), 10, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('b'), 11, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('e'), 14, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('f'), 15, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('g'), UT8_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_to_byte('\0'), UT8_MAX, "Mismatch");
|
||||
mu_end;
|
||||
}
|
||||
|
||||
bool test_rz_hex_nibble_pair_to_byte(void) {
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("1"), 1, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("11"), 17, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("12"), 18, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("fe"), 254, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("ff01"), 255, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("ff"), 255, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("F@"), 15, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte("p1"), UT16_MAX, "Mismatch");
|
||||
mu_assert_eq(rz_hex_digit_pair_to_byte(""), UT16_MAX, "Mismatch");
|
||||
mu_end;
|
||||
}
|
||||
|
||||
bool all_tests() {
|
||||
mu_run_test(test_rz_hex_from_c);
|
||||
mu_run_test(test_rz_hex_from_py);
|
||||
mu_run_test(test_rz_hex_from_code);
|
||||
mu_run_test(test_rz_hex_no_code);
|
||||
mu_run_test(test_rz_hex_nibble_to_byte);
|
||||
mu_run_test(test_rz_hex_nibble_pair_to_byte);
|
||||
mu_run_test(test_rz_str2bin);
|
||||
mu_run_test(test_rz_str2bin_msb);
|
||||
mu_run_test(test_rz_str2bin_mask);
|
||||
return tests_passed != tests_run;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue