Commit 0aa4b1fb authored by venaas's avatar venaas Committed by venaas
Browse files

make clientwr not try to connect (left to reader), changed some timing stuff,...

make clientwr not try to connect (left to reader), changed some timing stuff, issue with statusserver and connection down..., added optional cacheexpiry option for tls blocks

git-svn-id: https://svn.testnett.uninett.no/radsecproxy/trunk@398 e88ac4ed-0b26-0410-9574-a7f39faa03bf
parent 68d4aae0
...@@ -297,12 +297,16 @@ void *dtlsservernew(void *arg) { ...@@ -297,12 +297,16 @@ void *dtlsservernew(void *arg) {
struct list_node *cur = NULL; struct list_node *cur = NULL;
SSL *ssl = NULL; SSL *ssl = NULL;
X509 *cert = NULL; X509 *cert = NULL;
SSL_CTX *ctx = NULL;
uint8_t delay = 60; uint8_t delay = 60;
debug(DBG_DBG, "dtlsservernew: starting"); debug(DBG_DBG, "dtlsservernew: starting");
conf = find_clconf(RAD_DTLS, (struct sockaddr *)&params->addr, NULL); conf = find_clconf(RAD_DTLS, (struct sockaddr *)&params->addr, NULL);
if (conf) { if (conf) {
ssl = dtlsacccon(1, conf->ssl_ctx, params->sock, (struct sockaddr *)&params->addr, params->sesscache->rbios); ctx = tlsgetctx(RAD_DTLS, conf->tlsconf);
if (!ctx)
goto exit;
ssl = dtlsacccon(1, ctx, params->sock, (struct sockaddr *)&params->addr, params->sesscache->rbios);
if (!ssl) if (!ssl)
goto exit; goto exit;
cert = verifytlscert(ssl); cert = verifytlscert(ssl);
...@@ -472,7 +476,8 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char * ...@@ -472,7 +476,8 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char *
struct timeval now; struct timeval now;
time_t elapsed; time_t elapsed;
X509 *cert; X509 *cert;
SSL_CTX *ctx = NULL;
debug(DBG_DBG, "dtlsconnect: called from %s", text); debug(DBG_DBG, "dtlsconnect: called from %s", text);
pthread_mutex_lock(&server->lock); pthread_mutex_lock(&server->lock);
if (when && memcmp(&server->lastconnecttry, when, sizeof(struct timeval))) { if (when && memcmp(&server->lastconnecttry, when, sizeof(struct timeval))) {
...@@ -510,7 +515,11 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char * ...@@ -510,7 +515,11 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char *
debug(DBG_WARN, "dtlsconnect: trying to open DTLS connection to %s port %s", server->conf->host, server->conf->port); debug(DBG_WARN, "dtlsconnect: trying to open DTLS connection to %s port %s", server->conf->host, server->conf->port);
SSL_free(server->ssl); SSL_free(server->ssl);
server->ssl = dtlsacccon(0, server->conf->ssl_ctx, server->sock, server->conf->addrinfo->ai_addr, server->rbios); server->ssl = NULL;
ctx = tlsgetctx(RAD_DTLS, server->conf->tlsconf);
if (!ctx)
continue;
server->ssl = dtlsacccon(0, ctx, server->sock, server->conf->addrinfo->ai_addr, server->rbios);
if (!server->ssl) if (!server->ssl)
continue; continue;
debug(DBG_DBG, "dtlsconnect: DTLS: ok"); debug(DBG_DBG, "dtlsconnect: DTLS: ok");
...@@ -525,6 +534,7 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char * ...@@ -525,6 +534,7 @@ int dtlsconnect(struct server *server, struct timeval *when, int timeout, char *
} }
X509_free(cert); X509_free(cert);
debug(DBG_WARN, "dtlsconnect: DTLS connection to %s port %s up", server->conf->host, server->conf->port); debug(DBG_WARN, "dtlsconnect: DTLS connection to %s port %s up", server->conf->host, server->conf->port);
server->connectionok = 1;
gettimeofday(&server->lastconnecttry, NULL); gettimeofday(&server->lastconnecttry, NULL);
pthread_mutex_unlock(&server->lock); pthread_mutex_unlock(&server->lock);
return 1; return 1;
...@@ -536,12 +546,13 @@ int clientradputdtls(struct server *server, unsigned char *rad) { ...@@ -536,12 +546,13 @@ int clientradputdtls(struct server *server, unsigned char *rad) {
unsigned long error; unsigned long error;
struct clsrvconf *conf = server->conf; struct clsrvconf *conf = server->conf;
if (!server->ssl) if (!server->connectionok)
return 0; return 0;
len = RADLEN(rad); len = RADLEN(rad);
while ((cnt = SSL_write(server->ssl, rad, len)) <= 0) { if ((cnt = SSL_write(server->ssl, rad, len)) <= 0) {
while ((error = ERR_get_error())) while ((error = ERR_get_error()))
debug(DBG_ERR, "clientradputdtls: DTLS: %s", ERR_error_string(error, NULL)); debug(DBG_ERR, "clientradputdtls: DTLS: %s", ERR_error_string(error, NULL));
return 0;
} }
debug(DBG_DBG, "clientradputdtls: Sent %d bytes, Radius packet of length %d to DTLS peer %s", cnt, len, conf->host); debug(DBG_DBG, "clientradputdtls: Sent %d bytes, Radius packet of length %d to DTLS peer %s", cnt, len, conf->host);
return 1; return 1;
......
...@@ -1019,7 +1019,8 @@ void sendrq(struct server *to, struct request *rq) { ...@@ -1019,7 +1019,8 @@ void sendrq(struct server *to, struct request *rq) {
return; return;
errexit: errexit:
rmclientrq(rq, rq->msg->id); if (rq->from)
rmclientrq(rq, rq->msg->id);
freerq(rq); freerq(rq);
pthread_mutex_unlock(&to->newrq_mutex); pthread_mutex_unlock(&to->newrq_mutex);
} }
...@@ -2061,7 +2062,8 @@ void *clientwr(void *arg) { ...@@ -2061,7 +2062,8 @@ void *clientwr(void *arg) {
struct server *server = (struct server *)arg; struct server *server = (struct server *)arg;
struct rqout *rqout = NULL; struct rqout *rqout = NULL;
pthread_t clientrdth; pthread_t clientrdth;
int i, secs, dynconffail = 0; int i, dynconffail = 0;
time_t secs;
uint8_t rnd; uint8_t rnd;
struct timeval now, laststatsrv; struct timeval now, laststatsrv;
struct timespec timeout; struct timespec timeout;
...@@ -2107,6 +2109,8 @@ void *clientwr(void *arg) { ...@@ -2107,6 +2109,8 @@ void *clientwr(void *arg) {
rnd /= 32; rnd /= 32;
if (conf->statusserver) { if (conf->statusserver) {
secs = server->lastrcv.tv_sec > laststatsrv.tv_sec ? server->lastrcv.tv_sec : laststatsrv.tv_sec; secs = server->lastrcv.tv_sec > laststatsrv.tv_sec ? server->lastrcv.tv_sec : laststatsrv.tv_sec;
if (now.tv_sec - secs > STATUS_SERVER_PERIOD)
secs = now.tv_sec;
if (!timeout.tv_sec || timeout.tv_sec > secs + STATUS_SERVER_PERIOD + rnd) if (!timeout.tv_sec || timeout.tv_sec > secs + STATUS_SERVER_PERIOD + rnd)
timeout.tv_sec = secs + STATUS_SERVER_PERIOD + rnd; timeout.tv_sec = secs + STATUS_SERVER_PERIOD + rnd;
} else { } else {
...@@ -2182,7 +2186,7 @@ void *clientwr(void *arg) { ...@@ -2182,7 +2186,7 @@ void *clientwr(void *arg) {
conf->pdef->clientradput(server, rqout->rq->buf); conf->pdef->clientradput(server, rqout->rq->buf);
pthread_mutex_unlock(rqout->lock); pthread_mutex_unlock(rqout->lock);
} }
if (conf->statusserver) { if (conf->statusserver && server->connectionok) {
secs = server->lastrcv.tv_sec > laststatsrv.tv_sec ? server->lastrcv.tv_sec : laststatsrv.tv_sec; secs = server->lastrcv.tv_sec > laststatsrv.tv_sec ? server->lastrcv.tv_sec : laststatsrv.tv_sec;
gettimeofday(&now, NULL); gettimeofday(&now, NULL);
if (now.tv_sec - secs > STATUS_SERVER_PERIOD) { if (now.tv_sec - secs > STATUS_SERVER_PERIOD) {
...@@ -2388,24 +2392,50 @@ SSL_CTX *tlscreatectx(uint8_t type, struct tls *conf) { ...@@ -2388,24 +2392,50 @@ SSL_CTX *tlscreatectx(uint8_t type, struct tls *conf) {
return ctx; return ctx;
} }
SSL_CTX *tlsgetctx(uint8_t type, char *alt1, char *alt2) { struct tls *tlsgettls(char *alt1, char *alt2) {
struct tls *t; struct tls *t;
t = hash_read(tlsconfs, alt1, strlen(alt1)); t = hash_read(tlsconfs, alt1, strlen(alt1));
if (!t) { if (!t)
t = hash_read(tlsconfs, alt2, strlen(alt2)); t = hash_read(tlsconfs, alt2, strlen(alt2));
if (!t) return t;
return NULL; }
}
SSL_CTX *tlsgetctx(uint8_t type, struct tls *t) {
struct timeval now;
if (!t)
return NULL;
gettimeofday(&now, NULL);
switch (type) { switch (type) {
case RAD_TLS: case RAD_TLS:
if (!t->tlsctx) if (t->tlsexpiry && t->tlsctx) {
if (t->tlsexpiry < now.tv_sec) {
t->tlsexpiry = now.tv_sec + t->cacheexpiry;
SSL_CTX_free(t->tlsctx);
return t->tlsctx = tlscreatectx(RAD_TLS, t);
}
}
if (!t->tlsctx) {
t->tlsctx = tlscreatectx(RAD_TLS, t); t->tlsctx = tlscreatectx(RAD_TLS, t);
if (t->cacheexpiry)
t->tlsexpiry = now.tv_sec + t->cacheexpiry;
}
return t->tlsctx; return t->tlsctx;
case RAD_DTLS: case RAD_DTLS:
if (!t->dtlsctx) if (t->dtlsexpiry && t->dtlsctx) {
if (t->dtlsexpiry < now.tv_sec) {
t->dtlsexpiry = now.tv_sec + t->cacheexpiry;
SSL_CTX_free(t->dtlsctx);
return t->dtlsctx = tlscreatectx(RAD_DTLS, t);
}
}
if (!t->dtlsctx) {
t->dtlsctx = tlscreatectx(RAD_DTLS, t); t->dtlsctx = tlscreatectx(RAD_DTLS, t);
if (t->cacheexpiry)
t->dtlsexpiry = now.tv_sec + t->cacheexpiry;
}
return t->dtlsctx; return t->dtlsctx;
} }
return NULL; return NULL;
...@@ -3066,8 +3096,8 @@ int confclient_cb(struct gconffile **cf, void *arg, char *block, char *opt, char ...@@ -3066,8 +3096,8 @@ int confclient_cb(struct gconffile **cf, void *arg, char *block, char *opt, char
free(conftype); free(conftype);
if (conf->type == RAD_TLS || conf->type == RAD_DTLS) { if (conf->type == RAD_TLS || conf->type == RAD_DTLS) {
conf->ssl_ctx = conf->tls ? tlsgetctx(conf->type, conf->tls, NULL) : tlsgetctx(conf->type, "defaultclient", "default"); conf->tlsconf = conf->tls ? tlsgettls(conf->tls, NULL) : tlsgettls("defaultclient", "default");
if (!conf->ssl_ctx) if (!conf->tlsconf)
debugx(1, DBG_ERR, "error in block %s, no tls context defined", block); debugx(1, DBG_ERR, "error in block %s, no tls context defined", block);
if (conf->matchcertattr && !addmatchcertattr(conf)) if (conf->matchcertattr && !addmatchcertattr(conf))
debugx(1, DBG_ERR, "error in block %s, invalid MatchCertificateAttributeValue", block); debugx(1, DBG_ERR, "error in block %s, invalid MatchCertificateAttributeValue", block);
...@@ -3117,8 +3147,8 @@ int confclient_cb(struct gconffile **cf, void *arg, char *block, char *opt, char ...@@ -3117,8 +3147,8 @@ int confclient_cb(struct gconffile **cf, void *arg, char *block, char *opt, char
int compileserverconfig(struct clsrvconf *conf, const char *block) { int compileserverconfig(struct clsrvconf *conf, const char *block) {
if (conf->type == RAD_TLS || conf->type == RAD_DTLS) { if (conf->type == RAD_TLS || conf->type == RAD_DTLS) {
conf->ssl_ctx = conf->tls ? tlsgetctx(conf->type, conf->tls, NULL) : tlsgetctx(conf->type, "defaultserver", "default"); conf->tlsconf = conf->tls ? tlsgettls(conf->tls, NULL) : tlsgettls("defaultserver", "default");
if (!conf->ssl_ctx) { if (!conf->tlsconf) {
debug(DBG_ERR, "error in block %s, no tls context defined", block); debug(DBG_ERR, "error in block %s, no tls context defined", block);
return 0; return 0;
} }
...@@ -3306,6 +3336,7 @@ int confrealm_cb(struct gconffile **cf, void *arg, char *block, char *opt, char ...@@ -3306,6 +3336,7 @@ int confrealm_cb(struct gconffile **cf, void *arg, char *block, char *opt, char
int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *val) { int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *val) {
struct tls *conf; struct tls *conf;
long int expiry = LONG_MIN;
debug(DBG_DBG, "conftls_cb called for %s", block); debug(DBG_DBG, "conftls_cb called for %s", block);
...@@ -3322,6 +3353,7 @@ int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *v ...@@ -3322,6 +3353,7 @@ int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *v
"CertificateFile", CONF_STR, &conf->certfile, "CertificateFile", CONF_STR, &conf->certfile,
"CertificateKeyFile", CONF_STR, &conf->certkeyfile, "CertificateKeyFile", CONF_STR, &conf->certkeyfile,
"CertificateKeyPassword", CONF_STR, &conf->certkeypwd, "CertificateKeyPassword", CONF_STR, &conf->certkeypwd,
"CacheExpiry", CONF_LINT, &expiry,
"CRLCheck", CONF_BLN, &conf->crlcheck, "CRLCheck", CONF_BLN, &conf->crlcheck,
NULL NULL
)) { )) {
...@@ -3336,6 +3368,13 @@ int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *v ...@@ -3336,6 +3368,13 @@ int conftls_cb(struct gconffile **cf, void *arg, char *block, char *opt, char *v
debug(DBG_ERR, "conftls_cb: CA Certificate file or path need to be specified in block %s", val); debug(DBG_ERR, "conftls_cb: CA Certificate file or path need to be specified in block %s", val);
goto errexit; goto errexit;
} }
if (expiry != LONG_MIN) {
if (expiry < 0) {
debug(DBG_ERR, "error in block %s, value of option CacheExpiry is %ld, may not be negative", val, expiry);
goto errexit;
}
conf->cacheexpiry = expiry;
}
conf->name = stringcopy(val, 0); conf->name = stringcopy(val, 0);
if (!conf->name) { if (!conf->name) {
......
...@@ -90,12 +90,12 @@ struct clsrvconf { ...@@ -90,12 +90,12 @@ struct clsrvconf {
uint8_t retrycount; uint8_t retrycount;
uint8_t dupinterval; uint8_t dupinterval;
uint8_t certnamecheck; uint8_t certnamecheck;
SSL_CTX *ssl_ctx;
struct rewrite *rewritein; struct rewrite *rewritein;
struct rewrite *rewriteout; struct rewrite *rewriteout;
struct addrinfo *addrinfo; struct addrinfo *addrinfo;
uint8_t prefixlen; uint8_t prefixlen;
pthread_mutex_t *lock; /* only used for updating clients so far */ pthread_mutex_t *lock; /* only used for updating clients so far */
struct tls *tlsconf;
struct list *clients; struct list *clients;
struct server *servers; struct server *servers;
}; };
...@@ -150,6 +150,9 @@ struct tls { ...@@ -150,6 +150,9 @@ struct tls {
char *certkeyfile; char *certkeyfile;
char *certkeypwd; char *certkeypwd;
uint8_t crlcheck; uint8_t crlcheck;
uint32_t cacheexpiry;
uint32_t tlsexpiry;
uint32_t dtlsexpiry;
SSL_CTX *tlsctx; SSL_CTX *tlsctx;
SSL_CTX *dtlsctx; SSL_CTX *dtlsctx;
}; };
...@@ -212,3 +215,4 @@ int verifyconfcert(X509 *cert, struct clsrvconf *conf); ...@@ -212,3 +215,4 @@ int verifyconfcert(X509 *cert, struct clsrvconf *conf);
void replyh(struct server *server, unsigned char *buf); void replyh(struct server *server, unsigned char *buf);
int connecttcp(struct addrinfo *addrinfo, struct addrinfo *src); int connecttcp(struct addrinfo *addrinfo, struct addrinfo *src);
int bindtoaddr(struct addrinfo *addrinfo, int family, int reuse, int v6only); int bindtoaddr(struct addrinfo *addrinfo, int family, int reuse, int v6only);
SSL_CTX *tlsgetctx(uint8_t type, struct tls *t);
...@@ -75,6 +75,7 @@ int tcpconnect(struct server *server, struct timeval *when, int timeout, char *t ...@@ -75,6 +75,7 @@ int tcpconnect(struct server *server, struct timeval *when, int timeout, char *t
debug(DBG_ERR, "tcpconnect: connecttcp failed"); debug(DBG_ERR, "tcpconnect: connecttcp failed");
} }
debug(DBG_WARN, "tcpconnect: TCP connection to %s port %s up", server->conf->host, server->conf->port); debug(DBG_WARN, "tcpconnect: TCP connection to %s port %s up", server->conf->host, server->conf->port);
server->connectionok = 1;
gettimeofday(&server->lastconnecttry, NULL); gettimeofday(&server->lastconnecttry, NULL);
pthread_mutex_unlock(&server->lock); pthread_mutex_unlock(&server->lock);
return 1; return 1;
...@@ -150,18 +151,15 @@ unsigned char *radtcpget(int s, int timeout) { ...@@ -150,18 +151,15 @@ unsigned char *radtcpget(int s, int timeout) {
int clientradputtcp(struct server *server, unsigned char *rad) { int clientradputtcp(struct server *server, unsigned char *rad) {
int cnt; int cnt;
size_t len; size_t len;
struct timeval lastconnecttry;
struct clsrvconf *conf = server->conf; struct clsrvconf *conf = server->conf;
if (!server->connectionok)
return 0;
len = RADLEN(rad); len = RADLEN(rad);
lastconnecttry = server->lastconnecttry; if ((cnt = write(server->sock, rad, len)) <= 0) {
while ((cnt = write(server->sock, rad, len)) <= 0) {
debug(DBG_ERR, "clientradputtcp: write error"); debug(DBG_ERR, "clientradputtcp: write error");
tcpconnect(server, &lastconnecttry, 0, "clientradputtcp"); return 0;
lastconnecttry = server->lastconnecttry;
} }
server->connectionok = 1;
debug(DBG_DBG, "clientradputtcp: Sent %d bytes, Radius packet of length %d to TCP peer %s", cnt, len, conf->host); debug(DBG_DBG, "clientradputtcp: Sent %d bytes, Radius packet of length %d to TCP peer %s", cnt, len, conf->host);
return 1; return 1;
} }
......
...@@ -36,6 +36,7 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t ...@@ -36,6 +36,7 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t
struct timeval now; struct timeval now;
time_t elapsed; time_t elapsed;
X509 *cert; X509 *cert;
SSL_CTX *ctx = NULL;
unsigned long error; unsigned long error;
debug(DBG_DBG, "tlsconnect: called from %s", text); debug(DBG_DBG, "tlsconnect: called from %s", text);
...@@ -81,7 +82,14 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t ...@@ -81,7 +82,14 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t
} }
SSL_free(server->ssl); SSL_free(server->ssl);
server->ssl = SSL_new(server->conf->ssl_ctx); server->ssl = NULL;
ctx = tlsgetctx(RAD_TLS, server->conf->tlsconf);
if (!ctx)
continue;
server->ssl = SSL_new(ctx);
if (!server->ssl)
continue;
SSL_set_fd(server->ssl, server->sock); SSL_set_fd(server->ssl, server->sock);
if (SSL_connect(server->ssl) <= 0) { if (SSL_connect(server->ssl) <= 0) {
while ((error = ERR_get_error())) while ((error = ERR_get_error()))
...@@ -98,6 +106,7 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t ...@@ -98,6 +106,7 @@ int tlsconnect(struct server *server, struct timeval *when, int timeout, char *t
X509_free(cert); X509_free(cert);
} }
debug(DBG_WARN, "tlsconnect: TLS connection to %s port %s up", server->conf->host, server->conf->port); debug(DBG_WARN, "tlsconnect: TLS connection to %s port %s up", server->conf->host, server->conf->port);
server->connectionok = 1;
gettimeofday(&server->lastconnecttry, NULL); gettimeofday(&server->lastconnecttry, NULL);
pthread_mutex_unlock(&server->lock); pthread_mutex_unlock(&server->lock);
return 1; return 1;
...@@ -186,21 +195,17 @@ int clientradputtls(struct server *server, unsigned char *rad) { ...@@ -186,21 +195,17 @@ int clientradputtls(struct server *server, unsigned char *rad) {
int cnt; int cnt;
size_t len; size_t len;
unsigned long error; unsigned long error;
struct timeval lastconnecttry;
struct clsrvconf *conf = server->conf; struct clsrvconf *conf = server->conf;
if (!server->connectionok)
return 0;
len = RADLEN(rad); len = RADLEN(rad);
lastconnecttry = server->lastconnecttry; if ((cnt = SSL_write(server->ssl, rad, len)) <= 0) {
while ((cnt = SSL_write(server->ssl, rad, len)) <= 0) {
while ((error = ERR_get_error())) while ((error = ERR_get_error()))
debug(DBG_ERR, "clientradputtls: TLS: %s", ERR_error_string(error, NULL)); debug(DBG_ERR, "clientradputtls: TLS: %s", ERR_error_string(error, NULL));
if (server->dynamiclookuparg) return 0;
return 0;
tlsconnect(server, &lastconnecttry, 0, "clientradputtls");
lastconnecttry = server->lastconnecttry;
} }
server->connectionok = 1;
debug(DBG_DBG, "clientradputtls: Sent %d bytes, Radius packet of length %d to TLS peer %s", cnt, len, conf->host); debug(DBG_DBG, "clientradputtls: Sent %d bytes, Radius packet of length %d to TLS peer %s", cnt, len, conf->host);
return 1; return 1;
} }
...@@ -325,6 +330,7 @@ void *tlsservernew(void *arg) { ...@@ -325,6 +330,7 @@ void *tlsservernew(void *arg) {
struct list_node *cur = NULL; struct list_node *cur = NULL;
SSL *ssl = NULL; SSL *ssl = NULL;
X509 *cert = NULL; X509 *cert = NULL;
SSL_CTX *ctx = NULL;
unsigned long error; unsigned long error;
struct client *client; struct client *client;
...@@ -337,7 +343,12 @@ void *tlsservernew(void *arg) { ...@@ -337,7 +343,12 @@ void *tlsservernew(void *arg) {
conf = find_clconf(RAD_TLS, (struct sockaddr *)&from, &cur); conf = find_clconf(RAD_TLS, (struct sockaddr *)&from, &cur);
if (conf) { if (conf) {
ssl = SSL_new(conf->ssl_ctx); ctx = tlsgetctx(RAD_TLS, conf->tlsconf);
if (!ctx)
goto exit;
ssl = SSL_new(ctx);
if (!ssl)
goto exit;
SSL_set_fd(ssl, s); SSL_set_fd(ssl, s);
if (SSL_accept(ssl) <= 0) { if (SSL_accept(ssl) <= 0) {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment