Addition of argument types to the debug cli

Added commands to settign and clearign status bits in the servers
This commit is contained in:
Mark Riddoch
2013-06-25 20:15:57 +02:00
parent 66c130d8a4
commit 3338e9cdb0
3 changed files with 190 additions and 25 deletions

View File

@ -59,7 +59,7 @@ SERVER *server;
server->protocol = strdup(protocol); server->protocol = strdup(protocol);
server->port = port; server->port = port;
memset(&server->stats, sizeof(SERVER_STATS), 0); memset(&server->stats, sizeof(SERVER_STATS), 0);
server->status = 0; server->status = SERVER_RUNNING;
server->nextdb = NULL; server->nextdb = NULL;
spinlock_acquire(&server_spin); spinlock_acquire(&server_spin);
@ -159,6 +159,7 @@ SERVER *ptr;
{ {
dcb_printf(dcb, "Server %p\n", ptr); dcb_printf(dcb, "Server %p\n", ptr);
dcb_printf(dcb, "\tServer: %s\n", ptr->name); dcb_printf(dcb, "\tServer: %s\n", ptr->name);
dcb_printf(dcb, "\tStatus: %s\n", server_status(ptr));
dcb_printf(dcb, "\tProtocol: %s\n", ptr->protocol); dcb_printf(dcb, "\tProtocol: %s\n", ptr->protocol);
dcb_printf(dcb, "\tPort: %d\n", ptr->port); dcb_printf(dcb, "\tPort: %d\n", ptr->port);
dcb_printf(dcb, "\tNumber of connections: %d\n", ptr->stats.n_connections); dcb_printf(dcb, "\tNumber of connections: %d\n", ptr->stats.n_connections);
@ -167,6 +168,23 @@ SERVER *ptr;
spinlock_release(&server_spin); spinlock_release(&server_spin);
} }
/**
* Print server details to a DCB
*
* Designed to be called within a debugger session in order
* to display all active servers within the gateway
*/
void
dprintServer(DCB *dcb, SERVER *server)
{
dcb_printf(dcb, "Server %p\n", server);
dcb_printf(dcb, "\tServer: %s\n", server->name);
dcb_printf(dcb, "\tStatus: %s\n", server_status(server));
dcb_printf(dcb, "\tProtocol: %s\n", server->protocol);
dcb_printf(dcb, "\tPort: %d\n", server->port);
dcb_printf(dcb, "\tNumber of connections: %d\n", server->stats.n_connections);
}
/** /**
* Convert a set of server status flags to a string, the returned * Convert a set of server status flags to a string, the returned
* string has been malloc'd and must be free'd by the caller * string has been malloc'd and must be free'd by the caller
@ -192,3 +210,27 @@ char *status = NULL;
strcat(status, "Slave"); strcat(status, "Slave");
return status; return status;
} }
/**
* Set a status bit in the server
*
* @param server The server to update
* @param bit The bit to set for the server
*/
void
server_set_status(SERVER *server, int bit)
{
server->status |= bit;
}
/**
* Clear a status bit in the server
*
* @param server The server to update
* @param bit The bit to clear for the server
*/
void
server_clear_status(SERVER *server, int bit)
{
server->status &= ~bit;
}

View File

@ -67,5 +67,8 @@ extern int server_free(SERVER *);
extern void printServer(SERVER *); extern void printServer(SERVER *);
extern void printAllServers(); extern void printAllServers();
extern void dprintAllServers(DCB *); extern void dprintAllServers(DCB *);
extern void dprintServer(DCB *, SERVER *);
extern char *server_status(SERVER *); extern char *server_status(SERVER *);
extern void server_set_status(SERVER *, int);
extern void server_clear_status(SERVER *, int);
#endif #endif

View File

@ -46,6 +46,7 @@
#include <router.h> #include <router.h>
#include <modules.h> #include <modules.h>
#include <atomic.h> #include <atomic.h>
#include <server.h>
#include <spinlock.h> #include <spinlock.h>
#include <dcb.h> #include <dcb.h>
#include <poll.h> #include <poll.h>
@ -54,6 +55,8 @@
#define MAXARGS 5 #define MAXARGS 5
#define ARG_TYPE_ADDRESS 1
#define ARG_TYPE_STRING 2
/** /**
* The subcommand structure * The subcommand structure
* *
@ -64,22 +67,35 @@ struct subcommand {
int n_args; int n_args;
void (*fn)(); void (*fn)();
char *help; char *help;
int arg_types[3];
}; };
/** /**
* The subcommands of the show command * The subcommands of the show command
*/ */
struct subcommand showoptions[] = { struct subcommand showoptions[] = {
{ "sessions", 0, dprintAllSessions, "Show all active sessions in the gateway" }, { "sessions", 0, dprintAllSessions, "Show all active sessions in the gateway",
{ "session", 1, dprintSession, "Show a single session in the gateway, e.g. show session 0x284830" }, {0, 0, 0} },
{ "services", 0, dprintAllServices, "Show all configured services in the gateway" }, { "session", 1, dprintSession, "Show a single session in the gateway, e.g. show session 0x284830",
{ "servers", 0, dprintAllServers, "Show all configured servers" }, {ARG_TYPE_ADDRESS, 0, 0} },
{ "modules", 0, dprintAllModules, "Show all currently loaded modules" }, { "services", 0, dprintAllServices, "Show all configured services in the gateway",
{ "dcbs", 0, dprintAllDCBs, "Show all descriptor control blocks (network connections)" }, {0, 0, 0} },
{ "dcb", 1, dprintDCB, "Show a single descriptor control block e.g. show dcb 0x493340" }, { "servers", 0, dprintAllServers, "Show all configured servers",
{ "epoll", 0, dprintPollStats, "Show the poll statistics" }, {0, 0, 0} },
{ "users", 1, dcb_usersPrint, "Show statistics for a suers table" }, { "server", 1, dprintServer, "Show details for a server, e.g. show server 0x485390",
{ NULL, 0, NULL, NULL } {ARG_TYPE_ADDRESS, 0, 0} },
{ "modules", 0, dprintAllModules, "Show all currently loaded modules",
{0, 0, 0} },
{ "dcbs", 0, dprintAllDCBs, "Show all descriptor control blocks (network connections)",
{0, 0, 0} },
{ "dcb", 1, dprintDCB, "Show a single descriptor control block e.g. show dcb 0x493340",
{ARG_TYPE_ADDRESS, 0, 0} },
{ "epoll", 0, dprintPollStats, "Show the poll statistics",
{0, 0, 0} },
{ "users", 1, dcb_usersPrint, "Show statistics for a suers table",
{ARG_TYPE_ADDRESS, 0, 0} },
{ NULL, 0, NULL, NULL,
{0, 0, 0} }
}; };
extern void shutdown_gateway(); extern void shutdown_gateway();
@ -89,9 +105,12 @@ static void shutdown_service(DCB *dcb, SERVICE *service);
* The subcommands of the shutdown command * The subcommands of the shutdown command
*/ */
struct subcommand shutdownoptions[] = { struct subcommand shutdownoptions[] = {
{ "gateway", 0, shutdown_gateway, "Shutdown the gateway" }, { "gateway", 0, shutdown_gateway, "Shutdown the gateway",
{ "service", 1, shutdown_service, "Shutdown a service, e.g. shutdown service 0x4838320" }, {0, 0, 0} },
{ NULL, 0, NULL, NULL } { "service", 1, shutdown_service, "Shutdown a service, e.g. shutdown service 0x4838320",
{ARG_TYPE_ADDRESS, 0, 0} },
{ NULL, 0, NULL, NULL,
{0, 0, 0} }
}; };
static void restart_service(DCB *dcb, SERVICE *service); static void restart_service(DCB *dcb, SERVICE *service);
@ -99,8 +118,32 @@ static void restart_service(DCB *dcb, SERVICE *service);
* The subcommands of the restart command * The subcommands of the restart command
*/ */
struct subcommand restartoptions[] = { struct subcommand restartoptions[] = {
{ "service", 1, restart_service, "Restart a service, e.g. restart service 0x4838320" }, { "service", 1, restart_service, "Restart a service, e.g. restart service 0x4838320",
{ NULL, 0, NULL, NULL } {ARG_TYPE_ADDRESS, 0, 0} },
{ NULL, 0, NULL, NULL,
{0, 0, 0} }
};
static void set_server(DCB *dcb, SERVER *server, char *bit);
/**
* The subcommands of the set command
*/
struct subcommand setoptions[] = {
{ "server", 2, set_server, "Set the status of a server. E.g. set server 0x4838320 master",
{ARG_TYPE_ADDRESS, ARG_TYPE_STRING, 0} },
{ NULL, 0, NULL, NULL,
{0, 0, 0} }
};
static void clear_server(DCB *dcb, SERVER *server, char *bit);
/**
* The subcommands of the clear command
*/
struct subcommand clearoptions[] = {
{ "server", 2, clear_server, "Clear the status of a server. E.g. clear server 0x4838320 master",
{ARG_TYPE_ADDRESS, ARG_TYPE_STRING, 0} },
{ NULL, 0, NULL, NULL,
{0, 0, 0} }
}; };
/** /**
@ -113,6 +156,8 @@ static struct {
{ "show", showoptions }, { "show", showoptions },
{ "shutdown", shutdownoptions }, { "shutdown", shutdownoptions },
{ "restart", restartoptions }, { "restart", restartoptions },
{ "set", setoptions },
{ "clear", clearoptions },
{ NULL, NULL } { NULL, NULL }
}; };
@ -124,10 +169,17 @@ static struct {
* @param arg The string representation of the argument * @param arg The string representation of the argument
* @return The argument as a long integer * @return The argument as a long integer
*/ */
static long static unsigned long
convert_arg(char *arg) convert_arg(char *arg, int arg_type)
{ {
return strtol(arg, NULL, 0); switch (arg_type)
{
case ARG_TYPE_ADDRESS:
return (unsigned long)strtol(arg, NULL, 0);
case ARG_TYPE_STRING:
return (unsigned long)arg;
}
return 0;
} }
/** /**
@ -230,16 +282,22 @@ char *saveptr, *delim = " \t\r\n";
cmds[i].options[j].fn(dcb); cmds[i].options[j].fn(dcb);
break; break;
case 1: case 1:
cmds[i].options[j].fn(dcb, convert_arg(args[2])); cmds[i].options[j].fn(dcb, convert_arg(args[2],
cmds[i].options[j].arg_types[0]));
break; break;
case 2: case 2:
cmds[i].options[j].fn(dcb, convert_arg(args[2]), cmds[i].options[j].fn(dcb, convert_arg(args[2],
convert_arg(args[3])); cmds[i].options[j].arg_types[0]),
convert_arg(args[3],
cmds[i].options[j].arg_types[1]));
break; break;
case 3: case 3:
cmds[i].options[j].fn(dcb, convert_arg(args[2]), cmds[i].options[j].fn(dcb, convert_arg(args[2],
convert_arg(args[3]), cmds[i].options[j].arg_types[0]),
convert_arg(args[4])); convert_arg(args[3],
cmds[i].options[j].arg_types[1]),
convert_arg(args[4],
cmds[i].options[j].arg_types[2]));
} }
found = 1; found = 1;
} }
@ -279,3 +337,65 @@ restart_service(DCB *dcb, SERVICE *service)
{ {
serviceRestart(service); serviceRestart(service);
} }
static struct {
char *str;
unsigned int bit;
} ServerBits[] = {
{ "running", SERVER_RUNNING },
{ "master", SERVER_MASTER },
{ NULL, 0 }
};
/**
* Map the server status bit
*
* @param str String representation
* @return bit value or 0 on error
*/
static unsigned int
server_map_status(char *str)
{
int i;
for (i = 0; ServerBits[i].str; i++)
if (!strcasecmp(str, ServerBits[i].str))
return ServerBits[i].bit;
return 0;
}
/**
* Set the status bit of a server
*
* @param dcb DCB to send output to
* @param server The server to set the status of
* @param bit String representation of the status bit
*/
static void
set_server(DCB *dcb, SERVER *server, char *bit)
{
unsigned int bitvalue;
if ((bitvalue = server_map_status(bit)) != 0)
server_set_status(server, bitvalue);
else
dcb_printf(dcb, "Unknown status bit %s\n", bit);
}
/**
* Clear the status bit of a server
*
* @param dcb DCB to send output to
* @param server The server to set the status of
* @param bit String representation of the status bit
*/
static void
clear_server(DCB *dcb, SERVER *server, char *bit)
{
unsigned int bitvalue;
if ((bitvalue = server_map_status(bit)) != 0)
server_clear_status(server, bitvalue);
else
dcb_printf(dcb, "Unknown status bit %s\n", bit);
}