aboutsummaryrefslogtreecommitdiff
path: root/gas
diff options
context:
space:
mode:
authorAlan Modra <amodra@gmail.com>2022-03-28 17:51:30 +1030
committerAlan Modra <amodra@gmail.com>2022-03-29 11:27:23 +1030
commit1fc6fa2f1be66d99007bc2dba90f2c57f941bf58 (patch)
tree16a508481090acb6231912261c4aab7971619dec /gas
parent4a02e01a71fd8086361dee879cc07b93d57e25ab (diff)
downloadgdb-1fc6fa2f1be66d99007bc2dba90f2c57f941bf58.zip
gdb-1fc6fa2f1be66d99007bc2dba90f2c57f941bf58.tar.gz
gdb-1fc6fa2f1be66d99007bc2dba90f2c57f941bf58.tar.bz2
asan: heap buffer overflow in pa_chk_field_selector
The buffer overflow showed up running the gas "all macro" test. PR 29005 * config/tc-hppa.c (pa_chk_field_selector): Don't read past end of line.
Diffstat (limited to 'gas')
-rw-r--r--gas/config/tc-hppa.c45
1 files changed, 29 insertions, 16 deletions
diff --git a/gas/config/tc-hppa.c b/gas/config/tc-hppa.c
index 742d262..5a4db51 100644
--- a/gas/config/tc-hppa.c
+++ b/gas/config/tc-hppa.c
@@ -2432,24 +2432,37 @@ pa_chk_field_selector (char **str)
int middle, low, high;
int cmp;
char name[4];
+ char *s = *str;
/* Read past any whitespace. */
- /* FIXME: should we read past newlines and formfeeds??? */
- while (**str == ' ' || **str == '\t' || **str == '\n' || **str == '\f')
- *str = *str + 1;
-
- if ((*str)[1] == '\'' || (*str)[1] == '%')
- name[0] = TOLOWER ((*str)[0]),
- name[1] = 0;
- else if ((*str)[2] == '\'' || (*str)[2] == '%')
- name[0] = TOLOWER ((*str)[0]),
- name[1] = TOLOWER ((*str)[1]),
- name[2] = 0;
- else if ((*str)[3] == '\'' || (*str)[3] == '%')
- name[0] = TOLOWER ((*str)[0]),
- name[1] = TOLOWER ((*str)[1]),
- name[2] = TOLOWER ((*str)[2]),
- name[3] = 0;
+ while (*s == ' ' || *s == '\t')
+ s++;
+ *str = s;
+
+ if (is_end_of_line [(unsigned char) s[0]])
+ return e_fsel;
+ else if (s[1] == '\'' || s[1] == '%')
+ {
+ name[0] = TOLOWER (s[0]);
+ name[1] = 0;
+ }
+ else if (is_end_of_line [(unsigned char) s[1]])
+ return e_fsel;
+ else if (s[2] == '\'' || s[2] == '%')
+ {
+ name[0] = TOLOWER (s[0]);
+ name[1] = TOLOWER (s[1]);
+ name[2] = 0;
+ }
+ else if (is_end_of_line [(unsigned char) s[2]])
+ return e_fsel;
+ else if (s[3] == '\'' || s[3] == '%')
+ {
+ name[0] = TOLOWER (s[0]);
+ name[1] = TOLOWER (s[1]);
+ name[2] = TOLOWER (s[2]);
+ name[3] = 0;
+ }
else
return e_fsel;