summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYouness Alaoui <youness.alaoui@collabora.co.uk>2009-11-04 13:00:36 -0500
committerYouness Alaoui <youness.alaoui@collabora.co.uk>2009-11-04 13:00:36 -0500
commit8eab0facb3285ad43b3dc411e583d35a287a06eb (patch)
tree0de4ab47185281a04532e53fead9996d62bf47e3
parent9c56802a8b144e39bd875cc3419fe1f20758dc16 (diff)
downloadlibnice-8eab0facb3285ad43b3dc411e583d35a287a06eb.tar.gz
Add a stun_agent_set_software API and correctly append only the first 128 utf-8 characters
-rw-r--r--stun/stun5389.c34
-rw-r--r--stun/stun5389.h3
-rw-r--r--stun/stunagent.c26
-rw-r--r--stun/stunagent.h31
4 files changed, 82 insertions, 12 deletions
diff --git a/stun/stun5389.c b/stun/stun5389.c
index fa100fd..32f1c1b 100644
--- a/stun/stun5389.c
+++ b/stun/stun5389.c
@@ -53,6 +53,21 @@
#include "stuncrc32.h"
#include "stunmessage.h"
+
+static const char utf8_skip_data[256] = {
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
+ 2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,
+ 3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,5,5,5,5,6,6,1,1
+};
+
+#define next_utf8_char(p) (char *)((p) + \
+ utf8_skip_data[*(const unsigned char *)(p)])
+
uint32_t stun_fingerprint (const uint8_t *msg, size_t len,
bool wlm2009_stupid_crc32_typo)
{
@@ -81,10 +96,21 @@ bool stun_message_has_cookie (const StunMessage *msg)
}
-StunMessageReturn stun_message_append_software (StunMessage *msg)
+StunMessageReturn stun_message_append_software (StunMessage *msg,
+ const char *software)
{
- static const char software[] = PACKAGE_STRING;
- // assert (strlen (software) < 128);
+ int len = 0;
+ const char *ptr = NULL;
+
+ if (software == NULL)
+ software = PACKAGE_STRING;
+
+ ptr = software;
+ while (*ptr && len < 128) {
+ ptr = next_utf8_char (ptr);
+ len++;
+ }
- return stun_message_append_string (msg, STUN_ATTRIBUTE_SOFTWARE, software);
+ return stun_message_append_bytes (msg, STUN_ATTRIBUTE_SOFTWARE, software,
+ ptr - software);
}
diff --git a/stun/stun5389.h b/stun/stun5389.h
index 3387304..5f3a65e 100644
--- a/stun/stun5389.h
+++ b/stun/stun5389.h
@@ -60,7 +60,8 @@
uint32_t stun_fingerprint (const uint8_t *msg, size_t len,
bool wlm2009_stupid_crc32_typo);
-StunMessageReturn stun_message_append_software (StunMessage *msg);
+StunMessageReturn stun_message_append_software (StunMessage *msg,
+ const char *software);
#endif /* _STUN_5389_H */
diff --git a/stun/stunagent.c b/stun/stunagent.c
index fb8121c..68c81c3 100644
--- a/stun/stunagent.c
+++ b/stun/stunagent.c
@@ -59,6 +59,7 @@ void stun_agent_init (StunAgent *agent, const uint16_t *known_attributes,
agent->known_attributes = (uint16_t *) known_attributes;
agent->compatibility = compatibility;
agent->usage_flags = usage_flags;
+ agent->software_attribute = NULL;
for (i = 0; i < STUN_AGENT_MAX_SAVED_IDS; i++) {
agent->sent_ids[i].valid = FALSE;
@@ -358,6 +359,12 @@ bool stun_agent_init_request (StunAgent *agent, StunMessage *msg,
uint32_t cookie = htonl (STUN_MAGIC_COOKIE);
memcpy (msg->buffer + STUN_MESSAGE_TRANS_ID_POS, &cookie, sizeof (cookie));
}
+ if (agent->software_attribute != NULL ||
+ ((agent->compatibility == STUN_COMPATIBILITY_RFC5389 ||
+ agent->compatibility == STUN_COMPATIBILITY_WLM2009) &&
+ agent->usage_flags & STUN_AGENT_USAGE_ADD_SOFTWARE)) {
+ stun_message_append_software (msg, agent->software_attribute);
+ }
}
return ret;
@@ -416,10 +423,11 @@ bool stun_agent_init_response (StunAgent *agent, StunMessage *msg,
if (stun_message_init (msg, STUN_RESPONSE,
stun_message_get_method (request), id)) {
- if ((agent->compatibility == STUN_COMPATIBILITY_RFC5389 ||
+ if (agent->software_attribute != NULL ||
+ ((agent->compatibility == STUN_COMPATIBILITY_RFC5389 ||
agent->compatibility == STUN_COMPATIBILITY_WLM2009) &&
- agent->usage_flags & STUN_AGENT_USAGE_ADD_SOFTWARE) {
- stun_message_append_software (msg);
+ agent->usage_flags & STUN_AGENT_USAGE_ADD_SOFTWARE)) {
+ stun_message_append_software (msg, agent->software_attribute);
}
return TRUE;
}
@@ -452,10 +460,11 @@ bool stun_agent_init_error (StunAgent *agent, StunMessage *msg,
if (stun_message_init (msg, STUN_ERROR,
stun_message_get_method (request), id)) {
- if ((agent->compatibility == STUN_COMPATIBILITY_RFC5389 ||
+ if (agent->software_attribute != NULL ||
+ ((agent->compatibility == STUN_COMPATIBILITY_RFC5389 ||
agent->compatibility == STUN_COMPATIBILITY_WLM2009) &&
- agent->usage_flags & STUN_AGENT_USAGE_ADD_SOFTWARE) {
- stun_message_append_software (msg);
+ agent->usage_flags & STUN_AGENT_USAGE_ADD_SOFTWARE)) {
+ stun_message_append_software (msg, agent->software_attribute);
}
if (stun_message_append_error (msg, err) == STUN_MESSAGE_RETURN_SUCCESS) {
return TRUE;
@@ -674,3 +683,8 @@ stun_agent_find_unknowns (StunAgent *agent, const StunMessage * msg,
stun_debug ("STUN unknown: %u mandatory attribute(s)!\n", count);
return count;
}
+
+void stun_agent_set_software (StunAgent *agent, char *software)
+{
+ agent->software_attribute = software;
+}
diff --git a/stun/stunagent.h b/stun/stunagent.h
index 6aed2aa..f83837a 100644
--- a/stun/stunagent.h
+++ b/stun/stunagent.h
@@ -138,7 +138,10 @@ typedef enum {
* @STUN_AGENT_USAGE_USE_FINGERPRINT: The agent should add the FINGERPRINT
* attribute to the STUN messages it creates.
* @STUN_AGENT_USAGE_ADD_SOFTWARE: The agent should add the SOFTWARE attribute
- * to the STUN messages it creates
+ * to the STUN messages it creates. Calling nice_agent_set_software() will have
+ * the same effect as enabling this Usage. STUN Indications do not have the
+ * SOFTWARE attributes added to them though. The SOFTWARE attribute is only
+ * added for the RFC5389 and WLM2009 compatibility modes.
* @STUN_AGENT_USAGE_IGNORE_CREDENTIALS: The agent should ignore any credentials
* in the STUN messages it receives (the MESSAGE-INTEGRITY attribute
* will never be validated by stun_agent_validate())
@@ -184,6 +187,7 @@ struct stun_agent_t {
StunAgentSavedIds sent_ids[STUN_AGENT_MAX_SAVED_IDS];
uint16_t *known_attributes;
StunAgentUsageFlags usage_flags;
+ char *software_attribute;
};
/**
@@ -470,4 +474,29 @@ size_t stun_agent_finish_message (StunAgent *agent, StunMessage *msg,
bool stun_agent_forget_transaction (StunAgent *agent, StunTransactionId id);
+/**
+ * stun_agent_set_software:
+ * @agent: The #StunAgent
+ * @software: The value of the SOFTWARE attribute to add.
+ *
+ * This function will set the value of the SOFTWARE attribute to be added to
+ * STUN requests, responses and error responses.
+ * <para>
+ * Calling this function will automatically enable the addition of the SOFTWARE
+ * attribute for RFC5389 and WLM2009 compatibility modes.
+ * </para>
+ * <note>
+ <para>
+ The @software argument must be in UTF-8 encoding and only the first
+ 128 characters will be sent.
+ </para>
+ <para>
+ The value of the @software argument must stay valid throughout the life of
+ the StunAgent's life. Do not free its content.
+ </para>
+ </note>
+ *
+ */
+void stun_agent_set_software (StunAgent *agent, char *software);
+
#endif /* _STUN_AGENT_H */