X-Git-Url: https://git.saurik.com/redis.git/blobdiff_plain/f48cd4b90cc298a74ded3f7adc45740a4dd1a9c1..4d776dba3c706aa20fd7d95dd73bff32dc2148a7:/src/redis.c diff --git a/src/redis.c b/src/redis.c index da975636..ca49271d 100644 --- a/src/redis.c +++ b/src/redis.c @@ -31,11 +31,6 @@ #include "slowlog.h" #include "bio.h" -#ifdef HAVE_BACKTRACE -#include -#include -#endif /* HAVE_BACKTRACE */ - #include #include #include @@ -759,6 +754,9 @@ int serverCron(struct aeEventLoop *eventLoop, long long id, void *clientData) { * in order to guarantee a strict consistency. */ if (server.masterhost == NULL) activeExpireCycle(); + /* Close clients that need to be closed asynchronous */ + freeClientsInAsyncFreeQueue(); + /* Replication cron function -- used to reconnect to master and * to detect transfer failures. */ if (!(loops % 10)) replicationCron(); @@ -787,8 +785,11 @@ void beforeSleep(struct aeEventLoop *eventLoop) { c->flags &= ~REDIS_UNBLOCKED; /* Process remaining data in the input buffer. */ - if (c->querybuf && sdslen(c->querybuf) > 0) + if (c->querybuf && sdslen(c->querybuf) > 0) { + server.current_client = c; processInputBuffer(c); + server.current_client = NULL; + } } /* Write the AOF buffer on disk */ @@ -923,11 +924,22 @@ void initServerConfig() { server.masterhost = NULL; server.masterport = 6379; server.master = NULL; - server.replstate = REDIS_REPL_NONE; + server.repl_state = REDIS_REPL_NONE; server.repl_syncio_timeout = REDIS_REPL_SYNCIO_TIMEOUT; server.repl_serve_stale_data = 1; server.repl_down_since = -1; + /* Client output buffer limits */ + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_NORMAL].hard_limit_bytes = 0; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_NORMAL].soft_limit_bytes = 0; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_NORMAL].soft_limit_seconds = 0; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_SLAVE].hard_limit_bytes = 1024*1024*256; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_SLAVE].soft_limit_bytes = 1024*1024*64; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_SLAVE].soft_limit_seconds = 60; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_PUBSUB].hard_limit_bytes = 1024*1024*32; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_PUBSUB].soft_limit_bytes = 1024*1024*8; + server.client_obuf_limits[REDIS_CLIENT_LIMIT_CLASS_PUBSUB].soft_limit_seconds = 60; + /* Double constants initialization */ R_Zero = 0.0; R_PosInf = 1.0/R_Zero; @@ -1002,7 +1014,9 @@ void initServer() { server.syslog_facility); } + server.current_client = NULL; server.clients = listCreate(); + server.clients_to_close = listCreate(); server.slaves = listCreate(); server.monitors = listCreate(); server.unblocked_clients = listCreate(); @@ -1081,8 +1095,6 @@ void initServer() { scriptingInit(); slowlogInit(); bioInit(); - srand(time(NULL)^getpid()); - } /* Populates the Redis Command Table starting from the hard coded list @@ -1254,7 +1266,7 @@ int processCommand(redisClient *c) { /* Only allow INFO and SLAVEOF when slave-serve-stale-data is no and * we are a slave with a broken link with master. */ - if (server.masterhost && server.replstate != REDIS_REPL_CONNECTED && + if (server.masterhost && server.repl_state != REDIS_REPL_CONNECTED && server.repl_serve_stale_data == 0 && c->cmd->proc != infoCommand && c->cmd->proc != slaveofCommand) { @@ -1425,6 +1437,7 @@ sds genRedisInfoString(char *section) { "redis_git_dirty:%d\r\n" "arch_bits:%s\r\n" "multiplexing_api:%s\r\n" + "gcc_version:%d.%d.%d\r\n" "process_id:%ld\r\n" "tcp_port:%d\r\n" "uptime_in_seconds:%ld\r\n" @@ -1435,6 +1448,11 @@ sds genRedisInfoString(char *section) { strtol(redisGitDirty(),NULL,10) > 0, (sizeof(long) == 8) ? "64" : "32", aeGetApiName(), +#ifdef __GNUC__ + __GNUC__,__GNUC_MINOR__,__GNUC_PATCHLEVEL__, +#else + 0,0,0, +#endif (long) getpid(), server.port, uptime, @@ -1592,14 +1610,14 @@ sds genRedisInfoString(char *section) { "master_sync_in_progress:%d\r\n" ,server.masterhost, server.masterport, - (server.replstate == REDIS_REPL_CONNECTED) ? + (server.repl_state == REDIS_REPL_CONNECTED) ? "up" : "down", server.master ? ((int)(time(NULL)-server.master->lastinteraction)) : -1, - server.replstate == REDIS_REPL_TRANSFER + server.repl_state == REDIS_REPL_TRANSFER ); - if (server.replstate == REDIS_REPL_TRANSFER) { + if (server.repl_state == REDIS_REPL_TRANSFER) { info = sdscatprintf(info, "master_sync_left_bytes:%ld\r\n" "master_sync_last_io_seconds_ago:%d\r\n" @@ -1608,7 +1626,7 @@ sds genRedisInfoString(char *section) { ); } - if (server.replstate != REDIS_REPL_CONNECTED) { + if (server.repl_state != REDIS_REPL_CONNECTED) { info = sdscatprintf(info, "master_link_down_since_seconds:%ld\r\n", (long)time(NULL)-server.repl_down_since); @@ -1923,102 +1941,6 @@ void redisAsciiArt(void) { zfree(buf); } -#ifdef HAVE_BACKTRACE -static void *getMcontextEip(ucontext_t *uc) { -#if defined(__FreeBSD__) - return (void*) uc->uc_mcontext.mc_eip; -#elif defined(__dietlibc__) - return (void*) uc->uc_mcontext.eip; -#elif defined(__APPLE__) && !defined(MAC_OS_X_VERSION_10_6) - #if __x86_64__ - return (void*) uc->uc_mcontext->__ss.__rip; - #elif __i386__ - return (void*) uc->uc_mcontext->__ss.__eip; - #else - return (void*) uc->uc_mcontext->__ss.__srr0; - #endif -#elif defined(__APPLE__) && defined(MAC_OS_X_VERSION_10_6) - #if defined(_STRUCT_X86_THREAD_STATE64) && !defined(__i386__) - return (void*) uc->uc_mcontext->__ss.__rip; - #else - return (void*) uc->uc_mcontext->__ss.__eip; - #endif -#elif defined(__i386__) - return (void*) uc->uc_mcontext.gregs[14]; /* Linux 32 */ -#elif defined(__X86_64__) || defined(__x86_64__) - return (void*) uc->uc_mcontext.gregs[16]; /* Linux 64 */ -#elif defined(__ia64__) /* Linux IA64 */ - return (void*) uc->uc_mcontext.sc_ip; -#else - return NULL; -#endif -} - -void bugReportStart(void) { - if (server.bug_report_start == 0) { - redisLog(REDIS_WARNING, - "=== REDIS BUG REPORT START: Cut & paste starting from here ==="); - server.bug_report_start = 1; - } -} - -static void sigsegvHandler(int sig, siginfo_t *info, void *secret) { - void *trace[100]; - char **messages = NULL; - int i, trace_size = 0; - ucontext_t *uc = (ucontext_t*) secret; - sds infostring, clients; - struct sigaction act; - REDIS_NOTUSED(info); - - bugReportStart(); - redisLog(REDIS_WARNING, - " Redis %s crashed by signal: %d", REDIS_VERSION, sig); - redisLog(REDIS_WARNING, - " Failed assertion: %s (%s:%d)", server.assert_failed, - server.assert_file, server.assert_line); - - /* Generate the stack trace */ - trace_size = backtrace(trace, 100); - - /* overwrite sigaction with caller's address */ - if (getMcontextEip(uc) != NULL) { - trace[1] = getMcontextEip(uc); - } - messages = backtrace_symbols(trace, trace_size); - redisLog(REDIS_WARNING, "--- STACK TRACE"); - for (i=1; i= 2) { int j = 1; /* First option to parse in argv[] */ sds options = sdsempty();