xref: /openbmc/u-boot/tools/mxsimage.c (revision ed36323f)
1 /*
2  * Freescale i.MX23/i.MX28 SB image generator
3  *
4  * Copyright (C) 2012-2013 Marek Vasut <marex@denx.de>
5  *
6  * SPDX-License-Identifier:	GPL-2.0+
7  */
8 
9 #ifdef CONFIG_MXS
10 
11 #include <errno.h>
12 #include <fcntl.h>
13 #include <stdio.h>
14 #include <string.h>
15 #include <unistd.h>
16 #include <limits.h>
17 
18 #include <openssl/evp.h>
19 
20 #include "imagetool.h"
21 #include "mxsimage.h"
22 #include "pbl_crc32.h"
23 #include <image.h>
24 
25 
26 /*
27  * DCD block
28  * |-Write to address command block
29  * |  0xf00 == 0xf33d
30  * |  0xba2 == 0xb33f
31  * |-ORR address with mask command block
32  * |  0xf00 |= 0x1337
33  * |-Write to address command block
34  * |  0xba2 == 0xd00d
35  * :
36  */
37 #define SB_HAB_DCD_WRITE	0xccUL
38 #define SB_HAB_DCD_CHECK	0xcfUL
39 #define SB_HAB_DCD_NOOP		0xc0UL
40 #define SB_HAB_DCD_MASK_BIT	(1 << 3)
41 #define SB_HAB_DCD_SET_BIT	(1 << 4)
42 
43 /* Addr.n = Value.n */
44 #define	SB_DCD_WRITE	\
45 	(SB_HAB_DCD_WRITE << 24)
46 /* Addr.n &= ~Value.n */
47 #define	SB_DCD_ANDC	\
48 	((SB_HAB_DCD_WRITE << 24) | SB_HAB_DCD_SET_BIT)
49 /* Addr.n |= Value.n */
50 #define	SB_DCD_ORR	\
51 	((SB_HAB_DCD_WRITE << 24) | SB_HAB_DCD_SET_BIT | SB_HAB_DCD_MASK_BIT)
52 /* (Addr.n & Value.n) == 0 */
53 #define	SB_DCD_CHK_EQZ	\
54 	(SB_HAB_DCD_CHECK << 24)
55 /* (Addr.n & Value.n) == Value.n */
56 #define	SB_DCD_CHK_EQ	\
57 	((SB_HAB_DCD_CHECK << 24) | SB_HAB_DCD_SET_BIT)
58 /* (Addr.n & Value.n) != Value.n */
59 #define	SB_DCD_CHK_NEQ	\
60 	((SB_HAB_DCD_CHECK << 24) | SB_HAB_DCD_MASK_BIT)
61 /* (Addr.n & Value.n) != 0 */
62 #define	SB_DCD_CHK_NEZ	\
63 	((SB_HAB_DCD_CHECK << 24) | SB_HAB_DCD_SET_BIT | SB_HAB_DCD_MASK_BIT)
64 /* NOP */
65 #define	SB_DCD_NOOP	\
66 	(SB_HAB_DCD_NOOP << 24)
67 
68 struct sb_dcd_ctx {
69 	struct sb_dcd_ctx		*dcd;
70 
71 	uint32_t			id;
72 
73 	/* The DCD block. */
74 	uint32_t			*payload;
75 	/* Size of the whole DCD block. */
76 	uint32_t			size;
77 
78 	/* Pointer to previous DCD command block. */
79 	uint32_t			*prev_dcd_head;
80 };
81 
82 /*
83  * IMAGE
84  *   |-SECTION
85  *   |    |-CMD
86  *   |    |-CMD
87  *   |    `-CMD
88  *   |-SECTION
89  *   |    |-CMD
90  *   :    :
91  */
92 struct sb_cmd_list {
93 	char				*cmd;
94 	size_t				len;
95 	unsigned int			lineno;
96 };
97 
98 struct sb_cmd_ctx {
99 	uint32_t			size;
100 
101 	struct sb_cmd_ctx		*cmd;
102 
103 	uint8_t				*data;
104 	uint32_t			length;
105 
106 	struct sb_command		payload;
107 	struct sb_command		c_payload;
108 };
109 
110 struct sb_section_ctx {
111 	uint32_t			size;
112 
113 	/* Section flags */
114 	unsigned int			boot:1;
115 
116 	struct sb_section_ctx		*sect;
117 
118 	struct sb_cmd_ctx		*cmd_head;
119 	struct sb_cmd_ctx		*cmd_tail;
120 
121 	struct sb_sections_header	payload;
122 };
123 
124 struct sb_image_ctx {
125 	unsigned int			in_section:1;
126 	unsigned int			in_dcd:1;
127 	/* Image configuration */
128 	unsigned int			verbose_boot:1;
129 	unsigned int			silent_dump:1;
130 	char				*input_filename;
131 	char				*output_filename;
132 	char				*cfg_filename;
133 	uint8_t				image_key[16];
134 
135 	/* Number of section in the image */
136 	unsigned int			sect_count;
137 	/* Bootable section */
138 	unsigned int			sect_boot;
139 	unsigned int			sect_boot_found:1;
140 
141 	struct sb_section_ctx		*sect_head;
142 	struct sb_section_ctx		*sect_tail;
143 
144 	struct sb_dcd_ctx		*dcd_head;
145 	struct sb_dcd_ctx		*dcd_tail;
146 
147 	EVP_CIPHER_CTX			cipher_ctx;
148 	EVP_MD_CTX			md_ctx;
149 	uint8_t				digest[32];
150 	struct sb_key_dictionary_key	sb_dict_key;
151 
152 	struct sb_boot_image_header	payload;
153 };
154 
155 /*
156  * Instruction semantics:
157  * NOOP
158  * TAG [LAST]
159  * LOAD       address file
160  * LOAD  IVT  address IVT_entry_point
161  * FILL address pattern length
162  * JUMP [HAB] address [r0_arg]
163  * CALL [HAB] address [r0_arg]
164  * MODE mode
165  *      For i.MX23, mode = USB/I2C/SPI1_FLASH/SPI2_FLASH/NAND_BCH
166  *                         JTAG/SPI3_EEPROM/SD_SSP0/SD_SSP1
167  *      For i.MX28, mode = USB/I2C/SPI2_FLASH/SPI3_FLASH/NAND_BCH
168  *                         JTAG/SPI2_EEPROM/SD_SSP0/SD_SSP1
169  */
170 
171 /*
172  * AES libcrypto
173  */
174 static int sb_aes_init(struct sb_image_ctx *ictx, uint8_t *iv, int enc)
175 {
176 	EVP_CIPHER_CTX *ctx = &ictx->cipher_ctx;
177 	int ret;
178 
179 	/* If there is no init vector, init vector is all zeroes. */
180 	if (!iv)
181 		iv = ictx->image_key;
182 
183 	EVP_CIPHER_CTX_init(ctx);
184 	ret = EVP_CipherInit(ctx, EVP_aes_128_cbc(), ictx->image_key, iv, enc);
185 	if (ret == 1)
186 		EVP_CIPHER_CTX_set_padding(ctx, 0);
187 	return ret;
188 }
189 
190 static int sb_aes_crypt(struct sb_image_ctx *ictx, uint8_t *in_data,
191 			uint8_t *out_data, int in_len)
192 {
193 	EVP_CIPHER_CTX *ctx = &ictx->cipher_ctx;
194 	int ret, outlen;
195 	uint8_t *outbuf;
196 
197 	outbuf = malloc(in_len);
198 	if (!outbuf)
199 		return -ENOMEM;
200 	memset(outbuf, 0, sizeof(in_len));
201 
202 	ret = EVP_CipherUpdate(ctx, outbuf, &outlen, in_data, in_len);
203 	if (!ret) {
204 		ret = -EINVAL;
205 		goto err;
206 	}
207 
208 	if (out_data)
209 		memcpy(out_data, outbuf, outlen);
210 
211 err:
212 	free(outbuf);
213 	return ret;
214 }
215 
216 static int sb_aes_deinit(EVP_CIPHER_CTX *ctx)
217 {
218 	return EVP_CIPHER_CTX_cleanup(ctx);
219 }
220 
221 static int sb_aes_reinit(struct sb_image_ctx *ictx, int enc)
222 {
223 	int ret;
224 	EVP_CIPHER_CTX *ctx = &ictx->cipher_ctx;
225 	struct sb_boot_image_header *sb_header = &ictx->payload;
226 	uint8_t *iv = sb_header->iv;
227 
228 	ret = sb_aes_deinit(ctx);
229 	if (!ret)
230 		return ret;
231 	return sb_aes_init(ictx, iv, enc);
232 }
233 
234 /*
235  * Debug
236  */
237 static void soprintf(struct sb_image_ctx *ictx, const char *fmt, ...)
238 {
239 	va_list ap;
240 
241 	if (ictx->silent_dump)
242 		return;
243 
244 	va_start(ap, fmt);
245 	vfprintf(stdout, fmt, ap);
246 	va_end(ap);
247 }
248 
249 /*
250  * Code
251  */
252 static time_t sb_get_timestamp(void)
253 {
254 	struct tm time_2000 = {
255 		.tm_yday	= 1,	/* Jan. 1st */
256 		.tm_year	= 100,	/* 2000 */
257 	};
258 	time_t seconds_to_2000 = mktime(&time_2000);
259 	time_t seconds_to_now = time(NULL);
260 
261 	return seconds_to_now - seconds_to_2000;
262 }
263 
264 static int sb_get_time(time_t time, struct tm *tm)
265 {
266 	struct tm time_2000 = {
267 		.tm_yday	= 1,	/* Jan. 1st */
268 		.tm_year	= 0,	/* 1900 */
269 	};
270 	const time_t seconds_to_2000 = mktime(&time_2000);
271 	const time_t seconds_to_now = seconds_to_2000 + time;
272 	struct tm *ret;
273 	ret = gmtime_r(&seconds_to_now, tm);
274 	return ret ? 0 : -EINVAL;
275 }
276 
277 static void sb_encrypt_sb_header(struct sb_image_ctx *ictx)
278 {
279 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
280 	struct sb_boot_image_header *sb_header = &ictx->payload;
281 	uint8_t *sb_header_ptr = (uint8_t *)sb_header;
282 
283 	/* Encrypt the header, compute the digest. */
284 	sb_aes_crypt(ictx, sb_header_ptr, NULL, sizeof(*sb_header));
285 	EVP_DigestUpdate(md_ctx, sb_header_ptr, sizeof(*sb_header));
286 }
287 
288 static void sb_encrypt_sb_sections_header(struct sb_image_ctx *ictx)
289 {
290 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
291 	struct sb_section_ctx *sctx = ictx->sect_head;
292 	struct sb_sections_header *shdr;
293 	uint8_t *sb_sections_header_ptr;
294 	const int size = sizeof(*shdr);
295 
296 	while (sctx) {
297 		shdr = &sctx->payload;
298 		sb_sections_header_ptr = (uint8_t *)shdr;
299 
300 		sb_aes_crypt(ictx, sb_sections_header_ptr,
301 			     ictx->sb_dict_key.cbc_mac, size);
302 		EVP_DigestUpdate(md_ctx, sb_sections_header_ptr, size);
303 
304 		sctx = sctx->sect;
305 	};
306 }
307 
308 static void sb_encrypt_key_dictionary_key(struct sb_image_ctx *ictx)
309 {
310 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
311 
312 	sb_aes_crypt(ictx, ictx->image_key, ictx->sb_dict_key.key,
313 		     sizeof(ictx->sb_dict_key.key));
314 	EVP_DigestUpdate(md_ctx, &ictx->sb_dict_key, sizeof(ictx->sb_dict_key));
315 }
316 
317 static void sb_decrypt_key_dictionary_key(struct sb_image_ctx *ictx)
318 {
319 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
320 
321 	EVP_DigestUpdate(md_ctx, &ictx->sb_dict_key, sizeof(ictx->sb_dict_key));
322 	sb_aes_crypt(ictx, ictx->sb_dict_key.key, ictx->image_key,
323 		     sizeof(ictx->sb_dict_key.key));
324 }
325 
326 static void sb_encrypt_tag(struct sb_image_ctx *ictx,
327 		struct sb_cmd_ctx *cctx)
328 {
329 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
330 	struct sb_command *cmd = &cctx->payload;
331 
332 	sb_aes_crypt(ictx, (uint8_t *)cmd,
333 		     (uint8_t *)&cctx->c_payload, sizeof(*cmd));
334 	EVP_DigestUpdate(md_ctx, &cctx->c_payload, sizeof(*cmd));
335 }
336 
337 static int sb_encrypt_image(struct sb_image_ctx *ictx)
338 {
339 	/* Start image-wide crypto. */
340 	EVP_MD_CTX_init(&ictx->md_ctx);
341 	EVP_DigestInit(&ictx->md_ctx, EVP_sha1());
342 
343 	/*
344 	 * SB image header.
345 	 */
346 	sb_aes_init(ictx, NULL, 1);
347 	sb_encrypt_sb_header(ictx);
348 
349 	/*
350 	 * SB sections header.
351 	 */
352 	sb_encrypt_sb_sections_header(ictx);
353 
354 	/*
355 	 * Key dictionary.
356 	 */
357 	sb_aes_reinit(ictx, 1);
358 	sb_encrypt_key_dictionary_key(ictx);
359 
360 	/*
361 	 * Section tags.
362 	 */
363 	struct sb_cmd_ctx *cctx;
364 	struct sb_command *ccmd;
365 	struct sb_section_ctx *sctx = ictx->sect_head;
366 
367 	while (sctx) {
368 		cctx = sctx->cmd_head;
369 
370 		sb_aes_reinit(ictx, 1);
371 
372 		while (cctx) {
373 			ccmd = &cctx->payload;
374 
375 			sb_encrypt_tag(ictx, cctx);
376 
377 			if (ccmd->header.tag == ROM_TAG_CMD) {
378 				sb_aes_reinit(ictx, 1);
379 			} else if (ccmd->header.tag == ROM_LOAD_CMD) {
380 				sb_aes_crypt(ictx, cctx->data, cctx->data,
381 					     cctx->length);
382 				EVP_DigestUpdate(&ictx->md_ctx, cctx->data,
383 						 cctx->length);
384 			}
385 
386 			cctx = cctx->cmd;
387 		}
388 
389 		sctx = sctx->sect;
390 	};
391 
392 	/*
393 	 * Dump the SHA1 of the whole image.
394 	 */
395 	sb_aes_reinit(ictx, 1);
396 
397 	EVP_DigestFinal(&ictx->md_ctx, ictx->digest, NULL);
398 	sb_aes_crypt(ictx, ictx->digest, ictx->digest, sizeof(ictx->digest));
399 
400 	/* Stop the encryption session. */
401 	sb_aes_deinit(&ictx->cipher_ctx);
402 
403 	return 0;
404 }
405 
406 static int sb_load_file(struct sb_cmd_ctx *cctx, char *filename)
407 {
408 	long real_size, roundup_size;
409 	uint8_t *data;
410 	long ret;
411 	unsigned long size;
412 	FILE *fp;
413 
414 	if (!filename) {
415 		fprintf(stderr, "ERR: Missing filename!\n");
416 		return -EINVAL;
417 	}
418 
419 	fp = fopen(filename, "r");
420 	if (!fp)
421 		goto err_open;
422 
423 	ret = fseek(fp, 0, SEEK_END);
424 	if (ret < 0)
425 		goto err_file;
426 
427 	real_size = ftell(fp);
428 	if (real_size < 0)
429 		goto err_file;
430 
431 	ret = fseek(fp, 0, SEEK_SET);
432 	if (ret < 0)
433 		goto err_file;
434 
435 	roundup_size = roundup(real_size, SB_BLOCK_SIZE);
436 	data = calloc(1, roundup_size);
437 	if (!data)
438 		goto err_file;
439 
440 	size = fread(data, 1, real_size, fp);
441 	if (size != (unsigned long)real_size)
442 		goto err_alloc;
443 
444 	cctx->data = data;
445 	cctx->length = roundup_size;
446 
447 	fclose(fp);
448 	return 0;
449 
450 err_alloc:
451 	free(data);
452 err_file:
453 	fclose(fp);
454 err_open:
455 	fprintf(stderr, "ERR: Failed to load file \"%s\"\n", filename);
456 	return -EINVAL;
457 }
458 
459 static uint8_t sb_command_checksum(struct sb_command *inst)
460 {
461 	uint8_t *inst_ptr = (uint8_t *)inst;
462 	uint8_t csum = 0;
463 	unsigned int i;
464 
465 	for (i = 0; i < sizeof(struct sb_command); i++)
466 		csum += inst_ptr[i];
467 
468 	return csum;
469 }
470 
471 static int sb_token_to_long(char *tok, uint32_t *rid)
472 {
473 	char *endptr;
474 	unsigned long id;
475 
476 	if (tok[0] != '0' || tok[1] != 'x') {
477 		fprintf(stderr, "ERR: Invalid hexadecimal number!\n");
478 		return -EINVAL;
479 	}
480 
481 	tok += 2;
482 
483 	errno = 0;
484 	id = strtoul(tok, &endptr, 16);
485 	if ((errno == ERANGE && id == ULONG_MAX) || (errno != 0 && id == 0)) {
486 		fprintf(stderr, "ERR: Value can't be decoded!\n");
487 		return -EINVAL;
488 	}
489 
490 	/* Check for 32-bit overflow. */
491 	if (id > 0xffffffff) {
492 		fprintf(stderr, "ERR: Value too big!\n");
493 		return -EINVAL;
494 	}
495 
496 	if (endptr == tok) {
497 		fprintf(stderr, "ERR: Deformed value!\n");
498 		return -EINVAL;
499 	}
500 
501 	*rid = (uint32_t)id;
502 	return 0;
503 }
504 
505 static int sb_grow_dcd(struct sb_dcd_ctx *dctx, unsigned int inc_size)
506 {
507 	uint32_t *tmp;
508 
509 	if (!inc_size)
510 		return 0;
511 
512 	dctx->size += inc_size;
513 	tmp = realloc(dctx->payload, dctx->size);
514 	if (!tmp)
515 		return -ENOMEM;
516 
517 	dctx->payload = tmp;
518 
519 	/* Assemble and update the HAB DCD header. */
520 	dctx->payload[0] = htonl((SB_HAB_DCD_TAG << 24) |
521 				 (dctx->size << 8) |
522 				 SB_HAB_VERSION);
523 
524 	return 0;
525 }
526 
527 static int sb_build_dcd(struct sb_image_ctx *ictx, struct sb_cmd_list *cmd)
528 {
529 	struct sb_dcd_ctx *dctx;
530 
531 	char *tok;
532 	uint32_t id;
533 	int ret;
534 
535 	dctx = calloc(1, sizeof(*dctx));
536 	if (!dctx)
537 		return -ENOMEM;
538 
539 	ret = sb_grow_dcd(dctx, 4);
540 	if (ret)
541 		goto err_dcd;
542 
543 	/* Read DCD block number. */
544 	tok = strtok(cmd->cmd, " ");
545 	if (!tok) {
546 		fprintf(stderr, "#%i ERR: DCD block without number!\n",
547 			cmd->lineno);
548 		ret = -EINVAL;
549 		goto err_dcd;
550 	}
551 
552 	/* Parse the DCD block number. */
553 	ret = sb_token_to_long(tok, &id);
554 	if (ret) {
555 		fprintf(stderr, "#%i ERR: Malformed DCD block number!\n",
556 			cmd->lineno);
557 		goto err_dcd;
558 	}
559 
560 	dctx->id = id;
561 
562 	/*
563 	 * The DCD block is now constructed. Append it to the list.
564 	 * WARNING: The DCD size is still not computed and will be
565 	 * updated while parsing it's commands.
566 	 */
567 	if (!ictx->dcd_head) {
568 		ictx->dcd_head = dctx;
569 		ictx->dcd_tail = dctx;
570 	} else {
571 		ictx->dcd_tail->dcd = dctx;
572 		ictx->dcd_tail = dctx;
573 	}
574 
575 	return 0;
576 
577 err_dcd:
578 	free(dctx->payload);
579 	free(dctx);
580 	return ret;
581 }
582 
583 static int sb_build_dcd_block(struct sb_image_ctx *ictx,
584 			      struct sb_cmd_list *cmd,
585 			      uint32_t type)
586 {
587 	char *tok;
588 	uint32_t address, value, length;
589 	int ret;
590 
591 	struct sb_dcd_ctx *dctx = ictx->dcd_tail;
592 	uint32_t *dcd;
593 
594 	if (dctx->prev_dcd_head && (type != SB_DCD_NOOP) &&
595 	    ((dctx->prev_dcd_head[0] & 0xff0000ff) == type)) {
596 		/* Same instruction as before, just append it. */
597 		ret = sb_grow_dcd(dctx, 8);
598 		if (ret)
599 			return ret;
600 	} else if (type == SB_DCD_NOOP) {
601 		ret = sb_grow_dcd(dctx, 4);
602 		if (ret)
603 			return ret;
604 
605 		/* Update DCD command block pointer. */
606 		dctx->prev_dcd_head = dctx->payload +
607 				dctx->size / sizeof(*dctx->payload) - 1;
608 
609 		/* NOOP has only 4 bytes and no payload. */
610 		goto noop;
611 	} else {
612 		/*
613 		 * Either a different instruction block started now
614 		 * or this is the first instruction block.
615 		 */
616 		ret = sb_grow_dcd(dctx, 12);
617 		if (ret)
618 			return ret;
619 
620 		/* Update DCD command block pointer. */
621 		dctx->prev_dcd_head = dctx->payload +
622 				dctx->size / sizeof(*dctx->payload) - 3;
623 	}
624 
625 	dcd = dctx->payload + dctx->size / sizeof(*dctx->payload) - 2;
626 
627 	/*
628 	 * Prepare the command.
629 	 */
630 	tok = strtok(cmd->cmd, " ");
631 	if (!tok) {
632 		fprintf(stderr, "#%i ERR: Missing DCD address!\n",
633 			cmd->lineno);
634 		ret = -EINVAL;
635 		goto err;
636 	}
637 
638 	/* Read DCD destination address. */
639 	ret = sb_token_to_long(tok, &address);
640 	if (ret) {
641 		fprintf(stderr, "#%i ERR: Incorrect DCD address!\n",
642 			cmd->lineno);
643 		goto err;
644 	}
645 
646 	tok = strtok(NULL, " ");
647 	if (!tok) {
648 		fprintf(stderr, "#%i ERR: Missing DCD value!\n",
649 			cmd->lineno);
650 		ret = -EINVAL;
651 		goto err;
652 	}
653 
654 	/* Read DCD operation value. */
655 	ret = sb_token_to_long(tok, &value);
656 	if (ret) {
657 		fprintf(stderr, "#%i ERR: Incorrect DCD value!\n",
658 			cmd->lineno);
659 		goto err;
660 	}
661 
662 	/* Fill in the new DCD entry. */
663 	dcd[0] = htonl(address);
664 	dcd[1] = htonl(value);
665 
666 noop:
667 	/* Update the DCD command block. */
668 	length = dctx->size -
669 		 ((dctx->prev_dcd_head - dctx->payload) *
670 		 sizeof(*dctx->payload));
671 	dctx->prev_dcd_head[0] = htonl(type | (length << 8));
672 
673 err:
674 	return ret;
675 }
676 
677 static int sb_build_section(struct sb_image_ctx *ictx, struct sb_cmd_list *cmd)
678 {
679 	struct sb_section_ctx *sctx;
680 	struct sb_sections_header *shdr;
681 	char *tok;
682 	uint32_t bootable = 0;
683 	uint32_t id;
684 	int ret;
685 
686 	sctx = calloc(1, sizeof(*sctx));
687 	if (!sctx)
688 		return -ENOMEM;
689 
690 	/* Read section number. */
691 	tok = strtok(cmd->cmd, " ");
692 	if (!tok) {
693 		fprintf(stderr, "#%i ERR: Section without number!\n",
694 			cmd->lineno);
695 		ret = -EINVAL;
696 		goto err_sect;
697 	}
698 
699 	/* Parse the section number. */
700 	ret = sb_token_to_long(tok, &id);
701 	if (ret) {
702 		fprintf(stderr, "#%i ERR: Malformed section number!\n",
703 			cmd->lineno);
704 		goto err_sect;
705 	}
706 
707 	/* Read section's BOOTABLE flag. */
708 	tok = strtok(NULL, " ");
709 	if (tok && (strlen(tok) == 8) && !strncmp(tok, "BOOTABLE", 8))
710 		bootable = SB_SECTION_FLAG_BOOTABLE;
711 
712 	sctx->boot = bootable;
713 
714 	shdr = &sctx->payload;
715 	shdr->section_number = id;
716 	shdr->section_flags = bootable;
717 
718 	/*
719 	 * The section is now constructed. Append it to the list.
720 	 * WARNING: The section size is still not computed and will
721 	 * be updated while parsing it's commands.
722 	 */
723 	ictx->sect_count++;
724 
725 	/* Mark that this section is bootable one. */
726 	if (bootable) {
727 		if (ictx->sect_boot_found) {
728 			fprintf(stderr,
729 				"#%i WARN: Multiple bootable section!\n",
730 				cmd->lineno);
731 		} else {
732 			ictx->sect_boot = id;
733 			ictx->sect_boot_found = 1;
734 		}
735 	}
736 
737 	if (!ictx->sect_head) {
738 		ictx->sect_head = sctx;
739 		ictx->sect_tail = sctx;
740 	} else {
741 		ictx->sect_tail->sect = sctx;
742 		ictx->sect_tail = sctx;
743 	}
744 
745 	return 0;
746 
747 err_sect:
748 	free(sctx);
749 	return ret;
750 }
751 
752 static int sb_build_command_nop(struct sb_image_ctx *ictx)
753 {
754 	struct sb_section_ctx *sctx = ictx->sect_tail;
755 	struct sb_cmd_ctx *cctx;
756 	struct sb_command *ccmd;
757 
758 	cctx = calloc(1, sizeof(*cctx));
759 	if (!cctx)
760 		return -ENOMEM;
761 
762 	ccmd = &cctx->payload;
763 
764 	/*
765 	 * Construct the command.
766 	 */
767 	ccmd->header.checksum	= 0x5a;
768 	ccmd->header.tag	= ROM_NOP_CMD;
769 
770 	cctx->size = sizeof(*ccmd);
771 
772 	/*
773 	 * Append the command to the last section.
774 	 */
775 	if (!sctx->cmd_head) {
776 		sctx->cmd_head = cctx;
777 		sctx->cmd_tail = cctx;
778 	} else {
779 		sctx->cmd_tail->cmd = cctx;
780 		sctx->cmd_tail = cctx;
781 	}
782 
783 	return 0;
784 }
785 
786 static int sb_build_command_tag(struct sb_image_ctx *ictx,
787 				struct sb_cmd_list *cmd)
788 {
789 	struct sb_section_ctx *sctx = ictx->sect_tail;
790 	struct sb_cmd_ctx *cctx;
791 	struct sb_command *ccmd;
792 	char *tok;
793 
794 	cctx = calloc(1, sizeof(*cctx));
795 	if (!cctx)
796 		return -ENOMEM;
797 
798 	ccmd = &cctx->payload;
799 
800 	/*
801 	 * Prepare the command.
802 	 */
803 	/* Check for the LAST keyword. */
804 	tok = strtok(cmd->cmd, " ");
805 	if (tok && !strcmp(tok, "LAST"))
806 		ccmd->header.flags = ROM_TAG_CMD_FLAG_ROM_LAST_TAG;
807 
808 	/*
809 	 * Construct the command.
810 	 */
811 	ccmd->header.checksum	= 0x5a;
812 	ccmd->header.tag	= ROM_TAG_CMD;
813 
814 	cctx->size = sizeof(*ccmd);
815 
816 	/*
817 	 * Append the command to the last section.
818 	 */
819 	if (!sctx->cmd_head) {
820 		sctx->cmd_head = cctx;
821 		sctx->cmd_tail = cctx;
822 	} else {
823 		sctx->cmd_tail->cmd = cctx;
824 		sctx->cmd_tail = cctx;
825 	}
826 
827 	return 0;
828 }
829 
830 static int sb_build_command_load(struct sb_image_ctx *ictx,
831 				 struct sb_cmd_list *cmd)
832 {
833 	struct sb_section_ctx *sctx = ictx->sect_tail;
834 	struct sb_cmd_ctx *cctx;
835 	struct sb_command *ccmd;
836 	char *tok;
837 	int ret, is_ivt = 0, is_dcd = 0;
838 	uint32_t dest, dcd = 0;
839 
840 	cctx = calloc(1, sizeof(*cctx));
841 	if (!cctx)
842 		return -ENOMEM;
843 
844 	ccmd = &cctx->payload;
845 
846 	/*
847 	 * Prepare the command.
848 	 */
849 	tok = strtok(cmd->cmd, " ");
850 	if (!tok) {
851 		fprintf(stderr, "#%i ERR: Missing LOAD address or 'IVT'!\n",
852 			cmd->lineno);
853 		ret = -EINVAL;
854 		goto err;
855 	}
856 
857 	/* Check for "IVT" flag. */
858 	if (!strcmp(tok, "IVT"))
859 		is_ivt = 1;
860 	if (!strcmp(tok, "DCD"))
861 		is_dcd = 1;
862 	if (is_ivt || is_dcd) {
863 		tok = strtok(NULL, " ");
864 		if (!tok) {
865 			fprintf(stderr, "#%i ERR: Missing LOAD address!\n",
866 				cmd->lineno);
867 			ret = -EINVAL;
868 			goto err;
869 		}
870 	}
871 
872 	/* Read load destination address. */
873 	ret = sb_token_to_long(tok, &dest);
874 	if (ret) {
875 		fprintf(stderr, "#%i ERR: Incorrect LOAD address!\n",
876 			cmd->lineno);
877 		goto err;
878 	}
879 
880 	/* Read filename or IVT entrypoint or DCD block ID. */
881 	tok = strtok(NULL, " ");
882 	if (!tok) {
883 		fprintf(stderr,
884 			"#%i ERR: Missing LOAD filename or IVT ep or DCD block ID!\n",
885 			cmd->lineno);
886 		ret = -EINVAL;
887 		goto err;
888 	}
889 
890 	if (is_ivt) {
891 		/* Handle IVT. */
892 		struct sb_ivt_header *ivt;
893 		uint32_t ivtep;
894 		ret = sb_token_to_long(tok, &ivtep);
895 
896 		if (ret) {
897 			fprintf(stderr,
898 				"#%i ERR: Incorrect IVT entry point!\n",
899 				cmd->lineno);
900 			goto err;
901 		}
902 
903 		ivt = calloc(1, sizeof(*ivt));
904 		if (!ivt) {
905 			ret = -ENOMEM;
906 			goto err;
907 		}
908 
909 		ivt->header = sb_hab_ivt_header();
910 		ivt->entry = ivtep;
911 		ivt->self = dest;
912 
913 		cctx->data = (uint8_t *)ivt;
914 		cctx->length = sizeof(*ivt);
915 	} else if (is_dcd) {
916 		struct sb_dcd_ctx *dctx = ictx->dcd_head;
917 		uint32_t dcdid;
918 		uint8_t *payload;
919 		uint32_t asize;
920 		ret = sb_token_to_long(tok, &dcdid);
921 
922 		if (ret) {
923 			fprintf(stderr,
924 				"#%i ERR: Incorrect DCD block ID!\n",
925 				cmd->lineno);
926 			goto err;
927 		}
928 
929 		while (dctx) {
930 			if (dctx->id == dcdid)
931 				break;
932 			dctx = dctx->dcd;
933 		}
934 
935 		if (!dctx) {
936 			fprintf(stderr, "#%i ERR: DCD block %08x not found!\n",
937 				cmd->lineno, dcdid);
938 			goto err;
939 		}
940 
941 		asize = roundup(dctx->size, SB_BLOCK_SIZE);
942 		payload = calloc(1, asize);
943 		if (!payload) {
944 			ret = -ENOMEM;
945 			goto err;
946 		}
947 
948 		memcpy(payload, dctx->payload, dctx->size);
949 
950 		cctx->data = payload;
951 		cctx->length = asize;
952 
953 		/* Set the Load DCD flag. */
954 		dcd = ROM_LOAD_CMD_FLAG_DCD_LOAD;
955 	} else {
956 		/* Regular LOAD of a file. */
957 		ret = sb_load_file(cctx, tok);
958 		if (ret) {
959 			fprintf(stderr, "#%i ERR: Cannot load '%s'!\n",
960 				cmd->lineno, tok);
961 			goto err;
962 		}
963 	}
964 
965 	if (cctx->length & (SB_BLOCK_SIZE - 1)) {
966 		fprintf(stderr, "#%i ERR: Unaligned payload!\n",
967 			cmd->lineno);
968 	}
969 
970 	/*
971 	 * Construct the command.
972 	 */
973 	ccmd->header.checksum	= 0x5a;
974 	ccmd->header.tag	= ROM_LOAD_CMD;
975 	ccmd->header.flags	= dcd;
976 
977 	ccmd->load.address	= dest;
978 	ccmd->load.count	= cctx->length;
979 	ccmd->load.crc32	= pbl_crc32(0,
980 					    (const char *)cctx->data,
981 					    cctx->length);
982 
983 	cctx->size = sizeof(*ccmd) + cctx->length;
984 
985 	/*
986 	 * Append the command to the last section.
987 	 */
988 	if (!sctx->cmd_head) {
989 		sctx->cmd_head = cctx;
990 		sctx->cmd_tail = cctx;
991 	} else {
992 		sctx->cmd_tail->cmd = cctx;
993 		sctx->cmd_tail = cctx;
994 	}
995 
996 	return 0;
997 
998 err:
999 	free(cctx);
1000 	return ret;
1001 }
1002 
1003 static int sb_build_command_fill(struct sb_image_ctx *ictx,
1004 				 struct sb_cmd_list *cmd)
1005 {
1006 	struct sb_section_ctx *sctx = ictx->sect_tail;
1007 	struct sb_cmd_ctx *cctx;
1008 	struct sb_command *ccmd;
1009 	char *tok;
1010 	uint32_t address, pattern, length;
1011 	int ret;
1012 
1013 	cctx = calloc(1, sizeof(*cctx));
1014 	if (!cctx)
1015 		return -ENOMEM;
1016 
1017 	ccmd = &cctx->payload;
1018 
1019 	/*
1020 	 * Prepare the command.
1021 	 */
1022 	tok = strtok(cmd->cmd, " ");
1023 	if (!tok) {
1024 		fprintf(stderr, "#%i ERR: Missing FILL address!\n",
1025 			cmd->lineno);
1026 		ret = -EINVAL;
1027 		goto err;
1028 	}
1029 
1030 	/* Read fill destination address. */
1031 	ret = sb_token_to_long(tok, &address);
1032 	if (ret) {
1033 		fprintf(stderr, "#%i ERR: Incorrect FILL address!\n",
1034 			cmd->lineno);
1035 		goto err;
1036 	}
1037 
1038 	tok = strtok(NULL, " ");
1039 	if (!tok) {
1040 		fprintf(stderr, "#%i ERR: Missing FILL pattern!\n",
1041 			cmd->lineno);
1042 		ret = -EINVAL;
1043 		goto err;
1044 	}
1045 
1046 	/* Read fill pattern address. */
1047 	ret = sb_token_to_long(tok, &pattern);
1048 	if (ret) {
1049 		fprintf(stderr, "#%i ERR: Incorrect FILL pattern!\n",
1050 			cmd->lineno);
1051 		goto err;
1052 	}
1053 
1054 	tok = strtok(NULL, " ");
1055 	if (!tok) {
1056 		fprintf(stderr, "#%i ERR: Missing FILL length!\n",
1057 			cmd->lineno);
1058 		ret = -EINVAL;
1059 		goto err;
1060 	}
1061 
1062 	/* Read fill pattern address. */
1063 	ret = sb_token_to_long(tok, &length);
1064 	if (ret) {
1065 		fprintf(stderr, "#%i ERR: Incorrect FILL length!\n",
1066 			cmd->lineno);
1067 		goto err;
1068 	}
1069 
1070 	/*
1071 	 * Construct the command.
1072 	 */
1073 	ccmd->header.checksum	= 0x5a;
1074 	ccmd->header.tag	= ROM_FILL_CMD;
1075 
1076 	ccmd->fill.address	= address;
1077 	ccmd->fill.count	= length;
1078 	ccmd->fill.pattern	= pattern;
1079 
1080 	cctx->size = sizeof(*ccmd);
1081 
1082 	/*
1083 	 * Append the command to the last section.
1084 	 */
1085 	if (!sctx->cmd_head) {
1086 		sctx->cmd_head = cctx;
1087 		sctx->cmd_tail = cctx;
1088 	} else {
1089 		sctx->cmd_tail->cmd = cctx;
1090 		sctx->cmd_tail = cctx;
1091 	}
1092 
1093 	return 0;
1094 
1095 err:
1096 	free(cctx);
1097 	return ret;
1098 }
1099 
1100 static int sb_build_command_jump_call(struct sb_image_ctx *ictx,
1101 				      struct sb_cmd_list *cmd,
1102 				      unsigned int is_call)
1103 {
1104 	struct sb_section_ctx *sctx = ictx->sect_tail;
1105 	struct sb_cmd_ctx *cctx;
1106 	struct sb_command *ccmd;
1107 	char *tok;
1108 	uint32_t dest, arg = 0x0;
1109 	uint32_t hab = 0;
1110 	int ret;
1111 	const char *cmdname = is_call ? "CALL" : "JUMP";
1112 
1113 	cctx = calloc(1, sizeof(*cctx));
1114 	if (!cctx)
1115 		return -ENOMEM;
1116 
1117 	ccmd = &cctx->payload;
1118 
1119 	/*
1120 	 * Prepare the command.
1121 	 */
1122 	tok = strtok(cmd->cmd, " ");
1123 	if (!tok) {
1124 		fprintf(stderr,
1125 			"#%i ERR: Missing %s address or 'HAB'!\n",
1126 			cmd->lineno, cmdname);
1127 		ret = -EINVAL;
1128 		goto err;
1129 	}
1130 
1131 	/* Check for "HAB" flag. */
1132 	if (!strcmp(tok, "HAB")) {
1133 		hab = is_call ? ROM_CALL_CMD_FLAG_HAB : ROM_JUMP_CMD_FLAG_HAB;
1134 		tok = strtok(NULL, " ");
1135 		if (!tok) {
1136 			fprintf(stderr, "#%i ERR: Missing %s address!\n",
1137 				cmd->lineno, cmdname);
1138 			ret = -EINVAL;
1139 			goto err;
1140 		}
1141 	}
1142 	/* Read load destination address. */
1143 	ret = sb_token_to_long(tok, &dest);
1144 	if (ret) {
1145 		fprintf(stderr, "#%i ERR: Incorrect %s address!\n",
1146 			cmd->lineno, cmdname);
1147 		goto err;
1148 	}
1149 
1150 	tok = strtok(NULL, " ");
1151 	if (tok) {
1152 		ret = sb_token_to_long(tok, &arg);
1153 		if (ret) {
1154 			fprintf(stderr,
1155 				"#%i ERR: Incorrect %s argument!\n",
1156 				cmd->lineno, cmdname);
1157 			goto err;
1158 		}
1159 	}
1160 
1161 	/*
1162 	 * Construct the command.
1163 	 */
1164 	ccmd->header.checksum	= 0x5a;
1165 	ccmd->header.tag	= is_call ? ROM_CALL_CMD : ROM_JUMP_CMD;
1166 	ccmd->header.flags	= hab;
1167 
1168 	ccmd->call.address	= dest;
1169 	ccmd->call.argument	= arg;
1170 
1171 	cctx->size = sizeof(*ccmd);
1172 
1173 	/*
1174 	 * Append the command to the last section.
1175 	 */
1176 	if (!sctx->cmd_head) {
1177 		sctx->cmd_head = cctx;
1178 		sctx->cmd_tail = cctx;
1179 	} else {
1180 		sctx->cmd_tail->cmd = cctx;
1181 		sctx->cmd_tail = cctx;
1182 	}
1183 
1184 	return 0;
1185 
1186 err:
1187 	free(cctx);
1188 	return ret;
1189 }
1190 
1191 static int sb_build_command_jump(struct sb_image_ctx *ictx,
1192 				 struct sb_cmd_list *cmd)
1193 {
1194 	return sb_build_command_jump_call(ictx, cmd, 0);
1195 }
1196 
1197 static int sb_build_command_call(struct sb_image_ctx *ictx,
1198 				 struct sb_cmd_list *cmd)
1199 {
1200 	return sb_build_command_jump_call(ictx, cmd, 1);
1201 }
1202 
1203 static int sb_build_command_mode(struct sb_image_ctx *ictx,
1204 				 struct sb_cmd_list *cmd)
1205 {
1206 	struct sb_section_ctx *sctx = ictx->sect_tail;
1207 	struct sb_cmd_ctx *cctx;
1208 	struct sb_command *ccmd;
1209 	char *tok;
1210 	int ret;
1211 	unsigned int i;
1212 	uint32_t mode = 0xffffffff;
1213 
1214 	cctx = calloc(1, sizeof(*cctx));
1215 	if (!cctx)
1216 		return -ENOMEM;
1217 
1218 	ccmd = &cctx->payload;
1219 
1220 	/*
1221 	 * Prepare the command.
1222 	 */
1223 	tok = strtok(cmd->cmd, " ");
1224 	if (!tok) {
1225 		fprintf(stderr, "#%i ERR: Missing MODE boot mode argument!\n",
1226 			cmd->lineno);
1227 		ret = -EINVAL;
1228 		goto err;
1229 	}
1230 
1231 	for (i = 0; i < ARRAY_SIZE(modetable); i++) {
1232 		if (!strcmp(tok, modetable[i].name)) {
1233 			mode = modetable[i].mode;
1234 			break;
1235 		}
1236 
1237 		if (!modetable[i].altname)
1238 			continue;
1239 
1240 		if (!strcmp(tok, modetable[i].altname)) {
1241 			mode = modetable[i].mode;
1242 			break;
1243 		}
1244 	}
1245 
1246 	if (mode == 0xffffffff) {
1247 		fprintf(stderr, "#%i ERR: Invalid MODE boot mode argument!\n",
1248 			cmd->lineno);
1249 		ret = -EINVAL;
1250 		goto err;
1251 	}
1252 
1253 	/*
1254 	 * Construct the command.
1255 	 */
1256 	ccmd->header.checksum	= 0x5a;
1257 	ccmd->header.tag	= ROM_MODE_CMD;
1258 
1259 	ccmd->mode.mode		= mode;
1260 
1261 	cctx->size = sizeof(*ccmd);
1262 
1263 	/*
1264 	 * Append the command to the last section.
1265 	 */
1266 	if (!sctx->cmd_head) {
1267 		sctx->cmd_head = cctx;
1268 		sctx->cmd_tail = cctx;
1269 	} else {
1270 		sctx->cmd_tail->cmd = cctx;
1271 		sctx->cmd_tail = cctx;
1272 	}
1273 
1274 	return 0;
1275 
1276 err:
1277 	free(cctx);
1278 	return ret;
1279 }
1280 
1281 static int sb_prefill_image_header(struct sb_image_ctx *ictx)
1282 {
1283 	struct sb_boot_image_header *hdr = &ictx->payload;
1284 
1285 	/* Fill signatures */
1286 	memcpy(hdr->signature1, "STMP", 4);
1287 	memcpy(hdr->signature2, "sgtl", 4);
1288 
1289 	/* SB Image version 1.1 */
1290 	hdr->major_version = SB_VERSION_MAJOR;
1291 	hdr->minor_version = SB_VERSION_MINOR;
1292 
1293 	/* Boot image major version */
1294 	hdr->product_version.major = htons(0x999);
1295 	hdr->product_version.minor = htons(0x999);
1296 	hdr->product_version.revision = htons(0x999);
1297 	/* Boot image major version */
1298 	hdr->component_version.major = htons(0x999);
1299 	hdr->component_version.minor = htons(0x999);
1300 	hdr->component_version.revision = htons(0x999);
1301 
1302 	/* Drive tag must be 0x0 for i.MX23 */
1303 	hdr->drive_tag = 0;
1304 
1305 	hdr->header_blocks =
1306 		sizeof(struct sb_boot_image_header) / SB_BLOCK_SIZE;
1307 	hdr->section_header_size =
1308 		sizeof(struct sb_sections_header) / SB_BLOCK_SIZE;
1309 	hdr->timestamp_us = sb_get_timestamp() * 1000000;
1310 
1311 	/* FIXME -- add proper config option */
1312 	hdr->flags = ictx->verbose_boot ? SB_IMAGE_FLAG_VERBOSE : 0,
1313 
1314 	/* FIXME -- We support only default key */
1315 	hdr->key_count = 1;
1316 
1317 	return 0;
1318 }
1319 
1320 static int sb_postfill_image_header(struct sb_image_ctx *ictx)
1321 {
1322 	struct sb_boot_image_header *hdr = &ictx->payload;
1323 	struct sb_section_ctx *sctx = ictx->sect_head;
1324 	uint32_t kd_size, sections_blocks;
1325 	EVP_MD_CTX md_ctx;
1326 
1327 	/* The main SB header size in blocks. */
1328 	hdr->image_blocks = hdr->header_blocks;
1329 
1330 	/* Size of the key dictionary, which has single zero entry. */
1331 	kd_size = hdr->key_count * sizeof(struct sb_key_dictionary_key);
1332 	hdr->image_blocks += kd_size / SB_BLOCK_SIZE;
1333 
1334 	/* Now count the payloads. */
1335 	hdr->section_count = ictx->sect_count;
1336 	while (sctx) {
1337 		hdr->image_blocks += sctx->size / SB_BLOCK_SIZE;
1338 		sctx = sctx->sect;
1339 	}
1340 
1341 	if (!ictx->sect_boot_found) {
1342 		fprintf(stderr, "ERR: No bootable section selected!\n");
1343 		return -EINVAL;
1344 	}
1345 	hdr->first_boot_section_id = ictx->sect_boot;
1346 
1347 	/* The n * SB section size in blocks. */
1348 	sections_blocks = hdr->section_count * hdr->section_header_size;
1349 	hdr->image_blocks += sections_blocks;
1350 
1351 	/* Key dictionary offset. */
1352 	hdr->key_dictionary_block = hdr->header_blocks + sections_blocks;
1353 
1354 	/* Digest of the whole image. */
1355 	hdr->image_blocks += 2;
1356 
1357 	/* Pointer past the dictionary. */
1358 	hdr->first_boot_tag_block =
1359 		hdr->key_dictionary_block + kd_size / SB_BLOCK_SIZE;
1360 
1361 	/* Compute header digest. */
1362 	EVP_MD_CTX_init(&md_ctx);
1363 
1364 	EVP_DigestInit(&md_ctx, EVP_sha1());
1365 	EVP_DigestUpdate(&md_ctx, hdr->signature1,
1366 			 sizeof(struct sb_boot_image_header) -
1367 			 sizeof(hdr->digest));
1368 	EVP_DigestFinal(&md_ctx, hdr->digest, NULL);
1369 
1370 	return 0;
1371 }
1372 
1373 static int sb_fixup_sections_and_tags(struct sb_image_ctx *ictx)
1374 {
1375 	/* Fixup the placement of sections. */
1376 	struct sb_boot_image_header *ihdr = &ictx->payload;
1377 	struct sb_section_ctx *sctx = ictx->sect_head;
1378 	struct sb_sections_header *shdr;
1379 	struct sb_cmd_ctx *cctx;
1380 	struct sb_command *ccmd;
1381 	uint32_t offset = ihdr->first_boot_tag_block;
1382 
1383 	while (sctx) {
1384 		shdr = &sctx->payload;
1385 
1386 		/* Fill in the section TAG offset. */
1387 		shdr->section_offset = offset + 1;
1388 		offset += shdr->section_size;
1389 
1390 		/* Section length is measured from the TAG block. */
1391 		shdr->section_size--;
1392 
1393 		/* Fixup the TAG command. */
1394 		cctx = sctx->cmd_head;
1395 		while (cctx) {
1396 			ccmd = &cctx->payload;
1397 			if (ccmd->header.tag == ROM_TAG_CMD) {
1398 				ccmd->tag.section_number = shdr->section_number;
1399 				ccmd->tag.section_length = shdr->section_size;
1400 				ccmd->tag.section_flags = shdr->section_flags;
1401 			}
1402 
1403 			/* Update the command checksum. */
1404 			ccmd->header.checksum = sb_command_checksum(ccmd);
1405 
1406 			cctx = cctx->cmd;
1407 		}
1408 
1409 		sctx = sctx->sect;
1410 	}
1411 
1412 	return 0;
1413 }
1414 
1415 static int sb_parse_line(struct sb_image_ctx *ictx, struct sb_cmd_list *cmd)
1416 {
1417 	char *tok;
1418 	char *line = cmd->cmd;
1419 	char *rptr;
1420 	int ret;
1421 
1422 	/* Analyze the identifier on this line first. */
1423 	tok = strtok_r(line, " ", &rptr);
1424 	if (!tok || (strlen(tok) == 0)) {
1425 		fprintf(stderr, "#%i ERR: Invalid line!\n", cmd->lineno);
1426 		return -EINVAL;
1427 	}
1428 
1429 	cmd->cmd = rptr;
1430 
1431 	/* DCD */
1432 	if (!strcmp(tok, "DCD")) {
1433 		ictx->in_section = 0;
1434 		ictx->in_dcd = 1;
1435 		sb_build_dcd(ictx, cmd);
1436 		return 0;
1437 	}
1438 
1439 	/* Section */
1440 	if (!strcmp(tok, "SECTION")) {
1441 		ictx->in_section = 1;
1442 		ictx->in_dcd = 0;
1443 		sb_build_section(ictx, cmd);
1444 		return 0;
1445 	}
1446 
1447 	if (!ictx->in_section && !ictx->in_dcd) {
1448 		fprintf(stderr, "#%i ERR: Data outside of a section!\n",
1449 			cmd->lineno);
1450 		return -EINVAL;
1451 	}
1452 
1453 	if (ictx->in_section) {
1454 		/* Section commands */
1455 		if (!strcmp(tok, "NOP")) {
1456 			ret = sb_build_command_nop(ictx);
1457 		} else if (!strcmp(tok, "TAG")) {
1458 			ret = sb_build_command_tag(ictx, cmd);
1459 		} else if (!strcmp(tok, "LOAD")) {
1460 			ret = sb_build_command_load(ictx, cmd);
1461 		} else if (!strcmp(tok, "FILL")) {
1462 			ret = sb_build_command_fill(ictx, cmd);
1463 		} else if (!strcmp(tok, "JUMP")) {
1464 			ret = sb_build_command_jump(ictx, cmd);
1465 		} else if (!strcmp(tok, "CALL")) {
1466 			ret = sb_build_command_call(ictx, cmd);
1467 		} else if (!strcmp(tok, "MODE")) {
1468 			ret = sb_build_command_mode(ictx, cmd);
1469 		} else {
1470 			fprintf(stderr,
1471 				"#%i ERR: Unsupported instruction '%s'!\n",
1472 				cmd->lineno, tok);
1473 			return -ENOTSUP;
1474 		}
1475 	} else if (ictx->in_dcd) {
1476 		char *lptr;
1477 		uint32_t ilen = '1';
1478 
1479 		tok = strtok_r(tok, ".", &lptr);
1480 		if (!tok || (strlen(tok) == 0) || (lptr && strlen(lptr) != 1)) {
1481 			fprintf(stderr, "#%i ERR: Invalid line!\n",
1482 				cmd->lineno);
1483 			return -EINVAL;
1484 		}
1485 
1486 		if (lptr &&
1487 		    (lptr[0] != '1' && lptr[0] != '2' && lptr[0] != '4')) {
1488 			fprintf(stderr, "#%i ERR: Invalid instruction width!\n",
1489 				cmd->lineno);
1490 			return -EINVAL;
1491 		}
1492 
1493 		if (lptr)
1494 			ilen = lptr[0] - '1';
1495 
1496 		/* DCD commands */
1497 		if (!strcmp(tok, "WRITE")) {
1498 			ret = sb_build_dcd_block(ictx, cmd,
1499 						 SB_DCD_WRITE | ilen);
1500 		} else if (!strcmp(tok, "ANDC")) {
1501 			ret = sb_build_dcd_block(ictx, cmd,
1502 						 SB_DCD_ANDC | ilen);
1503 		} else if (!strcmp(tok, "ORR")) {
1504 			ret = sb_build_dcd_block(ictx, cmd,
1505 						 SB_DCD_ORR | ilen);
1506 		} else if (!strcmp(tok, "EQZ")) {
1507 			ret = sb_build_dcd_block(ictx, cmd,
1508 						 SB_DCD_CHK_EQZ | ilen);
1509 		} else if (!strcmp(tok, "EQ")) {
1510 			ret = sb_build_dcd_block(ictx, cmd,
1511 						 SB_DCD_CHK_EQ | ilen);
1512 		} else if (!strcmp(tok, "NEQ")) {
1513 			ret = sb_build_dcd_block(ictx, cmd,
1514 						 SB_DCD_CHK_NEQ | ilen);
1515 		} else if (!strcmp(tok, "NEZ")) {
1516 			ret = sb_build_dcd_block(ictx, cmd,
1517 						 SB_DCD_CHK_NEZ | ilen);
1518 		} else if (!strcmp(tok, "NOOP")) {
1519 			ret = sb_build_dcd_block(ictx, cmd, SB_DCD_NOOP);
1520 		} else {
1521 			fprintf(stderr,
1522 				"#%i ERR: Unsupported instruction '%s'!\n",
1523 				cmd->lineno, tok);
1524 			return -ENOTSUP;
1525 		}
1526 	} else {
1527 		fprintf(stderr, "#%i ERR: Unsupported instruction '%s'!\n",
1528 			cmd->lineno, tok);
1529 		return -ENOTSUP;
1530 	}
1531 
1532 	/*
1533 	 * Here we have at least one section with one command, otherwise we
1534 	 * would have failed already higher above.
1535 	 *
1536 	 * FIXME -- should the updating happen here ?
1537 	 */
1538 	if (ictx->in_section && !ret) {
1539 		ictx->sect_tail->size += ictx->sect_tail->cmd_tail->size;
1540 		ictx->sect_tail->payload.section_size =
1541 			ictx->sect_tail->size / SB_BLOCK_SIZE;
1542 	}
1543 
1544 	return ret;
1545 }
1546 
1547 static int sb_load_cmdfile(struct sb_image_ctx *ictx)
1548 {
1549 	struct sb_cmd_list cmd;
1550 	int lineno = 1;
1551 	FILE *fp;
1552 	char *line = NULL;
1553 	ssize_t rlen;
1554 	size_t len;
1555 
1556 	fp = fopen(ictx->cfg_filename, "r");
1557 	if (!fp)
1558 		goto err_file;
1559 
1560 	while ((rlen = getline(&line, &len, fp)) > 0) {
1561 		memset(&cmd, 0, sizeof(cmd));
1562 
1563 		/* Strip the trailing newline. */
1564 		line[rlen - 1] = '\0';
1565 
1566 		cmd.cmd = line;
1567 		cmd.len = rlen;
1568 		cmd.lineno = lineno++;
1569 
1570 		sb_parse_line(ictx, &cmd);
1571 	}
1572 
1573 	free(line);
1574 
1575 	fclose(fp);
1576 
1577 	return 0;
1578 
1579 err_file:
1580 	fclose(fp);
1581 	fprintf(stderr, "ERR: Failed to load file \"%s\"\n",
1582 		ictx->cfg_filename);
1583 	return -EINVAL;
1584 }
1585 
1586 static int sb_build_tree_from_cfg(struct sb_image_ctx *ictx)
1587 {
1588 	int ret;
1589 
1590 	ret = sb_load_cmdfile(ictx);
1591 	if (ret)
1592 		return ret;
1593 
1594 	ret = sb_prefill_image_header(ictx);
1595 	if (ret)
1596 		return ret;
1597 
1598 	ret = sb_postfill_image_header(ictx);
1599 	if (ret)
1600 		return ret;
1601 
1602 	ret = sb_fixup_sections_and_tags(ictx);
1603 	if (ret)
1604 		return ret;
1605 
1606 	return 0;
1607 }
1608 
1609 static int sb_verify_image_header(struct sb_image_ctx *ictx,
1610 				  FILE *fp, long fsize)
1611 {
1612 	/* Verify static fields in the image header. */
1613 	struct sb_boot_image_header *hdr = &ictx->payload;
1614 	const char *stat[2] = { "[PASS]", "[FAIL]" };
1615 	struct tm tm;
1616 	int sz, ret = 0;
1617 	unsigned char digest[20];
1618 	EVP_MD_CTX md_ctx;
1619 	unsigned long size;
1620 
1621 	/* Start image-wide crypto. */
1622 	EVP_MD_CTX_init(&ictx->md_ctx);
1623 	EVP_DigestInit(&ictx->md_ctx, EVP_sha1());
1624 
1625 	soprintf(ictx, "---------- Verifying SB Image Header ----------\n");
1626 
1627 	size = fread(&ictx->payload, 1, sizeof(ictx->payload), fp);
1628 	if (size != sizeof(ictx->payload)) {
1629 		fprintf(stderr, "ERR: SB image header too short!\n");
1630 		return -EINVAL;
1631 	}
1632 
1633 	/* Compute header digest. */
1634 	EVP_MD_CTX_init(&md_ctx);
1635 	EVP_DigestInit(&md_ctx, EVP_sha1());
1636 	EVP_DigestUpdate(&md_ctx, hdr->signature1,
1637 			 sizeof(struct sb_boot_image_header) -
1638 			 sizeof(hdr->digest));
1639 	EVP_DigestFinal(&md_ctx, digest, NULL);
1640 
1641 	sb_aes_init(ictx, NULL, 1);
1642 	sb_encrypt_sb_header(ictx);
1643 
1644 	if (memcmp(digest, hdr->digest, 20))
1645 		ret = -EINVAL;
1646 	soprintf(ictx, "%s Image header checksum:        %s\n", stat[!!ret],
1647 		 ret ? "BAD" : "OK");
1648 	if (ret)
1649 		return ret;
1650 
1651 	if (memcmp(hdr->signature1, "STMP", 4) ||
1652 	    memcmp(hdr->signature2, "sgtl", 4))
1653 		ret = -EINVAL;
1654 	soprintf(ictx, "%s Signatures:                   '%.4s' '%.4s'\n",
1655 		 stat[!!ret], hdr->signature1, hdr->signature2);
1656 	if (ret)
1657 		return ret;
1658 
1659 	if ((hdr->major_version != SB_VERSION_MAJOR) ||
1660 	    ((hdr->minor_version != 1) && (hdr->minor_version != 2)))
1661 		ret = -EINVAL;
1662 	soprintf(ictx, "%s Image version:                v%i.%i\n", stat[!!ret],
1663 		 hdr->major_version, hdr->minor_version);
1664 	if (ret)
1665 		return ret;
1666 
1667 	ret = sb_get_time(hdr->timestamp_us / 1000000, &tm);
1668 	soprintf(ictx,
1669 		 "%s Creation time:                %02i:%02i:%02i %02i/%02i/%04i\n",
1670 		 stat[!!ret], tm.tm_hour, tm.tm_min, tm.tm_sec,
1671 		 tm.tm_mday, tm.tm_mon, tm.tm_year + 2000);
1672 	if (ret)
1673 		return ret;
1674 
1675 	soprintf(ictx, "%s Product version:              %x.%x.%x\n", stat[0],
1676 		 ntohs(hdr->product_version.major),
1677 		 ntohs(hdr->product_version.minor),
1678 		 ntohs(hdr->product_version.revision));
1679 	soprintf(ictx, "%s Component version:            %x.%x.%x\n", stat[0],
1680 		 ntohs(hdr->component_version.major),
1681 		 ntohs(hdr->component_version.minor),
1682 		 ntohs(hdr->component_version.revision));
1683 
1684 	if (hdr->flags & ~SB_IMAGE_FLAG_VERBOSE)
1685 		ret = -EINVAL;
1686 	soprintf(ictx, "%s Image flags:                  %s\n", stat[!!ret],
1687 		 hdr->flags & SB_IMAGE_FLAG_VERBOSE ? "Verbose_boot" : "");
1688 	if (ret)
1689 		return ret;
1690 
1691 	if (hdr->drive_tag != 0)
1692 		ret = -EINVAL;
1693 	soprintf(ictx, "%s Drive tag:                    %i\n", stat[!!ret],
1694 		 hdr->drive_tag);
1695 	if (ret)
1696 		return ret;
1697 
1698 	sz = sizeof(struct sb_boot_image_header) / SB_BLOCK_SIZE;
1699 	if (hdr->header_blocks != sz)
1700 		ret = -EINVAL;
1701 	soprintf(ictx, "%s Image header size (blocks):   %i\n", stat[!!ret],
1702 		 hdr->header_blocks);
1703 	if (ret)
1704 		return ret;
1705 
1706 	sz = sizeof(struct sb_sections_header) / SB_BLOCK_SIZE;
1707 	if (hdr->section_header_size != sz)
1708 		ret = -EINVAL;
1709 	soprintf(ictx, "%s Section header size (blocks): %i\n", stat[!!ret],
1710 		 hdr->section_header_size);
1711 	if (ret)
1712 		return ret;
1713 
1714 	soprintf(ictx, "%s Sections count:               %i\n", stat[!!ret],
1715 		 hdr->section_count);
1716 	soprintf(ictx, "%s First bootable section        %i\n", stat[!!ret],
1717 		 hdr->first_boot_section_id);
1718 
1719 	if (hdr->image_blocks != fsize / SB_BLOCK_SIZE)
1720 		ret = -EINVAL;
1721 	soprintf(ictx, "%s Image size (blocks):          %i\n", stat[!!ret],
1722 		 hdr->image_blocks);
1723 	if (ret)
1724 		return ret;
1725 
1726 	sz = hdr->header_blocks + hdr->section_header_size * hdr->section_count;
1727 	if (hdr->key_dictionary_block != sz)
1728 		ret = -EINVAL;
1729 	soprintf(ictx, "%s Key dict offset (blocks):     %i\n", stat[!!ret],
1730 		 hdr->key_dictionary_block);
1731 	if (ret)
1732 		return ret;
1733 
1734 	if (hdr->key_count != 1)
1735 		ret = -EINVAL;
1736 	soprintf(ictx, "%s Number of encryption keys:    %i\n", stat[!!ret],
1737 		 hdr->key_count);
1738 	if (ret)
1739 		return ret;
1740 
1741 	sz = hdr->header_blocks + hdr->section_header_size * hdr->section_count;
1742 	sz += hdr->key_count *
1743 		sizeof(struct sb_key_dictionary_key) / SB_BLOCK_SIZE;
1744 	if (hdr->first_boot_tag_block != (unsigned)sz)
1745 		ret = -EINVAL;
1746 	soprintf(ictx, "%s First TAG block (blocks):     %i\n", stat[!!ret],
1747 		 hdr->first_boot_tag_block);
1748 	if (ret)
1749 		return ret;
1750 
1751 	return 0;
1752 }
1753 
1754 static void sb_decrypt_tag(struct sb_image_ctx *ictx,
1755 		struct sb_cmd_ctx *cctx)
1756 {
1757 	EVP_MD_CTX *md_ctx = &ictx->md_ctx;
1758 	struct sb_command *cmd = &cctx->payload;
1759 
1760 	sb_aes_crypt(ictx, (uint8_t *)&cctx->c_payload,
1761 		     (uint8_t *)&cctx->payload, sizeof(*cmd));
1762 	EVP_DigestUpdate(md_ctx, &cctx->c_payload, sizeof(*cmd));
1763 }
1764 
1765 static int sb_verify_command(struct sb_image_ctx *ictx,
1766 			     struct sb_cmd_ctx *cctx, FILE *fp,
1767 			     unsigned long *tsize)
1768 {
1769 	struct sb_command *ccmd = &cctx->payload;
1770 	unsigned long size, asize;
1771 	char *csum, *flag = "";
1772 	int ret;
1773 	unsigned int i;
1774 	uint8_t csn, csc = ccmd->header.checksum;
1775 	ccmd->header.checksum = 0x5a;
1776 	csn = sb_command_checksum(ccmd);
1777 	ccmd->header.checksum = csc;
1778 
1779 	if (csc == csn)
1780 		ret = 0;
1781 	else
1782 		ret = -EINVAL;
1783 	csum = ret ? "checksum BAD" : "checksum OK";
1784 
1785 	switch (ccmd->header.tag) {
1786 	case ROM_NOP_CMD:
1787 		soprintf(ictx, " NOOP # %s\n", csum);
1788 		return ret;
1789 	case ROM_TAG_CMD:
1790 		if (ccmd->header.flags & ROM_TAG_CMD_FLAG_ROM_LAST_TAG)
1791 			flag = "LAST";
1792 		soprintf(ictx, " TAG %s # %s\n", flag, csum);
1793 		sb_aes_reinit(ictx, 0);
1794 		return ret;
1795 	case ROM_LOAD_CMD:
1796 		soprintf(ictx, " LOAD addr=0x%08x length=0x%08x # %s\n",
1797 			 ccmd->load.address, ccmd->load.count, csum);
1798 
1799 		cctx->length = ccmd->load.count;
1800 		asize = roundup(cctx->length, SB_BLOCK_SIZE);
1801 		cctx->data = malloc(asize);
1802 		if (!cctx->data)
1803 			return -ENOMEM;
1804 
1805 		size = fread(cctx->data, 1, asize, fp);
1806 		if (size != asize) {
1807 			fprintf(stderr,
1808 				"ERR: SB LOAD command payload too short!\n");
1809 			return -EINVAL;
1810 		}
1811 
1812 		*tsize += size;
1813 
1814 		EVP_DigestUpdate(&ictx->md_ctx, cctx->data, asize);
1815 		sb_aes_crypt(ictx, cctx->data, cctx->data, asize);
1816 
1817 		if (ccmd->load.crc32 != pbl_crc32(0,
1818 						  (const char *)cctx->data,
1819 						  asize)) {
1820 			fprintf(stderr,
1821 				"ERR: SB LOAD command payload CRC32 invalid!\n");
1822 			return -EINVAL;
1823 		}
1824 		return 0;
1825 	case ROM_FILL_CMD:
1826 		soprintf(ictx,
1827 			 " FILL addr=0x%08x length=0x%08x pattern=0x%08x # %s\n",
1828 			 ccmd->fill.address, ccmd->fill.count,
1829 			 ccmd->fill.pattern, csum);
1830 		return 0;
1831 	case ROM_JUMP_CMD:
1832 		if (ccmd->header.flags & ROM_JUMP_CMD_FLAG_HAB)
1833 			flag = " HAB";
1834 		soprintf(ictx,
1835 			 " JUMP%s addr=0x%08x r0_arg=0x%08x # %s\n",
1836 			 flag, ccmd->fill.address, ccmd->jump.argument, csum);
1837 		return 0;
1838 	case ROM_CALL_CMD:
1839 		if (ccmd->header.flags & ROM_CALL_CMD_FLAG_HAB)
1840 			flag = " HAB";
1841 		soprintf(ictx,
1842 			 " CALL%s addr=0x%08x r0_arg=0x%08x # %s\n",
1843 			 flag, ccmd->fill.address, ccmd->jump.argument, csum);
1844 		return 0;
1845 	case ROM_MODE_CMD:
1846 		for (i = 0; i < ARRAY_SIZE(modetable); i++) {
1847 			if (ccmd->mode.mode == modetable[i].mode) {
1848 				soprintf(ictx, " MODE %s # %s\n",
1849 					 modetable[i].name, csum);
1850 				break;
1851 			}
1852 		}
1853 		fprintf(stderr, " MODE !INVALID! # %s\n", csum);
1854 		return 0;
1855 	}
1856 
1857 	return ret;
1858 }
1859 
1860 static int sb_verify_commands(struct sb_image_ctx *ictx,
1861 			      struct sb_section_ctx *sctx, FILE *fp)
1862 {
1863 	unsigned long size, tsize = 0;
1864 	struct sb_cmd_ctx *cctx;
1865 	int ret;
1866 
1867 	sb_aes_reinit(ictx, 0);
1868 
1869 	while (tsize < sctx->size) {
1870 		cctx = calloc(1, sizeof(*cctx));
1871 		if (!cctx)
1872 			return -ENOMEM;
1873 		if (!sctx->cmd_head) {
1874 			sctx->cmd_head = cctx;
1875 			sctx->cmd_tail = cctx;
1876 		} else {
1877 			sctx->cmd_tail->cmd = cctx;
1878 			sctx->cmd_tail = cctx;
1879 		}
1880 
1881 		size = fread(&cctx->c_payload, 1, sizeof(cctx->c_payload), fp);
1882 		if (size != sizeof(cctx->c_payload)) {
1883 			fprintf(stderr, "ERR: SB command header too short!\n");
1884 			return -EINVAL;
1885 		}
1886 
1887 		tsize += size;
1888 
1889 		sb_decrypt_tag(ictx, cctx);
1890 
1891 		ret = sb_verify_command(ictx, cctx, fp, &tsize);
1892 		if (ret)
1893 			return -EINVAL;
1894 	}
1895 
1896 	return 0;
1897 }
1898 
1899 static int sb_verify_sections_cmds(struct sb_image_ctx *ictx, FILE *fp)
1900 {
1901 	struct sb_boot_image_header *hdr = &ictx->payload;
1902 	struct sb_sections_header *shdr;
1903 	unsigned int i;
1904 	int ret;
1905 	struct sb_section_ctx *sctx;
1906 	unsigned long size;
1907 	char *bootable = "";
1908 
1909 	soprintf(ictx, "----- Verifying  SB Sections and Commands -----\n");
1910 
1911 	for (i = 0; i < hdr->section_count; i++) {
1912 		sctx = calloc(1, sizeof(*sctx));
1913 		if (!sctx)
1914 			return -ENOMEM;
1915 		if (!ictx->sect_head) {
1916 			ictx->sect_head = sctx;
1917 			ictx->sect_tail = sctx;
1918 		} else {
1919 			ictx->sect_tail->sect = sctx;
1920 			ictx->sect_tail = sctx;
1921 		}
1922 
1923 		size = fread(&sctx->payload, 1, sizeof(sctx->payload), fp);
1924 		if (size != sizeof(sctx->payload)) {
1925 			fprintf(stderr, "ERR: SB section header too short!\n");
1926 			return -EINVAL;
1927 		}
1928 	}
1929 
1930 	size = fread(&ictx->sb_dict_key, 1, sizeof(ictx->sb_dict_key), fp);
1931 	if (size != sizeof(ictx->sb_dict_key)) {
1932 		fprintf(stderr, "ERR: SB key dictionary too short!\n");
1933 		return -EINVAL;
1934 	}
1935 
1936 	sb_encrypt_sb_sections_header(ictx);
1937 	sb_aes_reinit(ictx, 0);
1938 	sb_decrypt_key_dictionary_key(ictx);
1939 
1940 	sb_aes_reinit(ictx, 0);
1941 
1942 	sctx = ictx->sect_head;
1943 	while (sctx) {
1944 		shdr = &sctx->payload;
1945 
1946 		if (shdr->section_flags & SB_SECTION_FLAG_BOOTABLE) {
1947 			sctx->boot = 1;
1948 			bootable = " BOOTABLE";
1949 		}
1950 
1951 		sctx->size = (shdr->section_size * SB_BLOCK_SIZE) +
1952 			     sizeof(struct sb_command);
1953 		soprintf(ictx, "SECTION 0x%x%s # size = %i bytes\n",
1954 			 shdr->section_number, bootable, sctx->size);
1955 
1956 		if (shdr->section_flags & ~SB_SECTION_FLAG_BOOTABLE)
1957 			fprintf(stderr, " WARN: Unknown section flag(s) %08x\n",
1958 				shdr->section_flags);
1959 
1960 		if ((shdr->section_flags & SB_SECTION_FLAG_BOOTABLE) &&
1961 		    (hdr->first_boot_section_id != shdr->section_number)) {
1962 			fprintf(stderr,
1963 				" WARN: Bootable section does ID not match image header ID!\n");
1964 		}
1965 
1966 		ret = sb_verify_commands(ictx, sctx, fp);
1967 		if (ret)
1968 			return ret;
1969 
1970 		sctx = sctx->sect;
1971 	}
1972 
1973 	/*
1974 	 * FIXME IDEA:
1975 	 * check if the first TAG command is at sctx->section_offset
1976 	 */
1977 	return 0;
1978 }
1979 
1980 static int sb_verify_image_end(struct sb_image_ctx *ictx,
1981 			       FILE *fp, off_t filesz)
1982 {
1983 	uint8_t digest[32];
1984 	unsigned long size;
1985 	off_t pos;
1986 	int ret;
1987 
1988 	soprintf(ictx, "------------- Verifying image end -------------\n");
1989 
1990 	size = fread(digest, 1, sizeof(digest), fp);
1991 	if (size != sizeof(digest)) {
1992 		fprintf(stderr, "ERR: SB key dictionary too short!\n");
1993 		return -EINVAL;
1994 	}
1995 
1996 	pos = ftell(fp);
1997 	if (pos != filesz) {
1998 		fprintf(stderr, "ERR: Trailing data past the image!\n");
1999 		return -EINVAL;
2000 	}
2001 
2002 	/* Check the image digest. */
2003 	EVP_DigestFinal(&ictx->md_ctx, ictx->digest, NULL);
2004 
2005 	/* Decrypt the image digest from the input image. */
2006 	sb_aes_reinit(ictx, 0);
2007 	sb_aes_crypt(ictx, digest, digest, sizeof(digest));
2008 
2009 	/* Check all of 20 bytes of the SHA1 hash. */
2010 	ret = memcmp(digest, ictx->digest, 20) ? -EINVAL : 0;
2011 
2012 	if (ret)
2013 		soprintf(ictx, "[FAIL] Full-image checksum:          BAD\n");
2014 	else
2015 		soprintf(ictx, "[PASS] Full-image checksum:          OK\n");
2016 
2017 	return ret;
2018 }
2019 
2020 
2021 static int sb_build_tree_from_img(struct sb_image_ctx *ictx)
2022 {
2023 	long filesize;
2024 	int ret;
2025 	FILE *fp;
2026 
2027 	if (!ictx->input_filename) {
2028 		fprintf(stderr, "ERR: Missing filename!\n");
2029 		return -EINVAL;
2030 	}
2031 
2032 	fp = fopen(ictx->input_filename, "r");
2033 	if (!fp)
2034 		goto err_open;
2035 
2036 	ret = fseek(fp, 0, SEEK_END);
2037 	if (ret < 0)
2038 		goto err_file;
2039 
2040 	filesize = ftell(fp);
2041 	if (filesize < 0)
2042 		goto err_file;
2043 
2044 	ret = fseek(fp, 0, SEEK_SET);
2045 	if (ret < 0)
2046 		goto err_file;
2047 
2048 	if (filesize < (signed)sizeof(ictx->payload)) {
2049 		fprintf(stderr, "ERR: File too short!\n");
2050 		goto err_file;
2051 	}
2052 
2053 	if (filesize & (SB_BLOCK_SIZE - 1)) {
2054 		fprintf(stderr, "ERR: The file is not aligned!\n");
2055 		goto err_file;
2056 	}
2057 
2058 	/* Load and verify image header */
2059 	ret = sb_verify_image_header(ictx, fp, filesize);
2060 	if (ret)
2061 		goto err_verify;
2062 
2063 	/* Load and verify sections and commands */
2064 	ret = sb_verify_sections_cmds(ictx, fp);
2065 	if (ret)
2066 		goto err_verify;
2067 
2068 	ret = sb_verify_image_end(ictx, fp, filesize);
2069 	if (ret)
2070 		goto err_verify;
2071 
2072 	ret = 0;
2073 
2074 err_verify:
2075 	soprintf(ictx, "-------------------- Result -------------------\n");
2076 	soprintf(ictx, "Verification %s\n", ret ? "FAILED" : "PASSED");
2077 
2078 	/* Stop the encryption session. */
2079 	sb_aes_deinit(&ictx->cipher_ctx);
2080 
2081 	fclose(fp);
2082 	return ret;
2083 
2084 err_file:
2085 	fclose(fp);
2086 err_open:
2087 	fprintf(stderr, "ERR: Failed to load file \"%s\"\n",
2088 		ictx->input_filename);
2089 	return -EINVAL;
2090 }
2091 
2092 static void sb_free_image(struct sb_image_ctx *ictx)
2093 {
2094 	struct sb_section_ctx *sctx = ictx->sect_head, *s_head;
2095 	struct sb_dcd_ctx *dctx = ictx->dcd_head, *d_head;
2096 	struct sb_cmd_ctx *cctx, *c_head;
2097 
2098 	while (sctx) {
2099 		s_head = sctx;
2100 		c_head = sctx->cmd_head;
2101 
2102 		while (c_head) {
2103 			cctx = c_head;
2104 			c_head = c_head->cmd;
2105 			if (cctx->data)
2106 				free(cctx->data);
2107 			free(cctx);
2108 		}
2109 
2110 		sctx = sctx->sect;
2111 		free(s_head);
2112 	}
2113 
2114 	while (dctx) {
2115 		d_head = dctx;
2116 		dctx = dctx->dcd;
2117 		free(d_head->payload);
2118 		free(d_head);
2119 	}
2120 }
2121 
2122 /*
2123  * MXSSB-MKIMAGE glue code.
2124  */
2125 static int mxsimage_check_image_types(uint8_t type)
2126 {
2127 	if (type == IH_TYPE_MXSIMAGE)
2128 		return EXIT_SUCCESS;
2129 	else
2130 		return EXIT_FAILURE;
2131 }
2132 
2133 static void mxsimage_set_header(void *ptr, struct stat *sbuf, int ifd,
2134 				struct image_tool_params *params)
2135 {
2136 }
2137 
2138 int mxsimage_check_params(struct image_tool_params *params)
2139 {
2140 	if (!params)
2141 		return -1;
2142 	if (!strlen(params->imagename)) {
2143 		fprintf(stderr,
2144 			"Error: %s - Configuration file not specified, it is needed for mxsimage generation\n",
2145 			params->cmdname);
2146 		return -1;
2147 	}
2148 
2149 	/*
2150 	 * Check parameters:
2151 	 * XIP is not allowed and verify that incompatible
2152 	 * parameters are not sent at the same time
2153 	 * For example, if list is required a data image must not be provided
2154 	 */
2155 	return	(params->dflag && (params->fflag || params->lflag)) ||
2156 		(params->fflag && (params->dflag || params->lflag)) ||
2157 		(params->lflag && (params->dflag || params->fflag)) ||
2158 		(params->xflag) || !(strlen(params->imagename));
2159 }
2160 
2161 static int mxsimage_verify_print_header(char *file, int silent)
2162 {
2163 	int ret;
2164 	struct sb_image_ctx ctx;
2165 
2166 	memset(&ctx, 0, sizeof(ctx));
2167 
2168 	ctx.input_filename = file;
2169 	ctx.silent_dump = silent;
2170 
2171 	ret = sb_build_tree_from_img(&ctx);
2172 	sb_free_image(&ctx);
2173 
2174 	return ret;
2175 }
2176 
2177 char *imagefile;
2178 static int mxsimage_verify_header(unsigned char *ptr, int image_size,
2179 			struct image_tool_params *params)
2180 {
2181 	struct sb_boot_image_header *hdr;
2182 
2183 	if (!ptr)
2184 		return -EINVAL;
2185 
2186 	hdr = (struct sb_boot_image_header *)ptr;
2187 
2188 	/*
2189 	 * Check if the header contains the MXS image signatures,
2190 	 * if so, do a full-image verification.
2191 	 */
2192 	if (memcmp(hdr->signature1, "STMP", 4) ||
2193 	    memcmp(hdr->signature2, "sgtl", 4))
2194 		return -EINVAL;
2195 
2196 	imagefile = params->imagefile;
2197 
2198 	return mxsimage_verify_print_header(params->imagefile, 1);
2199 }
2200 
2201 static void mxsimage_print_header(const void *hdr)
2202 {
2203 	if (imagefile)
2204 		mxsimage_verify_print_header(imagefile, 0);
2205 }
2206 
2207 static int sb_build_image(struct sb_image_ctx *ictx,
2208 			  struct image_type_params *tparams)
2209 {
2210 	struct sb_boot_image_header *sb_header = &ictx->payload;
2211 	struct sb_section_ctx *sctx;
2212 	struct sb_cmd_ctx *cctx;
2213 	struct sb_command *ccmd;
2214 	struct sb_key_dictionary_key *sb_dict_key = &ictx->sb_dict_key;
2215 
2216 	uint8_t *image, *iptr;
2217 
2218 	/* Calculate image size. */
2219 	uint32_t size = sizeof(*sb_header) +
2220 		ictx->sect_count * sizeof(struct sb_sections_header) +
2221 		sizeof(*sb_dict_key) + sizeof(ictx->digest);
2222 
2223 	sctx = ictx->sect_head;
2224 	while (sctx) {
2225 		size += sctx->size;
2226 		sctx = sctx->sect;
2227 	};
2228 
2229 	image = malloc(size);
2230 	if (!image)
2231 		return -ENOMEM;
2232 	iptr = image;
2233 
2234 	memcpy(iptr, sb_header, sizeof(*sb_header));
2235 	iptr += sizeof(*sb_header);
2236 
2237 	sctx = ictx->sect_head;
2238 	while (sctx) {
2239 		memcpy(iptr, &sctx->payload, sizeof(struct sb_sections_header));
2240 		iptr += sizeof(struct sb_sections_header);
2241 		sctx = sctx->sect;
2242 	};
2243 
2244 	memcpy(iptr, sb_dict_key, sizeof(*sb_dict_key));
2245 	iptr += sizeof(*sb_dict_key);
2246 
2247 	sctx = ictx->sect_head;
2248 	while (sctx) {
2249 		cctx = sctx->cmd_head;
2250 		while (cctx) {
2251 			ccmd = &cctx->payload;
2252 
2253 			memcpy(iptr, &cctx->c_payload, sizeof(cctx->payload));
2254 			iptr += sizeof(cctx->payload);
2255 
2256 			if (ccmd->header.tag == ROM_LOAD_CMD) {
2257 				memcpy(iptr, cctx->data, cctx->length);
2258 				iptr += cctx->length;
2259 			}
2260 
2261 			cctx = cctx->cmd;
2262 		}
2263 
2264 		sctx = sctx->sect;
2265 	};
2266 
2267 	memcpy(iptr, ictx->digest, sizeof(ictx->digest));
2268 	iptr += sizeof(ictx->digest);
2269 
2270 	/* Configure the mkimage */
2271 	tparams->hdr = image;
2272 	tparams->header_size = size;
2273 
2274 	return 0;
2275 }
2276 
2277 static int mxsimage_generate(struct image_tool_params *params,
2278 	struct image_type_params *tparams)
2279 {
2280 	int ret;
2281 	struct sb_image_ctx ctx;
2282 
2283 	/* Do not copy the U-Boot image! */
2284 	params->skipcpy = 1;
2285 
2286 	memset(&ctx, 0, sizeof(ctx));
2287 
2288 	ctx.cfg_filename = params->imagename;
2289 	ctx.output_filename = params->imagefile;
2290 	ctx.verbose_boot = 1;
2291 
2292 	ret = sb_build_tree_from_cfg(&ctx);
2293 	if (ret)
2294 		goto fail;
2295 
2296 	ret = sb_encrypt_image(&ctx);
2297 	if (!ret)
2298 		ret = sb_build_image(&ctx, tparams);
2299 
2300 fail:
2301 	sb_free_image(&ctx);
2302 
2303 	return ret;
2304 }
2305 
2306 /*
2307  * mxsimage parameters
2308  */
2309 static struct image_type_params mxsimage_params = {
2310 	.name		= "Freescale MXS Boot Image support",
2311 	.header_size	= 0,
2312 	.hdr		= NULL,
2313 	.check_image_type = mxsimage_check_image_types,
2314 	.verify_header	= mxsimage_verify_header,
2315 	.print_header	= mxsimage_print_header,
2316 	.set_header	= mxsimage_set_header,
2317 	.check_params	= mxsimage_check_params,
2318 	.vrec_header	= mxsimage_generate,
2319 };
2320 
2321 void init_mxs_image_type(void)
2322 {
2323 	register_image_type(&mxsimage_params);
2324 }
2325 
2326 #else
2327 void init_mxs_image_type(void)
2328 {
2329 }
2330 #endif
2331