274 lines
6.5 KiB
C
274 lines
6.5 KiB
C
/*
|
|
S y n c h r o n i z e
|
|
|
|
Synchronize parameters in this server with parameters from another
|
|
SICS server.
|
|
|
|
Mark Koennecke, March 2001
|
|
|
|
Use internal connection.
|
|
Mark Koennecke, July 2002
|
|
|
|
changed timeout units in NETRead from us to ms
|
|
the timing could be optimized (no need for SicsWait
|
|
when timeout properly choosen (could be in the region of 1 second )
|
|
M.Zolliker, August 04
|
|
*/
|
|
#include "sics.h"
|
|
#include "network.h"
|
|
#include "status.h"
|
|
#include "synchronize.h"
|
|
|
|
|
|
/*-----------------------------------------------------------------------
|
|
Some file statics which hold the connection parameters
|
|
------------------------------------------------------------------------*/
|
|
static char *hostname, *looser, *password, *syncFile;
|
|
static int port;
|
|
static mkChannel *connection = NULL;
|
|
/*-----------------------------------------------------------------------*/
|
|
static void syncLogin(void)
|
|
{
|
|
int test, i;
|
|
char pBueffel[2048], pRead[80];
|
|
|
|
/*
|
|
connect
|
|
*/
|
|
connection = NETConnect(hostname, port);
|
|
for (i = 0; i < 10; i++) {
|
|
NETRead(connection, pBueffel, 1020, 10); /* 10 ms M.Z */
|
|
if (strstr(pBueffel, "OK") != NULL) {
|
|
break;
|
|
}
|
|
SicsWait(1);
|
|
}
|
|
if (connection != NULL) {
|
|
/*
|
|
try a login
|
|
*/
|
|
snprintf(pBueffel,sizeof(pBueffel)-1, "%s %s\n", looser, password);
|
|
test = NETWrite(connection, pBueffel, strlen(pBueffel));
|
|
if (test != 1) {
|
|
printf("Failed at writing user/password\n");
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
}
|
|
|
|
pBueffel[0] = '\0';
|
|
for (i = 0; i < 60; i++) {
|
|
memset(pRead, 0, 80);
|
|
test = NETRead(connection, pRead, 70, 10); /* 10 ms M.Z. */
|
|
if (test < 0) {
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
} else {
|
|
strcat(pBueffel, pRead);
|
|
}
|
|
if (strstr(pBueffel, "Login OK") == NULL) {
|
|
test = 0;
|
|
} else {
|
|
test = 1;
|
|
break;
|
|
}
|
|
SicsWait(1);
|
|
}
|
|
if (!test) {
|
|
printf("Bad reply to login: %s\n", pBueffel);
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
}
|
|
}
|
|
}
|
|
|
|
/*---------------------------------------------------------------------*/
|
|
static void killSync(void *pData)
|
|
{
|
|
if (connection) {
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
}
|
|
if (hostname)
|
|
free(hostname);
|
|
if (looser)
|
|
free(looser);
|
|
if (password)
|
|
free(password);
|
|
if (syncFile)
|
|
free(syncFile);
|
|
}
|
|
|
|
/*----------------------------------------------------------------------*/
|
|
int MakeSync(SConnection * pCon, SicsInterp * pSics, void *pData,
|
|
int argc, char *argv[])
|
|
{
|
|
char pBueffel[256];
|
|
int iRet;
|
|
|
|
/*
|
|
check arguments: we need host, port, user and passwd
|
|
*/
|
|
if (argc < 5) {
|
|
SCWrite(pCon,
|
|
"ERROR: need parameters: host port user passwd : for sync creation",
|
|
eError);
|
|
return 0;
|
|
}
|
|
/*
|
|
copy parameters
|
|
*/
|
|
hostname = strdup(argv[1]);
|
|
port = atof(argv[2]);
|
|
looser = strdup(argv[3]);
|
|
password = strdup(argv[4]);
|
|
if (argc > 5) {
|
|
syncFile = strdup(argv[5]);
|
|
} else {
|
|
syncFile = NULL;
|
|
}
|
|
pServ->simMode = 1;
|
|
|
|
/*
|
|
add the command to the Interpreter
|
|
*/
|
|
iRet = AddCommand(pSics, "sync", Synchronize, killSync, NULL);
|
|
if (!iRet) {
|
|
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: duplicate command sync not created");
|
|
killSync(NULL);
|
|
SCWrite(pCon, pBueffel, eError);
|
|
return 0;
|
|
}
|
|
|
|
return 1;
|
|
}
|
|
|
|
/*----------------------------------------------------------------------*/
|
|
int Synchronize(SConnection * pCon, SicsInterp * pSics, void *pData,
|
|
int argc, char *argv[])
|
|
{
|
|
char pBueffel[2048];
|
|
char pRead[80];
|
|
int test, i;
|
|
SConnection *internalCon = NULL;
|
|
int try;
|
|
|
|
try = 2;
|
|
tryagain:
|
|
try--;
|
|
|
|
/*
|
|
check for connection
|
|
*/
|
|
if (connection == NULL) {
|
|
syncLogin();
|
|
if (connection == NULL) {
|
|
snprintf(pBueffel,sizeof(pBueffel)-1, "ERROR: failed to connect to %s, %d for sync 'ing",
|
|
hostname, port);
|
|
SCWrite(pCon, pBueffel, eError);
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
/*
|
|
first tell the remote server to backup
|
|
*/
|
|
SetStatusFixed(eBatch);
|
|
strcpy(pBueffel, "transact syncbackup");
|
|
if (syncFile != NULL) {
|
|
strcat(pBueffel, " ");
|
|
strcat(pBueffel, syncFile);
|
|
}
|
|
strcat(pBueffel, "\n");
|
|
test = NETWrite(connection, pBueffel, strlen(pBueffel));
|
|
if (test != 1) {
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
ClearFixedStatus(eEager);
|
|
if (try > 0)
|
|
goto tryagain;
|
|
SCWrite(pCon, "ERROR: Failed to contact main SICS server", eError);
|
|
return 0;
|
|
}
|
|
/*
|
|
wait 60 seconds for correct message
|
|
*/
|
|
pServ->simMode = 0; /* bug fix: SicsWait returns right away if this would be
|
|
left at normal. Reset after loop
|
|
*/
|
|
pBueffel[0] = '\0';
|
|
for (i = 0; i < 60; i++) {
|
|
pRead[0] = '\0';
|
|
test = NETRead(connection, pRead, 75, 20); /* 20 ms M.Z. */
|
|
if (test < 0) {
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
ClearFixedStatus(eEager);
|
|
pServ->simMode = 1;
|
|
if (try > 0)
|
|
goto tryagain;
|
|
SCWrite(pCon, "ERROR: Failed to contact main SICS server", eError);
|
|
return 0;
|
|
} else {
|
|
if (test > 0) {
|
|
strlcat(pBueffel, pRead, sizeof pBueffel);
|
|
}
|
|
}
|
|
if (strstr(pBueffel, "TRANSACTIONFINISHED") != NULL) {
|
|
test = 1;
|
|
break;
|
|
} else {
|
|
test = 0;
|
|
}
|
|
SicsWait(1);
|
|
}
|
|
pServ->simMode = 1;
|
|
if (!test) {
|
|
SCWrite(pCon, "WARNING: sync server may not have executed backup",
|
|
eWarning);
|
|
}
|
|
|
|
/*
|
|
* relase the connection, this may be more stable
|
|
*/
|
|
NETClosePort(connection);
|
|
free(connection);
|
|
connection = NULL;
|
|
|
|
|
|
|
|
/*
|
|
now read the backup file and we are done
|
|
*/
|
|
internalCon = SCCreateDummyConnection(pSics);
|
|
if (internalCon == NULL) {
|
|
SCWrite(pCon, "ERROR: out of memory in sync", eError);
|
|
ClearFixedStatus(eEager);
|
|
return 0;
|
|
|
|
}
|
|
if (syncFile != NULL) {
|
|
snprintf(pBueffel,sizeof(pBueffel)-1, "restore %s", syncFile);
|
|
} else {
|
|
strcpy(pBueffel, "restore");
|
|
}
|
|
test = InterpExecute(pSics, internalCon, pBueffel);
|
|
SCDeleteConnection(internalCon);
|
|
ClearFixedStatus(eEager);
|
|
if (test != 1) {
|
|
SCWrite(pCon, "ERROR: Failed to read sync information", eError);
|
|
return 0;
|
|
}
|
|
|
|
/*
|
|
tell everybody that we have sync'ed
|
|
*/
|
|
ServerWriteGlobal("Simulation Server has SYNCHRONIZED!", eWarning);
|
|
|
|
return 1;
|
|
}
|