aboutsummaryrefslogtreecommitdiffstats
path: root/plugins
diff options
context:
space:
mode:
authorLuis Ontanon <luis.ontanon@gmail.com>2006-02-16 00:54:56 +0000
committerLuis Ontanon <luis.ontanon@gmail.com>2006-02-16 00:54:56 +0000
commit1b096ab156506856495860ef6b356e6992a3ba8c (patch)
tree5239f05605e723d969ff9ebec90ec621b935ce0f /plugins
parent5a482871f31c5d8dfbc5e329a859e17b08cc79d8 (diff)
Have Field extractors being defined while reading the body of the script instead that during initialization.
Change their semantics too: ip_src_f = Field("ip.src") function tap.packet(pinfo) ip_src = ip_src() end svn path=/trunk/; revision=17315
Diffstat (limited to 'plugins')
-rw-r--r--plugins/lua/lua_tap.c115
-rw-r--r--plugins/lua/packet-lua.h2
2 files changed, 68 insertions, 49 deletions
diff --git a/plugins/lua/lua_tap.c b/plugins/lua/lua_tap.c
index 24b7e5de30..1207ec067a 100644
--- a/plugins/lua/lua_tap.c
+++ b/plugins/lua/lua_tap.c
@@ -33,37 +33,44 @@ LUA_CLASS_DEFINE(Field,FIELD,NOP)
static GPtrArray* wanted_fields = NULL;
-/* XXX this will be used in the future, called from somewhere in packet.c */
-#if 0
-void lua_prime_all_fields(proto_tree* tree) {
- guint i;
-
- for(i=0; i < wanted_fields->len; i++) {
- Field f = g_ptr_array_index(wanted_fields,i);
- for (;f;f = f->same_name_next) {
- proto_tree_prime_hfid(tree,f->id);
- }
- }
-}
-#else
-/* XXX - this will be used while we are a plugin */
+/*
+ * field extractor registartion is tricky, In order to allow
+ * the user to define them in the body of the script we will
+ * populate the Field value with a pointer of the abbrev of it
+ * to later replace it with the hfi.
+ *
+ * This will be added to the wanted_fields array that will
+ * exists only while they can be defined, and be cleared right
+ * after the fields are primed.
+ */
void lua_prime_all_fields(proto_tree* tree _U_) {
GString* fake_tap_filter = g_string_new("frame");
guint i;
- static gboolean fake_tap;
-
-
- if ( !wanted_fields || fake_tap ) return;
-
- fake_tap = FALSE;
+ static gboolean fake_tap = FALSE;
for(i=0; i < wanted_fields->len; i++) {
Field f = g_ptr_array_index(wanted_fields,i);
- g_string_sprintfa(fake_tap_filter," || %s",f->abbrev);
+ gchar* name = *((gchar**)f);
+
+ *f = proto_registrar_get_byname(name);
+
+ if (!*f) {
+ report_failure("Could not find field `%s'",name);
+ *f = NULL;
+ g_free(name);
+ continue;
+ }
+
+ g_free(name);
+
+ g_string_sprintfa(fake_tap_filter," || %s",(*f)->abbrev);
fake_tap = TRUE;
}
+ g_ptr_array_free(wanted_fields,TRUE);
+ wanted_fields = NULL;
+
if (fake_tap) {
/* a boring tap :-) */
GString* error = register_tap_listener("frame",
@@ -78,7 +85,6 @@ void lua_prime_all_fields(proto_tree* tree _U_) {
}
}
-#endif
static int Field_get (lua_State *L) {
const gchar* name = luaL_checkstring(L,1);
@@ -86,25 +92,34 @@ static int Field_get (lua_State *L) {
if (!name) return 0;
- f = proto_registrar_get_byname(name);
-
- if (!f) {
- luaL_error(L,"Could not find field `%s'",name);
+ if (!wanted_fields) {
+ luaL_error(L,"too late to define a Field extractor");
return 0;
}
- if (!wanted_fields)
- wanted_fields = g_ptr_array_new();
+ f = g_malloc(sizeof(void*));
+ *f = (header_field_info*)g_strdup(name); /* cheating */
g_ptr_array_add(wanted_fields,f);
pushField(L,f);
return 1;
-}
+}
static int Field_fetch (lua_State* L) {
- Field in = checkField(L,1);
+ Field f = checkField(L,1);
int items_found = 0;
+ header_field_info* in = *f;
+
+ if (! in) {
+ luaL_error(L,"invalid field");
+ return 0;
+ }
+
+ if (! lua_tree ) {
+ luaL_error(L,"fields cannot be used outside dissectors or taps");
+ return 0;
+ }
for (;in;in = in->same_name_next) {
GPtrArray* found = proto_find_finfo(lua_tree, in->id);
@@ -137,7 +152,7 @@ static int Field_fetch (lua_State* L) {
case FT_IPv4:
case FT_IPv6:
case FT_IPXNET:
- /* XXX -> Address */
+ /* XXX: use Address ??? */
case FT_STRING:
case FT_STRINGZ:
case FT_BYTES:
@@ -158,35 +173,39 @@ static int Field_fetch (lua_State* L) {
}
-static int Field_tostring (lua_State* L) {
- Field in = checkField(L,1);
+static int Field_tostring(lua_State* L) {
+ Field f = checkField(L,1);
+
+ if ( !(f && *f) ) {
+ luaL_error(L,"invalid Field");
+ return 0;
+ }
+
+ if (wanted_fields) {
+ lua_pushstring(L,*((gchar**)f));
+ } else {
+ lua_pushstring(L,(*f)->abbrev);
+ }
- lua_pushfstring(L,"Field: %s",in->abbrev);
return 1;
}
-static const luaL_reg Field_methods[] = {
- {"get", Field_get},
- {"fetch", Field_fetch },
- {0,0}
-};
-
static const luaL_reg Field_meta[] = {
{"__tostring", Field_tostring},
+ {"__call", Field_fetch},
{0, 0}
};
int Field_register(lua_State* L) {
- luaL_openlib(L, FIELD, Field_methods, 0);
+
+ wanted_fields = g_ptr_array_new();
+
luaL_newmetatable(L, FIELD);
luaL_openlib(L, 0, Field_meta, 0);
- lua_pushliteral(L, "__index");
- lua_pushvalue(L, -3);
- lua_rawset(L, -3);
- lua_pushliteral(L, "__metatable");
- lua_pushvalue(L, -3);
- lua_rawset(L, -3);
- lua_pop(L, 1);
+
+ lua_pushstring(L, "Field");
+ lua_pushcfunction(L, Field_get);
+ lua_settable(L, LUA_GLOBALSINDEX);
return 1;
}
diff --git a/plugins/lua/packet-lua.h b/plugins/lua/packet-lua.h
index 8311f99033..e8d3efe722 100644
--- a/plugins/lua/packet-lua.h
+++ b/plugins/lua/packet-lua.h
@@ -155,7 +155,7 @@ typedef proto_item* ProtoItem;
typedef address* Address;
#define FIELD "Field"
-typedef header_field_info* Field;
+typedef header_field_info** Field;
#define TAP "Tap"
typedef struct _eth_tap* Tap;