Scripting: add fget & fset commands

This commit is contained in:
d0k3 2018-04-11 01:28:34 +02:00
parent b656f0d90b
commit 4f8dfc1eaf
2 changed files with 87 additions and 6 deletions

View File

@ -95,6 +95,8 @@ typedef enum {
CMD_ID_UMOUNT, CMD_ID_UMOUNT,
CMD_ID_FIND, CMD_ID_FIND,
CMD_ID_FINDNOT, CMD_ID_FINDNOT,
CMD_ID_FGET,
CMD_ID_FSET,
CMD_ID_SHA, CMD_ID_SHA,
CMD_ID_SHAGET, CMD_ID_SHAGET,
CMD_ID_FIXCMAC, CMD_ID_FIXCMAC,
@ -157,6 +159,8 @@ Gm9ScriptCmd cmd_list[] = {
{ CMD_ID_UMOUNT , "imgumount",0, 0 }, { CMD_ID_UMOUNT , "imgumount",0, 0 },
{ CMD_ID_FIND , "find" , 2, _FLG('f') }, { CMD_ID_FIND , "find" , 2, _FLG('f') },
{ CMD_ID_FINDNOT , "findnot" , 2, 0 }, { CMD_ID_FINDNOT , "findnot" , 2, 0 },
{ CMD_ID_FGET , "fget" , 2, _FLG('e') },
{ CMD_ID_FSET , "fset" , 2, _FLG('e') },
{ CMD_ID_SHA , "sha" , 2, 0 }, { CMD_ID_SHA , "sha" , 2, 0 },
{ CMD_ID_SHAGET , "shaget" , 2, 0 }, { CMD_ID_SHAGET , "shaget" , 2, 0 },
{ CMD_ID_FIXCMAC , "fixcmac" , 1, 0 }, { CMD_ID_FIXCMAC , "fixcmac" , 1, 0 },
@ -202,23 +206,30 @@ static inline bool isntrboot(void) {
return (bootMediaStatus[3] == 2) && !bootMediaStatus[1] && !bootPartitionsStatus[0] && !bootPartitionsStatus[1]; return (bootMediaStatus[3] == 2) && !bootMediaStatus[1] && !bootPartitionsStatus[0] && !bootPartitionsStatus[1];
} }
static inline bool strntohex(const char* str, u8* hex, u32 len) { static inline u32 strntohex(const char* str, u8* hex, u32 len) {
if (!len) { if (!len) {
len = strlen(str); len = strlen(str);
if (len%1) return false; if (len%1) return 0;
else len >>= 1; else len >>= 1;
} else if (len*2 != strnlen(str, (len*2)+1)) { } else if (len*2 != strnlen(str, (len*2)+1)) {
return false; return 0;
} }
for (u32 i = 0; i < len; i++) { for (u32 i = 0; i < len; i++) {
char bytestr[2+1] = { 0 }; char bytestr[2+1] = { 0 };
u32 bytehex; u32 bytehex;
memcpy(bytestr, str + (i*2), 2); memcpy(bytestr, str + (i*2), 2);
if (sscanf(bytestr, "%02lx", &bytehex) != 1) if (sscanf(bytestr, "%02lx", &bytehex) != 1)
return false; return 0;
hex[i] = (u8) bytehex; hex[i] = (u8) bytehex;
} }
return true; return len;
}
static inline u32 hexntostr(const u8* hex, char* str, u32 len) {
if (!len) return 0;
for (u32 i = 0; i < len; i++)
snprintf(str + (i<<1), 2 + 1, "%02lx", (u32) hex[i]);
return len;
} }
static inline u32 line_len(const char* text, u32 len, u32 ww, const char* line) { static inline u32 line_len(const char* text, u32 len, u32 ww, const char* line) {
@ -507,6 +518,7 @@ u32 get_flag(char* str, u32 len, char* err_str) {
else if (strncmp(str, "--all", len) == 0) flag_char = 'a'; else if (strncmp(str, "--all", len) == 0) flag_char = 'a';
else if (strncmp(str, "--before", len) == 0) flag_char = 'b'; else if (strncmp(str, "--before", len) == 0) flag_char = 'b';
else if (strncmp(str, "--include_dirs", len) == 0) flag_char = 'd'; else if (strncmp(str, "--include_dirs", len) == 0) flag_char = 'd';
else if (strncmp(str, "--flip_endian", len) == 0) flag_char = 'e';
else if (strncmp(str, "--first", len) == 0) flag_char = 'f'; else if (strncmp(str, "--first", len) == 0) flag_char = 'f';
else if (strncmp(str, "--hash", len) == 0) flag_char = 'h'; else if (strncmp(str, "--hash", len) == 0) flag_char = 'h';
else if (strncmp(str, "--skip", len) == 0) flag_char = 'k'; else if (strncmp(str, "--skip", len) == 0) flag_char = 'k';
@ -775,7 +787,7 @@ bool run_cmd(cmd_id id, u32 flags, char** argv, char* err_str) {
// process arg0 @string // process arg0 @string
u64 at_org = 0; u64 at_org = 0;
u64 sz_org = 0; u64 sz_org = 0;
if ((id == CMD_ID_SHA) || (id == CMD_ID_SHAGET) || (id == CMD_ID_INJECT) || (id == CMD_ID_FILL)) { if ((id == CMD_ID_FGET) || (id == CMD_ID_FSET) || (id == CMD_ID_SHA) || (id == CMD_ID_SHAGET) || (id == CMD_ID_INJECT) || (id == CMD_ID_FILL)) {
char* atstr_org = strrchr(argv[0], '@'); char* atstr_org = strrchr(argv[0], '@');
if (atstr_org) { if (atstr_org) {
*(atstr_org++) = '\0'; *(atstr_org++) = '\0';
@ -1131,6 +1143,57 @@ bool run_cmd(cmd_id id, u32 flags, char** argv, char* err_str) {
if (err_str) snprintf(err_str, _ERR_STR_LEN, "var fail"); if (err_str) snprintf(err_str, _ERR_STR_LEN, "var fail");
} }
} }
else if (id == CMD_ID_FGET) {
u8 data[(_VAR_CNT_LEN-1)/2];
if (sz_org == 0) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "no size given");
} else if (sz_org > (_VAR_CNT_LEN-1)/2) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "size too big");
} else if (FileGetData(argv[0], data, sz_org, at_org) != sz_org) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "read fail");
} else {
char* var = set_var(argv[1], "");
if (!var) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "var fail");
} else {
if (flags & _FLG('e')) { // flip data
for (u32 i = 0; i < (sz_org >> 1); i++) {
u8 tmp = data[i];
data[i] = data[sz_org - 1 - i];
data[sz_org - 1 - i] = tmp;
}
}
ret = hexntostr(data, var, sz_org);
if (!ret && err_str) snprintf(err_str, _ERR_STR_LEN, "conversion fail");
}
}
}
else if (id == CMD_ID_FSET) {
u8 data[(_ARG_MAX_LEN-1)/2];
u32 len = strntohex(argv[1], data, 0);
if (!sz_org) sz_org = len;
if ((sz_org <= len) && (flags & _FLG('e'))) { // flip data
for (u32 i = 0; i < (sz_org >> 1); i++) {
u8 tmp = data[i];
data[i] = data[sz_org - 1 - i];
data[sz_org - 1 - i] = tmp;
}
}
if (!len) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "invalid data");
} else if (sz_org > len) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "size too big");
} else if (!FileSetData(argv[0], data, sz_org, at_org, false)) {
ret = false;
if (err_str) snprintf(err_str, _ERR_STR_LEN, "write fail");
}
}
else if (id == CMD_ID_SHA) { else if (id == CMD_ID_SHA) {
u8 sha256_fil[0x20]; u8 sha256_fil[0x20];
u8 sha256_cmp[0x20]; u8 sha256_cmp[0x20];

View File

@ -221,6 +221,24 @@ fdummy $[DUMMY] 400
fill $[DUMMY]@100:100 FF fill $[DUMMY]@100:100 FF
fill $[DUMMY]@300 80 fill $[DUMMY]@300 80
# 'fset' COMMAND
# This command sets a portition of a file with the specified data in hex
# The syntax is: fset destination@x hexdata
# x: destination offset (in hex)
# If x is not given, data is inserted at the beginning of the file
# -e / --flip_endian flips the order of the bytes
fset $[DUMMY]@100 48454c4c4f # 'HELLO'
# 'fget' COMMAND
# This command reads data from a file and stores it in a var
# The syntax is: fset origin@x:y var
# x: origin offset (in hex)
# y: origin size, starting at x (in hex)
# Both x and y have to be set(!)
# -e / --flip_endian flips the order of the bytes
fget -e $[DUMMY]@100:5 OLLEH
echo "This is 'HELLO', in hex and reverse:\n$[OLLEH]"
# 'fixcmac' COMMAND # 'fixcmac' COMMAND
# Use this to fix the CMACs for a file or a whole folder (recursively) # Use this to fix the CMACs for a file or a whole folder (recursively)
# This will count as success if a file does not contain a CMAC # This will count as success if a file does not contain a CMAC