mirror of
https://github.com/Rockbox/rockbox.git
synced 2025-10-13 18:17:39 -04:00
hwpatcher: add framework for CRC computation
Change-Id: Ib78f0fe58db5cec86f043d3e9e1ca14e69297ba0 Reviewed-on: http://gerrit.rockbox.org/911 Reviewed-by: Marcin Bukat <marcin.bukat@gmail.com>
This commit is contained in:
parent
bfbec3a3a7
commit
69df56504e
2 changed files with 106 additions and 11 deletions
|
@ -47,6 +47,8 @@
|
|||
#include "misc.h"
|
||||
#include "md5.h"
|
||||
|
||||
#define ARRAYLEN(arr) (sizeof(arr) / sizeof(arr[0]))
|
||||
|
||||
lua_State *g_lua;
|
||||
bool g_exit = false;
|
||||
|
||||
|
@ -59,6 +61,18 @@ enum fw_type_t
|
|||
FW_UNK, FW_ELF, FW_SB1, FW_SB2, FW_BIN, FW_EDOC
|
||||
};
|
||||
|
||||
enum crc_type_t
|
||||
{
|
||||
CRC_RKW
|
||||
};
|
||||
|
||||
struct crc_type_desc_t
|
||||
{
|
||||
enum crc_type_t type;
|
||||
const char *lua_name;
|
||||
unsigned (*fn)(uint8_t *buf, size_t len);
|
||||
};
|
||||
|
||||
struct bin_file_t
|
||||
{
|
||||
size_t size;
|
||||
|
@ -849,6 +863,66 @@ int my_lua_section_info(lua_State *state)
|
|||
return 1;
|
||||
}
|
||||
|
||||
unsigned crc_rkw(uint8_t *buf, size_t len)
|
||||
{
|
||||
/* polynomial 0x04c10db7 */
|
||||
static const uint32_t crc32_lookup[16] =
|
||||
{ /* lookup table for 4 bits at a time is affordable */
|
||||
0x00000000, 0x04C10DB7, 0x09821B6E, 0x0D4316D9,
|
||||
0x130436DC, 0x17C53B6B, 0x1A862DB2, 0x1E472005,
|
||||
0x26086DB8, 0x22C9600F, 0x2F8A76D6, 0x2B4B7B61,
|
||||
0x350C5B64, 0x31CD56D3, 0x3C8E400A, 0x384F4DBD
|
||||
};
|
||||
|
||||
uint32_t crc32 = 0;
|
||||
unsigned char byte;
|
||||
uint32_t t;
|
||||
|
||||
while (len--)
|
||||
{
|
||||
byte = *buf++; /* get one byte of data */
|
||||
|
||||
/* upper nibble of our data */
|
||||
t = crc32 >> 28; /* extract the 4 most significant bits */
|
||||
t ^= byte >> 4; /* XOR in 4 bits of data into the extracted bits */
|
||||
crc32 <<= 4; /* shift the CRC register left 4 bits */
|
||||
crc32 ^= crc32_lookup[t]; /* do the table lookup and XOR the result */
|
||||
|
||||
/* lower nibble of our data */
|
||||
t = crc32 >> 28; /* extract the 4 most significant bits */
|
||||
t ^= byte & 0x0F; /* XOR in 4 bits of data into the extracted bits */
|
||||
crc32 <<= 4; /* shift the CRC register left 4 bits */
|
||||
crc32 ^= crc32_lookup[t]; /* do the table lookup and XOR the result */
|
||||
}
|
||||
|
||||
return crc32;
|
||||
}
|
||||
|
||||
struct crc_type_desc_t crc_types[] =
|
||||
{
|
||||
{CRC_RKW, "RKW", crc_rkw}
|
||||
};
|
||||
|
||||
int my_lua_crc_buf(lua_State *state)
|
||||
{
|
||||
int n = lua_gettop(state);
|
||||
if(n != 2)
|
||||
return luaL_error(state, "crc_buf takes two arguments: a crc type and a buffer");
|
||||
unsigned type = lua_tounsigned(state, 1);
|
||||
size_t len;
|
||||
void *buf = my_lua_get_buffer(state, 2, &len);
|
||||
for(int i = 0; i < ARRAYLEN(crc_types); i++)
|
||||
if(crc_types[i].type == type)
|
||||
{
|
||||
lua_pushunsigned(state, crc_types[i].fn(buf, len));
|
||||
free(buf);
|
||||
return 1;
|
||||
}
|
||||
free(buf);
|
||||
luaL_error(state, "crc_buf: unknown crc type");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* compute MD5 sum of a buffer */
|
||||
static bool compute_md5sum_buf(void *buf, size_t sz, uint8_t file_md5sum[16])
|
||||
{
|
||||
|
@ -945,6 +1019,17 @@ static bool init_lua_hwp(void)
|
|||
lua_pushcfunction(g_lua, my_lua_md5sum);
|
||||
lua_setfield(g_lua, -2, "md5sum");
|
||||
|
||||
lua_newtable(g_lua);
|
||||
for(int i = 0; i < ARRAYLEN(crc_types); i++)
|
||||
{
|
||||
lua_pushunsigned(g_lua, crc_types[i].type);
|
||||
lua_setfield(g_lua, -2, crc_types[i].lua_name);
|
||||
}
|
||||
lua_setfield(g_lua, -2, "CRC");
|
||||
|
||||
lua_pushcfunction(g_lua, my_lua_crc_buf);
|
||||
lua_setfield(g_lua, -2, "crc_buf");
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -13,11 +13,16 @@ In the hwp table:
|
|||
- load_sb_file(filename) Load a firmware as SB
|
||||
- load_sb1_file(filename) Load a firmware as SB1
|
||||
- load_bin_file(filename) Load a firmware as binary
|
||||
- save_file(obj, filename) Save a firmware to a file
|
||||
- read(obj, addr, len) Read data from a firmware
|
||||
- write(obj, addr, data) Write data to a firmware
|
||||
- section_info(obj, sec) Return information about a section in a table (or nil)
|
||||
- save_file(fw, filename) Save a firmware to a file
|
||||
- read(fw, addr, len) Read data from a firmware
|
||||
- write(fw, addr, data) Write data to a firmware
|
||||
- section_info(fw, sec) Return information about a section in a table (or nil)
|
||||
- md5sum(filename) Compute the MD5 sum of a file
|
||||
- crc_buf(crc_type, buf) Compute the CRC of a byte buffer and return a byte buffer
|
||||
- crc(crc_type, fw, addr, len) Compute the CRC of a firmware part
|
||||
|
||||
The list of CRCs available is available the hwp.CRC table:
|
||||
- RKW
|
||||
|
||||
Data read/written from/to a firmware must must be an array of bytes.
|
||||
The address must be a table of the following fields:
|
||||
|
@ -27,7 +32,7 @@ Data section information is a table with the following fields:
|
|||
- address: first address if the section
|
||||
- size: size of the section
|
||||
We provide the following functions to help dealing with addresses:
|
||||
- make_addr
|
||||
- make_addr(addr, section) Build a firmware address from a raw address and a section
|
||||
|
||||
]]--
|
||||
|
||||
|
@ -105,3 +110,8 @@ function hwp.md5str(md5)
|
|||
end
|
||||
return s
|
||||
end
|
||||
|
||||
-- compute the CRC of a firmware part
|
||||
function hwp.crc(crc_type, fw, addr, len)
|
||||
return hwp.crc_buf(crc_type, hwp.read(fw, addr, len))
|
||||
end
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue