summaryrefslogtreecommitdiff
path: root/src/shell.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/shell.c')
-rw-r--r--src/shell.c330
1 files changed, 330 insertions, 0 deletions
diff --git a/src/shell.c b/src/shell.c
new file mode 100644
index 0000000..1f8d28d
--- /dev/null
+++ b/src/shell.c
@@ -0,0 +1,330 @@
+
+/* OpenIDA - Outil d'analyse de fichiers binaires
+ * shell.c - panneau d'affichage du shell Python
+ *
+ * Copyright (C) 2006-2007 Cyrille Bagard
+ *
+ * This file is part of OpenIDA.
+ *
+ * OpenIDA is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * OpenIDA is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+
+#include "shell.h"
+
+
+#include <pty.h>
+#include <stdio.h>
+#include <string.h>
+#include <sys/epoll.h>
+#include <sys/types.h>
+#include <vte/reaper.h>
+#include <vte/vte.h>
+
+
+#include <config.h>
+
+
+#include <Python.h>
+
+
+static pid_t child = 0;
+
+
+#define _(str) str
+
+
+
+/* Réagit à la terminaison d'un shell Python lancé. */
+static void terminal_child_exited_cb(VteReaper *, GPid, gint, VteTerminal *);
+
+/* Lance un nouveau shell Python dans un terminal donné. */
+static void run_new_shell_in_terminal(VteTerminal *);
+
+/* Réagit aux premières lignes de l'interpréteur Python. */
+void python_started_cb(VteTerminal *, gpointer);
+
+
+
+/* Exécute un shell interprétant du Python. */
+static gpointer python_shell_thread(gpointer);
+
+
+ int amaster;
+ int aslave;
+ char name[64];
+
+
+/******************************************************************************
+* *
+* Paramètres : ref = adresse de l'espace de référencements. *
+* *
+* Description : Construit le panneau d'affichage des symboles. *
+* *
+* Retour : Adresse du panneau mis en place. *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+GtkWidget *build_shell_panel(GObject *ref)
+{
+ GtkWidget *result; /* Panneau à retourner */
+ GtkWidget *term; /* Terminal proprement dit */
+
+
+
+ GError *error; /* Bilan de création de thread */
+
+
+
+ term = vte_terminal_new();
+
+ result = gtk_scrolled_window_new(NULL, GTK_ADJUSTMENT(VTE_TERMINAL(term)->adjustment));
+ gtk_widget_show(result);
+
+ gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(result), GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
+ gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(result), GTK_SHADOW_IN);
+
+ gtk_widget_show(term);
+ gtk_container_add(GTK_CONTAINER(result), term);
+
+
+ vte_terminal_set_cursor_blinks(VTE_TERMINAL(term), TRUE);
+
+
+ //return result;
+
+ openpty(&amaster, &aslave, name, NULL, NULL);
+
+
+ fprintf(stderr, "m = %d, s = %d, n = \"%s\"\n", amaster,
+ aslave, name);
+
+
+ vte_terminal_set_pty(VTE_TERMINAL(term), amaster);
+
+
+ if (!g_thread_create((GThreadFunc)python_shell_thread, term, FALSE, &error))
+ {
+ printf ("Failed to create the thread: %s\n", error->message);
+ }
+
+
+
+
+ /*
+ g_signal_connect(vte_reaper_get(), "child-exited",
+ G_CALLBACK(terminal_child_exited_cb), term);
+
+
+ run_new_shell_in_terminal(VTE_TERMINAL(term));
+ */
+
+
+ return result;
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : reaper = surveillant des processus exécuté dans le terminal. *
+* pid = identifiant du processus terminé. *
+* status = informations sur la sortie de l'interpréteur. *
+* term = terminal affiché à l'écran. *
+* *
+* Description : Réagit à la terminaison d'un shell Python lancé. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void terminal_child_exited_cb(VteReaper *reaper, GPid pid, gint status, VteTerminal *term)
+{
+
+ vte_terminal_feed(term, _("Exit detected ; lauching an new Python shell...\n\r"), -1);
+
+
+ run_new_shell_in_terminal(term);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : term = terminal affiché à l'écran. *
+* *
+* Description : Lance un nouveau shell Python dans un terminal donné. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static void run_new_shell_in_terminal(VteTerminal *term)
+{
+ gdouble refval; /* Attente active (bouh !) */
+ size_t len; /* Longueur de chaîne */
+
+ char *args[] = { "python", NULL };
+
+#ifdef DEBUG
+ char *env[] = { NULL, NULL };
+#else
+ char **env = NULL;
+#endif
+
+ refval = gtk_adjustment_get_value(GTK_ADJUSTMENT(term->adjustment));
+
+#ifdef DEBUG
+ len = strlen("PYTHONPATH=") + strlen(PACKAGE_SOURCE_DIR) + strlen("/src/plugins/pyoida");
+
+ env[0] = (char *)calloc(len + 1, sizeof(char));
+
+ strcpy(env[0], "PYTHONPATH=");
+ strcat(env[0], PACKAGE_SOURCE_DIR);
+ strcat(env[0], "/src/plugins/pyoida");
+#endif
+
+ child = vte_terminal_fork_command(VTE_TERMINAL(term), args[0], args,
+ env, NULL, 0, 0, 0);
+
+ vte_reaper_add_child(child);
+
+ printf("ref :: %g\n", refval);
+
+ //while (refval == gtk_adjustment_get_value(GTK_ADJUSTMENT(term->adjustment)));
+
+
+ g_signal_connect(term, "contents-changed",
+ G_CALLBACK(python_started_cb), NULL);
+
+}
+
+
+/******************************************************************************
+* *
+* Paramètres : term = terminal affiché à l'écran. *
+* data = adresse non utilisée ici. *
+* *
+* Description : Réagit aux premières lignes de l'interpréteur Python. *
+* *
+* Retour : - *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+void python_started_cb(VteTerminal *term, gpointer data)
+{
+ static int counter = 0; /* Saut du prologue */
+
+ if (counter++ == 0) return;
+ else counter = 0;
+
+ vte_terminal_feed_child(term, "import pyoida\n", -1);
+
+ vte_terminal_feed_child(term, "from pyoida import *\n", -1);
+
+ g_signal_handlers_disconnect_by_func(term, G_CALLBACK(python_started_cb), NULL);
+
+}
+
+
+
+/******************************************************************************
+* *
+* Paramètres : ????????????????????????????????????????????????? *
+* *
+* Description : Exécute un shell interprétant du Python. *
+* *
+* Retour : ??? *
+* *
+* Remarques : - *
+* *
+******************************************************************************/
+
+static gpointer python_shell_thread(gpointer data)
+{
+ FILE *stream;
+
+ printf("==== FE :: '%s'\n", ptsname(aslave));
+
+
+
+
+ //stream = fopen("/dev/pts/21", "w+");
+ stream = fdopen(aslave, "w+");
+ if (stream == NULL)
+ {
+ perror("fdopen");
+ return NULL;
+ }
+
+
+ /* Mise à jour des entrées/sorties */
+ /*
+ close(STDIN_FILENO);
+ close(STDOUT_FILENO);
+ close(STDERR_FILENO);
+ dup(aslave);
+ dup(aslave);
+ dup(aslave);
+ */
+
+
+
+
+ Py_Initialize();
+
+
+ amaster = STDIN_FILENO;
+
+
+ write(amaster, "import pyoida\n", strlen("import pyoida\n"));
+ write(amaster, "from pyoida import *\n", strlen("from pyoida import *\n"));
+
+
+
+
+
+ write(amaster, "logger.log_simple_message(2, 'uhih')\n", strlen("logger.log_simple_message(2, 'uhih')\n"));
+
+
+
+ write(amaster, "for i in pyoida.current_binary().lines():\n", strlen("for i in pyoida.current_binary().lines():\n"));
+ write(amaster, "\tprint i\n", strlen("\tprint i\n"));
+
+
+
+
+ printf("+++++++++++++++++++++++++++looping\n");
+
+ PyRun_AnyFile(stream, NULL);
+
+ printf("===========================looping\n");
+
+
+ Py_Finalize();
+
+
+
+ return NULL;
+
+}