Change in libosmocore[master]: add identifier sanitation for setting FSM instance ids

Neels Hofmeyr gerrit-no-reply at lists.osmocom.org
Wed Apr 10 17:50:44 UTC 2019


Neels Hofmeyr has uploaded this change for review. ( https://gerrit.osmocom.org/13574


Change subject: add identifier sanitation for setting FSM instance ids
......................................................................

add identifier sanitation for setting FSM instance ids

We often compose FSM instance IDs from context information, for example placing
an MSISDN string or IP:port information in the FSM instance id, using
osmo_fsm_inst_update_id_f(). This fails if any characters are contained that
don't pass osmo_identifier_valid(). Hence it is the task of the caller to make
sure only characters allowed in an FSM id are applied.

Provide API to trivially allow this by replacing illegal chars:
- osmo_identifier_sanitize_buf(), with access to the same set of illegal
  characters defined in utils.c,
- osmo_fsm_inst_update_id_f_sanitize() implicitly replaces non-identifier
  chars.

This makes it easy to add strings like '192.168.0.1:2342' or '+4987654321' to
an FSM instance id, without adding string mangling to each place that sets an
id; e.g. replacing with '-' to yield '192-168-0-1:2342' or '-4987654321'.

Change-Id: Ia40a6f3b2243c95fe428a080b938e11d8ab771a7
---
M include/osmocom/core/fsm.h
M include/osmocom/core/utils.h
M src/fsm.c
M src/utils.c
4 files changed, 54 insertions(+), 3 deletions(-)



  git pull ssh://gerrit.osmocom.org:29418/libosmocore refs/changes/74/13574/1

diff --git a/include/osmocom/core/fsm.h b/include/osmocom/core/fsm.h
index c9e1e0c..41d01a5 100644
--- a/include/osmocom/core/fsm.h
+++ b/include/osmocom/core/fsm.h
@@ -220,6 +220,7 @@
 
 int osmo_fsm_inst_update_id(struct osmo_fsm_inst *fi, const char *id);
 int osmo_fsm_inst_update_id_f(struct osmo_fsm_inst *fi, const char *fmt, ...);
+int osmo_fsm_inst_update_id_f_sanitize(struct osmo_fsm_inst *fi, char replace_with, const char *fmt, ...);
 
 const char *osmo_fsm_event_name(struct osmo_fsm *fsm, uint32_t event);
 const char *osmo_fsm_inst_name(struct osmo_fsm_inst *fi);
diff --git a/include/osmocom/core/utils.h b/include/osmocom/core/utils.h
index ecb04b5..3f28eec 100644
--- a/include/osmocom/core/utils.h
+++ b/include/osmocom/core/utils.h
@@ -136,6 +136,7 @@
 
 bool osmo_identifier_valid(const char *str);
 bool osmo_separated_identifiers_valid(const char *str, const char *sep_chars);
+void osmo_identifier_sanitize_buf(char *str, const char *sep_chars, char replace_with);
 
 const char *osmo_escape_str(const char *str, int len);
 const char *osmo_escape_str_buf(const char *str, int in_len, char *buf, size_t bufsize);
diff --git a/src/fsm.c b/src/fsm.c
index b6912c6..c32767b 100644
--- a/src/fsm.c
+++ b/src/fsm.c
@@ -364,6 +364,35 @@
 	return 0;
 }
 
+/*! Change id of the FSM instance using a string format, and ensuring a valid id.
+ * Replace any characters that are not permitted as FSM identifier with replace_with.
+ * \param[in] fi FSM instance.
+ * \param[in] replace_with Character to use instead of non-permitted FSM id characters.
+ *                         Make sure to choose a legal character, e.g. '-'.
+ * \param[in] fmt format string to compose new ID.
+ * \param[in] ... variable argument list for format string.
+ * \returns 0 if the ID was updated, otherwise -EINVAL.
+ */
+int osmo_fsm_inst_update_id_f_sanitize(struct osmo_fsm_inst *fi, char replace_with, const char *fmt, ...)
+{
+	char *id = NULL;
+	va_list ap;
+	int rc;
+
+	if (!fmt)
+		return osmo_fsm_inst_update_id(fi, NULL);
+
+	va_start(ap, fmt);
+	id = talloc_vasprintf(fi, fmt, ap);
+	va_end(ap);
+
+	osmo_identifier_sanitize_buf(id, NULL, replace_with);
+
+	rc = osmo_fsm_inst_update_id(fi, id);
+	talloc_free(id);
+	return rc;
+}
+
 /*! allocate a new instance of a specified FSM
  *  \param[in] fsm Descriptor of the FSM
  *  \param[in] ctx talloc context from which to allocate memory
diff --git a/src/utils.c b/src/utils.c
index 7def0b8..8ea51ed 100644
--- a/src/utils.c
+++ b/src/utils.c
@@ -510,6 +510,8 @@
 	return true;
 }
 
+static const char osmo_identifier_illegal_chars[] = "., {}[]()<>|~\\^`'\"?=;/+*&%$#!";
+
 /*! Determine if a given identifier is valid, i.e. doesn't contain illegal chars
  *  \param[in] str String to validate
  *  \param[in] sep_chars Permitted separation characters between identifiers.
@@ -518,7 +520,6 @@
 bool osmo_separated_identifiers_valid(const char *str, const char *sep_chars)
 {
 	/* characters that are illegal in names */
-	static const char illegal_chars[] = "., {}[]()<>|~\\^`'\"?=;/+*&%$#!";
 	unsigned int i;
 	size_t len;
 
@@ -535,7 +536,7 @@
 		if (!isprint((int)str[i]))
 			return false;
 		/* check for some explicit reserved control characters */
-		if (strchr(illegal_chars, str[i]))
+		if (strchr(osmo_identifier_illegal_chars, str[i]))
 			return false;
 	}
 
@@ -551,7 +552,26 @@
 	return osmo_separated_identifiers_valid(str, NULL);
 }
 
-/*! Return the string with all non-printable characters escapeda, in user-supplied buffer.
+/*! Replace characters in the given string buffer so that it is guaranteed to pass osmo_separated_identifiers_valid().
+ * To guarantee passing osmo_separated_identifiers_valid(), replace_with must not itself be an illegal character. If in
+ * doubt, use '-'.
+ * \param[inout] str  Identifier to sanitize, must be nul terminated and in a writable buffer.
+ * \param[in] sep_chars  Additional characters that are allowed besides osmo_identifier_illegal_chars.
+ * \param[in] replace_with  Replace any illegal characters with this character.
+ */
+void osmo_identifier_sanitize_buf(char *str, const char *sep_chars, char replace_with)
+{
+	char *pos;
+	if (!str)
+		return;
+	for (pos = str; *pos; pos++) {
+		if (strchr(osmo_identifier_illegal_chars, *pos)
+		    || (sep_chars && strchr(sep_chars, *pos)))
+			*pos = replace_with;
+	}
+}
+
+/*! Return the string with all non-printable characters escaped.
  * \param[in] str  A string that may contain any characters.
  * \param[in] len  Pass -1 to print until nul char, or >= 0 to force a length.
  * \param[inout] buf  string buffer to write escaped characters to.

-- 
To view, visit https://gerrit.osmocom.org/13574
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings

Gerrit-Project: libosmocore
Gerrit-Branch: master
Gerrit-MessageType: newchange
Gerrit-Change-Id: Ia40a6f3b2243c95fe428a080b938e11d8ab771a7
Gerrit-Change-Number: 13574
Gerrit-PatchSet: 1
Gerrit-Owner: Neels Hofmeyr <nhofmeyr at sysmocom.de>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osmocom.org/pipermail/gerrit-log/attachments/20190410/dc10c55f/attachment-0001.html>


More information about the gerrit-log mailing list