Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
ruanhaishen
redis
Commits
c4cd5f39
Commit
c4cd5f39
authored
Jun 06, 2009
by
antirez
Browse files
Merge
git://github.com/dierbro/redis
parents
a3cc9e36
433cc893
Changes
3
Hide whitespace changes
Inline
Side-by-side
Makefile
View file @
c4cd5f39
...
@@ -2,8 +2,8 @@
...
@@ -2,8 +2,8 @@
# Copyright (C) 2009 Salvatore Sanfilippo <antirez at gmail dot com>
# Copyright (C) 2009 Salvatore Sanfilippo <antirez at gmail dot com>
# This file is released under the BSD license, see the COPYING file
# This file is released under the BSD license, see the COPYING file
DEBUG
?=
-g
DEBUG
?=
-g
-rdynamic
-ggdb
CFLAGS
?=
-std
=
c99
-pedantic
-O
2
-Wall
-W
-DSDS_ABORT_ON_OOM
CFLAGS
?=
-std
=
c99
-pedantic
-O
0
-Wall
-W
-DSDS_ABORT_ON_OOM
CCOPT
=
$(CFLAGS)
CCOPT
=
$(CFLAGS)
OBJ
=
adlist.o ae.o anet.o dict.o redis.o sds.o zmalloc.o lzf_c.o lzf_d.o pqsort.o
OBJ
=
adlist.o ae.o anet.o dict.o redis.o sds.o zmalloc.o lzf_c.o lzf_d.o pqsort.o
...
...
redis.c
View file @
c4cd5f39
...
@@ -36,7 +36,10 @@
...
@@ -36,7 +36,10 @@
#include <string.h>
#include <string.h>
#include <time.h>
#include <time.h>
#include <unistd.h>
#include <unistd.h>
#define __USE_POSIX199309
#include <signal.h>
#include <signal.h>
#include <execinfo.h>
#include <ucontext.h>
#include <sys/wait.h>
#include <sys/wait.h>
#include <errno.h>
#include <errno.h>
#include <assert.h>
#include <assert.h>
...
@@ -51,6 +54,7 @@
...
@@ -51,6 +54,7 @@
#include <limits.h>
#include <limits.h>
#include <execinfo.h>
#include <execinfo.h>
#include "redis.h"
#include "ae.h"
/* Event driven programming library */
#include "ae.h"
/* Event driven programming library */
#include "sds.h"
/* Dynamic safe strings */
#include "sds.h"
/* Dynamic safe strings */
#include "anet.h"
/* Networking the easy way */
#include "anet.h"
/* Networking the easy way */
...
@@ -171,6 +175,7 @@
...
@@ -171,6 +175,7 @@
/* Anti-warning macro... */
/* Anti-warning macro... */
#define REDIS_NOTUSED(V) ((void) V)
#define REDIS_NOTUSED(V) ((void) V)
/*================================= Data types ============================== */
/*================================= Data types ============================== */
/* A redis object, that is a type able to hold a string / list / set */
/* A redis object, that is a type able to hold a string / list / set */
...
@@ -272,6 +277,11 @@ struct redisCommand {
...
@@ -272,6 +277,11 @@ struct redisCommand {
int
flags
;
int
flags
;
};
};
struct
redisFunctionSym
{
char
*
name
;
long
pointer
;
};
typedef
struct
_redisSortObject
{
typedef
struct
_redisSortObject
{
robj
*
obj
;
robj
*
obj
;
union
{
union
{
...
@@ -319,6 +329,7 @@ static time_t getExpire(redisDb *db, robj *key);
...
@@ -319,6 +329,7 @@ static time_t getExpire(redisDb *db, robj *key);
static
int
setExpire
(
redisDb
*
db
,
robj
*
key
,
time_t
when
);
static
int
setExpire
(
redisDb
*
db
,
robj
*
key
,
time_t
when
);
static
void
updateSalvesWaitingBgsave
(
int
bgsaveerr
);
static
void
updateSalvesWaitingBgsave
(
int
bgsaveerr
);
static
void
freeMemoryIfNeeded
(
void
);
static
void
freeMemoryIfNeeded
(
void
);
static
int
processCommand
(
redisClient
*
c
);
static
void
authCommand
(
redisClient
*
c
);
static
void
authCommand
(
redisClient
*
c
);
static
void
pingCommand
(
redisClient
*
c
);
static
void
pingCommand
(
redisClient
*
c
);
...
@@ -377,7 +388,7 @@ static void getSetCommand(redisClient *c);
...
@@ -377,7 +388,7 @@ static void getSetCommand(redisClient *c);
static
void
ttlCommand
(
redisClient
*
c
);
static
void
ttlCommand
(
redisClient
*
c
);
static
void
slaveofCommand
(
redisClient
*
c
);
static
void
slaveofCommand
(
redisClient
*
c
);
static
void
debugCommand
(
redisClient
*
c
);
static
void
debugCommand
(
redisClient
*
c
);
static
void
setupSigSegvAction
();
/*================================= Globals ================================= */
/*================================= Globals ================================= */
/* Global vars */
/* Global vars */
...
@@ -443,7 +454,91 @@ static struct redisCommand cmdTable[] = {
...
@@ -443,7 +454,91 @@ static struct redisCommand cmdTable[] = {
{
"debug"
,
debugCommand
,
-
2
,
REDIS_CMD_INLINE
},
{
"debug"
,
debugCommand
,
-
2
,
REDIS_CMD_INLINE
},
{
NULL
,
NULL
,
0
,
0
}
{
NULL
,
NULL
,
0
,
0
}
};
};
static
struct
redisFunctionSym
symsTable
[]
=
{
{
"freeStringObject"
,
(
long
)
freeStringObject
},
{
"freeListObject"
,
(
long
)
freeListObject
},
{
"freeSetObject"
,
(
long
)
freeSetObject
},
{
"decrRefCount"
,
(
long
)
decrRefCount
},
{
"createObject"
,
(
long
)
createObject
},
{
"freeClient"
,
(
long
)
freeClient
},
{
"rdbLoad"
,
(
long
)
rdbLoad
},
{
"addReply"
,
(
long
)
addReply
},
{
"addReplySds"
,
(
long
)
addReplySds
},
{
"incrRefCount"
,
(
long
)
incrRefCount
},
{
"rdbSaveBackground"
,
(
long
)
rdbSaveBackground
},
{
"createStringObject"
,
(
long
)
createStringObject
},
{
"replicationFeedSlaves"
,
(
long
)
replicationFeedSlaves
},
{
"syncWithMaster"
,
(
long
)
syncWithMaster
},
{
"tryObjectSharing"
,
(
long
)
tryObjectSharing
},
{
"removeExpire"
,
(
long
)
removeExpire
},
{
"expireIfNeeded"
,
(
long
)
expireIfNeeded
},
{
"deleteIfVolatile"
,
(
long
)
deleteIfVolatile
},
{
"deleteKey"
,
(
long
)
deleteKey
},
{
"getExpire"
,
(
long
)
getExpire
},
{
"setExpire"
,
(
long
)
setExpire
},
{
"updateSalvesWaitingBgsave"
,
(
long
)
updateSalvesWaitingBgsave
},
{
"freeMemoryIfNeeded"
,
(
long
)
freeMemoryIfNeeded
},
{
"authCommand"
,
(
long
)
authCommand
},
{
"pingCommand"
,
(
long
)
pingCommand
},
{
"echoCommand"
,
(
long
)
echoCommand
},
{
"setCommand"
,
(
long
)
setCommand
},
{
"setnxCommand"
,
(
long
)
setnxCommand
},
{
"getCommand"
,
(
long
)
getCommand
},
{
"delCommand"
,
(
long
)
delCommand
},
{
"existsCommand"
,
(
long
)
existsCommand
},
{
"incrCommand"
,
(
long
)
incrCommand
},
{
"decrCommand"
,
(
long
)
decrCommand
},
{
"incrbyCommand"
,
(
long
)
incrbyCommand
},
{
"decrbyCommand"
,
(
long
)
decrbyCommand
},
{
"selectCommand"
,
(
long
)
selectCommand
},
{
"randomkeyCommand"
,
(
long
)
randomkeyCommand
},
{
"keysCommand"
,
(
long
)
keysCommand
},
{
"dbsizeCommand"
,
(
long
)
dbsizeCommand
},
{
"lastsaveCommand"
,
(
long
)
lastsaveCommand
},
{
"saveCommand"
,
(
long
)
saveCommand
},
{
"bgsaveCommand"
,
(
long
)
bgsaveCommand
},
{
"shutdownCommand"
,
(
long
)
shutdownCommand
},
{
"moveCommand"
,
(
long
)
moveCommand
},
{
"renameCommand"
,
(
long
)
renameCommand
},
{
"renamenxCommand"
,
(
long
)
renamenxCommand
},
{
"lpushCommand"
,
(
long
)
lpushCommand
},
{
"rpushCommand"
,
(
long
)
rpushCommand
},
{
"lpopCommand"
,
(
long
)
lpopCommand
},
{
"rpopCommand"
,
(
long
)
rpopCommand
},
{
"llenCommand"
,
(
long
)
llenCommand
},
{
"lindexCommand"
,
(
long
)
lindexCommand
},
{
"lrangeCommand"
,
(
long
)
lrangeCommand
},
{
"ltrimCommand"
,
(
long
)
ltrimCommand
},
{
"typeCommand"
,
(
long
)
typeCommand
},
{
"lsetCommand"
,
(
long
)
lsetCommand
},
{
"saddCommand"
,
(
long
)
saddCommand
},
{
"sremCommand"
,
(
long
)
sremCommand
},
{
"smoveCommand"
,
(
long
)
smoveCommand
},
{
"sismemberCommand"
,
(
long
)
sismemberCommand
},
{
"scardCommand"
,
(
long
)
scardCommand
},
{
"sinterCommand"
,
(
long
)
sinterCommand
},
{
"sinterstoreCommand"
,
(
long
)
sinterstoreCommand
},
{
"sunionCommand"
,
(
long
)
sunionCommand
},
{
"sunionstoreCommand"
,
(
long
)
sunionstoreCommand
},
{
"sdiffCommand"
,
(
long
)
sdiffCommand
},
{
"sdiffstoreCommand"
,
(
long
)
sdiffstoreCommand
},
{
"syncCommand"
,
(
long
)
syncCommand
},
{
"flushdbCommand"
,
(
long
)
flushdbCommand
},
{
"flushallCommand"
,
(
long
)
flushallCommand
},
{
"sortCommand"
,
(
long
)
sortCommand
},
{
"lremCommand"
,
(
long
)
lremCommand
},
{
"infoCommand"
,
(
long
)
infoCommand
},
{
"mgetCommand"
,
(
long
)
mgetCommand
},
{
"monitorCommand"
,
(
long
)
monitorCommand
},
{
"expireCommand"
,
(
long
)
expireCommand
},
{
"getSetCommand"
,
(
long
)
getSetCommand
},
{
"ttlCommand"
,
(
long
)
ttlCommand
},
{
"slaveofCommand"
,
(
long
)
slaveofCommand
},
{
"debugCommand"
,
(
long
)
debugCommand
},
{
"processCommand"
,
(
long
)
processCommand
},
{
"setupSigSegvAction"
,
(
long
)
setupSigSegvAction
},
{
NULL
,
0
}
};
/*============================ Utility functions ============================ */
/*============================ Utility functions ============================ */
/* Glob-style pattern matching. */
/* Glob-style pattern matching. */
...
@@ -902,6 +997,7 @@ static void initServer() {
...
@@ -902,6 +997,7 @@ static void initServer() {
signal
(
SIGHUP
,
SIG_IGN
);
signal
(
SIGHUP
,
SIG_IGN
);
signal
(
SIGPIPE
,
SIG_IGN
);
signal
(
SIGPIPE
,
SIG_IGN
);
setupSigSegvAction
();
server
.
clients
=
listCreate
();
server
.
clients
=
listCreate
();
server
.
slaves
=
listCreate
();
server
.
slaves
=
listCreate
();
...
@@ -4096,7 +4192,94 @@ static void debugCommand(redisClient *c) {
...
@@ -4096,7 +4192,94 @@ static void debugCommand(redisClient *c) {
"-ERR Syntax error, try DEBUG [SEGFAULT|OBJECT <key>]
\r\n
"
));
"-ERR Syntax error, try DEBUG [SEGFAULT|OBJECT <key>]
\r\n
"
));
}
}
}
}
char
*
findFuncName
(
void
*
pointer
,
long
*
offset
){
int
i
,
ret
=-
1
;
long
val
,
off
;
for
(
i
=
0
;
symsTable
[
i
].
pointer
!=
0
;
i
++
){
val
=
(
long
)
pointer
-
symsTable
[
i
].
pointer
;
if
(
val
>=
0
&&
(
off
<
0
||
val
<=
off
)){
off
=
val
;
ret
=
i
;
}
}
if
(
ret
<
0
)
*
offset
=
0
;
else
*
offset
=
off
;
return
ret
>=
0
?
symsTable
[
ret
].
name
:
"unknown"
;
}
static
void
segvHandler
(
int
sig
,
siginfo_t
*
info
,
void
*
secret
)
{
void
*
trace
[
100
];
char
**
messages
=
(
char
**
)
NULL
;
char
*
tmp
;
int
i
,
trace_size
=
0
;
long
offset
=
0
;
ucontext_t
*
uc
=
(
ucontext_t
*
)
secret
;
time_t
uptime
=
time
(
NULL
)
-
server
.
stat_starttime
;
redisLog
(
REDIS_WARNING
,
"application: redis, signal: segmentation fault -%d-"
,
REDIS_VERSION
,
sig
);
redisLog
(
REDIS_WARNING
,
"%s"
,
sdscatprintf
(
sdsempty
(),
"redis_version:%s; "
"uptime_in_days:%d; "
"connected_clients:%d; "
"connected_slaves:%d; "
"used_memory:%zu; "
"changes_since_last_save:%lld; "
"bgsave_in_progress:%d; "
"last_save_time:%d; "
"total_connections_received:%lld; "
"total_commands_processed:%lld; "
"role:%s;"
,
REDIS_VERSION
,
uptime
,
listLength
(
server
.
clients
)
-
listLength
(
server
.
slaves
),
listLength
(
server
.
slaves
),
server
.
usedmemory
,
server
.
dirty
,
server
.
bgsaveinprogress
,
server
.
lastsave
,
server
.
stat_numconnections
,
server
.
stat_numcommands
,
server
.
masterhost
==
NULL
?
"master"
:
"slave"
));
redisLog
(
REDIS_WARNING
,
"EIP %p"
,
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_EIP
]);
redisLog
(
REDIS_WARNING
,
"EAX %p, EBX %p, ECX %p, EDX %p"
,
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_EAX
],
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_EBX
],
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_ECX
],
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_EDX
]);
trace_size
=
backtrace
(
trace
,
100
);
char
pointer
[
trace_size
][
11
];
/* overwrite sigaction with caller's address */
trace
[
1
]
=
(
void
*
)
uc
->
uc_mcontext
.
gregs
[
REG_EIP
];
for
(
i
=
1
;
i
<
trace_size
;
++
i
)
snprintf
(
pointer
[
i
],
11
,
"[%p]"
,
trace
[
i
]);
messages
=
backtrace_symbols
(
trace
,
trace_size
);
for
(
i
=
1
;
i
<
trace_size
;
++
i
){
tmp
=
strstr
(
messages
[
i
],
pointer
[
i
]);
if
((
tmp
-
2
)[
0
]
!=
')'
){
char
*
a
=
findFuncName
(
trace
[
i
],
&
offset
);
redisLog
(
REDIS_WARNING
,
"#%d (%s+0x%x) %s"
,
i
,
a
,
(
unsigned
int
)
offset
,
tmp
);
}
else
redisLog
(
REDIS_WARNING
,
"#%d %s"
,
i
,
messages
[
i
]);
}
free
(
messages
);
exit
(
0
);
}
void
setupSigSegvAction
(){
struct
sigaction
act
;
sigemptyset
(
&
act
.
sa_mask
);
/* When the SA_SIGINFO flag is set in sa_flags then sa_sigaction is used. Otherwise, sa_handler is used */
act
.
sa_flags
=
SA_NODEFER
|
SA_ONSTACK
|
SA_RESETHAND
|
SA_SIGINFO
;
act
.
sa_sigaction
=
segvHandler
;
sigaction
(
SIGSEGV
,
&
act
,
NULL
);
}
/* =================================== Main! ================================ */
/* =================================== Main! ================================ */
#ifdef __linux__
#ifdef __linux__
...
@@ -4149,7 +4332,7 @@ int main(int argc, char **argv) {
...
@@ -4149,7 +4332,7 @@ int main(int argc, char **argv) {
#ifdef __linux__
#ifdef __linux__
linuxOvercommitMemoryWarning
();
linuxOvercommitMemoryWarning
();
#endif
#endif
initServerConfig
();
initServerConfig
();
if
(
argc
==
2
)
{
if
(
argc
==
2
)
{
ResetServerSaveParams
();
ResetServerSaveParams
();
...
...
redis.h
0 → 100644
View file @
c4cd5f39
/*
* Copyright (c) 2006-2009, Salvatore Sanfilippo <antirez at gmail dot com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* * Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* * Neither the name of Redis nor the names of its contributors may be used
* to endorse or promote products derived from this software without
* specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __REDIS_H__
#define __REDIS_H__
enum
{
REG_GS
=
0
,
# define REG_GS REG_GS
REG_FS
,
# define REG_FS REG_FS
REG_ES
,
# define REG_ES REG_ES
REG_DS
,
# define REG_DS REG_DS
REG_EDI
,
# define REG_EDI REG_EDI
REG_ESI
,
# define REG_ESI REG_ESI
REG_EBP
,
# define REG_EBP REG_EBP
REG_ESP
,
# define REG_ESP REG_ESP
REG_EBX
,
# define REG_EBX REG_EBX
REG_EDX
,
# define REG_EDX REG_EDX
REG_ECX
,
# define REG_ECX REG_ECX
REG_EAX
,
# define REG_EAX REG_EAX
REG_TRAPNO
,
# define REG_TRAPNO REG_TRAPNO
REG_ERR
,
# define REG_ERR REG_ERR
REG_EIP
,
# define REG_EIP REG_EIP
REG_CS
,
# define REG_CS REG_CS
REG_EFL
,
# define REG_EFL REG_EFL
REG_UESP
,
# define REG_UESP REG_UESP
REG_SS
# define REG_SS REG_SS
};
#endif
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment