diff --git a/channels/chan_iax2.c b/channels/chan_iax2.c
index f4369213ef183335bc67e3a56f301b413211f015..fbf4752e71a3239c9c327003363904b16d7d69f2 100644
--- a/channels/chan_iax2.c
+++ b/channels/chan_iax2.c
@@ -612,6 +612,8 @@ struct iax2_registry {
 	struct sockaddr_in us;			/*!< Who the server thinks we are */
 	struct ast_dnsmgr_entry *dnsmgr;	/*!< DNS refresh manager */
 	AST_LIST_ENTRY(iax2_registry) entry;
+	int port;
+	char hostname[];
 };
 
 static AST_LIST_HEAD_STATIC(registrations, iax2_registry);
@@ -8480,6 +8482,17 @@ static int iax2_do_register(struct iax2_registry *reg);
 static void __iax2_do_register_s(const void *data)
 {
 	struct iax2_registry *reg = (struct iax2_registry *)data;
+
+	if (ast_sockaddr_isnull(&reg->addr)) {
+		reg->addr.ss.ss_family = AST_AF_UNSPEC;
+		ast_dnsmgr_lookup(reg->hostname, &reg->addr, &reg->dnsmgr, srvlookup ? "_iax._udp" : NULL);
+		if (!ast_sockaddr_port(&reg->addr)) {
+			ast_sockaddr_set_port(&reg->addr, reg->port);
+		} else {
+			reg->port = ast_sockaddr_port(&reg->addr);
+		}
+	}
+
 	reg->expire = -1;
 	iax2_do_register(reg);
 }
@@ -8707,8 +8720,9 @@ static int iax2_append_register(const char *hostname, const char *username,
 {
 	struct iax2_registry *reg;
 
-	if (!(reg = ast_calloc(1, sizeof(*reg))))
+	if (!(reg = ast_calloc(1, sizeof(*reg) + strlen(hostname) + 1))) {
 		return -1;
+	}
 
 	reg->addr.ss.ss_family = AF_INET;
 	if (ast_dnsmgr_lookup(hostname, &reg->addr, &reg->dnsmgr, srvlookup ? "_iax._udp" : NULL) < 0) {
@@ -8717,18 +8731,29 @@ static int iax2_append_register(const char *hostname, const char *username,
 	}
 
 	ast_copy_string(reg->username, username, sizeof(reg->username));
+	strcpy(reg->hostname, hostname); /* Note: This is safe */
 
-	if (secret)
+	if (secret) {
 		ast_copy_string(reg->secret, secret, sizeof(reg->secret));
+	}
 
 	reg->expire = -1;
 	reg->refresh = IAX_DEFAULT_REG_EXPIRE;
-	ast_sockaddr_set_port(&reg->addr, porta ? atoi(porta) : IAX_DEFAULT_PORTNO);
+
+	reg->port = ast_sockaddr_port(&reg->addr);
+
+	if (!porta && !reg->port) {
+		reg->port = IAX_DEFAULT_PORTNO;
+	} else if (porta) {
+		sscanf(porta, "%5d", &reg->port);
+	}
+
+	ast_sockaddr_set_port(&reg->addr, reg->port);
 
 	AST_LIST_LOCK(&registrations);
 	AST_LIST_INSERT_HEAD(&registrations, reg, entry);
 	AST_LIST_UNLOCK(&registrations);
-	
+
 	return 0;
 }
 
@@ -12200,6 +12225,9 @@ static int iax2_do_register(struct iax2_registry *reg)
 			(5 * reg->refresh / 6) * 1000, iax2_do_register_s, reg);
 		return -1;
 	}
+	if (!ast_sockaddr_port(&reg->addr) && reg->port) {
+		ast_sockaddr_set_port(&reg->addr, reg->port);
+	}
 
 	if (!reg->callno) {
 		struct sockaddr_in reg_addr;