Fix handling of leading spaces in scripts.

* grub-core/normal/cmdline.c (grub_cmdline_get): Don't strip leading
	spaces.
	* grub-core/normal/main.c (grub_file_getline): Remove all preprocessing
	other than skipping \r. All users updated.
	* tests/grub_script_echo1.in: Add space-related tests.
	* util/grub-menulst2cfg.c (main): Remove useless space skipping.
This commit is contained in:
Vladimir 'phcoder' Serbinenko 2012-03-11 14:43:18 +01:00
parent 1a1ac4f6cb
commit 9fdb2d7b11
10 changed files with 104 additions and 66 deletions

View File

@ -1,3 +1,14 @@
2012-03-11 Vladimir Serbinenko <phcoder@gmail.com>
Fix handling of leading spaces in scripts.
* grub-core/normal/cmdline.c (grub_cmdline_get): Don't strip leading
spaces.
* grub-core/normal/main.c (grub_file_getline): Remove all preprocessing
other than skipping \r. All users updated.
* tests/grub_script_echo1.in: Add space-related tests.
* util/grub-menulst2cfg.c (main): Remove useless space skipping.
2012-03-11 Vladimir Serbinenko <phcoder@gmail.com>
* grub-core/commands/cat.c (grub_cmd_cat): Fix termination key check.

View File

@ -103,6 +103,8 @@ check_list (const gcry_md_spec_t *hash, const char *hashfilename,
while (grub_free (buf), (buf = grub_file_getline (hashlist)))
{
const char *p = buf;
while (grub_isspace (p[0]))
p++;
for (i = 0; i < hash->mdlen; i++)
{
int high, low;
@ -112,8 +114,9 @@ check_list (const gcry_md_spec_t *hash, const char *hashfilename,
return grub_error (GRUB_ERR_BAD_FILE_TYPE, "invalid hash list");
expected[i] = (high << 4) | low;
}
if (*p++ != ' ' || *p++ != ' ')
if ((p[0] != ' ' && p[0] != '\t') || (p[1] != ' ' && p[1] != '\t'))
return grub_error (GRUB_ERR_BAD_FILE_TYPE, "invalid hash list");
p += 2;
if (prefix)
{
char *filename;

View File

@ -205,6 +205,8 @@ grub_cmd_parttool (grub_command_t cmd __attribute__ ((unused)),
break;
name = buf;
while (grub_isspace (name[0]))
name++;
if (! grub_isgraph (name[0]))
continue;
@ -214,8 +216,9 @@ grub_cmd_parttool (grub_command_t cmd __attribute__ ((unused)),
continue;
*p = '\0';
while (*++p == ' ')
;
p++;
while (*p == ' ' || *p == '\t')
p++;
if (! grub_isgraph (*p))
continue;

View File

@ -630,11 +630,6 @@ grub_cmdline_get (const char *prompt_translated)
grub_xputs ("\n");
grub_refresh ();
/* Remove leading spaces. */
lpos = 0;
while (buf[lpos] == ' ')
lpos++;
histpos = 0;
if (strlen_ucs4 (buf) > 0)
{
@ -643,7 +638,7 @@ grub_cmdline_get (const char *prompt_translated)
grub_history_add (empty, 0);
}
ret = grub_ucs4_to_utf8_alloc (buf + lpos, llen - lpos + 1);
ret = grub_ucs4_to_utf8_alloc (buf, llen + 1);
grub_free (buf);
grub_free (cl_terms);
return ret;

View File

@ -116,14 +116,17 @@ read_crypto_list (const char *prefix)
break;
name = buf;
while (grub_isspace (name[0]))
name++;
p = grub_strchr (name, ':');
if (! p)
continue;
*p = '\0';
while (*++p == ' ')
;
p++;
while (*p == ' ' || *p == '\t')
p++;
cur = grub_malloc (sizeof (*cur));
if (!cur)

View File

@ -141,6 +141,9 @@ read_command_list (const char *prefix)
break;
name = buf;
while (grub_isspace (name[0]))
name++;
if (*name == '*')
{
name++;
@ -155,8 +158,9 @@ read_command_list (const char *prefix)
continue;
*p = '\0';
while (*++p == ' ')
;
p++;
while (*p == ' ' || *p == '\t')
p++;
if (! grub_isgraph (*p))
continue;

View File

@ -45,10 +45,10 @@ char *
grub_file_getline (grub_file_t file)
{
char c;
int pos = 0;
int literal = 0;
grub_size_t pos = 0;
char *cmdline;
int max_len = 64;
int have_newline = 0;
grub_size_t max_len = 64;
/* Initially locate some space. */
cmdline = grub_malloc (max_len);
@ -64,59 +64,32 @@ grub_file_getline (grub_file_t file)
if (c == '\r')
continue;
/* Replace tabs with spaces. */
if (c == '\t')
c = ' ';
/* The previous is a backslash, then... */
if (literal)
if (pos >= max_len)
{
/* If it is a newline, replace it with a space and continue. */
if (c == '\n')
char *old_cmdline = cmdline;
max_len = max_len * 2;
cmdline = grub_realloc (cmdline, max_len);
if (! cmdline)
{
c = ' ';
/* Go back to overwrite the backslash. */
if (pos > 0)
pos--;
grub_free (old_cmdline);
return 0;
}
literal = 0;
}
if (c == '\\')
literal = 1;
if (pos == 0)
if (c == '\n')
{
if (! grub_isspace (c))
cmdline[pos++] = c;
have_newline = 1;
break;
}
else
{
if (pos >= max_len)
{
char *old_cmdline = cmdline;
max_len = max_len * 2;
cmdline = grub_realloc (cmdline, max_len);
if (! cmdline)
{
grub_free (old_cmdline);
return 0;
}
}
if (c == '\n')
break;
cmdline[pos++] = c;
}
cmdline[pos++] = c;
}
cmdline[pos] = '\0';
/* If the buffer is empty, don't return anything at all. */
if (pos == 0)
if (pos == 0 && !have_newline)
{
grub_free (cmdline);
cmdline = 0;

View File

@ -338,7 +338,11 @@ read_terminal_list (const char *prefix)
if (! buf)
break;
switch (buf[0])
p = buf;
while (grub_isspace (p[0]))
p++;
switch (p[0])
{
case 'i':
target = &grub_term_input_autoload;
@ -351,15 +355,15 @@ read_terminal_list (const char *prefix)
if (!target)
continue;
name = buf + 1;
name = p + 1;
p = grub_strchr (name, ':');
if (! p)
continue;
*p = '\0';
while (*++p == ' ')
;
p++;
while (*p == ' ' || *p == '\t')
p++;
cur = grub_malloc (sizeof (*cur));
if (!cur)

View File

@ -20,6 +20,9 @@
echo one two three
echo "one two three"
echo 'one two three'
echo "one two three"
echo "one two three"
echo "one two three"
# empty arguments
echo a "" b
@ -87,6 +90,13 @@ echo one'two
echo one'two
\'three
echo "one\
"
echo "one\
\""
echo "one\
two"
# echo "one\
# two"
# echo 'one\
@ -99,5 +109,40 @@ echo one'two
#
# two"
echo "one
"
echo "one
\""
echo "one
two"
echo one"two
"three
echo one"two
\""three
echo one"two
\"three\"
four"
echo 'one
'
echo 'one
\'
echo 'one
two'
echo one'two
'
echo one'two
\'
echo one'two
\'three
echo "one\
"
echo "one\
\""
echo "one\
two"
if test x$grubshell = xyes; then insmod regexp; fi
echo /boot/grub/i386-pc/normal.mod

View File

@ -80,12 +80,9 @@ main (int argc, char **argv)
{
char *oldname = NULL;
char *newsuffix;
char *ptr;
for (ptr = buf; *ptr && grub_isspace (*ptr); ptr++);
oldname = entryname;
parsed = grub_legacy_parse (ptr, &entryname, &newsuffix);
parsed = grub_legacy_parse (buf, &entryname, &newsuffix);
if (newsuffix)
{
suffixlen += strlen (newsuffix);