MFC: r207461

sparc64, and possibly other architectures, pads the length of the
  section holding the config file to sh_addralign bytes using NULs.
  This bogusly triggers an assert.  Break out of the loop when we hit an
  NUL within that many bytes of the end.
This commit is contained in:
Warner Losh 2010-05-04 03:56:25 +00:00
parent ddd1f79f79
commit c8ab44bfa8

View File

@ -670,7 +670,7 @@ kernconfdump(const char *file)
struct stat st;
FILE *fp, *pp;
int error, len, osz, r;
unsigned int i, off, size;
unsigned int i, off, size, t1, t2, align;
char *cmd, *o;
r = open(file, O_RDONLY);
@ -689,8 +689,8 @@ kernconfdump(const char *file)
if (o == NULL)
err(EXIT_FAILURE, "Couldn't allocate memory");
/* ELF note section header. */
asprintf(&cmd, "/usr/bin/elfdump -c %s | grep -A 5 kern_conf"
"| tail -2 | cut -d ' ' -f 2 | paste - - -", file);
asprintf(&cmd, "/usr/bin/elfdump -c %s | grep -A 8 kern_conf"
"| tail -5 | cut -d ' ' -f 2 | paste - - - - -", file);
if (cmd == NULL)
errx(EXIT_FAILURE, "asprintf() failed");
pp = popen(cmd, "r");
@ -699,24 +699,28 @@ kernconfdump(const char *file)
free(cmd);
len = fread(o, osz, 1, pp);
pclose(pp);
r = sscanf(o, "%d\t%d", &off, &size);
r = sscanf(o, "%d%d%d%d%d", &off, &size, &t1, &t2, &align);
free(o);
if (r != 2)
if (r != 5)
errx(EXIT_FAILURE, "File %s doesn't contain configuration "
"file. Either unsupported, or not compiled with "
"INCLUDE_CONFIG_FILE", file);
r = fseek(fp, off, SEEK_CUR);
if (r != 0)
err(EXIT_FAILURE, "fseek() failed");
for (i = 0; i < size - 1; i++) {
for (i = 0; i < size; i++) {
r = fgetc(fp);
if (r == EOF)
break;
/*
* If '\0' is present in the middle of the configuration
* string, this means something very weird is happening.
* Make such case very visible.
* Make such case very visible. However, some architectures
* pad the length of the section with NULs to a multiple of
* sh_addralign, allow a NUL in that part of the section.
*/
if (r == '\0' && (size - i) < align)
break;
assert(r != '\0' && ("Char present in the configuration "
"string mustn't be equal to 0"));
fputc(r, stdout);