[Swfdec] 2 commits - libswfdec/swfdec_debugger.c
libswfdec/swfdec_script.c libswfdec/swfdec_script.h
Benjamin Otte
company at kemper.freedesktop.org
Tue Mar 13 04:51:33 PDT 2007
libswfdec/swfdec_debugger.c | 122 +++++++++++++++++++++++++++++++++++++++++---
libswfdec/swfdec_script.c | 38 +++++++------
libswfdec/swfdec_script.h | 9 +++
3 files changed, 145 insertions(+), 24 deletions(-)
New commits:
diff-tree f3ceb92e7405d2cef3398baa79712eaee6eeabd1 (from b1cd2edf289dde1bd89d3c513da13b4cf27bdf13)
Author: Benjamin Otte <otte at gnome.org>
Date: Tue Mar 13 11:57:49 2007 +0100
print constant pool strings verbatim instead of printing "Pool x"
diff --git a/libswfdec/swfdec_debugger.c b/libswfdec/swfdec_debugger.c
index 7f3546d..c17c315 100644
--- a/libswfdec/swfdec_debugger.c
+++ b/libswfdec/swfdec_debugger.c
@@ -32,32 +32,138 @@
/*** SwfdecDebuggerScript ***/
+typedef struct {
+ SwfdecConstantPool * constant_pool; /* current constant pool */
+ GArray * commands; /* SwfdecDebuggerCommands parsed so far */
+} ScriptParser;
+
+static char *
+swfdec_debugger_print_push (ScriptParser *parser, const guint8 *data, guint len)
+{
+ gboolean first = TRUE;
+ SwfdecBits bits;
+ GString *string = g_string_new ("Push");
+
+ swfdec_bits_init_data (&bits, data, len);
+ while (swfdec_bits_left (&bits)) {
+ guint type = swfdec_bits_get_u8 (&bits);
+ if (first)
+ g_string_append (string, " ");
+ else
+ g_string_append (string, ", ");
+ first = FALSE;
+ switch (type) {
+ case 0: /* string */
+ {
+ const char *s = swfdec_bits_skip_string (&bits);
+ if (!s) {
+ g_string_free (string, TRUE);
+ return NULL;
+ }
+ g_string_append_c (string, '"');
+ g_string_append (string, s);
+ g_string_append_c (string, '"');
+ break;
+ }
+ case 1: /* float */
+ g_string_append_printf (string, "%g", swfdec_bits_get_float (&bits));
+ break;
+ case 2: /* null */
+ g_string_append (string, "null");
+ break;
+ case 3: /* undefined */
+ g_string_append (string, "undefined");
+ break;
+ case 4: /* register */
+ g_string_append_printf (string, "Register %u", swfdec_bits_get_u8 (&bits));
+ break;
+ case 5: /* boolean */
+ g_string_append (string, swfdec_bits_get_u8 (&bits) ? "True" : "False");
+ break;
+ case 6: /* double */
+ g_string_append_printf (string, "%g", swfdec_bits_get_double (&bits));
+ break;
+ case 7: /* 32bit int */
+ g_string_append_printf (string, "%d", swfdec_bits_get_u32 (&bits));
+ break;
+ case 8: /* 8bit ConstantPool address */
+ case 9: /* 16bit ConstantPool address */
+ {
+ guint id;
+ const char *s;
+
+ if (!parser->constant_pool) {
+ SWFDEC_ERROR ("no constant pool");
+ g_string_free (string, TRUE);
+ return NULL;
+ }
+ id = type == 8 ? swfdec_bits_get_u8 (&bits) : swfdec_bits_get_u16 (&bits);
+ s = swfdec_constant_pool_get (parser->constant_pool, id);
+ if (!s) {
+ SWFDEC_ERROR ("constant pool size too small");
+ g_string_free (string, TRUE);
+ return NULL;
+ }
+ g_string_append_c (string, '"');
+ g_string_append (string, s);
+ g_string_append_c (string, '"');
+ }
+ break;
+ default:
+ SWFDEC_ERROR ("Push: type %u not implemented", type);
+ return JS_FALSE;
+ }
+ }
+ return g_string_free (string, FALSE);
+}
+
+/* NB: constant pool actions are special in that they are called at init time */
static gboolean
swfdec_debugger_add_command (gconstpointer bytecode, guint action,
- const guint8 *data, guint len, gpointer arrayp)
+ const guint8 *data, guint len, gpointer parserp)
{
+ ScriptParser *parser = parserp;
SwfdecDebuggerCommand command;
command.code = bytecode;
command.breakpoint = 0;
- command.description = swfdec_script_print_action (action, data, len);
- g_array_append_val (arrayp, command);
+ if (action == 0x96) {
+ /* PUSH */
+ command.description = swfdec_debugger_print_push (parser, data, len);
+ } else {
+ command.description = swfdec_script_print_action (action, data, len);
+ }
+ g_array_append_val (parser->commands, command);
+ if (action == 0x88) {
+ /* constant pool */
+ if (parser->constant_pool)
+ swfdec_constant_pool_free (parser->constant_pool);
+ parser->constant_pool = swfdec_constant_pool_new_from_action (data, len);
+ }
return TRUE;
}
static SwfdecDebuggerScript *
swfdec_debugger_script_new (SwfdecScript *script)
{
- GArray *array;
+ ScriptParser parser;
SwfdecDebuggerScript *ret;
ret = g_new0 (SwfdecDebuggerScript, 1);
ret->script = script;
swfdec_script_ref (script);
- array = g_array_new (TRUE, FALSE, sizeof (SwfdecDebuggerCommand));
- swfdec_script_foreach (script, swfdec_debugger_add_command, array);
- ret->n_commands = array->len;
- ret->commands = (SwfdecDebuggerCommand *) g_array_free (array, FALSE);
+ parser.commands = g_array_new (TRUE, FALSE, sizeof (SwfdecDebuggerCommand));
+ if (script->constant_pool) {
+ parser.constant_pool = swfdec_constant_pool_new_from_action (
+ script->constant_pool->data + 3, script->constant_pool->length - 3);
+ } else {
+ parser.constant_pool = NULL;
+ }
+ swfdec_script_foreach (script, swfdec_debugger_add_command, &parser);
+ ret->n_commands = parser.commands->len;
+ ret->commands = (SwfdecDebuggerCommand *) g_array_free (parser.commands, FALSE);
+ if (parser.constant_pool)
+ swfdec_constant_pool_free (parser.constant_pool);
return ret;
}
diff-tree b1cd2edf289dde1bd89d3c513da13b4cf27bdf13 (from d569f40ce1d270b721fd0b1fb12ed77a512d6e74)
Author: Benjamin Otte <otte at gnome.org>
Date: Tue Mar 13 11:54:30 2007 +0100
make this more debugger-friendly
- export SwfdecConstantPool
- ensure scripts are only added to the player when they are completely
initialized.
diff --git a/libswfdec/swfdec_script.c b/libswfdec/swfdec_script.c
index ac47a97..e261d61 100644
--- a/libswfdec/swfdec_script.c
+++ b/libswfdec/swfdec_script.c
@@ -43,9 +43,7 @@
/*** CONSTANT POOLS ***/
-typedef GPtrArray SwfdecConstantPool;
-
-static SwfdecConstantPool *
+SwfdecConstantPool *
swfdec_constant_pool_new_from_action (const guint8 *data, guint len)
{
guint8 *next;
@@ -79,20 +77,20 @@ swfdec_constant_pool_new_from_action (co
return pool;
}
-static guint
+guint
swfdec_constant_pool_size (SwfdecConstantPool *pool)
{
return pool->len;
}
-static const char *
+const char *
swfdec_constant_pool_get (SwfdecConstantPool *pool, guint i)
{
g_assert (i < pool->len);
return g_ptr_array_index (pool, i);
}
-static void
+void
swfdec_constant_pool_free (SwfdecConstantPool *pool)
{
g_ptr_array_free (pool, TRUE);
@@ -125,6 +123,15 @@ swfdec_constant_pool_get_area (SwfdecScr
/*** SUPPORT FUNCTIONS ***/
+static void
+swfdec_script_add_to_player (SwfdecScript *script, SwfdecPlayer *player)
+{
+ if (SWFDEC_IS_DEBUGGER (player)) {
+ swfdec_debugger_add_script (SWFDEC_DEBUGGER (player), script);
+ script->debugger = player;
+ }
+}
+
/**
* swfdec_script_ensure_stack:
* @cx: #JSContext to check
@@ -1733,22 +1740,22 @@ swfdec_action_define_function (JSContext
}
if (name == NULL)
name = "unnamed_function";
- script = swfdec_script_new_for_player (JS_GetContextPrivate (cx),
- &bits, name, ((SwfdecScript *) cx->fp->swf)->version);
+ script = swfdec_script_new (&bits, name, ((SwfdecScript *) cx->fp->swf)->version);
swfdec_buffer_unref (buffer);
- if (cx->fp->constant_pool) {
- script->constant_pool = swfdec_constant_pool_get_area (cx->fp->swf,
- cx->fp->constant_pool);
- }
}
if (script == NULL) {
SWFDEC_ERROR ("failed to create script");
g_free (preloads);
return JS_FALSE;
}
+ if (cx->fp->constant_pool) {
+ script->constant_pool = swfdec_constant_pool_get_area (cx->fp->swf,
+ cx->fp->constant_pool);
+ }
script->flags = flags;
script->preloads = preloads;
fun->swf = script;
+ swfdec_script_add_to_player (script, JS_GetContextPrivate (cx));
/* attach the function */
if (*function_name == '\0') {
if (cx->fp->sp >= cx->fp->spend) {
@@ -2170,6 +2177,7 @@ swfdec_action_print_set_target (guint ac
}
return g_strconcat ("SetTarget ", data, NULL);
}
+
static char *
swfdec_action_print_define_function (guint action, const guint8 *data, guint len)
{
@@ -2664,10 +2672,8 @@ swfdec_script_new_for_player (SwfdecPlay
g_return_val_if_fail (bits != NULL, NULL);
script = swfdec_script_new (bits, name, version);
- if (SWFDEC_IS_DEBUGGER (player) && script) {
- swfdec_debugger_add_script (SWFDEC_DEBUGGER (player), script);
- script->debugger = player;
- }
+ if (script)
+ swfdec_script_add_to_player (script, player);
return script;
}
diff --git a/libswfdec/swfdec_script.h b/libswfdec/swfdec_script.h
index 8af5755..d55cdbc 100644
--- a/libswfdec/swfdec_script.h
+++ b/libswfdec/swfdec_script.h
@@ -28,6 +28,7 @@
G_BEGIN_DECLS
//typedef struct _SwfdecScript SwfdecScript;
+typedef GPtrArray SwfdecConstantPool;
typedef enum {
SWFDEC_SCRIPT_PRELOAD_THIS = (1 << 0),
@@ -62,6 +63,14 @@ struct _SwfdecScript {
const char * swfdec_action_get_name (guint action);
guint swfdec_action_get_from_name (const char * name);
+SwfdecConstantPool *
+ swfdec_constant_pool_new_from_action (const guint8 * data,
+ guint len);
+guint swfdec_constant_pool_size (SwfdecConstantPool * pool);
+const char * swfdec_constant_pool_get (SwfdecConstantPool * pool,
+ guint i);
+void swfdec_constant_pool_free (SwfdecConstantPool * pool);
+
SwfdecScript * swfdec_script_new (SwfdecBits * bits,
const char * name,
unsigned int version);
More information about the Swfdec
mailing list