From f56d3a4e5dec3aa75d25fae761a0642e6ebd7c3c Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Tue, 11 Oct 2005 00:58:04 +0000 Subject: * rename avahi_is_valid_service_type() to avahi_is_valid_service_type_generic() * add avahi_is_valid_service_type_strict() which doesn't allow subtypes and other strange things to pass * fix protocol validity checks in server.c * add new API function avahi_get_type_from_subtype() git-svn-id: file:///home/lennart/svn/public/avahi/trunk@716 941a03a8-eaeb-0310-b9a0-b1bbd8fe43fe --- avahi-common/domain-test.c | 24 +++++++++-- avahi-common/domain.c | 99 +++++++++++++++++++++++++++++++++++++++++++++- avahi-common/domain.h | 17 +++++++- 3 files changed, 133 insertions(+), 7 deletions(-) (limited to 'avahi-common') diff --git a/avahi-common/domain-test.c b/avahi-common/domain-test.c index 444f553..f1313cb 100644 --- a/avahi-common/domain-test.c +++ b/avahi-common/domain-test.c @@ -84,9 +84,27 @@ int main(int argc, char *argv[]) { assert(avahi_domain_ends_with("foo.bar.\\065\\\\\\.aaaa", "\\065\\\\\\.aaaa")); - assert(avahi_is_valid_service_type("_foo._bar._waldo")); - assert(!avahi_is_valid_service_type("_foo._bar.waldo")); - assert(!avahi_is_valid_service_type("")); + assert(avahi_is_valid_service_type_generic("_foo._bar._waldo")); + assert(!avahi_is_valid_service_type_strict("_foo._bar._waldo")); + assert(!avahi_is_valid_service_subtype("_foo._bar._waldo")); + + assert(avahi_is_valid_service_type_generic("_foo._tcp")); + assert(avahi_is_valid_service_type_strict("_foo._tcp")); + assert(!avahi_is_valid_service_subtype("_foo._tcp")); + + assert(!avahi_is_valid_service_type_generic("_foo._bar.waldo")); + assert(!avahi_is_valid_service_type_strict("_foo._bar.waldo")); + assert(!avahi_is_valid_service_subtype("_foo._bar.waldo")); + + assert(!avahi_is_valid_service_type_generic("")); + assert(!avahi_is_valid_service_type_strict("")); + assert(!avahi_is_valid_service_subtype("")); + + assert(avahi_is_valid_service_type_generic("_foo._sub._bar._tcp")); + assert(!avahi_is_valid_service_type_strict("_foo._sub._bar._tcp")); + assert(avahi_is_valid_service_subtype("_foo._sub._bar._tcp")); + + printf("%s\n", avahi_get_type_from_subtype("_foo._sub._bar._tcp")); assert(!avahi_is_valid_host_name("sf.ooo.")); assert(avahi_is_valid_host_name("sfooo.")); diff --git a/avahi-common/domain.c b/avahi-common/domain.c index b72a898..f2e4395 100644 --- a/avahi-common/domain.c +++ b/avahi-common/domain.c @@ -293,7 +293,7 @@ int avahi_binary_domain_cmp(const char *a, const char *b) { } } -int avahi_is_valid_service_type(const char *t) { +int avahi_is_valid_service_type_generic(const char *t) { assert(t); if (strlen(t) >= AVAHI_DOMAIN_NAME_MAX || !*t) @@ -313,6 +313,101 @@ int avahi_is_valid_service_type(const char *t) { return 1; } +int avahi_is_valid_service_type_strict(const char *t) { + char label[AVAHI_LABEL_MAX]; + assert(t); + + if (strlen(t) >= AVAHI_DOMAIN_NAME_MAX || !*t) + return 0; + + /* Application name */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return 0; + + if (strlen(label) <= 2 || label[0] != '_') + return 0; + + if (!*t) + return 0; + + /* _tcp or _udp boilerplate */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return 0; + + if (strcasecmp(label, "_tcp") && strcasecmp(label, "_udp")) + return 0; + + if (*t) + return 0; + + return 1; +} + +const char *avahi_get_type_from_subtype(const char *t) { + char label[AVAHI_LABEL_MAX]; + const char *ret; + assert(t); + + if (strlen(t) >= AVAHI_DOMAIN_NAME_MAX || !*t) + return NULL; + + /* Subtype name */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return NULL; + + if (strlen(label) <= 2 || label[0] != '_') + return NULL; + + if (!*t) + return NULL; + + /* String "_sub" */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return NULL; + + if (strcasecmp(label, "_sub")) + return NULL; + + if (!*t) + return NULL; + + ret = t; + + /* Application name */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return NULL; + + if (strlen(label) <= 2 || label[0] != '_') + return NULL; + + if (!*t) + return NULL; + + /* _tcp or _udp boilerplate */ + + if (!(avahi_unescape_label(&t, label, sizeof(label)))) + return NULL; + + if (strcasecmp(label, "_tcp") && strcasecmp(label, "_udp")) + return NULL; + + if (*t) + return NULL; + + return ret; +} + +int avahi_is_valid_service_subtype(const char *t) { + assert(t); + + return !!avahi_get_type_from_subtype(t); +} + int avahi_is_valid_domain_name(const char *t) { assert(t); @@ -407,7 +502,7 @@ int avahi_service_name_join(char *p, size_t size, const char *name, const char * if ((name && !avahi_is_valid_service_name(name))) return AVAHI_ERR_INVALID_SERVICE_NAME; - if (!avahi_is_valid_service_type(type)) + if (!avahi_is_valid_service_type_generic(type)) return AVAHI_ERR_INVALID_SERVICE_TYPE; if (!avahi_is_valid_domain_name(domain)) diff --git a/avahi-common/domain.h b/avahi-common/domain.h index bcd036e..26f4b73 100644 --- a/avahi-common/domain.h +++ b/avahi-common/domain.h @@ -75,8 +75,21 @@ char *avahi_unescape_label(const char **name, char *dest, size_t size); /** Escape the domain name in *src and write it to *ret_name */ char *avahi_escape_label(const char* src, size_t src_length, char **ret_name, size_t *ret_size); -/** Return 1 when the specified string contains a valid service type, 0 otherwise */ -int avahi_is_valid_service_type(const char *t); +/** Return 1 when the specified string contains a valid generic + * service type (i.e. a series of words starting with "_"), 0 + * otherwise */ +int avahi_is_valid_service_type_generic(const char *t); + +/** Return 1 when the specified string contains a valid strict service + * type (i.e. consisting of only two words, the latter being either + * _udp or _tcp), 0 otherwise */ +int avahi_is_valid_service_type_strict(const char *t); + +/** Return 1 when the specified string contains a valid service subtype, 0 otherwise */ +int avahi_is_valid_service_subtype(const char *t); + +/** Return a pointer to the type section of a subtype i.e. _foo._sub._bar._tcp => _bar._tcp */ +const char *avahi_get_type_from_subtype(const char *t); /** Return 1 when the specified string contains a valid domain name, 0 otherwise */ int avahi_is_valid_domain_name(const char *t); -- cgit