krb5 commit: Add krb5_expand_hostname() API

Greg Hudson ghudson at mit.edu
Wed Aug 24 12:44:56 EDT 2016


https://github.com/krb5/krb5/commit/faf9ad33e9e6b7ffaac02fcd249e60e2224f5ec7
commit faf9ad33e9e6b7ffaac02fcd249e60e2224f5ec7
Author: Greg Hudson <ghudson at mit.edu>
Date:   Tue Nov 17 13:06:31 2015 -0500

    Add krb5_expand_hostname() API
    
    Add a new public libkrb5 function expand_hostname().  It follows the
    same contract as the Heimdal function, except that the caller should
    use krb5_free_string() instead of krb5_xfree() to free the result.
    
    As a small side effect, we no longer remove trailing dots from the
    hostname in krb5_sname_to_principal() when invoked with type
    KRB5_NT_UNKNOWN.  Adjust a test case in t_sn2princ.py accordingly.
    
    ticket: 8278 (new)

 doc/appdev/refs/api/index.rst |    1 +
 src/include/krb5/krb5.hin     |   17 +++++++++++++++++
 src/lib/krb5/libkrb5.exports  |    1 +
 src/lib/krb5/os/sn2princ.c    |   30 ++++++++++++++----------------
 src/lib/krb5_32.def           |    1 +
 src/tests/t_sn2princ.py       |    9 ++++-----
 6 files changed, 38 insertions(+), 21 deletions(-)

diff --git a/doc/appdev/refs/api/index.rst b/doc/appdev/refs/api/index.rst
index 55acaf0..f2f27fe 100644
--- a/doc/appdev/refs/api/index.rst
+++ b/doc/appdev/refs/api/index.rst
@@ -24,6 +24,7 @@ Frequently used public interfaces
    krb5_cc_resolve.rst
    krb5_change_password.rst
    krb5_chpw_message.rst
+   krb5_expand_hostname.rst
    krb5_free_context.rst
    krb5_free_error_message.rst
    krb5_free_principal.rst
diff --git a/src/include/krb5/krb5.hin b/src/include/krb5/krb5.hin
index a1bf849..c8928cb 100644
--- a/src/include/krb5/krb5.hin
+++ b/src/include/krb5/krb5.hin
@@ -4968,6 +4968,23 @@ void KRB5_CALLCONV
 krb5_free_default_realm(krb5_context context, char *lrealm);
 
 /**
+ * Canonicalize a hostname, possibly using name service.
+ *
+ * @param [in]  context         Library context
+ * @param [in]  host            Input hostname
+ * @param [out] canonhost_out   Canonicalized hostname
+ *
+ * This function canonicalizes orig_hostname, possibly using name service
+ * lookups if configuration permits.  Use krb5_free_string() to free @a
+ * canonhost_out when it is no longer needed.
+ *
+ * @version New in 1.15
+ */
+krb5_error_code KRB5_CALLCONV
+krb5_expand_hostname(krb5_context context, const char *host,
+                     char **canonhost_out);
+
+/**
  * Generate a full principal name from a service name.
  *
  * @param [in]  context         Library context
diff --git a/src/lib/krb5/libkrb5.exports b/src/lib/krb5/libkrb5.exports
index cdda32d..ed6cad6 100644
--- a/src/lib/krb5/libkrb5.exports
+++ b/src/lib/krb5/libkrb5.exports
@@ -282,6 +282,7 @@ krb5_encode_authdata_container
 krb5_encode_kdc_rep
 krb5_encrypt_helper
 krb5_encrypt_tkt_part
+krb5_expand_hostname
 krb5_externalize_data
 krb5_externalize_opaque
 krb5_fcc_ops
diff --git a/src/lib/krb5/os/sn2princ.c b/src/lib/krb5/os/sn2princ.c
index 92969cd..5932fd9 100644
--- a/src/lib/krb5/os/sn2princ.c
+++ b/src/lib/krb5/os/sn2princ.c
@@ -53,11 +53,9 @@ use_reverse_dns(krb5_context context)
     return value;
 }
 
-/* Set *name_out to the canonicalized form of name, obeying relevant
- * configuration settings.  The caller must free the result. */
-static krb5_error_code
-canon_hostname(krb5_context context, krb5_int32 type, const char *host,
-               char **canonhost_out)
+krb5_error_code KRB5_CALLCONV
+krb5_expand_hostname(krb5_context context, const char *host,
+                     char **canonhost_out)
 {
     struct addrinfo *ai = NULL, hint;
     char namebuf[NI_MAXHOST], *copy, *p;
@@ -67,7 +65,7 @@ canon_hostname(krb5_context context, krb5_int32 type, const char *host,
     *canonhost_out = NULL;
 
     canonhost = host;
-    if (type == KRB5_NT_SRV_HST && context->dns_canonicalize_hostname) {
+    if (context->dns_canonicalize_hostname) {
         /* Try a forward lookup of the hostname. */
         memset(&hint, 0, sizeof(hint));
         hint.ai_flags = AI_CANONNAME;
@@ -92,12 +90,10 @@ canon_hostname(krb5_context context, krb5_int32 type, const char *host,
     if (copy == NULL)
         goto cleanup;
 
-    if (type == KRB5_NT_SRV_HST) {
-        /* Convert the hostname to lower case. */
-        for (p = copy; *p != '\0'; p++) {
-            if (isupper((unsigned char)*p))
-                *p = tolower((unsigned char)*p);
-        }
+    /* Convert the hostname to lower case. */
+    for (p = copy; *p != '\0'; p++) {
+        if (isupper((unsigned char)*p))
+            *p = tolower((unsigned char)*p);
     }
 
     /* Remove any trailing dot. */
@@ -167,10 +163,12 @@ krb5_sname_to_principal(krb5_context context, const char *hostname,
     }
 
     /* Canonicalize the hostname if appropriate. */
-    ret = canon_hostname(context, type, hostname, &canonhost);
-    if (ret)
-        goto cleanup;
-    hostname = canonhost;
+    if (type == KRB5_NT_SRV_HST) {
+        ret = krb5_expand_hostname(context, hostname, &canonhost);
+        if (ret)
+            goto cleanup;
+        hostname = canonhost;
+    }
 
     /* Find the realm of the host. */
     ret = krb5_get_host_realm(context, hostname, &hrealms);
diff --git a/src/lib/krb5_32.def b/src/lib/krb5_32.def
index 3b271d3..e5b560d 100644
--- a/src/lib/krb5_32.def
+++ b/src/lib/krb5_32.def
@@ -469,3 +469,4 @@ EXPORTS
 	krb5_set_kdc_recv_hook				@434
 	krb5_get_init_creds_opt_set_pac_request		@435
 	krb5int_trace					@436 ; PRIVATE GSSAPI
+	krb5_expand_hostname				@437
diff --git a/src/tests/t_sn2princ.py b/src/tests/t_sn2princ.py
index 6a349c4..19a0d2f 100755
--- a/src/tests/t_sn2princ.py
+++ b/src/tests/t_sn2princ.py
@@ -44,11 +44,10 @@ testu('ptr-mismatch.kerberos.org', 'ptr-mismatch.kerberos.org', 'R1')
 testu('Example.COM', 'Example.COM', 'R2')
 testu('abcde', 'abcde', '')
 
-# A ':port' or ':instance' trailer should be ignored for hostname
-# adjustment and realm lookup.  If there is more than one colon in the
-# name, we assume it's an IPv6 address and don't treat it as having a
-# trailer.
-testu('example.com.:123', 'example.com:123', 'R2')
+# A ':port' or ':instance' trailer should be ignored for realm lookup.
+# If there is more than one colon in the name, we assume it's an IPv6
+# address and don't treat it as having a trailer.
+testu('example.com.:123', 'example.com.:123', 'R2')
 testu('Example.COM:xyZ', 'Example.COM:xyZ', 'R2')
 testu('example.com.::123', 'example.com.::123', '')
 


More information about the cvs-krb5 mailing list