[Freeciv-Dev] (PR#10282) internal civserver run inside gdb
[Top] [All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
To: |
undisclosed-recipients: ; |
Subject: |
[Freeciv-Dev] (PR#10282) internal civserver run inside gdb |
From: |
"Mateusz Stefek" <mstefek@xxxxxxxxx> |
Date: |
Thu, 23 Sep 2004 12:15:30 -0700 |
Reply-to: |
rt@xxxxxxxxxxx |
<URL: http://rt.freeciv.org/Ticket/Display.html?id=10282 >
With this patch civclient runs it's internal civserver through gdb.
Backtrace is displayed in chat window, if server crashes.
This is of course not intended for commit.
(If I added runtime gdb detection, who knows)
To test it run a simple game, set timeout to -1 and type
'killall -11 civserver' in console.
--
mateusz
? civgame-3000.sav.gz
? civgame-3500.sav.gz
? civgame-3950.sav.gz
? core.16019
? gdb_script
Index: clinet.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/clinet.c,v
retrieving revision 1.100
diff -u -r1.100 clinet.c
--- clinet.c 20 Jul 2004 17:13:52 -0000 1.100
+++ clinet.c 23 Sep 2004 19:12:09 -0000
@@ -74,6 +74,7 @@
#include "chatline_g.h"
#include "civclient.h"
#include "climisc.h"
+#include "connectdlg_common.h"
#include "connectdlg_g.h"
#include "dialogs_g.h" /* popdown_races_dialog() */
#include "gui_main_g.h" /* add_net_input(), remove_net_input()
*/
@@ -119,6 +120,7 @@
append_output_window(_("Lost connection to server!"));
freelog(LOG_NORMAL, "lost connection to server");
close_socket_nomessage(pc);
+ client_kill_server();
}
/**************************************************************************
Index: connectdlg_common.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/connectdlg_common.c,v
retrieving revision 1.23
diff -u -r1.23 connectdlg_common.c
--- connectdlg_common.c 18 Sep 2004 17:47:28 -0000 1.23
+++ connectdlg_common.c 23 Sep 2004 19:12:10 -0000
@@ -124,6 +124,8 @@
return client_has_hack;
}
+static int client_gdb[2];
+static int gdb_client[2];
/**************************************************************************
Kills the server if the client has started it.
**************************************************************************/
@@ -139,6 +141,13 @@
server_process = INVALID_HANDLE_VALUE;
loghandle = INVALID_HANDLE_VALUE;
#else
+ char buf[50000];
+ append_output_window("Internal server killed. Gdb output:");
+ int l = read(gdb_client[0], buf, 50000);
+ if (l != -1) {
+ buf[l] = '\0';
+ }
+ append_output_window(buf);
kill(server_pid, SIGTERM);
waitpid(server_pid, NULL, WUNTRACED);
server_pid = - 1;
@@ -155,6 +164,7 @@
client_kill_server();
}
+
/****************************************************************
forks a server if it can. returns FALSE is we find we couldn't start
the server.
@@ -197,66 +207,34 @@
internal_server_port = find_next_free_port(DEFAULT_SOCK_PORT);
# ifdef HAVE_WORKING_FORK
+
+ pipe(client_gdb);
+ pipe(gdb_client);
+ FILE* gdb_script = fopen("gdb_script", "w+");
+ fprintf(gdb_script, "run -p %d -q 3 -e >/dev/null\nbacktrace\nquit\n\n",
internal_server_port);
+ fclose(gdb_script);
+
server_pid = fork();
if (server_pid == 0) {
- int fd, argc = 0;
const int max_nargs = 13;
- char *argv[max_nargs + 1], port_buf[32];
-
- /* inside the child */
-
- /* Set up the command-line parameters. */
- my_snprintf(port_buf, sizeof(port_buf), "%d", internal_server_port);
- argv[argc++] = "civserver";
- argv[argc++] = "-p";
- argv[argc++] = port_buf;
- argv[argc++] = "-q";
- argv[argc++] = "1";
- argv[argc++] = "-e";
- if (logfile) {
- argv[argc++] = "--debug";
- argv[argc++] = "3";
- argv[argc++] = "--log";
- argv[argc++] = logfile;
- }
- if (scriptfile) {
- argv[argc++] = "--read";
- argv[argc++] = scriptfile;
- }
- argv[argc] = NULL;
- assert(argc <= max_nargs);
-
- /* avoid terminal spam, but still make server output available */
- fclose(stdout);
- fclose(stderr);
-
- /* include the port to avoid duplication */
- if (logfile) {
- fd = open(logfile, O_WRONLY | O_CREAT);
-
- if (fd != 1) {
- dup2(fd, 1);
- }
- if (fd != 2) {
- dup2(fd, 2);
- }
- fchmod(1, 0644);
- }
-
- /* If it's still attatched to our terminal, things get messed up,
- but civserver needs *something* */
- fclose(stdin);
- fd = open("/dev/null", O_RDONLY);
- if (fd != 0) {
- dup2(fd, 0);
- }
-
- /* these won't return on success */
- execvp("./ser", argv);
- execvp("./server/civserver", argv);
- execvp("civserver", argv);
+ char *argv[max_nargs + 1];
+ dup2(client_gdb[0], 0);
+ dup2(gdb_client[1], 1);
+ close(2);
+ close(client_gdb[0]);
+ close(client_gdb[1]);
+ close(gdb_client[0]);
+ close(gdb_client[1]);
+ argv[0] = "gdb";
+ argv[1] = "civserver";
+ argv[2] = "-x";
+ argv[3] = "gdb_script";
+ argv[4] = "-q";
+ argv[5] = NULL;
+ execvp("gdb", argv);
+
/* This line is only reached if civserver cannot be started,
* so we kill the forked process.
* Calling exit here is dangerous due to X11 problems (async replies) */
@@ -313,7 +291,7 @@
# endif
# endif
-
+
/* a reasonable number of tries */
while (connect_to_server(user_name, "localhost", internal_server_port,
buf, sizeof(buf)) == -1) {
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Freeciv-Dev] (PR#10282) internal civserver run inside gdb,
Mateusz Stefek <=
|
|