// SPDX-License-Identifier: GPL-2.0+
/*
 * Copyright (c) 2013, Google Inc.
 * Written by Simon Glass <sjg@chromium.org>
 *
 * Perform a grep of an FDT either displaying the source subset or producing
 * a new .dtb subset which can be used as required.
 */

#include <assert.h>
#include <ctype.h>
#include <errno.h>
#include <getopt.h>
#include <fcntl.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fdt_region.h>

#include "fdt_host.h"
#include "libfdt_internal.h"

/* Define DEBUG to get some debugging output on stderr */
#ifdef DEBUG
#define debug(a, b...) fprintf(stderr, a, ## b)
#else
#define debug(a, b...)
#endif

/* A linked list of values we are grepping for */
struct value_node {
	int type;		/* Types this value matches (FDT_IS... mask) */
	int include;		/* 1 to include matches, 0 to exclude */
	const char *string;	/* String to match */
	struct value_node *next;	/* Pointer to next node, or NULL */
};

/* Output formats we support */
enum output_t {
	OUT_DTS,		/* Device tree source */
	OUT_DTB,		/* Valid device tree binary */
	OUT_BIN,		/* Fragment of .dtb, for hashing */
};

/* Holds information which controls our output and options */
struct display_info {
	enum output_t output;	/* Output format */
	int add_aliases;	/* Add aliases node to output */
	int all;		/* Display all properties/nodes */
	int colour;		/* Display output in ANSI colour */
	int region_list;	/* Output a region list */
	int flags;		/* Flags (FDT_REG_...) */
	int list_strings;	/* List strings in string table */
	int show_offset;	/* Show offset */
	int show_addr;		/* Show address */
	int header;		/* Output an FDT header */
	int diff;		/* Show +/- diff markers */
	int include_root;	/* Include the root node and all properties */
	int remove_strings;	/* Remove unused strings */
	int show_dts_version;	/* Put '/dts-v1/;' on the first line */
	int types_inc;		/* Mask of types that we include (FDT_IS...) */
	int types_exc;		/* Mask of types that we exclude (FDT_IS...) */
	int invert;		/* Invert polarity of match */
	struct value_node *value_head;	/* List of values to match */
	const char *output_fname;	/* Output filename */
	FILE *fout;		/* File to write dts/dtb output */
};

static void report_error(const char *where, int err)
{
	fprintf(stderr, "Error at '%s': %s\n", where, fdt_strerror(err));
}

/* Supported ANSI colours */
enum {
	COL_BLACK,
	COL_RED,
	COL_GREEN,
	COL_YELLOW,
	COL_BLUE,
	COL_MAGENTA,
	COL_CYAN,
	COL_WHITE,

	COL_NONE = -1,
};

/**
 * print_ansi_colour() - Print out the ANSI sequence for a colour
 *
 * @fout:	Output file
 * @col:	Colour to output (COL_...), or COL_NONE to reset colour
 */
static void print_ansi_colour(FILE *fout, int col)
{
	if (col == COL_NONE)
		fprintf(fout, "\033[0m");
	else
		fprintf(fout, "\033[1;%dm", col + 30);
}


/**
 * value_add() - Add a new value to our list of things to grep for
 *
 * @disp:	Display structure, holding info about our options
 * @headp:	Pointer to header pointer of list
 * @type:	Type of this value (FDT_IS_...)
 * @include:	1 if we want to include matches, 0 to exclude
 * @str:	String value to match
 */
static int value_add(struct display_info *disp, struct value_node **headp,
		     int type, int include, const char *str)
{
	struct value_node *node;

	/*
	 * Keep track of which types we are excluding/including. We don't
	 * allow both including and excluding things, because it doesn't make
	 * sense. 'Including' means that everything not mentioned is
	 * excluded. 'Excluding' means that everything not mentioned is
	 * included. So using the two together would be meaningless.
	 */
	if (include)
		disp->types_inc |= type;
	else
		disp->types_exc |= type;
	if (disp->types_inc & disp->types_exc & type) {
		fprintf(stderr,
			"Cannot use both include and exclude for '%s'\n", str);
		return -1;
	}

	str = strdup(str);
	if (!str)
		goto err_mem;
	node = malloc(sizeof(*node));
	if (!node)
		goto err_mem;
	node->next = *headp;
	node->type = type;
	node->include = include;
	node->string = str;
	*headp = node;

	return 0;
err_mem:
	fprintf(stderr, "Out of memory\n");
	return -1;
}

static bool util_is_printable_string(const void *data, int len)
{
	const char *s = data;
	const char *ss, *se;

	/* zero length is not */
	if (len == 0)
		return 0;

	/* must terminate with zero */
	if (s[len - 1] != '\0')
		return 0;

	se = s + len;

	while (s < se) {
		ss = s;
		while (s < se && *s && isprint((unsigned char)*s))
			s++;

		/* not zero, or not done yet */
		if (*s != '\0' || s == ss)
			return 0;

		s++;
	}

	return 1;
}

static void utilfdt_print_data(const char *data, int len)
{
	int i;
	const char *p = data;
	const char *s;

	/* no data, don't print */
	if (len == 0)
		return;

	if (util_is_printable_string(data, len)) {
		printf(" = ");

		s = data;
		do {
			printf("\"%s\"", s);
			s += strlen(s) + 1;
			if (s < data + len)
				printf(", ");
		} while (s < data + len);

	} else if ((len % 4) == 0) {
		const uint32_t *cell = (const uint32_t *)data;

		printf(" = <");
		for (i = 0, len /= 4; i < len; i++)
			printf("0x%08x%s", fdt32_to_cpu(cell[i]),
			       i < (len - 1) ? " " : "");
		printf(">");
	} else {
		printf(" = [");
		for (i = 0; i < len; i++)
			printf("%02x%s", (unsigned char)*p++, i < len - 1 ? " " : "");
		printf("]");
	}
}

/**
 * display_fdt_by_regions() - Display regions of an FDT source
 *
 * This dumps an FDT as source, but only certain regions of it. This is the
 * final stage of the grep - we have a list of regions we want to display,
 * and this function displays them.
 *
 * @disp:	Display structure, holding info about our options
 * @blob:	FDT blob to display
 * @region:	List of regions to display
 * @count:	Number of regions
 */
static int display_fdt_by_regions(struct display_info *disp, const void *blob,
		struct fdt_region region[], int count)
{
	struct fdt_region *reg = region, *reg_end = region + count;
	uint32_t off_mem_rsvmap = fdt_off_mem_rsvmap(blob);
	int base = fdt_off_dt_struct(blob);
	int version = fdt_version(blob);
	int offset, nextoffset;
	int tag, depth, shift;
	FILE *f = disp->fout;
	uint64_t addr, size;
	int in_region;
	int file_ofs;
	int i;

	if (disp->show_dts_version)
		fprintf(f, "/dts-v1/;\n");

	if (disp->header) {
		fprintf(f, "// magic:\t\t0x%x\n", fdt_magic(blob));
		fprintf(f, "// totalsize:\t\t0x%x (%d)\n", fdt_totalsize(blob),
			fdt_totalsize(blob));
		fprintf(f, "// off_dt_struct:\t0x%x\n",
			fdt_off_dt_struct(blob));
		fprintf(f, "// off_dt_strings:\t0x%x\n",
			fdt_off_dt_strings(blob));
		fprintf(f, "// off_mem_rsvmap:\t0x%x\n", off_mem_rsvmap);
		fprintf(f, "// version:\t\t%d\n", version);
		fprintf(f, "// last_comp_version:\t%d\n",
			fdt_last_comp_version(blob));
		if (version >= 2) {
			fprintf(f, "// boot_cpuid_phys:\t0x%x\n",
				fdt_boot_cpuid_phys(blob));
		}
		if (version >= 3) {
			fprintf(f, "// size_dt_strings:\t0x%x\n",
				fdt_size_dt_strings(blob));
		}
		if (version >= 17) {
			fprintf(f, "// size_dt_struct:\t0x%x\n",
				fdt_size_dt_struct(blob));
		}
		fprintf(f, "\n");
	}

	if (disp->flags & FDT_REG_ADD_MEM_RSVMAP) {
		const struct fdt_reserve_entry *p_rsvmap;

		p_rsvmap = (const struct fdt_reserve_entry *)
				((const char *)blob + off_mem_rsvmap);
		for (i = 0; ; i++) {
			addr = fdt64_to_cpu(p_rsvmap[i].address);
			size = fdt64_to_cpu(p_rsvmap[i].size);
			if (addr == 0 && size == 0)
				break;

			fprintf(f, "/memreserve/ %llx %llx;\n",
				(unsigned long long)addr,
				(unsigned long long)size);
		}
	}

	depth = 0;
	nextoffset = 0;
	shift = 4;	/* 4 spaces per indent */
	do {
		const struct fdt_property *prop;
		const char *name;
		int show;
		int len;

		offset = nextoffset;

		/*
		 * Work out the file offset of this offset, and decide
		 * whether it is in the region list or not
		 */
		file_ofs = base + offset;
		if (reg < reg_end && file_ofs >= reg->offset + reg->size)
			reg++;
		in_region = reg < reg_end && file_ofs >= reg->offset &&
				file_ofs < reg->offset + reg->size;
		tag = fdt_next_tag(blob, offset, &nextoffset);

		if (tag == FDT_END)
			break;
		show = in_region || disp->all;
		if (show && disp->diff)
			fprintf(f, "%c", in_region ? '+' : '-');

		if (!show) {
			/* Do this here to avoid 'if (show)' in every 'case' */
			if (tag == FDT_BEGIN_NODE)
				depth++;
			else if (tag == FDT_END_NODE)
				depth--;
			continue;
		}
		if (tag != FDT_END) {
			if (disp->show_addr)
				fprintf(f, "%4x: ", file_ofs);
			if (disp->show_offset)
				fprintf(f, "%4x: ", file_ofs - base);
		}

		/* Green means included, red means excluded */
		if (disp->colour)
			print_ansi_colour(f, in_region ? COL_GREEN : COL_RED);

		switch (tag) {
		case FDT_PROP:
			prop = fdt_get_property_by_offset(blob, offset, NULL);
			name = fdt_string(blob, fdt32_to_cpu(prop->nameoff));
			fprintf(f, "%*s%s", depth * shift, "", name);
			utilfdt_print_data(prop->data,
					   fdt32_to_cpu(prop->len));
			fprintf(f, ";");
			break;

		case FDT_NOP:
			fprintf(f, "%*s// [NOP]", depth * shift, "");
			break;

		case FDT_BEGIN_NODE:
			name = fdt_get_name(blob, offset, &len);
			fprintf(f, "%*s%s {", depth++ * shift, "",
				*name ? name : "/");
			break;

		case FDT_END_NODE:
			fprintf(f, "%*s};", --depth * shift, "");
			break;
		}

		/* Reset colour back to normal before end of line */
		if (disp->colour)
			print_ansi_colour(f, COL_NONE);
		fprintf(f, "\n");
	} while (1);

	/* Print a list of strings if requested */
	if (disp->list_strings) {
		const char *str;
		int str_base = fdt_off_dt_strings(blob);

		for (offset = 0; offset < fdt_size_dt_strings(blob);
				offset += strlen(str) + 1) {
			str = fdt_string(blob, offset);
			int len = strlen(str) + 1;
			int show;

			/* Only print strings that are in the region */
			file_ofs = str_base + offset;
			in_region = reg < reg_end &&
					file_ofs >= reg->offset &&
					file_ofs + len < reg->offset +
						reg->size;
			show = in_region || disp->all;
			if (show && disp->diff)
				printf("%c", in_region ? '+' : '-');
			if (disp->show_addr)
				printf("%4x: ", file_ofs);
			if (disp->show_offset)
				printf("%4x: ", offset);
			printf("%s\n", str);
		}
	}

	return 0;
}

/**
 * dump_fdt_regions() - Dump regions of an FDT as binary data
 *
 * This dumps an FDT as binary, but only certain regions of it. This is the
 * final stage of the grep - we have a list of regions we want to dump,
 * and this function dumps them.
 *
 * The output of this function may or may not be a valid FDT. To ensure it
 * is, these disp->flags must be set:
 *
 *   FDT_REG_SUPERNODES: ensures that subnodes are preceded by their
 *		parents. Without this option, fragments of subnode data may be
 *		output without the supernodes above them. This is useful for
 *		hashing but cannot produce a valid FDT.
 *   FDT_REG_ADD_STRING_TAB: Adds a string table to the end of the FDT.
 *		Without this none of the properties will have names
 *   FDT_REG_ADD_MEM_RSVMAP: Adds a mem_rsvmap table - an FDT is invalid
 *		without this.
 *
 * @disp:	Display structure, holding info about our options
 * @blob:	FDT blob to display
 * @region:	List of regions to display
 * @count:	Number of regions
 * @out:	Output destination
 */
static int dump_fdt_regions(struct display_info *disp, const void *blob,
		struct fdt_region region[], int count, char *out)
{
	struct fdt_header *fdt;
	int size, struct_start;
	int ptr;
	int i;

	/* Set up a basic header (even if we don't actually write it) */
	fdt = (struct fdt_header *)out;
	memset(fdt, '\0', sizeof(*fdt));
	fdt_set_magic(fdt, FDT_MAGIC);
	struct_start = sizeof(struct fdt_header);
	fdt_set_off_mem_rsvmap(fdt, struct_start);
	fdt_set_version(fdt, FDT_LAST_SUPPORTED_VERSION);
	fdt_set_last_comp_version(fdt, FDT_FIRST_SUPPORTED_VERSION);

	/*
	 * Calculate the total size of the regions we are writing out. The
	 * first will be the mem_rsvmap if the FDT_REG_ADD_MEM_RSVMAP flag
	 * is set. The last will be the string table if FDT_REG_ADD_STRING_TAB
	 * is set.
	 */
	for (i = size = 0; i < count; i++)
		size += region[i].size;

	/* Bring in the mem_rsvmap section from the old file if requested */
	if (count > 0 && (disp->flags & FDT_REG_ADD_MEM_RSVMAP)) {
		struct_start += region[0].size;
		size -= region[0].size;
	}
	fdt_set_off_dt_struct(fdt, struct_start);

	/* Update the header to have the correct offsets/sizes */
	if (count >= 2 && (disp->flags & FDT_REG_ADD_STRING_TAB)) {
		int str_size;

		str_size = region[count - 1].size;
		fdt_set_size_dt_struct(fdt, size - str_size);
		fdt_set_off_dt_strings(fdt, struct_start + size - str_size);
		fdt_set_size_dt_strings(fdt, str_size);
		fdt_set_totalsize(fdt, struct_start + size);
	}

	/* Write the header if required */
	ptr = 0;
	if (disp->header) {
		ptr = sizeof(*fdt);
		while (ptr < fdt_off_mem_rsvmap(fdt))
			out[ptr++] = '\0';
	}

	/* Output all the nodes including any mem_rsvmap/string table */
	for (i = 0; i < count; i++) {
		struct fdt_region *reg = &region[i];

		memcpy(out + ptr, (const char *)blob + reg->offset, reg->size);
		ptr += reg->size;
	}

	return ptr;
}

/**
 * show_region_list() - Print out a list of regions
 *
 * The list includes the region offset (absolute offset from start of FDT
 * blob in bytes) and size
 *
 * @reg:	List of regions to print
 * @count:	Number of regions
 */
static void show_region_list(struct fdt_region *reg, int count)
{
	int i;

	printf("Regions: %d\n", count);
	for (i = 0; i < count; i++, reg++) {
		printf("%d:  %-10x  %-10x\n", i, reg->offset,
		       reg->offset + reg->size);
	}
}

static int check_type_include(void *priv, int type, const char *data, int size)
{
	struct display_info *disp = priv;
	struct value_node *val;
	int match, none_match = FDT_IS_ANY;

	/* If none of our conditions mention this type, we know nothing */
	debug("type=%x, data=%s\n", type, data ? data : "(null)");
	if (!((disp->types_inc | disp->types_exc) & type)) {
		debug("   - not in any condition\n");
		return -1;
	}

	/*
	 * Go through the list of conditions. For inclusive conditions, we
	 * return 1 at the first match. For exclusive conditions, we must
	 * check that there are no matches.
	 */
	if (data) {
		for (val = disp->value_head; val; val = val->next) {
			if (!(type & val->type))
				continue;
			match = fdt_stringlist_contains(data, size,
							val->string);
			debug("      - val->type=%x, str='%s', match=%d\n",
			      val->type, val->string, match);
			if (match && val->include) {
				debug("   - match inc %s\n", val->string);
				return 1;
			}
			if (match)
				none_match &= ~val->type;
		}
	}

	/*
	 * If this is an exclusive condition, and nothing matches, then we
	 * should return 1.
	 */
	if ((type & disp->types_exc) && (none_match & type)) {
		debug("   - match exc\n");
		/*
		 * Allow FDT_IS_COMPAT to make the final decision in the
		 * case where there is no specific type
		 */
		if (type == FDT_IS_NODE && disp->types_exc == FDT_ANY_GLOBAL) {
			debug("   - supressed exc node\n");
			return -1;
		}
		return 1;
	}

	/*
	 * Allow FDT_IS_COMPAT to make the final decision in the
	 * case where there is no specific type (inclusive)
	 */
	if (type == FDT_IS_NODE && disp->types_inc == FDT_ANY_GLOBAL)
		return -1;

	debug("   - no match, types_inc=%x, types_exc=%x, none_match=%x\n",
	      disp->types_inc, disp->types_exc, none_match);

	return 0;
}

/**
 * h_include() - Include handler function for fdt_find_regions()
 *
 * This function decides whether to include or exclude a node, property or
 * compatible string. The function is defined by fdt_find_regions().
 *
 * The algorithm is documented in the code - disp->invert is 0 for normal
 * operation, and 1 to invert the sense of all matches.
 *
 * See
 */
static int h_include(void *priv, const void *fdt, int offset, int type,
		     const char *data, int size)
{
	struct display_info *disp = priv;
	int inc, len;

	inc = check_type_include(priv, type, data, size);
	if (disp->include_root && type == FDT_IS_PROP && offset == 0 && inc)
		return 1;

	/*
	 * If the node name does not tell us anything, check the
	 * compatible string
	 */
	if (inc == -1 && type == FDT_IS_NODE) {
		debug("   - checking compatible2\n");
		data = fdt_getprop(fdt, offset, "compatible", &len);
		inc = check_type_include(priv, FDT_IS_COMPAT, data, len);
	}

	/* If we still have no idea, check for properties in the node */
	if (inc != 1 && type == FDT_IS_NODE &&
	    (disp->types_inc & FDT_NODE_HAS_PROP)) {
		debug("   - checking node '%s'\n",
		      fdt_get_name(fdt, offset, NULL));
		for (offset = fdt_first_property_offset(fdt, offset);
		     offset > 0 && inc != 1;
		     offset = fdt_next_property_offset(fdt, offset)) {
			const struct fdt_property *prop;
			const char *str;

			prop = fdt_get_property_by_offset(fdt, offset, NULL);
			if (!prop)
				continue;
			str = fdt_string(fdt, fdt32_to_cpu(prop->nameoff));
			inc = check_type_include(priv, FDT_NODE_HAS_PROP, str,
						 strlen(str));
		}
		if (inc == -1)
			inc = 0;
	}

	switch (inc) {
	case 1:
		inc = !disp->invert;
		break;
	case 0:
		inc = disp->invert;
		break;
	}
	debug("   - returning %d\n", inc);

	return inc;
}

static int h_cmp_region(const void *v1, const void *v2)
{
	const struct fdt_region *region1 = v1, *region2 = v2;

	return region1->offset - region2->offset;
}

static int fdtgrep_find_regions(const void *fdt,
		int (*include_func)(void *priv, const void *fdt, int offset,
				 int type, const char *data, int size),
		struct display_info *disp, struct fdt_region *region,
		int max_regions, char *path, int path_len, int flags)
{
	struct fdt_region_state state;
	int count;
	int ret;

	count = 0;
	ret = fdt_first_region(fdt, include_func, disp,
			&region[count++], path, path_len,
			disp->flags, &state);
	while (ret == 0) {
		ret = fdt_next_region(fdt, include_func, disp,
				count < max_regions ? &region[count] : NULL,
				path, path_len, disp->flags, &state);
		if (!ret)
			count++;
	}
	if (ret && ret != -FDT_ERR_NOTFOUND)
		return ret;

	/* Find all the aliases and add those regions back in */
	if (disp->add_aliases && count < max_regions) {
		int new_count;

		new_count = fdt_add_alias_regions(fdt, region, count,
						  max_regions, &state);
		if (new_count == -FDT_ERR_NOTFOUND) {
			/* No alias node found */
		} else if (new_count < 0) {
			return new_count;
		} else if (new_count <= max_regions) {
			/*
			* The alias regions will now be at the end of the list.
			* Sort the regions by offset to get things into the
			* right order
			*/
			count = new_count;
			qsort(region, count, sizeof(struct fdt_region),
			      h_cmp_region);
		}
	}

	return count;
}

int utilfdt_read_err_len(const char *filename, char **buffp, off_t *len)
{
	int fd = 0;	/* assume stdin */
	char *buf = NULL;
	off_t bufsize = 1024, offset = 0;
	int ret = 0;

	*buffp = NULL;
	if (strcmp(filename, "-") != 0) {
		fd = open(filename, O_RDONLY);
		if (fd < 0)
			return errno;
	}

	/* Loop until we have read everything */
	buf = malloc(bufsize);
	if (!buf)
		return -ENOMEM;
	do {
		/* Expand the buffer to hold the next chunk */
		if (offset == bufsize) {
			bufsize *= 2;
			buf = realloc(buf, bufsize);
			if (!buf)
				return -ENOMEM;
		}

		ret = read(fd, &buf[offset], bufsize - offset);
		if (ret < 0) {
			ret = errno;
			break;
		}
		offset += ret;
	} while (ret != 0);

	/* Clean up, including closing stdin; return errno on error */
	close(fd);
	if (ret)
		free(buf);
	else
		*buffp = buf;
	*len = bufsize;
	return ret;
}

int utilfdt_read_err(const char *filename, char **buffp)
{
	off_t len;
	return utilfdt_read_err_len(filename, buffp, &len);
}

char *utilfdt_read_len(const char *filename, off_t *len)
{
	char *buff;
	int ret = utilfdt_read_err_len(filename, &buff, len);

	if (ret) {
		fprintf(stderr, "Couldn't open blob from '%s': %s\n", filename,
			strerror(ret));
		return NULL;
	}
	/* Successful read */
	return buff;
}

char *utilfdt_read(const char *filename)
{
	off_t len;
	return utilfdt_read_len(filename, &len);
}

/**
 * Run the main fdtgrep operation, given a filename and valid arguments
 *
 * @param disp		Display information / options
 * @param filename	Filename of blob file
 * @param return 0 if ok, -ve on error
 */
static int do_fdtgrep(struct display_info *disp, const char *filename)
{
	struct fdt_region *region = NULL;
	int max_regions;
	int count = 100;
	char path[1024];
	char *blob;
	int i, ret;

	blob = utilfdt_read(filename);
	if (!blob)
		return -1;
	ret = fdt_check_header(blob);
	if (ret) {
		fprintf(stderr, "Error: %s\n", fdt_strerror(ret));
		return ret;
	}

	/* Allow old files, but they are untested */
	if (fdt_version(blob) < 17 && disp->value_head) {
		fprintf(stderr,
			"Warning: fdtgrep does not fully support version %d files\n",
			fdt_version(blob));
	}

	/*
	 * We do two passes, since we don't know how many regions we need.
	 * The first pass will count the regions, but if it is too many,
	 * we do another pass to actually record them.
	 */
	for (i = 0; i < 2; i++) {
		region = realloc(region, count * sizeof(struct fdt_region));
		if (!region) {
			fprintf(stderr, "Out of memory for %d regions\n",
				count);
			return -1;
		}
		max_regions = count;
		count = fdtgrep_find_regions(blob,
				h_include, disp,
				region, max_regions, path, sizeof(path),
				disp->flags);
		if (count < 0) {
			report_error("fdt_find_regions", count);
			free(region);
			return -1;
		}
		if (count <= max_regions)
			break;
	}
	if (count > max_regions) {
		free(region);
		fprintf(stderr, "Internal error with fdtgrep_find_region()\n");
		return -1;
	}

	/* Optionally print a list of regions */
	if (disp->region_list)
		show_region_list(region, count);

	/* Output either source .dts or binary .dtb */
	if (disp->output == OUT_DTS) {
		ret = display_fdt_by_regions(disp, blob, region, count);
	} else {
		void *fdt;
		/* Allow reserved memory section to expand slightly */
		int size = fdt_totalsize(blob) + 16;

		fdt = malloc(size);
		if (!fdt) {
			fprintf(stderr, "Out_of_memory\n");
			ret = -1;
			goto err;
		}
		size = dump_fdt_regions(disp, blob, region, count, fdt);
		if (disp->remove_strings) {
			void *out;

			out = malloc(size);
			if (!out) {
				fprintf(stderr, "Out_of_memory\n");
				ret = -1;
				goto err;
			}
			ret = fdt_remove_unused_strings(fdt, out);
			if (ret < 0) {
				fprintf(stderr,
					"Failed to remove unused strings: err=%d\n",
					ret);
				goto err;
			}
			free(fdt);
			fdt = out;
			ret = fdt_pack(fdt);
			if (ret < 0) {
				fprintf(stderr, "Failed to pack: err=%d\n",
					ret);
				goto err;
			}
			size = fdt_totalsize(fdt);
		}

		if (size != fwrite(fdt, 1, size, disp->fout)) {
			fprintf(stderr, "Write failure, %d bytes\n", size);
			free(fdt);
			ret = 1;
			goto err;
		}
		free(fdt);
	}
err:
	free(blob);
	free(region);

	return ret;
}

static const char usage_synopsis[] =
	"fdtgrep - extract portions from device tree\n"
	"\n"
	"Usage:\n"
	"	fdtgrep <options> <dt file>|-\n\n"
	"Output formats are:\n"
	"\tdts - device tree soure text\n"
	"\tdtb - device tree blob (sets -Hmt automatically)\n"
	"\tbin - device tree fragment (may not be a valid .dtb)";

/* Helper for usage_short_opts string constant */
#define USAGE_COMMON_SHORT_OPTS "hV"

/* Helper for aligning long_opts array */
#define a_argument required_argument

/* Helper for usage_long_opts option array */
#define USAGE_COMMON_LONG_OPTS \
	{"help",      no_argument, NULL, 'h'}, \
	{"version",   no_argument, NULL, 'V'}, \
	{NULL,        no_argument, NULL, 0x0}

/* Helper for usage_opts_help array */
#define USAGE_COMMON_OPTS_HELP \
	"Print this help and exit", \
	"Print version and exit", \
	NULL

/* Helper for getopt case statements */
#define case_USAGE_COMMON_FLAGS \
	case 'h': usage(NULL); \
	/* fallthrough */ \
	case 'V': util_version(); \
	/* fallthrough */ \
	case '?': usage("unknown option");

static const char usage_short_opts[] =
		"haAc:b:C:defg:G:HIlLmn:N:o:O:p:P:rRsStTv"
		USAGE_COMMON_SHORT_OPTS;
static struct option const usage_long_opts[] = {
	{"show-address",	no_argument, NULL, 'a'},
	{"colour",		no_argument, NULL, 'A'},
	{"include-node-with-prop", a_argument, NULL, 'b'},
	{"include-compat",	a_argument, NULL, 'c'},
	{"exclude-compat",	a_argument, NULL, 'C'},
	{"diff",		no_argument, NULL, 'd'},
	{"enter-node",		no_argument, NULL, 'e'},
	{"show-offset",		no_argument, NULL, 'f'},
	{"include-match",	a_argument, NULL, 'g'},
	{"exclude-match",	a_argument, NULL, 'G'},
	{"show-header",		no_argument, NULL, 'H'},
	{"show-version",	no_argument, NULL, 'I'},
	{"list-regions",	no_argument, NULL, 'l'},
	{"list-strings",	no_argument, NULL, 'L'},
	{"include-mem",		no_argument, NULL, 'm'},
	{"include-node",	a_argument, NULL, 'n'},
	{"exclude-node",	a_argument, NULL, 'N'},
	{"include-prop",	a_argument, NULL, 'p'},
	{"exclude-prop",	a_argument, NULL, 'P'},
	{"remove-strings",	no_argument, NULL, 'r'},
	{"include-root",	no_argument, NULL, 'R'},
	{"show-subnodes",	no_argument, NULL, 's'},
	{"skip-supernodes",	no_argument, NULL, 'S'},
	{"show-stringtab",	no_argument, NULL, 't'},
	{"show-aliases",	no_argument, NULL, 'T'},
	{"out",			a_argument, NULL, 'o'},
	{"out-format",		a_argument, NULL, 'O'},
	{"invert-match",	no_argument, NULL, 'v'},
	USAGE_COMMON_LONG_OPTS,
};
static const char * const usage_opts_help[] = {
	"Display address",
	"Show all nodes/tags, colour those that match",
	"Include contains containing property",
	"Compatible nodes to include in grep",
	"Compatible nodes to exclude in grep",
	"Diff: Mark matching nodes with +, others with -",
	"Enter direct subnode names of matching nodes",
	"Display offset",
	"Node/property/compatible string to include in grep",
	"Node/property/compatible string to exclude in grep",
	"Output a header",
	"Put \"/dts-v1/;\" on first line of dts output",
	"Output a region list",
	"List strings in string table",
	"Include mem_rsvmap section in binary output",
	"Node to include in grep",
	"Node to exclude in grep",
	"Property to include in grep",
	"Property to exclude in grep",
	"Remove unused strings from string table",
	"Include root node and all properties",
	"Show all subnodes matching nodes",
	"Don't include supernodes of matching nodes",
	"Include string table in binary output",
	"Include matching aliases in output",
	"-o <output file>",
	"-O <output format>",
	"Invert the sense of matching (select non-matching lines)",
	USAGE_COMMON_OPTS_HELP
};

/**
 * Call getopt_long() with standard options
 *
 * Since all util code runs getopt in the same way, provide a helper.
 */
#define util_getopt_long() getopt_long(argc, argv, usage_short_opts, \
				       usage_long_opts, NULL)

void util_usage(const char *errmsg, const char *synopsis,
		const char *short_opts, struct option const long_opts[],
		const char * const opts_help[])
{
	FILE *fp = errmsg ? stderr : stdout;
	const char a_arg[] = "<arg>";
	size_t a_arg_len = strlen(a_arg) + 1;
	size_t i;
	int optlen;

	fprintf(fp,
		"Usage: %s\n"
		"\n"
		"Options: -[%s]\n", synopsis, short_opts);

	/* prescan the --long opt length to auto-align */
	optlen = 0;
	for (i = 0; long_opts[i].name; ++i) {
		/* +1 is for space between --opt and help text */
		int l = strlen(long_opts[i].name) + 1;
		if (long_opts[i].has_arg == a_argument)
			l += a_arg_len;
		if (optlen < l)
			optlen = l;
	}

	for (i = 0; long_opts[i].name; ++i) {
		/* helps when adding new applets or options */
		assert(opts_help[i] != NULL);

		/* first output the short flag if it has one */
		if (long_opts[i].val > '~')
			fprintf(fp, "      ");
		else
			fprintf(fp, "  -%c, ", long_opts[i].val);

		/* then the long flag */
		if (long_opts[i].has_arg == no_argument) {
			fprintf(fp, "--%-*s", optlen, long_opts[i].name);
		} else {
			fprintf(fp, "--%s %s%*s", long_opts[i].name, a_arg,
				(int)(optlen - strlen(long_opts[i].name) -
				a_arg_len), "");
		}

		/* finally the help text */
		fprintf(fp, "%s\n", opts_help[i]);
	}

	if (errmsg) {
		fprintf(fp, "\nError: %s\n", errmsg);
		exit(EXIT_FAILURE);
	} else {
		exit(EXIT_SUCCESS);
	}
}

/**
 * Show usage and exit
 *
 * If you name all your usage variables with usage_xxx, then you can call this
 * help macro rather than expanding all arguments yourself.
 *
 * @param errmsg	If non-NULL, an error message to display
 */
#define usage(errmsg) \
	util_usage(errmsg, usage_synopsis, usage_short_opts, \
		   usage_long_opts, usage_opts_help)

void util_version(void)
{
	printf("Version: %s\n", "(U-Boot)");
	exit(0);
}

static void scan_args(struct display_info *disp, int argc, char *argv[])
{
	int opt;

	while ((opt = util_getopt_long()) != EOF) {
		int type = 0;
		int inc = 1;

		switch (opt) {
		case_USAGE_COMMON_FLAGS
		/* fallthrough */
		case 'a':
			disp->show_addr = 1;
			break;
		case 'A':
			disp->all = 1;
			break;
		case 'b':
			type = FDT_NODE_HAS_PROP;
			break;
		case 'C':
			inc = 0;
			/* fallthrough */
		case 'c':
			type = FDT_IS_COMPAT;
			break;
		case 'd':
			disp->diff = 1;
			break;
		case 'e':
			disp->flags |= FDT_REG_DIRECT_SUBNODES;
			break;
		case 'f':
			disp->show_offset = 1;
			break;
		case 'G':
			inc = 0;
			/* fallthrough */
		case 'g':
			type = FDT_ANY_GLOBAL;
			break;
		case 'H':
			disp->header = 1;
			break;
		case 'l':
			disp->region_list = 1;
			break;
		case 'L':
			disp->list_strings = 1;
			break;
		case 'm':
			disp->flags |= FDT_REG_ADD_MEM_RSVMAP;
			break;
		case 'N':
			inc = 0;
			/* fallthrough */
		case 'n':
			type = FDT_IS_NODE;
			break;
		case 'o':
			disp->output_fname = optarg;
			break;
		case 'O':
			if (!strcmp(optarg, "dtb"))
				disp->output = OUT_DTB;
			else if (!strcmp(optarg, "dts"))
				disp->output = OUT_DTS;
			else if (!strcmp(optarg, "bin"))
				disp->output = OUT_BIN;
			else
				usage("Unknown output format");
			break;
		case 'P':
			inc = 0;
			/* fallthrough */
		case 'p':
			type = FDT_IS_PROP;
			break;
		case 'r':
			disp->remove_strings = 1;
			break;
		case 'R':
			disp->include_root = 1;
			break;
		case 's':
			disp->flags |= FDT_REG_ALL_SUBNODES;
			break;
		case 'S':
			disp->flags &= ~FDT_REG_SUPERNODES;
			break;
		case 't':
			disp->flags |= FDT_REG_ADD_STRING_TAB;
			break;
		case 'T':
			disp->add_aliases = 1;
			break;
		case 'v':
			disp->invert = 1;
			break;
		case 'I':
			disp->show_dts_version = 1;
			break;
		}

		if (type && value_add(disp, &disp->value_head, type, inc,
				      optarg))
			usage("Cannot add value");
	}

	if (disp->invert && disp->types_exc)
		usage("-v has no meaning when used with 'exclude' conditions");
}

int main(int argc, char *argv[])
{
	char *filename = NULL;
	struct display_info disp;
	int ret;

	/* set defaults */
	memset(&disp, '\0', sizeof(disp));
	disp.flags = FDT_REG_SUPERNODES;	/* Default flags */

	scan_args(&disp, argc, argv);

	/* Show matched lines in colour if we can */
	disp.colour = disp.all && isatty(0);

	/* Any additional arguments can match anything, just like -g */
	while (optind < argc - 1) {
		if (value_add(&disp, &disp.value_head, FDT_IS_ANY, 1,
			      argv[optind++]))
			usage("Cannot add value");
	}

	if (optind < argc)
		filename = argv[optind++];
	if (!filename)
		usage("Missing filename");

	/* If a valid .dtb is required, set flags to ensure we get one */
	if (disp.output == OUT_DTB) {
		disp.header = 1;
		disp.flags |= FDT_REG_ADD_MEM_RSVMAP | FDT_REG_ADD_STRING_TAB;
	}

	if (disp.output_fname) {
		disp.fout = fopen(disp.output_fname, "w");
		if (!disp.fout)
			usage("Cannot open output file");
	} else {
		disp.fout = stdout;
	}

	/* Run the grep and output the results */
	ret = do_fdtgrep(&disp, filename);
	if (disp.output_fname)
		fclose(disp.fout);
	if (ret)
		return 1;

	return 0;
}
