The parser can crash upon weird input to the "append" option:
- a bare "append" with no value makes parse_sliteral() fail on the T_EOL
  token and leave label->append untouched, so the NULL is handed straight
  to strstr();

- "initrd=" as the last token on the line makes strchr(s, ' ') return
  NULL, so the length becomes a huge negative number and the following
  malloc()/strncpy() pair runs wild.

Bail out on a failed parse, and use strcspn() so an unterminated value
simply runs to the end of the string. strndup() then folds the
allocate-copy-terminate sequence into one call.

Signed-off-by: Alexey Charkov <[email protected]>
---
 boot/pxe_utils.c | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/boot/pxe_utils.c b/boot/pxe_utils.c
index 02bd43ac46e2..078eb2d0c244 100644
--- a/boot/pxe_utils.c
+++ b/boot/pxe_utils.c
@@ -1333,16 +1333,16 @@ static int parse_label(char **c, struct pxe_menu *cfg)
 
                case T_APPEND:
                        err = parse_sliteral(c, &label->append);
-                       if (label->initrd)
+                       if (err < 0 || label->initrd)
                                break;
                        s = strstr(label->append, "initrd=");
                        if (!s)
                                break;
-                       s += 7;
-                       len = (int)(strchr(s, ' ') - s);
-                       label->initrd = malloc(len + 1);
-                       strncpy(label->initrd, s, len);
-                       label->initrd[len] = '\0';
+                       s += strlen("initrd=");
+                       len = strcspn(s, " ");
+                       label->initrd = strndup(s, len);
+                       if (!label->initrd)
+                               err = -ENOMEM;
 
                        break;
 

-- 
2.54.0

Reply via email to