summaryrefslogtreecommitdiff
path: root/Src/utils.c
diff options
context:
space:
mode:
authorJun-ichi Takimoto <takimoto-j@kba.biglobe.ne.jp>2021-04-06 23:05:03 +0900
committerJun-ichi Takimoto <takimoto-j@kba.biglobe.ne.jp>2021-04-06 23:05:03 +0900
commit0f62e07c802e3fa58d1199f34fcf9772da70c264 (patch)
treea85aec1da2877c2c97439f5fac5b1b24692e1f94 /Src/utils.c
parentccc7ff90a46d7b1bdcf61bae2dba20d68dca7654 (diff)
downloadzsh-0f62e07c802e3fa58d1199f34fcf9772da70c264.tar.gz
zsh-0f62e07c802e3fa58d1199f34fcf9772da70c264.zip
48389: getkeystring() should not return ptr to local var
Now it returns NULL if called with GETKEY_SINGLE_CHAR and next character is not found. Caller must check the return value.
Diffstat (limited to 'Src/utils.c')
-rw-r--r--Src/utils.c33
1 files changed, 25 insertions, 8 deletions
diff --git a/Src/utils.c b/Src/utils.c
index 1ac064a4e..5a9222919 100644
--- a/Src/utils.c
+++ b/Src/utils.c
@@ -6697,13 +6697,21 @@ ucs4toutf8(char *dest, unsigned int wval)
*
* The return value is unmetafied unless GETKEY_DOLLAR_QUOTE is
* in use.
+ *
+ * If GETKEY_SINGLE_CHAR is set in how, a next character in the given
+ * string is parsed, and the character code for it is returned in misc.
+ * The return value of the function is a pointer to the byte in the
+ * given string from where the next parsing should start. If the next
+ * character can't be found then NULL is returned.
+ * CAUTION: Currently, GETKEY_SINGLE_CHAR can be used only via
+ * GETKEYS_MATH. Other use of it may cause trouble.
*/
/**/
mod_export char *
getkeystring(char *s, int *len, int how, int *misc)
{
- char *buf, tmp[1];
+ char *buf = NULL, tmp[1];
char *t, *tdest = NULL, *u = NULL, *sstart = s, *tbuf = NULL;
char svchar = '\0';
int meta = 0, control = 0, ignoring = 0;
@@ -6729,9 +6737,11 @@ getkeystring(char *s, int *len, int how, int *misc)
DPUTS((how & (GETKEY_DOLLAR_QUOTE|GETKEY_SINGLE_CHAR)) ==
(GETKEY_DOLLAR_QUOTE|GETKEY_SINGLE_CHAR),
"BUG: incompatible options in getkeystring");
+ DPUTS((how & GETKEY_SINGLE_CHAR) && (how != GETKEYS_MATH),
+ "BUG: unsupported options in getkeystring");
if (how & GETKEY_SINGLE_CHAR)
- t = buf = tmp;
+ t = tmp;
else {
/* Length including terminating NULL */
int maxlen = 1;
@@ -7165,13 +7175,20 @@ getkeystring(char *s, int *len, int how, int *misc)
*/
DPUTS((how & (GETKEY_DOLLAR_QUOTE|GETKEY_UPDATE_OFFSET)) ==
GETKEY_DOLLAR_QUOTE, "BUG: unterminated $' substitution");
- *t = '\0';
- if (how & GETKEY_DOLLAR_QUOTE)
- *tdest = '\0';
- if (how & GETKEY_SINGLE_CHAR)
+
+ if (how & GETKEY_SINGLE_CHAR) {
+ /* couldn't find a character */
*misc = 0;
- else
- *len = ((how & GETKEY_DOLLAR_QUOTE) ? tdest : t) - buf;
+ return NULL;
+ }
+ if (how & GETKEY_DOLLAR_QUOTE) {
+ *tdest = '\0';
+ *len = tdest - buf;
+ }
+ else {
+ *t = '\0';
+ *len = t - buf;
+ }
return buf;
}