Clean up when there is an I/O error

This commit is contained in:
Pieter Noordhuis 2010-09-19 19:01:31 +02:00
parent 457cdbf7c5
commit 62c8054dbe
2 changed files with 26 additions and 9 deletions

View File

@ -73,7 +73,7 @@ redisReply *redisConnect(int *fd, const char *ip, int port) {
/* Create a reply object */ /* Create a reply object */
static redisReply *createReplyObject(int type, sds reply) { static redisReply *createReplyObject(int type, sds reply) {
redisReply *r = malloc(sizeof(*r)); redisReply *r = calloc(sizeof(*r),1);
if (!r) redisOOM(); if (!r) redisOOM();
r->type = type; r->type = type;
@ -94,6 +94,7 @@ void freeReplyObject(redisReply *r) {
free(r->element); free(r->element);
break; break;
default: default:
if (r->reply != NULL)
sdsfree(r->reply); sdsfree(r->reply);
break; break;
} }
@ -303,8 +304,13 @@ static redisReply *redisReadReply(int fd) {
} }
/* read from socket into buffer */ /* read from socket into buffer */
if ((bytes = read(fd,r.buf+r.avail,READ_BUFFER_SIZE)) <= 0) if ((bytes = read(fd,r.buf+r.avail,READ_BUFFER_SIZE)) <= 0) {
/* rlist[0] is the "root" reply object */
freeReplyObject(r.rlist[0]);
free(r.buf);
free(r.rlist);
return redisIOError(); return redisIOError();
}
r.avail += bytes; r.avail += bytes;
r.buf[r.avail] = '\0'; r.buf[r.avail] = '\0';

23
test.c
View File

@ -15,20 +15,31 @@ long long usec(void) {
return (((long long)tv.tv_sec)*1000000)+tv.tv_usec; return (((long long)tv.tv_sec)*1000000)+tv.tv_usec;
} }
void connect(int *fd) {
redisReply *reply = redisConnect(fd, "127.0.0.1", 6379);
if (reply != NULL) {
printf("Connection error: %s", reply->reply);
exit(1);
}
}
int main(void) { int main(void) {
int fd; int fd;
int i, fails = 0; int i, fails = 0;
long long t1, t2; long long t1, t2;
redisReply *reply; redisReply *reply;
connect(&fd);
reply = redisConnect(&fd, "127.0.0.1", 6379); /* test 0 */
if (reply != NULL) { printf("#0 Returns I/O error when the connection is lost: ");
printf("Connection error: %s", reply->reply); reply = redisCommand(fd,"QUIT");
exit(1); test_cond(reply->type == REDIS_REPLY_ERROR &&
} strcasecmp(reply->reply,"i/o error") == 0);
freeReplyObject(reply);
connect(&fd); /* reconnect */
/* test 1 */ /* test 1 */
printf("\n#1 Is able to deliver commands: "); printf("#1 Is able to deliver commands: ");
reply = redisCommand(fd,"PING"); reply = redisCommand(fd,"PING");
test_cond(reply->type == REDIS_REPLY_STRING && test_cond(reply->type == REDIS_REPLY_STRING &&
strcasecmp(reply->reply,"pong") == 0) strcasecmp(reply->reply,"pong") == 0)