[PATCH nft v2 2/6] json: osf: add version json support

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Signed-off-by: Fernando Fernandez Mancera <ffmancera@xxxxxxxxxx>
---
v1: initial patch
v2: flags type is now u32
---
 doc/libnftables-json.adoc |  7 +++++-
 src/json.c                | 13 +++++++++++
 src/parser_json.c         | 48 ++++++++++++++++++++++++++++++++++++++-
 3 files changed, 66 insertions(+), 2 deletions(-)

diff --git a/doc/libnftables-json.adoc b/doc/libnftables-json.adoc
index dbe5ac3..6981c69 100644
--- a/doc/libnftables-json.adoc
+++ b/doc/libnftables-json.adoc
@@ -1302,11 +1302,16 @@ Construct a reference to packet's socket.
 ____
 *{ "osf": {
 	"key":* 'OSF_KEY'*,
-	"ttl":* 'OSF_TTL'
+	"ttl":* 'OSF_TTL'*,
+	"flags":* 'OSF_FLAGS'
 *}}*
 
 'OSF_KEY' := *"name"*
 'OSF_TTL' := *"loose"* | *"skip"*
+
+'OSF_FLAGS' := 'OSF_FLAG' | *[* 'OSF_FLAG_LIST' *]*
+'OSF_FLAG_LIST' := 'OSF_FLAG' [*,* 'OSF_FLAG_LIST' ]
+'OSF_FLAG' := *"version"*
 ____
 
 Perform OS fingerprinting. This expression is typically used in the LHS of a *match*
diff --git a/src/json.c b/src/json.c
index 276a3c0..a46188d 100644
--- a/src/json.c
+++ b/src/json.c
@@ -865,6 +865,7 @@ json_t *socket_expr_json(const struct expr *expr, struct output_ctx *octx)
 json_t *osf_expr_json(const struct expr *expr, struct output_ctx *octx)
 {
 	json_t *root = json_pack("{s:s}", "key", "name");
+	const char *osf_flags[] = { "version" }
 
 	switch (expr->osf.ttl) {
 	case 1:
@@ -875,6 +876,18 @@ json_t *osf_expr_json(const struct expr *expr, struct output_ctx *octx)
 		break;
 	}
 
+	if (expr->osf.flags) {
+		json_t *tmp = json_array();
+		unsigned int i;
+
+		for (i = 0; i < array_size(osf_flags); i++) {
+			if (osf.flags & (1 << i)) {
+				json_array_append_new(tmp, json_string(osf_flags[i]));
+			}
+		}
+		json_object_set_new(root, "flags", tmp);
+	}
+
 	return json_pack("{s:o}", "osf", root);
 }
 
diff --git a/src/parser_json.c b/src/parser_json.c
index 7b190bc..ae197f0 100644
--- a/src/parser_json.c
+++ b/src/parser_json.c
@@ -377,10 +377,26 @@ static struct expr *json_parse_meta_expr(struct json_ctx *ctx,
 	return meta_expr_alloc(int_loc, key);
 }
 
+static int osf_flag_parse(const char *name, int *flagval)
+{
+	const char *osf_flags[] = { "version" };
+	unsigned int i;
+
+	for (i = 0; i < array_size(osf_flags); i++) {
+		if (!strcmp(name, osf_flags[i])) {
+			*flagval |= (1 << i);
+			return 0;
+		}
+	}
+	return 1;
+}
+
 static struct expr *json_parse_osf_expr(struct json_ctx *ctx,
 					const char *type, json_t *root)
 {
+	json_t *flags, *value;
 	const char *key, *ttl;
+	uint8_t flagval = 0;
 	uint8_t ttlval = 0;
 
 	if (json_unpack_err(ctx, root, "{s:s}", "key", &key))
@@ -397,8 +413,38 @@ static struct expr *json_parse_osf_expr(struct json_ctx *ctx,
 		}
 	}
 
+	if (!json_unpack(root, "{s:o}", "flags", &flags)) {
+		const char *flag;
+
+		if (json_is_string(flags)) {
+			flag = json_string_value(flags);
+
+			if (osf_flag_parse(flag, &flagval)) {
+				json_error(ctx, "Invalidad osf flag '%s'.", flag);
+				return NULL;
+			}
+
+		} else if (!json_is_array) {
+			json_error(ctx, "Unexpected object type in osf flags tuple.");
+			return NULL;
+		}
+
+		json_array_foreach(flags, index, value) {
+			if (!json_is_string(value)) {
+				json_error(ctx, "Unexpected object type in osf flags array at index %zd.", index);
+				return NULL;
+			}
+			flag = json_string_value(value);
+
+			if (osf_flag_parse(flag, &flagval)) {
+				json_error(ctx, "Invalid osf flag '%s'.", flag);
+				return NULL;
+			}
+		}
+	}
+
 	if (!strcmp(key, "name"))
-		return osf_expr_alloc(int_loc, ttlval);
+		return osf_expr_alloc(int_loc, ttlval, flagval);
 
 	json_error(ctx, "Invalid osf key value.");
 	return NULL;
-- 
2.20.1




[Index of Archives]     [Netfitler Users]     [Berkeley Packet Filter]     [LARTC]     [Bugtraq]     [Yosemite Forum]

  Powered by Linux