/* X509_VERIFY_PARAM functions */
+#define SET_HOST 0
+#define ADD_HOST 1
+
+static char *str_copy(const char *s) { return OPENSSL_strdup(s); }
+static void str_free(char *s) { OPENSSL_free(s); }
+
+#define string_stack_free(sk) sk_OPENSSL_STRING_pop_free(sk, str_free)
+
+static int int_x509_param_set_hosts(X509_VERIFY_PARAM_ID *id, int mode,
+ const unsigned char *name, size_t namelen)
+ {
+ char *copy;
+
+ /*
+ * Refuse names with embedded NUL bytes, except perhaps as final byte.
+ * XXX: Do we need to push an error onto the error stack?
+ */
+ if (namelen == 0)
+ namelen = name ? strlen((char *)name) : 0;
+ else if (name && memchr(name, '\0', namelen > 1 ? namelen-1 : namelen))
+ return 0;
+ if (name && name[namelen-1] == '\0')
+ --namelen;
+
+ if (mode == SET_HOST && id->hosts)
+ {
+ string_stack_free(id->hosts);
+ id->hosts = NULL;
+ }
+ if (name == NULL || namelen == 0)
+ return 1;
+
+ copy = BUF_strndup((char *)name, namelen);
+ if (copy == NULL)
+ return 0;
+
+ if (id->hosts == NULL &&
+ (id->hosts = sk_OPENSSL_STRING_new_null()) == NULL)
+ {
+ OPENSSL_free(copy);
+ return 0;
+ }
+
+ if (!sk_OPENSSL_STRING_push(id->hosts, copy))
+ {
+ OPENSSL_free(copy);
+ if (sk_OPENSSL_STRING_num(id->hosts) == 0)
+ {
+ sk_OPENSSL_STRING_free(id->hosts);
+ id->hosts = NULL;
+ }
+ return 0;
+ }
+
+ return 1;
+ }
+
static void x509_verify_param_zero(X509_VERIFY_PARAM *param)
{
X509_VERIFY_PARAM_ID *paramid;
param->policies = NULL;
}
paramid = param->id;
- if (paramid->host)
+ if (paramid->hosts)
{
- OPENSSL_free(paramid->host);
- paramid->host = NULL;
+ string_stack_free(paramid->hosts);
+ paramid->hosts = NULL;
}
if (paramid->email)
{
return 0;
}
- if (test_x509_verify_param_copy_id(host, NULL))
+ /* Copy the host flags if and only if we're copying the host list */
+ if (test_x509_verify_param_copy_id(hosts, NULL))
{
- if (!X509_VERIFY_PARAM_set1_host(dest, id->host, 0))
- return 0;
- dest->id->hostflags = id->hostflags;
+ if (dest->id->hosts)
+ {
+ string_stack_free(dest->id->hosts);
+ dest->id->hosts = NULL;
+ }
+ if (id->hosts)
+ {
+ dest->id->hosts =
+ sk_OPENSSL_STRING_deep_copy(id->hosts,
+ str_copy, str_free);
+ if (dest->id->hosts == NULL)
+ return 0;
+ dest->id->hostflags = id->hostflags;
+ }
}
if (test_x509_verify_param_copy_id(email, NULL))
int X509_VERIFY_PARAM_set1_host(X509_VERIFY_PARAM *param,
const unsigned char *name, size_t namelen)
{
- return int_x509_param_set1(¶m->id->host, NULL, name, namelen);
+ return int_x509_param_set_hosts(param->id, SET_HOST, name, namelen);
+ }
+
+int X509_VERIFY_PARAM_add1_host(X509_VERIFY_PARAM *param,
+ const unsigned char *name, size_t namelen)
+ {
+ return int_x509_param_set_hosts(param->id, ADD_HOST, name, namelen);
}
void X509_VERIFY_PARAM_set_hostflags(X509_VERIFY_PARAM *param,