[PATCH v2 5/8] makedumpfile: Read and process filter commands from config file.
Ken'ichi Ohmichi
oomichi at mxs.nes.nec.co.jp
Thu Aug 11 20:08:25 EDT 2011
Hi Mahesh,
Thank you for checking the above also.
commit 92d2934f9e1694e7195d93f9816fbea8a657f05f fixes them.
Thanks
Ken'ichi Ohmichi
On Thu, 11 Aug 2011 17:03:06 +0530
Mahesh Jagannath Salgaonkar <mahesh at linux.vnet.ibm.com> wrote:
>
> Hi Ken'ichi,
>
> On 08/11/2011 07:37 AM, Ken'ichi Ohmichi wrote:
> >
> > Hi Mahesh,
> >
> > On Wed, 18 May 2011 01:34:15 +0530
> > Mahesh J Salgaonkar <mahesh at linux.vnet.ibm.com> wrote:
> >>
> >> This patch enables to makedumpfile to read and process filter commands from
> >> specified config file. It builds a list of filter info consisting of memory
> >> address (paddr) and size to be filtered out. This list is used during
> >> read_pfn() function to filter out user specified kernel data from vmcore
> >> before writing it to compressed DUMPFILE. The filtered memory locations are
> >> filled with 'X' (0x58) character.
> >>
> >> The filter command syntax is:
> >> erase <Symbol>[.member[...]] [size <SizeValue>[K|M]]
> >> erase <Symbol>[.member[...]] [size <SizeSymbol>]
> >> erase <Symbol>[.member[...]] [nullify]
> >>
> >> Below are the examples how filter commands in config file look like:
> >>
> >> erase modules
> >> erase cred_jar.name size 10
> >> erase vmlist.addr nullify
> >
> > Thank you for the work.
> > I tested this feature by the above example, and confirmed the feature
> > works fine. Nice work :-)
>
> Thanks :-)
>
> >
> > There are some comments in the below lines.
> > Can you check them ?
> >
> >> +/*
> >> + * Read the non-terminal's which are in the form of <Symbol>[.member[...]]
> >> + */
> >> +struct config_entry *
> >> +create_config_entry(const char *token, unsigned short flag, int line)
> >> +{
> >> + struct config_entry *ce = NULL, *ptr, *prev_ce;
> >> + char *str, *cur, *next;
> >> + long len;
> >> + int depth = 0;
> >> +
> >> + if (!token)
> >> + return NULL;
> >> +
> >> + cur = str = strdup(token);
> >> + prev_ce = ptr = NULL;
> >> + while (cur != NULL) {
> >> + if ((next = strchr(cur, '.')) != NULL) {
> >> + *next++ = '\0';
> >> + }
> >> + if (!strlen(cur)) {
> >> + cur = next;
> >> + continue;
> >> + }
> >> +
> >> + if ((ptr = calloc(1, sizeof(struct config_entry))) == NULL) {
> >> + ERRMSG("Can't allocate memory for config_entry\n");
> >> + goto err_out;
> >> + }
> >> + ptr->line = line;
> >> + ptr->flag |= flag;
> >> + if (depth == 0) {
> >> + /* First node is always a symbol name */
> >> + ptr->flag |= SYMBOL_ENTRY;
> >> + }
> >> + if (flag & FILTER_ENTRY) {
> >> + ptr->name = strdup(cur);
> >> + }
> >> + if (flag & SIZE_ENTRY) {
> >> + char ch = '\0';
> >> + int n = 0;
> >> + /* See if absolute length is provided */
> >> + if ((depth == 0) &&
> >> + ((n = sscanf(cur, "%zd%c", &len, &ch)) > 0)) {
> >> + if (len < 0) {
> >> + ERRMSG("Config error at %d: size "
> >> + "value must be positive.\n",
> >> + line);
> >> + goto err_out;
> >> + }
> >> + ptr->size = len;
> >> + ptr->flag |= ENTRY_RESOLVED;
> >> + if (n == 2) {
> >> + /* Handle suffix.
> >> + * K = Kilobytes
> >> + * M = Megabytes
> >> + */
> >> + switch (ch) {
> >> + case 'M':
> >> + case 'm':
> >> + ptr->size *= 1024;
> >> + case 'K':
> >> + case 'k':
> >> + ptr->size *= 1024;
> >> + break;
> >> + }
> >> + }
> >> + }
> >> + else
> >> + ptr->name = strdup(cur);
> >> + }
> >> + if (prev_ce) {
> >> + prev_ce->next = ptr;
> >> + prev_ce = ptr;
> >> + }
> >> + else
> >> + ce = prev_ce = ptr;
> >> + cur = next;
> >> + depth++;
> >> + ptr = NULL;
> >> + }
> >> + free(str);
> >> + return ce;
> >> +
> >> +err_out:
> >> + if (ce)
> >> + free_config_entry(ce);
> >> + if (ptr)
> >> + free_config_entry(ptr);
> >
> > "free(str);" is necessary.
> >
>
> Nice catch. Agree.
>
> >> + return NULL;
> >> +}
> >
> > [..]
> >
> >> +/*
> >> + * read filter config file and return each string token. If the parameter
> >> + * expected_token is non-NULL, then return the current token if it matches
> >> + * with expected_token otherwise save the current token and return NULL.
> >> + * At start of every module section filter_config.new_section is set to 1 and
> >> + * subsequent function invocations return NULL untill filter_config.new_section
> >> + * is reset to 0 by passing @flag = CONFIG_NEW_CMD (0x02).
> >> + *
> >> + * Parameters:
> >> + * @expected_token INPUT
> >> + * Token string to match with currnet token.
> >> + * =NULL - return the current available token.
> >> + *
> >> + * @flag INPUT
> >> + * =0x01 - Skip to next module section.
> >> + * =0x02 - Treat the next token as next filter command and reset.
> >> + *
> >> + * @line OUTPUT
> >> + * Line number of current token in filter config file.
> >> + *
> >> + * @cur_mod OUTPUT
> >> + * Points to current module section name on non-NULL return value.
> >> + *
> >> + * @eof OUTPUT
> >> + * set to -1 when end of file is reached.
> >> + * set to -2 when end of section is reached.
> >> + */
> >> +static char *
> >> +get_config_token(char *expected_token, unsigned char flag, int *line,
> >> + char **cur_mod, int *eof)
> >> +{
> >> + char *p;
> >> + struct filter_config *fc = &filter_config;
> >> + int skip = flag & CONFIG_SKIP_SECTION;
> >
> > CONFIG_SKIP_SECTION is used only here, and we need to fix get_config()
> > for the readability. Please check my comment in get_config().
> >
> > [..]
> >
> >> +/*
> >> + * Configuration file 'makedumpfile.conf' contains filter commands.
> >> + * Every individual filter command is considered as a config entry. A config
> >> + * entry can be provided on a single line or multiple lines.
> >> + */
> >> +struct config *
> >> +get_config(int skip)
> >> +{
> >> + struct config *config;
> >> + char *token = NULL;
> >> + static int line_count = 0;
> >> + char *cur_module = NULL;
> >> + int eof = 0;
> >> + unsigned char flag = CONFIG_NEW_CMD | skip;
> >
> > We need to change the above:
> >
> > unsigned char flag = CONFIG_NEW_CMD;
> > if (skip)
> > flag |= CONFIG_SKIP_SECTION;
> >
>
> Agree.
>
> Thanks,
> -Mahesh.
>
> _______________________________________________
> kexec mailing list
> kexec at lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/kexec
More information about the kexec
mailing list