Update of /cvsroot/monetdb/sql/src/backends/monet5
In directory sc8-pr-cvs16.sourceforge.net:/tmp/cvs-serv12059
Modified Files:
merovingian.mx monetdb.1 monetdb.mx
Log Message:
Many things as avalanche result of wanting to be able to list discovered
databases. (Which still isn't implemented fully ;) )
- switch from a fifo to a bi-directional UNIX socket
* allows for confirmation communication
* allows for sending discovered databases
- removed the -w option to start, stop, kill, since it now is the
default, since we now wait for a confirmation message from merovingian
or a detailed error message (huge improvement if you ask me)
- greatly simplified and cleaned up monetdb's code
U monetdb.1
Index: monetdb.1
===================================================================
RCS file: /cvsroot/monetdb/sql/src/backends/monet5/monetdb.1,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -d -r1.9 -r1.10
--- monetdb.1 28 Aug 2008 14:05:47 -0000 1.9
+++ monetdb.1 30 Aug 2008 10:52:13 -0000 1.10
@@ -101,9 +101,9 @@
.I \-s
flag is absent, is
.I rscl.
-.IP "start [\-aw] database [database ...]"
-.IP "stop [\-aw] database [database ...]"
-.IP "kill [\-aw] database [database ...]"
+.IP "start [\-a] database [database ...]"
+.IP "stop [\-a] database [database ...]"
+.IP "kill [\-a] database [database ...]"
Starts, stops or kills the given database(s) or, when
.I \-a
is supplied, all known databases, if the MonetDB Database Server
@@ -115,13 +115,6 @@
.B stop
command. Killing a database may result in (partial) data loss.
The
-.I \-w
-flag causes the command only to return once it knows the required action
-was taken. In other words, it waits for the action to be applied. This
-can be useful when starting large databases that have a long startup
-time. When the
-.I \-w
-flag is used,
.BR monetdb (1)
will output diagnostic messages if the requested action failed. When
encountering an error, one should always consult the logfile of
U merovingian.mx
Index: merovingian.mx
===================================================================
RCS file: /cvsroot/monetdb/sql/src/backends/monet5/merovingian.mx,v
retrieving revision 1.52
retrieving revision 1.53
diff -u -d -r1.52 -r1.53
--- merovingian.mx 21 Aug 2008 08:01:32 -0000 1.52
+++ merovingian.mx 30 Aug 2008 10:52:12 -0000 1.53
@@ -50,32 +50,23 @@
FIXME: actually implement that
@h
-#define MEROV_VERSION "0.7"
+#define MEROV_VERSION "0.8"
#define MEROV_PORT 50000
@c
#include "sql_config.h"
#include "merovingian.h"
#include "mal_sabaoth.h"
-#include <stream_socket.h>
#include <stdlib.h> /* exit, getenv, rand, srand */
#include <stdarg.h> /* variadic stuff */
#include <stdio.h> /* fprintf */
#include <sys/types.h>
#include <sys/wait.h> /* wait */
-#ifdef HAVE_SYS_SOCKET_H
#include <sys/socket.h>
-#endif
-#ifdef HAVE_SYS_UN_H
#include <sys/un.h>
-#endif
-#ifdef HAVE_NETDB_H
#include <netdb.h>
#include <netinet/in.h>
-#endif
-#ifdef HAVE_FCNTL_H
#include <fcntl.h>
-#endif
#include <unistd.h>
#include <string.h> /* strerror */
#ifdef HAVE_ALLOCA_H
@@ -85,6 +76,8 @@
#include <signal.h> /* handle Ctrl-C, etc. */
#include <pthread.h>
#include <time.h>
+#include <stream.h>
+#include <stream_socket.h>
#define SOCKPTR struct sockaddr *
#ifdef HAVE_SOCKLEN_T
@@ -812,6 +805,19 @@
return(NO_ERR);
}
+static void
+listDiscoveries(stream *fout)
+{
+ remotedb rdb;
+
+ rdb = _merovingian_remotedbs;
+ while (rdb != NULL) {
+ stream_printf(fout, "%s\t%s\t%d\n",
+ rdb->dbname, rdb->conn, rdb->ttl);
+ rdb = rdb->next;
+ }
+}
+
static err
handleClient(int sock)
{
@@ -939,6 +945,15 @@
*s = 0;
}
+ if (strcmp(lang, "eximius") == 0) {
+ /* return a list of remote databases from our Aranita */
+ listDiscoveries(fout);
+ stream_flush(fout);
+ close_stream(fout);
+ close_stream(fdin);
+ return(NO_ERR);
+ }
+
if (*database == '\0') {
/* we need to have a database, if we haven't gotten one,
* complain */
@@ -1112,6 +1127,34 @@
return(NO_ERR);
}
+static err
+openConnectionUNIX(int *ret, char *path)
+{
+ struct sockaddr_un server;
+ int sock = -1;
+
+ sock = socket(AF_UNIX, SOCK_STREAM, 0);
+ if (sock < 0)
+ return(newErr("creation of UNIX stream socket failed: %s",
+ strerror(errno)));
+
+ memset(&server, 0, sizeof(struct sockaddr_un));
+ server.sun_family = AF_UNIX;
+ strncpy(server.sun_path, path, sizeof(server.sun_path) - 1);
+
+ if (bind(sock, (SOCKPTR) &server, sizeof(struct sockaddr_un)) < 0)
+ return(newErr("binding to UNIX stream socket at %s failed: %s",
+ path, strerror(errno)));
+
+ /* keep queue of 5 */
+ listen(sock, 5);
+
+ merlog("listening for UNIX connections on %s", path);
+
+ *ret = sock;
+ return(NO_ERR);
+}
+
static int _keepListening = 1;
static str
acceptConnections(int sock)
@@ -1126,8 +1169,7 @@
do {
/* handle socket connections */
FD_ZERO(&fds);
- if (sock >= 0)
- FD_SET(sock, &fds);
+ FD_SET(sock, &fds);
/* Wait up to 0.5 seconds. */
tv.tv_sec = 0;
@@ -1147,7 +1189,7 @@
}
continue;
}
- if (sock >= 0 && FD_ISSET(sock, &fds)) {
+ if (FD_ISSET(sock, &fds)) {
if ((msgsock = accept(sock, (SOCKPTR) 0, (socklen_t *)
0)) < 0) {
if (_keepListening == 0)
break;
@@ -1179,99 +1221,164 @@
static void
controlRunner(void *d)
{
+ int sock = *(int *)d;
char buf[256];
+ char buf2[256];
char *p, *q;
sabdb *stats;
- int fd;
int pos = 0;
+ int retval;
+ struct timeval tv;
+ fd_set fds;
+ int msgsock;
+ size_t len;
+ err e;
/* Try to handle control signals. We can get race conditions due to
* clients coming in at the same time. We might need to fix this
* situation sometime. */
- fd = open((char *)d, O_RDONLY); /* note: this blocks */
- while (_keepListening == 1) {
- if (pos == 0) {
- if ((pos = read(fd, buf, 255)) == 0) {
- /* ignore EOF, but don't spin-lock */
- MT_sleep_ms(500);
- continue;
- } else if (pos == -1) {
- /* we got interrupted ... so what? */
- if (errno == EINTR) {
- pos = 0;
- continue;
- }
- /* hmmm error ... give up */
- fprintf(stderr, "error reading from control
channel: %s\n",
- strerror(errno));
+ do {
+ /* handle socket connections */
+ FD_ZERO(&fds);
+ FD_SET(sock, &fds);
+
+ /* Wait up to 0.5 seconds. */
+ tv.tv_sec = 0;
+ tv.tv_usec = 500;
+
+ retval = select(sock + 1, &fds, NULL, NULL, &tv);
+ if (retval == 0) {
+ /* nothing interesting has happened */
+ continue;
+ }
+ if (retval < 0) {
+ if (_keepListening == 0)
break;
- } else {
- buf[pos] = '\0';
- pos = 0;
+ if (errno != EINTR) {
+ e = newErr("control runner: error during
select: %s",
+ strerror(errno));
+ goto error;
}
- }
- q = buf + pos;
- p = strchr(q, '\n');
- if (p == NULL) {
- /* skip, must be garbage */
- fprintf(stderr, "skipping garbage on control channel:
%s\n", buf);
- pos = 0;
continue;
}
- *p++ = '\0';
- if (*p == '\0') {
- pos = 0;
- } else {
- pos = p - buf;
- }
+ if (FD_ISSET(sock, &fds)) {
+ if ((msgsock = accept(sock, (SOCKPTR) 0, (socklen_t *)
0)) < 0) {
+ if (_keepListening == 0)
+ break;
+ if (errno != EINTR) {
+ e = newErr("control runner: error
during accept: %s",
+ strerror(errno));
+ goto error;
+ }
+ continue;
+ }
+ } else
+ continue;
- /* format is simple: database<space>command */
- if ((p = strchr(q, ' ')) == NULL) {
- fprintf(stderr, "malformed control signal: %s\n", q);
- } else {
- *p++ = '\0';
- if (strcmp(p, "start") == 0) {
- err e;
- merlog("starting database %s due to control
signal", q);
- if ((e = forkMserver(q, &stats, 1)) != NO_ERR) {
- fprintf(stderr, "failed to fork
mserver: %s\n",
- getErrMsg(e));
- freeErr(e);
+ while (_keepListening) {
+ if (pos == 0) {
+ if ((pos = recv(msgsock, buf, sizeof(buf), 0))
== 0) {
+ /* EOF */
+ break;
+ } else if (pos == -1) {
+ /* we got interrupted ... so what? */
+ if (errno == EINTR) {
+ pos = 0;
+ continue;
+ }
+ /* hmmm error ... give up */
+ fprintf(stderr, "error reading from
control channel: %s\n",
+ strerror(errno));
+ break;
+ } else {
+ buf[pos] = '\0';
+ pos = 0;
}
- if (stats != NULL)
- SABAOTHfreeStatus(&stats);
- } else if (strcmp(p, "stop") == 0 ||
- strcmp(p, "kill") == 0)
- {
- /* we need to find the right dpair, that is we
- * sort of assume the control signal is right */
- dpair dp = topdp;
- while (dp != NULL) {
- if (strcmp(dp->dbname, q) == 0) {
- if (strcmp(p, "stop") == 0) {
- merlog("stopping
database %s due to control "
-
"signal", q);
- kill(dp->pid, SIGTERM);
- } else {
- merlog("killing
database %s due to control "
-
"signal", q);
- kill(dp->pid, SIGKILL);
+ }
+ q = buf + pos;
+ p = strchr(q, '\n');
+ if (p == NULL) {
+ /* skip, must be garbage */
+ fprintf(stderr, "skipping garbage on control
channel: %s\n", buf);
+ pos = 0;
+ continue;
+ }
+ *p++ = '\0';
+ if (*p == '\0') {
+ pos = 0;
+ } else {
+ pos = p - buf;
+ }
+
+ /* format is simple: database<space>command */
+ if ((p = strchr(q, ' ')) == NULL) {
+ fprintf(stderr, "malformed control signal:
%s\n", q);
+ } else {
+ *p++ = '\0';
+ if (strcmp(p, "start") == 0) {
+ err e;
+ merlog("starting database %s due to
control signal", q);
+ if ((e = forkMserver(q, &stats, 1)) !=
NO_ERR) {
+ fprintf(stderr, "failed to fork
mserver: %s\n",
+ getErrMsg(e));
+ len = snprintf(buf2,
sizeof(buf2), "starting %s failed: %s\n",
+ q,
getErrMsg(e));
+ send(msgsock, buf2, len, 0);
+ freeErr(e);
+ } else {
+ len = snprintf(buf2,
sizeof(buf2), "OK\n");
+ send(msgsock, buf2, len, 0);
+ }
+
+ if (stats != NULL)
+ SABAOTHfreeStatus(&stats);
+ } else if (strcmp(p, "stop") == 0 ||
+ strcmp(p, "kill") == 0)
+ {
+ /* we need to find the right dpair,
that is we
+ * sort of assume the control signal is
right */
+ dpair dp = topdp;
+ while (dp != NULL) {
+ if (strcmp(dp->dbname, q) == 0)
{
+ if (strcmp(p, "stop")
== 0) {
+
merlog("stopping database %s due to control "
+
"signal", q);
+ kill(dp->pid,
SIGTERM);
+ } else {
+ merlog("killing
database %s due to control "
+
"signal", q);
+ kill(dp->pid,
SIGKILL);
+ }
+ len = snprintf(buf2,
sizeof(buf2), "OK\n");
+ send(msgsock, buf2,
len, 0);
+ break;
}
- break;
+ dp = dp->next;
}
- dp = dp->next;
- }
- if (dp == NULL) {
- fprintf(stderr, "received control stop
signal for "
- "database not under
merovingian control: %s\n",
- q);
+ if (dp == NULL) {
+ fprintf(stderr, "received
control stop signal for "
+ "database not
under merovingian control: %s\n",
+ q);
+ len = snprintf(buf2,
sizeof(buf2),
+ "%s is not
controlled by merovingian\n", q);
+ send(msgsock, buf2, len, 0);
+ }
+ } else {
+ fprintf(stderr, "unknown control
command: %s", p);
+ len = snprintf(buf2, sizeof(buf2),
+ "unknown command:
%s\n", p);
+ send(msgsock, buf2, len, 0);
}
- } else {
- fprintf(stderr, "unknown control command: %s",
p);
}
}
- }
- close(fd);
+ close(msgsock);
+ continue;
+
+error:
+ fprintf(stderr, "%s\n", e);
+ } while (_keepListening);
+ shutdown(sock, SHUT_RDWR);
+ close(sock);
merlog("control channel closed");
}
@@ -1502,6 +1609,8 @@
rdb->ttl = time(NULL) +
atoi(ttl);
}
rdb = prv;
+ merlog("refresh from %s for
database %s",
+ host, dbname);
break; /* skip duplicate
entries */
}
prv = rdb;
@@ -1655,6 +1764,7 @@
str p, prefix;
FILE *cnf = NULL, *pidfile = NULL;
char buf[1024];
+ char lockfile[512];
sabdb* stats = NULL;
dpair d;
int pfd[2];
@@ -1664,6 +1774,7 @@
int ret;
int sock = -1;
int usock = -1;
+ int unsock = -1;
struct stat sb;
FILE *oerr = NULL;
unsigned short port = MEROV_PORT;
@@ -1824,9 +1935,9 @@
return(1);
}
- snprintf(buf, 1024, "%s/.merovingian_lock", dbfarm);
+ snprintf(lockfile, 512, "%s/.merovingian_lock", dbfarm);
/* lock such that we are alone on this world */
- if ((ret = MT_lockf(buf, F_TLOCK, 4, 1)) == -1) {
+ if ((ret = MT_lockf(lockfile, F_TLOCK, 4, 1)) == -1) {
/* locking failed */
fprintf(stderr, "another merovingian is already running\n");
fflush(stderr);
@@ -1841,16 +1952,6 @@
return(1);
}
- snprintf(buf, 1024, "%s/.merovingian_control", dbfarm);
- unlink(buf);
- if ((ret = mkfifo(buf, S_IRUSR | S_IWUSR)) != 0) {
- fprintf(stderr, "failed to create a control channel %s: %s\n",
- buf, strerror(errno));
- fflush(stderr);
- MERO_EXIT(1);
- return(1);
- }
-
topdp = alloca(sizeof(struct _dpair));
topdp->pid = 0;
topdp->dbname = NULL;
@@ -1985,13 +2086,21 @@
SABAOTHinit(dbfarm, NULL);
- /* open up a connection */
- e = openConnectionTCP(&sock, port);
- if (e == NO_ERR && (e = openConnectionUDP(&usock, port)) == NO_ERR) {
+ /* set up control channel path */
+ snprintf(buf, 1024, "%s/.merovingian_control", dbfarm);
+ unlink(buf);
+ GDKfree(dbfarm);
+
+ /* open up connections */
+ if (
+ (e = openConnectionTCP(&sock, port)) == NO_ERR &&
+ (e = openConnectionUDP(&usock, port)) == NO_ERR &&
+ (e = openConnectionUNIX(&unsock, buf)) == NO_ERR)
+ {
pthread_t ctid = 0;
pthread_t dtid = 0;
- /* from this point merovingian considers itself to be in
position to
+ /* From this point merovingian considers itself to be in
position to
* start running, so flag the parent we will have fun. */
MERO_EXIT(0);
@@ -2006,14 +2115,12 @@
}
/* handle control commands */
- snprintf(buf, 1024, "%s/.merovingian_control", dbfarm);
if (pthread_create(&ctid, NULL, (void *(*)(void
*))controlRunner,
- (void *)buf) < 0)
+ (void *)&unsock) < 0)
{
fprintf(stderr, "unable to create control command
thread\n");
ctid = 0;
}
- GDKfree(dbfarm);
/* start neighbour discovery and notification thread */
if (pthread_create(&dtid, NULL, (void *(*)(void
*))discoveryRunner,
@@ -2026,17 +2133,15 @@
/* handle external connections main loop */
e = acceptConnections(sock);
- /* connect to ourself to avoid a hang when we close, and the
- * control channel hasn't been used */
- fclose(fopen(buf, "a"));
+ /* wait for the control runner and discovery thread to have
+ * finished announcing it's going down */
if (ctid != 0)
pthread_join(ctid, NULL);
- /* wait for the discovery thread to have finished announcing
- * it's going down */
if (dtid != 0)
pthread_join(dtid, NULL);
}
+ unlink(lockfile);
unlink(buf);
if (e != NO_ERR) {
U monetdb.mx
Index: monetdb.mx
===================================================================
RCS file: /cvsroot/monetdb/sql/src/backends/monet5/monetdb.mx,v
retrieving revision 1.23
retrieving revision 1.24
diff -u -d -r1.23 -r1.24
--- monetdb.mx 29 Aug 2008 16:23:31 -0000 1.23
+++ monetdb.mx 30 Aug 2008 10:52:14 -0000 1.24
@@ -40,11 +40,15 @@
#include <dirent.h> /* readdir */
#include <unistd.h> /* stat, rmdir, unlink */
#include <time.h> /* strftime */
+#include <sys/socket.h> /* socket */
+#include <sys/un.h> /* sockaddr_un */
#ifdef HAVE_ALLOCA_H
#include <alloca.h>
#endif
#include <errno.h>
+#define SOCKPTR struct sockaddr *
+
typedef char* err;
#define freeErr(X) GDKfree(X)
@@ -552,17 +556,18 @@
command_merocom(int argc, char *argv[], merocom mode)
{
int doall = 0;
- int wait = 0;
char path[8096];
- FILE *f;
+ int sock = -1;
+ struct sockaddr_un server;
char buf[256];
int i;
err e;
+ sabdb *orig;
sabdb *stats;
- sabdb *waitstats = NULL;
char *type = NULL;
char *p;
int ret = 0;
+ int len;
snprintf(path, 8095, "%s/.merovingian_control", dbfarm);
path[8095] = '\0';
@@ -595,9 +600,6 @@
case 'a':
doall = 1;
break;
- case 'w':
- wait = 1;
- break;
case '-':
if (p[1] == '\0') {
if (argc - 1 > i)
@@ -625,197 +627,110 @@
exit(1);
}
- if ((f = fopen(path, "a")) == NULL) {
- fprintf(stderr, "%s: cannot write command: %s\n",
+ if ((sock = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) {
+ fprintf(stderr, "%s: cannot open connection: %s\n",
+ type, strerror(errno));
+ exit(2);
+ }
+ memset(&server, 0, sizeof(struct sockaddr_un));
+ server.sun_family = AF_UNIX;
+ strncpy(server.sun_path, path, sizeof(server.sun_path) - 1);
+ if (connect(sock, (SOCKPTR) &server, sizeof(struct sockaddr_un))) {
+ fprintf(stderr, "%s: cannot connect: %s\n",
type, strerror(errno));
exit(2);
}
if (doall == 1) {
- sabdb *orig;
/* don't even look at the arguments, because we are instructed
- * to work on all known databases */
- if ((e = SABAOTHgetStatus(&stats, NULL)) != MAL_SUCCEED) {
+ * to list all known databases */
+ if ((e = SABAOTHgetStatus(&orig, NULL)) != MAL_SUCCEED) {
fprintf(stderr, "%s: internal error: %s\n", type, e);
GDKfree(e);
exit(2);
}
-
- orig = stats;
- while (stats != NULL) {
- if (((mode == STOP || mode == KILL)
- && stats->state == SABdbRunning))
- {
- snprintf(buf, 256, "%s %s\n", stats->dbname,
type);
- fputs(buf, f);
- fflush(f);
- if (wait == 1) {
- waitstats = NULL;
- printf("%sing database '%s'... ", type,
stats->dbname);
- fflush(stdout);
- do {
- /* don't spinlock, just wait
half a seconds ;) */
- MT_sleep_ms(500);
- if (waitstats != NULL)
-
SABAOTHfreeStatus(&waitstats);
- if ((e =
SABAOTHgetStatus(&waitstats, stats->dbname)) != MAL_SUCCEED) {
- fprintf(stderr, "\n%s:
internal error: %s\n", type, e);
- GDKfree(e);
- exit(2);
- }
- } while (waitstats->state ==
SABdbRunning);
- if (waitstats->state == SABdbCrashed) {
- printf("CRASHED after shutting
down!\n");
- ret = 1;
- } else {
- printf("done\n");
- }
- SABAOTHfreeStatus(&waitstats);
+ } else {
+ sabdb *w = NULL;
+ orig = NULL;
+ for (i = 1; i < argc; i++) {
+ if (argv[i] != NULL) {
+ if ((e = SABAOTHgetStatus(&stats, argv[i])) !=
MAL_SUCCEED) {
+ fprintf(stderr, "status: internal
error: %s\n", e);
+ GDKfree(e);
+ exit(2);
}
- } else if (mode == START && stats->state !=
SABdbRunning) {
- snprintf(buf, 256, "%s %s\n", stats->dbname,
type);
- fputs(buf, f);
- fflush(f);
- if (wait == 1) {
- waitstats = NULL;
- printf("%sing database '%s'... ", type,
stats->dbname);
- fflush(stdout);
- do {
- /* don't spinlock, just wait
half a seconds ;) */
- MT_sleep_ms(500);
- if (waitstats != NULL)
-
SABAOTHfreeStatus(&waitstats);
- if ((e =
SABAOTHgetStatus(&waitstats, stats->dbname)) != MAL_SUCCEED) {
- fprintf(stderr, "\n%s:
internal error: %s\n", type, e);
- GDKfree(e);
- exit(2);
- }
- if (waitstats->state ==
SABdbRunning &&
-
waitstats->conns != NULL &&
-
waitstats->conns->val != NULL)
- {
- break;
- }
- /* note: we cannot see the
difference between a
- * still starting server
(inactive) and a server
- * that shuts down after
startup (inactive),
- * hence we don't check for
that here */
- } while (waitstats->state !=
SABdbCrashed);
- if (waitstats->state == SABdbCrashed) {
- printf("CRASHED during
startup!\n");
- ret = 1;
+
+ if (stats == NULL) {
+ fprintf(stderr, "status: no such
database: %s\n", argv[i]);
+ argv[i] = NULL;
+ } else {
+ if (orig == NULL) {
+ orig = stats;
+ w = stats;
} else {
- printf("done\n");
+ w = w->next = stats;
}
- SABAOTHfreeStatus(&waitstats);
}
}
- stats = stats->next;
}
-
- fclose(f);
-
- if (orig != NULL)
- SABAOTHfreeStatus(&orig);
-
- exit(ret);
}
-
- for (i = 1; i < argc; i++) {
- if (argv[i] != NULL) {
- if ((e = SABAOTHgetStatus(&stats, argv[i])) !=
MAL_SUCCEED) {
- fprintf(stderr, "%s: internal error: %s\n",
type, e);
- GDKfree(e);
- exit(2);
+
+ stats = orig;
+ while (stats != NULL) {
+ if (mode == STOP || mode == KILL) {
+ if (stats->state == SABdbRunning) {
+ printf("%sing database '%s'... ", type,
stats->dbname);
+ fflush(stdout);
+ len = snprintf(buf, sizeof(buf),
+ "%s %s\n", stats->dbname, type);
+ send(sock, buf, len, 0);
+ if ((len = recv(sock, buf, sizeof(buf), 0)) <=
0) {
+ fprintf(stderr, "\n%s: no response from
merovingian\n",
+ type);
+ exit(2);
+ }
+ buf[len] = '\0';
+ if (strcmp(buf, "OK\n") == 0) {
+ printf("done\n");
+ } else {
+ printf("FAILED:\n%s", buf);
+ ret = 1;
+ }
+ } else if (doall != 1) {
+ printf("%s: database is not running: %s\n",
type, argv[i]);
}
-
- if (stats == NULL) {
- fprintf(stderr, "%s: no such database: %s\n",
type, argv[i]);
- } else {
- if ((mode == STOP || mode == KILL) &&
- stats->state != SABdbRunning)
- {
- printf("%s: database is not running:
%s\n", type, argv[i]);
- } else if (mode == START && stats->state ==
SABdbRunning) {
- printf("%s: database is already
running: %s\n",
- type, argv[i]);
+ } else if (mode == START) {
+ if (stats->state != SABdbRunning) {
+ printf("%sing database '%s'... ", type,
stats->dbname);
+ fflush(stdout);
+ len = snprintf(buf, sizeof(buf),
+ "%s %s\n", stats->dbname, type);
+ send(sock, buf, len, 0);
+ if ((len = recv(sock, buf, sizeof(buf), 0)) <=
0) {
+ fprintf(stderr, "\n%s: no response from
merovingian\n",
+ type);
+ exit(2);
+ }
+ buf[len] = '\0';
+ if (strcmp(buf, "OK\n") == 0) {
+ printf("done\n");
} else {
- if (mode == STOP || mode == KILL) {
- snprintf(buf, 256, "%s %s\n",
stats->dbname, type);
- fputs(buf, f);
- fflush(f);
- if (wait == 1) {
- waitstats = NULL;
- printf("%sing database
'%s'... ",
- type,
stats->dbname);
- fflush(stdout);
- do {
- /* don't
spinlock, just wait half a seconds ;) */
-
MT_sleep_ms(500);
- if (waitstats
!= NULL)
-
SABAOTHfreeStatus(&waitstats);
- if ((e =
SABAOTHgetStatus(&waitstats, stats->dbname)) != MAL_SUCCEED) {
-
fprintf(stderr, "\n%s: internal error: %s\n", type, e);
-
GDKfree(e);
- exit(2);
- }
- } while
(waitstats->state == SABdbRunning);
- if (waitstats->state ==
SABdbCrashed) {
- printf("CRASHED
after shutting down!\n");
- ret = 1;
- } else {
-
printf("done\n");
- }
-
SABAOTHfreeStatus(&waitstats);
- }
- } else if (mode == START) {
- snprintf(buf, 256, "%s %s\n",
stats->dbname, type);
- fputs(buf, f);
- fflush(f);
- if (wait == 1) {
- waitstats = NULL;
- printf("%sing database
'%s'... ",
- type,
stats->dbname);
- fflush(stdout);
- do {
- /* don't
spinlock, just wait half a seconds ;) */
-
MT_sleep_ms(500);
- if (waitstats
!= NULL)
-
SABAOTHfreeStatus(&waitstats);
- if ((e =
SABAOTHgetStatus(&waitstats, stats->dbname)) != MAL_SUCCEED) {
-
fprintf(stderr, "\n%s: internal error: %s\n", type, e);
-
GDKfree(e);
- exit(2);
- }
- if
(waitstats->state == SABdbRunning &&
-
waitstats->conns != NULL &&
-
waitstats->conns->val != NULL)
- {
- break;
- }
- /* note: we
cannot see the difference
- * between a
still starting server
- * (inactive)
and a server that shuts
- * down after
startup (inactive), hence
- * we don't
check for that here */
- } while
(waitstats->state != SABdbCrashed);
- if (waitstats->state ==
SABdbCrashed) {
- printf("CRASHED
during startup!\n");
- ret = 1;
- } else {
-
printf("done\n");
- }
-
SABAOTHfreeStatus(&waitstats);
- }
- }
+ printf("FAILED:\n%s", buf);
+ ret = 1;
}
-
- SABAOTHfreeStatus(&stats);
+ } else if (doall != 1 && stats->state == SABdbRunning) {
+ printf("%s: database is already running: %s\n",
+ type, stats->dbname);
}
}
+ stats = stats->next;
}
- fclose(f);
+ close(sock);
+
+ if (orig != NULL)
+ SABAOTHfreeStatus(&orig);
+
exit(ret);
}
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
_______________________________________________
Monetdb-sql-checkins mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/monetdb-sql-checkins