Skip to content

Commit

Permalink
Fix BUG microsoftarchive#442 about the missing save
Browse files Browse the repository at this point in the history
  • Loading branch information
MattiaVicari committed Nov 3, 2017
1 parent 10a978f commit acb40af
Show file tree
Hide file tree
Showing 5 changed files with 62 additions and 24 deletions.
38 changes: 22 additions & 16 deletions src/Win32_Interop/Win32_service.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,7 @@ this should preceed the other arguments passed to redis. For instance:
#include <sstream>
#include <vector>
#include <iostream>
#include <signal.h>
#include "Win32_RedisLog.h"
#include "Win32_CommandLine.h"
using namespace std;
Expand Down Expand Up @@ -527,21 +528,26 @@ DWORD WINAPI ServiceCtrlHandler(DWORD dwControl, DWORD dwEventType, LPVOID lpEve
case SERVICE_CONTROL_STOP:
{
DWORD start = GetTickCount();
while (GetTickCount() - start > cPreshutdownInterval) {
if (WaitForSingleObject(g_ServiceStoppedEvent, cPreshutdownInterval / 10) == WAIT_OBJECT_0) {
break;
}

g_ServiceStatus.dwControlsAccepted = 0;
g_ServiceStatus.dwCurrentState = SERVICE_STOP_PENDING;
g_ServiceStatus.dwWin32ExitCode = 0;
g_ServiceStatus.dwCheckPoint = 4;

if (SetServiceStatus(g_StatusHandle, &g_ServiceStatus) == FALSE) {
throw std::system_error(GetLastError(), system_category(), "SetServiceStatus failed");
}
}

/* BUG #442: in order to resolve the bug about the missing save, I send the signal SIGTERM.
* We need to wait that all the processes are terminated before stop the main process. */
raise(SIGTERM);

while (true/*GetTickCount() - start > cPreshutdownInterval*/) {
// It is needed to wait that all the processes are terminated.
if (WaitForSingleObject(g_ServiceStoppedEvent, INFINITE/*cPreshutdownInterval / 10*/) == WAIT_OBJECT_0) {
break;
}

g_ServiceStatus.dwControlsAccepted = 0;
g_ServiceStatus.dwCurrentState = SERVICE_STOP_PENDING;
g_ServiceStatus.dwWin32ExitCode = 0;
g_ServiceStatus.dwCheckPoint = 4;

if (SetServiceStatus(g_StatusHandle, &g_ServiceStatus) == FALSE) {
throw std::system_error(GetLastError(), system_category(), "SetServiceStatus failed");
}
}

g_ServiceStatus.dwControlsAccepted = 0;
g_ServiceStatus.dwCurrentState = SERVICE_STOPPED;
g_ServiceStatus.dwWin32ExitCode = 0;
Expand All @@ -555,7 +561,7 @@ DWORD WINAPI ServiceCtrlHandler(DWORD dwControl, DWORD dwEventType, LPVOID lpEve

default:
{
break;
break;
}
}

Expand Down
8 changes: 4 additions & 4 deletions src/asciilogo.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,10 +32,10 @@ char *ascii_logo =
" _.-``__ ''-._ \n"
" _.-`` `. `_. ''-._ Redis %s (%s/%d) %s bit\n"
" .-`` .-```. ```\\/ _.,_ ''-._ \n"
" ( ' , .-` | `, ) Running in %s mode\n"
" |`-._`-...-` __...-.``-._|'` _.-'| Port: %d\n"
" | `-._ `._ / _.-' | PID: %ld\n"
" `-._ `-._ `-./ _.-' _.-' \n"
" ( ' , .-` | `, ) Author: %s, %s\n"
" |`-._`-...-` __...-.``-._|'` _.-'| Running in %s mode\n"
" | `-._ `._ / _.-' | Port: %d\n"
" `-._ `-._ `-./ _.-' _.-' PID: %ld\n"
" |`-._`-._ `-.__.-' _.-'_.-'| \n"
" | `-._`-._ _.-'_.-' | http://redis.io \n"
" `-._ `-._`-.__.-'_.-' _.-' \n"
Expand Down
34 changes: 32 additions & 2 deletions src/redis.c
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,10 @@ POSIX_ONLY(#include <sys/utsname.h>)
#include <locale.h>


#ifdef _WIN32
extern BOOL RunningAsService();
#endif

/* Our shared "common" objects */

struct sharedObjectsStruct shared;
Expand Down Expand Up @@ -1126,9 +1130,31 @@ int serverCron(struct aeEventLoop *eventLoop, PORT_LONGLONG id, void *clientData
/* We received a SIGTERM, shutting down here in a safe way, as it is
* not ok doing so inside the signal handler. */
if (server.shutdown_asap) {
if (prepareForShutdown(0) == REDIS_OK) exit(0);
#ifdef _WIN32
/* For Redis running as a Windows service, we want to shutdown gracefully.
* The serverCron will be closed next by the aeStop() function when the service has been terminated so,
* the stop with exit(0), is not good in this situation (in that way we can avoid the "Pipe Terminated" error). */
if (RunningAsService())
{
if (prepareForShutdown(0) != REDIS_OK)
{
redisLog(REDIS_WARNING, "SIGTERM received but errors trying to shut down the server, check the logs for more information");
server.shutdown_asap = 0;
}
else
eventLoop->stop = 1; // The event timer should be stop
}
else
{
if (prepareForShutdown(0) == REDIS_OK) exit(0);
redisLog(REDIS_WARNING,"SIGTERM received but errors trying to shut down the server, check the logs for more information");
server.shutdown_asap = 0;
}
#else
if (prepareForShutdown(0) == REDIS_OK) exit(0);
redisLog(REDIS_WARNING,"SIGTERM received but errors trying to shut down the server, check the logs for more information");
server.shutdown_asap = 0;
#endif
}

/* Show some info about non-empty databases */
Expand Down Expand Up @@ -3518,11 +3544,13 @@ void redisAsciiArt(void) {

if (server.syslog_enabled) {
redisLog(REDIS_NOTICE,
"Redis %s (%s/%d) %s bit, %s mode, port %d, pid %ld ready to start.",
"Redis %s (%s/%d) %s bit, Author %s, %s, %s mode, port %d, pid %ld ready to start.",
REDIS_VERSION,
redisGitSHA1(),
strtol(redisGitDirty(),NULL,10) > 0,
(sizeof(PORT_LONG) == 8) ? "64" : "32",
VERSION_AUTHOR,
VERSION_COMPANY,
mode, server.port,
(PORT_LONG) getpid()
);
Expand All @@ -3532,6 +3560,8 @@ void redisAsciiArt(void) {
redisGitSHA1(),
strtol(redisGitDirty(),NULL,10) > 0,
(sizeof(PORT_LONG) == 8) ? "64" : "32",
VERSION_AUTHOR,
VERSION_COMPANY,
mode, server.port,
(PORT_LONG) getpid()
);
Expand Down
2 changes: 1 addition & 1 deletion src/redis.h
Original file line number Diff line number Diff line change
Expand Up @@ -1264,7 +1264,7 @@ void call(redisClient *c, int flags);
void propagate(struct redisCommand *cmd, int dbid, robj **argv, int argc, int flags);
void alsoPropagate(struct redisCommand *cmd, int dbid, robj **argv, int argc, int target);
void forceCommandPropagation(redisClient *c, int flags);
int prepareForShutdown();
int prepareForShutdown(int flags);
#ifdef __GNUC__
void redisLog(int level, const char *fmt, ...)
__attribute__((format(printf, 2, 3)));
Expand Down
4 changes: 3 additions & 1 deletion src/version.h
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
#define REDIS_VERSION "3.0.504"
#define REDIS_VERSION "3.0.504.1"
#define VERSION_AUTHOR "Mattia Vicari"
#define VERSION_COMPANY "InfoC.E.R. s.r.l."

0 comments on commit acb40af

Please sign in to comment.