diff options
author | Pieter Noordhuis <pcnoordhuis@gmail.com> | 2011-03-06 11:38:07 +0100 |
---|---|---|
committer | Pieter Noordhuis <pcnoordhuis@gmail.com> | 2011-03-06 11:38:07 +0100 |
commit | 8e2c39200d2a643180b1bc07aaa234056d5354f4 (patch) | |
tree | cb3dc0066b572aa36ce6d943d4bb4f2496c2afd1 | |
parent | bf544ce81c55f6ae64470efeec04f368dec9ac3d (diff) |
Fix formatCommand to work with all empty interpolations
-rw-r--r-- | hiredis.c | 13 | ||||
-rw-r--r-- | test.c | 6 |
2 files changed, 12 insertions, 7 deletions
@@ -596,7 +596,7 @@ int redisvFormatCommand(char **target, const char *format, va_list ap) { char *cmd = NULL; /* final command */ int pos; /* position in final command */ sds current; /* current argument */ - int interpolated = 0; /* did we do interpolation on an argument? */ + int touched = 0; /* was the current argument touched? */ char **argv = NULL; int argc = 0, j; int totlen = 0; @@ -610,13 +610,14 @@ int redisvFormatCommand(char **target, const char *format, va_list ap) { while(*c != '\0') { if (*c != '%' || c[1] == '\0') { if (*c == ' ') { - if (sdslen(current) != 0) { + if (touched) { addArgument(current, &argv, &argc, &totlen); current = sdsempty(); - interpolated = 0; + touched = 0; } } else { current = sdscatlen(current,c,1); + touched = 1; } } else { switch(c[1]) { @@ -625,14 +626,12 @@ int redisvFormatCommand(char **target, const char *format, va_list ap) { size = strlen(arg); if (size > 0) current = sdscatlen(current,arg,size); - interpolated = 1; break; case 'b': arg = va_arg(ap,char*); size = va_arg(ap,size_t); if (size > 0) current = sdscatlen(current,arg,size); - interpolated = 1; break; case '%': current = sdscat(current,"%"); @@ -678,7 +677,6 @@ int redisvFormatCommand(char **target, const char *format, va_list ap) { _format[_l] = '\0'; va_copy(_cpy,ap); current = sdscatvprintf(current,_format,_cpy); - interpolated = 1; va_end(_cpy); /* Update current position (note: outer blocks @@ -691,13 +689,14 @@ int redisvFormatCommand(char **target, const char *format, va_list ap) { va_arg(ap,void); } } + touched = 1; c++; } c++; } /* Add the last argument if needed */ - if (interpolated || sdslen(current) != 0) { + if (touched) { addArgument(current, &argv, &argc, &totlen); } else { sdsfree(current); @@ -54,6 +54,12 @@ static void test_format_commands(void) { len == 4+4+(3+2)+4+(3+2)+4+(0+2)); free(cmd); + test("Format command with an empty string in between proper interpolations: "); + len = redisFormatCommand(&cmd,"SET %s %s","","foo"); + test_cond(strncmp(cmd,"*3\r\n$3\r\nSET\r\n$0\r\n\r\n$3\r\nfoo\r\n",len) == 0 && + len == 4+4+(3+2)+4+(0+2)+4+(3+2)); + free(cmd); + test("Format command with %%b string interpolation: "); len = redisFormatCommand(&cmd,"SET %b %b","foo",3,"b\0r",3); test_cond(strncmp(cmd,"*3\r\n$3\r\nSET\r\n$3\r\nfoo\r\n$3\r\nb\0r\r\n",len) == 0 && |