Skip to content

Instantly share code, notes, and snippets.

@f00b4r0
Created June 7, 2020 10:59
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save f00b4r0/8e97de73f3abe80ed67feded529f27ce to your computer and use it in GitHub Desktop.
Save f00b4r0/8e97de73f3abe80ed67feded529f27ce to your computer and use it in GitHub Desktop.
//
// dump_config.c
//
//
// Copyright (C) 2020 Thibaut VARÈNE - License: GPLv2 only
//
#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <stdlib.h>
#define BYTESWAP 1 // 1: enabled / 0: disabled
#define RB_MAGIC_HARD (('H') | ('a' << 8) | ('r' << 16) | ('d' << 24))
#define RB_MAGIC_SOFT (('S') | ('o' << 8) | ('f' << 16) | ('t' << 24))
#if BYTESWAP
static inline uint16_t bswap_16(uint16_t x)
{
return (x >> 8) | (x << 8);
}
static inline uint32_t bswap_32(uint32_t x)
{
return (bswap_16(x & 0xffff) << 16) | (bswap_16(x >> 16));
}
#else
static inline uint16_t bswap_16(uint16_t x)
{
return x;
}
static inline uint32_t bswap_32(uint32_t x)
{
return x;
}
#endif
void routerboot_tag_show_u32s(const uint8_t *pld, uint16_t pld_len)
{
uint32_t *data; // cpu-endian
char buf[5];
if (pld_len && (pld_len % sizeof(*data)))
return;
data = (uint32_t *)pld;
do {
memcpy(buf, data, sizeof(*data));
buf[4] = '\0';
printf(" 0x%08x - %s\n", bswap_32(*data), buf);
data++;
} while ((pld_len -= sizeof(*data)));
}
int routerboot_tag_find(const uint8_t *bufhead, const size_t buflen, const uint16_t tag_id,
uint16_t *pld_ofs, uint16_t *pld_len)
{
const uint32_t *datum, *bufend;
uint32_t node;
uint16_t id, len;
int ret;
if (!bufhead)
return -1;
ret = -1;
datum = (const uint32_t *)bufhead;
bufend = (const uint32_t *)(bufhead + buflen);
while (datum < bufend) {
node = *datum++;
node = bswap_32(node);
/* Tag list ends with null node */
if (!node)
break;
id = node & 0xFFFF;
len = node >> 16;
if (datum >= bufend)
break;
if (pld_ofs)
*pld_ofs = (uint16_t)((uint8_t *)datum - bufhead);
if (pld_len)
*pld_len = len;
if ((!tag_id) || (tag_id == id))
printf("found tag 0x%02x, len: %d\n", id, len);
if ((!tag_id && (len < 0x40)) || (tag_id == id))
routerboot_tag_show_u32s((uint8_t *)datum, len);
datum += len / sizeof(*datum);
}
return ret;
}
int main(int argc, char **argv)
{
FILE *fp;
size_t len = 0x1000;
unsigned char buf[len], *p;
uint32_t *data;
uint16_t id;
if ((argc < 2) || (argc > 3)) {
printf("usage: %s <file> [tagid]\n", argv[0]);
return -1;
}
printf("Byteswapping is %s.\n", (BYTESWAP) ? "enabled" : "disabled");
fp = fopen(argv[1], "rb");
len = fread(buf, 1, len, fp);
fclose(fp);
if (argc == 3)
id = strtol(argv[2], NULL, 0);
else
id = 0;
p = buf;
data = (uint32_t *)p;
if (bswap_32(*data) == RB_MAGIC_HARD) {
printf("hard_config found.\n");
p += 4;
len -= 4;
} else if (bswap_32(*data) == RB_MAGIC_SOFT) {
printf("soft_config found.\n");
p += 8;
len -= 8;
} else {
printf("Magic not found!\n");
return -1;
}
routerboot_tag_find(p, len, id, NULL, NULL);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment