*/
#define _GNU_SOURCE
+#include <byteswap.h>
#include <limits.h>
#include <unistd.h>
#include <stdlib.h>
#define MAX_ARGS 8
#define JFFS2_DEFAULT_DIR "" /* directory name without /, empty means root dir */
+#define TRX_MAGIC 0x48445230 /* "HDR0" */
+#define SEAMA_MAGIC 0x5ea3a417
+
+#if !defined(__BYTE_ORDER)
+#error "Unknown byte order"
+#endif
+
+#if __BYTE_ORDER == __BIG_ENDIAN
+#define cpu_to_be32(x) (x)
+#define be32_to_cpu(x) (x)
+#elif __BYTE_ORDER == __LITTLE_ENDIAN
+#define cpu_to_be32(x) bswap_32(x)
+#define be32_to_cpu(x) bswap_32(x)
+#else
+#error "Unsupported endianness"
+#endif
+
+enum mtd_image_format {
+ MTD_IMAGE_FORMAT_UNKNOWN,
+ MTD_IMAGE_FORMAT_TRX,
+ MTD_IMAGE_FORMAT_SEAMA,
+};
+
static char *buf = NULL;
static char *imagefile = NULL;
+static enum mtd_image_format imageformat = MTD_IMAGE_FORMAT_UNKNOWN;
static char *jffs2file = NULL, *jffs2dir = JFFS2_DEFAULT_DIR;
static int buflen = 0;
int quiet;
return 0;
}
-
static int
image_check(int imagefd, const char *mtd)
{
+ uint32_t magic;
int ret = 1;
- if (trx_check) {
- ret = trx_check(imagefd, mtd, buf, &buflen);
+
+ if (buflen < sizeof(magic)) {
+ buflen += read(imagefd, buf + buflen, sizeof(magic) - buflen);
+ if (buflen < sizeof(magic)) {
+ fprintf(stdout, "Could not get image magic\n");
+ return 0;
+ }
+ }
+ magic = ((uint32_t *)buf)[0];
+
+ if (be32_to_cpu(magic) == TRX_MAGIC)
+ imageformat = MTD_IMAGE_FORMAT_TRX;
+ else if (be32_to_cpu(magic) == SEAMA_MAGIC)
+ imageformat = MTD_IMAGE_FORMAT_SEAMA;
+
+ switch (imageformat) {
+ case MTD_IMAGE_FORMAT_TRX:
+ if (trx_check)
+ ret = trx_check(imagefd, mtd, buf, &buflen);
+ break;
+ case MTD_IMAGE_FORMAT_SEAMA:
+ break;
+ default:
+#ifdef target_brcm
+ if (!strcmp(mtd, "firmware"))
+ ret = 0;
+#endif
+ break;
}
return ret;
uint32_t offsets[3]; /* Offsets of partitions from start of header */
};
-#define SEAMA_MAGIC 0x17a4a35e
-
#if __BYTE_ORDER == __BIG_ENDIAN
#define STORE32_LE(X) ((((X) & 0x000000FF) << 24) | (((X) & 0x0000FF00) << 8) | (((X) & 0x00FF0000) >> 8) | (((X) & 0xFF000000) >> 24))
#elif __BYTE_ORDER == __LITTLE_ENDIAN
if (strcmp(mtd, "firmware") != 0)
return 1;
- *len = read(imagefd, buf, 32);
if (*len < 32) {
- fprintf(stdout, "Could not get image header, file too small (%d bytes)\n", *len);
- return 0;
+ *len += read(imagefd, buf + *len, 32 - *len);
+ if (*len < 32) {
+ fprintf(stdout, "Could not get image header, file too small (%d bytes)\n", *len);
+ return 0;
+ }
}
- /* Allow writing Seama files to firmware without an extra validation */
- if (trx->magic == SEAMA_MAGIC)
- return 1;
-
if (trx->magic != TRX_MAGIC || trx->len < sizeof(struct trx_header)) {
if (quiet < 2) {
fprintf(stderr, "Bad trx header\n");