Unify coding style
@sjaeckel integrated clang-format with formal coding style. Run his script and commit changes. There are pros and cons of this commit. Mixed coding style is a "broken window". A good single style simplifies reading and writing code. On the other hand, this is a big change which will lead to conflicts.
This commit is contained in:
@@ -19,23 +19,23 @@
|
||||
|
||||
#include <strophe.h>
|
||||
|
||||
int handle_reply(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
int handle_reply(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_stanza_t *query, *item;
|
||||
const char *type;
|
||||
|
||||
type = xmpp_stanza_get_type(stanza);
|
||||
if (strcmp(type, "error") == 0)
|
||||
fprintf(stderr, "ERROR: query failed\n");
|
||||
fprintf(stderr, "ERROR: query failed\n");
|
||||
else {
|
||||
query = xmpp_stanza_get_child_by_name(stanza, "query");
|
||||
printf("Active Sessions:\n");
|
||||
for (item = xmpp_stanza_get_children(query); item;
|
||||
item = xmpp_stanza_get_next(item))
|
||||
printf("\t %s\n", xmpp_stanza_get_attribute(item, "jid"));
|
||||
printf("END OF LIST\n");
|
||||
query = xmpp_stanza_get_child_by_name(stanza, "query");
|
||||
printf("Active Sessions:\n");
|
||||
for (item = xmpp_stanza_get_children(query); item;
|
||||
item = xmpp_stanza_get_next(item))
|
||||
printf("\t %s\n", xmpp_stanza_get_attribute(item, "jid"));
|
||||
printf("END OF LIST\n");
|
||||
}
|
||||
|
||||
/* disconnect */
|
||||
@@ -44,41 +44,43 @@ int handle_reply(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
const int error, xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
xmpp_stanza_t *iq, *query;
|
||||
|
||||
if (status == XMPP_CONN_CONNECT) {
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
|
||||
/* create iq stanza for request */
|
||||
iq = xmpp_iq_new(ctx, "get", "active1");
|
||||
xmpp_stanza_set_to(iq, "xxxxxxxxx.com");
|
||||
/* create iq stanza for request */
|
||||
iq = xmpp_iq_new(ctx, "get", "active1");
|
||||
xmpp_stanza_set_to(iq, "xxxxxxxxx.com");
|
||||
|
||||
query = xmpp_stanza_new(ctx);
|
||||
xmpp_stanza_set_name(query, "query");
|
||||
xmpp_stanza_set_ns(query, XMPP_NS_DISCO_ITEMS);
|
||||
xmpp_stanza_set_attribute(query, "node", "sessions");
|
||||
query = xmpp_stanza_new(ctx);
|
||||
xmpp_stanza_set_name(query, "query");
|
||||
xmpp_stanza_set_ns(query, XMPP_NS_DISCO_ITEMS);
|
||||
xmpp_stanza_set_attribute(query, "node", "sessions");
|
||||
|
||||
xmpp_stanza_add_child(iq, query);
|
||||
xmpp_stanza_add_child(iq, query);
|
||||
|
||||
/* we can release the stanza since it belongs to iq now */
|
||||
xmpp_stanza_release(query);
|
||||
/* we can release the stanza since it belongs to iq now */
|
||||
xmpp_stanza_release(query);
|
||||
|
||||
/* set up reply handler */
|
||||
xmpp_id_handler_add(conn, handle_reply, "active1", ctx);
|
||||
/* set up reply handler */
|
||||
xmpp_id_handler_add(conn, handle_reply, "active1", ctx);
|
||||
|
||||
/* send out the stanza */
|
||||
xmpp_send(conn, iq);
|
||||
/* send out the stanza */
|
||||
xmpp_send(conn, iq);
|
||||
|
||||
/* release the stanza */
|
||||
xmpp_stanza_release(iq);
|
||||
/* release the stanza */
|
||||
xmpp_stanza_release(iq);
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -88,8 +90,8 @@ int main(int argc, char **argv)
|
||||
xmpp_conn_t *conn;
|
||||
|
||||
if (argc != 3) {
|
||||
fprintf(stderr, "Usage: active <jid> <pass>\n\n");
|
||||
return 1;
|
||||
fprintf(stderr, "Usage: active <jid> <pass>\n\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* initialize lib */
|
||||
|
||||
@@ -19,9 +19,11 @@
|
||||
#define KA_INTERVAL 1
|
||||
|
||||
/* define a handler for connection events */
|
||||
void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
const int error, xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
int secured;
|
||||
@@ -32,8 +34,7 @@ void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
fprintf(stderr, "DEBUG: connection is %s.\n",
|
||||
secured ? "secured" : "NOT secured");
|
||||
xmpp_disconnect(conn);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
}
|
||||
@@ -70,7 +71,7 @@ int main(int argc, char **argv)
|
||||
" --legacy-ssl Use old style SSL.\n"
|
||||
" --tcp-keepalive Configure TCP keepalive.\n\n"
|
||||
"Note: --disable-tls conflicts with --mandatory-tls or "
|
||||
"--legacy-ssl\n");
|
||||
"--legacy-ssl\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -87,8 +88,9 @@ int main(int argc, char **argv)
|
||||
/* init library */
|
||||
xmpp_initialize();
|
||||
|
||||
/* pass NULL instead to silence output */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG);
|
||||
/* create a context */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG); /* pass NULL instead to silence output */
|
||||
ctx = xmpp_ctx_new(NULL, log);
|
||||
|
||||
/* create a connection */
|
||||
@@ -97,7 +99,8 @@ int main(int argc, char **argv)
|
||||
/* configure connection properties (optional) */
|
||||
xmpp_conn_set_flags(conn, flags);
|
||||
/* configure TCP keepalive (optional) */
|
||||
if (tcp_keepalive) xmpp_conn_set_keepalive(conn, KA_TIMEOUT, KA_INTERVAL);
|
||||
if (tcp_keepalive)
|
||||
xmpp_conn_set_keepalive(conn, KA_TIMEOUT, KA_INTERVAL);
|
||||
|
||||
/* setup authentication information */
|
||||
xmpp_conn_set_jid(conn, jid);
|
||||
|
||||
@@ -22,12 +22,13 @@
|
||||
|
||||
#include <strophe.h>
|
||||
|
||||
|
||||
int version_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void * const userdata)
|
||||
int version_handler(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_stanza_t *reply, *query, *name, *version, *text;
|
||||
const char *ns;
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t*)userdata;
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
|
||||
printf("Received version request from %s\n", xmpp_stanza_get_from(stanza));
|
||||
|
||||
@@ -69,10 +70,11 @@ int version_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
int message_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void * const userdata)
|
||||
int message_handler(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t*)userdata;
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
xmpp_stanza_t *body, *reply;
|
||||
const char *type;
|
||||
char *intext, *replytext;
|
||||
@@ -87,7 +89,8 @@ int message_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void
|
||||
|
||||
intext = xmpp_stanza_get_text(body);
|
||||
|
||||
printf("Incoming message from %s: %s\n", xmpp_stanza_get_from(stanza), intext);
|
||||
printf("Incoming message from %s: %s\n", xmpp_stanza_get_from(stanza),
|
||||
intext);
|
||||
|
||||
reply = xmpp_stanza_reply(stanza);
|
||||
if (xmpp_stanza_get_type(reply) == NULL)
|
||||
@@ -97,7 +100,7 @@ int message_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void
|
||||
replytext = strdup("bye!");
|
||||
quit = 1;
|
||||
} else {
|
||||
replytext = (char *) malloc(strlen(" to you too!") + strlen(intext) + 1);
|
||||
replytext = (char *)malloc(strlen(" to you too!") + strlen(intext) + 1);
|
||||
strcpy(replytext, intext);
|
||||
strcat(replytext, " to you too!");
|
||||
}
|
||||
@@ -115,24 +118,26 @@ int message_handler(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza, void
|
||||
}
|
||||
|
||||
/* define a handler for connection events */
|
||||
void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
const int error, xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
|
||||
if (status == XMPP_CONN_CONNECT) {
|
||||
xmpp_stanza_t* pres;
|
||||
xmpp_stanza_t *pres;
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
xmpp_handler_add(conn, version_handler, "jabber:iq:version", "iq", NULL, ctx);
|
||||
xmpp_handler_add(conn, version_handler, "jabber:iq:version", "iq", NULL,
|
||||
ctx);
|
||||
xmpp_handler_add(conn, message_handler, NULL, "message", NULL, ctx);
|
||||
|
||||
/* Send initial <presence/> so that we appear online to contacts */
|
||||
pres = xmpp_presence_new(ctx);
|
||||
xmpp_send(conn, pres);
|
||||
xmpp_stanza_release(pres);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
}
|
||||
@@ -157,8 +162,9 @@ int main(int argc, char **argv)
|
||||
/* init library */
|
||||
xmpp_initialize();
|
||||
|
||||
/* pass NULL instead to silence output */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG);
|
||||
/* create a context */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG); /* pass NULL instead to silence output */
|
||||
ctx = xmpp_ctx_new(NULL, log);
|
||||
|
||||
/* create a connection */
|
||||
|
||||
@@ -19,19 +19,19 @@
|
||||
|
||||
#include <strophe.h>
|
||||
|
||||
|
||||
/* define a handler for connection events */
|
||||
void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
const int error, xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
|
||||
if (status == XMPP_CONN_CONNECT) {
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
xmpp_disconnect(conn);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
}
|
||||
@@ -56,19 +56,20 @@ int main(int argc, char **argv)
|
||||
host = argv[3];
|
||||
|
||||
if (argc == 5) {
|
||||
short tmp_port = (short) strtol(argv[4], &port_err, 10);
|
||||
short tmp_port = (short)strtol(argv[4], &port_err, 10);
|
||||
if (tmp_port < 0 || *port_err != '\0') {
|
||||
fprintf(stderr, "Invalid value of <port> [%s].\n", argv[4]);
|
||||
return 1;
|
||||
}
|
||||
port = (unsigned short) tmp_port;
|
||||
port = (unsigned short)tmp_port;
|
||||
}
|
||||
|
||||
/* init library */
|
||||
xmpp_initialize();
|
||||
|
||||
/* pass NULL instead to silence output */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG);
|
||||
/* create a context */
|
||||
log = xmpp_get_default_logger(XMPP_LEVEL_DEBUG); /* pass NULL instead to silence output */
|
||||
ctx = xmpp_ctx_new(NULL, log);
|
||||
|
||||
/* create a connection */
|
||||
@@ -94,4 +95,3 @@ int main(int argc, char **argv)
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -36,9 +36,8 @@ typedef struct {
|
||||
|
||||
#define FEATURES_TIMEOUT 5000 /* 5 seconds */
|
||||
|
||||
static void iq_reg_send_form(xmpp_reg_t *reg,
|
||||
xmpp_conn_t *conn,
|
||||
xmpp_stanza_t *stanza)
|
||||
static void
|
||||
iq_reg_send_form(xmpp_reg_t *reg, xmpp_conn_t *conn, xmpp_stanza_t *stanza)
|
||||
{
|
||||
xmpp_ctx_t *ctx = reg->ctx;
|
||||
xmpp_stanza_t *query;
|
||||
@@ -101,9 +100,9 @@ static void iq_reg_send_form(xmpp_reg_t *reg,
|
||||
}
|
||||
}
|
||||
|
||||
static int iq_reg2_cb(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int iq_reg2_cb(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
const char *type;
|
||||
|
||||
@@ -126,9 +125,9 @@ quit:
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int iq_reg_cb(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int iq_reg_cb(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_reg_t *reg = (xmpp_reg_t *)userdata;
|
||||
xmpp_stanza_t *registered = NULL;
|
||||
@@ -163,9 +162,9 @@ quit:
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _handle_error(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int _handle_error(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
fprintf(stderr, "DEBUG: received stream error\n");
|
||||
xmpp_disconnect(conn);
|
||||
@@ -173,9 +172,9 @@ static int _handle_error(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _handle_proceedtls_default(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int _handle_proceedtls_default(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
const char *name = xmpp_stanza_get_name(stanza);
|
||||
|
||||
@@ -193,8 +192,8 @@ static int _handle_proceedtls_default(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _handle_missing_features(xmpp_conn_t * const conn,
|
||||
void * const userdata)
|
||||
static int _handle_missing_features(xmpp_conn_t *const conn,
|
||||
void *const userdata)
|
||||
{
|
||||
fprintf(stderr, "DEBUG: timeout\n");
|
||||
xmpp_disconnect(conn);
|
||||
@@ -202,9 +201,9 @@ static int _handle_missing_features(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _handle_features(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int _handle_features(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_reg_t *reg = (xmpp_reg_t *)userdata;
|
||||
xmpp_ctx_t *ctx = reg->ctx;
|
||||
@@ -221,8 +220,8 @@ static int _handle_features(xmpp_conn_t * const conn,
|
||||
child = xmpp_stanza_new(ctx);
|
||||
xmpp_stanza_set_name(child, "starttls");
|
||||
xmpp_stanza_set_ns(child, XMPP_NS_TLS);
|
||||
xmpp_handler_add(conn, _handle_proceedtls_default,
|
||||
XMPP_NS_TLS, NULL, NULL, NULL);
|
||||
xmpp_handler_add(conn, _handle_proceedtls_default, XMPP_NS_TLS, NULL,
|
||||
NULL, NULL);
|
||||
xmpp_send(conn, child);
|
||||
xmpp_stanza_release(child);
|
||||
return 0;
|
||||
@@ -255,11 +254,11 @@ static int _handle_features(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void conn_handler(xmpp_conn_t * const conn,
|
||||
static void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_reg_t *reg = (xmpp_reg_t *)userdata;
|
||||
int secured;
|
||||
@@ -274,14 +273,14 @@ static void conn_handler(xmpp_conn_t * const conn,
|
||||
secured ? "secured" : "NOT secured");
|
||||
|
||||
/* setup handler for stream:error */
|
||||
xmpp_handler_add(conn, _handle_error, XMPP_NS_STREAMS,
|
||||
"error", NULL, NULL);
|
||||
xmpp_handler_add(conn, _handle_error, XMPP_NS_STREAMS, "error", NULL,
|
||||
NULL);
|
||||
|
||||
/* setup handlers for incoming <stream:features> */
|
||||
xmpp_handler_add(conn, _handle_features, XMPP_NS_STREAMS,
|
||||
"features", NULL, reg);
|
||||
xmpp_timed_handler_add(conn, _handle_missing_features,
|
||||
FEATURES_TIMEOUT, NULL);
|
||||
xmpp_handler_add(conn, _handle_features, XMPP_NS_STREAMS, "features",
|
||||
NULL, reg);
|
||||
xmpp_timed_handler_add(conn, _handle_missing_features, FEATURES_TIMEOUT,
|
||||
NULL);
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(reg->ctx);
|
||||
|
||||
@@ -18,31 +18,29 @@
|
||||
|
||||
#include <strophe.h>
|
||||
|
||||
int handle_reply(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
int handle_reply(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_stanza_t *query, *item;
|
||||
const char *type, *name;
|
||||
|
||||
type = xmpp_stanza_get_type(stanza);
|
||||
if (strcmp(type, "error") == 0)
|
||||
fprintf(stderr, "ERROR: query failed\n");
|
||||
fprintf(stderr, "ERROR: query failed\n");
|
||||
else {
|
||||
query = xmpp_stanza_get_child_by_name(stanza, "query");
|
||||
printf("Roster:\n");
|
||||
for (item = xmpp_stanza_get_children(query); item;
|
||||
item = xmpp_stanza_get_next(item))
|
||||
if ((name = xmpp_stanza_get_attribute(item, "name")))
|
||||
printf("\t %s (%s) sub=%s\n",
|
||||
name,
|
||||
xmpp_stanza_get_attribute(item, "jid"),
|
||||
xmpp_stanza_get_attribute(item, "subscription"));
|
||||
else
|
||||
printf("\t %s sub=%s\n",
|
||||
xmpp_stanza_get_attribute(item, "jid"),
|
||||
xmpp_stanza_get_attribute(item, "subscription"));
|
||||
printf("END OF LIST\n");
|
||||
query = xmpp_stanza_get_child_by_name(stanza, "query");
|
||||
printf("Roster:\n");
|
||||
for (item = xmpp_stanza_get_children(query); item;
|
||||
item = xmpp_stanza_get_next(item))
|
||||
if ((name = xmpp_stanza_get_attribute(item, "name")))
|
||||
printf("\t %s (%s) sub=%s\n", name,
|
||||
xmpp_stanza_get_attribute(item, "jid"),
|
||||
xmpp_stanza_get_attribute(item, "subscription"));
|
||||
else
|
||||
printf("\t %s sub=%s\n", xmpp_stanza_get_attribute(item, "jid"),
|
||||
xmpp_stanza_get_attribute(item, "subscription"));
|
||||
printf("END OF LIST\n");
|
||||
}
|
||||
|
||||
/* disconnect */
|
||||
@@ -51,39 +49,41 @@ int handle_reply(xmpp_conn_t * const conn,
|
||||
return 0;
|
||||
}
|
||||
|
||||
void conn_handler(xmpp_conn_t * const conn, const xmpp_conn_event_t status,
|
||||
const int error, xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_ctx_t *ctx = (xmpp_ctx_t *)userdata;
|
||||
xmpp_stanza_t *iq, *query;
|
||||
|
||||
if (status == XMPP_CONN_CONNECT) {
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
fprintf(stderr, "DEBUG: connected\n");
|
||||
|
||||
/* create iq stanza for request */
|
||||
iq = xmpp_iq_new(ctx, "get", "roster1");
|
||||
/* create iq stanza for request */
|
||||
iq = xmpp_iq_new(ctx, "get", "roster1");
|
||||
|
||||
query = xmpp_stanza_new(ctx);
|
||||
xmpp_stanza_set_name(query, "query");
|
||||
xmpp_stanza_set_ns(query, XMPP_NS_ROSTER);
|
||||
query = xmpp_stanza_new(ctx);
|
||||
xmpp_stanza_set_name(query, "query");
|
||||
xmpp_stanza_set_ns(query, XMPP_NS_ROSTER);
|
||||
|
||||
xmpp_stanza_add_child(iq, query);
|
||||
xmpp_stanza_add_child(iq, query);
|
||||
|
||||
/* we can release the stanza since it belongs to iq now */
|
||||
xmpp_stanza_release(query);
|
||||
/* we can release the stanza since it belongs to iq now */
|
||||
xmpp_stanza_release(query);
|
||||
|
||||
/* set up reply handler */
|
||||
xmpp_id_handler_add(conn, handle_reply, "roster1", ctx);
|
||||
/* set up reply handler */
|
||||
xmpp_id_handler_add(conn, handle_reply, "roster1", ctx);
|
||||
|
||||
/* send out the stanza */
|
||||
xmpp_send(conn, iq);
|
||||
/* send out the stanza */
|
||||
xmpp_send(conn, iq);
|
||||
|
||||
/* release the stanza */
|
||||
xmpp_stanza_release(iq);
|
||||
/* release the stanza */
|
||||
xmpp_stanza_release(iq);
|
||||
} else {
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
fprintf(stderr, "DEBUG: disconnected\n");
|
||||
xmpp_stop(ctx);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -93,8 +93,8 @@ int main(int argc, char **argv)
|
||||
xmpp_conn_t *conn;
|
||||
|
||||
if (argc != 3) {
|
||||
fprintf(stderr, "Usage: roster <jid> <pass>\n\n");
|
||||
return 1;
|
||||
fprintf(stderr, "Usage: roster <jid> <pass>\n\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* initialize lib */
|
||||
|
||||
@@ -76,8 +76,8 @@ static void vcard_photo(vcard_t *vc, xmpp_stanza_t *stanza)
|
||||
xmpp_free(vc->ctx, img);
|
||||
}
|
||||
|
||||
static void vcard_print_string(vcard_t *vc, xmpp_stanza_t *stanza,
|
||||
const char *info)
|
||||
static void
|
||||
vcard_print_string(vcard_t *vc, xmpp_stanza_t *stanza, const char *info)
|
||||
{
|
||||
char *s = xmpp_stanza_get_text(stanza);
|
||||
|
||||
@@ -140,14 +140,9 @@ static vcard_cb_t vcard_cb_get(xmpp_stanza_t *stanza)
|
||||
const char *tag;
|
||||
vcard_cb_t cb;
|
||||
} vcard_tbl[] = {
|
||||
{ "PHOTO", vcard_photo },
|
||||
{ "BDAY", vcard_bday },
|
||||
{ "DESC", vcard_desc },
|
||||
{ "EMAIL", vcard_email },
|
||||
{ "FN", vcard_fn },
|
||||
{ "N", vcard_name },
|
||||
{ "NICKNAME", vcard_nick },
|
||||
{ "URL", vcard_url },
|
||||
{"PHOTO", vcard_photo}, {"BDAY", vcard_bday}, {"DESC", vcard_desc},
|
||||
{"EMAIL", vcard_email}, {"FN", vcard_fn}, {"N", vcard_name},
|
||||
{"NICKNAME", vcard_nick}, {"URL", vcard_url},
|
||||
};
|
||||
|
||||
tag = xmpp_stanza_get_name(stanza);
|
||||
@@ -165,7 +160,7 @@ exit:
|
||||
return cb;
|
||||
}
|
||||
|
||||
static int timedout(xmpp_conn_t * const conn, void * const userdata)
|
||||
static int timedout(xmpp_conn_t *const conn, void *const userdata)
|
||||
{
|
||||
fprintf(stderr, "Timeout reached.\n");
|
||||
xmpp_disconnect(conn);
|
||||
@@ -173,8 +168,9 @@ static int timedout(xmpp_conn_t * const conn, void * const userdata)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int recv_vcard(xmpp_conn_t * const conn, xmpp_stanza_t * const stanza,
|
||||
void * const userdata)
|
||||
static int recv_vcard(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata)
|
||||
{
|
||||
vcard_t *vc = userdata;
|
||||
vcard_cb_t cb;
|
||||
@@ -213,16 +209,17 @@ exit:
|
||||
static void send_vcard_req(xmpp_conn_t *conn, const char *to, const char *id)
|
||||
{
|
||||
printf("Requesting vCard from %s.\n", to);
|
||||
xmpp_send_raw_string(conn, "<iq from='%s' to='%s' type='get' id='%s'>"
|
||||
"<vCard xmlns='vcard-temp'/></iq>",
|
||||
xmpp_conn_get_bound_jid(conn), to, id);
|
||||
xmpp_send_raw_string(conn,
|
||||
"<iq from='%s' to='%s' type='get' id='%s'>"
|
||||
"<vCard xmlns='vcard-temp'/></iq>",
|
||||
xmpp_conn_get_bound_jid(conn), to, id);
|
||||
}
|
||||
|
||||
static void conn_handler(xmpp_conn_t * const conn,
|
||||
static void conn_handler(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t status,
|
||||
const int error,
|
||||
xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata)
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata)
|
||||
{
|
||||
vcard_t *vc = userdata;
|
||||
|
||||
@@ -235,25 +232,26 @@ static void conn_handler(xmpp_conn_t * const conn,
|
||||
fprintf(stderr, "Disconnected with error=%d.\n", error);
|
||||
if (stream_error != NULL)
|
||||
fprintf(stderr, "Stream error type=%d text=%s.\n",
|
||||
stream_error->type, stream_error->text);
|
||||
stream_error->type, stream_error->text);
|
||||
xmpp_stop(vc->ctx);
|
||||
}
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
xmpp_log_t *log;
|
||||
xmpp_ctx_t *ctx;
|
||||
xmpp_log_t *log;
|
||||
xmpp_ctx_t *ctx;
|
||||
xmpp_conn_t *conn;
|
||||
const char *jid;
|
||||
const char *pass;
|
||||
char *prog;
|
||||
vcard_t vcard;
|
||||
const char *jid;
|
||||
const char *pass;
|
||||
char *prog;
|
||||
vcard_t vcard;
|
||||
|
||||
if (argc < 4 || argc > 5) {
|
||||
prog = argc > 0 ? strdup(argv[0]) : NULL;
|
||||
printf("Usage: %s <login-jid> <password> <recipient-jid> "
|
||||
"[image-file]\n\n", prog == NULL ? "vcard" : basename(prog));
|
||||
"[image-file]\n\n",
|
||||
prog == NULL ? "vcard" : basename(prog));
|
||||
printf("If vCard contains a photo it will be stored to "
|
||||
"image-file. If you don't provide the image-file "
|
||||
"default filename will be generated.\n");
|
||||
@@ -281,4 +279,3 @@ int main(int argc, char **argv)
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
965
src/auth.c
965
src/auth.c
File diff suppressed because it is too large
Load Diff
101
src/common.h
101
src/common.h
@@ -19,7 +19,6 @@
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
|
||||
|
||||
#include "strophe.h"
|
||||
#include "ostypes.h"
|
||||
#include "sock.h"
|
||||
@@ -54,35 +53,33 @@ struct _xmpp_ctx_t {
|
||||
unsigned long timeout;
|
||||
};
|
||||
|
||||
|
||||
/* convenience functions for accessing the context */
|
||||
void *xmpp_alloc(const xmpp_ctx_t * const ctx, const size_t size);
|
||||
void *xmpp_realloc(const xmpp_ctx_t * const ctx, void *p,
|
||||
const size_t size);
|
||||
char *xmpp_strdup(const xmpp_ctx_t * const ctx, const char * const s);
|
||||
void *xmpp_alloc(const xmpp_ctx_t *const ctx, const size_t size);
|
||||
void *xmpp_realloc(const xmpp_ctx_t *const ctx, void *p, const size_t size);
|
||||
char *xmpp_strdup(const xmpp_ctx_t *const ctx, const char *const s);
|
||||
|
||||
void xmpp_log(const xmpp_ctx_t * const ctx,
|
||||
void xmpp_log(const xmpp_ctx_t *const ctx,
|
||||
const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
va_list ap);
|
||||
|
||||
/* wrappers for xmpp_log at specific levels */
|
||||
void xmpp_error(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
void xmpp_error(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...);
|
||||
void xmpp_warn(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
...);
|
||||
void xmpp_info(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
...);
|
||||
void xmpp_debug(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
void xmpp_warn(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...);
|
||||
void xmpp_info(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...);
|
||||
void xmpp_debug(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...);
|
||||
|
||||
/** connection **/
|
||||
@@ -135,7 +132,7 @@ struct _xmpp_handlist_t {
|
||||
|
||||
#define MAX_DOMAIN_LEN 256
|
||||
|
||||
#define SASL_MASK_PLAIN (1 << 0)
|
||||
#define SASL_MASK_PLAIN (1 << 0)
|
||||
#define SASL_MASK_DIGESTMD5 (1 << 1)
|
||||
#define SASL_MASK_ANONYMOUS (1 << 2)
|
||||
#define SASL_MASK_SCRAMSHA1 (1 << 3)
|
||||
@@ -146,7 +143,7 @@ enum {
|
||||
XMPP_PORT_COMPONENT = 5347,
|
||||
};
|
||||
|
||||
typedef void (*xmpp_open_handler)(xmpp_conn_t * const conn);
|
||||
typedef void (*xmpp_open_handler)(xmpp_conn_t *const conn);
|
||||
|
||||
struct _xmpp_conn_t {
|
||||
unsigned int ref;
|
||||
@@ -160,7 +157,7 @@ struct _xmpp_conn_t {
|
||||
xmpp_stream_error_t *stream_error;
|
||||
|
||||
sock_t sock;
|
||||
int ka_timeout; /* TCP keepalive timeout */
|
||||
int ka_timeout; /* TCP keepalive timeout */
|
||||
int ka_interval; /* TCP keepalive interval */
|
||||
|
||||
tls_t *tls;
|
||||
@@ -169,7 +166,7 @@ struct _xmpp_conn_t {
|
||||
int tls_mandatory;
|
||||
int tls_legacy_ssl;
|
||||
int tls_trust;
|
||||
int tls_failed; /* set when tls fails, so we don't try again */
|
||||
int tls_failed; /* set when tls fails, so we don't try again */
|
||||
int sasl_support; /* if true, field is a bitfield of supported
|
||||
mechanisms */
|
||||
int auth_legacy_enabled;
|
||||
@@ -218,14 +215,13 @@ struct _xmpp_conn_t {
|
||||
xmpp_handlist_t *handlers;
|
||||
};
|
||||
|
||||
void conn_disconnect(xmpp_conn_t * const conn);
|
||||
void conn_disconnect_clean(xmpp_conn_t * const conn);
|
||||
void conn_established(xmpp_conn_t * const conn);
|
||||
void conn_open_stream(xmpp_conn_t * const conn);
|
||||
int conn_tls_start(xmpp_conn_t * const conn);
|
||||
void conn_prepare_reset(xmpp_conn_t * const conn, xmpp_open_handler handler);
|
||||
void conn_parser_reset(xmpp_conn_t * const conn);
|
||||
|
||||
void conn_disconnect(xmpp_conn_t *const conn);
|
||||
void conn_disconnect_clean(xmpp_conn_t *const conn);
|
||||
void conn_established(xmpp_conn_t *const conn);
|
||||
void conn_open_stream(xmpp_conn_t *const conn);
|
||||
int conn_tls_start(xmpp_conn_t *const conn);
|
||||
void conn_prepare_reset(xmpp_conn_t *const conn, xmpp_open_handler handler);
|
||||
void conn_parser_reset(xmpp_conn_t *const conn);
|
||||
|
||||
typedef enum {
|
||||
XMPP_STANZA_UNKNOWN,
|
||||
@@ -250,33 +246,32 @@ struct _xmpp_stanza_t {
|
||||
};
|
||||
|
||||
/* handler management */
|
||||
void handler_fire_stanza(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza);
|
||||
uint64_t handler_fire_timed(xmpp_ctx_t * const ctx);
|
||||
void handler_fire_stanza(xmpp_conn_t *const conn, xmpp_stanza_t *const stanza);
|
||||
uint64_t handler_fire_timed(xmpp_ctx_t *const ctx);
|
||||
void handler_reset_timed(xmpp_conn_t *conn, int user_only);
|
||||
void handler_add_timed(xmpp_conn_t * const conn,
|
||||
void handler_add_timed(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void * const userdata);
|
||||
void handler_add_id(xmpp_conn_t * const conn,
|
||||
void *const userdata);
|
||||
void handler_add_id(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata);
|
||||
void handler_add(xmpp_conn_t * const conn,
|
||||
const char *const id,
|
||||
void *const userdata);
|
||||
void handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata);
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata);
|
||||
void handler_system_delete_all(xmpp_conn_t *conn);
|
||||
|
||||
/* utility functions */
|
||||
void disconnect_mem_error(xmpp_conn_t * const conn);
|
||||
void disconnect_mem_error(xmpp_conn_t *const conn);
|
||||
|
||||
/* auth functions */
|
||||
void auth_handle_open(xmpp_conn_t * const conn);
|
||||
void auth_handle_component_open(xmpp_conn_t * const conn);
|
||||
void auth_handle_open_raw(xmpp_conn_t * const conn);
|
||||
void auth_handle_open_stub(xmpp_conn_t * const conn);
|
||||
void auth_handle_open(xmpp_conn_t *const conn);
|
||||
void auth_handle_component_open(xmpp_conn_t *const conn);
|
||||
void auth_handle_open_raw(xmpp_conn_t *const conn);
|
||||
void auth_handle_open_stub(xmpp_conn_t *const conn);
|
||||
|
||||
#endif /* __LIBSTROPHE_COMMON_H__ */
|
||||
|
||||
371
src/conn.c
371
src/conn.c
@@ -48,32 +48,35 @@
|
||||
#define CONNECT_TIMEOUT 5000 /* 5 seconds */
|
||||
#endif
|
||||
|
||||
static int _disconnect_cleanup(xmpp_conn_t * const conn,
|
||||
void * const userdata);
|
||||
static char *_conn_build_stream_tag(xmpp_conn_t * const conn,
|
||||
char **attributes, size_t attributes_len);
|
||||
static void _conn_attributes_new(xmpp_conn_t *conn, char **attrs,
|
||||
char ***attributes, size_t *attributes_len);
|
||||
static void _conn_attributes_destroy(xmpp_conn_t *conn, char **attributes,
|
||||
static int _disconnect_cleanup(xmpp_conn_t *const conn, void *const userdata);
|
||||
static char *_conn_build_stream_tag(xmpp_conn_t *const conn,
|
||||
char **attributes,
|
||||
size_t attributes_len);
|
||||
static void _conn_attributes_new(xmpp_conn_t *conn,
|
||||
char **attrs,
|
||||
char ***attributes,
|
||||
size_t *attributes_len);
|
||||
static void _conn_attributes_destroy(xmpp_conn_t *conn,
|
||||
char **attributes,
|
||||
size_t attributes_len);
|
||||
static void _handle_stream_start(char *name, char **attrs,
|
||||
void * const userdata);
|
||||
static void _handle_stream_end(char *name,
|
||||
void * const userdata);
|
||||
static void _handle_stream_stanza(xmpp_stanza_t *stanza,
|
||||
void * const userdata);
|
||||
static unsigned short _conn_default_port(xmpp_conn_t * const conn,
|
||||
static void
|
||||
_handle_stream_start(char *name, char **attrs, void *const userdata);
|
||||
static void _handle_stream_end(char *name, void *const userdata);
|
||||
static void _handle_stream_stanza(xmpp_stanza_t *stanza, void *const userdata);
|
||||
static unsigned short _conn_default_port(xmpp_conn_t *const conn,
|
||||
xmpp_conn_type_t type);
|
||||
static void _conn_reset(xmpp_conn_t * const conn);
|
||||
static int _conn_connect(xmpp_conn_t * const conn,
|
||||
const char * const domain,
|
||||
const char * const host,
|
||||
static void _conn_reset(xmpp_conn_t *const conn);
|
||||
static int _conn_connect(xmpp_conn_t *const conn,
|
||||
const char *const domain,
|
||||
const char *const host,
|
||||
unsigned short port,
|
||||
xmpp_conn_type_t type,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata);
|
||||
void *const userdata);
|
||||
|
||||
void xmpp_send_error(xmpp_conn_t * const conn, xmpp_error_type_t const type, char * const text)
|
||||
void xmpp_send_error(xmpp_conn_t *const conn,
|
||||
xmpp_error_type_t const type,
|
||||
char *const text)
|
||||
{
|
||||
xmpp_stanza_t *error = xmpp_error_new(conn->ctx, type, text);
|
||||
|
||||
@@ -90,12 +93,13 @@ void xmpp_send_error(xmpp_conn_t * const conn, xmpp_error_type_t const type, cha
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx)
|
||||
xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t *const ctx)
|
||||
{
|
||||
xmpp_conn_t *conn = NULL;
|
||||
xmpp_connlist_t *tail, *item;
|
||||
|
||||
if (ctx == NULL) return NULL;
|
||||
if (ctx == NULL)
|
||||
return NULL;
|
||||
|
||||
conn = xmpp_alloc(ctx, sizeof(xmpp_conn_t));
|
||||
if (conn != NULL) {
|
||||
@@ -146,11 +150,9 @@ xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx)
|
||||
conn->bind_required = 0;
|
||||
conn->session_required = 0;
|
||||
|
||||
conn->parser = parser_new(conn->ctx,
|
||||
_handle_stream_start,
|
||||
_handle_stream_end,
|
||||
_handle_stream_stanza,
|
||||
conn);
|
||||
conn->parser =
|
||||
parser_new(conn->ctx, _handle_stream_start, _handle_stream_end,
|
||||
_handle_stream_stanza, conn);
|
||||
conn->reset_parser = 0;
|
||||
|
||||
conn->authenticated = 0;
|
||||
@@ -166,7 +168,8 @@ xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx)
|
||||
|
||||
/* add connection to ctx->connlist */
|
||||
tail = conn->ctx->connlist;
|
||||
while (tail && tail->next) tail = tail->next;
|
||||
while (tail && tail->next)
|
||||
tail = tail->next;
|
||||
|
||||
item = xmpp_alloc(conn->ctx, sizeof(xmpp_connlist_t));
|
||||
if (!item) {
|
||||
@@ -179,8 +182,10 @@ xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx)
|
||||
item->conn = conn;
|
||||
item->next = NULL;
|
||||
|
||||
if (tail) tail->next = item;
|
||||
else conn->ctx->connlist = item;
|
||||
if (tail)
|
||||
tail->next = item;
|
||||
else
|
||||
conn->ctx->connlist = item;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -196,7 +201,7 @@ xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
xmpp_conn_t *xmpp_conn_clone(xmpp_conn_t * const conn)
|
||||
xmpp_conn_t *xmpp_conn_clone(xmpp_conn_t *const conn)
|
||||
{
|
||||
conn->ref++;
|
||||
return conn;
|
||||
@@ -214,7 +219,7 @@ xmpp_conn_t *xmpp_conn_clone(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_conn_set_keepalive(xmpp_conn_t * const conn, int timeout, int interval)
|
||||
void xmpp_conn_set_keepalive(xmpp_conn_t *const conn, int timeout, int interval)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
@@ -240,7 +245,7 @@ void xmpp_conn_set_keepalive(xmpp_conn_t * const conn, int timeout, int interval
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_release(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_release(xmpp_conn_t *const conn)
|
||||
{
|
||||
xmpp_ctx_t *ctx;
|
||||
xmpp_connlist_t *item, *prev;
|
||||
@@ -255,8 +260,7 @@ int xmpp_conn_release(xmpp_conn_t * const conn)
|
||||
ctx = conn->ctx;
|
||||
|
||||
if (conn->state == XMPP_STATE_CONNECTING ||
|
||||
conn->state == XMPP_STATE_CONNECTED)
|
||||
{
|
||||
conn->state == XMPP_STATE_CONNECTED) {
|
||||
conn_disconnect(conn);
|
||||
}
|
||||
|
||||
@@ -317,17 +321,23 @@ int xmpp_conn_release(xmpp_conn_t * const conn)
|
||||
thli = hlitem;
|
||||
hlitem = hlitem->next;
|
||||
|
||||
if (thli->u.ns) xmpp_free(ctx, thli->u.ns);
|
||||
if (thli->u.name) xmpp_free(ctx, thli->u.name);
|
||||
if (thli->u.type) xmpp_free(ctx, thli->u.type);
|
||||
if (thli->u.ns)
|
||||
xmpp_free(ctx, thli->u.ns);
|
||||
if (thli->u.name)
|
||||
xmpp_free(ctx, thli->u.name);
|
||||
if (thli->u.type)
|
||||
xmpp_free(ctx, thli->u.type);
|
||||
xmpp_free(ctx, thli);
|
||||
}
|
||||
|
||||
parser_free(conn->parser);
|
||||
|
||||
if (conn->jid) xmpp_free(ctx, conn->jid);
|
||||
if (conn->pass) xmpp_free(ctx, conn->pass);
|
||||
if (conn->lang) xmpp_free(ctx, conn->lang);
|
||||
if (conn->jid)
|
||||
xmpp_free(ctx, conn->jid);
|
||||
if (conn->pass)
|
||||
xmpp_free(ctx, conn->pass);
|
||||
if (conn->lang)
|
||||
xmpp_free(ctx, conn->lang);
|
||||
xmpp_free(ctx, conn);
|
||||
released = 1;
|
||||
}
|
||||
@@ -343,7 +353,7 @@ int xmpp_conn_release(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
const char *xmpp_conn_get_jid(const xmpp_conn_t * const conn)
|
||||
const char *xmpp_conn_get_jid(const xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->jid;
|
||||
}
|
||||
@@ -361,7 +371,7 @@ const char *xmpp_conn_get_jid(const xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
const char *xmpp_conn_get_bound_jid(const xmpp_conn_t * const conn)
|
||||
const char *xmpp_conn_get_bound_jid(const xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->bound_jid;
|
||||
}
|
||||
@@ -377,9 +387,10 @@ const char *xmpp_conn_get_bound_jid(const xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_conn_set_jid(xmpp_conn_t * const conn, const char * const jid)
|
||||
void xmpp_conn_set_jid(xmpp_conn_t *const conn, const char *const jid)
|
||||
{
|
||||
if (conn->jid) xmpp_free(conn->ctx, conn->jid);
|
||||
if (conn->jid)
|
||||
xmpp_free(conn->ctx, conn->jid);
|
||||
conn->jid = xmpp_strdup(conn->ctx, jid);
|
||||
}
|
||||
|
||||
@@ -391,7 +402,7 @@ void xmpp_conn_set_jid(xmpp_conn_t * const conn, const char * const jid)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
const char *xmpp_conn_get_pass(const xmpp_conn_t * const conn)
|
||||
const char *xmpp_conn_get_pass(const xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->pass;
|
||||
}
|
||||
@@ -405,22 +416,23 @@ const char *xmpp_conn_get_pass(const xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_conn_set_pass(xmpp_conn_t * const conn, const char * const pass)
|
||||
void xmpp_conn_set_pass(xmpp_conn_t *const conn, const char *const pass)
|
||||
{
|
||||
if (conn->pass) xmpp_free(conn->ctx, conn->pass);
|
||||
if (conn->pass)
|
||||
xmpp_free(conn->ctx, conn->pass);
|
||||
conn->pass = xmpp_strdup(conn->ctx, pass);
|
||||
}
|
||||
|
||||
/** Get the strophe context that the connection is associated with.
|
||||
* @param conn a Strophe connection object
|
||||
*
|
||||
* @return a Strophe context
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
xmpp_ctx_t* xmpp_conn_get_context(xmpp_conn_t * const conn)
|
||||
* @param conn a Strophe connection object
|
||||
*
|
||||
* @return a Strophe context
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
xmpp_ctx_t *xmpp_conn_get_context(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->ctx;
|
||||
return conn->ctx;
|
||||
}
|
||||
|
||||
/** Initiate a connection to the XMPP server.
|
||||
@@ -444,11 +456,11 @@ xmpp_ctx_t* xmpp_conn_get_context(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
const char * const altdomain,
|
||||
int xmpp_connect_client(xmpp_conn_t *const conn,
|
||||
const char *const altdomain,
|
||||
unsigned short altport,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata)
|
||||
void *const userdata)
|
||||
{
|
||||
resolver_srv_rr_t *srv_rr_list = NULL;
|
||||
resolver_srv_rr_t *rr;
|
||||
@@ -459,7 +471,8 @@ int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
int rc;
|
||||
|
||||
domain = xmpp_jid_domain(conn->ctx, conn->jid);
|
||||
if (!domain) return XMPP_EMEM;
|
||||
if (!domain)
|
||||
return XMPP_EMEM;
|
||||
|
||||
if (altdomain != NULL) {
|
||||
xmpp_debug(conn->ctx, "xmpp", "Connecting via altdomain.");
|
||||
@@ -467,16 +480,17 @@ int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
port = altport ? altport : _conn_default_port(conn, XMPP_CLIENT);
|
||||
found = XMPP_DOMAIN_ALTDOMAIN;
|
||||
|
||||
/* SSL tunneled connection on 5223 port is legacy and doesn't
|
||||
* have an SRV record. */
|
||||
/* SSL tunneled connection on 5223 port is legacy and doesn't
|
||||
* have an SRV record. */
|
||||
} else if (!conn->tls_legacy_ssl) {
|
||||
found = resolver_srv_lookup(conn->ctx, "xmpp-client", "tcp", domain,
|
||||
&srv_rr_list);
|
||||
}
|
||||
|
||||
if (XMPP_DOMAIN_NOT_FOUND == found) {
|
||||
xmpp_debug(conn->ctx, "xmpp", "SRV lookup failed, "
|
||||
"connecting via domain.");
|
||||
xmpp_debug(conn->ctx, "xmpp",
|
||||
"SRV lookup failed, "
|
||||
"connecting via domain.");
|
||||
host = domain;
|
||||
port = altport ? altport : _conn_default_port(conn, XMPP_CLIENT);
|
||||
found = XMPP_DOMAIN_ALTDOMAIN;
|
||||
@@ -489,8 +503,8 @@ int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
port = rr->port;
|
||||
rr = rr->next;
|
||||
}
|
||||
rc = _conn_connect(conn, domain, host, port, XMPP_CLIENT,
|
||||
callback, userdata);
|
||||
rc = _conn_connect(conn, domain, host, port, XMPP_CLIENT, callback,
|
||||
userdata);
|
||||
} while (rc != 0 && rr != NULL);
|
||||
|
||||
xmpp_free(conn->ctx, domain);
|
||||
@@ -522,18 +536,22 @@ int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_connect_component(xmpp_conn_t * const conn, const char * const server,
|
||||
unsigned short port, xmpp_conn_handler callback,
|
||||
void * const userdata)
|
||||
int xmpp_connect_component(xmpp_conn_t *const conn,
|
||||
const char *const server,
|
||||
unsigned short port,
|
||||
xmpp_conn_handler callback,
|
||||
void *const userdata)
|
||||
{
|
||||
/* The server domain, jid and password MUST be specified. */
|
||||
if (!(server && conn->jid && conn->pass)) return XMPP_EINVOP;
|
||||
if (!(server && conn->jid && conn->pass))
|
||||
return XMPP_EINVOP;
|
||||
|
||||
/* XEP-0114 does not support TLS */
|
||||
xmpp_conn_disable_tls(conn);
|
||||
if (!conn->tls_disabled) {
|
||||
xmpp_error(conn->ctx, "conn", "Failed to disable TLS. "
|
||||
"XEP-0114 does not support TLS");
|
||||
xmpp_error(conn->ctx, "conn",
|
||||
"Failed to disable TLS. "
|
||||
"XEP-0114 does not support TLS");
|
||||
return XMPP_EINT;
|
||||
}
|
||||
|
||||
@@ -565,18 +583,18 @@ int xmpp_connect_component(xmpp_conn_t * const conn, const char * const server,
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_connect_raw(xmpp_conn_t * const conn,
|
||||
const char * const altdomain,
|
||||
int xmpp_connect_raw(xmpp_conn_t *const conn,
|
||||
const char *const altdomain,
|
||||
unsigned short altport,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata)
|
||||
void *const userdata)
|
||||
{
|
||||
conn->is_raw = 1;
|
||||
return xmpp_connect_client(conn, altdomain, altport, callback, userdata);
|
||||
}
|
||||
|
||||
/* Called when tcp connection is established. */
|
||||
void conn_established(xmpp_conn_t * const conn)
|
||||
void conn_established(xmpp_conn_t *const conn)
|
||||
{
|
||||
if (conn->tls_legacy_ssl && !conn->is_raw) {
|
||||
xmpp_debug(conn->ctx, "xmpp", "using legacy SSL connection");
|
||||
@@ -591,7 +609,8 @@ void conn_established(xmpp_conn_t * const conn)
|
||||
/* we skip authentication for a "raw" connection, but the event loop
|
||||
ignores user's handlers when conn->authenticated is not set. */
|
||||
conn->authenticated = 1;
|
||||
conn->conn_handler(conn, XMPP_CONN_RAW_CONNECT, 0, NULL, conn->userdata);
|
||||
conn->conn_handler(conn, XMPP_CONN_RAW_CONNECT, 0, NULL,
|
||||
conn->userdata);
|
||||
} else {
|
||||
/* send stream init */
|
||||
conn_open_stream(conn);
|
||||
@@ -609,7 +628,7 @@ void conn_established(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_open_stream_default(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_open_stream_default(xmpp_conn_t *const conn)
|
||||
{
|
||||
if (!conn->is_raw)
|
||||
return XMPP_EINVOP;
|
||||
@@ -636,7 +655,8 @@ int xmpp_conn_open_stream_default(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_open_stream(xmpp_conn_t * const conn, char **attributes,
|
||||
int xmpp_conn_open_stream(xmpp_conn_t *const conn,
|
||||
char **attributes,
|
||||
size_t attributes_len)
|
||||
{
|
||||
char *tag;
|
||||
@@ -661,7 +681,7 @@ int xmpp_conn_open_stream(xmpp_conn_t * const conn, char **attributes,
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_tls_start(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_tls_start(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn_tls_start(conn);
|
||||
}
|
||||
@@ -672,7 +692,7 @@ int xmpp_conn_tls_start(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @param conn a Strophe connection object
|
||||
*/
|
||||
void conn_disconnect_clean(xmpp_conn_t * const conn)
|
||||
void conn_disconnect_clean(xmpp_conn_t *const conn)
|
||||
{
|
||||
/* remove the timed handler */
|
||||
xmpp_timed_handler_delete(conn, _disconnect_cleanup);
|
||||
@@ -686,7 +706,7 @@ void conn_disconnect_clean(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @param conn a Strophe connection object
|
||||
*/
|
||||
void conn_disconnect(xmpp_conn_t * const conn)
|
||||
void conn_disconnect(xmpp_conn_t *const conn)
|
||||
{
|
||||
xmpp_debug(conn->ctx, "xmpp", "Closing socket.");
|
||||
conn->state = XMPP_STATE_DISCONNECTED;
|
||||
@@ -704,14 +724,14 @@ void conn_disconnect(xmpp_conn_t * const conn)
|
||||
|
||||
/* prepares a parser reset. this is called from handlers. we can't
|
||||
* reset the parser immediately as it is not re-entrant. */
|
||||
void conn_prepare_reset(xmpp_conn_t * const conn, xmpp_open_handler handler)
|
||||
void conn_prepare_reset(xmpp_conn_t *const conn, xmpp_open_handler handler)
|
||||
{
|
||||
conn->reset_parser = 1;
|
||||
conn->open_handler = handler;
|
||||
}
|
||||
|
||||
/* reset the parser */
|
||||
void conn_parser_reset(xmpp_conn_t * const conn)
|
||||
void conn_parser_reset(xmpp_conn_t *const conn)
|
||||
{
|
||||
conn->reset_parser = 0;
|
||||
parser_reset(conn->parser);
|
||||
@@ -726,7 +746,7 @@ void conn_parser_reset(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_disconnect(xmpp_conn_t * const conn)
|
||||
void xmpp_disconnect(xmpp_conn_t *const conn)
|
||||
{
|
||||
if (conn->state != XMPP_STATE_CONNECTING &&
|
||||
conn->state != XMPP_STATE_CONNECTED)
|
||||
@@ -736,8 +756,7 @@ void xmpp_disconnect(xmpp_conn_t * const conn)
|
||||
xmpp_send_raw_string(conn, "</stream:stream>");
|
||||
|
||||
/* setup timed handler in case disconnect takes too long */
|
||||
handler_add_timed(conn, _disconnect_cleanup,
|
||||
DISCONNECT_TIMEOUT, NULL);
|
||||
handler_add_timed(conn, _disconnect_cleanup, DISCONNECT_TIMEOUT, NULL);
|
||||
}
|
||||
|
||||
/** Send a raw string to the XMPP server.
|
||||
@@ -753,8 +772,7 @@ void xmpp_disconnect(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_send_raw_string(xmpp_conn_t * const conn,
|
||||
const char * const fmt, ...)
|
||||
void xmpp_send_raw_string(xmpp_conn_t *const conn, const char *const fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
size_t len;
|
||||
@@ -771,7 +789,8 @@ void xmpp_send_raw_string(xmpp_conn_t * const conn,
|
||||
len++; /* account for trailing \0 */
|
||||
bigbuf = xmpp_alloc(conn->ctx, len);
|
||||
if (!bigbuf) {
|
||||
xmpp_debug(conn->ctx, "xmpp", "Could not allocate memory for send_raw_string");
|
||||
xmpp_debug(conn->ctx, "xmpp",
|
||||
"Could not allocate memory for send_raw_string");
|
||||
return;
|
||||
}
|
||||
va_start(ap, fmt);
|
||||
@@ -802,16 +821,19 @@ void xmpp_send_raw_string(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_send_raw(xmpp_conn_t * const conn,
|
||||
const char * const data, const size_t len)
|
||||
void xmpp_send_raw(xmpp_conn_t *const conn,
|
||||
const char *const data,
|
||||
const size_t len)
|
||||
{
|
||||
xmpp_send_queue_t *item;
|
||||
|
||||
if (conn->state != XMPP_STATE_CONNECTED) return;
|
||||
if (conn->state != XMPP_STATE_CONNECTED)
|
||||
return;
|
||||
|
||||
/* create send queue item for queue */
|
||||
item = xmpp_alloc(conn->ctx, sizeof(xmpp_send_queue_t));
|
||||
if (!item) return;
|
||||
if (!item)
|
||||
return;
|
||||
|
||||
item->data = xmpp_alloc(conn->ctx, len);
|
||||
if (!item->data) {
|
||||
@@ -845,8 +867,7 @@ void xmpp_send_raw(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_send(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza)
|
||||
void xmpp_send(xmpp_conn_t *const conn, xmpp_stanza_t *const stanza)
|
||||
{
|
||||
char *buf;
|
||||
size_t len;
|
||||
@@ -866,23 +887,22 @@ void xmpp_send(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @param conn a Strophe connection object
|
||||
*/
|
||||
void conn_open_stream(xmpp_conn_t * const conn)
|
||||
void conn_open_stream(xmpp_conn_t *const conn)
|
||||
{
|
||||
xmpp_send_raw_string(conn,
|
||||
"<?xml version=\"1.0\"?>" \
|
||||
"<stream:stream to=\"%s\" " \
|
||||
"xml:lang=\"%s\" " \
|
||||
"version=\"1.0\" " \
|
||||
"xmlns=\"%s\" " \
|
||||
"<?xml version=\"1.0\"?>"
|
||||
"<stream:stream to=\"%s\" "
|
||||
"xml:lang=\"%s\" "
|
||||
"version=\"1.0\" "
|
||||
"xmlns=\"%s\" "
|
||||
"xmlns:stream=\"%s\">",
|
||||
conn->domain,
|
||||
conn->lang,
|
||||
conn->type == XMPP_CLIENT ? XMPP_NS_CLIENT :
|
||||
XMPP_NS_COMPONENT,
|
||||
conn->domain, conn->lang,
|
||||
conn->type == XMPP_CLIENT ? XMPP_NS_CLIENT
|
||||
: XMPP_NS_COMPONENT,
|
||||
XMPP_NS_STREAMS);
|
||||
}
|
||||
|
||||
int conn_tls_start(xmpp_conn_t * const conn)
|
||||
int conn_tls_start(xmpp_conn_t *const conn)
|
||||
{
|
||||
int rc;
|
||||
|
||||
@@ -906,8 +926,10 @@ int conn_tls_start(xmpp_conn_t * const conn)
|
||||
}
|
||||
}
|
||||
if (rc != 0) {
|
||||
xmpp_debug(conn->ctx, "conn", "Couldn't start TLS! "
|
||||
"error %d tls_error %d", rc, conn->error);
|
||||
xmpp_debug(conn->ctx, "conn",
|
||||
"Couldn't start TLS! "
|
||||
"error %d tls_error %d",
|
||||
rc, conn->error);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
@@ -920,7 +942,7 @@ int conn_tls_start(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
long xmpp_conn_get_flags(const xmpp_conn_t * const conn)
|
||||
long xmpp_conn_get_flags(const xmpp_conn_t *const conn)
|
||||
{
|
||||
long flags;
|
||||
|
||||
@@ -928,7 +950,8 @@ long xmpp_conn_get_flags(const xmpp_conn_t * const conn)
|
||||
XMPP_CONN_FLAG_MANDATORY_TLS * conn->tls_mandatory |
|
||||
XMPP_CONN_FLAG_LEGACY_SSL * conn->tls_legacy_ssl |
|
||||
XMPP_CONN_FLAG_TRUST_TLS * conn->tls_trust |
|
||||
XMPP_CONN_FLAG_LEGACY_AUTH * conn->auth_legacy_enabled;;
|
||||
XMPP_CONN_FLAG_LEGACY_AUTH * conn->auth_legacy_enabled;
|
||||
;
|
||||
|
||||
return flags;
|
||||
}
|
||||
@@ -955,11 +978,12 @@ long xmpp_conn_get_flags(const xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_set_flags(xmpp_conn_t * const conn, long flags)
|
||||
int xmpp_conn_set_flags(xmpp_conn_t *const conn, long flags)
|
||||
{
|
||||
if (conn->state != XMPP_STATE_DISCONNECTED) {
|
||||
xmpp_error(conn->ctx, "conn", "Flags can be set only "
|
||||
"for disconnected connection");
|
||||
xmpp_error(conn->ctx, "conn",
|
||||
"Flags can be set only "
|
||||
"for disconnected connection");
|
||||
return XMPP_EINVOP;
|
||||
}
|
||||
if (flags & XMPP_CONN_FLAG_DISABLE_TLS &&
|
||||
@@ -989,7 +1013,7 @@ int xmpp_conn_set_flags(xmpp_conn_t * const conn, long flags)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
void xmpp_conn_disable_tls(xmpp_conn_t * const conn)
|
||||
void xmpp_conn_disable_tls(xmpp_conn_t *const conn)
|
||||
{
|
||||
long flags = xmpp_conn_get_flags(conn);
|
||||
|
||||
@@ -1003,7 +1027,7 @@ void xmpp_conn_disable_tls(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_is_secured(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_is_secured(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->secured && !conn->tls_failed && conn->tls != NULL ? 1 : 0;
|
||||
}
|
||||
@@ -1013,7 +1037,7 @@ int xmpp_conn_is_secured(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_is_connecting(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_is_connecting(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->state == XMPP_STATE_CONNECTING ? 1 : 0;
|
||||
}
|
||||
@@ -1023,7 +1047,7 @@ int xmpp_conn_is_connecting(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_is_connected(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_is_connected(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->state == XMPP_STATE_CONNECTED ? 1 : 0;
|
||||
}
|
||||
@@ -1033,26 +1057,24 @@ int xmpp_conn_is_connected(xmpp_conn_t * const conn)
|
||||
*
|
||||
* @ingroup Connections
|
||||
*/
|
||||
int xmpp_conn_is_disconnected(xmpp_conn_t * const conn)
|
||||
int xmpp_conn_is_disconnected(xmpp_conn_t *const conn)
|
||||
{
|
||||
return conn->state == XMPP_STATE_DISCONNECTED ? 1 : 0;
|
||||
}
|
||||
|
||||
|
||||
/* timed handler for cleanup if normal disconnect procedure takes too long */
|
||||
static int _disconnect_cleanup(xmpp_conn_t * const conn,
|
||||
void * const userdata)
|
||||
static int _disconnect_cleanup(xmpp_conn_t *const conn, void *const userdata)
|
||||
{
|
||||
xmpp_debug(conn->ctx, "xmpp",
|
||||
"disconnection forced by cleanup timeout");
|
||||
xmpp_debug(conn->ctx, "xmpp", "disconnection forced by cleanup timeout");
|
||||
|
||||
conn_disconnect(conn);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static char *_conn_build_stream_tag(xmpp_conn_t * const conn,
|
||||
char **attributes, size_t attributes_len)
|
||||
static char *_conn_build_stream_tag(xmpp_conn_t *const conn,
|
||||
char **attributes,
|
||||
size_t attributes_len)
|
||||
{
|
||||
char *tag;
|
||||
size_t len;
|
||||
@@ -1068,7 +1090,8 @@ static char *_conn_build_stream_tag(xmpp_conn_t * const conn,
|
||||
for (i = 0; i < attributes_len; ++i)
|
||||
len += strlen(attributes[i]) + 2;
|
||||
tag = xmpp_alloc(conn->ctx, len + 1);
|
||||
if (!tag) return NULL;
|
||||
if (!tag)
|
||||
return NULL;
|
||||
|
||||
strcpy(tag, tag_head);
|
||||
for (i = 0; i < attributes_len; ++i) {
|
||||
@@ -1084,8 +1107,9 @@ static char *_conn_build_stream_tag(xmpp_conn_t * const conn,
|
||||
strcat(tag, tag_tail);
|
||||
|
||||
if (strlen(tag) != len) {
|
||||
xmpp_error(conn->ctx, "xmpp", "Internal error in "
|
||||
"_conn_build_stream_tag().");
|
||||
xmpp_error(conn->ctx, "xmpp",
|
||||
"Internal error in "
|
||||
"_conn_build_stream_tag().");
|
||||
xmpp_free(conn->ctx, tag);
|
||||
tag = NULL;
|
||||
}
|
||||
@@ -1093,20 +1117,24 @@ static char *_conn_build_stream_tag(xmpp_conn_t * const conn,
|
||||
return tag;
|
||||
}
|
||||
|
||||
static void _conn_attributes_new(xmpp_conn_t *conn, char **attrs,
|
||||
char ***attributes, size_t *attributes_len)
|
||||
static void _conn_attributes_new(xmpp_conn_t *conn,
|
||||
char **attrs,
|
||||
char ***attributes,
|
||||
size_t *attributes_len)
|
||||
{
|
||||
char **array = NULL;
|
||||
size_t nr = 0;
|
||||
size_t i;
|
||||
|
||||
if (attrs) {
|
||||
for (; attrs[nr]; ++nr);
|
||||
for (; attrs[nr]; ++nr)
|
||||
;
|
||||
array = xmpp_alloc(conn->ctx, sizeof(*array) * nr);
|
||||
for (i = 0; array && i < nr; ++i) {
|
||||
array[i] = (i & 1) == 0 ? parser_attr_name(conn->ctx, attrs[i])
|
||||
: xmpp_strdup(conn->ctx, attrs[i]);
|
||||
if (array[i] == NULL) break;
|
||||
if (array[i] == NULL)
|
||||
break;
|
||||
}
|
||||
if (!array || i < nr) {
|
||||
xmpp_error(conn->ctx, "xmpp", "Memory allocation error.");
|
||||
@@ -1119,7 +1147,8 @@ static void _conn_attributes_new(xmpp_conn_t *conn, char **attrs,
|
||||
*attributes_len = nr;
|
||||
}
|
||||
|
||||
static void _conn_attributes_destroy(xmpp_conn_t *conn, char **attributes,
|
||||
static void _conn_attributes_destroy(xmpp_conn_t *conn,
|
||||
char **attributes,
|
||||
size_t attributes_len)
|
||||
{
|
||||
size_t i;
|
||||
@@ -1150,23 +1179,24 @@ static char *_get_stream_attribute(char **attrs, char *name)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (!attrs) return NULL;
|
||||
if (!attrs)
|
||||
return NULL;
|
||||
|
||||
for (i = 0; attrs[i]; i += 2)
|
||||
if (strcmp(name, attrs[i]) == 0)
|
||||
return attrs[i+1];
|
||||
return attrs[i + 1];
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void _handle_stream_start(char *name, char **attrs,
|
||||
void * const userdata)
|
||||
static void _handle_stream_start(char *name, char **attrs, void *const userdata)
|
||||
{
|
||||
xmpp_conn_t *conn = (xmpp_conn_t *)userdata;
|
||||
char *id;
|
||||
int failed = 0;
|
||||
|
||||
if (conn->stream_id) xmpp_free(conn->ctx, conn->stream_id);
|
||||
if (conn->stream_id)
|
||||
xmpp_free(conn->ctx, conn->stream_id);
|
||||
conn->stream_id = NULL;
|
||||
|
||||
if (strcmp(name, "stream") == 0) {
|
||||
@@ -1180,8 +1210,10 @@ static void _handle_stream_start(char *name, char **attrs,
|
||||
failed = 1;
|
||||
}
|
||||
} else {
|
||||
xmpp_error(conn->ctx, "conn", "Server did not open valid stream."
|
||||
" name = %s.", name);
|
||||
xmpp_error(conn->ctx, "conn",
|
||||
"Server did not open valid stream."
|
||||
" name = %s.",
|
||||
name);
|
||||
failed = 1;
|
||||
}
|
||||
|
||||
@@ -1193,8 +1225,7 @@ static void _handle_stream_start(char *name, char **attrs,
|
||||
}
|
||||
}
|
||||
|
||||
static void _handle_stream_end(char *name,
|
||||
void * const userdata)
|
||||
static void _handle_stream_end(char *name, void *const userdata)
|
||||
{
|
||||
xmpp_conn_t *conn = (xmpp_conn_t *)userdata;
|
||||
|
||||
@@ -1203,8 +1234,7 @@ static void _handle_stream_end(char *name,
|
||||
conn_disconnect_clean(conn);
|
||||
}
|
||||
|
||||
static void _handle_stream_stanza(xmpp_stanza_t *stanza,
|
||||
void * const userdata)
|
||||
static void _handle_stream_stanza(xmpp_stanza_t *stanza, void *const userdata)
|
||||
{
|
||||
xmpp_conn_t *conn = (xmpp_conn_t *)userdata;
|
||||
char *buf;
|
||||
@@ -1218,13 +1248,13 @@ static void _handle_stream_stanza(xmpp_stanza_t *stanza,
|
||||
handler_fire_stanza(conn, stanza);
|
||||
}
|
||||
|
||||
static unsigned short _conn_default_port(xmpp_conn_t * const conn,
|
||||
static unsigned short _conn_default_port(xmpp_conn_t *const conn,
|
||||
xmpp_conn_type_t type)
|
||||
{
|
||||
switch (type) {
|
||||
case XMPP_CLIENT:
|
||||
return conn->tls_legacy_ssl ? XMPP_PORT_CLIENT_LEGACY_SSL :
|
||||
XMPP_PORT_CLIENT;
|
||||
return conn->tls_legacy_ssl ? XMPP_PORT_CLIENT_LEGACY_SSL
|
||||
: XMPP_PORT_CLIENT;
|
||||
case XMPP_COMPONENT:
|
||||
return XMPP_PORT_COMPONENT;
|
||||
default:
|
||||
@@ -1232,7 +1262,7 @@ static unsigned short _conn_default_port(xmpp_conn_t * const conn,
|
||||
};
|
||||
}
|
||||
|
||||
static void _conn_reset(xmpp_conn_t * const conn)
|
||||
static void _conn_reset(xmpp_conn_t *const conn)
|
||||
{
|
||||
xmpp_ctx_t *ctx = conn->ctx;
|
||||
xmpp_send_queue_t *sq, *tsq;
|
||||
@@ -1262,9 +1292,12 @@ static void _conn_reset(xmpp_conn_t * const conn)
|
||||
conn->stream_error = NULL;
|
||||
}
|
||||
|
||||
if (conn->domain) xmpp_free(ctx, conn->domain);
|
||||
if (conn->bound_jid) xmpp_free(ctx, conn->bound_jid);
|
||||
if (conn->stream_id) xmpp_free(ctx, conn->stream_id);
|
||||
if (conn->domain)
|
||||
xmpp_free(ctx, conn->domain);
|
||||
if (conn->bound_jid)
|
||||
xmpp_free(ctx, conn->bound_jid);
|
||||
if (conn->stream_id)
|
||||
xmpp_free(ctx, conn->stream_id);
|
||||
conn->domain = NULL;
|
||||
conn->bound_jid = NULL;
|
||||
conn->stream_id = NULL;
|
||||
@@ -1280,30 +1313,35 @@ static void _conn_reset(xmpp_conn_t * const conn)
|
||||
handler_system_delete_all(conn);
|
||||
}
|
||||
|
||||
static int _conn_connect(xmpp_conn_t * const conn,
|
||||
const char * const domain,
|
||||
const char * const host,
|
||||
static int _conn_connect(xmpp_conn_t *const conn,
|
||||
const char *const domain,
|
||||
const char *const host,
|
||||
unsigned short port,
|
||||
xmpp_conn_type_t type,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata)
|
||||
void *const userdata)
|
||||
{
|
||||
xmpp_open_handler open_handler;
|
||||
|
||||
if (conn->state != XMPP_STATE_DISCONNECTED) return XMPP_EINVOP;
|
||||
if (type != XMPP_CLIENT && type != XMPP_COMPONENT) return XMPP_EINVOP;
|
||||
if (host == NULL || port == 0) return XMPP_EINT;
|
||||
if (conn->state != XMPP_STATE_DISCONNECTED)
|
||||
return XMPP_EINVOP;
|
||||
if (type != XMPP_CLIENT && type != XMPP_COMPONENT)
|
||||
return XMPP_EINVOP;
|
||||
if (host == NULL || port == 0)
|
||||
return XMPP_EINT;
|
||||
|
||||
_conn_reset(conn);
|
||||
|
||||
conn->type = type;
|
||||
conn->domain = xmpp_strdup(conn->ctx, domain);
|
||||
if (!conn->domain) return XMPP_EMEM;
|
||||
if (!conn->domain)
|
||||
return XMPP_EMEM;
|
||||
|
||||
conn->sock = sock_connect(host, port);
|
||||
xmpp_debug(conn->ctx, "xmpp", "sock_connect() to %s:%u returned %d",
|
||||
host, port, conn->sock);
|
||||
if (conn->sock == -1) return XMPP_EINT;
|
||||
xmpp_debug(conn->ctx, "xmpp", "sock_connect() to %s:%u returned %d", host,
|
||||
port, conn->sock);
|
||||
if (conn->sock == -1)
|
||||
return XMPP_EINT;
|
||||
if (conn->ka_timeout || conn->ka_interval)
|
||||
sock_set_keepalive(conn->sock, conn->ka_timeout, conn->ka_interval);
|
||||
|
||||
@@ -1311,9 +1349,10 @@ static int _conn_connect(xmpp_conn_t * const conn,
|
||||
conn->conn_handler = callback;
|
||||
conn->userdata = userdata;
|
||||
|
||||
open_handler = conn->is_raw ? auth_handle_open_stub :
|
||||
type == XMPP_CLIENT ? auth_handle_open :
|
||||
auth_handle_component_open;
|
||||
open_handler = conn->is_raw
|
||||
? auth_handle_open_stub
|
||||
: type == XMPP_CLIENT ? auth_handle_open
|
||||
: auth_handle_component_open;
|
||||
conn_prepare_reset(conn, open_handler);
|
||||
|
||||
/* FIXME: it could happen that the connect returns immediately as
|
||||
|
||||
240
src/crypto.c
240
src/crypto.c
@@ -20,13 +20,13 @@
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <string.h> /* memset, memcpy */
|
||||
#include <string.h> /* memset, memcpy */
|
||||
|
||||
#include "common.h" /* xmpp_alloc */
|
||||
#include "ostypes.h" /* uint8_t, size_t */
|
||||
#include "common.h" /* xmpp_alloc */
|
||||
#include "ostypes.h" /* uint8_t, size_t */
|
||||
#include "sha1.h"
|
||||
#include "snprintf.h" /* xmpp_snprintf */
|
||||
#include "strophe.h" /* xmpp_ctx_t, xmpp_free */
|
||||
#include "snprintf.h" /* xmpp_snprintf */
|
||||
#include "strophe.h" /* xmpp_ctx_t, xmpp_free */
|
||||
|
||||
struct _xmpp_sha1_t {
|
||||
xmpp_ctx_t *xmpp_ctx;
|
||||
@@ -91,7 +91,8 @@ char *xmpp_sha1(xmpp_ctx_t *ctx, const unsigned char *data, size_t len)
|
||||
*
|
||||
* @ingroup Digests
|
||||
*/
|
||||
void xmpp_sha1_digest(const unsigned char *data, size_t len,
|
||||
void xmpp_sha1_digest(const unsigned char *data,
|
||||
size_t len,
|
||||
unsigned char *digest)
|
||||
{
|
||||
crypto_SHA1((const uint8_t *)data, len, digest);
|
||||
@@ -214,52 +215,44 @@ void xmpp_sha1_to_digest(xmpp_sha1_t *sha1, unsigned char *digest)
|
||||
memcpy(digest, sha1->digest, SHA1_DIGEST_SIZE);
|
||||
}
|
||||
|
||||
|
||||
/* Base64 encoding routines. Implemented according to RFC 3548. */
|
||||
|
||||
/* map of all byte values to the base64 values, or to
|
||||
'65' which indicates an invalid character. '=' is '64' */
|
||||
static const unsigned char _base64_invcharmap[256] = {
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,62, 65,65,65,63,
|
||||
52,53,54,55, 56,57,58,59, 60,61,65,65, 65,64,65,65,
|
||||
65, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10, 11,12,13,14,
|
||||
15,16,17,18, 19,20,21,22, 23,24,25,65, 65,65,65,65,
|
||||
65,26,27,28, 29,30,31,32, 33,34,35,36, 37,38,39,40,
|
||||
41,42,43,44, 45,46,47,48, 49,50,51,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65,
|
||||
65,65,65,65, 65,65,65,65, 65,65,65,65, 65,65,65,65
|
||||
};
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 62, 65, 65, 65, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60,
|
||||
61, 65, 65, 65, 64, 65, 65, 65, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
|
||||
11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 65, 65, 65, 65,
|
||||
65, 65, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42,
|
||||
43, 44, 45, 46, 47, 48, 49, 50, 51, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65, 65,
|
||||
65, 65, 65, 65, 65, 65, 65, 65, 65};
|
||||
|
||||
/* map of all 6-bit values to their corresponding byte
|
||||
in the base64 alphabet. Padding char is the value '64' */
|
||||
static const char _base64_charmap[65] = {
|
||||
'A','B','C','D', 'E','F','G','H',
|
||||
'I','J','K','L', 'M','N','O','P',
|
||||
'Q','R','S','T', 'U','V','W','X',
|
||||
'Y','Z','a','b', 'c','d','e','f',
|
||||
'g','h','i','j', 'k','l','m','n',
|
||||
'o','p','q','r', 's','t','u','v',
|
||||
'w','x','y','z', '0','1','2','3',
|
||||
'4','5','6','7', '8','9','+','/',
|
||||
'='
|
||||
};
|
||||
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
|
||||
'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
|
||||
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
|
||||
'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
|
||||
'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/', '='};
|
||||
|
||||
static size_t base64_encoded_len(const size_t len)
|
||||
{
|
||||
/* encoded steam is 4 bytes for every three, rounded up */
|
||||
return ((len + 2)/3) << 2;
|
||||
return ((len + 2) / 3) << 2;
|
||||
}
|
||||
|
||||
static char *base64_encode(xmpp_ctx_t *ctx,
|
||||
const unsigned char * const buffer, const size_t len)
|
||||
const unsigned char *const buffer,
|
||||
const size_t len)
|
||||
{
|
||||
size_t clen;
|
||||
char *cbuf, *c;
|
||||
@@ -272,7 +265,7 @@ static char *base64_encode(xmpp_ctx_t *ctx,
|
||||
c = cbuf;
|
||||
/* loop over data, turning every 3 bytes into 4 characters */
|
||||
for (i = 0; i + 2 < len; i += 3) {
|
||||
word = buffer[i] << 16 | buffer[i+1] << 8 | buffer[i+2];
|
||||
word = buffer[i] << 16 | buffer[i + 1] << 8 | buffer[i + 2];
|
||||
hextet = (word & 0x00FC0000) >> 18;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = (word & 0x0003F000) >> 12;
|
||||
@@ -284,26 +277,26 @@ static char *base64_encode(xmpp_ctx_t *ctx,
|
||||
}
|
||||
/* zero, one or two bytes left */
|
||||
switch (len - i) {
|
||||
case 0:
|
||||
break;
|
||||
case 1:
|
||||
hextet = (buffer[len-1] & 0xFC) >> 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = (buffer[len-1] & 0x03) << 4;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
break;
|
||||
case 2:
|
||||
hextet = (buffer[len-2] & 0xFC) >> 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = ((buffer[len-2] & 0x03) << 4) |
|
||||
((buffer[len-1] & 0xF0) >> 4);
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = (buffer[len-1] & 0x0F) << 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
break;
|
||||
case 0:
|
||||
break;
|
||||
case 1:
|
||||
hextet = (buffer[len - 1] & 0xFC) >> 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = (buffer[len - 1] & 0x03) << 4;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
break;
|
||||
case 2:
|
||||
hextet = (buffer[len - 2] & 0xFC) >> 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = ((buffer[len - 2] & 0x03) << 4) |
|
||||
((buffer[len - 1] & 0xF0) >> 4);
|
||||
*c++ = _base64_charmap[hextet];
|
||||
hextet = (buffer[len - 1] & 0x0F) << 2;
|
||||
*c++ = _base64_charmap[hextet];
|
||||
*c++ = _base64_charmap[64]; /* pad */
|
||||
break;
|
||||
}
|
||||
/* add a terminal null */
|
||||
*c = '\0';
|
||||
@@ -311,30 +304,37 @@ static char *base64_encode(xmpp_ctx_t *ctx,
|
||||
return cbuf;
|
||||
}
|
||||
|
||||
static size_t base64_decoded_len(const char * const buffer, const size_t len)
|
||||
static size_t base64_decoded_len(const char *const buffer, const size_t len)
|
||||
{
|
||||
size_t nudge = 0;
|
||||
unsigned char c;
|
||||
size_t i;
|
||||
|
||||
if (len < 4) return 0;
|
||||
if (len < 4)
|
||||
return 0;
|
||||
|
||||
/* count the padding characters for the remainder */
|
||||
for (i = len; i > 0; --i) {
|
||||
c = _base64_invcharmap[(unsigned char)buffer[i-1]];
|
||||
if (c < 64) break;
|
||||
if (c == 64) ++nudge;
|
||||
if (c > 64) return 0;
|
||||
c = _base64_invcharmap[(unsigned char)buffer[i - 1]];
|
||||
if (c < 64)
|
||||
break;
|
||||
if (c == 64)
|
||||
++nudge;
|
||||
if (c > 64)
|
||||
return 0;
|
||||
}
|
||||
if (nudge > 2) return 0;
|
||||
if (nudge > 2)
|
||||
return 0;
|
||||
|
||||
/* decoded steam is 3 bytes for every four */
|
||||
return 3 * (len >> 2) - nudge;
|
||||
}
|
||||
|
||||
static void base64_decode(xmpp_ctx_t *ctx,
|
||||
const char * const buffer, const size_t len,
|
||||
unsigned char **out, size_t *outlen)
|
||||
const char *const buffer,
|
||||
const size_t len,
|
||||
unsigned char **out,
|
||||
size_t *outlen)
|
||||
{
|
||||
size_t dlen;
|
||||
unsigned char *dbuf, *d;
|
||||
@@ -342,10 +342,12 @@ static void base64_decode(xmpp_ctx_t *ctx,
|
||||
size_t i;
|
||||
|
||||
/* len must be a multiple of 4 */
|
||||
if (len & 0x03) goto _base64_error;
|
||||
if (len & 0x03)
|
||||
goto _base64_error;
|
||||
|
||||
dlen = base64_decoded_len(buffer, len);
|
||||
if (dlen == 0) goto _base64_error;
|
||||
if (dlen == 0)
|
||||
goto _base64_error;
|
||||
|
||||
dbuf = xmpp_alloc(ctx, dlen + 1);
|
||||
if (dbuf != NULL) {
|
||||
@@ -353,57 +355,70 @@ static void base64_decode(xmpp_ctx_t *ctx,
|
||||
/* loop over each set of 4 characters, decoding 3 bytes */
|
||||
for (i = 0; i + 3 < len; i += 4) {
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i]];
|
||||
if (hextet & 0xC0) break;
|
||||
if (hextet & 0xC0)
|
||||
break;
|
||||
word = hextet << 18;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i+1]];
|
||||
if (hextet & 0xC0) break;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i + 1]];
|
||||
if (hextet & 0xC0)
|
||||
break;
|
||||
word |= hextet << 12;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i+2]];
|
||||
if (hextet & 0xC0) break;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i + 2]];
|
||||
if (hextet & 0xC0)
|
||||
break;
|
||||
word |= hextet << 6;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i+3]];
|
||||
if (hextet & 0xC0) break;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[i + 3]];
|
||||
if (hextet & 0xC0)
|
||||
break;
|
||||
word |= hextet;
|
||||
*d++ = (word & 0x00FF0000) >> 16;
|
||||
*d++ = (word & 0x0000FF00) >> 8;
|
||||
*d++ = (word & 0x000000FF);
|
||||
}
|
||||
if (hextet > 64) goto _base64_decode_error;
|
||||
if (hextet > 64)
|
||||
goto _base64_decode_error;
|
||||
/* handle the remainder */
|
||||
switch (dlen % 3) {
|
||||
case 0:
|
||||
/* nothing to do */
|
||||
break;
|
||||
case 1:
|
||||
/* redo the last quartet, checking for correctness */
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-4]];
|
||||
if (hextet & 0xC0) goto _base64_decode_error;
|
||||
word = hextet << 2;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-3]];
|
||||
if (hextet & 0xC0) goto _base64_decode_error;
|
||||
word |= hextet >> 4;
|
||||
*d++ = word & 0xFF;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-2]];
|
||||
if (hextet != 64) goto _base64_decode_error;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-1]];
|
||||
if (hextet != 64) goto _base64_decode_error;
|
||||
break;
|
||||
case 2:
|
||||
/* redo the last quartet, checking for correctness */
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-4]];
|
||||
if (hextet & 0xC0) goto _base64_decode_error;
|
||||
word = hextet << 10;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-3]];
|
||||
if (hextet & 0xC0) goto _base64_decode_error;
|
||||
word |= hextet << 4;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-2]];
|
||||
if (hextet & 0xC0) goto _base64_decode_error;
|
||||
word |= hextet >> 2;
|
||||
*d++ = (word & 0xFF00) >> 8;
|
||||
*d++ = (word & 0x00FF);
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len-1]];
|
||||
if (hextet != 64) goto _base64_decode_error;
|
||||
break;
|
||||
case 0:
|
||||
/* nothing to do */
|
||||
break;
|
||||
case 1:
|
||||
/* redo the last quartet, checking for correctness */
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 4]];
|
||||
if (hextet & 0xC0)
|
||||
goto _base64_decode_error;
|
||||
word = hextet << 2;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 3]];
|
||||
if (hextet & 0xC0)
|
||||
goto _base64_decode_error;
|
||||
word |= hextet >> 4;
|
||||
*d++ = word & 0xFF;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 2]];
|
||||
if (hextet != 64)
|
||||
goto _base64_decode_error;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 1]];
|
||||
if (hextet != 64)
|
||||
goto _base64_decode_error;
|
||||
break;
|
||||
case 2:
|
||||
/* redo the last quartet, checking for correctness */
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 4]];
|
||||
if (hextet & 0xC0)
|
||||
goto _base64_decode_error;
|
||||
word = hextet << 10;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 3]];
|
||||
if (hextet & 0xC0)
|
||||
goto _base64_decode_error;
|
||||
word |= hextet << 4;
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 2]];
|
||||
if (hextet & 0xC0)
|
||||
goto _base64_decode_error;
|
||||
word |= hextet >> 2;
|
||||
*d++ = (word & 0xFF00) >> 8;
|
||||
*d++ = (word & 0x00FF);
|
||||
hextet = _base64_invcharmap[(unsigned char)buffer[len - 1]];
|
||||
if (hextet != 64)
|
||||
goto _base64_decode_error;
|
||||
break;
|
||||
}
|
||||
*d = '\0';
|
||||
}
|
||||
@@ -484,8 +499,11 @@ char *xmpp_base64_decode_str(xmpp_ctx_t *ctx, const char *base64, size_t len)
|
||||
*
|
||||
* @ingroup Encodings
|
||||
*/
|
||||
void xmpp_base64_decode_bin(xmpp_ctx_t *ctx, const char *base64, size_t len,
|
||||
unsigned char **out, size_t *outlen)
|
||||
void xmpp_base64_decode_bin(xmpp_ctx_t *ctx,
|
||||
const char *base64,
|
||||
size_t len,
|
||||
unsigned char **out,
|
||||
size_t *outlen)
|
||||
{
|
||||
base64_decode(ctx, base64, len, out, outlen);
|
||||
}
|
||||
|
||||
106
src/ctx.c
106
src/ctx.c
@@ -52,7 +52,7 @@
|
||||
|
||||
/* Workaround for visual studio without va_copy support. */
|
||||
#if defined(_MSC_VER) && _MSC_VER < 1800 || defined(__HAIKU__)
|
||||
#define va_copy(d,s) ((d) = (s))
|
||||
#define va_copy(d, s) ((d) = (s))
|
||||
#endif
|
||||
|
||||
/** Initialize the Strophe library.
|
||||
@@ -61,7 +61,7 @@
|
||||
*
|
||||
* @ingroup Init
|
||||
*/
|
||||
void xmpp_initialize(void)
|
||||
void xmpp_initialize(void)
|
||||
{
|
||||
sock_initialize();
|
||||
resolver_initialize();
|
||||
@@ -113,8 +113,7 @@ void xmpp_shutdown(void)
|
||||
*/
|
||||
int xmpp_version_check(int major, int minor)
|
||||
{
|
||||
return (major == LIBXMPP_VERSION_MAJOR) &&
|
||||
(minor >= LIBXMPP_VERSION_MINOR);
|
||||
return (major == LIBXMPP_VERSION_MAJOR) && (minor >= LIBXMPP_VERSION_MINOR);
|
||||
}
|
||||
|
||||
/* We define the global default allocator, logger, and context here. */
|
||||
@@ -122,17 +121,17 @@ int xmpp_version_check(int major, int minor)
|
||||
/* Wrap stdlib routines malloc, free, and realloc for default memory
|
||||
* management.
|
||||
*/
|
||||
static void *_malloc(const size_t size, void * const userdata)
|
||||
static void *_malloc(const size_t size, void *const userdata)
|
||||
{
|
||||
return malloc(size);
|
||||
}
|
||||
|
||||
static void _free(void *p, void * const userdata)
|
||||
static void _free(void *p, void *const userdata)
|
||||
{
|
||||
free(p);
|
||||
}
|
||||
|
||||
static void *_realloc(void *p, const size_t size, void * const userdata)
|
||||
static void *_realloc(void *p, const size_t size, void *const userdata)
|
||||
{
|
||||
return realloc(p, size);
|
||||
}
|
||||
@@ -140,17 +139,13 @@ static void *_realloc(void *p, const size_t size, void * const userdata)
|
||||
/* default memory function map */
|
||||
static xmpp_mem_t xmpp_default_mem = {
|
||||
_malloc, /* use the thinly wrapped stdlib routines by default */
|
||||
_free,
|
||||
_realloc,
|
||||
NULL
|
||||
};
|
||||
_free, _realloc, NULL};
|
||||
|
||||
/* log levels and names */
|
||||
static const char * const _xmpp_log_level_name[4] = {"DEBUG", "INFO", "WARN", "ERROR"};
|
||||
static const xmpp_log_level_t _xmpp_default_logger_levels[] = {XMPP_LEVEL_DEBUG,
|
||||
XMPP_LEVEL_INFO,
|
||||
XMPP_LEVEL_WARN,
|
||||
XMPP_LEVEL_ERROR};
|
||||
static const char *const _xmpp_log_level_name[4] = {"DEBUG", "INFO", "WARN",
|
||||
"ERROR"};
|
||||
static const xmpp_log_level_t _xmpp_default_logger_levels[] = {
|
||||
XMPP_LEVEL_DEBUG, XMPP_LEVEL_INFO, XMPP_LEVEL_WARN, XMPP_LEVEL_ERROR};
|
||||
|
||||
/** Log a message.
|
||||
* The default logger writes to stderr.
|
||||
@@ -161,22 +156,25 @@ static const xmpp_log_level_t _xmpp_default_logger_levels[] = {XMPP_LEVEL_DEBUG,
|
||||
* @param area the area the log message is for
|
||||
* @param msg the log message
|
||||
*/
|
||||
static void xmpp_default_logger(void * const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const msg)
|
||||
static void xmpp_default_logger(void *const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char *const area,
|
||||
const char *const msg)
|
||||
{
|
||||
xmpp_log_level_t filter_level = * (xmpp_log_level_t*)userdata;
|
||||
xmpp_log_level_t filter_level = *(xmpp_log_level_t *)userdata;
|
||||
if (level >= filter_level)
|
||||
fprintf(stderr, "%s %s %s\n", area, _xmpp_log_level_name[level], msg);
|
||||
}
|
||||
|
||||
static const xmpp_log_t _xmpp_default_loggers[] = {
|
||||
{&xmpp_default_logger, (void*)&_xmpp_default_logger_levels[XMPP_LEVEL_DEBUG]},
|
||||
{&xmpp_default_logger, (void*)&_xmpp_default_logger_levels[XMPP_LEVEL_INFO]},
|
||||
{&xmpp_default_logger, (void*)&_xmpp_default_logger_levels[XMPP_LEVEL_WARN]},
|
||||
{&xmpp_default_logger, (void*)&_xmpp_default_logger_levels[XMPP_LEVEL_ERROR]}
|
||||
};
|
||||
{&xmpp_default_logger,
|
||||
(void *)&_xmpp_default_logger_levels[XMPP_LEVEL_DEBUG]},
|
||||
{&xmpp_default_logger,
|
||||
(void *)&_xmpp_default_logger_levels[XMPP_LEVEL_INFO]},
|
||||
{&xmpp_default_logger,
|
||||
(void *)&_xmpp_default_logger_levels[XMPP_LEVEL_WARN]},
|
||||
{&xmpp_default_logger,
|
||||
(void *)&_xmpp_default_logger_levels[XMPP_LEVEL_ERROR]}};
|
||||
|
||||
/** Get a default logger with filtering.
|
||||
* The default logger provides a basic logging setup which writes log
|
||||
@@ -192,12 +190,13 @@ static const xmpp_log_t _xmpp_default_loggers[] = {
|
||||
xmpp_log_t *xmpp_get_default_logger(xmpp_log_level_t level)
|
||||
{
|
||||
/* clamp to the known range */
|
||||
if (level > XMPP_LEVEL_ERROR) level = XMPP_LEVEL_ERROR;
|
||||
if (level > XMPP_LEVEL_ERROR)
|
||||
level = XMPP_LEVEL_ERROR;
|
||||
|
||||
return (xmpp_log_t*)&_xmpp_default_loggers[level];
|
||||
return (xmpp_log_t *)&_xmpp_default_loggers[level];
|
||||
}
|
||||
|
||||
static xmpp_log_t xmpp_default_log = { NULL, NULL };
|
||||
static xmpp_log_t xmpp_default_log = {NULL, NULL};
|
||||
|
||||
/* convenience functions for accessing the context */
|
||||
|
||||
@@ -209,7 +208,7 @@ static xmpp_log_t xmpp_default_log = { NULL, NULL };
|
||||
*
|
||||
* @return a pointer to the allocated memory or NULL on an error
|
||||
*/
|
||||
void *xmpp_alloc(const xmpp_ctx_t * const ctx, const size_t size)
|
||||
void *xmpp_alloc(const xmpp_ctx_t *const ctx, const size_t size)
|
||||
{
|
||||
return ctx->mem->alloc(size, ctx->mem->userdata);
|
||||
}
|
||||
@@ -220,7 +219,7 @@ void *xmpp_alloc(const xmpp_ctx_t * const ctx, const size_t size)
|
||||
* @param ctx a Strophe context object
|
||||
* @param p a pointer referencing memory to be freed
|
||||
*/
|
||||
void xmpp_free(const xmpp_ctx_t * const ctx, void *p)
|
||||
void xmpp_free(const xmpp_ctx_t *const ctx, void *p)
|
||||
{
|
||||
ctx->mem->free(p, ctx->mem->userdata);
|
||||
}
|
||||
@@ -234,8 +233,7 @@ void xmpp_free(const xmpp_ctx_t * const ctx, void *p)
|
||||
*
|
||||
* @return a pointer to the reallocated memory or NULL on an error
|
||||
*/
|
||||
void *xmpp_realloc(const xmpp_ctx_t * const ctx, void *p,
|
||||
const size_t size)
|
||||
void *xmpp_realloc(const xmpp_ctx_t *const ctx, void *p, const size_t size)
|
||||
{
|
||||
return ctx->mem->realloc(p, size, ctx->mem->userdata);
|
||||
}
|
||||
@@ -253,10 +251,10 @@ void *xmpp_realloc(const xmpp_ctx_t * const ctx, void *p,
|
||||
* @param fmt a printf-style format string for the message
|
||||
* @param ap variable argument list supplied for the format string
|
||||
*/
|
||||
void xmpp_log(const xmpp_ctx_t * const ctx,
|
||||
void xmpp_log(const xmpp_ctx_t *const ctx,
|
||||
const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
va_list ap)
|
||||
{
|
||||
int oldret, ret;
|
||||
@@ -304,9 +302,9 @@ void xmpp_log(const xmpp_ctx_t * const ctx,
|
||||
* @param fmt a printf-style format string followed by a variable list of
|
||||
* arguments to format
|
||||
*/
|
||||
void xmpp_error(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
void xmpp_error(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...)
|
||||
{
|
||||
va_list ap;
|
||||
@@ -326,10 +324,10 @@ void xmpp_error(const xmpp_ctx_t * const ctx,
|
||||
* @param fmt a printf-style format string followed by a variable list of
|
||||
* arguments to format
|
||||
*/
|
||||
void xmpp_warn(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
...)
|
||||
void xmpp_warn(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...)
|
||||
{
|
||||
va_list ap;
|
||||
|
||||
@@ -348,10 +346,10 @@ void xmpp_warn(const xmpp_ctx_t * const ctx,
|
||||
* @param fmt a printf-style format string followed by a variable list of
|
||||
* arguments to format
|
||||
*/
|
||||
void xmpp_info(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
...)
|
||||
void xmpp_info(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...)
|
||||
{
|
||||
va_list ap;
|
||||
|
||||
@@ -370,9 +368,9 @@ void xmpp_info(const xmpp_ctx_t * const ctx,
|
||||
* @param fmt a printf-style format string followed by a variable list of
|
||||
* arguments to format
|
||||
*/
|
||||
void xmpp_debug(const xmpp_ctx_t * const ctx,
|
||||
const char * const area,
|
||||
const char * const fmt,
|
||||
void xmpp_debug(const xmpp_ctx_t *const ctx,
|
||||
const char *const area,
|
||||
const char *const fmt,
|
||||
...)
|
||||
{
|
||||
va_list ap;
|
||||
@@ -396,8 +394,8 @@ void xmpp_debug(const xmpp_ctx_t * const ctx,
|
||||
*
|
||||
* @ingroup Context
|
||||
*/
|
||||
xmpp_ctx_t *xmpp_ctx_new(const xmpp_mem_t * const mem,
|
||||
const xmpp_log_t * const log)
|
||||
xmpp_ctx_t *xmpp_ctx_new(const xmpp_mem_t *const mem,
|
||||
const xmpp_log_t *const log)
|
||||
{
|
||||
xmpp_ctx_t *ctx = NULL;
|
||||
|
||||
@@ -436,7 +434,7 @@ xmpp_ctx_t *xmpp_ctx_new(const xmpp_mem_t * const mem,
|
||||
*
|
||||
* @ingroup Context
|
||||
*/
|
||||
void xmpp_ctx_free(xmpp_ctx_t * const ctx)
|
||||
void xmpp_ctx_free(xmpp_ctx_t *const ctx)
|
||||
{
|
||||
/* mem and log are owned by their suppliers */
|
||||
xmpp_rand_free(ctx, ctx->rand);
|
||||
@@ -450,7 +448,7 @@ void xmpp_ctx_free(xmpp_ctx_t * const ctx)
|
||||
*
|
||||
* @ingroup Context
|
||||
*/
|
||||
void xmpp_ctx_set_timeout(xmpp_ctx_t * const ctx, const unsigned long timeout)
|
||||
void xmpp_ctx_set_timeout(xmpp_ctx_t *const ctx, const unsigned long timeout)
|
||||
{
|
||||
ctx->timeout = timeout;
|
||||
}
|
||||
|
||||
33
src/event.c
33
src/event.c
@@ -38,7 +38,7 @@
|
||||
#include <sys/select.h>
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#define _sleep(x) usleep((x) * 1000)
|
||||
#define _sleep(x) usleep((x)*1000)
|
||||
#else
|
||||
#include <winsock2.h>
|
||||
#ifndef ETIMEDOUT
|
||||
@@ -88,7 +88,8 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
uint64_t usec;
|
||||
int tls_read_bytes = 0;
|
||||
|
||||
if (ctx->loop_status == XMPP_LOOP_QUIT) return;
|
||||
if (ctx->loop_status == XMPP_LOOP_QUIT)
|
||||
return;
|
||||
|
||||
/* send queued data */
|
||||
connitem = ctx->connlist;
|
||||
@@ -141,7 +142,8 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
/* pop the top item */
|
||||
conn->send_queue_head = sq;
|
||||
/* if we've sent everything update the tail */
|
||||
if (!sq) conn->send_queue_tail = NULL;
|
||||
if (!sq)
|
||||
conn->send_queue_tail = NULL;
|
||||
}
|
||||
|
||||
/* tear down connection on error */
|
||||
@@ -162,7 +164,6 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
conn_parser_reset(connitem->conn);
|
||||
}
|
||||
|
||||
|
||||
/* fire any ready timed handlers, then make sure we don't wait past
|
||||
the time when timed handlers need to be called */
|
||||
next = handler_fire_timed(ctx);
|
||||
@@ -217,7 +218,7 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
|
||||
/* check for events */
|
||||
if (max > 0)
|
||||
ret = select(max + 1, &rfds, &wfds, NULL, &tv);
|
||||
ret = select(max + 1, &rfds, &wfds, NULL, &tv);
|
||||
else {
|
||||
if (timeout > 0)
|
||||
_sleep(timeout);
|
||||
@@ -233,7 +234,8 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
}
|
||||
|
||||
/* no events happened */
|
||||
if (ret == 0 && tls_read_bytes == 0) return;
|
||||
if (ret == 0 && tls_read_bytes == 0)
|
||||
return;
|
||||
|
||||
/* process events */
|
||||
connitem = ctx->connlist;
|
||||
@@ -261,29 +263,35 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
|
||||
break;
|
||||
case XMPP_STATE_CONNECTED:
|
||||
if (FD_ISSET(conn->sock, &rfds) || (conn->tls && tls_pending(conn->tls))) {
|
||||
if (FD_ISSET(conn->sock, &rfds) ||
|
||||
(conn->tls && tls_pending(conn->tls))) {
|
||||
if (conn->tls) {
|
||||
ret = tls_read(conn->tls, buf, STROPE_MESSAGE_BUFFER_SIZE);
|
||||
} else {
|
||||
ret = sock_read(conn->sock, buf, STROPE_MESSAGE_BUFFER_SIZE);
|
||||
ret =
|
||||
sock_read(conn->sock, buf, STROPE_MESSAGE_BUFFER_SIZE);
|
||||
}
|
||||
|
||||
if (ret > 0) {
|
||||
ret = parser_feed(conn->parser, buf, ret);
|
||||
if (!ret) {
|
||||
xmpp_debug(ctx, "xmpp", "parse error [%s]", buf);
|
||||
xmpp_send_error(conn, XMPP_SE_INVALID_XML, "parse error");
|
||||
xmpp_send_error(conn, XMPP_SE_INVALID_XML,
|
||||
"parse error");
|
||||
}
|
||||
} else {
|
||||
if (conn->tls) {
|
||||
if (!tls_is_recoverable(tls_error(conn->tls))) {
|
||||
xmpp_debug(ctx, "xmpp", "Unrecoverable TLS error, %d.", tls_error(conn->tls));
|
||||
xmpp_debug(ctx, "xmpp",
|
||||
"Unrecoverable TLS error, %d.",
|
||||
tls_error(conn->tls));
|
||||
conn->error = tls_error(conn->tls);
|
||||
conn_disconnect(conn);
|
||||
}
|
||||
} else {
|
||||
/* return of 0 means socket closed by server */
|
||||
xmpp_debug(ctx, "xmpp", "Socket closed by remote host.");
|
||||
xmpp_debug(ctx, "xmpp",
|
||||
"Socket closed by remote host.");
|
||||
conn->error = ECONNRESET;
|
||||
conn_disconnect(conn);
|
||||
}
|
||||
@@ -314,7 +322,8 @@ void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout)
|
||||
*/
|
||||
void xmpp_run(xmpp_ctx_t *ctx)
|
||||
{
|
||||
if (ctx->loop_status != XMPP_LOOP_NOTSTARTED) return;
|
||||
if (ctx->loop_status != XMPP_LOOP_NOTSTARTED)
|
||||
return;
|
||||
|
||||
ctx->loop_status = XMPP_LOOP_RUNNING;
|
||||
while (ctx->loop_status == XMPP_LOOP_RUNNING) {
|
||||
|
||||
155
src/handler.c
155
src/handler.c
@@ -33,8 +33,7 @@
|
||||
* TODO Convert handler lists to double-linked lists. Current implementation
|
||||
* works for O(n).
|
||||
*/
|
||||
static void _handler_item_remove(xmpp_handlist_t **head,
|
||||
xmpp_handlist_t *item)
|
||||
static void _handler_item_remove(xmpp_handlist_t **head, xmpp_handlist_t *item)
|
||||
{
|
||||
xmpp_handlist_t *i = *head;
|
||||
|
||||
@@ -56,8 +55,7 @@ static void _handler_item_remove(xmpp_handlist_t **head,
|
||||
* @param conn a Strophe connection object
|
||||
* @param stanza a Strophe stanza object
|
||||
*/
|
||||
void handler_fire_stanza(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza)
|
||||
void handler_fire_stanza(xmpp_conn_t *const conn, xmpp_stanza_t *const stanza)
|
||||
{
|
||||
xmpp_handlist_t *item, *next, *head, *head_old;
|
||||
const char *id, *ns, *name, *type;
|
||||
@@ -75,7 +73,8 @@ void handler_fire_stanza(xmpp_conn_t * const conn,
|
||||
while (item) {
|
||||
/* don't fire user handlers until authentication succeeds and
|
||||
and skip newly added handlers */
|
||||
if ((item->user_handler && !conn->authenticated) || !item->enabled) {
|
||||
if ((item->user_handler && !conn->authenticated) ||
|
||||
!item->enabled) {
|
||||
item = item->next;
|
||||
continue;
|
||||
}
|
||||
@@ -127,9 +126,12 @@ void handler_fire_stanza(xmpp_conn_t * const conn,
|
||||
if (!ret) {
|
||||
/* handler is one-shot, so delete it */
|
||||
_handler_item_remove(&conn->handlers, item);
|
||||
if (item->u.ns) xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name) xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type) xmpp_free(conn->ctx, item->u.type);
|
||||
if (item->u.ns)
|
||||
xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name)
|
||||
xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type)
|
||||
xmpp_free(conn->ctx, item->u.type);
|
||||
xmpp_free(conn->ctx, item);
|
||||
}
|
||||
}
|
||||
@@ -144,7 +146,7 @@ void handler_fire_stanza(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @return the time in milliseconds until the next handler will be ready
|
||||
*/
|
||||
uint64_t handler_fire_timed(xmpp_ctx_t * const ctx)
|
||||
uint64_t handler_fire_timed(xmpp_ctx_t *const ctx)
|
||||
{
|
||||
xmpp_connlist_t *connitem;
|
||||
xmpp_handlist_t *item, *next;
|
||||
@@ -171,7 +173,8 @@ uint64_t handler_fire_timed(xmpp_ctx_t * const ctx)
|
||||
while (item) {
|
||||
/* don't fire user handlers until authentication succeeds and
|
||||
skip newly added handlers */
|
||||
if ((item->user_handler && !conn->authenticated) || !item->enabled) {
|
||||
if ((item->user_handler && !conn->authenticated) ||
|
||||
!item->enabled) {
|
||||
item = item->next;
|
||||
continue;
|
||||
}
|
||||
@@ -221,10 +224,10 @@ void handler_reset_timed(xmpp_conn_t *conn, int user_only)
|
||||
}
|
||||
}
|
||||
|
||||
static void _timed_handler_add(xmpp_conn_t * const conn,
|
||||
static void _timed_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void * const userdata,
|
||||
void *const userdata,
|
||||
const int user_handler)
|
||||
{
|
||||
xmpp_handlist_t *item, *tail;
|
||||
@@ -236,11 +239,13 @@ static void _timed_handler_add(xmpp_conn_t * const conn,
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (item) return;
|
||||
if (item)
|
||||
return;
|
||||
|
||||
/* build new item */
|
||||
item = xmpp_alloc(conn->ctx, sizeof(xmpp_handlist_t));
|
||||
if (!item) return;
|
||||
if (!item)
|
||||
return;
|
||||
|
||||
item->user_handler = user_handler;
|
||||
item->handler = handler;
|
||||
@@ -269,12 +274,13 @@ static void _timed_handler_add(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_timed_handler_delete(xmpp_conn_t * const conn,
|
||||
void xmpp_timed_handler_delete(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler)
|
||||
{
|
||||
xmpp_handlist_t *item, *prev;
|
||||
|
||||
if (!conn->timed_handlers) return;
|
||||
if (!conn->timed_handlers)
|
||||
return;
|
||||
|
||||
prev = NULL;
|
||||
item = conn->timed_handlers;
|
||||
@@ -294,10 +300,11 @@ void xmpp_timed_handler_delete(xmpp_conn_t * const conn,
|
||||
}
|
||||
}
|
||||
|
||||
static void _id_handler_add(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata, int user_handler)
|
||||
static void _id_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char *const id,
|
||||
void *const userdata,
|
||||
int user_handler)
|
||||
{
|
||||
xmpp_handlist_t *item, *tail;
|
||||
|
||||
@@ -310,11 +317,13 @@ static void _id_handler_add(xmpp_conn_t * const conn,
|
||||
}
|
||||
item = item->next;
|
||||
}
|
||||
if (item) return;
|
||||
if (item)
|
||||
return;
|
||||
|
||||
/* build new item */
|
||||
item = xmpp_alloc(conn->ctx, sizeof(xmpp_handlist_t));
|
||||
if (!item) return;
|
||||
if (!item)
|
||||
return;
|
||||
|
||||
item->user_handler = user_handler;
|
||||
item->handler = handler;
|
||||
@@ -347,15 +356,16 @@ static void _id_handler_add(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_id_handler_delete(xmpp_conn_t * const conn,
|
||||
void xmpp_id_handler_delete(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id)
|
||||
const char *const id)
|
||||
{
|
||||
xmpp_handlist_t *item, *prev, *next;
|
||||
|
||||
prev = NULL;
|
||||
item = (xmpp_handlist_t *)hash_get(conn->id_handlers, id);
|
||||
if (!item) return;
|
||||
if (!item)
|
||||
return;
|
||||
|
||||
while (item) {
|
||||
next = item->next;
|
||||
@@ -379,12 +389,13 @@ void xmpp_id_handler_delete(xmpp_conn_t * const conn,
|
||||
}
|
||||
|
||||
/* add a stanza handler */
|
||||
static void _handler_add(xmpp_conn_t * const conn,
|
||||
static void _handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata, int user_handler)
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata,
|
||||
int user_handler)
|
||||
{
|
||||
xmpp_handlist_t *item, *tail;
|
||||
|
||||
@@ -397,11 +408,13 @@ static void _handler_add(xmpp_conn_t * const conn,
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (item) return;
|
||||
if (item)
|
||||
return;
|
||||
|
||||
/* build new item */
|
||||
item = (xmpp_handlist_t *)xmpp_alloc(conn->ctx, sizeof(xmpp_handlist_t));
|
||||
if (!item) return;
|
||||
if (!item)
|
||||
return;
|
||||
|
||||
item->user_handler = user_handler;
|
||||
item->handler = handler;
|
||||
@@ -417,20 +430,25 @@ static void _handler_add(xmpp_conn_t * const conn,
|
||||
}
|
||||
} else
|
||||
item->u.ns = NULL;
|
||||
|
||||
if (name) {
|
||||
item->u.name = xmpp_strdup(conn->ctx, name);
|
||||
if (!item->u.name) {
|
||||
if (item->u.ns) xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.ns)
|
||||
xmpp_free(conn->ctx, item->u.ns);
|
||||
xmpp_free(conn->ctx, item);
|
||||
return;
|
||||
}
|
||||
} else
|
||||
item->u.name = NULL;
|
||||
|
||||
if (type) {
|
||||
item->u.type = xmpp_strdup(conn->ctx, type);
|
||||
if (!item->u.type) {
|
||||
if (item->u.ns) xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name) xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.ns)
|
||||
xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name)
|
||||
xmpp_free(conn->ctx, item->u.name);
|
||||
xmpp_free(conn->ctx, item);
|
||||
}
|
||||
} else
|
||||
@@ -454,12 +472,12 @@ static void _handler_add(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_handler_delete(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler)
|
||||
void xmpp_handler_delete(xmpp_conn_t *const conn, xmpp_handler handler)
|
||||
{
|
||||
xmpp_handlist_t *prev, *item;
|
||||
|
||||
if (!conn->handlers) return;
|
||||
if (!conn->handlers)
|
||||
return;
|
||||
|
||||
prev = NULL;
|
||||
item = conn->handlers;
|
||||
@@ -470,9 +488,12 @@ void xmpp_handler_delete(xmpp_conn_t * const conn,
|
||||
else
|
||||
conn->handlers = item->next;
|
||||
|
||||
if (item->u.ns) xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name) xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type) xmpp_free(conn->ctx, item->u.type);
|
||||
if (item->u.ns)
|
||||
xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name)
|
||||
xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type)
|
||||
xmpp_free(conn->ctx, item->u.type);
|
||||
xmpp_free(conn->ctx, item);
|
||||
item = prev ? prev->next : conn->handlers;
|
||||
} else {
|
||||
@@ -498,10 +519,10 @@ void xmpp_handler_delete(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_timed_handler_add(xmpp_conn_t * const conn,
|
||||
void xmpp_timed_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void * const userdata)
|
||||
void *const userdata)
|
||||
{
|
||||
_timed_handler_add(conn, handler, period, userdata, 1);
|
||||
}
|
||||
@@ -515,10 +536,10 @@ void xmpp_timed_handler_add(xmpp_conn_t * const conn,
|
||||
* @param period the time in milliseconds between firings
|
||||
* @param userdata an opaque data pointer that will be passed to the handler
|
||||
*/
|
||||
void handler_add_timed(xmpp_conn_t * const conn,
|
||||
void handler_add_timed(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void * const userdata)
|
||||
void *const userdata)
|
||||
{
|
||||
_timed_handler_add(conn, handler, period, userdata, 0);
|
||||
}
|
||||
@@ -539,10 +560,10 @@ void handler_add_timed(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_id_handler_add(xmpp_conn_t * const conn,
|
||||
void xmpp_id_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata)
|
||||
const char *const id,
|
||||
void *const userdata)
|
||||
{
|
||||
_id_handler_add(conn, handler, id, userdata, 1);
|
||||
}
|
||||
@@ -556,10 +577,10 @@ void xmpp_id_handler_add(xmpp_conn_t * const conn,
|
||||
* @param id a string with the id
|
||||
* @param userdata an opaque data pointer that will be passed to the handler
|
||||
*/
|
||||
void handler_add_id(xmpp_conn_t * const conn,
|
||||
void handler_add_id(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata)
|
||||
const char *const id,
|
||||
void *const userdata)
|
||||
{
|
||||
_id_handler_add(conn, handler, id, userdata, 0);
|
||||
}
|
||||
@@ -586,12 +607,12 @@ void handler_add_id(xmpp_conn_t * const conn,
|
||||
*
|
||||
* @ingroup Handlers
|
||||
*/
|
||||
void xmpp_handler_add(xmpp_conn_t * const conn,
|
||||
void xmpp_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata)
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata)
|
||||
{
|
||||
_handler_add(conn, handler, ns, name, type, userdata, 1);
|
||||
}
|
||||
@@ -607,12 +628,12 @@ void xmpp_handler_add(xmpp_conn_t * const conn,
|
||||
* @param type a string with the 'type' attribute value to match
|
||||
* @param userdata an opaque data pointer that will be passed to the handler
|
||||
*/
|
||||
void handler_add(xmpp_conn_t * const conn,
|
||||
void handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata)
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata)
|
||||
{
|
||||
_handler_add(conn, handler, ns, name, type, userdata, 0);
|
||||
}
|
||||
@@ -636,9 +657,12 @@ void handler_system_delete_all(xmpp_conn_t *conn)
|
||||
if (!item->user_handler) {
|
||||
next = item->next;
|
||||
_handler_item_remove(&conn->handlers, item);
|
||||
if (item->u.ns) xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name) xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type) xmpp_free(conn->ctx, item->u.type);
|
||||
if (item->u.ns)
|
||||
xmpp_free(conn->ctx, item->u.ns);
|
||||
if (item->u.name)
|
||||
xmpp_free(conn->ctx, item->u.name);
|
||||
if (item->u.type)
|
||||
xmpp_free(conn->ctx, item->u.type);
|
||||
xmpp_free(conn->ctx, item);
|
||||
item = next;
|
||||
} else
|
||||
@@ -686,5 +710,6 @@ void handler_system_delete_all(xmpp_conn_t *conn)
|
||||
xmpp_free(conn->ctx, key2);
|
||||
}
|
||||
}
|
||||
if (iter) hash_iter_release(iter);
|
||||
if (iter)
|
||||
hash_iter_release(iter);
|
||||
}
|
||||
|
||||
257
src/hash.c
257
src/hash.c
@@ -46,171 +46,176 @@ struct _hash_iterator_t {
|
||||
};
|
||||
|
||||
/** allocate and initialize a new hash table */
|
||||
hash_t *hash_new(xmpp_ctx_t * const ctx, const int size,
|
||||
hash_free_func free_func)
|
||||
hash_t *
|
||||
hash_new(xmpp_ctx_t *const ctx, const int size, hash_free_func free_func)
|
||||
{
|
||||
hash_t *result = NULL;
|
||||
|
||||
result = xmpp_alloc(ctx, sizeof(hash_t));
|
||||
if (result != NULL) {
|
||||
result->entries = xmpp_alloc(ctx, size * sizeof(hashentry_t *));
|
||||
if (result->entries == NULL) {
|
||||
xmpp_free(ctx, result);
|
||||
return NULL;
|
||||
}
|
||||
memset(result->entries, 0, size * sizeof(hashentry_t *));
|
||||
result->length = size;
|
||||
result->entries = xmpp_alloc(ctx, size * sizeof(hashentry_t *));
|
||||
if (result->entries == NULL) {
|
||||
xmpp_free(ctx, result);
|
||||
return NULL;
|
||||
}
|
||||
memset(result->entries, 0, size * sizeof(hashentry_t *));
|
||||
result->length = size;
|
||||
|
||||
result->ctx = ctx;
|
||||
result->free = free_func;
|
||||
result->num_keys = 0;
|
||||
/* give the caller a reference */
|
||||
result->ref = 1;
|
||||
result->ctx = ctx;
|
||||
result->free = free_func;
|
||||
result->num_keys = 0;
|
||||
/* give the caller a reference */
|
||||
result->ref = 1;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/** obtain a new reference to an existing hash table */
|
||||
hash_t *hash_clone(hash_t * const table)
|
||||
hash_t *hash_clone(hash_t *const table)
|
||||
{
|
||||
table->ref++;
|
||||
return table;
|
||||
}
|
||||
|
||||
/** release a hash table that is no longer needed */
|
||||
void hash_release(hash_t * const table)
|
||||
void hash_release(hash_t *const table)
|
||||
{
|
||||
xmpp_ctx_t *ctx = table->ctx;
|
||||
hashentry_t *entry, *next;
|
||||
int i;
|
||||
|
||||
if (table->ref > 1)
|
||||
table->ref--;
|
||||
table->ref--;
|
||||
else {
|
||||
for (i = 0; i < table->length; i++) {
|
||||
entry = table->entries[i];
|
||||
while (entry != NULL) {
|
||||
next = entry->next;
|
||||
xmpp_free(ctx, entry->key);
|
||||
if (table->free) table->free(ctx, entry->value);
|
||||
xmpp_free(ctx, entry);
|
||||
entry = next;
|
||||
}
|
||||
}
|
||||
xmpp_free(ctx, table->entries);
|
||||
xmpp_free(ctx, table);
|
||||
for (i = 0; i < table->length; i++) {
|
||||
entry = table->entries[i];
|
||||
while (entry != NULL) {
|
||||
next = entry->next;
|
||||
xmpp_free(ctx, entry->key);
|
||||
if (table->free)
|
||||
table->free(ctx, entry->value);
|
||||
xmpp_free(ctx, entry);
|
||||
entry = next;
|
||||
}
|
||||
}
|
||||
xmpp_free(ctx, table->entries);
|
||||
xmpp_free(ctx, table);
|
||||
}
|
||||
}
|
||||
|
||||
/** hash a key for our table lookup */
|
||||
static int _hash_key(hash_t *table, const char *key)
|
||||
{
|
||||
unsigned hash = 0;
|
||||
unsigned shift = 0;
|
||||
const unsigned char *c = (const unsigned char *)key;
|
||||
unsigned hash = 0;
|
||||
unsigned shift = 0;
|
||||
const unsigned char *c = (const unsigned char *)key;
|
||||
|
||||
while (*c != 0) {
|
||||
/* assume 32 bit ints */
|
||||
hash ^= ((unsigned)*c++ << shift);
|
||||
shift += 8;
|
||||
if (shift > 24) shift = 0;
|
||||
}
|
||||
return hash % (unsigned)table->length;
|
||||
while (*c != 0) {
|
||||
/* assume 32 bit ints */
|
||||
hash ^= ((unsigned)*c++ << shift);
|
||||
shift += 8;
|
||||
if (shift > 24)
|
||||
shift = 0;
|
||||
}
|
||||
return hash % (unsigned)table->length;
|
||||
}
|
||||
|
||||
hashentry_t *_hash_entry_find(hash_t *table, const char *key)
|
||||
{
|
||||
hashentry_t *entry;
|
||||
int table_index = _hash_key(table, key);
|
||||
hashentry_t *entry;
|
||||
int table_index = _hash_key(table, key);
|
||||
|
||||
/* look up the hash entry */
|
||||
entry = table->entries[table_index];
|
||||
while (entry != NULL) {
|
||||
/* traverse the linked list looking for the key */
|
||||
if (!strcmp(key, entry->key)) {
|
||||
/* match */
|
||||
break;
|
||||
}
|
||||
entry = entry->next;
|
||||
}
|
||||
return entry;
|
||||
/* look up the hash entry */
|
||||
entry = table->entries[table_index];
|
||||
while (entry != NULL) {
|
||||
/* traverse the linked list looking for the key */
|
||||
if (!strcmp(key, entry->key)) {
|
||||
/* match */
|
||||
break;
|
||||
}
|
||||
entry = entry->next;
|
||||
}
|
||||
return entry;
|
||||
}
|
||||
|
||||
/** add a key, value pair to a hash table.
|
||||
* each key can appear only once; the value of any
|
||||
* identical key will be replaced
|
||||
*/
|
||||
int hash_add(hash_t *table, const char * const key, void *data)
|
||||
int hash_add(hash_t *table, const char *const key, void *data)
|
||||
{
|
||||
xmpp_ctx_t *ctx = table->ctx;
|
||||
hashentry_t *entry = NULL;
|
||||
int table_index = _hash_key(table, key);
|
||||
xmpp_ctx_t *ctx = table->ctx;
|
||||
hashentry_t *entry = NULL;
|
||||
int table_index = _hash_key(table, key);
|
||||
|
||||
/* find and replace existing entry, if any */
|
||||
entry = _hash_entry_find(table, key);
|
||||
/* find and replace existing entry, if any */
|
||||
entry = _hash_entry_find(table, key);
|
||||
|
||||
if (entry == NULL) {
|
||||
/* allocate and fill a new entry */
|
||||
entry = xmpp_alloc(ctx, sizeof(hashentry_t));
|
||||
if (!entry) return -1;
|
||||
entry->key = xmpp_strdup(ctx, key);
|
||||
if (!entry->key) {
|
||||
xmpp_free(ctx, entry);
|
||||
return -1;
|
||||
}
|
||||
/* insert ourselves in the linked list */
|
||||
entry->next = table->entries[table_index];
|
||||
table->entries[table_index] = entry;
|
||||
table->num_keys++;
|
||||
} else {
|
||||
if (table->free) table->free(ctx, entry->value);
|
||||
}
|
||||
if (entry == NULL) {
|
||||
/* allocate and fill a new entry */
|
||||
entry = xmpp_alloc(ctx, sizeof(hashentry_t));
|
||||
if (!entry)
|
||||
return -1;
|
||||
entry->key = xmpp_strdup(ctx, key);
|
||||
if (!entry->key) {
|
||||
xmpp_free(ctx, entry);
|
||||
return -1;
|
||||
}
|
||||
/* insert ourselves in the linked list */
|
||||
entry->next = table->entries[table_index];
|
||||
table->entries[table_index] = entry;
|
||||
table->num_keys++;
|
||||
} else {
|
||||
if (table->free)
|
||||
table->free(ctx, entry->value);
|
||||
}
|
||||
|
||||
entry->value = data;
|
||||
entry->value = data;
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** look up a key in a hash table */
|
||||
void *hash_get(hash_t *table, const char *key)
|
||||
{
|
||||
hashentry_t *entry;
|
||||
hashentry_t *entry;
|
||||
|
||||
entry = _hash_entry_find(table, key);
|
||||
return entry == NULL ? NULL : entry->value;
|
||||
entry = _hash_entry_find(table, key);
|
||||
return entry == NULL ? NULL : entry->value;
|
||||
}
|
||||
|
||||
/** delete a key from a hash table */
|
||||
int hash_drop(hash_t *table, const char *key)
|
||||
{
|
||||
xmpp_ctx_t *ctx = table->ctx;
|
||||
hashentry_t *entry, *prev;
|
||||
int table_index = _hash_key(table, key);
|
||||
xmpp_ctx_t *ctx = table->ctx;
|
||||
hashentry_t *entry, *prev;
|
||||
int table_index = _hash_key(table, key);
|
||||
|
||||
/* look up the hash entry */
|
||||
entry = table->entries[table_index];
|
||||
prev = NULL;
|
||||
while (entry != NULL) {
|
||||
/* traverse the linked list looking for the key */
|
||||
if (!strcmp(key, entry->key)) {
|
||||
/* match, remove the entry */
|
||||
xmpp_free(ctx, entry->key);
|
||||
if (table->free) table->free(ctx, entry->value);
|
||||
if (prev == NULL) {
|
||||
table->entries[table_index] = entry->next;
|
||||
} else {
|
||||
prev->next = entry->next;
|
||||
}
|
||||
xmpp_free(ctx, entry);
|
||||
table->num_keys--;
|
||||
return 0;
|
||||
}
|
||||
prev = entry;
|
||||
entry = entry->next;
|
||||
}
|
||||
/* no match */
|
||||
return -1;
|
||||
/* look up the hash entry */
|
||||
entry = table->entries[table_index];
|
||||
prev = NULL;
|
||||
while (entry != NULL) {
|
||||
/* traverse the linked list looking for the key */
|
||||
if (!strcmp(key, entry->key)) {
|
||||
/* match, remove the entry */
|
||||
xmpp_free(ctx, entry->key);
|
||||
if (table->free)
|
||||
table->free(ctx, entry->value);
|
||||
if (prev == NULL) {
|
||||
table->entries[table_index] = entry->next;
|
||||
} else {
|
||||
prev->next = entry->next;
|
||||
}
|
||||
xmpp_free(ctx, entry);
|
||||
table->num_keys--;
|
||||
return 0;
|
||||
}
|
||||
prev = entry;
|
||||
entry = entry->next;
|
||||
}
|
||||
/* no match */
|
||||
return -1;
|
||||
}
|
||||
|
||||
int hash_num_keys(hash_t *table)
|
||||
@@ -226,16 +231,15 @@ hash_iterator_t *hash_iter_new(hash_t *table)
|
||||
|
||||
iter = xmpp_alloc(ctx, sizeof(*iter));
|
||||
if (iter != NULL) {
|
||||
iter->ref = 1;
|
||||
iter->table = hash_clone(table);
|
||||
iter->entry = NULL;
|
||||
iter->index = -1;
|
||||
iter->ref = 1;
|
||||
iter->table = hash_clone(table);
|
||||
iter->entry = NULL;
|
||||
iter->index = -1;
|
||||
}
|
||||
|
||||
return iter;
|
||||
}
|
||||
|
||||
|
||||
/** release an iterator that is no longer needed */
|
||||
void hash_iter_release(hash_iterator_t *iter)
|
||||
{
|
||||
@@ -244,37 +248,38 @@ void hash_iter_release(hash_iterator_t *iter)
|
||||
iter->ref--;
|
||||
|
||||
if (iter->ref == 0) { // ref is unsigned!!!
|
||||
hash_release(iter->table);
|
||||
xmpp_free(ctx, iter);
|
||||
hash_release(iter->table);
|
||||
xmpp_free(ctx, iter);
|
||||
}
|
||||
}
|
||||
|
||||
/** return the next hash table key from the iterator.
|
||||
the returned key should not be freed */
|
||||
const char * hash_iter_next(hash_iterator_t *iter)
|
||||
const char *hash_iter_next(hash_iterator_t *iter)
|
||||
{
|
||||
hash_t *table = iter->table;
|
||||
hashentry_t *entry = iter->entry;
|
||||
int i;
|
||||
|
||||
/* advance until we find the next entry */
|
||||
if (entry != NULL) entry = entry->next;
|
||||
if (entry != NULL)
|
||||
entry = entry->next;
|
||||
if (entry == NULL) {
|
||||
/* we're off the end of list, search for a new entry */
|
||||
i = iter->index + 1;
|
||||
while (i < iter->table->length) {
|
||||
entry = table->entries[i];
|
||||
if (entry != NULL) {
|
||||
iter->index = i;
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
/* we're off the end of list, search for a new entry */
|
||||
i = iter->index + 1;
|
||||
while (i < iter->table->length) {
|
||||
entry = table->entries[i];
|
||||
if (entry != NULL) {
|
||||
iter->index = i;
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
if (entry == NULL) {
|
||||
/* no more keys! */
|
||||
return NULL;
|
||||
/* no more keys! */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* remember our current match */
|
||||
|
||||
18
src/hash.h
18
src/hash.h
@@ -1,7 +1,7 @@
|
||||
/* hash.h
|
||||
** strophe XMPP client library -- hash table interface
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
@@ -18,23 +18,23 @@
|
||||
|
||||
typedef struct _hash_t hash_t;
|
||||
|
||||
typedef void (*hash_free_func)(const xmpp_ctx_t * const ctx, void *p);
|
||||
typedef void (*hash_free_func)(const xmpp_ctx_t *const ctx, void *p);
|
||||
|
||||
/** allocate and initialize a new hash table */
|
||||
hash_t *hash_new(xmpp_ctx_t * const ctx, const int size,
|
||||
hash_free_func free_func);
|
||||
hash_t *
|
||||
hash_new(xmpp_ctx_t *const ctx, const int size, hash_free_func free_func);
|
||||
|
||||
/** allocate a new reference to an existing hash table */
|
||||
hash_t *hash_clone(hash_t * const table);
|
||||
hash_t *hash_clone(hash_t *const table);
|
||||
|
||||
/** release a hash table when no longer needed */
|
||||
void hash_release(hash_t * const table);
|
||||
void hash_release(hash_t *const table);
|
||||
|
||||
/** add a key, value pair to a hash table.
|
||||
* each key can appear only once; the value of any
|
||||
* identical key will be replaced
|
||||
*/
|
||||
int hash_add(hash_t *table, const char * const key, void *data);
|
||||
int hash_add(hash_t *table, const char *const key, void *data);
|
||||
|
||||
/** look up a key in a hash table */
|
||||
void *hash_get(hash_t *table, const char *key);
|
||||
@@ -56,6 +56,6 @@ void hash_iter_release(hash_iterator_t *iter);
|
||||
|
||||
/** return the next hash table key from the iterator.
|
||||
the returned key should not be freed */
|
||||
const char * hash_iter_next(hash_iterator_t *iter);
|
||||
const char *hash_iter_next(hash_iterator_t *iter);
|
||||
|
||||
#endif /* __LIBXMPPP_HASH_H__ */
|
||||
|
||||
54
src/jid.c
54
src/jid.c
@@ -28,15 +28,17 @@
|
||||
* @return an allocated string with the full JID or NULL if no domain
|
||||
* is specified
|
||||
*/
|
||||
char *xmpp_jid_new(xmpp_ctx_t *ctx, const char *node,
|
||||
const char *domain,
|
||||
const char *resource)
|
||||
char *xmpp_jid_new(xmpp_ctx_t *ctx,
|
||||
const char *node,
|
||||
const char *domain,
|
||||
const char *resource)
|
||||
{
|
||||
char *result;
|
||||
size_t len, nlen, dlen, rlen;
|
||||
|
||||
/* jid must at least have a domain */
|
||||
if (domain == NULL) return NULL;
|
||||
if (domain == NULL)
|
||||
return NULL;
|
||||
|
||||
/* accumulate lengths */
|
||||
dlen = strlen(domain);
|
||||
@@ -47,16 +49,16 @@ char *xmpp_jid_new(xmpp_ctx_t *ctx, const char *node,
|
||||
/* concat components */
|
||||
result = xmpp_alloc(ctx, len + 1);
|
||||
if (result != NULL) {
|
||||
if (node != NULL) {
|
||||
memcpy(result, node, nlen - 1);
|
||||
result[nlen-1] = '@';
|
||||
}
|
||||
if (node != NULL) {
|
||||
memcpy(result, node, nlen - 1);
|
||||
result[nlen - 1] = '@';
|
||||
}
|
||||
memcpy(result + nlen, domain, dlen);
|
||||
if (resource != NULL) {
|
||||
result[nlen+dlen] = '/';
|
||||
memcpy(result+nlen+dlen+1, resource, rlen - 1);
|
||||
}
|
||||
result[len] = '\0';
|
||||
if (resource != NULL) {
|
||||
result[nlen + dlen] = '/';
|
||||
memcpy(result + nlen + dlen + 1, resource, rlen - 1);
|
||||
}
|
||||
result[len] = '\0';
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -77,8 +79,8 @@ char *xmpp_jid_bare(xmpp_ctx_t *ctx, const char *jid)
|
||||
len = strcspn(jid, "/");
|
||||
result = xmpp_alloc(ctx, len + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, jid, len);
|
||||
result[len] = '\0';
|
||||
memcpy(result, jid, len);
|
||||
result[len] = '\0';
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -99,11 +101,11 @@ char *xmpp_jid_node(xmpp_ctx_t *ctx, const char *jid)
|
||||
|
||||
c = strchr(jid, '@');
|
||||
if (c != NULL) {
|
||||
result = xmpp_alloc(ctx, (c-jid) + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, jid, (c-jid));
|
||||
result[c-jid] = '\0';
|
||||
}
|
||||
result = xmpp_alloc(ctx, (c - jid) + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, jid, (c - jid));
|
||||
result[c - jid] = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -124,17 +126,17 @@ char *xmpp_jid_domain(xmpp_ctx_t *ctx, const char *jid)
|
||||
|
||||
c = strchr(jid, '@');
|
||||
if (c == NULL) {
|
||||
/* no node, assume domain */
|
||||
c = jid;
|
||||
/* no node, assume domain */
|
||||
c = jid;
|
||||
} else {
|
||||
/* advance past the separator */
|
||||
c++;
|
||||
/* advance past the separator */
|
||||
c++;
|
||||
}
|
||||
dlen = strcspn(c, "/"); /* do not include resource */
|
||||
result = xmpp_alloc(ctx, dlen + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, c, dlen);
|
||||
result[dlen] = '\0';
|
||||
memcpy(result, c, dlen);
|
||||
result[dlen] = '\0';
|
||||
}
|
||||
|
||||
return result;
|
||||
|
||||
26
src/md5.c
26
src/md5.c
@@ -29,19 +29,19 @@
|
||||
#include "md5.h"
|
||||
|
||||
/* little-endian word access macros */
|
||||
#define GET_32BIT_LSB_FIRST(cp) \
|
||||
(((uint32_t)(unsigned char)(cp)[0]) | \
|
||||
((uint32_t)(unsigned char)(cp)[1] << 8 ) | \
|
||||
#define GET_32BIT_LSB_FIRST(cp) \
|
||||
(((uint32_t)(unsigned char)(cp)[0]) | \
|
||||
((uint32_t)(unsigned char)(cp)[1] << 8) | \
|
||||
((uint32_t)(unsigned char)(cp)[2] << 16) | \
|
||||
((uint32_t)(unsigned char)(cp)[3] << 24))
|
||||
|
||||
#define PUT_32BIT_LSB_FIRST(cp, value) \
|
||||
do { \
|
||||
(cp)[0] = (value) & 0xFF; \
|
||||
(cp)[1] = ((value) >> 8) & 0xFF; \
|
||||
#define PUT_32BIT_LSB_FIRST(cp, value) \
|
||||
do { \
|
||||
(cp)[0] = (value)&0xFF; \
|
||||
(cp)[1] = ((value) >> 8) & 0xFF; \
|
||||
(cp)[2] = ((value) >> 16) & 0xFF; \
|
||||
(cp)[3] = ((value) >> 24) & 0xFF; \
|
||||
} while(0)
|
||||
} while (0)
|
||||
|
||||
static void MD5Transform(uint32_t buf[4], const unsigned char inext[64]);
|
||||
|
||||
@@ -74,10 +74,10 @@ void MD5Update(struct MD5Context *ctx, unsigned char const *buf, uint32_t len)
|
||||
|
||||
t = ctx->bits[0];
|
||||
if ((ctx->bits[0] = (t + ((uint32_t)len << 3)) & 0xffffffff) < t)
|
||||
ctx->bits[1]++; /* Carry from low to high */
|
||||
ctx->bits[1]++; /* Carry from low to high */
|
||||
ctx->bits[1] += len >> 29;
|
||||
|
||||
t = (t >> 3) & 0x3f; /* Bytes already in shsInfo->data */
|
||||
t = (t >> 3) & 0x3f; /* Bytes already in shsInfo->data */
|
||||
|
||||
/* Handle any leading odd-sized chunks */
|
||||
|
||||
@@ -150,7 +150,7 @@ void MD5Final(unsigned char digest[16], struct MD5Context *ctx)
|
||||
PUT_32BIT_LSB_FIRST(digest + 4, ctx->buf[1]);
|
||||
PUT_32BIT_LSB_FIRST(digest + 8, ctx->buf[2]);
|
||||
PUT_32BIT_LSB_FIRST(digest + 12, ctx->buf[3]);
|
||||
memset(ctx, 0, sizeof(*ctx)); /* In case it's sensitive */
|
||||
memset(ctx, 0, sizeof(*ctx)); /* In case it's sensitive */
|
||||
}
|
||||
|
||||
/* The four core functions - F1 is optimized somewhat */
|
||||
@@ -172,7 +172,7 @@ void MD5Final(unsigned char digest[16], struct MD5Context *ctx)
|
||||
w = w<<s | w>>(32-s), printf(" - w: %x\n", w), w += x )
|
||||
*/
|
||||
#define MD5STEP(f, w, x, y, z, data, s) \
|
||||
( w += f(x, y, z) + data, w = w<<s | w>>(32-s), w += x )
|
||||
(w += f(x, y, z) + data, w = w << s | w >> (32 - s), w += x)
|
||||
|
||||
/*
|
||||
* The core of the MD5 algorithm, this alters an existing MD5 hash to
|
||||
@@ -185,7 +185,7 @@ static void MD5Transform(uint32_t buf[4], const unsigned char inext[64])
|
||||
uint32_t in[16];
|
||||
|
||||
for (i = 0; i < 16; i++)
|
||||
in[i] = GET_32BIT_LSB_FIRST(inext + 4 * i);
|
||||
in[i] = GET_32BIT_LSB_FIRST(inext + 4 * i);
|
||||
|
||||
a = buf[0];
|
||||
b = buf[1];
|
||||
|
||||
@@ -21,7 +21,8 @@ struct MD5Context {
|
||||
};
|
||||
|
||||
void MD5Init(struct MD5Context *context);
|
||||
void MD5Update(struct MD5Context *context, unsigned char const *buf,
|
||||
void MD5Update(struct MD5Context *context,
|
||||
unsigned char const *buf,
|
||||
uint32_t len);
|
||||
void MD5Final(unsigned char digest[16], struct MD5Context *context);
|
||||
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
/* ostypes.h
|
||||
** strophe XMPP client library -- type definitions for platforms
|
||||
** strophe XMPP client library -- type definitions for platforms
|
||||
** without stdint.h
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
@@ -17,9 +17,9 @@
|
||||
#ifndef __LIBSTROPHE_OSTYPES_H__
|
||||
#define __LIBSTROPHE_OSTYPES_H__
|
||||
|
||||
#include <stddef.h> /* size_t */
|
||||
#include <stddef.h> /* size_t */
|
||||
|
||||
#if defined (_MSC_VER) && _MSC_VER < 1600
|
||||
#if defined(_MSC_VER) && _MSC_VER < 1600
|
||||
typedef signed char int8_t;
|
||||
typedef short int int16_t;
|
||||
typedef int int32_t;
|
||||
@@ -28,7 +28,7 @@ typedef __int64 int64_t;
|
||||
typedef unsigned char uint8_t;
|
||||
typedef unsigned short int uint16_t;
|
||||
typedef unsigned int uint32_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
|
||||
#ifndef UINT16_MAX
|
||||
#define UINT16_MAX ((uint16_t)0xffff)
|
||||
|
||||
13
src/parser.h
13
src/parser.h
@@ -1,7 +1,7 @@
|
||||
/* parser.h
|
||||
** strophe XMPP client library -- parser structures and functions
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express or
|
||||
** implied.
|
||||
@@ -22,19 +22,18 @@ typedef struct _parser_t parser_t;
|
||||
|
||||
typedef void (*parser_start_callback)(char *name,
|
||||
char **attrs,
|
||||
void * const userdata);
|
||||
typedef void (*parser_end_callback)(char *name, void * const userdata);
|
||||
void *const userdata);
|
||||
typedef void (*parser_end_callback)(char *name, void *const userdata);
|
||||
typedef void (*parser_stanza_callback)(xmpp_stanza_t *stanza,
|
||||
void * const userdata);
|
||||
void *const userdata);
|
||||
|
||||
|
||||
parser_t *parser_new(xmpp_ctx_t *ctx,
|
||||
parser_t *parser_new(xmpp_ctx_t *ctx,
|
||||
parser_start_callback startcb,
|
||||
parser_end_callback endcb,
|
||||
parser_stanza_callback stanzacb,
|
||||
void *userdata);
|
||||
void parser_free(parser_t *parser);
|
||||
char* parser_attr_name(xmpp_ctx_t *ctx, char *nsname);
|
||||
char *parser_attr_name(xmpp_ctx_t *ctx, char *nsname);
|
||||
int parser_reset(parser_t *parser);
|
||||
int parser_feed(parser_t *parser, char *chunk, int len);
|
||||
|
||||
|
||||
@@ -38,7 +38,7 @@ struct _parser_t {
|
||||
void *userdata;
|
||||
int depth;
|
||||
xmpp_stanza_t *stanza;
|
||||
char* inner_text;
|
||||
char *inner_text;
|
||||
/* number of allocated bytes */
|
||||
int inner_text_size;
|
||||
/* excluding terminal '\0' */
|
||||
@@ -94,14 +94,15 @@ static char *_xml_name(xmpp_ctx_t *ctx, const char *nsname)
|
||||
size_t len;
|
||||
|
||||
c = strchr(nsname, namespace_sep);
|
||||
if (c == NULL) return xmpp_strdup(ctx, nsname);
|
||||
if (c == NULL)
|
||||
return xmpp_strdup(ctx, nsname);
|
||||
|
||||
c++;
|
||||
len = strlen(c);
|
||||
result = xmpp_alloc(ctx, len + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, c, len);
|
||||
result[len] = '\0';
|
||||
memcpy(result, c, len);
|
||||
result[len] = '\0';
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -115,11 +116,11 @@ static char *_xml_namespace(xmpp_ctx_t *ctx, const char *nsname)
|
||||
|
||||
c = strchr(nsname, namespace_sep);
|
||||
if (c != NULL) {
|
||||
result = xmpp_alloc(ctx, (c-nsname) + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, nsname, (c-nsname));
|
||||
result[c-nsname] = '\0';
|
||||
}
|
||||
result = xmpp_alloc(ctx, (c - nsname) + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, nsname, (c - nsname));
|
||||
result[c - nsname] = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -130,12 +131,13 @@ static void _set_attributes(xmpp_stanza_t *stanza, const XML_Char **attrs)
|
||||
char *attr;
|
||||
int i;
|
||||
|
||||
if (!attrs) return;
|
||||
if (!attrs)
|
||||
return;
|
||||
|
||||
for (i = 0; attrs[i]; i += 2) {
|
||||
/* namespaced attributes aren't used in xmpp, discard namespace */
|
||||
attr = _xml_name(stanza->ctx, attrs[i]);
|
||||
xmpp_stanza_set_attribute(stanza, attr, attrs[i+1]);
|
||||
xmpp_stanza_set_attribute(stanza, attr, attrs[i + 1]);
|
||||
xmpp_free(stanza->ctx, attr);
|
||||
}
|
||||
}
|
||||
@@ -160,9 +162,8 @@ static void complete_inner_text(parser_t *parser)
|
||||
}
|
||||
}
|
||||
|
||||
static void _start_element(void *userdata,
|
||||
const XML_Char *nsname,
|
||||
const XML_Char **attrs)
|
||||
static void
|
||||
_start_element(void *userdata, const XML_Char *nsname, const XML_Char **attrs)
|
||||
{
|
||||
parser_t *parser = (parser_t *)userdata;
|
||||
xmpp_stanza_t *child;
|
||||
@@ -174,8 +175,7 @@ static void _start_element(void *userdata,
|
||||
if (parser->depth == 0) {
|
||||
/* notify the owner */
|
||||
if (parser->startcb)
|
||||
parser->startcb(name, (char **)attrs,
|
||||
parser->userdata);
|
||||
parser->startcb(name, (char **)attrs, parser->userdata);
|
||||
} else {
|
||||
/* build stanzas at depth 1 */
|
||||
if (!parser->stanza && parser->depth != 1) {
|
||||
@@ -201,8 +201,10 @@ static void _start_element(void *userdata,
|
||||
}
|
||||
}
|
||||
|
||||
if (ns) xmpp_free(parser->ctx, ns);
|
||||
if (name) xmpp_free(parser->ctx, name);
|
||||
if (ns)
|
||||
xmpp_free(parser->ctx, ns);
|
||||
if (name)
|
||||
xmpp_free(parser->ctx, name);
|
||||
|
||||
parser->depth++;
|
||||
}
|
||||
@@ -224,8 +226,7 @@ static void _end_element(void *userdata, const XML_Char *name)
|
||||
parser->stanza = parser->stanza->parent;
|
||||
} else {
|
||||
if (parser->stanzacb)
|
||||
parser->stanzacb(parser->stanza,
|
||||
parser->userdata);
|
||||
parser->stanzacb(parser->stanza, parser->userdata);
|
||||
xmpp_stanza_release(parser->stanza);
|
||||
parser->stanza = NULL;
|
||||
}
|
||||
@@ -237,13 +238,14 @@ static void _characters(void *userdata, const XML_Char *s, int len)
|
||||
parser_t *parser = (parser_t *)userdata;
|
||||
char *p;
|
||||
|
||||
if (parser->depth < 2) return;
|
||||
if (parser->depth < 2)
|
||||
return;
|
||||
|
||||
/* Join all parts to a single resulting string. Stanza is created in
|
||||
* _start_element() and _end_element(). */
|
||||
if (parser->inner_text_used + len >= parser->inner_text_size) {
|
||||
parser->inner_text_size = parser->inner_text_used + len + 1 +
|
||||
INNER_TEXT_PADDING;
|
||||
parser->inner_text_size =
|
||||
parser->inner_text_used + len + 1 + INNER_TEXT_PADDING;
|
||||
p = xmpp_realloc(parser->ctx, parser->inner_text,
|
||||
parser->inner_text_size);
|
||||
if (p == NULL) {
|
||||
@@ -288,7 +290,7 @@ parser_t *parser_new(xmpp_ctx_t *ctx,
|
||||
return parser;
|
||||
}
|
||||
|
||||
char* parser_attr_name(xmpp_ctx_t *ctx, char *nsname)
|
||||
char *parser_attr_name(xmpp_ctx_t *ctx, char *nsname)
|
||||
{
|
||||
return _xml_name(ctx, nsname);
|
||||
}
|
||||
@@ -300,7 +302,7 @@ void parser_free(parser_t *parser)
|
||||
XML_ParserFree(parser->expat);
|
||||
|
||||
if (parser->inner_text) {
|
||||
xmpp_free (parser->ctx, parser->inner_text);
|
||||
xmpp_free(parser->ctx, parser->inner_text);
|
||||
parser->inner_text = NULL;
|
||||
}
|
||||
|
||||
|
||||
@@ -36,53 +36,56 @@ struct _parser_t {
|
||||
xmpp_stanza_t *stanza;
|
||||
};
|
||||
|
||||
static void _set_attributes(xmpp_stanza_t *stanza, int nattrs,
|
||||
const xmlChar **attrs)
|
||||
static void
|
||||
_set_attributes(xmpp_stanza_t *stanza, int nattrs, const xmlChar **attrs)
|
||||
{
|
||||
int i, len;
|
||||
char *value;
|
||||
|
||||
if (!attrs) return;
|
||||
if (!attrs)
|
||||
return;
|
||||
|
||||
/* SAX2 uses array of localname/prefix/uri/value_begin/value_end */
|
||||
for (i = 0; i < nattrs*5; i += 5) {
|
||||
len = attrs[i+4] - attrs[i+3];
|
||||
for (i = 0; i < nattrs * 5; i += 5) {
|
||||
len = attrs[i + 4] - attrs[i + 3];
|
||||
value = xmpp_alloc(stanza->ctx, len + 1);
|
||||
if (value) {
|
||||
memcpy(value, attrs[i+3], len);
|
||||
value[len] = '\0';
|
||||
xmpp_stanza_set_attribute(stanza, (const char *)attrs[i], value);
|
||||
xmpp_free(stanza->ctx, value);
|
||||
}
|
||||
if (value) {
|
||||
memcpy(value, attrs[i + 3], len);
|
||||
value[len] = '\0';
|
||||
xmpp_stanza_set_attribute(stanza, (const char *)attrs[i], value);
|
||||
xmpp_free(stanza->ctx, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* SAX2 gives us the attrs in an incredibly inconvenient array,
|
||||
* convert it to what the start callback is expecting */
|
||||
static char **_convert_attrs(parser_t *parser, int nattrs,
|
||||
const xmlChar **attrs)
|
||||
static char **
|
||||
_convert_attrs(parser_t *parser, int nattrs, const xmlChar **attrs)
|
||||
{
|
||||
int c, i, o, len;
|
||||
char *value;
|
||||
char **ret;
|
||||
|
||||
if (!attrs) return NULL;
|
||||
if (!attrs)
|
||||
return NULL;
|
||||
|
||||
ret = xmpp_alloc(parser->ctx, (nattrs+1)*2*sizeof(char*));
|
||||
if (!ret) return NULL;
|
||||
memset(ret, 0, (nattrs+1)*2*sizeof(char*));
|
||||
ret = xmpp_alloc(parser->ctx, (nattrs + 1) * 2 * sizeof(char *));
|
||||
if (!ret)
|
||||
return NULL;
|
||||
memset(ret, 0, (nattrs + 1) * 2 * sizeof(char *));
|
||||
|
||||
for (c = 0; c < nattrs; c++) {
|
||||
i = c * 5;
|
||||
o = c * 2;
|
||||
|
||||
len = attrs[i+4] - attrs[i+3];
|
||||
len = attrs[i + 4] - attrs[i + 3];
|
||||
value = xmpp_alloc(parser->ctx, len + 1);
|
||||
if (value) {
|
||||
memcpy(value, attrs[i+3], len);
|
||||
memcpy(value, attrs[i + 3], len);
|
||||
value[len] = '\0';
|
||||
ret[o] = xmpp_strdup(parser->ctx, (char*)attrs[i]);
|
||||
ret[o+1] = value;
|
||||
ret[o] = xmpp_strdup(parser->ctx, (char *)attrs[i]);
|
||||
ret[o + 1] = value;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -97,18 +100,24 @@ static void _free_cbattrs(parser_t *parser, char **attrs)
|
||||
return;
|
||||
|
||||
for (i = 0; attrs[i]; i += 2) {
|
||||
if (attrs[i]) xmpp_free(parser->ctx, attrs[i]);
|
||||
if (attrs[i+1]) xmpp_free(parser->ctx, attrs[i+1]);
|
||||
if (attrs[i])
|
||||
xmpp_free(parser->ctx, attrs[i]);
|
||||
if (attrs[i + 1])
|
||||
xmpp_free(parser->ctx, attrs[i + 1]);
|
||||
}
|
||||
|
||||
xmpp_free(parser->ctx, attrs);
|
||||
}
|
||||
|
||||
static void _start_element(void *userdata,
|
||||
const xmlChar *name, const xmlChar *prefix,
|
||||
const xmlChar *uri, int nnamespaces,
|
||||
const xmlChar **namespaces, int nattrs,
|
||||
int ndefaulted, const xmlChar **attrs)
|
||||
const xmlChar *name,
|
||||
const xmlChar *prefix,
|
||||
const xmlChar *uri,
|
||||
int nnamespaces,
|
||||
const xmlChar **namespaces,
|
||||
int nattrs,
|
||||
int ndefaulted,
|
||||
const xmlChar **attrs)
|
||||
{
|
||||
parser_t *parser = (parser_t *)userdata;
|
||||
xmpp_stanza_t *child;
|
||||
@@ -118,53 +127,54 @@ static void _start_element(void *userdata,
|
||||
/* notify the owner */
|
||||
if (parser->startcb) {
|
||||
cbattrs = _convert_attrs(parser, nattrs, attrs);
|
||||
parser->startcb((char *)name, cbattrs,
|
||||
parser->userdata);
|
||||
parser->startcb((char *)name, cbattrs, parser->userdata);
|
||||
_free_cbattrs(parser, cbattrs);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
/* build stanzas at depth 1 */
|
||||
if (!parser->stanza && parser->depth != 1) {
|
||||
/* something terrible happened */
|
||||
/* FIXME: we should probably trigger a disconnect */
|
||||
xmpp_error(parser->ctx, "parser", "oops, where did our stanza go?");
|
||||
} else if (!parser->stanza) {
|
||||
/* starting a new toplevel stanza */
|
||||
parser->stanza = xmpp_stanza_new(parser->ctx);
|
||||
if (!parser->stanza) {
|
||||
/* FIXME: can't allocate, disconnect */
|
||||
}
|
||||
xmpp_stanza_set_name(parser->stanza, (char *)name);
|
||||
_set_attributes(parser->stanza, nattrs, attrs);
|
||||
if (uri)
|
||||
xmpp_stanza_set_ns(parser->stanza, (char *)uri);
|
||||
} else {
|
||||
/* starting a child of conn->stanza */
|
||||
child = xmpp_stanza_new(parser->ctx);
|
||||
if (!child) {
|
||||
/* FIXME: can't allocate, disconnect */
|
||||
}
|
||||
xmpp_stanza_set_name(child, (char *)name);
|
||||
_set_attributes(child, nattrs, attrs);
|
||||
if (uri)
|
||||
xmpp_stanza_set_ns(child, (char *)uri);
|
||||
/* build stanzas at depth 1 */
|
||||
if (!parser->stanza && parser->depth != 1) {
|
||||
/* something terrible happened */
|
||||
/* FIXME: we should probably trigger a disconnect */
|
||||
xmpp_error(parser->ctx, "parser", "oops, where did our stanza go?");
|
||||
} else if (!parser->stanza) {
|
||||
/* starting a new toplevel stanza */
|
||||
parser->stanza = xmpp_stanza_new(parser->ctx);
|
||||
if (!parser->stanza) {
|
||||
/* FIXME: can't allocate, disconnect */
|
||||
}
|
||||
xmpp_stanza_set_name(parser->stanza, (char *)name);
|
||||
_set_attributes(parser->stanza, nattrs, attrs);
|
||||
if (uri)
|
||||
xmpp_stanza_set_ns(parser->stanza, (char *)uri);
|
||||
} else {
|
||||
/* starting a child of conn->stanza */
|
||||
child = xmpp_stanza_new(parser->ctx);
|
||||
if (!child) {
|
||||
/* FIXME: can't allocate, disconnect */
|
||||
}
|
||||
xmpp_stanza_set_name(child, (char *)name);
|
||||
_set_attributes(child, nattrs, attrs);
|
||||
if (uri)
|
||||
xmpp_stanza_set_ns(child, (char *)uri);
|
||||
|
||||
/* add child to parent */
|
||||
xmpp_stanza_add_child(parser->stanza, child);
|
||||
/* add child to parent */
|
||||
xmpp_stanza_add_child(parser->stanza, child);
|
||||
|
||||
/* the child is owned by the toplevel stanza now */
|
||||
xmpp_stanza_release(child);
|
||||
/* the child is owned by the toplevel stanza now */
|
||||
xmpp_stanza_release(child);
|
||||
|
||||
/* make child the current stanza */
|
||||
parser->stanza = child;
|
||||
}
|
||||
/* make child the current stanza */
|
||||
parser->stanza = child;
|
||||
}
|
||||
}
|
||||
|
||||
parser->depth++;
|
||||
}
|
||||
|
||||
static void _end_element(void *userdata, const xmlChar *name,
|
||||
const xmlChar *prefix, const xmlChar *uri)
|
||||
static void _end_element(void *userdata,
|
||||
const xmlChar *name,
|
||||
const xmlChar *prefix,
|
||||
const xmlChar *uri)
|
||||
{
|
||||
parser_t *parser = (parser_t *)userdata;
|
||||
|
||||
@@ -175,16 +185,15 @@ static void _end_element(void *userdata, const xmlChar *name,
|
||||
if (parser->endcb)
|
||||
parser->endcb((char *)name, parser->userdata);
|
||||
} else {
|
||||
if (parser->stanza->parent) {
|
||||
/* we're finishing a child stanza, so set current to the parent */
|
||||
parser->stanza = parser->stanza->parent;
|
||||
} else {
|
||||
if (parser->stanza->parent) {
|
||||
/* we're finishing a child stanza, so set current to the parent */
|
||||
parser->stanza = parser->stanza->parent;
|
||||
} else {
|
||||
if (parser->stanzacb)
|
||||
parser->stanzacb(parser->stanza,
|
||||
parser->userdata);
|
||||
parser->stanzacb(parser->stanza, parser->userdata);
|
||||
xmpp_stanza_release(parser->stanza);
|
||||
parser->stanza = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -194,13 +203,14 @@ static void _characters(void *userdata, const xmlChar *chr, int len)
|
||||
xmpp_stanza_t *stanza;
|
||||
|
||||
/* skip unimportant whitespace, etc */
|
||||
if (parser->depth < 2) return;
|
||||
if (parser->depth < 2)
|
||||
return;
|
||||
|
||||
/* create and populate stanza */
|
||||
stanza = xmpp_stanza_new(parser->ctx);
|
||||
if (!stanza) {
|
||||
/* FIXME: allocation error, disconnect */
|
||||
return;
|
||||
/* FIXME: allocation error, disconnect */
|
||||
return;
|
||||
}
|
||||
xmpp_stanza_set_text_with_size(stanza, (char *)chr, len);
|
||||
|
||||
@@ -239,7 +249,7 @@ parser_t *parser_new(xmpp_ctx_t *ctx,
|
||||
return parser;
|
||||
}
|
||||
|
||||
char* parser_attr_name(xmpp_ctx_t *ctx, char *nsname)
|
||||
char *parser_attr_name(xmpp_ctx_t *ctx, char *nsname)
|
||||
{
|
||||
return xmpp_strdup(ctx, nsname);
|
||||
}
|
||||
@@ -260,13 +270,13 @@ int parser_reset(parser_t *parser)
|
||||
if (parser->xmlctx)
|
||||
xmlFreeParserCtxt(parser->xmlctx);
|
||||
if (parser->stanza)
|
||||
xmpp_stanza_release(parser->stanza);
|
||||
xmpp_stanza_release(parser->stanza);
|
||||
|
||||
parser->stanza = NULL;
|
||||
parser->depth = 0;
|
||||
|
||||
parser->xmlctx = xmlCreatePushParserCtxt(&parser->handlers,
|
||||
parser, NULL, 0, NULL);
|
||||
parser->xmlctx =
|
||||
xmlCreatePushParserCtxt(&parser->handlers, parser, NULL, 0, NULL);
|
||||
|
||||
return parser->xmlctx ? 1 : 0;
|
||||
}
|
||||
|
||||
56
src/rand.c
56
src/rand.c
@@ -20,15 +20,15 @@
|
||||
*/
|
||||
|
||||
#include <assert.h>
|
||||
#include <string.h> /* memeset */
|
||||
#include <time.h> /* clock, time */
|
||||
#include <string.h> /* memeset */
|
||||
#include <time.h> /* clock, time */
|
||||
|
||||
#include "common.h" /* xmpp_alloc, xmpp_free */
|
||||
#include "ostypes.h" /* uint8_t, uint32_t, size_t */
|
||||
#include "common.h" /* xmpp_alloc, xmpp_free */
|
||||
#include "ostypes.h" /* uint8_t, uint32_t, size_t */
|
||||
#include "sha1.h"
|
||||
#include "snprintf.h" /* xmpp_snprintf */
|
||||
#include "snprintf.h" /* xmpp_snprintf */
|
||||
|
||||
#include "rand.h" /* xmpp_rand_t */
|
||||
#include "rand.h" /* xmpp_rand_t */
|
||||
|
||||
#define outlen SHA1_DIGEST_SIZE
|
||||
#define seedlen (440 / 8)
|
||||
@@ -55,15 +55,15 @@ struct _xmpp_rand_t {
|
||||
};
|
||||
|
||||
/* returns smallest number mupliple of y that not less than x */
|
||||
#define round_up(x, y) (((x) + (y) - 1) / (y) * (y))
|
||||
#define round_up(x, y) (((x) + (y)-1) / (y) * (y))
|
||||
/* returns smallest integer number that not less than x/y */
|
||||
#define div_round_up(x, y) (((x) + (y) - 1) / (y))
|
||||
#define div_round_up(x, y) (((x) + (y)-1) / (y))
|
||||
|
||||
/* adds two arrays as numbers in big-endian representation and stores
|
||||
* result in the first one.
|
||||
*/
|
||||
static void arr_add(uint8_t *arr1, size_t arr1_len,
|
||||
uint8_t *arr2, size_t arr2_len)
|
||||
static void
|
||||
arr_add(uint8_t *arr1, size_t arr1_len, uint8_t *arr2, size_t arr2_len)
|
||||
{
|
||||
size_t i;
|
||||
uint32_t acc;
|
||||
@@ -89,8 +89,10 @@ static void store_be32(uint32_t val, uint8_t be[4])
|
||||
be[3] = (uint8_t)(val & 0xff);
|
||||
}
|
||||
|
||||
static void Hash_df(uint8_t *input_string, size_t input_string_len,
|
||||
uint8_t *output_string, size_t no_of_bytes_to_return)
|
||||
static void Hash_df(uint8_t *input_string,
|
||||
size_t input_string_len,
|
||||
uint8_t *output_string,
|
||||
size_t no_of_bytes_to_return)
|
||||
{
|
||||
uint8_t counter;
|
||||
uint8_t temp[round_up(seedlen, outlen)];
|
||||
@@ -119,7 +121,8 @@ static void Hash_df(uint8_t *input_string, size_t input_string_len,
|
||||
static void Hash_DRBG_Instantiate(Hash_DRBG_CTX *ctx,
|
||||
uint8_t *entropy_input,
|
||||
size_t entropy_input_len,
|
||||
uint8_t *nonce, size_t nonce_len)
|
||||
uint8_t *nonce,
|
||||
size_t nonce_len)
|
||||
{
|
||||
uint8_t seed_material[ENTROPY_MAX + NONCE_MAX];
|
||||
uint8_t seed0[seedlen + 1];
|
||||
@@ -162,8 +165,8 @@ static void Hash_DRBG_Reseed(Hash_DRBG_CTX *ctx,
|
||||
ctx->reseed_counter = 1;
|
||||
}
|
||||
|
||||
static void Hashgen(uint8_t *V, uint8_t *output,
|
||||
size_t requested_number_of_bytes)
|
||||
static void
|
||||
Hashgen(uint8_t *V, uint8_t *output, size_t requested_number_of_bytes)
|
||||
{
|
||||
uint8_t data[seedlen];
|
||||
uint8_t W[GENERATE_MAX];
|
||||
@@ -187,7 +190,8 @@ static void Hashgen(uint8_t *V, uint8_t *output,
|
||||
}
|
||||
|
||||
/* assume additional_input is zero length string */
|
||||
static int Hash_DRBG_Generate(Hash_DRBG_CTX *ctx, uint8_t *output,
|
||||
static int Hash_DRBG_Generate(Hash_DRBG_CTX *ctx,
|
||||
uint8_t *output,
|
||||
size_t requested_number_of_bytes)
|
||||
{
|
||||
uint8_t H[outlen];
|
||||
@@ -211,14 +215,14 @@ static int Hash_DRBG_Generate(Hash_DRBG_CTX *ctx, uint8_t *output,
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define ENTROPY_ACCUMULATE(ptr, last, type, arg) \
|
||||
do { \
|
||||
type __arg = (type)(arg); \
|
||||
if ((char*)ptr + sizeof(__arg) < (char*)last) { \
|
||||
*(type*)ptr = __arg; \
|
||||
ptr = (void*)((char*)ptr + sizeof(__arg)); \
|
||||
} \
|
||||
} while (0)
|
||||
#define ENTROPY_ACCUMULATE(ptr, last, type, arg) \
|
||||
do { \
|
||||
type __arg = (type)(arg); \
|
||||
if ((char *)ptr + sizeof(__arg) < (char *)last) { \
|
||||
*(type *)ptr = __arg; \
|
||||
ptr = (void *)((char *)ptr + sizeof(__arg)); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static void xmpp_rand_reseed(xmpp_rand_t *rand)
|
||||
{
|
||||
@@ -291,8 +295,8 @@ int xmpp_rand(xmpp_rand_t *rand)
|
||||
|
||||
static void rand_byte2hex(unsigned char byte, char *hex)
|
||||
{
|
||||
static const char hex_tbl[16] = { '0', '1', '2', '3', '4', '5', '6', '7',
|
||||
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
|
||||
static const char hex_tbl[16] = {'0', '1', '2', '3', '4', '5', '6', '7',
|
||||
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
|
||||
|
||||
hex[0] = hex_tbl[(byte >> 4) & 0x0f];
|
||||
hex[1] = hex_tbl[byte & 0x0f];
|
||||
|
||||
@@ -16,8 +16,8 @@
|
||||
#ifndef __LIBSTROPHE_RAND_H__
|
||||
#define __LIBSTROPHE_RAND_H__
|
||||
|
||||
#include <stddef.h> /* size_t */
|
||||
#include "strophe.h" /* xmpp_ctx_t */
|
||||
#include <stddef.h> /* size_t */
|
||||
#include "strophe.h" /* xmpp_ctx_t */
|
||||
|
||||
typedef struct _xmpp_rand_t xmpp_rand_t;
|
||||
|
||||
|
||||
681
src/resolver.c
681
src/resolver.c
@@ -16,8 +16,8 @@
|
||||
#if !defined(_WIN32) && !defined(HAVE_CARES)
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/nameser.h>
|
||||
#include <resolv.h> /* res_query */
|
||||
#endif /* _WIN32 && HAVE_CARES */
|
||||
#include <resolv.h> /* res_query */
|
||||
#endif /* _WIN32 && HAVE_CARES */
|
||||
|
||||
#ifdef HAVE_CARES
|
||||
#include <ares.h>
|
||||
@@ -31,11 +31,11 @@
|
||||
#endif /* !_WIN32 */
|
||||
#endif /* HAVE_CARES */
|
||||
|
||||
#include <string.h> /* strncpy */
|
||||
#include <string.h> /* strncpy */
|
||||
|
||||
#include "ostypes.h"
|
||||
#include "snprintf.h"
|
||||
#include "util.h" /* xmpp_min */
|
||||
#include "util.h" /* xmpp_min */
|
||||
#include "resolver.h"
|
||||
|
||||
#define MESSAGE_HEADER_LEN 12
|
||||
@@ -52,7 +52,8 @@ static int resolver_ares_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
const unsigned char *buf,
|
||||
size_t len,
|
||||
resolver_srv_rr_t **srv_rr_list);
|
||||
static int resolver_ares_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
static int resolver_ares_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *fulldomain,
|
||||
resolver_srv_rr_t **srv_rr_list);
|
||||
#endif /* HAVE_CARES */
|
||||
|
||||
@@ -64,10 +65,12 @@ static int resolver_raw_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
#endif /* !HAVE_CARES */
|
||||
|
||||
#ifdef _WIN32
|
||||
static int resolver_win32_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
static int resolver_win32_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *fulldomain,
|
||||
resolver_srv_rr_t **srv_rr_list);
|
||||
static int resolver_win32_srv_query(const char *fulldomain,
|
||||
unsigned char *buf, size_t len);
|
||||
unsigned char *buf,
|
||||
size_t len);
|
||||
#endif /* _WIN32 */
|
||||
|
||||
/*******************************************************************************
|
||||
@@ -118,8 +121,7 @@ static void resolver_srv_list_sort(resolver_srv_rr_t **srv_rr_list)
|
||||
*/
|
||||
if ((rr_current->priority > rr_next->priority) ||
|
||||
(rr_current->priority == rr_next->priority &&
|
||||
rr_current->weight < rr_next->weight))
|
||||
{
|
||||
rr_current->weight < rr_next->weight)) {
|
||||
/* Swap node */
|
||||
swap = 1;
|
||||
if (rr_prev != NULL) {
|
||||
@@ -145,8 +147,10 @@ static void resolver_srv_list_sort(resolver_srv_rr_t **srv_rr_list)
|
||||
*srv_rr_list = rr_head;
|
||||
}
|
||||
|
||||
int resolver_srv_lookup_buf(xmpp_ctx_t *ctx, const unsigned char *buf,
|
||||
size_t len, resolver_srv_rr_t **srv_rr_list)
|
||||
int resolver_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
const unsigned char *buf,
|
||||
size_t len,
|
||||
resolver_srv_rr_t **srv_rr_list)
|
||||
{
|
||||
int set;
|
||||
|
||||
@@ -160,8 +164,11 @@ int resolver_srv_lookup_buf(xmpp_ctx_t *ctx, const unsigned char *buf,
|
||||
return set;
|
||||
}
|
||||
|
||||
int resolver_srv_lookup(xmpp_ctx_t *ctx, const char *service, const char *proto,
|
||||
const char *domain, resolver_srv_rr_t **srv_rr_list)
|
||||
int resolver_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *service,
|
||||
const char *proto,
|
||||
const char *domain,
|
||||
resolver_srv_rr_t **srv_rr_list)
|
||||
{
|
||||
#define RESOLVER_BUF_MAX 65536
|
||||
unsigned char *buf;
|
||||
@@ -172,8 +179,8 @@ int resolver_srv_lookup(xmpp_ctx_t *ctx, const char *service, const char *proto,
|
||||
(void)buf;
|
||||
(void)len;
|
||||
|
||||
xmpp_snprintf(fulldomain, sizeof(fulldomain),
|
||||
"_%s._%s.%s", service, proto, domain);
|
||||
xmpp_snprintf(fulldomain, sizeof(fulldomain), "_%s._%s.%s", service, proto,
|
||||
domain);
|
||||
|
||||
*srv_rr_list = NULL;
|
||||
|
||||
@@ -193,7 +200,7 @@ int resolver_srv_lookup(xmpp_ctx_t *ctx, const char *service, const char *proto,
|
||||
|
||||
#ifdef _WIN32
|
||||
len = resolver_win32_srv_query(fulldomain, buf, RESOLVER_BUF_MAX);
|
||||
#else /* _WIN32 */
|
||||
#else /* _WIN32 */
|
||||
len = res_query(fulldomain, MESSAGE_C_IN, MESSAGE_T_SRV, buf,
|
||||
RESOLVER_BUF_MAX);
|
||||
#endif /* _WIN32 */
|
||||
@@ -259,9 +266,11 @@ static uint8_t message_header_rcode(const struct message_header *header)
|
||||
* Returns length of the non-truncated resulting string, may be bigger than
|
||||
* name_max.
|
||||
*/
|
||||
static size_t message_name_append_safe(char *name, size_t name_len,
|
||||
static size_t message_name_append_safe(char *name,
|
||||
size_t name_len,
|
||||
size_t name_max,
|
||||
const char *tail, size_t tail_len)
|
||||
const char *tail,
|
||||
size_t tail_len)
|
||||
{
|
||||
size_t copy_len;
|
||||
|
||||
@@ -274,9 +283,11 @@ static size_t message_name_append_safe(char *name, size_t name_len,
|
||||
}
|
||||
|
||||
/* Returns length of the compressed name. This is NOT the same as strlen(). */
|
||||
static unsigned message_name_get(const unsigned char *buf, size_t buf_len,
|
||||
static unsigned message_name_get(const unsigned char *buf,
|
||||
size_t buf_len,
|
||||
unsigned buf_offset,
|
||||
char *name, size_t name_max)
|
||||
char *name,
|
||||
size_t name_max)
|
||||
{
|
||||
size_t name_len = 0;
|
||||
unsigned i = buf_offset;
|
||||
@@ -284,26 +295,29 @@ static unsigned message_name_get(const unsigned char *buf, size_t buf_len,
|
||||
unsigned rc;
|
||||
unsigned char label_len;
|
||||
|
||||
|
||||
while (1) {
|
||||
if (i >= buf_len) return 0;
|
||||
if (i >= buf_len)
|
||||
return 0;
|
||||
label_len = buf[i++];
|
||||
if (label_len == 0) break;
|
||||
if (label_len == 0)
|
||||
break;
|
||||
|
||||
/* Label */
|
||||
if ((label_len & 0xc0) == 0) {
|
||||
if (i + label_len - 1 >= buf_len) return 0;
|
||||
if (i + label_len - 1 >= buf_len)
|
||||
return 0;
|
||||
if (name != NULL) {
|
||||
name_len = message_name_append_safe(name, name_len, name_max,
|
||||
(char *)&buf[i], label_len);
|
||||
name_len = message_name_append_safe(name, name_len, name_max,
|
||||
".", 1);
|
||||
name_len =
|
||||
message_name_append_safe(name, name_len, name_max, ".", 1);
|
||||
}
|
||||
i += label_len;
|
||||
|
||||
/* Pointer */
|
||||
/* Pointer */
|
||||
} else if ((label_len & 0xc0) == 0xc0) {
|
||||
if (i >= buf_len) return 0;
|
||||
if (i >= buf_len)
|
||||
return 0;
|
||||
pointer = (label_len & 0x3f) << 8 | buf[i++];
|
||||
if (name != NULL && name_len >= name_max && name_max > 0) {
|
||||
/* We have filled the name buffer. Don't pass it recursively. */
|
||||
@@ -311,20 +325,22 @@ static unsigned message_name_get(const unsigned char *buf, size_t buf_len,
|
||||
name = NULL;
|
||||
name_max = 0;
|
||||
}
|
||||
rc = message_name_get(buf, buf_len, pointer,
|
||||
name != NULL ? &name[name_len] : NULL,
|
||||
name_max > name_len ? name_max - name_len : 0);
|
||||
if (rc == 0) return 0;
|
||||
rc = message_name_get(
|
||||
buf, buf_len, pointer, name != NULL ? &name[name_len] : NULL,
|
||||
name_max > name_len ? name_max - name_len : 0);
|
||||
if (rc == 0)
|
||||
return 0;
|
||||
/* Pointer is always the last. */
|
||||
break;
|
||||
|
||||
/* The 10 and 01 combinations are reserved for future use. */
|
||||
/* The 10 and 01 combinations are reserved for future use. */
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
if (label_len == 0) {
|
||||
if (name_len == 0) name_len = 1;
|
||||
if (name_len == 0)
|
||||
name_len = 1;
|
||||
/*
|
||||
* At this point name_len is length of the resulting name,
|
||||
* including '\0'. This value can be exported to allocate buffer
|
||||
@@ -342,20 +358,21 @@ static unsigned message_name_get(const unsigned char *buf, size_t buf_len,
|
||||
return i - buf_offset;
|
||||
}
|
||||
|
||||
static unsigned message_name_len(const unsigned char *buf, size_t buf_len,
|
||||
unsigned buf_offset)
|
||||
static unsigned
|
||||
message_name_len(const unsigned char *buf, size_t buf_len, unsigned buf_offset)
|
||||
{
|
||||
return message_name_get(buf, buf_len, buf_offset, NULL, SIZE_MAX);
|
||||
}
|
||||
|
||||
#define BUF_OVERFLOW_CHECK(ptr, len) do { \
|
||||
if ((ptr) >= (len)) { \
|
||||
if (*srv_rr_list != NULL) \
|
||||
resolver_srv_free(ctx, *srv_rr_list); \
|
||||
*srv_rr_list = NULL; \
|
||||
return XMPP_DOMAIN_NOT_FOUND; \
|
||||
} \
|
||||
} while (0)
|
||||
#define BUF_OVERFLOW_CHECK(ptr, len) \
|
||||
do { \
|
||||
if ((ptr) >= (len)) { \
|
||||
if (*srv_rr_list != NULL) \
|
||||
resolver_srv_free(ctx, *srv_rr_list); \
|
||||
*srv_rr_list = NULL; \
|
||||
return XMPP_DOMAIN_NOT_FOUND; \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static int resolver_raw_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
const unsigned char *buf,
|
||||
@@ -384,8 +401,7 @@ static int resolver_raw_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
header.nscount = xmpp_ntohs_ptr(&buf[8]);
|
||||
header.arcount = xmpp_ntohs_ptr(&buf[10]);
|
||||
if (message_header_qr(&header) != MESSAGE_RESPONSE ||
|
||||
message_header_rcode(&header) != 0)
|
||||
{
|
||||
message_header_rcode(&header) != 0) {
|
||||
return XMPP_DOMAIN_NOT_FOUND;
|
||||
}
|
||||
j = MESSAGE_HEADER_LEN;
|
||||
@@ -395,7 +411,8 @@ static int resolver_raw_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
BUF_OVERFLOW_CHECK(j, len);
|
||||
name_len = message_name_len(buf, len, j);
|
||||
/* error in name format */
|
||||
if (name_len == 0) return XMPP_DOMAIN_NOT_FOUND;
|
||||
if (name_len == 0)
|
||||
return XMPP_DOMAIN_NOT_FOUND;
|
||||
j += name_len + 4;
|
||||
}
|
||||
|
||||
@@ -403,7 +420,8 @@ static int resolver_raw_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
BUF_OVERFLOW_CHECK(j, len);
|
||||
name_len = message_name_len(buf, len, j);
|
||||
/* error in name format */
|
||||
if (name_len == 0) return XMPP_DOMAIN_NOT_FOUND;
|
||||
if (name_len == 0)
|
||||
return XMPP_DOMAIN_NOT_FOUND;
|
||||
j += name_len;
|
||||
BUF_OVERFLOW_CHECK(j + 16, len);
|
||||
type = xmpp_ntohs_ptr(&buf[j]);
|
||||
@@ -477,8 +495,8 @@ static int resolver_ares_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
return *srv_rr_list == NULL ? XMPP_DOMAIN_NOT_FOUND : XMPP_DOMAIN_FOUND;
|
||||
}
|
||||
|
||||
static void ares_srv_lookup_callback(void *arg, int status, int timeouts,
|
||||
unsigned char *buf, int len)
|
||||
static void ares_srv_lookup_callback(
|
||||
void *arg, int status, int timeouts, unsigned char *buf, int len)
|
||||
{
|
||||
struct resolver_ares_ctx *actx = arg;
|
||||
|
||||
@@ -489,7 +507,8 @@ static void ares_srv_lookup_callback(void *arg, int status, int timeouts,
|
||||
&actx->srv_rr_list);
|
||||
}
|
||||
|
||||
static int resolver_ares_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
static int resolver_ares_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *fulldomain,
|
||||
resolver_srv_rr_t **srv_rr_list)
|
||||
{
|
||||
struct resolver_ares_ctx actx;
|
||||
@@ -546,133 +565,136 @@ static int resolver_ares_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
#include <windns.h>
|
||||
#include <Iphlpapi.h>
|
||||
|
||||
struct dnsquery_header
|
||||
{
|
||||
unsigned short id;
|
||||
unsigned char qr;
|
||||
unsigned char opcode;
|
||||
unsigned char aa;
|
||||
unsigned char tc;
|
||||
unsigned char rd;
|
||||
unsigned char ra;
|
||||
unsigned char z;
|
||||
unsigned char rcode;
|
||||
unsigned short qdcount;
|
||||
unsigned short ancount;
|
||||
unsigned short nscount;
|
||||
unsigned short arcount;
|
||||
struct dnsquery_header {
|
||||
unsigned short id;
|
||||
unsigned char qr;
|
||||
unsigned char opcode;
|
||||
unsigned char aa;
|
||||
unsigned char tc;
|
||||
unsigned char rd;
|
||||
unsigned char ra;
|
||||
unsigned char z;
|
||||
unsigned char rcode;
|
||||
unsigned short qdcount;
|
||||
unsigned short ancount;
|
||||
unsigned short nscount;
|
||||
unsigned short arcount;
|
||||
};
|
||||
|
||||
struct dnsquery_question
|
||||
{
|
||||
char qname[1024];
|
||||
unsigned short qtype;
|
||||
unsigned short qclass;
|
||||
struct dnsquery_question {
|
||||
char qname[1024];
|
||||
unsigned short qtype;
|
||||
unsigned short qclass;
|
||||
};
|
||||
|
||||
static void netbuf_add_16bitnum(unsigned char *buf, int buflen, int *offset, unsigned short num)
|
||||
static void netbuf_add_16bitnum(unsigned char *buf,
|
||||
int buflen,
|
||||
int *offset,
|
||||
unsigned short num)
|
||||
{
|
||||
unsigned char *start = buf + *offset;
|
||||
unsigned char *p = start;
|
||||
unsigned char *start = buf + *offset;
|
||||
unsigned char *p = start;
|
||||
|
||||
/* assuming big endian */
|
||||
*p++ = (num >> 8) & 0xff;
|
||||
*p++ = (num) & 0xff;
|
||||
/* assuming big endian */
|
||||
*p++ = (num >> 8) & 0xff;
|
||||
*p++ = (num)&0xff;
|
||||
|
||||
*offset += 2;
|
||||
*offset += 2;
|
||||
}
|
||||
|
||||
static void netbuf_add_domain_name(unsigned char *buf, int buflen, int *offset,
|
||||
char *name)
|
||||
static void
|
||||
netbuf_add_domain_name(unsigned char *buf, int buflen, int *offset, char *name)
|
||||
{
|
||||
unsigned char *start = buf + *offset;
|
||||
unsigned char *p = start;
|
||||
unsigned char *wordstart, *wordend;
|
||||
unsigned char *start = buf + *offset;
|
||||
unsigned char *p = start;
|
||||
unsigned char *wordstart, *wordend;
|
||||
|
||||
wordstart = (unsigned char *)name;
|
||||
wordstart = (unsigned char *)name;
|
||||
|
||||
while (*wordstart)
|
||||
{
|
||||
int len;
|
||||
wordend = wordstart;
|
||||
while (*wordend && *wordend != '.')
|
||||
{
|
||||
wordend++;
|
||||
}
|
||||
while (*wordstart) {
|
||||
int len;
|
||||
wordend = wordstart;
|
||||
while (*wordend && *wordend != '.') {
|
||||
wordend++;
|
||||
}
|
||||
|
||||
len = (int)(wordend - wordstart);
|
||||
len = (int)(wordend - wordstart);
|
||||
|
||||
if (len > 0x3F)
|
||||
{
|
||||
len = 0x3F;
|
||||
}
|
||||
if (len > 0x3F) {
|
||||
len = 0x3F;
|
||||
}
|
||||
|
||||
*p++ = len;
|
||||
*p++ = len;
|
||||
|
||||
while (wordstart != wordend)
|
||||
{
|
||||
*p++ = *wordstart++;
|
||||
}
|
||||
while (wordstart != wordend) {
|
||||
*p++ = *wordstart++;
|
||||
}
|
||||
|
||||
if (*wordstart == '.')
|
||||
{
|
||||
wordstart++;
|
||||
}
|
||||
}
|
||||
if (*wordstart == '.') {
|
||||
wordstart++;
|
||||
}
|
||||
}
|
||||
|
||||
*p++ = '\0';
|
||||
*p++ = '\0';
|
||||
|
||||
*offset += (int)(p - start);
|
||||
*offset += (int)(p - start);
|
||||
}
|
||||
|
||||
static void netbuf_add_dnsquery_header(unsigned char *buf, int buflen, int *offset, struct dnsquery_header *header)
|
||||
static void netbuf_add_dnsquery_header(unsigned char *buf,
|
||||
int buflen,
|
||||
int *offset,
|
||||
struct dnsquery_header *header)
|
||||
{
|
||||
unsigned char *p;
|
||||
unsigned char *p;
|
||||
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->id);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->id);
|
||||
|
||||
p = buf + *offset;
|
||||
*p++ = ((header->qr & 0x01) << 7)
|
||||
| ((header->opcode & 0x0F) << 3)
|
||||
| ((header->aa & 0x01) << 2)
|
||||
| ((header->tc & 0x01) << 1)
|
||||
| ((header->rd & 0x01));
|
||||
*p++ = ((header->ra & 0x01) << 7)
|
||||
| ((header->z & 0x07) << 4)
|
||||
| ((header->rcode & 0x0F));
|
||||
*offset += 2;
|
||||
p = buf + *offset;
|
||||
*p++ = ((header->qr & 0x01) << 7) | ((header->opcode & 0x0F) << 3) |
|
||||
((header->aa & 0x01) << 2) | ((header->tc & 0x01) << 1) |
|
||||
((header->rd & 0x01));
|
||||
*p++ = ((header->ra & 0x01) << 7) | ((header->z & 0x07) << 4) |
|
||||
((header->rcode & 0x0F));
|
||||
*offset += 2;
|
||||
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->qdcount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->ancount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->nscount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->arcount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->qdcount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->ancount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->nscount);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, header->arcount);
|
||||
}
|
||||
|
||||
static void netbuf_add_dnsquery_question(unsigned char *buf, int buflen, int *offset, struct dnsquery_question *question)
|
||||
static void netbuf_add_dnsquery_question(unsigned char *buf,
|
||||
int buflen,
|
||||
int *offset,
|
||||
struct dnsquery_question *question)
|
||||
{
|
||||
netbuf_add_domain_name(buf, buflen, offset, question->qname);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, question->qtype);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, question->qclass);
|
||||
netbuf_add_domain_name(buf, buflen, offset, question->qname);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, question->qtype);
|
||||
netbuf_add_16bitnum(buf, buflen, offset, question->qclass);
|
||||
}
|
||||
|
||||
static int resolver_win32_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
static int resolver_win32_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *fulldomain,
|
||||
resolver_srv_rr_t **srv_rr_list)
|
||||
{
|
||||
resolver_srv_rr_t *rr;
|
||||
HINSTANCE hdnsapi = NULL;
|
||||
|
||||
DNS_STATUS (WINAPI * pDnsQuery_A)(PCSTR, WORD, DWORD, PIP4_ARRAY, DNS_RECORDA**, PVOID*);
|
||||
void (WINAPI * pDnsRecordListFree)(DNS_RECORDA*, DNS_FREE_TYPE);
|
||||
DNS_STATUS(WINAPI * pDnsQuery_A)
|
||||
(PCSTR, WORD, DWORD, PIP4_ARRAY, DNS_RECORDA **, PVOID *);
|
||||
void(WINAPI * pDnsRecordListFree)(DNS_RECORDA *, DNS_FREE_TYPE);
|
||||
|
||||
if (hdnsapi = LoadLibrary("dnsapi.dll")) {
|
||||
pDnsQuery_A = (void *)GetProcAddress(hdnsapi, "DnsQuery_A");
|
||||
pDnsRecordListFree = (void *)GetProcAddress(hdnsapi, "DnsRecordListFree");
|
||||
pDnsRecordListFree =
|
||||
(void *)GetProcAddress(hdnsapi, "DnsRecordListFree");
|
||||
|
||||
if (pDnsQuery_A && pDnsRecordListFree) {
|
||||
DNS_RECORDA *dnsrecords = NULL;
|
||||
DNS_STATUS error;
|
||||
|
||||
error = pDnsQuery_A(fulldomain, DNS_TYPE_SRV, DNS_QUERY_STANDARD, NULL, &dnsrecords, NULL);
|
||||
error = pDnsQuery_A(fulldomain, DNS_TYPE_SRV, DNS_QUERY_STANDARD,
|
||||
NULL, &dnsrecords, NULL);
|
||||
|
||||
if (error == 0) {
|
||||
DNS_RECORDA *current = dnsrecords;
|
||||
@@ -704,252 +726,243 @@ static int resolver_win32_srv_lookup(xmpp_ctx_t *ctx, const char *fulldomain,
|
||||
return *srv_rr_list != NULL ? XMPP_DOMAIN_FOUND : XMPP_DOMAIN_NOT_FOUND;
|
||||
}
|
||||
|
||||
static int resolver_win32_srv_query(const char *fulldomain,
|
||||
unsigned char *buf, size_t len)
|
||||
static int
|
||||
resolver_win32_srv_query(const char *fulldomain, unsigned char *buf, size_t len)
|
||||
{
|
||||
int set = 0;
|
||||
int insize = 0;
|
||||
|
||||
/* if dnsapi didn't work/isn't there, try querying the dns server manually */
|
||||
if (!set)
|
||||
{
|
||||
struct dnsquery_header header;
|
||||
struct dnsquery_question question;
|
||||
int offset = 0;
|
||||
int addrlen;
|
||||
sock_t sock;
|
||||
struct sockaddr_in dnsaddr;
|
||||
char dnsserverips[16][256];
|
||||
int numdnsservers = 0;
|
||||
int j;
|
||||
/* if dnsapi didn't work/isn't there, try querying the dns server manually
|
||||
*/
|
||||
if (!set) {
|
||||
struct dnsquery_header header;
|
||||
struct dnsquery_question question;
|
||||
int offset = 0;
|
||||
int addrlen;
|
||||
sock_t sock;
|
||||
struct sockaddr_in dnsaddr;
|
||||
char dnsserverips[16][256];
|
||||
int numdnsservers = 0;
|
||||
int j;
|
||||
|
||||
/* Try getting the DNS server ips from GetNetworkParams() in iphlpapi first */
|
||||
if (!numdnsservers)
|
||||
{
|
||||
HINSTANCE hiphlpapi = NULL;
|
||||
DWORD (WINAPI * pGetNetworkParams)(PFIXED_INFO, PULONG);
|
||||
/* Try getting the DNS server ips from GetNetworkParams() in iphlpapi
|
||||
* first */
|
||||
if (!numdnsservers) {
|
||||
HINSTANCE hiphlpapi = NULL;
|
||||
DWORD(WINAPI * pGetNetworkParams)(PFIXED_INFO, PULONG);
|
||||
|
||||
if (hiphlpapi = LoadLibrary("Iphlpapi.dll"))
|
||||
{
|
||||
pGetNetworkParams = (void *)GetProcAddress(hiphlpapi, "GetNetworkParams");
|
||||
if (hiphlpapi = LoadLibrary("Iphlpapi.dll")) {
|
||||
pGetNetworkParams =
|
||||
(void *)GetProcAddress(hiphlpapi, "GetNetworkParams");
|
||||
|
||||
if (pGetNetworkParams)
|
||||
{
|
||||
FIXED_INFO *fi;
|
||||
ULONG len;
|
||||
DWORD error;
|
||||
char buffer[65535];
|
||||
if (pGetNetworkParams) {
|
||||
FIXED_INFO *fi;
|
||||
ULONG len;
|
||||
DWORD error;
|
||||
char buffer[65535];
|
||||
|
||||
len = 65535;
|
||||
fi = (FIXED_INFO *)buffer;
|
||||
len = 65535;
|
||||
fi = (FIXED_INFO *)buffer;
|
||||
|
||||
if ((error = pGetNetworkParams(fi, &len)) == ERROR_SUCCESS)
|
||||
{
|
||||
IP_ADDR_STRING *pias = &(fi->DnsServerList);
|
||||
if ((error = pGetNetworkParams(fi, &len)) ==
|
||||
ERROR_SUCCESS) {
|
||||
IP_ADDR_STRING *pias = &(fi->DnsServerList);
|
||||
|
||||
while (pias && numdnsservers < 16)
|
||||
{
|
||||
strcpy(dnsserverips[numdnsservers++], pias->IpAddress.String);
|
||||
pias = pias->Next;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
FreeLibrary(hiphlpapi);
|
||||
}
|
||||
while (pias && numdnsservers < 16) {
|
||||
strcpy(dnsserverips[numdnsservers++],
|
||||
pias->IpAddress.String);
|
||||
pias = pias->Next;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
FreeLibrary(hiphlpapi);
|
||||
}
|
||||
|
||||
/* Next, try getting the DNS server ips from the registry */
|
||||
if (!numdnsservers)
|
||||
{
|
||||
HKEY search;
|
||||
LONG error;
|
||||
/* Next, try getting the DNS server ips from the registry */
|
||||
if (!numdnsservers) {
|
||||
HKEY search;
|
||||
LONG error;
|
||||
|
||||
error = RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters", 0, KEY_READ, &search);
|
||||
error = RegOpenKeyEx(
|
||||
HKEY_LOCAL_MACHINE,
|
||||
"SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters", 0,
|
||||
KEY_READ, &search);
|
||||
|
||||
if (error != ERROR_SUCCESS)
|
||||
{
|
||||
error = RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Services\\VxD\\MSTCP", 0, KEY_READ, &search);
|
||||
}
|
||||
if (error != ERROR_SUCCESS) {
|
||||
error = RegOpenKeyEx(
|
||||
HKEY_LOCAL_MACHINE,
|
||||
"SYSTEM\\CurrentControlSet\\Services\\VxD\\MSTCP", 0,
|
||||
KEY_READ, &search);
|
||||
}
|
||||
|
||||
if (error == ERROR_SUCCESS)
|
||||
{
|
||||
char name[512];
|
||||
DWORD len = 512;
|
||||
if (error == ERROR_SUCCESS) {
|
||||
char name[512];
|
||||
DWORD len = 512;
|
||||
|
||||
error = RegQueryValueEx(search, "NameServer", NULL, NULL, (LPBYTE)name, &len);
|
||||
error = RegQueryValueEx(search, "NameServer", NULL, NULL,
|
||||
(LPBYTE)name, &len);
|
||||
|
||||
if (error != ERROR_SUCCESS)
|
||||
{
|
||||
error = RegQueryValueEx(search, "DhcpNameServer", NULL, NULL, (LPBYTE)name, &len);
|
||||
}
|
||||
if (error != ERROR_SUCCESS) {
|
||||
error = RegQueryValueEx(search, "DhcpNameServer", NULL,
|
||||
NULL, (LPBYTE)name, &len);
|
||||
}
|
||||
|
||||
if (error == ERROR_SUCCESS)
|
||||
{
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
if (error == ERROR_SUCCESS) {
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
|
||||
while (*start && numdnsservers < 16)
|
||||
{
|
||||
while (strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*start && numdnsservers < 16) {
|
||||
while (strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
strncpy(dnsserverips[numdnsservers++], start, end - start);
|
||||
strncpy(dnsserverips[numdnsservers++], start,
|
||||
end - start);
|
||||
|
||||
while (*end && !strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*end && !strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
start = end;
|
||||
}
|
||||
}
|
||||
}
|
||||
start = end;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RegCloseKey(search);
|
||||
}
|
||||
RegCloseKey(search);
|
||||
}
|
||||
|
||||
if (!numdnsservers)
|
||||
{
|
||||
HKEY searchlist;
|
||||
LONG error;
|
||||
if (!numdnsservers) {
|
||||
HKEY searchlist;
|
||||
LONG error;
|
||||
|
||||
error = RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces", 0, KEY_READ, &searchlist);
|
||||
error = RegOpenKeyEx(HKEY_LOCAL_MACHINE,
|
||||
"SYSTEM\\CurrentControlSet\\Services\\Tcpip\\P"
|
||||
"arameters\\Interfaces",
|
||||
0, KEY_READ, &searchlist);
|
||||
|
||||
if (error == ERROR_SUCCESS)
|
||||
{
|
||||
unsigned int i;
|
||||
DWORD numinterfaces = 0;
|
||||
if (error == ERROR_SUCCESS) {
|
||||
unsigned int i;
|
||||
DWORD numinterfaces = 0;
|
||||
|
||||
RegQueryInfoKey(searchlist, NULL, NULL, NULL, &numinterfaces, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
|
||||
RegQueryInfoKey(searchlist, NULL, NULL, NULL, &numinterfaces,
|
||||
NULL, NULL, NULL, NULL, NULL, NULL, NULL);
|
||||
|
||||
for (i = 0; i < numinterfaces; i++)
|
||||
{
|
||||
char name[512];
|
||||
DWORD len = 512;
|
||||
HKEY searchentry;
|
||||
for (i = 0; i < numinterfaces; i++) {
|
||||
char name[512];
|
||||
DWORD len = 512;
|
||||
HKEY searchentry;
|
||||
|
||||
RegEnumKeyEx(searchlist, i, (LPTSTR)name, &len, NULL, NULL, NULL, NULL);
|
||||
RegEnumKeyEx(searchlist, i, (LPTSTR)name, &len, NULL, NULL,
|
||||
NULL, NULL);
|
||||
|
||||
if (RegOpenKeyEx(searchlist, name, 0, KEY_READ, &searchentry) == ERROR_SUCCESS)
|
||||
{
|
||||
if (RegQueryValueEx(searchentry, "DhcpNameServer", NULL, NULL, (LPBYTE)name, &len) == ERROR_SUCCESS)
|
||||
{
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
if (RegOpenKeyEx(searchlist, name, 0, KEY_READ,
|
||||
&searchentry) == ERROR_SUCCESS) {
|
||||
if (RegQueryValueEx(searchentry, "DhcpNameServer", NULL,
|
||||
NULL, (LPBYTE)name,
|
||||
&len) == ERROR_SUCCESS) {
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
|
||||
while (*start && numdnsservers < 16)
|
||||
{
|
||||
while (strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*start && numdnsservers < 16) {
|
||||
while (strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
strncpy(dnsserverips[numdnsservers++], start, end - start);
|
||||
strncpy(dnsserverips[numdnsservers++], start,
|
||||
end - start);
|
||||
|
||||
while (*end && !strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*end && !strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
start = end;
|
||||
}
|
||||
}
|
||||
else if (RegQueryValueEx(searchentry, "NameServer", NULL, NULL, (LPBYTE)name, &len) == ERROR_SUCCESS)
|
||||
{
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
start = end;
|
||||
}
|
||||
} else if (RegQueryValueEx(searchentry, "NameServer",
|
||||
NULL, NULL, (LPBYTE)name,
|
||||
&len) == ERROR_SUCCESS) {
|
||||
char *parse = "0123456789.", *start, *end;
|
||||
start = name;
|
||||
end = name;
|
||||
name[len] = '\0';
|
||||
|
||||
while (*start && numdnsservers < 16)
|
||||
{
|
||||
while (strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*start && numdnsservers < 16) {
|
||||
while (strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
strncpy(dnsserverips[numdnsservers++], start, end - start);
|
||||
strncpy(dnsserverips[numdnsservers++], start,
|
||||
end - start);
|
||||
|
||||
while (*end && !strchr(parse, *end))
|
||||
{
|
||||
end++;
|
||||
}
|
||||
while (*end && !strchr(parse, *end)) {
|
||||
end++;
|
||||
}
|
||||
|
||||
start = end;
|
||||
}
|
||||
}
|
||||
RegCloseKey(searchentry);
|
||||
}
|
||||
}
|
||||
RegCloseKey(searchlist);
|
||||
}
|
||||
}
|
||||
start = end;
|
||||
}
|
||||
}
|
||||
RegCloseKey(searchentry);
|
||||
}
|
||||
}
|
||||
RegCloseKey(searchlist);
|
||||
}
|
||||
}
|
||||
|
||||
/* If we have a DNS server, use it */
|
||||
if (numdnsservers)
|
||||
{
|
||||
ULONG nonblocking = 1;
|
||||
int i;
|
||||
/* If we have a DNS server, use it */
|
||||
if (numdnsservers) {
|
||||
ULONG nonblocking = 1;
|
||||
int i;
|
||||
|
||||
memset(&header, 0, sizeof(header));
|
||||
header.id = 12345; /* FIXME: Get a better id here */
|
||||
header.rd = 1;
|
||||
header.qdcount = 1;
|
||||
memset(&header, 0, sizeof(header));
|
||||
header.id = 12345; /* FIXME: Get a better id here */
|
||||
header.rd = 1;
|
||||
header.qdcount = 1;
|
||||
|
||||
netbuf_add_dnsquery_header(buf, (int)len, &offset, &header);
|
||||
netbuf_add_dnsquery_header(buf, (int)len, &offset, &header);
|
||||
|
||||
memset(&question, 0, sizeof(question));
|
||||
strncpy(question.qname, fulldomain, 1024);
|
||||
question.qtype = 33; /* SRV */
|
||||
question.qclass = 1; /* INTERNET! */
|
||||
memset(&question, 0, sizeof(question));
|
||||
strncpy(question.qname, fulldomain, 1024);
|
||||
question.qtype = 33; /* SRV */
|
||||
question.qclass = 1; /* INTERNET! */
|
||||
|
||||
netbuf_add_dnsquery_question(buf, (int)len, &offset, &question);
|
||||
netbuf_add_dnsquery_question(buf, (int)len, &offset, &question);
|
||||
|
||||
insize = 0;
|
||||
for (i = 0; i < numdnsservers && insize <= 0; i++)
|
||||
{
|
||||
sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
|
||||
ioctlsocket(sock, FIONBIO, &nonblocking);
|
||||
insize = 0;
|
||||
for (i = 0; i < numdnsservers && insize <= 0; i++) {
|
||||
sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
|
||||
ioctlsocket(sock, FIONBIO, &nonblocking);
|
||||
|
||||
memset(&dnsaddr, 0, sizeof(dnsaddr));
|
||||
memset(&dnsaddr, 0, sizeof(dnsaddr));
|
||||
|
||||
dnsaddr.sin_family = AF_INET;
|
||||
dnsaddr.sin_port = htons(53);
|
||||
dnsaddr.sin_addr.s_addr = inet_addr(dnsserverips[i]);
|
||||
dnsaddr.sin_family = AF_INET;
|
||||
dnsaddr.sin_port = htons(53);
|
||||
dnsaddr.sin_addr.s_addr = inet_addr(dnsserverips[i]);
|
||||
|
||||
addrlen = sizeof(dnsaddr);
|
||||
sendto(sock, (char *)buf, offset, 0, (struct sockaddr *)&dnsaddr, addrlen);
|
||||
for (j = 0; j < 50; j++)
|
||||
{
|
||||
insize = recvfrom(sock, (char *)buf, (int)len, 0, (struct sockaddr *)&dnsaddr, &addrlen);
|
||||
if (insize == SOCKET_ERROR)
|
||||
{
|
||||
if (sock_error() == WSAEWOULDBLOCK)
|
||||
{
|
||||
Sleep(100);
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
closesocket(sock);
|
||||
}
|
||||
set = insize > 0;
|
||||
}
|
||||
addrlen = sizeof(dnsaddr);
|
||||
sendto(sock, (char *)buf, offset, 0,
|
||||
(struct sockaddr *)&dnsaddr, addrlen);
|
||||
for (j = 0; j < 50; j++) {
|
||||
insize = recvfrom(sock, (char *)buf, (int)len, 0,
|
||||
(struct sockaddr *)&dnsaddr, &addrlen);
|
||||
if (insize == SOCKET_ERROR) {
|
||||
if (sock_error() == WSAEWOULDBLOCK) {
|
||||
Sleep(100);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
closesocket(sock);
|
||||
}
|
||||
set = insize > 0;
|
||||
}
|
||||
}
|
||||
|
||||
return set ? insize : -1;
|
||||
|
||||
@@ -46,8 +46,10 @@ void resolver_shutdown(void);
|
||||
*
|
||||
* @return XMPP_DOMAIN_FOUND on success or XMPP_DOMAIN_NOT_FOUND on fail
|
||||
*/
|
||||
int resolver_srv_lookup_buf(xmpp_ctx_t *ctx, const unsigned char *buf,
|
||||
size_t len, resolver_srv_rr_t **srv_rr_list);
|
||||
int resolver_srv_lookup_buf(xmpp_ctx_t *ctx,
|
||||
const unsigned char *buf,
|
||||
size_t len,
|
||||
resolver_srv_rr_t **srv_rr_list);
|
||||
/** Resolve SRV record.
|
||||
*
|
||||
* @param ctx a Strophe context object
|
||||
@@ -58,8 +60,11 @@ int resolver_srv_lookup_buf(xmpp_ctx_t *ctx, const unsigned char *buf,
|
||||
*
|
||||
* @return XMPP_DOMAIN_FOUND on success or XMPP_DOMAIN_NOT_FOUND on fail
|
||||
*/
|
||||
int resolver_srv_lookup(xmpp_ctx_t *ctx, const char *service, const char *proto,
|
||||
const char *domain, resolver_srv_rr_t **srv_rr_list);
|
||||
int resolver_srv_lookup(xmpp_ctx_t *ctx,
|
||||
const char *service,
|
||||
const char *proto,
|
||||
const char *domain,
|
||||
resolver_srv_rr_t **srv_rr_list);
|
||||
|
||||
/** Release a list returned by resolver_srv_lookup() or
|
||||
* resolver_srv_lookup_buf().
|
||||
|
||||
221
src/sasl.c
221
src/sasl.c
@@ -29,16 +29,16 @@
|
||||
/* strtok_s() has appeared in visual studio 2005.
|
||||
Use own implementation for older versions. */
|
||||
#ifdef _MSC_VER
|
||||
# if (_MSC_VER >= 1400)
|
||||
# define strtok_r strtok_s
|
||||
# else
|
||||
# define strtok_r xmpp_strtok_r
|
||||
# endif
|
||||
#if (_MSC_VER >= 1400)
|
||||
#define strtok_r strtok_s
|
||||
#else
|
||||
#define strtok_r xmpp_strtok_r
|
||||
#endif
|
||||
#endif /* _MSC_VER */
|
||||
|
||||
|
||||
/** generate authentication string for the SASL PLAIN mechanism */
|
||||
char *sasl_plain(xmpp_ctx_t *ctx, const char *authid, const char *password) {
|
||||
char *sasl_plain(xmpp_ctx_t *ctx, const char *authid, const char *password)
|
||||
{
|
||||
size_t idlen, passlen;
|
||||
size_t msglen;
|
||||
char *result = NULL;
|
||||
@@ -52,12 +52,12 @@ char *sasl_plain(xmpp_ctx_t *ctx, const char *authid, const char *password) {
|
||||
msglen = 2 + idlen + passlen;
|
||||
msg = xmpp_alloc(ctx, msglen);
|
||||
if (msg != NULL) {
|
||||
msg[0] = '\0';
|
||||
memcpy(msg+1, authid, idlen);
|
||||
msg[1+idlen] = '\0';
|
||||
memcpy(msg+1+idlen+1, password, passlen);
|
||||
result = xmpp_base64_encode(ctx, (unsigned char *)msg, msglen);
|
||||
xmpp_free(ctx, msg);
|
||||
msg[0] = '\0';
|
||||
memcpy(msg + 1, authid, idlen);
|
||||
msg[1 + idlen] = '\0';
|
||||
memcpy(msg + 1 + idlen + 1, password, passlen);
|
||||
result = xmpp_base64_encode(ctx, (unsigned char *)msg, msglen);
|
||||
xmpp_free(ctx, msg);
|
||||
}
|
||||
|
||||
return result;
|
||||
@@ -72,8 +72,8 @@ static char *_make_string(xmpp_ctx_t *ctx, const char *s, const unsigned len)
|
||||
|
||||
result = xmpp_alloc(ctx, len + 1);
|
||||
if (result != NULL) {
|
||||
memcpy(result, s, len);
|
||||
result[len] = '\0';
|
||||
memcpy(result, s, len);
|
||||
result[len] = '\0';
|
||||
}
|
||||
return result;
|
||||
}
|
||||
@@ -86,10 +86,10 @@ static char *_make_quoted(xmpp_ctx_t *ctx, const char *s)
|
||||
|
||||
result = xmpp_alloc(ctx, len + 3);
|
||||
if (result != NULL) {
|
||||
result[0] = '"';
|
||||
memcpy(result+1, s, len);
|
||||
result[len+1] = '"';
|
||||
result[len+2] = '\0';
|
||||
result[0] = '"';
|
||||
memcpy(result + 1, s, len);
|
||||
result[len + 1] = '"';
|
||||
result[len + 2] = '\0';
|
||||
}
|
||||
return result;
|
||||
}
|
||||
@@ -104,51 +104,56 @@ static hash_t *_parse_digest_challenge(xmpp_ctx_t *ctx, const char *msg)
|
||||
|
||||
text = (unsigned char *)xmpp_base64_decode_str(ctx, msg, strlen(msg));
|
||||
if (text == NULL) {
|
||||
xmpp_error(ctx, "SASL", "couldn't Base64 decode challenge!");
|
||||
return NULL;
|
||||
xmpp_error(ctx, "SASL", "couldn't Base64 decode challenge!");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
result = hash_new(ctx, 10, xmpp_free);
|
||||
if (result != NULL) {
|
||||
s = text;
|
||||
while (*s != '\0') {
|
||||
/* skip any leading commas and spaces */
|
||||
while ((*s == ',') || (*s == ' ')) s++;
|
||||
/* accumulate a key ending at '=' */
|
||||
t = s;
|
||||
while ((*t != '=') && (*t != '\0')) t++;
|
||||
if (*t == '\0') break; /* bad string */
|
||||
key = _make_string(ctx, (char *)s, (t-s));
|
||||
if (key == NULL) break;
|
||||
s = text;
|
||||
while (*s != '\0') {
|
||||
/* skip any leading commas and spaces */
|
||||
while ((*s == ',') || (*s == ' '))
|
||||
s++;
|
||||
/* accumulate a key ending at '=' */
|
||||
t = s;
|
||||
while ((*t != '=') && (*t != '\0'))
|
||||
t++;
|
||||
if (*t == '\0')
|
||||
break; /* bad string */
|
||||
key = _make_string(ctx, (char *)s, (t - s));
|
||||
if (key == NULL)
|
||||
break;
|
||||
/* advance our start pointer past the key */
|
||||
s = t + 1;
|
||||
t = s;
|
||||
/* if we see quotes, grab the string in between */
|
||||
if ((*s == '\'') || (*s == '"')) {
|
||||
t++;
|
||||
while ((*t != *s) && (*t != '\0'))
|
||||
t++;
|
||||
value = _make_string(ctx, (char *)s+1, (t-s-1));
|
||||
if (*t == *s) {
|
||||
s = t + 1;
|
||||
} else {
|
||||
s = t;
|
||||
}
|
||||
/* otherwise, accumulate a value ending in ',' or '\0' */
|
||||
} else {
|
||||
while ((*t != ',') && (*t != '\0')) t++;
|
||||
value = _make_string(ctx, (char *)s, (t-s));
|
||||
s = t;
|
||||
}
|
||||
if (value == NULL) {
|
||||
xmpp_free(ctx, key);
|
||||
break;
|
||||
}
|
||||
/* TODO: check for collisions per spec */
|
||||
hash_add(result, key, value);
|
||||
/* hash table now owns the value, free the key */
|
||||
xmpp_free(ctx, key);
|
||||
}
|
||||
s = t + 1;
|
||||
t = s;
|
||||
/* if we see quotes, grab the string in between */
|
||||
if ((*s == '\'') || (*s == '"')) {
|
||||
t++;
|
||||
while ((*t != *s) && (*t != '\0'))
|
||||
t++;
|
||||
value = _make_string(ctx, (char *)s + 1, (t - s - 1));
|
||||
if (*t == *s) {
|
||||
s = t + 1;
|
||||
} else {
|
||||
s = t;
|
||||
}
|
||||
/* otherwise, accumulate a value ending in ',' or '\0' */
|
||||
} else {
|
||||
while ((*t != ',') && (*t != '\0'))
|
||||
t++;
|
||||
value = _make_string(ctx, (char *)s, (t - s));
|
||||
s = t;
|
||||
}
|
||||
if (value == NULL) {
|
||||
xmpp_free(ctx, key);
|
||||
break;
|
||||
}
|
||||
/* TODO: check for collisions per spec */
|
||||
hash_add(result, key, value);
|
||||
/* hash table now owns the value, free the key */
|
||||
xmpp_free(ctx, key);
|
||||
}
|
||||
}
|
||||
xmpp_free(ctx, text);
|
||||
|
||||
@@ -162,63 +167,75 @@ static void _digest_to_hex(const char *digest, char *hex)
|
||||
const char hexdigit[] = "0123456789abcdef";
|
||||
|
||||
for (i = 0; i < 16; i++) {
|
||||
*hex++ = hexdigit[ (digest[i] >> 4) & 0x0F ];
|
||||
*hex++ = hexdigit[ digest[i] & 0x0F ];
|
||||
*hex++ = hexdigit[(digest[i] >> 4) & 0x0F];
|
||||
*hex++ = hexdigit[digest[i] & 0x0F];
|
||||
}
|
||||
}
|
||||
|
||||
/** append 'key="value"' to a buffer, growing as necessary */
|
||||
static char *_add_key(xmpp_ctx_t *ctx, hash_t *table, const char *key,
|
||||
char *buf, int *len, int quote)
|
||||
static char *_add_key(xmpp_ctx_t *ctx,
|
||||
hash_t *table,
|
||||
const char *key,
|
||||
char *buf,
|
||||
int *len,
|
||||
int quote)
|
||||
{
|
||||
int olen,nlen;
|
||||
int olen, nlen;
|
||||
int keylen, valuelen;
|
||||
const char *value, *qvalue;
|
||||
char *c;
|
||||
|
||||
/* allocate a zero-length string if necessary */
|
||||
if (buf == NULL) {
|
||||
buf = xmpp_alloc(ctx, 1);
|
||||
buf[0] = '\0';
|
||||
buf = xmpp_alloc(ctx, 1);
|
||||
buf[0] = '\0';
|
||||
}
|
||||
if (buf == NULL) return NULL;
|
||||
if (buf == NULL)
|
||||
return NULL;
|
||||
|
||||
/* get current string length */
|
||||
olen = strlen(buf);
|
||||
value = hash_get(table, key);
|
||||
if (value == NULL) {
|
||||
xmpp_error(ctx, "SASL", "couldn't retrieve value for '%s'", key);
|
||||
value = "";
|
||||
xmpp_error(ctx, "SASL", "couldn't retrieve value for '%s'", key);
|
||||
value = "";
|
||||
}
|
||||
if (quote) {
|
||||
qvalue = _make_quoted(ctx, value);
|
||||
qvalue = _make_quoted(ctx, value);
|
||||
} else {
|
||||
qvalue = value;
|
||||
qvalue = value;
|
||||
}
|
||||
/* added length is key + '=' + value */
|
||||
/* (+ ',' if we're not the first entry */
|
||||
keylen = strlen(key);
|
||||
valuelen = strlen(qvalue);
|
||||
nlen = (olen ? 1 : 0) + keylen + 1 + valuelen + 1;
|
||||
buf = xmpp_realloc(ctx, buf, olen+nlen);
|
||||
buf = xmpp_realloc(ctx, buf, olen + nlen);
|
||||
|
||||
if (buf != NULL) {
|
||||
c = buf + olen;
|
||||
if (olen) *c++ = ',';
|
||||
memcpy(c, key, keylen); c += keylen;
|
||||
*c++ = '=';
|
||||
memcpy(c, qvalue, valuelen); c += valuelen;
|
||||
*c++ = '\0';
|
||||
c = buf + olen;
|
||||
if (olen)
|
||||
*c++ = ',';
|
||||
memcpy(c, key, keylen);
|
||||
c += keylen;
|
||||
*c++ = '=';
|
||||
memcpy(c, qvalue, valuelen);
|
||||
c += valuelen;
|
||||
*c++ = '\0';
|
||||
}
|
||||
|
||||
if (quote) xmpp_free(ctx, (char *)qvalue);
|
||||
if (quote)
|
||||
xmpp_free(ctx, (char *)qvalue);
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
/** generate auth response string for the SASL DIGEST-MD5 mechanism */
|
||||
char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
const char *jid, const char *password) {
|
||||
char *sasl_digest_md5(xmpp_ctx_t *ctx,
|
||||
const char *challenge,
|
||||
const char *jid,
|
||||
const char *password)
|
||||
{
|
||||
hash_t *table;
|
||||
char *result = NULL;
|
||||
char *node, *domain, *realm;
|
||||
@@ -231,21 +248,21 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
char cnonce[13];
|
||||
|
||||
/* our digest response is
|
||||
Hex( KD( HEX(MD5(A1)),
|
||||
nonce ':' nc ':' cnonce ':' qop ':' HEX(MD5(A2))
|
||||
))
|
||||
Hex( KD( HEX(MD5(A1)),
|
||||
nonce ':' nc ':' cnonce ':' qop ':' HEX(MD5(A2))
|
||||
))
|
||||
|
||||
where KD(k, s) = MD5(k ':' s),
|
||||
A1 = MD5( node ':' realm ':' password ) ':' nonce ':' cnonce
|
||||
A2 = "AUTHENTICATE" ':' "xmpp/" domain
|
||||
A1 = MD5( node ':' realm ':' password ) ':' nonce ':' cnonce
|
||||
A2 = "AUTHENTICATE" ':' "xmpp/" domain
|
||||
|
||||
If there is an authzid it is ':'-appended to A1 */
|
||||
|
||||
/* parse the challenge */
|
||||
table = _parse_digest_challenge(ctx, challenge);
|
||||
if (table == NULL) {
|
||||
xmpp_error(ctx, "SASL", "couldn't parse digest challenge");
|
||||
return NULL;
|
||||
xmpp_error(ctx, "SASL", "couldn't parse digest challenge");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
node = xmpp_jid_node(ctx, jid);
|
||||
@@ -255,8 +272,8 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
server */
|
||||
realm = hash_get(table, "realm");
|
||||
if (realm == NULL || strlen(realm) == 0) {
|
||||
hash_add(table, "realm", xmpp_strdup(ctx, domain));
|
||||
realm = hash_get(table, "realm");
|
||||
hash_add(table, "realm", xmpp_strdup(ctx, domain));
|
||||
realm = hash_get(table, "realm");
|
||||
}
|
||||
|
||||
/* add our response fields */
|
||||
@@ -268,8 +285,8 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
hash_add(table, "qop", xmpp_strdup(ctx, "auth"));
|
||||
value = xmpp_alloc(ctx, 5 + strlen(domain) + 1);
|
||||
memcpy(value, "xmpp/", 5);
|
||||
memcpy(value+5, domain, strlen(domain));
|
||||
value[5+strlen(domain)] = '\0';
|
||||
memcpy(value + 5, domain, strlen(domain));
|
||||
value[5 + strlen(domain)] = '\0';
|
||||
hash_add(table, "digest-uri", value);
|
||||
|
||||
/* generate response */
|
||||
@@ -304,8 +321,8 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
value = hash_get(table, "digest-uri");
|
||||
MD5Update(&MD5, (unsigned char *)value, strlen(value));
|
||||
if (strcmp(hash_get(table, "qop"), "auth") != 0) {
|
||||
MD5Update(&MD5, (unsigned char *)":00000000000000000000000000000000",
|
||||
33);
|
||||
MD5Update(&MD5, (unsigned char *)":00000000000000000000000000000000",
|
||||
33);
|
||||
}
|
||||
MD5Final(digest, &MD5);
|
||||
|
||||
@@ -332,7 +349,7 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
MD5Update(&MD5, (unsigned char *)hex, 32);
|
||||
MD5Final(digest, &MD5);
|
||||
|
||||
response = xmpp_alloc(ctx, 32+1);
|
||||
response = xmpp_alloc(ctx, 32 + 1);
|
||||
_digest_to_hex((char *)digest, hex);
|
||||
memcpy(response, hex, 32);
|
||||
response[32] = '\0';
|
||||
@@ -363,8 +380,10 @@ char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
}
|
||||
|
||||
/** generate auth response string for the SASL SCRAM-SHA-1 mechanism */
|
||||
char *sasl_scram_sha1(xmpp_ctx_t *ctx, const char *challenge,
|
||||
const char *first_bare, const char *jid,
|
||||
char *sasl_scram_sha1(xmpp_ctx_t *ctx,
|
||||
const char *challenge,
|
||||
const char *first_bare,
|
||||
const char *jid,
|
||||
const char *password)
|
||||
{
|
||||
uint8_t key[SHA1_DIGEST_SIZE];
|
||||
@@ -430,8 +449,8 @@ char *sasl_scram_sha1(xmpp_ctx_t *ctx, const char *challenge,
|
||||
xmpp_snprintf(auth, auth_len, "%s,%s,%s", first_bare + 3, challenge,
|
||||
response);
|
||||
|
||||
SCRAM_SHA1_ClientKey((uint8_t *)password, strlen(password),
|
||||
(uint8_t *)sval, sval_len, (uint32_t)ival, key);
|
||||
SCRAM_SHA1_ClientKey((uint8_t *)password, strlen(password), (uint8_t *)sval,
|
||||
sval_len, (uint32_t)ival, key);
|
||||
SCRAM_SHA1_ClientSignature(key, (uint8_t *)auth, strlen(auth), sign);
|
||||
for (j = 0; j < SHA1_DIGEST_SIZE; j++) {
|
||||
sign[j] ^= key[j];
|
||||
@@ -450,8 +469,8 @@ char *sasl_scram_sha1(xmpp_ctx_t *ctx, const char *challenge,
|
||||
strcat(response, sign_b64);
|
||||
xmpp_free(ctx, sign_b64);
|
||||
|
||||
response_b64 = xmpp_base64_encode(ctx, (unsigned char *)response,
|
||||
strlen(response));
|
||||
response_b64 =
|
||||
xmpp_base64_encode(ctx, (unsigned char *)response, strlen(response));
|
||||
if (!response_b64) {
|
||||
goto out_response;
|
||||
}
|
||||
|
||||
16
src/sasl.h
16
src/sasl.h
@@ -1,7 +1,7 @@
|
||||
/* sasl.h
|
||||
** strophe XMPP client library -- SASL authentication helpers
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
@@ -21,10 +21,14 @@
|
||||
/** low-level sasl routines */
|
||||
|
||||
char *sasl_plain(xmpp_ctx_t *ctx, const char *authid, const char *password);
|
||||
char *sasl_digest_md5(xmpp_ctx_t *ctx, const char *challenge,
|
||||
const char *jid, const char *password);
|
||||
char *sasl_scram_sha1(xmpp_ctx_t *ctx, const char *challenge,
|
||||
const char *first_bare, const char *jid,
|
||||
char *sasl_digest_md5(xmpp_ctx_t *ctx,
|
||||
const char *challenge,
|
||||
const char *jid,
|
||||
const char *password);
|
||||
char *sasl_scram_sha1(xmpp_ctx_t *ctx,
|
||||
const char *challenge,
|
||||
const char *first_bare,
|
||||
const char *jid,
|
||||
const char *password);
|
||||
|
||||
#endif /* _LIBXMPP_SASL_H__ */
|
||||
|
||||
25
src/scram.c
25
src/scram.c
@@ -29,8 +29,10 @@
|
||||
static const uint8_t ipad = 0x36;
|
||||
static const uint8_t opad = 0x5C;
|
||||
|
||||
static void crypto_HMAC_SHA1(const uint8_t *key, size_t key_len,
|
||||
const uint8_t *text, size_t len,
|
||||
static void crypto_HMAC_SHA1(const uint8_t *key,
|
||||
size_t key_len,
|
||||
const uint8_t *text,
|
||||
size_t len,
|
||||
uint8_t *digest)
|
||||
{
|
||||
uint8_t key_pad[HMAC_BLOCK_SIZE];
|
||||
@@ -64,11 +66,14 @@ static void crypto_HMAC_SHA1(const uint8_t *key, size_t key_len,
|
||||
crypto_SHA1_Final(&ctx, digest);
|
||||
}
|
||||
|
||||
static void SCRAM_SHA1_Hi(const uint8_t *text, size_t len,
|
||||
const uint8_t *salt, size_t salt_len, uint32_t i,
|
||||
static void SCRAM_SHA1_Hi(const uint8_t *text,
|
||||
size_t len,
|
||||
const uint8_t *salt,
|
||||
size_t salt_len,
|
||||
uint32_t i,
|
||||
uint8_t *digest)
|
||||
{
|
||||
int k;
|
||||
int k;
|
||||
uint32_t j;
|
||||
uint8_t tmp[128];
|
||||
|
||||
@@ -97,8 +102,11 @@ static void SCRAM_SHA1_Hi(const uint8_t *text, size_t len,
|
||||
}
|
||||
}
|
||||
|
||||
void SCRAM_SHA1_ClientKey(const uint8_t *password, size_t len,
|
||||
const uint8_t *salt, size_t salt_len, uint32_t i,
|
||||
void SCRAM_SHA1_ClientKey(const uint8_t *password,
|
||||
size_t len,
|
||||
const uint8_t *salt,
|
||||
size_t salt_len,
|
||||
uint32_t i,
|
||||
uint8_t *key)
|
||||
{
|
||||
uint8_t salted[SHA1_DIGEST_SIZE];
|
||||
@@ -111,7 +119,8 @@ void SCRAM_SHA1_ClientKey(const uint8_t *password, size_t len,
|
||||
}
|
||||
|
||||
void SCRAM_SHA1_ClientSignature(const uint8_t *ClientKey,
|
||||
const uint8_t *AuthMessage, size_t len,
|
||||
const uint8_t *AuthMessage,
|
||||
size_t len,
|
||||
uint8_t *sign)
|
||||
{
|
||||
uint8_t stored[SHA1_DIGEST_SIZE];
|
||||
|
||||
10
src/scram.h
10
src/scram.h
@@ -21,12 +21,16 @@
|
||||
|
||||
#include "sha1.h"
|
||||
|
||||
void SCRAM_SHA1_ClientKey(const uint8_t *password, size_t len,
|
||||
const uint8_t *salt, size_t salt_len, uint32_t i,
|
||||
void SCRAM_SHA1_ClientKey(const uint8_t *password,
|
||||
size_t len,
|
||||
const uint8_t *salt,
|
||||
size_t salt_len,
|
||||
uint32_t i,
|
||||
uint8_t *key);
|
||||
|
||||
void SCRAM_SHA1_ClientSignature(const uint8_t *ClientKey,
|
||||
const uint8_t *AuthMessage, size_t len,
|
||||
const uint8_t *AuthMessage,
|
||||
size_t len,
|
||||
uint8_t *sign);
|
||||
|
||||
void SCRAM_SHA1_ClientProof(const uint8_t *ClientKey,
|
||||
|
||||
90
src/sha1.c
90
src/sha1.c
@@ -14,10 +14,10 @@ Still 100% Public Domain
|
||||
|
||||
Corrected a problem which generated improper hash values on 16 bit machines
|
||||
Routine SHA1Update changed from
|
||||
void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned int
|
||||
void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned int
|
||||
len)
|
||||
to
|
||||
void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned
|
||||
void SHA1Update(SHA1_CTX* context, unsigned char* data, unsigned
|
||||
long len)
|
||||
|
||||
The 'len' parameter was declared an int which works fine on 32 bit machines.
|
||||
@@ -86,27 +86,38 @@ static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64]);
|
||||
/* blk0() and blk() perform the initial expand. */
|
||||
/* I got the idea of expanding during the round function from SSLeay */
|
||||
#define blk0(i) (block->l[i] = host_to_be(block->l[i]))
|
||||
#define blk(i) (block->l[i&15] = rol(block->l[(i+13)&15]^block->l[(i+8)&15] \
|
||||
^block->l[(i+2)&15]^block->l[i&15],1))
|
||||
#define blk(i) \
|
||||
(block->l[i & 15] = rol(block->l[(i + 13) & 15] ^ block->l[(i + 8) & 15] ^ \
|
||||
block->l[(i + 2) & 15] ^ block->l[i & 15], \
|
||||
1))
|
||||
|
||||
/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */
|
||||
#define R0(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk0(i)+0x5A827999+rol(v,5);w=rol(w,30);
|
||||
#define R1(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk(i)+0x5A827999+rol(v,5);w=rol(w,30);
|
||||
#define R2(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0x6ED9EBA1+rol(v,5);w=rol(w,30);
|
||||
#define R3(v,w,x,y,z,i) z+=(((w|x)&y)|(w&x))+blk(i)+0x8F1BBCDC+rol(v,5);w=rol(w,30);
|
||||
#define R4(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0xCA62C1D6+rol(v,5);w=rol(w,30);
|
||||
|
||||
#define R0(v, w, x, y, z, i) \
|
||||
z += ((w & (x ^ y)) ^ y) + blk0(i) + 0x5A827999 + rol(v, 5); \
|
||||
w = rol(w, 30);
|
||||
#define R1(v, w, x, y, z, i) \
|
||||
z += ((w & (x ^ y)) ^ y) + blk(i) + 0x5A827999 + rol(v, 5); \
|
||||
w = rol(w, 30);
|
||||
#define R2(v, w, x, y, z, i) \
|
||||
z += (w ^ x ^ y) + blk(i) + 0x6ED9EBA1 + rol(v, 5); \
|
||||
w = rol(w, 30);
|
||||
#define R3(v, w, x, y, z, i) \
|
||||
z += (((w | x) & y) | (w & x)) + blk(i) + 0x8F1BBCDC + rol(v, 5); \
|
||||
w = rol(w, 30);
|
||||
#define R4(v, w, x, y, z, i) \
|
||||
z += (w ^ x ^ y) + blk(i) + 0xCA62C1D6 + rol(v, 5); \
|
||||
w = rol(w, 30);
|
||||
|
||||
static uint32_t host_to_be(uint32_t i)
|
||||
{
|
||||
#define le_to_be(i) ((rol((i),24) & 0xFF00FF00) | (rol((i),8) & 0x00FF00FF))
|
||||
#if defined(__BIG_ENDIAN__) || \
|
||||
#define le_to_be(i) ((rol((i), 24) & 0xFF00FF00) | (rol((i), 8) & 0x00FF00FF))
|
||||
#if defined(__BIG_ENDIAN__) || \
|
||||
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && \
|
||||
__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
|
||||
__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
|
||||
return i;
|
||||
#elif defined(__LITTLE_ENDIAN__) || \
|
||||
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && \
|
||||
__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)
|
||||
#elif defined(__LITTLE_ENDIAN__) || \
|
||||
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && \
|
||||
__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)
|
||||
return le_to_be(i);
|
||||
#else /* fallback to run-time check */
|
||||
static const union {
|
||||
@@ -126,14 +137,14 @@ static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64])
|
||||
uint8_t c[64];
|
||||
uint32_t l[16];
|
||||
} CHAR64LONG16;
|
||||
CHAR64LONG16* block;
|
||||
CHAR64LONG16 *block;
|
||||
|
||||
#ifdef SHA1HANDSOFF
|
||||
static uint8_t workspace[64];
|
||||
block = (CHAR64LONG16*)workspace;
|
||||
block = (CHAR64LONG16 *)workspace;
|
||||
memcpy(block, buffer, 64);
|
||||
#else
|
||||
block = (CHAR64LONG16*)buffer;
|
||||
block = (CHAR64LONG16 *)buffer;
|
||||
#endif
|
||||
|
||||
/* Copy context->state[] to working vars */
|
||||
@@ -144,6 +155,7 @@ static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64])
|
||||
e = state[4];
|
||||
|
||||
/* 4 rounds of 20 operations each. Loop unrolled. */
|
||||
/* clang-format off */
|
||||
R0(a,b,c,d,e, 0); R0(e,a,b,c,d, 1); R0(d,e,a,b,c, 2); R0(c,d,e,a,b, 3);
|
||||
R0(b,c,d,e,a, 4); R0(a,b,c,d,e, 5); R0(e,a,b,c,d, 6); R0(d,e,a,b,c, 7);
|
||||
R0(c,d,e,a,b, 8); R0(b,c,d,e,a, 9); R0(a,b,c,d,e,10); R0(e,a,b,c,d,11);
|
||||
@@ -164,6 +176,7 @@ static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64])
|
||||
R4(c,d,e,a,b,68); R4(b,c,d,e,a,69); R4(a,b,c,d,e,70); R4(e,a,b,c,d,71);
|
||||
R4(d,e,a,b,c,72); R4(c,d,e,a,b,73); R4(b,c,d,e,a,74); R4(a,b,c,d,e,75);
|
||||
R4(e,a,b,c,d,76); R4(d,e,a,b,c,77); R4(c,d,e,a,b,78); R4(b,c,d,e,a,79);
|
||||
/* clang-format on */
|
||||
|
||||
/* Add the working vars back into context.state[] */
|
||||
state[0] += a;
|
||||
@@ -176,9 +189,8 @@ static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64])
|
||||
a = b = c = d = e = 0;
|
||||
}
|
||||
|
||||
|
||||
/* SHA1Init - Initialize new context */
|
||||
void crypto_SHA1_Init(SHA1_CTX* context)
|
||||
void crypto_SHA1_Init(SHA1_CTX *context)
|
||||
{
|
||||
/* SHA1 initialization constants */
|
||||
context->state[0] = 0x67452301;
|
||||
@@ -189,9 +201,9 @@ void crypto_SHA1_Init(SHA1_CTX* context)
|
||||
context->count[0] = context->count[1] = 0;
|
||||
}
|
||||
|
||||
|
||||
/* Run your data through this. */
|
||||
void crypto_SHA1_Update(SHA1_CTX* context, const uint8_t* data,
|
||||
void crypto_SHA1_Update(SHA1_CTX *context,
|
||||
const uint8_t *data,
|
||||
const size_t len)
|
||||
{
|
||||
size_t i, j;
|
||||
@@ -201,51 +213,51 @@ void crypto_SHA1_Update(SHA1_CTX* context, const uint8_t* data,
|
||||
context->count[1]++;
|
||||
context->count[1] += (uint32_t)(len >> 29);
|
||||
if ((j + len) > 63) {
|
||||
memcpy(&context->buffer[j], data, (i = 64-j));
|
||||
memcpy(&context->buffer[j], data, (i = 64 - j));
|
||||
SHA1_Transform(context->state, context->buffer);
|
||||
for ( ; i + 63 < len; i += 64) {
|
||||
for (; i + 63 < len; i += 64) {
|
||||
SHA1_Transform(context->state, data + i);
|
||||
}
|
||||
j = 0;
|
||||
}
|
||||
else i = 0;
|
||||
} else
|
||||
i = 0;
|
||||
memcpy(&context->buffer[j], &data[i], len - i);
|
||||
}
|
||||
|
||||
|
||||
/* Add padding and return the message digest. */
|
||||
void crypto_SHA1_Final(SHA1_CTX* context, uint8_t* digest)
|
||||
void crypto_SHA1_Final(SHA1_CTX *context, uint8_t *digest)
|
||||
{
|
||||
uint32_t i;
|
||||
uint8_t finalcount[8];
|
||||
uint8_t finalcount[8];
|
||||
|
||||
for (i = 0; i < 8; i++) {
|
||||
finalcount[i] = (unsigned char)((context->count[(i >= 4 ? 0 : 1)]
|
||||
>> ((3-(i & 3)) * 8) ) & 255); /* Endian independent */
|
||||
finalcount[i] = (unsigned char)((context->count[(i >= 4 ? 0 : 1)] >>
|
||||
((3 - (i & 3)) * 8)) &
|
||||
255); /* Endian independent */
|
||||
}
|
||||
crypto_SHA1_Update(context, (uint8_t *)"\200", 1);
|
||||
while ((context->count[0] & 504) != 448) {
|
||||
crypto_SHA1_Update(context, (uint8_t *)"\0", 1);
|
||||
}
|
||||
crypto_SHA1_Update(context, finalcount, 8); /* Should cause a SHA1_Transform() */
|
||||
crypto_SHA1_Update(context, finalcount,
|
||||
8); /* Should cause a SHA1_Transform() */
|
||||
for (i = 0; i < SHA1_DIGEST_SIZE; i++) {
|
||||
digest[i] = (uint8_t)
|
||||
((context->state[i>>2] >> ((3-(i & 3)) * 8) ) & 255);
|
||||
digest[i] =
|
||||
(uint8_t)((context->state[i >> 2] >> ((3 - (i & 3)) * 8)) & 255);
|
||||
}
|
||||
|
||||
/* Wipe variables */
|
||||
memset(context->buffer, 0, 64);
|
||||
memset(context->state, 0, 20);
|
||||
memset(context->count, 0, 8);
|
||||
memset(finalcount, 0, 8); /* SWR */
|
||||
memset(finalcount, 0, 8); /* SWR */
|
||||
|
||||
#ifdef SHA1HANDSOFF /* make SHA1Transform overwrite its own static vars */
|
||||
#ifdef SHA1HANDSOFF /* make SHA1Transform overwrite its own static vars */
|
||||
SHA1_Transform(context->state, context->buffer);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
void crypto_SHA1(const uint8_t* data, size_t len, uint8_t* digest)
|
||||
void crypto_SHA1(const uint8_t *data, size_t len, uint8_t *digest)
|
||||
{
|
||||
SHA1_CTX ctx;
|
||||
crypto_SHA1_Init(&ctx);
|
||||
|
||||
11
src/sha1.h
11
src/sha1.h
@@ -18,16 +18,17 @@ extern "C" {
|
||||
typedef struct {
|
||||
uint32_t state[5];
|
||||
uint32_t count[2];
|
||||
uint8_t buffer[64];
|
||||
uint8_t buffer[64];
|
||||
} SHA1_CTX;
|
||||
|
||||
#define SHA1_DIGEST_SIZE 20
|
||||
|
||||
void crypto_SHA1_Init(SHA1_CTX* context);
|
||||
void crypto_SHA1_Update(SHA1_CTX* context, const uint8_t* data,
|
||||
void crypto_SHA1_Init(SHA1_CTX *context);
|
||||
void crypto_SHA1_Update(SHA1_CTX *context,
|
||||
const uint8_t *data,
|
||||
const size_t len);
|
||||
void crypto_SHA1_Final(SHA1_CTX* context, uint8_t* digest);
|
||||
void crypto_SHA1(const uint8_t* data, size_t len, uint8_t* digest);
|
||||
void crypto_SHA1_Final(SHA1_CTX *context, uint8_t *digest);
|
||||
void crypto_SHA1(const uint8_t *data, size_t len, uint8_t *digest);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
||||
1084
src/snprintf.c
1084
src/snprintf.c
File diff suppressed because it is too large
Load Diff
32
src/sock.c
32
src/sock.c
@@ -22,7 +22,7 @@
|
||||
#include <winsock2.h>
|
||||
#include <ws2tcpip.h>
|
||||
#include <Iphlpapi.h>
|
||||
#include <Mstcpip.h> /* tcp_keepalive */
|
||||
#include <Mstcpip.h> /* tcp_keepalive */
|
||||
#else
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
@@ -69,7 +69,7 @@ static int _in_progress(int error)
|
||||
#endif
|
||||
}
|
||||
|
||||
sock_t sock_connect(const char * const host, const unsigned short port)
|
||||
sock_t sock_connect(const char *const host, const unsigned short port)
|
||||
{
|
||||
sock_t sock;
|
||||
char service[6];
|
||||
@@ -123,7 +123,8 @@ int sock_set_keepalive(const sock_t sock, int timeout, int interval)
|
||||
ka.onoff = optval;
|
||||
ka.keepalivetime = timeout * 1000;
|
||||
ka.keepaliveinterval = interval * 1000;
|
||||
ret = WSAIoctl(sock, SIO_KEEPALIVE_VALS, &ka, sizeof(ka), NULL, 0, &dw, NULL, NULL);
|
||||
ret = WSAIoctl(sock, SIO_KEEPALIVE_VALS, &ka, sizeof(ka), NULL, 0, &dw,
|
||||
NULL, NULL);
|
||||
#else
|
||||
ret = setsockopt(sock, SOL_SOCKET, SO_KEEPALIVE, &optval, sizeof(optval));
|
||||
if (ret < 0)
|
||||
@@ -131,15 +132,19 @@ int sock_set_keepalive(const sock_t sock, int timeout, int interval)
|
||||
|
||||
if (optval) {
|
||||
#ifdef TCP_KEEPIDLE
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPIDLE, &timeout, sizeof(timeout));
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPIDLE, &timeout,
|
||||
sizeof(timeout));
|
||||
#elif defined(TCP_KEEPALIVE)
|
||||
/* QNX receives `struct timeval' as argument, but it seems OSX does int */
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPALIVE, &timeout, sizeof(timeout));
|
||||
/* QNX receives `struct timeval' as argument, but it seems OSX does int
|
||||
*/
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPALIVE, &timeout,
|
||||
sizeof(timeout));
|
||||
#endif /* TCP_KEEPIDLE */
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
#ifdef TCP_KEEPINTVL
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPINTVL, &interval, sizeof(interval));
|
||||
ret = setsockopt(sock, IPPROTO_TCP, TCP_KEEPINTVL, &interval,
|
||||
sizeof(interval));
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
#endif /* TCP_KEEPINTVL */
|
||||
@@ -185,12 +190,12 @@ int sock_set_nonblocking(const sock_t sock)
|
||||
return _sock_set_blocking_mode(sock, 0);
|
||||
}
|
||||
|
||||
int sock_read(const sock_t sock, void * const buff, const size_t len)
|
||||
int sock_read(const sock_t sock, void *const buff, const size_t len)
|
||||
{
|
||||
return recv(sock, buff, len, 0);
|
||||
}
|
||||
|
||||
int sock_write(const sock_t sock, const void * const buff, const size_t len)
|
||||
int sock_write(const sock_t sock, const void *const buff, const size_t len)
|
||||
{
|
||||
return send(sock, buff, len, 0);
|
||||
}
|
||||
@@ -217,17 +222,18 @@ int sock_connect_error(const sock_t sock)
|
||||
|
||||
/* we don't actually care about the peer name, we're just checking if
|
||||
* we're connected or not */
|
||||
if (getpeername(sock, &sa, &len) == 0)
|
||||
{
|
||||
if (getpeername(sock, &sa, &len) == 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* it's possible that the error wasn't ENOTCONN, so if it wasn't,
|
||||
* return that */
|
||||
#ifdef _WIN32
|
||||
if (sock_error() != WSAENOTCONN) return sock_error();
|
||||
if (sock_error() != WSAENOTCONN)
|
||||
return sock_error();
|
||||
#else
|
||||
if (sock_error() != ENOTCONN) return sock_error();
|
||||
if (sock_error() != ENOTCONN)
|
||||
return sock_error();
|
||||
#endif
|
||||
|
||||
/* load the correct error into errno through error slippage */
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* sock.h
|
||||
** strophe XMPP client library -- socket abstraction header
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
@@ -30,13 +30,13 @@ void sock_shutdown(void);
|
||||
|
||||
int sock_error(void);
|
||||
|
||||
sock_t sock_connect(const char * const host, const unsigned short port);
|
||||
sock_t sock_connect(const char *const host, const unsigned short port);
|
||||
int sock_close(const sock_t sock);
|
||||
|
||||
int sock_set_blocking(const sock_t sock);
|
||||
int sock_set_nonblocking(const sock_t sock);
|
||||
int sock_read(const sock_t sock, void * const buff, const size_t len);
|
||||
int sock_write(const sock_t sock, const void * const buff, const size_t len);
|
||||
int sock_read(const sock_t sock, void *const buff, const size_t len);
|
||||
int sock_write(const sock_t sock, const void *const buff, const size_t len);
|
||||
int sock_is_recoverable(const int error);
|
||||
/* checks for an error after connect, return 0 if connect successful */
|
||||
int sock_connect_error(const sock_t sock);
|
||||
|
||||
483
src/stanza.c
483
src/stanza.c
@@ -63,7 +63,7 @@ xmpp_stanza_t *xmpp_stanza_new(xmpp_ctx_t *ctx)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_clone(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_t *xmpp_stanza_clone(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
stanza->ref++;
|
||||
|
||||
@@ -73,8 +73,8 @@ xmpp_stanza_t *xmpp_stanza_clone(xmpp_stanza_t * const stanza)
|
||||
/*
|
||||
* Copy the attributes of stanza src into stanza dst. Return -1 on error.
|
||||
*/
|
||||
static int _stanza_copy_attributes(xmpp_stanza_t * dst,
|
||||
const xmpp_stanza_t * const src)
|
||||
static int _stanza_copy_attributes(xmpp_stanza_t *dst,
|
||||
const xmpp_stanza_t *const src)
|
||||
{
|
||||
hash_iterator_t *iter;
|
||||
const char *key;
|
||||
@@ -82,11 +82,13 @@ static int _stanza_copy_attributes(xmpp_stanza_t * dst,
|
||||
int rc = XMPP_EOK;
|
||||
|
||||
iter = hash_iter_new(src->attributes);
|
||||
if (!iter) rc = XMPP_EMEM;
|
||||
if (!iter)
|
||||
rc = XMPP_EMEM;
|
||||
|
||||
while (rc == XMPP_EOK && (key = hash_iter_next(iter))) {
|
||||
val = hash_get(src->attributes, key);
|
||||
if (!val) rc = XMPP_EINT;
|
||||
if (!val)
|
||||
rc = XMPP_EINT;
|
||||
if (rc == XMPP_EOK)
|
||||
rc = xmpp_stanza_set_attribute(dst, key, val);
|
||||
}
|
||||
@@ -111,18 +113,20 @@ static int _stanza_copy_attributes(xmpp_stanza_t * dst,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t *const stanza)
|
||||
{
|
||||
xmpp_stanza_t *copy, *child, *copychild, *tail;
|
||||
|
||||
copy = xmpp_stanza_new(stanza->ctx);
|
||||
if (!copy) goto copy_error;
|
||||
if (!copy)
|
||||
goto copy_error;
|
||||
|
||||
copy->type = stanza->type;
|
||||
|
||||
if (stanza->data) {
|
||||
copy->data = xmpp_strdup(stanza->ctx, stanza->data);
|
||||
if (!copy->data) goto copy_error;
|
||||
if (!copy->data)
|
||||
goto copy_error;
|
||||
}
|
||||
|
||||
if (stanza->attributes) {
|
||||
@@ -133,7 +137,8 @@ xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t * const stanza)
|
||||
tail = copy->children;
|
||||
for (child = stanza->children; child; child = child->next) {
|
||||
copychild = xmpp_stanza_copy(child);
|
||||
if (!copychild) goto copy_error;
|
||||
if (!copychild)
|
||||
goto copy_error;
|
||||
copychild->parent = copy;
|
||||
|
||||
if (tail) {
|
||||
@@ -148,7 +153,8 @@ xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t * const stanza)
|
||||
|
||||
copy_error:
|
||||
/* release all the hitherto allocated memory */
|
||||
if (copy) xmpp_stanza_release(copy);
|
||||
if (copy)
|
||||
xmpp_stanza_release(copy);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -162,7 +168,7 @@ copy_error:
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_release(xmpp_stanza_t * const stanza)
|
||||
int xmpp_stanza_release(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
int released = 0;
|
||||
xmpp_stanza_t *child, *tchild;
|
||||
@@ -179,8 +185,10 @@ int xmpp_stanza_release(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_release(tchild);
|
||||
}
|
||||
|
||||
if (stanza->attributes) hash_release(stanza->attributes);
|
||||
if (stanza->data) xmpp_free(stanza->ctx, stanza->data);
|
||||
if (stanza->attributes)
|
||||
hash_release(stanza->attributes);
|
||||
if (stanza->data)
|
||||
xmpp_free(stanza->ctx, stanza->data);
|
||||
xmpp_free(stanza->ctx, stanza);
|
||||
released = 1;
|
||||
}
|
||||
@@ -196,7 +204,7 @@ int xmpp_stanza_release(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_ctx_t *xmpp_stanza_get_context(const xmpp_stanza_t * const stanza)
|
||||
xmpp_ctx_t *xmpp_stanza_get_context(const xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return stanza->ctx;
|
||||
}
|
||||
@@ -209,7 +217,7 @@ xmpp_ctx_t *xmpp_stanza_get_context(const xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_is_text(xmpp_stanza_t * const stanza)
|
||||
int xmpp_stanza_is_text(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return (stanza && stanza->type == XMPP_STANZA_TEXT);
|
||||
}
|
||||
@@ -222,7 +230,7 @@ int xmpp_stanza_is_text(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_is_tag(xmpp_stanza_t * const stanza)
|
||||
int xmpp_stanza_is_tag(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return (stanza && stanza->type == XMPP_STANZA_TAG);
|
||||
}
|
||||
@@ -233,7 +241,7 @@ int xmpp_stanza_is_tag(xmpp_stanza_t * const stanza)
|
||||
* On failure, returns NULL.
|
||||
*/
|
||||
|
||||
static char *_escape_xml(xmpp_ctx_t * const ctx, char *text)
|
||||
static char *_escape_xml(xmpp_ctx_t *const ctx, char *text)
|
||||
{
|
||||
size_t len = 0;
|
||||
char *src;
|
||||
@@ -241,44 +249,44 @@ static char *_escape_xml(xmpp_ctx_t * const ctx, char *text)
|
||||
char *buf;
|
||||
for (src = text; *src != '\0'; src++) {
|
||||
switch (*src) {
|
||||
case '<': /* "<" */
|
||||
case '>': /* ">" */
|
||||
len += 4;
|
||||
break;
|
||||
case '&': /* "&" */
|
||||
len += 5;
|
||||
break;
|
||||
case '"':
|
||||
len += 6; /*""" */
|
||||
break;
|
||||
default:
|
||||
len++;
|
||||
case '<': /* "<" */
|
||||
case '>': /* ">" */
|
||||
len += 4;
|
||||
break;
|
||||
case '&': /* "&" */
|
||||
len += 5;
|
||||
break;
|
||||
case '"':
|
||||
len += 6; /*""" */
|
||||
break;
|
||||
default:
|
||||
len++;
|
||||
}
|
||||
}
|
||||
if ((buf = xmpp_alloc(ctx, (len+1) * sizeof(char))) == NULL)
|
||||
return NULL; /* Error */
|
||||
if ((buf = xmpp_alloc(ctx, (len + 1) * sizeof(char))) == NULL)
|
||||
return NULL; /* Error */
|
||||
dst = buf;
|
||||
for (src = text; *src != '\0'; src++) {
|
||||
switch (*src) {
|
||||
case '<':
|
||||
strcpy(dst, "<");
|
||||
dst += 4;
|
||||
break;
|
||||
case '>':
|
||||
strcpy(dst, ">");
|
||||
dst += 4;
|
||||
break;
|
||||
case '&':
|
||||
strcpy(dst, "&");
|
||||
dst += 5;
|
||||
break;
|
||||
case '"':
|
||||
strcpy(dst, """);
|
||||
dst += 6;
|
||||
break;
|
||||
default:
|
||||
*dst = *src;
|
||||
dst++;
|
||||
case '<':
|
||||
strcpy(dst, "<");
|
||||
dst += 4;
|
||||
break;
|
||||
case '>':
|
||||
strcpy(dst, ">");
|
||||
dst += 4;
|
||||
break;
|
||||
case '&':
|
||||
strcpy(dst, "&");
|
||||
dst += 5;
|
||||
break;
|
||||
case '"':
|
||||
strcpy(dst, """);
|
||||
dst += 6;
|
||||
break;
|
||||
default:
|
||||
*dst = *src;
|
||||
dst++;
|
||||
}
|
||||
}
|
||||
*dst = '\0';
|
||||
@@ -286,9 +294,11 @@ static char *_escape_xml(xmpp_ctx_t * const ctx, char *text)
|
||||
}
|
||||
|
||||
/* small helper function */
|
||||
static void _render_update(int *written, const int length,
|
||||
static void _render_update(int *written,
|
||||
const int length,
|
||||
const int lastwrite,
|
||||
size_t *left, char **ptr)
|
||||
size_t *left,
|
||||
char **ptr)
|
||||
{
|
||||
*written += lastwrite;
|
||||
|
||||
@@ -307,7 +317,8 @@ static void _render_update(int *written, const int length,
|
||||
* and return values > buflen indicate buffer was not large enough
|
||||
*/
|
||||
static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
char * const buf, size_t const buflen)
|
||||
char *const buf,
|
||||
size_t const buflen)
|
||||
{
|
||||
char *ptr = buf;
|
||||
size_t left = buflen;
|
||||
@@ -319,23 +330,29 @@ static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
|
||||
written = 0;
|
||||
|
||||
if (stanza->type == XMPP_STANZA_UNKNOWN) return XMPP_EINVOP;
|
||||
if (stanza->type == XMPP_STANZA_UNKNOWN)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
if (stanza->type == XMPP_STANZA_TEXT) {
|
||||
if (!stanza->data) return XMPP_EINVOP;
|
||||
if (!stanza->data)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
tmp = _escape_xml(stanza->ctx, stanza->data);
|
||||
if (tmp == NULL) return XMPP_EMEM;
|
||||
if (tmp == NULL)
|
||||
return XMPP_EMEM;
|
||||
ret = xmpp_snprintf(ptr, left, "%s", tmp);
|
||||
xmpp_free(stanza->ctx, tmp);
|
||||
if (ret < 0) return XMPP_EMEM;
|
||||
if (ret < 0)
|
||||
return XMPP_EMEM;
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
} else { /* stanza->type == XMPP_STANZA_TAG */
|
||||
if (!stanza->data) return XMPP_EINVOP;
|
||||
if (!stanza->data)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
/* write beginning of tag and attributes */
|
||||
ret = xmpp_snprintf(ptr, left, "<%s", stanza->data);
|
||||
if (ret < 0) return XMPP_EMEM;
|
||||
if (ret < 0)
|
||||
return XMPP_EMEM;
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
|
||||
if (stanza->attributes && hash_num_keys(stanza->attributes) > 0) {
|
||||
@@ -343,20 +360,20 @@ static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
while ((key = hash_iter_next(iter))) {
|
||||
if (!strcmp(key, "xmlns")) {
|
||||
/* don't output namespace if parent stanza is the same */
|
||||
if (stanza->parent &&
|
||||
stanza->parent->attributes &&
|
||||
if (stanza->parent && stanza->parent->attributes &&
|
||||
hash_get(stanza->parent->attributes, key) &&
|
||||
!strcmp((char*)hash_get(stanza->attributes, key),
|
||||
(char*)hash_get(stanza->parent->attributes, key)))
|
||||
!strcmp(
|
||||
(char *)hash_get(stanza->attributes, key),
|
||||
(char *)hash_get(stanza->parent->attributes, key)))
|
||||
continue;
|
||||
/* or if this is the stream namespace */
|
||||
if (!stanza->parent &&
|
||||
!strcmp((char*)hash_get(stanza->attributes, key),
|
||||
XMPP_NS_CLIENT))
|
||||
!strcmp((char *)hash_get(stanza->attributes, key),
|
||||
XMPP_NS_CLIENT))
|
||||
continue;
|
||||
}
|
||||
tmp = _escape_xml(stanza->ctx,
|
||||
(char *)hash_get(stanza->attributes, key));
|
||||
(char *)hash_get(stanza->attributes, key));
|
||||
if (tmp == NULL) {
|
||||
hash_iter_release(iter);
|
||||
return XMPP_EMEM;
|
||||
@@ -375,21 +392,24 @@ static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
if (!stanza->children) {
|
||||
/* write end if singleton tag */
|
||||
ret = xmpp_snprintf(ptr, left, "/>");
|
||||
if (ret < 0) return XMPP_EMEM;
|
||||
if (ret < 0)
|
||||
return XMPP_EMEM;
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
} else {
|
||||
/* this stanza has child stanzas */
|
||||
|
||||
/* write end of start tag */
|
||||
ret = xmpp_snprintf(ptr, left, ">");
|
||||
if (ret < 0) return XMPP_EMEM;
|
||||
if (ret < 0)
|
||||
return XMPP_EMEM;
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
|
||||
/* iterate and recurse over child stanzas */
|
||||
child = stanza->children;
|
||||
while (child) {
|
||||
ret = _render_stanza_recursive(child, ptr, left);
|
||||
if (ret < 0) return ret;
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
|
||||
@@ -398,7 +418,8 @@ static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
|
||||
/* write end tag */
|
||||
ret = xmpp_snprintf(ptr, left, "</%s>", stanza->data);
|
||||
if (ret < 0) return XMPP_EMEM;
|
||||
if (ret < 0)
|
||||
return XMPP_EMEM;
|
||||
|
||||
_render_update(&written, buflen, ret, &left, &ptr);
|
||||
}
|
||||
@@ -423,8 +444,8 @@ static int _render_stanza_recursive(xmpp_stanza_t *stanza,
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_to_text(xmpp_stanza_t *stanza,
|
||||
char ** const buf,
|
||||
size_t * const buflen)
|
||||
char **const buf,
|
||||
size_t *const buflen)
|
||||
{
|
||||
char *buffer, *tmp;
|
||||
size_t length;
|
||||
@@ -485,12 +506,13 @@ int xmpp_stanza_to_text(xmpp_stanza_t *stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_name(xmpp_stanza_t *stanza,
|
||||
const char * const name)
|
||||
int xmpp_stanza_set_name(xmpp_stanza_t *stanza, const char *const name)
|
||||
{
|
||||
if (stanza->type == XMPP_STANZA_TEXT) return XMPP_EINVOP;
|
||||
if (stanza->type == XMPP_STANZA_TEXT)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
if (stanza->data) xmpp_free(stanza->ctx, stanza->data);
|
||||
if (stanza->data)
|
||||
xmpp_free(stanza->ctx, stanza->data);
|
||||
|
||||
stanza->type = XMPP_STANZA_TAG;
|
||||
stanza->data = xmpp_strdup(stanza->ctx, name);
|
||||
@@ -508,9 +530,10 @@ int xmpp_stanza_set_name(xmpp_stanza_t *stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_name(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_name(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
if (stanza->type == XMPP_STANZA_TEXT) return NULL;
|
||||
if (stanza->type == XMPP_STANZA_TEXT)
|
||||
return NULL;
|
||||
return stanza->data;
|
||||
}
|
||||
|
||||
@@ -522,7 +545,7 @@ const char *xmpp_stanza_get_name(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_get_attribute_count(xmpp_stanza_t * const stanza)
|
||||
int xmpp_stanza_get_attribute_count(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
if (stanza->attributes == NULL) {
|
||||
return 0;
|
||||
@@ -545,8 +568,9 @@ int xmpp_stanza_get_attribute_count(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_get_attributes(xmpp_stanza_t * const stanza,
|
||||
const char **attr, int attrlen)
|
||||
int xmpp_stanza_get_attributes(xmpp_stanza_t *const stanza,
|
||||
const char **attr,
|
||||
int attrlen)
|
||||
{
|
||||
hash_iterator_t *iter;
|
||||
const char *key;
|
||||
@@ -586,18 +610,20 @@ int xmpp_stanza_get_attributes(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const key,
|
||||
const char * const value)
|
||||
int xmpp_stanza_set_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const key,
|
||||
const char *const value)
|
||||
{
|
||||
char *val;
|
||||
int rc;
|
||||
|
||||
if (stanza->type != XMPP_STANZA_TAG) return XMPP_EINVOP;
|
||||
if (stanza->type != XMPP_STANZA_TAG)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
if (!stanza->attributes) {
|
||||
stanza->attributes = hash_new(stanza->ctx, 8, xmpp_free);
|
||||
if (!stanza->attributes) return XMPP_EMEM;
|
||||
if (!stanza->attributes)
|
||||
return XMPP_EMEM;
|
||||
}
|
||||
|
||||
val = xmpp_strdup(stanza->ctx, value);
|
||||
@@ -625,8 +651,7 @@ int xmpp_stanza_set_attribute(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_ns(xmpp_stanza_t * const stanza,
|
||||
const char * const ns)
|
||||
int xmpp_stanza_set_ns(xmpp_stanza_t *const stanza, const char *const ns)
|
||||
{
|
||||
return xmpp_stanza_set_attribute(stanza, "xmlns", ns);
|
||||
}
|
||||
@@ -646,7 +671,8 @@ int xmpp_stanza_set_ns(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_add_child_ex(xmpp_stanza_t *stanza, xmpp_stanza_t *child,
|
||||
int xmpp_stanza_add_child_ex(xmpp_stanza_t *stanza,
|
||||
xmpp_stanza_t *child,
|
||||
int do_clone)
|
||||
{
|
||||
xmpp_stanza_t *s;
|
||||
@@ -662,7 +688,8 @@ int xmpp_stanza_add_child_ex(xmpp_stanza_t *stanza, xmpp_stanza_t *child,
|
||||
stanza->children = child;
|
||||
else {
|
||||
s = stanza->children;
|
||||
while (s->next) s = s->next;
|
||||
while (s->next)
|
||||
s = s->next;
|
||||
s->next = child;
|
||||
child->prev = s;
|
||||
}
|
||||
@@ -699,14 +726,15 @@ int xmpp_stanza_add_child(xmpp_stanza_t *stanza, xmpp_stanza_t *child)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_text(xmpp_stanza_t *stanza,
|
||||
const char * const text)
|
||||
int xmpp_stanza_set_text(xmpp_stanza_t *stanza, const char *const text)
|
||||
{
|
||||
if (stanza->type == XMPP_STANZA_TAG) return XMPP_EINVOP;
|
||||
if (stanza->type == XMPP_STANZA_TAG)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
stanza->type = XMPP_STANZA_TEXT;
|
||||
|
||||
if (stanza->data) xmpp_free(stanza->ctx, stanza->data);
|
||||
if (stanza->data)
|
||||
xmpp_free(stanza->ctx, stanza->data);
|
||||
stanza->data = xmpp_strdup(stanza->ctx, text);
|
||||
|
||||
return stanza->data == NULL ? XMPP_EMEM : XMPP_EOK;
|
||||
@@ -727,16 +755,19 @@ int xmpp_stanza_set_text(xmpp_stanza_t *stanza,
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_text_with_size(xmpp_stanza_t *stanza,
|
||||
const char * const text,
|
||||
const char *const text,
|
||||
const size_t size)
|
||||
{
|
||||
if (stanza->type == XMPP_STANZA_TAG) return XMPP_EINVOP;
|
||||
if (stanza->type == XMPP_STANZA_TAG)
|
||||
return XMPP_EINVOP;
|
||||
|
||||
stanza->type = XMPP_STANZA_TEXT;
|
||||
|
||||
if (stanza->data) xmpp_free(stanza->ctx, stanza->data);
|
||||
if (stanza->data)
|
||||
xmpp_free(stanza->ctx, stanza->data);
|
||||
stanza->data = xmpp_alloc(stanza->ctx, size + 1);
|
||||
if (!stanza->data) return XMPP_EMEM;
|
||||
if (!stanza->data)
|
||||
return XMPP_EMEM;
|
||||
|
||||
memcpy(stanza->data, text, size);
|
||||
stanza->data[size] = 0;
|
||||
@@ -754,7 +785,7 @@ int xmpp_stanza_set_text_with_size(xmpp_stanza_t *stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_id(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_id(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return xmpp_stanza_get_attribute(stanza, "id");
|
||||
}
|
||||
@@ -769,7 +800,7 @@ const char *xmpp_stanza_get_id(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_ns(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_ns(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return xmpp_stanza_get_attribute(stanza, "xmlns");
|
||||
}
|
||||
@@ -784,7 +815,7 @@ const char *xmpp_stanza_get_ns(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_type(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_type(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return xmpp_stanza_get_attribute(stanza, "type");
|
||||
}
|
||||
@@ -799,7 +830,7 @@ const char *xmpp_stanza_get_type(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_to(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_to(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return xmpp_stanza_get_attribute(stanza, "to");
|
||||
}
|
||||
@@ -814,7 +845,7 @@ const char *xmpp_stanza_get_to(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_from(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_from(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return xmpp_stanza_get_attribute(stanza, "from");
|
||||
}
|
||||
@@ -830,8 +861,8 @@ const char *xmpp_stanza_get_from(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name(xmpp_stanza_t * const stanza,
|
||||
const char * const name)
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name(xmpp_stanza_t *const stanza,
|
||||
const char *const name)
|
||||
{
|
||||
xmpp_stanza_t *child;
|
||||
|
||||
@@ -856,8 +887,8 @@ xmpp_stanza_t *xmpp_stanza_get_child_by_name(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_ns(xmpp_stanza_t * const stanza,
|
||||
const char * const ns)
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_ns(xmpp_stanza_t *const stanza,
|
||||
const char *const ns)
|
||||
{
|
||||
xmpp_stanza_t *child;
|
||||
const char *child_ns;
|
||||
@@ -884,9 +915,9 @@ xmpp_stanza_t *xmpp_stanza_get_child_by_ns(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name_and_ns(xmpp_stanza_t * const stanza,
|
||||
const char * const name,
|
||||
const char * const ns)
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name_and_ns(xmpp_stanza_t *const stanza,
|
||||
const char *const name,
|
||||
const char *const ns)
|
||||
{
|
||||
xmpp_stanza_t *child;
|
||||
const char *child_ns;
|
||||
@@ -915,7 +946,7 @@ xmpp_stanza_t *xmpp_stanza_get_child_by_name_and_ns(xmpp_stanza_t * const stanza
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_get_children(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_t *xmpp_stanza_get_children(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return stanza->children;
|
||||
}
|
||||
@@ -928,7 +959,7 @@ xmpp_stanza_t *xmpp_stanza_get_children(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_get_next(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_t *xmpp_stanza_get_next(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
return stanza->next;
|
||||
}
|
||||
@@ -944,7 +975,7 @@ xmpp_stanza_t *xmpp_stanza_get_next(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
char *xmpp_stanza_get_text(xmpp_stanza_t * const stanza)
|
||||
char *xmpp_stanza_get_text(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
size_t len, clen;
|
||||
xmpp_stanza_t *child;
|
||||
@@ -962,10 +993,12 @@ char *xmpp_stanza_get_text(xmpp_stanza_t * const stanza)
|
||||
if (child->type == XMPP_STANZA_TEXT)
|
||||
len += strlen(child->data);
|
||||
|
||||
if (len == 0) return NULL;
|
||||
if (len == 0)
|
||||
return NULL;
|
||||
|
||||
text = (char *)xmpp_alloc(stanza->ctx, len + 1);
|
||||
if (!text) return NULL;
|
||||
if (!text)
|
||||
return NULL;
|
||||
|
||||
len = 0;
|
||||
for (child = stanza->children; child; child = child->next)
|
||||
@@ -993,7 +1026,7 @@ char *xmpp_stanza_get_text(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_text_ptr(xmpp_stanza_t * const stanza)
|
||||
const char *xmpp_stanza_get_text_ptr(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
if (stanza->type == XMPP_STANZA_TEXT)
|
||||
return stanza->data;
|
||||
@@ -1012,8 +1045,7 @@ const char *xmpp_stanza_get_text_ptr(xmpp_stanza_t * const stanza)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_id(xmpp_stanza_t * const stanza,
|
||||
const char * const id)
|
||||
int xmpp_stanza_set_id(xmpp_stanza_t *const stanza, const char *const id)
|
||||
{
|
||||
return xmpp_stanza_set_attribute(stanza, "id", id);
|
||||
}
|
||||
@@ -1029,8 +1061,7 @@ int xmpp_stanza_set_id(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_type(xmpp_stanza_t * const stanza,
|
||||
const char * const type)
|
||||
int xmpp_stanza_set_type(xmpp_stanza_t *const stanza, const char *const type)
|
||||
{
|
||||
return xmpp_stanza_set_attribute(stanza, "type", type);
|
||||
}
|
||||
@@ -1047,8 +1078,7 @@ int xmpp_stanza_set_type(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_to(xmpp_stanza_t * const stanza,
|
||||
const char * const to)
|
||||
int xmpp_stanza_set_to(xmpp_stanza_t *const stanza, const char *const to)
|
||||
{
|
||||
return xmpp_stanza_set_attribute(stanza, "to", to);
|
||||
}
|
||||
@@ -1065,8 +1095,7 @@ int xmpp_stanza_set_to(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_set_from(xmpp_stanza_t * const stanza,
|
||||
const char * const from)
|
||||
int xmpp_stanza_set_from(xmpp_stanza_t *const stanza, const char *const from)
|
||||
{
|
||||
return xmpp_stanza_set_attribute(stanza, "from", from);
|
||||
}
|
||||
@@ -1082,8 +1111,8 @@ int xmpp_stanza_set_from(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
const char *xmpp_stanza_get_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const name)
|
||||
const char *xmpp_stanza_get_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const name)
|
||||
{
|
||||
if (stanza->type != XMPP_STANZA_TAG)
|
||||
return NULL;
|
||||
@@ -1103,8 +1132,8 @@ const char *xmpp_stanza_get_attribute(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_stanza_del_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const name)
|
||||
int xmpp_stanza_del_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const name)
|
||||
{
|
||||
if (stanza->type != XMPP_STANZA_TAG)
|
||||
return -1;
|
||||
@@ -1127,23 +1156,26 @@ int xmpp_stanza_del_attribute(xmpp_stanza_t * const stanza,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_stanza_reply(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_t *xmpp_stanza_reply(xmpp_stanza_t *const stanza)
|
||||
{
|
||||
xmpp_stanza_t *copy = NULL;
|
||||
const char *from;
|
||||
int rc;
|
||||
|
||||
from = xmpp_stanza_get_from(stanza);
|
||||
if (!from) goto copy_error;
|
||||
if (!from)
|
||||
goto copy_error;
|
||||
|
||||
copy = xmpp_stanza_new(stanza->ctx);
|
||||
if (!copy) goto copy_error;
|
||||
if (!copy)
|
||||
goto copy_error;
|
||||
|
||||
copy->type = stanza->type;
|
||||
|
||||
if (stanza->data) {
|
||||
copy->data = xmpp_strdup(stanza->ctx, stanza->data);
|
||||
if (!copy->data) goto copy_error;
|
||||
if (!copy->data)
|
||||
goto copy_error;
|
||||
}
|
||||
|
||||
if (stanza->attributes) {
|
||||
@@ -1154,19 +1186,22 @@ xmpp_stanza_t *xmpp_stanza_reply(xmpp_stanza_t * const stanza)
|
||||
xmpp_stanza_del_attribute(copy, "to");
|
||||
xmpp_stanza_del_attribute(copy, "from");
|
||||
rc = xmpp_stanza_set_to(copy, from);
|
||||
if (rc != XMPP_EOK) goto copy_error;
|
||||
if (rc != XMPP_EOK)
|
||||
goto copy_error;
|
||||
|
||||
return copy;
|
||||
|
||||
copy_error:
|
||||
if (copy) xmpp_stanza_release(copy);
|
||||
if (copy)
|
||||
xmpp_stanza_release(copy);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static xmpp_stanza_t *
|
||||
_stanza_new_with_attrs(xmpp_ctx_t *ctx, const char * const name,
|
||||
const char * const type, const char * const id,
|
||||
const char * const to)
|
||||
static xmpp_stanza_t *_stanza_new_with_attrs(xmpp_ctx_t *ctx,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
const char *const id,
|
||||
const char *const to)
|
||||
{
|
||||
xmpp_stanza_t *stanza = xmpp_stanza_new(ctx);
|
||||
int ret;
|
||||
@@ -1199,8 +1234,10 @@ _stanza_new_with_attrs(xmpp_ctx_t *ctx, const char * const name,
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_message_new(xmpp_ctx_t *ctx, const char * const type,
|
||||
const char * const to, const char * const id)
|
||||
xmpp_stanza_t *xmpp_message_new(xmpp_ctx_t *ctx,
|
||||
const char *const type,
|
||||
const char *const to,
|
||||
const char *const id)
|
||||
{
|
||||
return _stanza_new_with_attrs(ctx, "message", type, id, to);
|
||||
}
|
||||
@@ -1239,7 +1276,7 @@ char *xmpp_message_get_body(xmpp_stanza_t *msg)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
int xmpp_message_set_body(xmpp_stanza_t *msg, const char * const text)
|
||||
int xmpp_message_set_body(xmpp_stanza_t *msg, const char *const text)
|
||||
{
|
||||
xmpp_ctx_t *ctx = msg->ctx;
|
||||
xmpp_stanza_t *body;
|
||||
@@ -1285,8 +1322,8 @@ int xmpp_message_set_body(xmpp_stanza_t *msg, const char * const text)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_iq_new(xmpp_ctx_t *ctx, const char * const type,
|
||||
const char * const id)
|
||||
xmpp_stanza_t *
|
||||
xmpp_iq_new(xmpp_ctx_t *ctx, const char *const type, const char *const id)
|
||||
{
|
||||
return _stanza_new_with_attrs(ctx, "iq", type, id, NULL);
|
||||
}
|
||||
@@ -1317,88 +1354,90 @@ xmpp_stanza_t *xmpp_presence_new(xmpp_ctx_t *ctx)
|
||||
*
|
||||
* @ingroup Stanza
|
||||
*/
|
||||
xmpp_stanza_t *xmpp_error_new(xmpp_ctx_t *ctx, xmpp_error_type_t const type,
|
||||
const char * const text)
|
||||
xmpp_stanza_t *xmpp_error_new(xmpp_ctx_t *ctx,
|
||||
xmpp_error_type_t const type,
|
||||
const char *const text)
|
||||
{
|
||||
xmpp_stanza_t *error = _stanza_new_with_attrs(ctx, "stream:error", NULL, NULL, NULL);
|
||||
xmpp_stanza_t *error =
|
||||
_stanza_new_with_attrs(ctx, "stream:error", NULL, NULL, NULL);
|
||||
xmpp_stanza_t *error_type = xmpp_stanza_new(ctx);
|
||||
|
||||
switch(type) {
|
||||
case XMPP_SE_BAD_FORMAT:
|
||||
xmpp_stanza_set_name(error_type, "bad-format");
|
||||
break;
|
||||
case XMPP_SE_BAD_NS_PREFIX:
|
||||
xmpp_stanza_set_name(error_type, "bad-namespace-prefix");
|
||||
break;
|
||||
case XMPP_SE_CONFLICT:
|
||||
xmpp_stanza_set_name(error_type, "conflict");
|
||||
break;
|
||||
case XMPP_SE_CONN_TIMEOUT:
|
||||
xmpp_stanza_set_name(error_type, "connection-timeout");
|
||||
break;
|
||||
case XMPP_SE_HOST_GONE:
|
||||
xmpp_stanza_set_name(error_type, "host-gone");
|
||||
break;
|
||||
case XMPP_SE_HOST_UNKNOWN:
|
||||
xmpp_stanza_set_name(error_type, "host-unknown");
|
||||
break;
|
||||
case XMPP_SE_IMPROPER_ADDR:
|
||||
xmpp_stanza_set_name(error_type, "improper-addressing");
|
||||
break;
|
||||
case XMPP_SE_INTERNAL_SERVER_ERROR:
|
||||
xmpp_stanza_set_name(error_type, "internal-server-error");
|
||||
break;
|
||||
case XMPP_SE_INVALID_FROM:
|
||||
xmpp_stanza_set_name(error_type, "invalid-from");
|
||||
break;
|
||||
case XMPP_SE_INVALID_ID:
|
||||
xmpp_stanza_set_name(error_type, "invalid-id");
|
||||
break;
|
||||
case XMPP_SE_INVALID_NS:
|
||||
xmpp_stanza_set_name(error_type, "invalid-namespace");
|
||||
break;
|
||||
case XMPP_SE_INVALID_XML:
|
||||
xmpp_stanza_set_name(error_type, "invalid-xml");
|
||||
break;
|
||||
case XMPP_SE_NOT_AUTHORIZED:
|
||||
xmpp_stanza_set_name(error_type, "not-authorized");
|
||||
break;
|
||||
case XMPP_SE_POLICY_VIOLATION:
|
||||
xmpp_stanza_set_name(error_type, "policy-violation");
|
||||
break;
|
||||
case XMPP_SE_REMOTE_CONN_FAILED:
|
||||
xmpp_stanza_set_name(error_type, "remote-connection-failed");
|
||||
break;
|
||||
case XMPP_SE_RESOURCE_CONSTRAINT:
|
||||
xmpp_stanza_set_name(error_type, "resource-constraint");
|
||||
break;
|
||||
case XMPP_SE_RESTRICTED_XML:
|
||||
xmpp_stanza_set_name(error_type, "restricted-xml");
|
||||
break;
|
||||
case XMPP_SE_SEE_OTHER_HOST:
|
||||
xmpp_stanza_set_name(error_type, "see-other-host");
|
||||
break;
|
||||
case XMPP_SE_SYSTEM_SHUTDOWN:
|
||||
xmpp_stanza_set_name(error_type, "system-shutdown");
|
||||
break;
|
||||
case XMPP_SE_UNDEFINED_CONDITION:
|
||||
xmpp_stanza_set_name(error_type, "undefined-condition");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_ENCODING:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-encoding");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_STANZA_TYPE:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-stanza-type");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_VERSION:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-version");
|
||||
break;
|
||||
case XMPP_SE_XML_NOT_WELL_FORMED:
|
||||
xmpp_stanza_set_name(error_type, "xml-not-well-formed");
|
||||
break;
|
||||
default:
|
||||
xmpp_stanza_set_name(error_type, "internal-server-error");
|
||||
break;
|
||||
switch (type) {
|
||||
case XMPP_SE_BAD_FORMAT:
|
||||
xmpp_stanza_set_name(error_type, "bad-format");
|
||||
break;
|
||||
case XMPP_SE_BAD_NS_PREFIX:
|
||||
xmpp_stanza_set_name(error_type, "bad-namespace-prefix");
|
||||
break;
|
||||
case XMPP_SE_CONFLICT:
|
||||
xmpp_stanza_set_name(error_type, "conflict");
|
||||
break;
|
||||
case XMPP_SE_CONN_TIMEOUT:
|
||||
xmpp_stanza_set_name(error_type, "connection-timeout");
|
||||
break;
|
||||
case XMPP_SE_HOST_GONE:
|
||||
xmpp_stanza_set_name(error_type, "host-gone");
|
||||
break;
|
||||
case XMPP_SE_HOST_UNKNOWN:
|
||||
xmpp_stanza_set_name(error_type, "host-unknown");
|
||||
break;
|
||||
case XMPP_SE_IMPROPER_ADDR:
|
||||
xmpp_stanza_set_name(error_type, "improper-addressing");
|
||||
break;
|
||||
case XMPP_SE_INTERNAL_SERVER_ERROR:
|
||||
xmpp_stanza_set_name(error_type, "internal-server-error");
|
||||
break;
|
||||
case XMPP_SE_INVALID_FROM:
|
||||
xmpp_stanza_set_name(error_type, "invalid-from");
|
||||
break;
|
||||
case XMPP_SE_INVALID_ID:
|
||||
xmpp_stanza_set_name(error_type, "invalid-id");
|
||||
break;
|
||||
case XMPP_SE_INVALID_NS:
|
||||
xmpp_stanza_set_name(error_type, "invalid-namespace");
|
||||
break;
|
||||
case XMPP_SE_INVALID_XML:
|
||||
xmpp_stanza_set_name(error_type, "invalid-xml");
|
||||
break;
|
||||
case XMPP_SE_NOT_AUTHORIZED:
|
||||
xmpp_stanza_set_name(error_type, "not-authorized");
|
||||
break;
|
||||
case XMPP_SE_POLICY_VIOLATION:
|
||||
xmpp_stanza_set_name(error_type, "policy-violation");
|
||||
break;
|
||||
case XMPP_SE_REMOTE_CONN_FAILED:
|
||||
xmpp_stanza_set_name(error_type, "remote-connection-failed");
|
||||
break;
|
||||
case XMPP_SE_RESOURCE_CONSTRAINT:
|
||||
xmpp_stanza_set_name(error_type, "resource-constraint");
|
||||
break;
|
||||
case XMPP_SE_RESTRICTED_XML:
|
||||
xmpp_stanza_set_name(error_type, "restricted-xml");
|
||||
break;
|
||||
case XMPP_SE_SEE_OTHER_HOST:
|
||||
xmpp_stanza_set_name(error_type, "see-other-host");
|
||||
break;
|
||||
case XMPP_SE_SYSTEM_SHUTDOWN:
|
||||
xmpp_stanza_set_name(error_type, "system-shutdown");
|
||||
break;
|
||||
case XMPP_SE_UNDEFINED_CONDITION:
|
||||
xmpp_stanza_set_name(error_type, "undefined-condition");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_ENCODING:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-encoding");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_STANZA_TYPE:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-stanza-type");
|
||||
break;
|
||||
case XMPP_SE_UNSUPPORTED_VERSION:
|
||||
xmpp_stanza_set_name(error_type, "unsupported-version");
|
||||
break;
|
||||
case XMPP_SE_XML_NOT_WELL_FORMED:
|
||||
xmpp_stanza_set_name(error_type, "xml-not-well-formed");
|
||||
break;
|
||||
default:
|
||||
xmpp_stanza_set_name(error_type, "internal-server-error");
|
||||
break;
|
||||
}
|
||||
|
||||
xmpp_stanza_set_ns(error_type, XMPP_NS_STREAMS_IETF);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* tls.h
|
||||
** strophe XMPP client library -- TLS abstraction header
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
@@ -35,8 +35,8 @@ int tls_stop(tls_t *tls);
|
||||
int tls_error(tls_t *tls);
|
||||
|
||||
int tls_pending(tls_t *tls);
|
||||
int tls_read(tls_t *tls, void * const buff, const size_t len);
|
||||
int tls_write(tls_t *tls, const void * const buff, const size_t len);
|
||||
int tls_read(tls_t *tls, void *const buff, const size_t len);
|
||||
int tls_write(tls_t *tls, const void *const buff, const size_t len);
|
||||
|
||||
int tls_clear_pending_write(tls_t *tls);
|
||||
int tls_is_recoverable(int error);
|
||||
|
||||
@@ -70,12 +70,12 @@ int tls_pending(tls_t *tls)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
int tls_read(tls_t *tls, void *const buff, const size_t len)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
int tls_write(tls_t *tls, const void *const buff, const size_t len)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -79,8 +79,8 @@ int tls_set_credentials(tls_t *tls, const char *cafilename)
|
||||
int err;
|
||||
|
||||
/* set trusted credentials -- takes a .pem filename */
|
||||
err = gnutls_certificate_set_x509_trust_file(tls->cred,
|
||||
cafilename, GNUTLS_X509_FMT_PEM);
|
||||
err = gnutls_certificate_set_x509_trust_file(tls->cred, cafilename,
|
||||
GNUTLS_X509_FMT_PEM);
|
||||
if (err >= 0) {
|
||||
err = gnutls_credentials_set(tls->session, GNUTLS_CRD_CERTIFICATE,
|
||||
tls->cred);
|
||||
@@ -117,10 +117,10 @@ int tls_is_recoverable(int error)
|
||||
|
||||
int tls_pending(tls_t *tls)
|
||||
{
|
||||
return gnutls_record_check_pending (tls->session);
|
||||
return gnutls_record_check_pending(tls->session);
|
||||
}
|
||||
|
||||
int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
int tls_read(tls_t *tls, void *const buff, const size_t len)
|
||||
{
|
||||
int ret;
|
||||
|
||||
@@ -130,7 +130,7 @@ int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
return ret;
|
||||
}
|
||||
|
||||
int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
int tls_write(tls_t *tls, const void *const buff, const size_t len)
|
||||
{
|
||||
int ret;
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
* TLS implementation with OpenSSL.
|
||||
*/
|
||||
|
||||
#include <errno.h> /* EINTR */
|
||||
#include <errno.h> /* EINTR */
|
||||
#include <string.h>
|
||||
|
||||
#ifndef _WIN32
|
||||
@@ -39,11 +39,11 @@
|
||||
#if (defined LIBRESSL_VERSION_NUMBER && OPENSSL_VERSION_NUMBER == 0x20000000L)
|
||||
#undef OPENSSL_VERSION_NUMBER
|
||||
#if (LIBRESSL_VERSION_NUMBER >= 0x2080000fL)
|
||||
#define OPENSSL_VERSION_NUMBER 0x1010000fL
|
||||
#define OPENSSL_VERSION_NUMBER 0x1010000fL
|
||||
#elif (LIBRESSL_VERSION_NUMBER >= 0x2070000fL)
|
||||
#define OPENSSL_VERSION_NUMBER 0x1000200fL
|
||||
#define OPENSSL_VERSION_NUMBER 0x1000200fL
|
||||
#else
|
||||
#define OPENSSL_VERSION_NUMBER 0x1000107fL
|
||||
#define OPENSSL_VERSION_NUMBER 0x1000107fL
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -169,9 +169,11 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
* Allow only complete wildcards. RFC 6125 discourages wildcard usage
|
||||
* completely, and lists internationalized domain names as a reason
|
||||
* against partial wildcards.
|
||||
* See https://tools.ietf.org/html/rfc6125#section-7.2 for more information.
|
||||
* See https://tools.ietf.org/html/rfc6125#section-7.2 for more
|
||||
* information.
|
||||
*/
|
||||
X509_VERIFY_PARAM_set_hostflags(param, X509_CHECK_FLAG_NO_PARTIAL_WILDCARDS);
|
||||
X509_VERIFY_PARAM_set_hostflags(param,
|
||||
X509_CHECK_FLAG_NO_PARTIAL_WILDCARDS);
|
||||
X509_VERIFY_PARAM_set1_host(param, conn->domain, 0);
|
||||
#endif
|
||||
|
||||
@@ -271,10 +273,9 @@ int tls_stop(tls_t *tls)
|
||||
|
||||
int tls_is_recoverable(int error)
|
||||
{
|
||||
return (error == SSL_ERROR_NONE || error == SSL_ERROR_WANT_READ
|
||||
|| error == SSL_ERROR_WANT_WRITE
|
||||
|| error == SSL_ERROR_WANT_CONNECT
|
||||
|| error == SSL_ERROR_WANT_ACCEPT);
|
||||
return (error == SSL_ERROR_NONE || error == SSL_ERROR_WANT_READ ||
|
||||
error == SSL_ERROR_WANT_WRITE || error == SSL_ERROR_WANT_CONNECT ||
|
||||
error == SSL_ERROR_WANT_ACCEPT);
|
||||
}
|
||||
|
||||
int tls_pending(tls_t *tls)
|
||||
@@ -282,7 +283,7 @@ int tls_pending(tls_t *tls)
|
||||
return SSL_pending(tls->ssl);
|
||||
}
|
||||
|
||||
int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
int tls_read(tls_t *tls, void *const buff, const size_t len)
|
||||
{
|
||||
int ret;
|
||||
|
||||
@@ -292,7 +293,7 @@ int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
return ret;
|
||||
}
|
||||
|
||||
int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
int tls_write(tls_t *tls, const void *const buff, const size_t len)
|
||||
{
|
||||
int ret;
|
||||
|
||||
@@ -315,7 +316,8 @@ static void _tls_sock_wait(tls_t *tls, int error)
|
||||
int nfds;
|
||||
int ret;
|
||||
|
||||
if (error == SSL_ERROR_NONE) return;
|
||||
if (error == SSL_ERROR_NONE)
|
||||
return;
|
||||
|
||||
FD_ZERO(&rfds);
|
||||
FD_ZERO(&wfds);
|
||||
@@ -323,8 +325,9 @@ static void _tls_sock_wait(tls_t *tls, int error)
|
||||
FD_SET(tls->sock, &rfds);
|
||||
if (error == SSL_ERROR_WANT_WRITE)
|
||||
FD_SET(tls->sock, &wfds);
|
||||
nfds = (error == SSL_ERROR_WANT_READ || error == SSL_ERROR_WANT_WRITE) ?
|
||||
tls->sock + 1 : 0;
|
||||
nfds = (error == SSL_ERROR_WANT_READ || error == SSL_ERROR_WANT_WRITE)
|
||||
? tls->sock + 1
|
||||
: 0;
|
||||
do {
|
||||
tv.tv_sec = TLS_TIMEOUT_SEC;
|
||||
tv.tv_usec = TLS_TIMEOUT_USEC;
|
||||
|
||||
@@ -84,13 +84,13 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
|
||||
/* no TLS support on win9x/me, despite what anyone says */
|
||||
if (osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS) {
|
||||
return NULL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
tls = xmpp_alloc(ctx, sizeof(*tls));
|
||||
|
||||
if (!tls) {
|
||||
return NULL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memset(tls, 0, sizeof(*tls));
|
||||
@@ -98,30 +98,29 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
tls->conn = conn;
|
||||
tls->sock = sock;
|
||||
|
||||
if (!(tls->hsec32 = LoadLibrary ("secur32.dll"))) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
if (!(tls->hsec32 = LoadLibrary("secur32.dll"))) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(pInitSecurityInterface =
|
||||
(void *)GetProcAddress(tls->hsec32, "InitSecurityInterfaceA"))) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
(void *)GetProcAddress(tls->hsec32, "InitSecurityInterfaceA"))) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
tls->sft = pInitSecurityInterface();
|
||||
|
||||
if (!tls->sft) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ret = tls->sft->QuerySecurityPackageInfo(UNISP_NAME, &(tls->spi));
|
||||
|
||||
if (ret != SEC_E_OK)
|
||||
{
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
if (ret != SEC_E_OK) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
xmpp_debug(ctx, "TLSS", "QuerySecurityPackageInfo() success");
|
||||
@@ -140,13 +139,13 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
(void)algs;
|
||||
#endif
|
||||
|
||||
ret = tls->sft->AcquireCredentialsHandleA(NULL, UNISP_NAME,
|
||||
SECPKG_CRED_OUTBOUND, NULL, &scred, NULL, NULL, &(tls->hcred), NULL);
|
||||
ret = tls->sft->AcquireCredentialsHandleA(
|
||||
NULL, UNISP_NAME, SECPKG_CRED_OUTBOUND, NULL, &scred, NULL, NULL,
|
||||
&(tls->hcred), NULL);
|
||||
|
||||
if (ret != SEC_E_OK)
|
||||
{
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
if (ret != SEC_E_OK) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
xmpp_debug(ctx, "TLSS", "AcquireCredentialsHandle() success");
|
||||
@@ -155,25 +154,25 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
|
||||
/* This bunch of queries should trip up wine until someone fixes
|
||||
* schannel support there */
|
||||
ret = tls->sft->QueryCredentialsAttributes(&(tls->hcred), SECPKG_ATTR_SUPPORTED_ALGS, &spc_sa);
|
||||
if (ret != SEC_E_OK)
|
||||
{
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
ret = tls->sft->QueryCredentialsAttributes(
|
||||
&(tls->hcred), SECPKG_ATTR_SUPPORTED_ALGS, &spc_sa);
|
||||
if (ret != SEC_E_OK) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ret = tls->sft->QueryCredentialsAttributes(&(tls->hcred), SECPKG_ATTR_CIPHER_STRENGTHS, &spc_cs);
|
||||
if (ret != SEC_E_OK)
|
||||
{
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
ret = tls->sft->QueryCredentialsAttributes(
|
||||
&(tls->hcred), SECPKG_ATTR_CIPHER_STRENGTHS, &spc_cs);
|
||||
if (ret != SEC_E_OK) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ret = tls->sft->QueryCredentialsAttributes(&(tls->hcred), SECPKG_ATTR_SUPPORTED_PROTOCOLS, &spc_sp);
|
||||
if (ret != SEC_E_OK)
|
||||
{
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
ret = tls->sft->QueryCredentialsAttributes(
|
||||
&(tls->hcred), SECPKG_ATTR_SUPPORTED_PROTOCOLS, &spc_sp);
|
||||
if (ret != SEC_E_OK) {
|
||||
tls_free(tls);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return tls;
|
||||
@@ -182,26 +181,26 @@ tls_t *tls_new(xmpp_conn_t *conn)
|
||||
void tls_free(tls_t *tls)
|
||||
{
|
||||
if (tls->recvbuffer) {
|
||||
xmpp_free(tls->ctx, tls->recvbuffer);
|
||||
xmpp_free(tls->ctx, tls->recvbuffer);
|
||||
}
|
||||
|
||||
if (tls->readybuffer) {
|
||||
xmpp_free(tls->ctx, tls->readybuffer);
|
||||
xmpp_free(tls->ctx, tls->readybuffer);
|
||||
}
|
||||
|
||||
if (tls->sendbuffer) {
|
||||
xmpp_free(tls->ctx, tls->sendbuffer);
|
||||
xmpp_free(tls->ctx, tls->sendbuffer);
|
||||
}
|
||||
|
||||
if (tls->init) {
|
||||
tls->sft->FreeCredentialsHandle(&(tls->hcred));
|
||||
tls->sft->FreeCredentialsHandle(&(tls->hcred));
|
||||
}
|
||||
|
||||
tls->sft = NULL;
|
||||
|
||||
if (tls->hsec32) {
|
||||
FreeLibrary(tls->hsec32);
|
||||
tls->hsec32 = NULL;
|
||||
FreeLibrary(tls->hsec32);
|
||||
tls->hsec32 = NULL;
|
||||
}
|
||||
|
||||
xmpp_free(tls->ctx, tls);
|
||||
@@ -225,10 +224,10 @@ int tls_start(tls_t *tls)
|
||||
/* use the domain there as our name */
|
||||
name = tls->conn->domain;
|
||||
|
||||
ctxtreq = ISC_REQ_SEQUENCE_DETECT | ISC_REQ_REPLAY_DETECT
|
||||
| ISC_REQ_CONFIDENTIALITY | ISC_RET_EXTENDED_ERROR
|
||||
| ISC_REQ_ALLOCATE_MEMORY | ISC_REQ_STREAM
|
||||
| ISC_REQ_MANUAL_CRED_VALIDATION | ISC_REQ_INTEGRITY;
|
||||
ctxtreq = ISC_REQ_SEQUENCE_DETECT | ISC_REQ_REPLAY_DETECT |
|
||||
ISC_REQ_CONFIDENTIALITY | ISC_RET_EXTENDED_ERROR |
|
||||
ISC_REQ_ALLOCATE_MEMORY | ISC_REQ_STREAM |
|
||||
ISC_REQ_MANUAL_CRED_VALIDATION | ISC_REQ_INTEGRITY;
|
||||
|
||||
memset(&(sbout[0]), 0, sizeof(sbout[0]));
|
||||
sbout[0].BufferType = SECBUFFER_TOKEN;
|
||||
@@ -251,134 +250,127 @@ int tls_start(tls_t *tls)
|
||||
sbdin.cBuffers = 2;
|
||||
sbdin.pBuffers = sbin;
|
||||
|
||||
ret = tls->sft->InitializeSecurityContextA(&(tls->hcred), NULL, name, ctxtreq, 0, 0,
|
||||
NULL, 0, &(tls->hctxt), &sbdout,
|
||||
&ctxtattr, NULL);
|
||||
ret = tls->sft->InitializeSecurityContextA(
|
||||
&(tls->hcred), NULL, name, ctxtreq, 0, 0, NULL, 0, &(tls->hctxt),
|
||||
&sbdout, &ctxtattr, NULL);
|
||||
|
||||
unsigned char *p = sbin[0].pvBuffer;
|
||||
int len = 0;
|
||||
|
||||
while (ret == SEC_I_CONTINUE_NEEDED
|
||||
|| ret == SEC_I_INCOMPLETE_CREDENTIALS
|
||||
|| ret == SEC_E_INCOMPLETE_MESSAGE) {
|
||||
int inbytes = 0;
|
||||
while (ret == SEC_I_CONTINUE_NEEDED ||
|
||||
ret == SEC_I_INCOMPLETE_CREDENTIALS ||
|
||||
ret == SEC_E_INCOMPLETE_MESSAGE) {
|
||||
int inbytes = 0;
|
||||
|
||||
if (ret != SEC_E_INCOMPLETE_MESSAGE) {
|
||||
len = 0;
|
||||
p = sbin[0].pvBuffer;
|
||||
}
|
||||
if (ret != SEC_E_INCOMPLETE_MESSAGE) {
|
||||
len = 0;
|
||||
p = sbin[0].pvBuffer;
|
||||
}
|
||||
|
||||
if (sbdout.pBuffers[0].cbBuffer) {
|
||||
unsigned char *writebuff = sbdout.pBuffers[0].pvBuffer;
|
||||
unsigned int writelen = sbdout.pBuffers[0].cbBuffer;
|
||||
if (sbdout.pBuffers[0].cbBuffer) {
|
||||
unsigned char *writebuff = sbdout.pBuffers[0].pvBuffer;
|
||||
unsigned int writelen = sbdout.pBuffers[0].cbBuffer;
|
||||
|
||||
sent = sock_write(tls->sock, writebuff, writelen);
|
||||
if (sent == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
}
|
||||
else
|
||||
{
|
||||
writebuff += sent;
|
||||
writelen -= sent;
|
||||
}
|
||||
tls->sft->FreeContextBuffer(sbdout.pBuffers[0].pvBuffer);
|
||||
sbdout.pBuffers[0].pvBuffer = NULL;
|
||||
sbdout.pBuffers[0].cbBuffer = 0;
|
||||
}
|
||||
sent = sock_write(tls->sock, writebuff, writelen);
|
||||
if (sent == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
} else {
|
||||
writebuff += sent;
|
||||
writelen -= sent;
|
||||
}
|
||||
tls->sft->FreeContextBuffer(sbdout.pBuffers[0].pvBuffer);
|
||||
sbdout.pBuffers[0].pvBuffer = NULL;
|
||||
sbdout.pBuffers[0].cbBuffer = 0;
|
||||
}
|
||||
|
||||
/* poll for a bit until the remote server stops sending data, ie it
|
||||
* finishes sending the token */
|
||||
inbytes = 1;
|
||||
{
|
||||
fd_set fds;
|
||||
struct timeval tv;
|
||||
/* poll for a bit until the remote server stops sending data, ie it
|
||||
* finishes sending the token */
|
||||
inbytes = 1;
|
||||
{
|
||||
fd_set fds;
|
||||
struct timeval tv;
|
||||
|
||||
tv.tv_sec = 2;
|
||||
tv.tv_usec = 0;
|
||||
tv.tv_sec = 2;
|
||||
tv.tv_usec = 0;
|
||||
|
||||
FD_ZERO(&fds);
|
||||
FD_SET(tls->sock, &fds);
|
||||
FD_ZERO(&fds);
|
||||
FD_SET(tls->sock, &fds);
|
||||
|
||||
select(tls->sock, &fds, NULL, NULL, &tv);
|
||||
}
|
||||
select(tls->sock, &fds, NULL, NULL, &tv);
|
||||
}
|
||||
|
||||
while (inbytes > 0) {
|
||||
fd_set fds;
|
||||
struct timeval tv;
|
||||
while (inbytes > 0) {
|
||||
fd_set fds;
|
||||
struct timeval tv;
|
||||
|
||||
tv.tv_sec = 0;
|
||||
tv.tv_usec = 1000;
|
||||
tv.tv_sec = 0;
|
||||
tv.tv_usec = 1000;
|
||||
|
||||
FD_ZERO(&fds);
|
||||
FD_SET(tls->sock, &fds);
|
||||
FD_ZERO(&fds);
|
||||
FD_SET(tls->sock, &fds);
|
||||
|
||||
select(tls->sock, &fds, NULL, NULL, &tv);
|
||||
select(tls->sock, &fds, NULL, NULL, &tv);
|
||||
|
||||
inbytes = sock_read(tls->sock, p, tls->spi->cbMaxToken - len);
|
||||
inbytes = sock_read(tls->sock, p, tls->spi->cbMaxToken - len);
|
||||
|
||||
if (inbytes > 0) {
|
||||
len += inbytes;
|
||||
p += inbytes;
|
||||
}
|
||||
else
|
||||
{
|
||||
tls->lasterror = sock_error();
|
||||
}
|
||||
if (inbytes > 0) {
|
||||
len += inbytes;
|
||||
p += inbytes;
|
||||
} else {
|
||||
tls->lasterror = sock_error();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
sbin[0].cbBuffer = len;
|
||||
|
||||
sbin[0].cbBuffer = len;
|
||||
|
||||
ret = tls->sft->InitializeSecurityContextA(&(tls->hcred), &(tls->hctxt), name,
|
||||
ctxtreq, 0, 0, &sbdin, 0,
|
||||
&(tls->hctxt), &sbdout,
|
||||
&ctxtattr, NULL);
|
||||
ret = tls->sft->InitializeSecurityContextA(
|
||||
&(tls->hcred), &(tls->hctxt), name, ctxtreq, 0, 0, &sbdin, 0,
|
||||
&(tls->hctxt), &sbdout, &ctxtattr, NULL);
|
||||
}
|
||||
|
||||
if (ret == SEC_E_OK) {
|
||||
if (sbdout.pBuffers[0].cbBuffer) {
|
||||
unsigned char *writebuff = sbdout.pBuffers[0].pvBuffer;
|
||||
unsigned int writelen = sbdout.pBuffers[0].cbBuffer;
|
||||
sent = sock_write(tls->sock, writebuff, writelen);
|
||||
if (sent == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
}
|
||||
else
|
||||
{
|
||||
writebuff += sent;
|
||||
writelen -= sent;
|
||||
}
|
||||
tls->sft->FreeContextBuffer(sbdout.pBuffers[0].pvBuffer);
|
||||
sbdout.pBuffers[0].pvBuffer = NULL;
|
||||
sbdout.pBuffers[0].cbBuffer = 0;
|
||||
}
|
||||
if (sbdout.pBuffers[0].cbBuffer) {
|
||||
unsigned char *writebuff = sbdout.pBuffers[0].pvBuffer;
|
||||
unsigned int writelen = sbdout.pBuffers[0].cbBuffer;
|
||||
sent = sock_write(tls->sock, writebuff, writelen);
|
||||
if (sent == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
} else {
|
||||
writebuff += sent;
|
||||
writelen -= sent;
|
||||
}
|
||||
tls->sft->FreeContextBuffer(sbdout.pBuffers[0].pvBuffer);
|
||||
sbdout.pBuffers[0].pvBuffer = NULL;
|
||||
sbdout.pBuffers[0].cbBuffer = 0;
|
||||
}
|
||||
}
|
||||
|
||||
xmpp_free(tls->ctx, sbin[0].pvBuffer);
|
||||
|
||||
if (ret != SEC_E_OK) {
|
||||
tls->lasterror = ret;
|
||||
xmpp_error(tls->ctx, "TLSS", "Schannel error 0x%lx", (unsigned long)ret);
|
||||
return 0;
|
||||
tls->lasterror = ret;
|
||||
xmpp_error(tls->ctx, "TLSS", "Schannel error 0x%lx",
|
||||
(unsigned long)ret);
|
||||
return 0;
|
||||
}
|
||||
|
||||
tls->sft->QueryContextAttributes(&(tls->hctxt), SECPKG_ATTR_STREAM_SIZES,
|
||||
&(tls->spcss));
|
||||
&(tls->spcss));
|
||||
|
||||
tls->recvbuffermaxlen = tls->spcss.cbHeader + tls->spcss.cbMaximumMessage
|
||||
+ tls->spcss.cbTrailer;
|
||||
tls->recvbuffer = xmpp_alloc(tls->ctx, tls->recvbuffermaxlen);
|
||||
tls->recvbufferpos = 0;
|
||||
tls->recvbuffermaxlen = tls->spcss.cbHeader + tls->spcss.cbMaximumMessage +
|
||||
tls->spcss.cbTrailer;
|
||||
tls->recvbuffer = xmpp_alloc(tls->ctx, tls->recvbuffermaxlen);
|
||||
tls->recvbufferpos = 0;
|
||||
|
||||
tls->sendbuffermaxlen = tls->spcss.cbHeader + tls->spcss.cbMaximumMessage
|
||||
+ tls->spcss.cbTrailer;
|
||||
tls->sendbuffer = xmpp_alloc(tls->ctx, tls->sendbuffermaxlen);
|
||||
tls->sendbufferpos = 0;
|
||||
tls->sendbufferlen = 0;
|
||||
tls->sendbuffermaxlen = tls->spcss.cbHeader + tls->spcss.cbMaximumMessage +
|
||||
tls->spcss.cbTrailer;
|
||||
tls->sendbuffer = xmpp_alloc(tls->ctx, tls->sendbuffermaxlen);
|
||||
tls->sendbufferpos = 0;
|
||||
tls->sendbufferlen = 0;
|
||||
|
||||
tls->readybuffer = xmpp_alloc(tls->ctx, tls->spcss.cbMaximumMessage);
|
||||
tls->readybufferpos = 0;
|
||||
tls->readybufferlen = 0;
|
||||
tls->readybuffer = xmpp_alloc(tls->ctx, tls->spcss.cbMaximumMessage);
|
||||
tls->readybufferpos = 0;
|
||||
tls->readybufferlen = 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -395,67 +387,67 @@ int tls_error(tls_t *tls)
|
||||
|
||||
int tls_is_recoverable(int error)
|
||||
{
|
||||
return (error == SEC_E_OK || error == SEC_E_INCOMPLETE_MESSAGE
|
||||
|| error == WSAEWOULDBLOCK || error == WSAEMSGSIZE
|
||||
|| error == WSAEINPROGRESS);
|
||||
return (error == SEC_E_OK || error == SEC_E_INCOMPLETE_MESSAGE ||
|
||||
error == WSAEWOULDBLOCK || error == WSAEMSGSIZE ||
|
||||
error == WSAEINPROGRESS);
|
||||
}
|
||||
|
||||
int tls_pending(tls_t *tls) {
|
||||
// There are 3 cases:
|
||||
// - there is data in ready buffer, so it is by default pending
|
||||
// - there is data in recv buffer. If it is not decrypted yet, means it
|
||||
// was incomplete. This should be processed again only if there is data
|
||||
// on the physical connection
|
||||
// - there is data on the physical connection. This case is treated
|
||||
// outside the tls (in event.c)
|
||||
int tls_pending(tls_t *tls)
|
||||
{
|
||||
// There are 3 cases:
|
||||
// - there is data in ready buffer, so it is by default pending
|
||||
// - there is data in recv buffer. If it is not decrypted yet, means it
|
||||
// was incomplete. This should be processed again only if there is data
|
||||
// on the physical connection
|
||||
// - there is data on the physical connection. This case is treated
|
||||
// outside the tls (in event.c)
|
||||
|
||||
if (tls->readybufferpos < tls->readybufferlen) {
|
||||
return tls->readybufferlen - tls->readybufferpos;
|
||||
}
|
||||
return tls->readybufferlen - tls->readybufferpos;
|
||||
}
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
int tls_read(tls_t *tls, void *const buff, const size_t len)
|
||||
{
|
||||
int bytes;
|
||||
|
||||
/* first, if we've got some ready data, put that in the buffer */
|
||||
if (tls->readybufferpos < tls->readybufferlen)
|
||||
{
|
||||
if (len < tls->readybufferlen - tls->readybufferpos) {
|
||||
bytes = len;
|
||||
} else {
|
||||
bytes = tls->readybufferlen - tls->readybufferpos;
|
||||
}
|
||||
if (tls->readybufferpos < tls->readybufferlen) {
|
||||
if (len < tls->readybufferlen - tls->readybufferpos) {
|
||||
bytes = len;
|
||||
} else {
|
||||
bytes = tls->readybufferlen - tls->readybufferpos;
|
||||
}
|
||||
|
||||
memcpy(buff, tls->readybuffer + tls->readybufferpos, bytes);
|
||||
memcpy(buff, tls->readybuffer + tls->readybufferpos, bytes);
|
||||
|
||||
if (len < tls->readybufferlen - tls->readybufferpos) {
|
||||
tls->readybufferpos += bytes;
|
||||
return bytes;
|
||||
} else {
|
||||
unsigned char *newbuff = buff;
|
||||
int read;
|
||||
tls->readybufferpos += bytes;
|
||||
newbuff += bytes;
|
||||
read = tls_read(tls, newbuff, len - bytes);
|
||||
if (len < tls->readybufferlen - tls->readybufferpos) {
|
||||
tls->readybufferpos += bytes;
|
||||
return bytes;
|
||||
} else {
|
||||
unsigned char *newbuff = buff;
|
||||
int read;
|
||||
tls->readybufferpos += bytes;
|
||||
newbuff += bytes;
|
||||
read = tls_read(tls, newbuff, len - bytes);
|
||||
|
||||
if (read == -1) {
|
||||
if (tls_is_recoverable(tls->lasterror)) {
|
||||
return bytes;
|
||||
}
|
||||
if (read == -1) {
|
||||
if (tls_is_recoverable(tls->lasterror)) {
|
||||
return bytes;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
return bytes + read;
|
||||
}
|
||||
return bytes + read;
|
||||
}
|
||||
}
|
||||
|
||||
/* next, top up our recv buffer */
|
||||
bytes = sock_read(tls->sock, tls->recvbuffer + tls->recvbufferpos,
|
||||
tls->recvbuffermaxlen - tls->recvbufferpos);
|
||||
tls->recvbuffermaxlen - tls->recvbufferpos);
|
||||
|
||||
if (bytes == 0) {
|
||||
tls->lasterror = WSAECONNRESET;
|
||||
@@ -463,76 +455,75 @@ int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
}
|
||||
|
||||
if (bytes == -1) {
|
||||
if (!tls_is_recoverable(sock_error())) {
|
||||
tls->lasterror = sock_error();
|
||||
return -1;
|
||||
}
|
||||
if (!tls_is_recoverable(sock_error())) {
|
||||
tls->lasterror = sock_error();
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (bytes > 0) {
|
||||
tls->recvbufferpos += bytes;
|
||||
tls->recvbufferpos += bytes;
|
||||
}
|
||||
|
||||
/* next, try to decrypt the recv buffer */
|
||||
if (tls->recvbufferpos > 0) {
|
||||
SecBufferDesc sbddec;
|
||||
SecBuffer sbdec[4];
|
||||
int ret;
|
||||
SecBufferDesc sbddec;
|
||||
SecBuffer sbdec[4];
|
||||
int ret;
|
||||
|
||||
memset(&sbddec, 0, sizeof(sbddec));
|
||||
sbddec.ulVersion = SECBUFFER_VERSION;
|
||||
sbddec.cBuffers = 4;
|
||||
sbddec.pBuffers = sbdec;
|
||||
memset(&sbddec, 0, sizeof(sbddec));
|
||||
sbddec.ulVersion = SECBUFFER_VERSION;
|
||||
sbddec.cBuffers = 4;
|
||||
sbddec.pBuffers = sbdec;
|
||||
|
||||
memset(&(sbdec[0]), 0, sizeof(sbdec[0]));
|
||||
sbdec[0].BufferType = SECBUFFER_DATA;
|
||||
sbdec[0].pvBuffer = tls->recvbuffer;
|
||||
sbdec[0].cbBuffer = tls->recvbufferpos;
|
||||
memset(&(sbdec[0]), 0, sizeof(sbdec[0]));
|
||||
sbdec[0].BufferType = SECBUFFER_DATA;
|
||||
sbdec[0].pvBuffer = tls->recvbuffer;
|
||||
sbdec[0].cbBuffer = tls->recvbufferpos;
|
||||
|
||||
memset(&(sbdec[1]), 0, sizeof(sbdec[1]));
|
||||
sbdec[1].BufferType = SECBUFFER_EMPTY;
|
||||
memset(&(sbdec[1]), 0, sizeof(sbdec[1]));
|
||||
sbdec[1].BufferType = SECBUFFER_EMPTY;
|
||||
|
||||
memset(&(sbdec[2]), 0, sizeof(sbdec[2]));
|
||||
sbdec[2].BufferType = SECBUFFER_EMPTY;
|
||||
memset(&(sbdec[2]), 0, sizeof(sbdec[2]));
|
||||
sbdec[2].BufferType = SECBUFFER_EMPTY;
|
||||
|
||||
memset(&(sbdec[3]), 0, sizeof(sbdec[3]));
|
||||
sbdec[3].BufferType = SECBUFFER_EMPTY;
|
||||
memset(&(sbdec[3]), 0, sizeof(sbdec[3]));
|
||||
sbdec[3].BufferType = SECBUFFER_EMPTY;
|
||||
|
||||
ret = tls->sft->DecryptMessage(&(tls->hctxt), &sbddec, 0, NULL);
|
||||
ret = tls->sft->DecryptMessage(&(tls->hctxt), &sbddec, 0, NULL);
|
||||
|
||||
if (ret == SEC_E_OK) {
|
||||
memcpy(tls->readybuffer, sbdec[1].pvBuffer, sbdec[1].cbBuffer);
|
||||
tls->readybufferpos = 0;
|
||||
tls->readybufferlen = sbdec[1].cbBuffer;
|
||||
/* have we got some data left over? If so, copy it to the start
|
||||
* of the recv buffer */
|
||||
if (sbdec[3].BufferType == SECBUFFER_EXTRA) {
|
||||
memcpy(tls->recvbuffer, sbdec[3].pvBuffer, sbdec[3].cbBuffer);
|
||||
tls->recvbufferpos = sbdec[3].cbBuffer;
|
||||
} else {
|
||||
tls->recvbufferpos = 0;
|
||||
}
|
||||
if (ret == SEC_E_OK) {
|
||||
memcpy(tls->readybuffer, sbdec[1].pvBuffer, sbdec[1].cbBuffer);
|
||||
tls->readybufferpos = 0;
|
||||
tls->readybufferlen = sbdec[1].cbBuffer;
|
||||
/* have we got some data left over? If so, copy it to the start
|
||||
* of the recv buffer */
|
||||
if (sbdec[3].BufferType == SECBUFFER_EXTRA) {
|
||||
memcpy(tls->recvbuffer, sbdec[3].pvBuffer, sbdec[3].cbBuffer);
|
||||
tls->recvbufferpos = sbdec[3].cbBuffer;
|
||||
} else {
|
||||
tls->recvbufferpos = 0;
|
||||
}
|
||||
|
||||
return tls_read(tls, buff, len);
|
||||
} else if (ret == SEC_E_INCOMPLETE_MESSAGE) {
|
||||
tls->lasterror = SEC_E_INCOMPLETE_MESSAGE;
|
||||
return -1;
|
||||
} else if (ret == SEC_I_RENEGOTIATE) {
|
||||
ret = tls_start(tls);
|
||||
if (!ret)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
return tls_read(tls, buff, len);
|
||||
} else if (ret == SEC_E_INCOMPLETE_MESSAGE) {
|
||||
tls->lasterror = SEC_E_INCOMPLETE_MESSAGE;
|
||||
return -1;
|
||||
} else if (ret == SEC_I_RENEGOTIATE) {
|
||||
ret = tls_start(tls);
|
||||
if (!ret) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* fake an incomplete message so we're called again */
|
||||
tls->lasterror = SEC_E_INCOMPLETE_MESSAGE;
|
||||
return -1;
|
||||
}
|
||||
/* fake an incomplete message so we're called again */
|
||||
tls->lasterror = SEC_E_INCOMPLETE_MESSAGE;
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* something bad happened, so we bail */
|
||||
tls->lasterror = ret;
|
||||
/* something bad happened, so we bail */
|
||||
tls->lasterror = ret;
|
||||
|
||||
return -1;
|
||||
return -1;
|
||||
}
|
||||
|
||||
tls->lasterror = SEC_E_INCOMPLETE_MESSAGE;
|
||||
@@ -542,29 +533,28 @@ int tls_read(tls_t *tls, void * const buff, const size_t len)
|
||||
|
||||
int tls_clear_pending_write(tls_t *tls)
|
||||
{
|
||||
if (tls->sendbufferpos < tls->sendbufferlen)
|
||||
{
|
||||
int bytes;
|
||||
if (tls->sendbufferpos < tls->sendbufferlen) {
|
||||
int bytes;
|
||||
|
||||
bytes = sock_write(tls->sock, tls->sendbuffer + tls->sendbufferpos,
|
||||
tls->sendbufferlen - tls->sendbufferpos);
|
||||
bytes = sock_write(tls->sock, tls->sendbuffer + tls->sendbufferpos,
|
||||
tls->sendbufferlen - tls->sendbufferpos);
|
||||
|
||||
if (bytes == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
return -1;
|
||||
} else if (bytes > 0) {
|
||||
tls->sendbufferpos += bytes;
|
||||
}
|
||||
if (bytes == -1) {
|
||||
tls->lasterror = sock_error();
|
||||
return -1;
|
||||
} else if (bytes > 0) {
|
||||
tls->sendbufferpos += bytes;
|
||||
}
|
||||
|
||||
if (tls->sendbufferpos < tls->sendbufferlen) {
|
||||
return 0;
|
||||
}
|
||||
if (tls->sendbufferpos < tls->sendbufferlen) {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
int tls_write(tls_t *tls, const void *const buff, const size_t len)
|
||||
{
|
||||
SecBufferDesc sbdenc;
|
||||
SecBuffer sbenc[4];
|
||||
@@ -573,7 +563,7 @@ int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
|
||||
ret = tls_clear_pending_write(tls);
|
||||
if (ret <= 0) {
|
||||
return ret;
|
||||
return ret;
|
||||
}
|
||||
|
||||
tls->sendbufferpos = 0;
|
||||
@@ -601,51 +591,49 @@ int tls_write(tls_t *tls, const void * const buff, const size_t len)
|
||||
|
||||
sbenc[1].pvBuffer = tls->sendbuffer + tls->spcss.cbHeader;
|
||||
|
||||
while (remain > 0)
|
||||
{
|
||||
if (remain > tls->spcss.cbMaximumMessage) {
|
||||
sbenc[1].cbBuffer = tls->spcss.cbMaximumMessage;
|
||||
} else {
|
||||
sbenc[1].cbBuffer = remain;
|
||||
}
|
||||
while (remain > 0) {
|
||||
if (remain > tls->spcss.cbMaximumMessage) {
|
||||
sbenc[1].cbBuffer = tls->spcss.cbMaximumMessage;
|
||||
} else {
|
||||
sbenc[1].cbBuffer = remain;
|
||||
}
|
||||
|
||||
sbenc[2].pvBuffer = (unsigned char *)sbenc[1].pvBuffer
|
||||
+ sbenc[1].cbBuffer;
|
||||
sbenc[2].pvBuffer =
|
||||
(unsigned char *)sbenc[1].pvBuffer + sbenc[1].cbBuffer;
|
||||
sbenc[2].cbBuffer = tls->spcss.cbTrailer;
|
||||
|
||||
memcpy(sbenc[1].pvBuffer, p, sbenc[1].cbBuffer);
|
||||
p += tls->spcss.cbMaximumMessage;
|
||||
memcpy(sbenc[1].pvBuffer, p, sbenc[1].cbBuffer);
|
||||
p += tls->spcss.cbMaximumMessage;
|
||||
|
||||
tls->sendbufferlen = sbenc[0].cbBuffer + sbenc[1].cbBuffer
|
||||
+ sbenc[2].cbBuffer;
|
||||
tls->sendbufferlen =
|
||||
sbenc[0].cbBuffer + sbenc[1].cbBuffer + sbenc[2].cbBuffer;
|
||||
|
||||
ret = tls->sft->EncryptMessage(&(tls->hctxt), 0, &sbdenc, 0);
|
||||
ret = tls->sft->EncryptMessage(&(tls->hctxt), 0, &sbdenc, 0);
|
||||
|
||||
if (ret != SEC_E_OK) {
|
||||
tls->lasterror = ret;
|
||||
return -1;
|
||||
}
|
||||
if (ret != SEC_E_OK) {
|
||||
tls->lasterror = ret;
|
||||
return -1;
|
||||
}
|
||||
|
||||
tls->sendbufferpos = 0;
|
||||
tls->sendbufferpos = 0;
|
||||
|
||||
ret = tls_clear_pending_write(tls);
|
||||
ret = tls_clear_pending_write(tls);
|
||||
|
||||
if (ret == -1 && !tls_is_recoverable(tls_error(tls))) {
|
||||
return -1;
|
||||
}
|
||||
if (ret == -1 && !tls_is_recoverable(tls_error(tls))) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (remain > tls->spcss.cbMaximumMessage) {
|
||||
sent += tls->spcss.cbMaximumMessage;
|
||||
remain -= tls->spcss.cbMaximumMessage;
|
||||
} else {
|
||||
sent += remain;
|
||||
remain = 0;
|
||||
}
|
||||
|
||||
if (ret == 0 || (ret == -1 && tls_is_recoverable(tls_error(tls)))) {
|
||||
return sent;
|
||||
}
|
||||
if (remain > tls->spcss.cbMaximumMessage) {
|
||||
sent += tls->spcss.cbMaximumMessage;
|
||||
remain -= tls->spcss.cbMaximumMessage;
|
||||
} else {
|
||||
sent += remain;
|
||||
remain = 0;
|
||||
}
|
||||
|
||||
if (ret == 0 || (ret == -1 && tls_is_recoverable(tls_error(tls)))) {
|
||||
return sent;
|
||||
}
|
||||
}
|
||||
|
||||
return sent;
|
||||
|
||||
@@ -38,7 +38,7 @@
|
||||
*
|
||||
* @return a new allocates string with the same data as s or NULL on error
|
||||
*/
|
||||
char *xmpp_strdup(const xmpp_ctx_t * const ctx, const char * const s)
|
||||
char *xmpp_strdup(const xmpp_ctx_t *const ctx, const char *const s)
|
||||
{
|
||||
size_t len;
|
||||
char *copy;
|
||||
@@ -135,7 +135,7 @@ uint64_t time_elapsed(uint64_t t1, uint64_t t2)
|
||||
*
|
||||
* @param conn a Strophe connection object
|
||||
*/
|
||||
void disconnect_mem_error(xmpp_conn_t * const conn)
|
||||
void disconnect_mem_error(xmpp_conn_t *const conn)
|
||||
{
|
||||
xmpp_error(conn->ctx, "xmpp", "Memory allocation error");
|
||||
xmpp_disconnect(conn);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* util.h
|
||||
** strophe XMPP client library -- various utility functions
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
** This software is provided AS-IS with no warranty, either express
|
||||
** or implied.
|
||||
|
||||
321
strophe.h
321
strophe.h
@@ -16,7 +16,7 @@
|
||||
#ifndef __LIBSTROPHE_STROPHE_H__
|
||||
#define __LIBSTROPHE_STROPHE_H__
|
||||
|
||||
#include <stddef.h> /* size_t */
|
||||
#include <stddef.h> /* size_t */
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
@@ -118,18 +118,18 @@ typedef struct _xmpp_log_t xmpp_log_t;
|
||||
/* opaque run time context containing the above hooks */
|
||||
typedef struct _xmpp_ctx_t xmpp_ctx_t;
|
||||
|
||||
xmpp_ctx_t *xmpp_ctx_new(const xmpp_mem_t * const mem,
|
||||
const xmpp_log_t * const log);
|
||||
void xmpp_ctx_free(xmpp_ctx_t * const ctx);
|
||||
xmpp_ctx_t *xmpp_ctx_new(const xmpp_mem_t *const mem,
|
||||
const xmpp_log_t *const log);
|
||||
void xmpp_ctx_free(xmpp_ctx_t *const ctx);
|
||||
|
||||
/* free some blocks returned by other APIs, for example the
|
||||
buffer you get from xmpp_stanza_to_text */
|
||||
void xmpp_free(const xmpp_ctx_t * const ctx, void *p);
|
||||
void xmpp_free(const xmpp_ctx_t *const ctx, void *p);
|
||||
|
||||
struct _xmpp_mem_t {
|
||||
void *(*alloc)(const size_t size, void * const userdata);
|
||||
void (*free)(void *p, void * const userdata);
|
||||
void *(*realloc)(void *p, const size_t size, void * const userdata);
|
||||
void *(*alloc)(const size_t size, void *const userdata);
|
||||
void (*free)(void *p, void *const userdata);
|
||||
void *(*realloc)(void *p, const size_t size, void *const userdata);
|
||||
void *userdata;
|
||||
};
|
||||
|
||||
@@ -140,16 +140,12 @@ typedef enum {
|
||||
XMPP_LEVEL_ERROR
|
||||
} xmpp_log_level_t;
|
||||
|
||||
typedef enum {
|
||||
XMPP_UNKNOWN,
|
||||
XMPP_CLIENT,
|
||||
XMPP_COMPONENT
|
||||
} xmpp_conn_type_t;
|
||||
typedef enum { XMPP_UNKNOWN, XMPP_CLIENT, XMPP_COMPONENT } xmpp_conn_type_t;
|
||||
|
||||
typedef void (*xmpp_log_handler)(void * const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const msg);
|
||||
typedef void (*xmpp_log_handler)(void *const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char *const area,
|
||||
const char *const msg);
|
||||
|
||||
struct _xmpp_log_t {
|
||||
xmpp_log_handler handler;
|
||||
@@ -166,17 +162,17 @@ typedef struct _xmpp_conn_t xmpp_conn_t;
|
||||
typedef struct _xmpp_stanza_t xmpp_stanza_t;
|
||||
|
||||
/* connection flags */
|
||||
#define XMPP_CONN_FLAG_DISABLE_TLS (1UL << 0)
|
||||
#define XMPP_CONN_FLAG_DISABLE_TLS (1UL << 0)
|
||||
#define XMPP_CONN_FLAG_MANDATORY_TLS (1UL << 1)
|
||||
#define XMPP_CONN_FLAG_LEGACY_SSL (1UL << 2)
|
||||
#define XMPP_CONN_FLAG_LEGACY_SSL (1UL << 2)
|
||||
/** @def XMPP_CONN_FLAG_TRUST_TLS
|
||||
* Trust server's certificate even if it is invalid.
|
||||
*/
|
||||
#define XMPP_CONN_FLAG_TRUST_TLS (1UL << 3)
|
||||
#define XMPP_CONN_FLAG_TRUST_TLS (1UL << 3)
|
||||
/** @def XMPP_CONN_FLAG_LEGACY_AUTH
|
||||
* Enable legacy authentication support.
|
||||
*/
|
||||
#define XMPP_CONN_FLAG_LEGACY_AUTH (1UL << 4)
|
||||
#define XMPP_CONN_FLAG_LEGACY_AUTH (1UL << 4)
|
||||
|
||||
/* connect callback */
|
||||
typedef enum {
|
||||
@@ -219,98 +215,101 @@ typedef struct {
|
||||
xmpp_stanza_t *stanza;
|
||||
} xmpp_stream_error_t;
|
||||
|
||||
typedef void (*xmpp_conn_handler)(xmpp_conn_t * const conn,
|
||||
const xmpp_conn_event_t event,
|
||||
const int error,
|
||||
xmpp_stream_error_t * const stream_error,
|
||||
void * const userdata);
|
||||
typedef void (*xmpp_conn_handler)(xmpp_conn_t *const conn,
|
||||
const xmpp_conn_event_t event,
|
||||
const int error,
|
||||
xmpp_stream_error_t *const stream_error,
|
||||
void *const userdata);
|
||||
|
||||
void xmpp_send_error(xmpp_conn_t * const conn, xmpp_error_type_t const type, char * const text);
|
||||
xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t * const ctx);
|
||||
xmpp_conn_t *xmpp_conn_clone(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_release(xmpp_conn_t * const conn);
|
||||
void xmpp_send_error(xmpp_conn_t *const conn,
|
||||
xmpp_error_type_t const type,
|
||||
char *const text);
|
||||
xmpp_conn_t *xmpp_conn_new(xmpp_ctx_t *const ctx);
|
||||
xmpp_conn_t *xmpp_conn_clone(xmpp_conn_t *const conn);
|
||||
int xmpp_conn_release(xmpp_conn_t *const conn);
|
||||
|
||||
long xmpp_conn_get_flags(const xmpp_conn_t * const conn);
|
||||
int xmpp_conn_set_flags(xmpp_conn_t * const conn, long flags);
|
||||
const char *xmpp_conn_get_jid(const xmpp_conn_t * const conn);
|
||||
const char *xmpp_conn_get_bound_jid(const xmpp_conn_t * const conn);
|
||||
void xmpp_conn_set_jid(xmpp_conn_t * const conn, const char * const jid);
|
||||
const char *xmpp_conn_get_pass(const xmpp_conn_t * const conn);
|
||||
void xmpp_conn_set_pass(xmpp_conn_t * const conn, const char * const pass);
|
||||
xmpp_ctx_t *xmpp_conn_get_context(xmpp_conn_t * const conn);
|
||||
void xmpp_conn_disable_tls(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_is_secured(xmpp_conn_t * const conn);
|
||||
void xmpp_conn_set_keepalive(xmpp_conn_t * const conn, int timeout, int interval);
|
||||
int xmpp_conn_is_connecting(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_is_connected(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_is_disconnected(xmpp_conn_t * const conn);
|
||||
long xmpp_conn_get_flags(const xmpp_conn_t *const conn);
|
||||
int xmpp_conn_set_flags(xmpp_conn_t *const conn, long flags);
|
||||
const char *xmpp_conn_get_jid(const xmpp_conn_t *const conn);
|
||||
const char *xmpp_conn_get_bound_jid(const xmpp_conn_t *const conn);
|
||||
void xmpp_conn_set_jid(xmpp_conn_t *const conn, const char *const jid);
|
||||
const char *xmpp_conn_get_pass(const xmpp_conn_t *const conn);
|
||||
void xmpp_conn_set_pass(xmpp_conn_t *const conn, const char *const pass);
|
||||
xmpp_ctx_t *xmpp_conn_get_context(xmpp_conn_t *const conn);
|
||||
void xmpp_conn_disable_tls(xmpp_conn_t *const conn);
|
||||
int xmpp_conn_is_secured(xmpp_conn_t *const conn);
|
||||
void xmpp_conn_set_keepalive(xmpp_conn_t *const conn,
|
||||
int timeout,
|
||||
int interval);
|
||||
int xmpp_conn_is_connecting(xmpp_conn_t *const conn);
|
||||
int xmpp_conn_is_connected(xmpp_conn_t *const conn);
|
||||
int xmpp_conn_is_disconnected(xmpp_conn_t *const conn);
|
||||
|
||||
int xmpp_connect_client(xmpp_conn_t * const conn,
|
||||
const char * const altdomain,
|
||||
unsigned short altport,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata);
|
||||
int xmpp_connect_client(xmpp_conn_t *const conn,
|
||||
const char *const altdomain,
|
||||
unsigned short altport,
|
||||
xmpp_conn_handler callback,
|
||||
void *const userdata);
|
||||
|
||||
int xmpp_connect_component(xmpp_conn_t * const conn, const char * const server,
|
||||
unsigned short port, xmpp_conn_handler callback,
|
||||
void * const userdata);
|
||||
int xmpp_connect_component(xmpp_conn_t *const conn,
|
||||
const char *const server,
|
||||
unsigned short port,
|
||||
xmpp_conn_handler callback,
|
||||
void *const userdata);
|
||||
|
||||
int xmpp_connect_raw(xmpp_conn_t * const conn,
|
||||
const char * const altdomain,
|
||||
int xmpp_connect_raw(xmpp_conn_t *const conn,
|
||||
const char *const altdomain,
|
||||
unsigned short altport,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata);
|
||||
int xmpp_conn_open_stream_default(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_open_stream(xmpp_conn_t * const conn, char **attributes,
|
||||
void *const userdata);
|
||||
int xmpp_conn_open_stream_default(xmpp_conn_t *const conn);
|
||||
int xmpp_conn_open_stream(xmpp_conn_t *const conn,
|
||||
char **attributes,
|
||||
size_t attributes_len);
|
||||
int xmpp_conn_tls_start(xmpp_conn_t * const conn);
|
||||
int xmpp_conn_tls_start(xmpp_conn_t *const conn);
|
||||
|
||||
void xmpp_disconnect(xmpp_conn_t * const conn);
|
||||
void xmpp_disconnect(xmpp_conn_t *const conn);
|
||||
|
||||
void xmpp_send(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza);
|
||||
|
||||
void xmpp_send_raw_string(xmpp_conn_t * const conn,
|
||||
const char * const fmt, ...);
|
||||
void xmpp_send_raw(xmpp_conn_t * const conn,
|
||||
const char * const data, const size_t len);
|
||||
void xmpp_send(xmpp_conn_t *const conn, xmpp_stanza_t *const stanza);
|
||||
|
||||
void xmpp_send_raw_string(xmpp_conn_t *const conn, const char *const fmt, ...);
|
||||
void xmpp_send_raw(xmpp_conn_t *const conn,
|
||||
const char *const data,
|
||||
const size_t len);
|
||||
|
||||
/* handlers */
|
||||
|
||||
/* if the handle returns false it is removed */
|
||||
typedef int (*xmpp_timed_handler)(xmpp_conn_t * const conn,
|
||||
void * const userdata);
|
||||
|
||||
void xmpp_timed_handler_add(xmpp_conn_t * const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void * const userdata);
|
||||
void xmpp_timed_handler_delete(xmpp_conn_t * const conn,
|
||||
xmpp_timed_handler handler);
|
||||
typedef int (*xmpp_timed_handler)(xmpp_conn_t *const conn,
|
||||
void *const userdata);
|
||||
|
||||
void xmpp_timed_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler,
|
||||
const unsigned long period,
|
||||
void *const userdata);
|
||||
void xmpp_timed_handler_delete(xmpp_conn_t *const conn,
|
||||
xmpp_timed_handler handler);
|
||||
|
||||
/* if the handler returns false it is removed */
|
||||
typedef int (*xmpp_handler)(xmpp_conn_t * const conn,
|
||||
xmpp_stanza_t * const stanza,
|
||||
void * const userdata);
|
||||
typedef int (*xmpp_handler)(xmpp_conn_t *const conn,
|
||||
xmpp_stanza_t *const stanza,
|
||||
void *const userdata);
|
||||
|
||||
void xmpp_handler_add(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata);
|
||||
void xmpp_handler_delete(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler);
|
||||
void xmpp_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata);
|
||||
void xmpp_handler_delete(xmpp_conn_t *const conn, xmpp_handler handler);
|
||||
|
||||
void xmpp_id_handler_add(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata);
|
||||
void xmpp_id_handler_delete(xmpp_conn_t * const conn,
|
||||
xmpp_handler handler,
|
||||
const char * const id);
|
||||
void xmpp_id_handler_add(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char *const id,
|
||||
void *const userdata);
|
||||
void xmpp_id_handler_delete(xmpp_conn_t *const conn,
|
||||
xmpp_handler handler,
|
||||
const char *const id);
|
||||
|
||||
/*
|
||||
void xmpp_register_stanza_handler(conn, stanza, xmlns, type, handler)
|
||||
@@ -322,93 +321,98 @@ void xmpp_register_stanza_handler(conn, stanza, xmlns, type, handler)
|
||||
xmpp_stanza_t *xmpp_stanza_new(xmpp_ctx_t *ctx);
|
||||
|
||||
/* clone a stanza */
|
||||
xmpp_stanza_t *xmpp_stanza_clone(xmpp_stanza_t * const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_clone(xmpp_stanza_t *const stanza);
|
||||
|
||||
/* copies a stanza and all children */
|
||||
xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t * const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_copy(const xmpp_stanza_t *const stanza);
|
||||
|
||||
/* free a stanza object and it's contents */
|
||||
int xmpp_stanza_release(xmpp_stanza_t * const stanza);
|
||||
int xmpp_stanza_release(xmpp_stanza_t *const stanza);
|
||||
|
||||
xmpp_ctx_t *xmpp_stanza_get_context(const xmpp_stanza_t * const stanza);
|
||||
xmpp_ctx_t *xmpp_stanza_get_context(const xmpp_stanza_t *const stanza);
|
||||
|
||||
int xmpp_stanza_is_text(xmpp_stanza_t * const stanza);
|
||||
int xmpp_stanza_is_tag(xmpp_stanza_t * const stanza);
|
||||
int xmpp_stanza_is_text(xmpp_stanza_t *const stanza);
|
||||
int xmpp_stanza_is_tag(xmpp_stanza_t *const stanza);
|
||||
|
||||
/* marshall a stanza into text for transmission or display */
|
||||
int xmpp_stanza_to_text(xmpp_stanza_t *stanza,
|
||||
char ** const buf, size_t * const buflen);
|
||||
char **const buf,
|
||||
size_t *const buflen);
|
||||
|
||||
xmpp_stanza_t *xmpp_stanza_get_children(xmpp_stanza_t * const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name(xmpp_stanza_t * const stanza,
|
||||
const char * const name);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_ns(xmpp_stanza_t * const stanza,
|
||||
const char * const ns);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name_and_ns(xmpp_stanza_t * const stanza,
|
||||
const char * const name,
|
||||
const char * const ns);
|
||||
xmpp_stanza_t *xmpp_stanza_get_next(xmpp_stanza_t * const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_get_children(xmpp_stanza_t *const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name(xmpp_stanza_t *const stanza,
|
||||
const char *const name);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_ns(xmpp_stanza_t *const stanza,
|
||||
const char *const ns);
|
||||
xmpp_stanza_t *xmpp_stanza_get_child_by_name_and_ns(xmpp_stanza_t *const stanza,
|
||||
const char *const name,
|
||||
const char *const ns);
|
||||
xmpp_stanza_t *xmpp_stanza_get_next(xmpp_stanza_t *const stanza);
|
||||
int xmpp_stanza_add_child(xmpp_stanza_t *stanza, xmpp_stanza_t *child);
|
||||
int xmpp_stanza_add_child_ex(xmpp_stanza_t *stanza, xmpp_stanza_t *child,
|
||||
int xmpp_stanza_add_child_ex(xmpp_stanza_t *stanza,
|
||||
xmpp_stanza_t *child,
|
||||
int do_clone);
|
||||
|
||||
const char *xmpp_stanza_get_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const name);
|
||||
int xmpp_stanza_get_attribute_count(xmpp_stanza_t * const stanza);
|
||||
int xmpp_stanza_get_attributes(xmpp_stanza_t * const stanza,
|
||||
const char **attr, int attrlen);
|
||||
const char *xmpp_stanza_get_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const name);
|
||||
int xmpp_stanza_get_attribute_count(xmpp_stanza_t *const stanza);
|
||||
int xmpp_stanza_get_attributes(xmpp_stanza_t *const stanza,
|
||||
const char **attr,
|
||||
int attrlen);
|
||||
/* concatenate all child text nodes. this function
|
||||
* returns a string that must be freed by the caller */
|
||||
char *xmpp_stanza_get_text(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_text_ptr(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_name(xmpp_stanza_t * const stanza);
|
||||
char *xmpp_stanza_get_text(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_text_ptr(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_name(xmpp_stanza_t *const stanza);
|
||||
/* set_attribute adds/replaces attributes */
|
||||
int xmpp_stanza_set_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const key,
|
||||
const char * const value);
|
||||
int xmpp_stanza_set_name(xmpp_stanza_t *stanza,
|
||||
const char * const name);
|
||||
int xmpp_stanza_set_text(xmpp_stanza_t *stanza,
|
||||
const char * const text);
|
||||
int xmpp_stanza_set_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const key,
|
||||
const char *const value);
|
||||
int xmpp_stanza_set_name(xmpp_stanza_t *stanza, const char *const name);
|
||||
int xmpp_stanza_set_text(xmpp_stanza_t *stanza, const char *const text);
|
||||
int xmpp_stanza_set_text_with_size(xmpp_stanza_t *stanza,
|
||||
const char * const text,
|
||||
const size_t size);
|
||||
int xmpp_stanza_del_attribute(xmpp_stanza_t * const stanza,
|
||||
const char * const name);
|
||||
const char *const text,
|
||||
const size_t size);
|
||||
int xmpp_stanza_del_attribute(xmpp_stanza_t *const stanza,
|
||||
const char *const name);
|
||||
|
||||
/* common stanza helpers */
|
||||
const char *xmpp_stanza_get_ns(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_type(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_id(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_to(xmpp_stanza_t * const stanza);
|
||||
const char *xmpp_stanza_get_from(xmpp_stanza_t * const stanza);
|
||||
int xmpp_stanza_set_ns(xmpp_stanza_t * const stanza, const char * const ns);
|
||||
int xmpp_stanza_set_id(xmpp_stanza_t * const stanza, const char * const id);
|
||||
int xmpp_stanza_set_type(xmpp_stanza_t * const stanza, const char * const type);
|
||||
int xmpp_stanza_set_to(xmpp_stanza_t * const stanza, const char * const to);
|
||||
int xmpp_stanza_set_from(xmpp_stanza_t * const stanza, const char * const from);
|
||||
const char *xmpp_stanza_get_ns(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_type(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_id(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_to(xmpp_stanza_t *const stanza);
|
||||
const char *xmpp_stanza_get_from(xmpp_stanza_t *const stanza);
|
||||
int xmpp_stanza_set_ns(xmpp_stanza_t *const stanza, const char *const ns);
|
||||
int xmpp_stanza_set_id(xmpp_stanza_t *const stanza, const char *const id);
|
||||
int xmpp_stanza_set_type(xmpp_stanza_t *const stanza, const char *const type);
|
||||
int xmpp_stanza_set_to(xmpp_stanza_t *const stanza, const char *const to);
|
||||
int xmpp_stanza_set_from(xmpp_stanza_t *const stanza, const char *const from);
|
||||
|
||||
/* allocate and initialize a stanza in reply to another */
|
||||
xmpp_stanza_t *xmpp_stanza_reply(xmpp_stanza_t * const stanza);
|
||||
xmpp_stanza_t *xmpp_stanza_reply(xmpp_stanza_t *const stanza);
|
||||
|
||||
/* stanza subclasses */
|
||||
xmpp_stanza_t *xmpp_message_new(xmpp_ctx_t *ctx, const char * const type,
|
||||
const char * const to, const char * const id);
|
||||
xmpp_stanza_t *xmpp_message_new(xmpp_ctx_t *ctx,
|
||||
const char *const type,
|
||||
const char *const to,
|
||||
const char *const id);
|
||||
char *xmpp_message_get_body(xmpp_stanza_t *msg);
|
||||
int xmpp_message_set_body(xmpp_stanza_t *msg, const char * const text);
|
||||
int xmpp_message_set_body(xmpp_stanza_t *msg, const char *const text);
|
||||
|
||||
xmpp_stanza_t *xmpp_iq_new(xmpp_ctx_t *ctx, const char * const type,
|
||||
const char * const id);
|
||||
xmpp_stanza_t *
|
||||
xmpp_iq_new(xmpp_ctx_t *ctx, const char *const type, const char *const id);
|
||||
xmpp_stanza_t *xmpp_presence_new(xmpp_ctx_t *ctx);
|
||||
xmpp_stanza_t *xmpp_error_new(xmpp_ctx_t *ctx, xmpp_error_type_t const type,
|
||||
const char * const text);
|
||||
xmpp_stanza_t *xmpp_error_new(xmpp_ctx_t *ctx,
|
||||
xmpp_error_type_t const type,
|
||||
const char *const text);
|
||||
|
||||
/* jid */
|
||||
|
||||
/* these return new strings that must be xmpp_free()'d */
|
||||
char *xmpp_jid_new(xmpp_ctx_t *ctx, const char *node,
|
||||
const char *domain,
|
||||
const char *resource);
|
||||
char *xmpp_jid_new(xmpp_ctx_t *ctx,
|
||||
const char *node,
|
||||
const char *domain,
|
||||
const char *resource);
|
||||
char *xmpp_jid_bare(xmpp_ctx_t *ctx, const char *jid);
|
||||
char *xmpp_jid_node(xmpp_ctx_t *ctx, const char *jid);
|
||||
char *xmpp_jid_domain(xmpp_ctx_t *ctx, const char *jid);
|
||||
@@ -416,10 +420,10 @@ char *xmpp_jid_resource(xmpp_ctx_t *ctx, const char *jid);
|
||||
|
||||
/* event loop */
|
||||
|
||||
void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout);
|
||||
void xmpp_run_once(xmpp_ctx_t *ctx, const unsigned long timeout);
|
||||
void xmpp_run(xmpp_ctx_t *ctx);
|
||||
void xmpp_stop(xmpp_ctx_t *ctx);
|
||||
void xmpp_ctx_set_timeout(xmpp_ctx_t * const ctx, const unsigned long timeout);
|
||||
void xmpp_ctx_set_timeout(xmpp_ctx_t *const ctx, const unsigned long timeout);
|
||||
|
||||
/* UUID */
|
||||
|
||||
@@ -435,7 +439,8 @@ char *xmpp_uuid_gen(xmpp_ctx_t *ctx);
|
||||
typedef struct _xmpp_sha1_t xmpp_sha1_t;
|
||||
|
||||
char *xmpp_sha1(xmpp_ctx_t *ctx, const unsigned char *data, size_t len);
|
||||
void xmpp_sha1_digest(const unsigned char *data, size_t len,
|
||||
void xmpp_sha1_digest(const unsigned char *data,
|
||||
size_t len,
|
||||
unsigned char *digest);
|
||||
|
||||
xmpp_sha1_t *xmpp_sha1_new(xmpp_ctx_t *ctx);
|
||||
@@ -448,10 +453,14 @@ void xmpp_sha1_to_digest(xmpp_sha1_t *sha1, unsigned char *digest);
|
||||
|
||||
/* Base64 */
|
||||
|
||||
char *xmpp_base64_encode(xmpp_ctx_t *ctx, const unsigned char *data, size_t len);
|
||||
char *
|
||||
xmpp_base64_encode(xmpp_ctx_t *ctx, const unsigned char *data, size_t len);
|
||||
char *xmpp_base64_decode_str(xmpp_ctx_t *ctx, const char *base64, size_t len);
|
||||
void xmpp_base64_decode_bin(xmpp_ctx_t *ctx, const char *base64, size_t len,
|
||||
unsigned char **out, size_t *outlen);
|
||||
void xmpp_base64_decode_bin(xmpp_ctx_t *ctx,
|
||||
const char *base64,
|
||||
size_t len,
|
||||
unsigned char **out,
|
||||
size_t *outlen);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
||||
199
strophepp.h
199
strophepp.h
@@ -18,116 +18,119 @@
|
||||
|
||||
#include "strophe.h"
|
||||
|
||||
namespace XMPP {
|
||||
class Context {
|
||||
private:
|
||||
xmpp_mem_t m_mem;
|
||||
xmpp_log_t m_log;
|
||||
xmpp_ctx_t *m_ctx;
|
||||
namespace XMPP
|
||||
{
|
||||
class Context
|
||||
{
|
||||
private:
|
||||
xmpp_mem_t m_mem;
|
||||
xmpp_log_t m_log;
|
||||
xmpp_ctx_t *m_ctx;
|
||||
|
||||
public:
|
||||
Context();
|
||||
virtual ~Context();
|
||||
public:
|
||||
Context();
|
||||
virtual ~Context();
|
||||
|
||||
virtual void *alloc(const size_t size);
|
||||
virtual void *realloc(void *p, const size_t size);
|
||||
virtual void free(void *p);
|
||||
virtual void log(const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const msg);
|
||||
virtual void *alloc(const size_t size);
|
||||
virtual void *realloc(void *p, const size_t size);
|
||||
virtual void free(void *p);
|
||||
virtual void log(const xmpp_log_level_t level,
|
||||
const char *const area,
|
||||
const char *const msg);
|
||||
|
||||
xmpp_ctx_t *getContext();
|
||||
xmpp_ctx_t *getContext();
|
||||
|
||||
private:
|
||||
static void *callAlloc(const size_t size, void * const userdata);
|
||||
static void *callRealloc(void *p, const size_t size,
|
||||
void * const userdata);
|
||||
static void callFree(void *p, void * const userdata);
|
||||
static void callLog(void * const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char * const area,
|
||||
const char * const msg);
|
||||
};
|
||||
private:
|
||||
static void *callAlloc(const size_t size, void *const userdata);
|
||||
static void *callRealloc(void *p, const size_t size, void *const userdata);
|
||||
static void callFree(void *p, void *const userdata);
|
||||
static void callLog(void *const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char *const area,
|
||||
const char *const msg);
|
||||
};
|
||||
|
||||
class Stanza {
|
||||
private:
|
||||
Context *m_ctx;
|
||||
xmpp_stanza_t *m_stanza;
|
||||
class Stanza
|
||||
{
|
||||
private:
|
||||
Context *m_ctx;
|
||||
xmpp_stanza_t *m_stanza;
|
||||
|
||||
void *operator new(size_t size, Context *ctx);
|
||||
void operator delete(void *p);
|
||||
Stanza(Context *ctx);
|
||||
virtual ~Stanza();
|
||||
void *operator new(size_t size, Context *ctx);
|
||||
void operator delete(void *p);
|
||||
Stanza(Context *ctx);
|
||||
virtual ~Stanza();
|
||||
|
||||
public:
|
||||
static Stanza *create(Context *ctx);
|
||||
void release();
|
||||
Stanza *clone();
|
||||
Stanza *copy();
|
||||
public:
|
||||
static Stanza *create(Context *ctx);
|
||||
void release();
|
||||
Stanza *clone();
|
||||
Stanza *copy();
|
||||
|
||||
int toText(const char ** const buf, size_t * const buflen);
|
||||
Stanza *getChildren();
|
||||
Stanza *getChildByName(const char * const name);
|
||||
Stanza *getNext();
|
||||
char *getAttribute(const char * const name);
|
||||
char *getNamespace();
|
||||
char *getText();
|
||||
char *getName();
|
||||
void addChild(Stanza *child);
|
||||
void setNamespace(const char * const ns);
|
||||
void setAttribute(const char * const key, const char * const value);
|
||||
void setName(const char * const name);
|
||||
void setText(const char * const text);
|
||||
void setText(const char * const text, const size_t size);
|
||||
char *getType();
|
||||
char *getId();
|
||||
char *getTo();
|
||||
char *getFrom();
|
||||
void setType(const char * const type);
|
||||
void setId(const char * const id);
|
||||
void setTo(const char * const to);
|
||||
void setFrom(const char * const from);
|
||||
};
|
||||
int toText(const char **const buf, size_t *const buflen);
|
||||
Stanza *getChildren();
|
||||
Stanza *getChildByName(const char *const name);
|
||||
Stanza *getNext();
|
||||
char *getAttribute(const char *const name);
|
||||
char *getNamespace();
|
||||
char *getText();
|
||||
char *getName();
|
||||
void addChild(Stanza *child);
|
||||
void setNamespace(const char *const ns);
|
||||
void setAttribute(const char *const key, const char *const value);
|
||||
void setName(const char *const name);
|
||||
void setText(const char *const text);
|
||||
void setText(const char *const text, const size_t size);
|
||||
char *getType();
|
||||
char *getId();
|
||||
char *getTo();
|
||||
char *getFrom();
|
||||
void setType(const char *const type);
|
||||
void setId(const char *const id);
|
||||
void setTo(const char *const to);
|
||||
void setFrom(const char *const from);
|
||||
};
|
||||
|
||||
class Connection {
|
||||
private:
|
||||
Context *m_ctx;
|
||||
xmpp_conn_t *conn;
|
||||
class Connection
|
||||
{
|
||||
private:
|
||||
Context *m_ctx;
|
||||
xmpp_conn_t *conn;
|
||||
|
||||
void *operator new(size_t size, Context *ctx);
|
||||
Connection(Context *ctx);
|
||||
void *operator new(size_t size, Context *ctx);
|
||||
Connection(Context *ctx);
|
||||
|
||||
public:
|
||||
static Connection *create(Context *ctx);
|
||||
virtual ~Connection();
|
||||
Connection *clone();
|
||||
void operator delete(void *p);
|
||||
public:
|
||||
static Connection *create(Context *ctx);
|
||||
virtual ~Connection();
|
||||
Connection *clone();
|
||||
void operator delete(void *p);
|
||||
|
||||
const char *getJID();
|
||||
void setJID(const char * const jid);
|
||||
const char *getPass();
|
||||
void setPass(const char * const pass);
|
||||
bool connectClient(const char * const domain,
|
||||
xmpp_conn_handler callback,
|
||||
void * const userdata);
|
||||
void disconnect();
|
||||
void send(Stanza *stanza);
|
||||
const char *getJID();
|
||||
void setJID(const char *const jid);
|
||||
const char *getPass();
|
||||
void setPass(const char *const pass);
|
||||
bool connectClient(const char *const domain,
|
||||
xmpp_conn_handler callback,
|
||||
void *const userdata);
|
||||
void disconnect();
|
||||
void send(Stanza *stanza);
|
||||
|
||||
void addTimedHandler(xmpp_timed_handler handler,
|
||||
const unsigned long perdio,
|
||||
void * const userdata);
|
||||
void deleteTimedHandler(xmpp_timed_handler handler);
|
||||
void addHandler(xmpp_handler handler,
|
||||
const char * const ns,
|
||||
const char * const name,
|
||||
const char * const type,
|
||||
void * const userdata);
|
||||
void deleteHandler(xmpp_handler handler);
|
||||
void addIdHandler(xmpp_handler handler,
|
||||
const char * const id,
|
||||
void * const userdata);
|
||||
void deleteIdHandler(xmpp_handler handler);
|
||||
};
|
||||
}
|
||||
void addTimedHandler(xmpp_timed_handler handler,
|
||||
const unsigned long perdio,
|
||||
void *const userdata);
|
||||
void deleteTimedHandler(xmpp_timed_handler handler);
|
||||
void addHandler(xmpp_handler handler,
|
||||
const char *const ns,
|
||||
const char *const name,
|
||||
const char *const type,
|
||||
void *const userdata);
|
||||
void deleteHandler(xmpp_handler handler);
|
||||
void addIdHandler(xmpp_handler handler,
|
||||
const char *const id,
|
||||
void *const userdata);
|
||||
void deleteIdHandler(xmpp_handler handler);
|
||||
};
|
||||
} // namespace XMPP
|
||||
|
||||
#endif /* __LIBSTROPHE_STROPHEPP_H__ */
|
||||
|
||||
@@ -18,14 +18,15 @@
|
||||
|
||||
#include "test.h"
|
||||
|
||||
#define fail_unless(expr) do { \
|
||||
int result = (expr); \
|
||||
if (!result) { \
|
||||
printf("%s:%d: Assertion failed: %s\n", \
|
||||
__FILE__, __LINE__, #expr); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
#define fail_unless(expr) \
|
||||
do { \
|
||||
int result = (expr); \
|
||||
if (!result) { \
|
||||
printf("%s:%d: Assertion failed: %s\n", __FILE__, __LINE__, \
|
||||
#expr); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
static void create_destroy(void)
|
||||
{
|
||||
@@ -67,9 +68,7 @@ static void callbacks(void)
|
||||
int ret;
|
||||
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
parser = parser_new(ctx,
|
||||
cbtest_handle_start,
|
||||
cbtest_handle_end,
|
||||
parser = parser_new(ctx, cbtest_handle_start, cbtest_handle_end,
|
||||
cbtest_handle_stanza, NULL);
|
||||
|
||||
ret = parser_feed(parser, "<stream>", 8);
|
||||
|
||||
@@ -55,8 +55,8 @@ int main(int argc, char **argv)
|
||||
}
|
||||
|
||||
domain = argv[1];
|
||||
snprintf(fulldomain, sizeof(fulldomain), "_%s._%s.%s",
|
||||
service, proto, domain);
|
||||
snprintf(fulldomain, sizeof(fulldomain), "_%s._%s.%s", service, proto,
|
||||
domain);
|
||||
errno = 0;
|
||||
len = res_query(fulldomain, C_IN, T_SRV, buf, sizeof(buf));
|
||||
|
||||
|
||||
@@ -16,9 +16,9 @@
|
||||
|
||||
static uint8_t char_to_bin(char c)
|
||||
{
|
||||
return c <= '9' ? (uint8_t)(c - '0') :
|
||||
c <= 'Z' ? (uint8_t)(c - 'A' + 10) :
|
||||
(uint8_t)(c - 'a' + 10);
|
||||
return c <= '9'
|
||||
? (uint8_t)(c - '0')
|
||||
: c <= 'Z' ? (uint8_t)(c - 'A' + 10) : (uint8_t)(c - 'a' + 10);
|
||||
}
|
||||
|
||||
void test_hex_to_bin(const char *hex, uint8_t *bin, size_t *bin_len)
|
||||
|
||||
75
tests/test.h
75
tests/test.h
@@ -17,51 +17,48 @@
|
||||
#include <string.h>
|
||||
#include "ostypes.h"
|
||||
|
||||
#define TEST_MAIN \
|
||||
int main(int argc, char **argv) { \
|
||||
int num_failed; \
|
||||
Suite *s = parser_suite(); \
|
||||
SRunner *sr = srunner_create(s); \
|
||||
srunner_run_all(sr, CK_NORMAL); \
|
||||
num_failed = srunner_ntests_failed(sr); \
|
||||
srunner_free(sr); \
|
||||
return (num_failed == 0) ? EXIT_SUCCESS : EXIT_FAILURE; \
|
||||
}
|
||||
#define TEST_MAIN \
|
||||
int main(int argc, char **argv) \
|
||||
{ \
|
||||
int num_failed; \
|
||||
Suite *s = parser_suite(); \
|
||||
SRunner *sr = srunner_create(s); \
|
||||
srunner_run_all(sr, CK_NORMAL); \
|
||||
num_failed = srunner_ntests_failed(sr); \
|
||||
srunner_free(sr); \
|
||||
return (num_failed == 0) ? EXIT_SUCCESS : EXIT_FAILURE; \
|
||||
}
|
||||
|
||||
#ifndef ARRAY_SIZE
|
||||
#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
|
||||
#endif
|
||||
|
||||
#define COMPARE(v1, v2) \
|
||||
do { \
|
||||
const char *__v1 = v1; \
|
||||
const char *__v2 = v2; \
|
||||
if (strcmp(__v1, __v2) != 0) { \
|
||||
printf("%s differs!\n" \
|
||||
"expected: %s\n" \
|
||||
"got: %s\n", \
|
||||
#v1, __v1, __v2); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
#define COMPARE(v1, v2) \
|
||||
do { \
|
||||
const char *__v1 = v1; \
|
||||
const char *__v2 = v2; \
|
||||
if (strcmp(__v1, __v2) != 0) { \
|
||||
printf("%s differs!\n" \
|
||||
"expected: %s\n" \
|
||||
"got: %s\n", \
|
||||
#v1, __v1, __v2); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define COMPARE_BUF(v1, len1, v2, len2) \
|
||||
do { \
|
||||
const uint8_t *__v1 = (uint8_t *)(v1); \
|
||||
const uint8_t *__v2 = (uint8_t *)(v2); \
|
||||
size_t __len1 = len1; \
|
||||
size_t __len2 = len2; \
|
||||
if (__len1 != __len2 || \
|
||||
memcmp(__v1, __v2, __len1) != 0) \
|
||||
{ \
|
||||
printf("%s differs!\n", #v1); \
|
||||
printf("expected: 0x%s\n", \
|
||||
test_bin_to_hex(__v1, __len1)); \
|
||||
printf("got: 0x%s\n", \
|
||||
test_bin_to_hex(__v2, __len2)); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
#define COMPARE_BUF(v1, len1, v2, len2) \
|
||||
do { \
|
||||
const uint8_t *__v1 = (uint8_t *)(v1); \
|
||||
const uint8_t *__v2 = (uint8_t *)(v2); \
|
||||
size_t __len1 = len1; \
|
||||
size_t __len2 = len2; \
|
||||
if (__len1 != __len2 || memcmp(__v1, __v2, __len1) != 0) { \
|
||||
printf("%s differs!\n", #v1); \
|
||||
printf("expected: 0x%s\n", test_bin_to_hex(__v1, __len1)); \
|
||||
printf("got: 0x%s\n", test_bin_to_hex(__v2, __len2)); \
|
||||
exit(1); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
void test_hex_to_bin(const char *hex, uint8_t *bin, size_t *bin_len);
|
||||
const char *test_bin_to_hex(const uint8_t *bin, size_t len);
|
||||
|
||||
@@ -17,11 +17,11 @@
|
||||
|
||||
#include "test.h"
|
||||
|
||||
static const unsigned char test_2_raw[] =
|
||||
{0x14, 0xfb, 0x9c, 0x03, 0xd9, 0x7e, 0x00};
|
||||
static const unsigned char test_4_raw[] =
|
||||
{0xd6, 0x2f, 0x27, 0x49, 0x7e, 0xdd, 0xf3, 0xd5,
|
||||
0x41, 0xbc, 0x1b, 0xe9, 0xdf, 0xe9, 0xb3, 0x08, 0x00};
|
||||
static const unsigned char test_2_raw[] = {0x14, 0xfb, 0x9c, 0x03,
|
||||
0xd9, 0x7e, 0x00};
|
||||
static const unsigned char test_4_raw[] = {0xd6, 0x2f, 0x27, 0x49, 0x7e, 0xdd,
|
||||
0xf3, 0xd5, 0x41, 0xbc, 0x1b, 0xe9,
|
||||
0xdf, 0xe9, 0xb3, 0x08, 0x00};
|
||||
|
||||
static const struct {
|
||||
char *raw;
|
||||
@@ -36,30 +36,26 @@ static const struct {
|
||||
.base64 = "FPucA9l+",
|
||||
},
|
||||
{
|
||||
.raw =
|
||||
"From rest and sleep, which but thy pictures be, "
|
||||
"Much pleasure; then from thee much more must flow, "
|
||||
"And soonest our best men with thee do go, "
|
||||
"Rest of their bones, and soul's delivery.",
|
||||
.base64 =
|
||||
"RnJvbSByZXN0IGFuZCBzbGVlcCwgd2hpY2ggYnV0IHRoeSBwaWN0dXJl"
|
||||
"cyBiZSwgTXVjaCBwbGVhc3VyZTsgdGhlbiBmcm9tIHRoZWUgbXVjaCBt"
|
||||
"b3JlIG11c3QgZmxvdywgQW5kIHNvb25lc3Qgb3VyIGJlc3QgbWVuIHdp"
|
||||
"dGggdGhlZSBkbyBnbywgUmVzdCBvZiB0aGVpciBib25lcywgYW5kIHNv"
|
||||
"dWwncyBkZWxpdmVyeS4=",
|
||||
.raw = "From rest and sleep, which but thy pictures be, "
|
||||
"Much pleasure; then from thee much more must flow, "
|
||||
"And soonest our best men with thee do go, "
|
||||
"Rest of their bones, and soul's delivery.",
|
||||
.base64 = "RnJvbSByZXN0IGFuZCBzbGVlcCwgd2hpY2ggYnV0IHRoeSBwaWN0dXJl"
|
||||
"cyBiZSwgTXVjaCBwbGVhc3VyZTsgdGhlbiBmcm9tIHRoZWUgbXVjaCBt"
|
||||
"b3JlIG11c3QgZmxvdywgQW5kIHNvb25lc3Qgb3VyIGJlc3QgbWVuIHdp"
|
||||
"dGggdGhlZSBkbyBnbywgUmVzdCBvZiB0aGVpciBib25lcywgYW5kIHNv"
|
||||
"dWwncyBkZWxpdmVyeS4=",
|
||||
},
|
||||
{
|
||||
.raw = (char *)test_4_raw,
|
||||
.base64 = "1i8nSX7d89VBvBvp3+mzCA==",
|
||||
},
|
||||
{
|
||||
.raw =
|
||||
"realm=\"chesspark.com\",nonce=\"b243c0d663257a9149999cef2f83"
|
||||
"a22116559e93\",qop=\"auth\",charset=utf-8,algorithm=md5-sess",
|
||||
.base64 =
|
||||
"cmVhbG09ImNoZXNzcGFyay5jb20iLG5vbmNlPSJiMjQzYzBkNjYzMjU3"
|
||||
"YTkxNDk5OTljZWYyZjgzYTIyMTE2NTU5ZTkzIixxb3A9ImF1dGgiLGNo"
|
||||
"YXJzZXQ9dXRmLTgsYWxnb3JpdGhtPW1kNS1zZXNz",
|
||||
.raw = "realm=\"chesspark.com\",nonce=\"b243c0d663257a9149999cef2f83"
|
||||
"a22116559e93\",qop=\"auth\",charset=utf-8,algorithm=md5-sess",
|
||||
.base64 = "cmVhbG09ImNoZXNzcGFyay5jb20iLG5vbmNlPSJiMjQzYzBkNjYzMjU3"
|
||||
"YTkxNDk5OTljZWYyZjgzYTIyMTE2NTU5ZTkzIixxb3A9ImF1dGgiLGNo"
|
||||
"YXJzZXQ9dXRmLTgsYWxnb3JpdGhtPW1kNS1zZXNz",
|
||||
},
|
||||
|
||||
/* RFC4648 test vectors */
|
||||
@@ -94,38 +90,27 @@ static const struct {
|
||||
};
|
||||
|
||||
static const unsigned char bin_data[] = {
|
||||
0xda, 0xa8, 0x81, 0x80, 0x00, 0x01, 0x00, 0x05,
|
||||
0x00, 0x00, 0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x05, 0x67,
|
||||
0x6d, 0x61, 0x69, 0x6c, 0x03, 0x63, 0x6f, 0x6d,
|
||||
0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00,
|
||||
0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04,
|
||||
0x61, 0x6c, 0x74, 0x31, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67,
|
||||
0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00, 0xc0,
|
||||
0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14,
|
||||
0x66, 0x04, 0x61, 0x6c, 0x74, 0x34, 0x04, 0x78,
|
||||
0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f,
|
||||
0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d,
|
||||
0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00,
|
||||
0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x32,
|
||||
0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06,
|
||||
0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00,
|
||||
0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x19, 0x00,
|
||||
0x05, 0x00, 0x00, 0x14, 0x66, 0x04, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f,
|
||||
0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00,
|
||||
0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00,
|
||||
0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00,
|
||||
0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x33, 0x04,
|
||||
0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67,
|
||||
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f,
|
||||
0x6d, 0x00,
|
||||
0xda, 0xa8, 0x81, 0x80, 0x00, 0x01, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00,
|
||||
0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x05, 0x67, 0x6d, 0x61, 0x69, 0x6c,
|
||||
0x03, 0x63, 0x6f, 0x6d, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x31, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04, 0x61, 0x6c,
|
||||
0x74, 0x34, 0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f,
|
||||
0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x32, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x19, 0x00, 0x05, 0x00, 0x00, 0x14, 0x66, 0x04, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03,
|
||||
0x63, 0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00,
|
||||
0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04, 0x61,
|
||||
0x6c, 0x74, 0x33, 0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67,
|
||||
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00,
|
||||
};
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
/* test_ctx.c
|
||||
** libstrophe XMPP client library -- test routines for the library run-time context
|
||||
** libstrophe XMPP client library -- test routines for the library run-time
|
||||
*context
|
||||
**
|
||||
** Copyright (C) 2005-2009 Collecta, Inc.
|
||||
**
|
||||
@@ -21,30 +22,32 @@ static int mem_alloc_called = 0;
|
||||
static int mem_free_called = 0;
|
||||
static int mem_realloc_called = 0;
|
||||
|
||||
void *my_alloc(const size_t size, void * const userdata)
|
||||
void *my_alloc(const size_t size, void *const userdata)
|
||||
{
|
||||
mem_alloc_called++;
|
||||
return malloc(size);
|
||||
}
|
||||
|
||||
void my_free(void *p, void * const userdata)
|
||||
void my_free(void *p, void *const userdata)
|
||||
{
|
||||
mem_free_called++;
|
||||
return free(p);
|
||||
}
|
||||
|
||||
void *my_realloc(void *p, const size_t size, void * const userdata)
|
||||
void *my_realloc(void *p, const size_t size, void *const userdata)
|
||||
{
|
||||
mem_realloc_called++;
|
||||
return realloc(p, size);
|
||||
}
|
||||
|
||||
void my_logger(void * const userdata, const xmpp_log_level_t level,
|
||||
const char * const area, const char * const msg)
|
||||
void my_logger(void *const userdata,
|
||||
const xmpp_log_level_t level,
|
||||
const char *const area,
|
||||
const char *const msg)
|
||||
{
|
||||
if (strcmp((char *)userdata, "asdf") == 0 && level == XMPP_LEVEL_DEBUG
|
||||
&& strcmp(area, "test") == 0 && strcmp(msg, "hello") == 0)
|
||||
log_called++;
|
||||
if (strcmp((char *)userdata, "asdf") == 0 && level == XMPP_LEVEL_DEBUG &&
|
||||
strcmp(area, "test") == 0 && strcmp(msg, "hello") == 0)
|
||||
log_called++;
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
@@ -56,7 +59,8 @@ int main(int argc, char **argv)
|
||||
void *testptr1, *testptr2;
|
||||
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
if (ctx == NULL) return 1;
|
||||
if (ctx == NULL)
|
||||
return 1;
|
||||
|
||||
/* destroy context */
|
||||
xmpp_ctx_free(ctx);
|
||||
@@ -75,15 +79,15 @@ int main(int argc, char **argv)
|
||||
|
||||
testptr1 = xmpp_alloc(ctx, 1024);
|
||||
if (testptr1 == NULL) {
|
||||
xmpp_ctx_free(ctx);
|
||||
return 1;
|
||||
xmpp_ctx_free(ctx);
|
||||
return 1;
|
||||
}
|
||||
|
||||
testptr2 = xmpp_realloc(ctx, testptr1, 2048);
|
||||
if (testptr2 == NULL) {
|
||||
xmpp_free(ctx, testptr1);
|
||||
xmpp_ctx_free(ctx);
|
||||
return 1;
|
||||
xmpp_free(ctx, testptr1);
|
||||
xmpp_ctx_free(ctx);
|
||||
return 1;
|
||||
}
|
||||
|
||||
xmpp_free(ctx, testptr2);
|
||||
@@ -92,8 +96,8 @@ int main(int argc, char **argv)
|
||||
|
||||
/* check for test failure */
|
||||
if (!(log_called && mem_alloc_called && mem_realloc_called &&
|
||||
mem_free_called))
|
||||
return 1;
|
||||
mem_free_called))
|
||||
return 1;
|
||||
if (mem_alloc_called != mem_free_called)
|
||||
return 1;
|
||||
|
||||
|
||||
@@ -22,12 +22,8 @@
|
||||
#define TESTSIZE 500
|
||||
|
||||
/* static test data */
|
||||
const char *keys[] = {
|
||||
"foo", "bar", "baz", "quux", "xyzzy"
|
||||
};
|
||||
const char *values[] = {
|
||||
"wuzzle", "mug", "canonical", "rosebud", "lottery"
|
||||
};
|
||||
const char *keys[] = {"foo", "bar", "baz", "quux", "xyzzy"};
|
||||
const char *values[] = {"wuzzle", "mug", "canonical", "rosebud", "lottery"};
|
||||
const int nkeys = ARRAY_SIZE(keys);
|
||||
|
||||
int main(int argc, char **argv)
|
||||
@@ -43,10 +39,10 @@ int main(int argc, char **argv)
|
||||
|
||||
/* initialize random numbers */
|
||||
if (argc > 2) {
|
||||
/* use a seed from the command line */
|
||||
seed = (unsigned int)atoi(argv[1]);
|
||||
/* use a seed from the command line */
|
||||
seed = (unsigned int)atoi(argv[1]);
|
||||
} else {
|
||||
seed = (unsigned int)clock();
|
||||
seed = (unsigned int)clock();
|
||||
}
|
||||
/* using random seed 'seed' */
|
||||
srand(seed);
|
||||
@@ -54,37 +50,42 @@ int main(int argc, char **argv)
|
||||
/* allocate a default context */
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
if (ctx == NULL) {
|
||||
/* ctx allocation failed! */
|
||||
return -1;
|
||||
/* ctx allocation failed! */
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* allocate a hash table */
|
||||
table = hash_new(ctx, TABLESIZE, xmpp_free);
|
||||
if (table == NULL) {
|
||||
/* table allocation failed! */
|
||||
return 1;
|
||||
/* table allocation failed! */
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* test insertion */
|
||||
for (i = 0; i < nkeys; i++) {
|
||||
err = hash_add(table, keys[i], xmpp_strdup(ctx, values[i]));
|
||||
if (err) return err;
|
||||
err = hash_add(table, keys[i], xmpp_strdup(ctx, values[i]));
|
||||
if (err)
|
||||
return err;
|
||||
}
|
||||
|
||||
/* test key count */
|
||||
if (hash_num_keys(table) != nkeys) {
|
||||
/* wrong number of keys in table! */
|
||||
return 1;
|
||||
/* wrong number of keys in table! */
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* test replacing old values */
|
||||
for (i = 0; i < nkeys; i++) {
|
||||
err = hash_add(table, keys[0], xmpp_strdup(ctx, values[i]));
|
||||
if (err) return err;
|
||||
if (hash_num_keys(table) != nkeys) return 1;
|
||||
if (err)
|
||||
return err;
|
||||
if (hash_num_keys(table) != nkeys)
|
||||
return 1;
|
||||
result = hash_get(table, keys[0]);
|
||||
if (result == NULL) return 1;
|
||||
if (strcmp(result, values[i]) != 0) return 1;
|
||||
if (result == NULL)
|
||||
return 1;
|
||||
if (strcmp(result, values[i]) != 0)
|
||||
return 1;
|
||||
}
|
||||
/* restore value for the 1st key */
|
||||
hash_add(table, keys[0], xmpp_strdup(ctx, values[0]));
|
||||
@@ -94,36 +95,36 @@ int main(int argc, char **argv)
|
||||
|
||||
/* test lookup */
|
||||
for (i = 0; i < nkeys; i++) {
|
||||
result = hash_get(clone, keys[i]);
|
||||
if (result == NULL) {
|
||||
/* lookup failed! */
|
||||
return 1;
|
||||
}
|
||||
if (strcmp(values[i], result)) {
|
||||
/* lookup returned incorrect value! */
|
||||
return 1;
|
||||
}
|
||||
result = hash_get(clone, keys[i]);
|
||||
if (result == NULL) {
|
||||
/* lookup failed! */
|
||||
return 1;
|
||||
}
|
||||
if (strcmp(values[i], result)) {
|
||||
/* lookup returned incorrect value! */
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
/* test key iterator */
|
||||
iter = hash_iter_new(clone);
|
||||
if (iter == NULL) {
|
||||
/* iterator allocation failed! */
|
||||
return 1;
|
||||
/* iterator allocation failed! */
|
||||
return 1;
|
||||
}
|
||||
for (i = 0; i < nkeys; i++) {
|
||||
key = hash_iter_next(iter);
|
||||
printf("key: '%s'\n", key);
|
||||
key = hash_iter_next(iter);
|
||||
printf("key: '%s'\n", key);
|
||||
}
|
||||
key = hash_iter_next(iter);
|
||||
if (key != NULL) {
|
||||
/* extra keys returned! */
|
||||
return 1;
|
||||
/* extra keys returned! */
|
||||
return 1;
|
||||
}
|
||||
key = hash_iter_next(iter);
|
||||
if (key != NULL) {
|
||||
/* extra keys returned! */
|
||||
return 1;
|
||||
/* extra keys returned! */
|
||||
return 1;
|
||||
}
|
||||
hash_iter_release(iter);
|
||||
|
||||
@@ -132,14 +133,19 @@ int main(int argc, char **argv)
|
||||
|
||||
/* test drops */
|
||||
hash_drop(clone, keys[2]);
|
||||
if (hash_get(clone, keys[2]) != NULL) return 1;
|
||||
if (hash_get(clone, keys[2]) != NULL)
|
||||
return 1;
|
||||
hash_drop(clone, keys[1]);
|
||||
hash_drop(clone, keys[4]);
|
||||
if (hash_get(clone, keys[4]) != NULL) return 1;
|
||||
if (hash_get(clone, keys[1]) != NULL) return 1;
|
||||
if (hash_get(clone, keys[4]) != NULL)
|
||||
return 1;
|
||||
if (hash_get(clone, keys[1]) != NULL)
|
||||
return 1;
|
||||
/* keys 0,3 should still be available */
|
||||
if (hash_get(clone, keys[0]) == NULL) return 1;
|
||||
if (hash_get(clone, keys[3]) == NULL) return 1;
|
||||
if (hash_get(clone, keys[0]) == NULL)
|
||||
return 1;
|
||||
if (hash_get(clone, keys[3]) == NULL)
|
||||
return 1;
|
||||
|
||||
/* release our clone */
|
||||
hash_release(clone);
|
||||
|
||||
136
tests/test_jid.c
136
tests/test_jid.c
@@ -36,61 +36,93 @@ int test_jid(xmpp_ctx_t *ctx)
|
||||
node = xmpp_jid_node(ctx, jid1);
|
||||
domain = xmpp_jid_domain(ctx, jid1);
|
||||
resource = xmpp_jid_resource(ctx, jid1);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n",
|
||||
jid1, _s(node), _s(domain), _s(resource));
|
||||
if (bare == NULL || strcmp(bare, "foo@bar.com")) return 1;
|
||||
if (node == NULL || strcmp(node, "foo")) return 1;
|
||||
if (domain == NULL || strcmp(domain, "bar.com")) return 1;
|
||||
if (resource != NULL) return 1;
|
||||
if (bare) xmpp_free(ctx, bare);
|
||||
if (node) xmpp_free(ctx, node);
|
||||
if (domain) xmpp_free(ctx, domain);
|
||||
if (resource) xmpp_free(ctx, resource);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n", jid1, _s(node), _s(domain),
|
||||
_s(resource));
|
||||
if (bare == NULL || strcmp(bare, "foo@bar.com"))
|
||||
return 1;
|
||||
if (node == NULL || strcmp(node, "foo"))
|
||||
return 1;
|
||||
if (domain == NULL || strcmp(domain, "bar.com"))
|
||||
return 1;
|
||||
if (resource != NULL)
|
||||
return 1;
|
||||
if (bare)
|
||||
xmpp_free(ctx, bare);
|
||||
if (node)
|
||||
xmpp_free(ctx, node);
|
||||
if (domain)
|
||||
xmpp_free(ctx, domain);
|
||||
if (resource)
|
||||
xmpp_free(ctx, resource);
|
||||
|
||||
bare = xmpp_jid_bare(ctx, jid2);
|
||||
node = xmpp_jid_node(ctx, jid2);
|
||||
domain = xmpp_jid_domain(ctx, jid2);
|
||||
resource = xmpp_jid_resource(ctx, jid2);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n",
|
||||
jid2, _s(node), _s(domain), _s(resource));
|
||||
if (bare == NULL || strcmp(bare, "anyone@example.com")) return 1;
|
||||
if (node == NULL || strcmp(node, "anyone")) return 1;
|
||||
if (domain == NULL || strcmp(domain, "example.com")) return 1;
|
||||
if (resource == NULL || strcmp(resource, "hullo")) return 1;
|
||||
if (bare) xmpp_free(ctx, bare);
|
||||
if (node) xmpp_free(ctx, node);
|
||||
if (domain) xmpp_free(ctx, domain);
|
||||
if (resource) xmpp_free(ctx, resource);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n", jid2, _s(node), _s(domain),
|
||||
_s(resource));
|
||||
if (bare == NULL || strcmp(bare, "anyone@example.com"))
|
||||
return 1;
|
||||
if (node == NULL || strcmp(node, "anyone"))
|
||||
return 1;
|
||||
if (domain == NULL || strcmp(domain, "example.com"))
|
||||
return 1;
|
||||
if (resource == NULL || strcmp(resource, "hullo"))
|
||||
return 1;
|
||||
if (bare)
|
||||
xmpp_free(ctx, bare);
|
||||
if (node)
|
||||
xmpp_free(ctx, node);
|
||||
if (domain)
|
||||
xmpp_free(ctx, domain);
|
||||
if (resource)
|
||||
xmpp_free(ctx, resource);
|
||||
|
||||
bare = xmpp_jid_bare(ctx, jid3);
|
||||
node = xmpp_jid_node(ctx, jid3);
|
||||
domain = xmpp_jid_domain(ctx, jid3);
|
||||
resource = xmpp_jid_resource(ctx, jid3);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n",
|
||||
jid3, _s(node), _s(domain), _s(resource));
|
||||
if (bare == NULL || strcmp(bare, "manic.porter@xyz.net")) return 1;
|
||||
if (node == NULL || strcmp(node, "manic.porter")) return 1;
|
||||
if (domain == NULL || strcmp(domain, "xyz.net")) return 1;
|
||||
if (resource == NULL || strcmp(resource, "frob")) return 1;
|
||||
if (bare) xmpp_free(ctx, bare);
|
||||
if (node) xmpp_free(ctx, node);
|
||||
if (domain) xmpp_free(ctx, domain);
|
||||
if (resource) xmpp_free(ctx, resource);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n", jid3, _s(node), _s(domain),
|
||||
_s(resource));
|
||||
if (bare == NULL || strcmp(bare, "manic.porter@xyz.net"))
|
||||
return 1;
|
||||
if (node == NULL || strcmp(node, "manic.porter"))
|
||||
return 1;
|
||||
if (domain == NULL || strcmp(domain, "xyz.net"))
|
||||
return 1;
|
||||
if (resource == NULL || strcmp(resource, "frob"))
|
||||
return 1;
|
||||
if (bare)
|
||||
xmpp_free(ctx, bare);
|
||||
if (node)
|
||||
xmpp_free(ctx, node);
|
||||
if (domain)
|
||||
xmpp_free(ctx, domain);
|
||||
if (resource)
|
||||
xmpp_free(ctx, resource);
|
||||
|
||||
bare = xmpp_jid_bare(ctx, jid4);
|
||||
node = xmpp_jid_node(ctx, jid4);
|
||||
domain = xmpp_jid_domain(ctx, jid4);
|
||||
resource = xmpp_jid_resource(ctx, jid4);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n",
|
||||
jid4, _s(node), _s(domain), _s(resource));
|
||||
if (bare == NULL || strcmp(bare, "domain.tld")) return 1;
|
||||
if (node != NULL) return 1;
|
||||
if (domain == NULL || strcmp(domain, "domain.tld")) return 1;
|
||||
if (resource != NULL) return 1;
|
||||
if (bare) xmpp_free(ctx, bare);
|
||||
if (node) xmpp_free(ctx, node);
|
||||
if (domain) xmpp_free(ctx, domain);
|
||||
if (resource) xmpp_free(ctx, resource);
|
||||
printf("jid '%s' parsed to %s, %s, %s\n", jid4, _s(node), _s(domain),
|
||||
_s(resource));
|
||||
if (bare == NULL || strcmp(bare, "domain.tld"))
|
||||
return 1;
|
||||
if (node != NULL)
|
||||
return 1;
|
||||
if (domain == NULL || strcmp(domain, "domain.tld"))
|
||||
return 1;
|
||||
if (resource != NULL)
|
||||
return 1;
|
||||
if (bare)
|
||||
xmpp_free(ctx, bare);
|
||||
if (node)
|
||||
xmpp_free(ctx, node);
|
||||
if (domain)
|
||||
xmpp_free(ctx, domain);
|
||||
if (resource)
|
||||
xmpp_free(ctx, resource);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -101,12 +133,14 @@ int test_jid_new(xmpp_ctx_t *ctx)
|
||||
|
||||
jid = xmpp_jid_new(ctx, "node", "domain", "resource");
|
||||
printf("new jid: '%s'\n", jid);
|
||||
if (strcmp(jid, "node@domain/resource")) return 1;
|
||||
if (strcmp(jid, "node@domain/resource"))
|
||||
return 1;
|
||||
xmpp_free(ctx, jid);
|
||||
|
||||
jid = xmpp_jid_new(ctx, "foo", "bar.com", NULL);
|
||||
printf("new jid: '%s'\n", jid);
|
||||
if (strcmp(jid, "foo@bar.com")) return 1;
|
||||
if (strcmp(jid, "foo@bar.com"))
|
||||
return 1;
|
||||
xmpp_free(ctx, jid);
|
||||
|
||||
return 0;
|
||||
@@ -119,20 +153,26 @@ int main(int argc, char *argv[])
|
||||
|
||||
printf("allocating context... ");
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
if (ctx == NULL) printf("failed to create context\n");
|
||||
if (ctx == NULL) return -1;
|
||||
if (ctx == NULL)
|
||||
printf("failed to create context\n");
|
||||
if (ctx == NULL)
|
||||
return -1;
|
||||
printf("ok.\n");
|
||||
|
||||
printf("testing jid routines...\n");
|
||||
ret = test_jid(ctx);
|
||||
if (ret) printf("testing jid routines... failed!\n");
|
||||
if (ret) return ret;
|
||||
if (ret)
|
||||
printf("testing jid routines... failed!\n");
|
||||
if (ret)
|
||||
return ret;
|
||||
printf("testing jid routines... ok.\n");
|
||||
|
||||
printf("testing jid new routines...\n");
|
||||
ret = test_jid_new(ctx);
|
||||
if (ret) printf("testing jid new routines... failed!\n");
|
||||
if (ret) return ret;
|
||||
if (ret)
|
||||
printf("testing jid new routines... failed!\n");
|
||||
if (ret)
|
||||
return ret;
|
||||
printf("testing jid new routines... ok.\n");
|
||||
|
||||
printf("freeing context... ");
|
||||
|
||||
@@ -21,14 +21,17 @@
|
||||
#include "rand.c"
|
||||
|
||||
/* stubs to build test without whole libstrophe */
|
||||
void *xmpp_alloc(const xmpp_ctx_t * const ctx, const size_t size) {
|
||||
void *xmpp_alloc(const xmpp_ctx_t *const ctx, const size_t size)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
void xmpp_free(const xmpp_ctx_t * const ctx, void *p) { }
|
||||
int xmpp_snprintf (char *str, size_t count, const char *fmt, ...) {
|
||||
void xmpp_free(const xmpp_ctx_t *const ctx, void *p) {}
|
||||
int xmpp_snprintf(char *str, size_t count, const char *fmt, ...)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
uint64_t time_stamp(void) {
|
||||
uint64_t time_stamp(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -121,8 +124,8 @@ int main()
|
||||
&entropy_input_len);
|
||||
test_hex_to_bin(test_vectors[i].nonce, nonce, &nonce_len);
|
||||
|
||||
Hash_DRBG_Instantiate(&ctx, entropy_input, entropy_input_len,
|
||||
nonce, nonce_len);
|
||||
Hash_DRBG_Instantiate(&ctx, entropy_input, entropy_input_len, nonce,
|
||||
nonce_len);
|
||||
COMPARE(test_vectors[i].V1, test_bin_to_hex(ctx.V, sizeof(ctx.V)));
|
||||
COMPARE(test_vectors[i].C1, test_bin_to_hex(ctx.C, sizeof(ctx.C)));
|
||||
assert(ctx.reseed_counter == 1);
|
||||
|
||||
@@ -19,117 +19,94 @@
|
||||
|
||||
/* res_query("_xmpp-client._tcp.jabber.kiev.ua", C_IN, T_SRV, ...) */
|
||||
static const unsigned char data1[] = {
|
||||
0x95, 0xf3, 0x81, 0x80, 0x00, 0x01, 0x00, 0x01,
|
||||
0x00, 0x00, 0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a,
|
||||
0x61, 0x62, 0x62, 0x65, 0x72, 0x04, 0x6b, 0x69,
|
||||
0x65, 0x76, 0x02, 0x75, 0x61, 0x00, 0x00, 0x21,
|
||||
0x00, 0x01, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01,
|
||||
0x00, 0x00, 0x00, 0x3b, 0x00, 0x16, 0x00, 0x01,
|
||||
0x00, 0x00, 0x14, 0x66, 0x06, 0x6a, 0x61, 0x62,
|
||||
0x62, 0x65, 0x72, 0x04, 0x6b, 0x69, 0x65, 0x76,
|
||||
0x02, 0x75, 0x61, 0x00,
|
||||
0x95, 0xf3, 0x81, 0x80, 0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00,
|
||||
0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a, 0x61, 0x62, 0x62, 0x65,
|
||||
0x72, 0x04, 0x6b, 0x69, 0x65, 0x76, 0x02, 0x75, 0x61, 0x00, 0x00, 0x21,
|
||||
0x00, 0x01, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x00, 0x3b,
|
||||
0x00, 0x16, 0x00, 0x01, 0x00, 0x00, 0x14, 0x66, 0x06, 0x6a, 0x61, 0x62,
|
||||
0x62, 0x65, 0x72, 0x04, 0x6b, 0x69, 0x65, 0x76, 0x02, 0x75, 0x61, 0x00,
|
||||
};
|
||||
/* res_query("_xmpp-client._tcp.jabber.org", C_IN, T_SRV, ...) */
|
||||
static const unsigned char data2[] = {
|
||||
0xf2, 0x98, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02,
|
||||
0x00, 0x00, 0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a,
|
||||
0x61, 0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72,
|
||||
0x67, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c,
|
||||
0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, 0x83,
|
||||
0x00, 0x1a, 0x00, 0x1e, 0x00, 0x1e, 0x14, 0x66,
|
||||
0x07, 0x68, 0x65, 0x72, 0x6d, 0x65, 0x73, 0x32,
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03,
|
||||
0x6f, 0x72, 0x67, 0x00, 0xc0, 0x0c, 0x00, 0x21,
|
||||
0x00, 0x01, 0x00, 0x00, 0x03, 0x83, 0x00, 0x1c,
|
||||
0x00, 0x1f, 0x00, 0x1e, 0x14, 0x66, 0x09, 0x68,
|
||||
0x65, 0x72, 0x6d, 0x65, 0x73, 0x32, 0x76, 0x36,
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03,
|
||||
0xf2, 0x98, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00,
|
||||
0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a, 0x61, 0x62, 0x62, 0x65,
|
||||
0x72, 0x03, 0x6f, 0x72, 0x67, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c,
|
||||
0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, 0x83, 0x00, 0x1a, 0x00, 0x1e,
|
||||
0x00, 0x1e, 0x14, 0x66, 0x07, 0x68, 0x65, 0x72, 0x6d, 0x65, 0x73, 0x32,
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72, 0x67, 0x00,
|
||||
0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, 0x83, 0x00, 0x1c,
|
||||
0x00, 0x1f, 0x00, 0x1e, 0x14, 0x66, 0x09, 0x68, 0x65, 0x72, 0x6d, 0x65,
|
||||
0x73, 0x32, 0x76, 0x36, 0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03,
|
||||
0x6f, 0x72, 0x67, 0x00,
|
||||
};
|
||||
/* res_query("_xmpp-client._tcp.gmail.com", C_IN, T_SRV, ...) */
|
||||
static const unsigned char data3[] = {
|
||||
0xda, 0xa8, 0x81, 0x80, 0x00, 0x01, 0x00, 0x05,
|
||||
0x00, 0x00, 0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x05, 0x67,
|
||||
0x6d, 0x61, 0x69, 0x6c, 0x03, 0x63, 0x6f, 0x6d,
|
||||
0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00,
|
||||
0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04,
|
||||
0x61, 0x6c, 0x74, 0x31, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67,
|
||||
0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00, 0xc0,
|
||||
0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14,
|
||||
0x66, 0x04, 0x61, 0x6c, 0x74, 0x34, 0x04, 0x78,
|
||||
0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f,
|
||||
0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d,
|
||||
0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00,
|
||||
0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x32,
|
||||
0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06,
|
||||
0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00,
|
||||
0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x19, 0x00,
|
||||
0x05, 0x00, 0x00, 0x14, 0x66, 0x04, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f,
|
||||
0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00,
|
||||
0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00,
|
||||
0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00,
|
||||
0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x33, 0x04,
|
||||
0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67,
|
||||
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f,
|
||||
0x6d, 0x00,
|
||||
0xda, 0xa8, 0x81, 0x80, 0x00, 0x01, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00,
|
||||
0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x05, 0x67, 0x6d, 0x61, 0x69, 0x6c,
|
||||
0x03, 0x63, 0x6f, 0x6d, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x31, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04, 0x61, 0x6c,
|
||||
0x74, 0x34, 0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f,
|
||||
0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00,
|
||||
0x21, 0x00, 0x01, 0x00, 0x00, 0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00,
|
||||
0x00, 0x14, 0x66, 0x04, 0x61, 0x6c, 0x74, 0x32, 0x04, 0x78, 0x6d, 0x70,
|
||||
0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63,
|
||||
0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x02,
|
||||
0x43, 0x00, 0x19, 0x00, 0x05, 0x00, 0x00, 0x14, 0x66, 0x04, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x01, 0x6c, 0x06, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03,
|
||||
0x63, 0x6f, 0x6d, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00,
|
||||
0x02, 0x43, 0x00, 0x1e, 0x00, 0x14, 0x00, 0x00, 0x14, 0x66, 0x04, 0x61,
|
||||
0x6c, 0x74, 0x33, 0x04, 0x78, 0x6d, 0x70, 0x70, 0x01, 0x6c, 0x06, 0x67,
|
||||
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00,
|
||||
};
|
||||
/* res_query("_xmpp-client._tcp.jabber.calyxinstitute.org", C_IN, T_SRV, ...) */
|
||||
static const unsigned char data4[] = {
|
||||
0x8d, 0x58, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, // .X........
|
||||
0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, // ..._xmpp-c
|
||||
0x6c, 0x69, 0x65, 0x6e, 0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, // lient._tcp
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x0e, 0x63, 0x61, // .jabber.ca
|
||||
0x6c, 0x79, 0x78, 0x69, 0x6e, 0x73, 0x74, 0x69, 0x74, 0x75, // lyxinstitu
|
||||
0x74, 0x65, 0x03, 0x6f, 0x72, 0x67, 0x00, 0x00, 0x21, 0x00, // te.org..!.
|
||||
0x01, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, // ....!.....
|
||||
0x83, 0x00, 0x1e, 0x00, 0x04, 0x00, 0x00, 0x14, 0x66, 0x10, // ........f.
|
||||
0x69, 0x6a, 0x65, 0x65, 0x79, 0x6e, 0x72, 0x63, 0x36, 0x78, // ijeeynrc6x
|
||||
0x32, 0x75, 0x79, 0x35, 0x6f, 0x62, 0x05, 0x6f, 0x6e, 0x69, // 2uy5ob.oni
|
||||
0x6f, 0x6e, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, // on....!...
|
||||
0x00, 0x03, 0x83, 0x00, 0x21, 0x00, 0x05, 0x00, 0x01, 0x14, // ....!.....
|
||||
0x66, 0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x0e, 0x63, // f.jabber.c
|
||||
0x61, 0x6c, 0x79, 0x78, 0x69, 0x6e, 0x73, 0x74, 0x69, 0x74, // alyxinstit
|
||||
0x75, 0x74, 0x65, 0x03, 0x6f, 0x72, 0x67, 0x00, // ute.org.
|
||||
0x8d, 0x58, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, // .X........
|
||||
0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, // ..._xmpp-c
|
||||
0x6c, 0x69, 0x65, 0x6e, 0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, // lient._tcp
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x0e, 0x63, 0x61, // .jabber.ca
|
||||
0x6c, 0x79, 0x78, 0x69, 0x6e, 0x73, 0x74, 0x69, 0x74, 0x75, // lyxinstitu
|
||||
0x74, 0x65, 0x03, 0x6f, 0x72, 0x67, 0x00, 0x00, 0x21, 0x00, // te.org..!.
|
||||
0x01, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, // ....!.....
|
||||
0x83, 0x00, 0x1e, 0x00, 0x04, 0x00, 0x00, 0x14, 0x66, 0x10, // ........f.
|
||||
0x69, 0x6a, 0x65, 0x65, 0x79, 0x6e, 0x72, 0x63, 0x36, 0x78, // ijeeynrc6x
|
||||
0x32, 0x75, 0x79, 0x35, 0x6f, 0x62, 0x05, 0x6f, 0x6e, 0x69, // 2uy5ob.oni
|
||||
0x6f, 0x6e, 0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, // on....!...
|
||||
0x00, 0x03, 0x83, 0x00, 0x21, 0x00, 0x05, 0x00, 0x01, 0x14, // ....!.....
|
||||
0x66, 0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x0e, 0x63, // f.jabber.c
|
||||
0x61, 0x6c, 0x79, 0x78, 0x69, 0x6e, 0x73, 0x74, 0x69, 0x74, // alyxinstit
|
||||
0x75, 0x74, 0x65, 0x03, 0x6f, 0x72, 0x67, 0x00, // ute.org.
|
||||
};
|
||||
/* res_query("_xmpp-client._tcp.jabber.org", C_IN, T_SRV, ...) with pointers */
|
||||
static const unsigned char data5[] = {
|
||||
0x00, 0x00, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, // ..........
|
||||
0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, // ..._xmpp-c
|
||||
0x6c, 0x69, 0x65, 0x6e, 0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, // lient._tcp
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72, // .jabber.or
|
||||
0x67, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00, 0x21, // g..!.....!
|
||||
0x00, 0x01, 0x00, 0x00, 0x01, 0x9e, 0x00, 0x12, 0x00, 0x1f, // ..........
|
||||
0x00, 0x1e, 0x14, 0x66, 0x09, 0x68, 0x65, 0x72, 0x6d, 0x65, // ...f.herme
|
||||
0x73, 0x32, 0x76, 0x36, 0xc0, 0x1e, 0xc0, 0x0c, 0x00, 0x21, // s2v6.....!
|
||||
0x00, 0x01, 0x00, 0x00, 0x01, 0x9e, 0x00, 0x10, 0x00, 0x1e, // ..........
|
||||
0x00, 0x1e, 0x14, 0x66, 0x07, 0x68, 0x65, 0x72, 0x6d, 0x65, // ...f.herme
|
||||
0x73, 0x32, 0xc0, 0x1e, // s2..
|
||||
0x00, 0x00, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, // ..........
|
||||
0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, // ..._xmpp-c
|
||||
0x6c, 0x69, 0x65, 0x6e, 0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, // lient._tcp
|
||||
0x06, 0x6a, 0x61, 0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72, // .jabber.or
|
||||
0x67, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c, 0x00, 0x21, // g..!.....!
|
||||
0x00, 0x01, 0x00, 0x00, 0x01, 0x9e, 0x00, 0x12, 0x00, 0x1f, // ..........
|
||||
0x00, 0x1e, 0x14, 0x66, 0x09, 0x68, 0x65, 0x72, 0x6d, 0x65, // ...f.herme
|
||||
0x73, 0x32, 0x76, 0x36, 0xc0, 0x1e, 0xc0, 0x0c, 0x00, 0x21, // s2v6.....!
|
||||
0x00, 0x01, 0x00, 0x00, 0x01, 0x9e, 0x00, 0x10, 0x00, 0x1e, // ..........
|
||||
0x00, 0x1e, 0x14, 0x66, 0x07, 0x68, 0x65, 0x72, 0x6d, 0x65, // ...f.herme
|
||||
0x73, 0x32, 0xc0, 0x1e, // s2..
|
||||
};
|
||||
/* hacked data2 with two empty-string targets. */
|
||||
static const unsigned char data6[] = {
|
||||
0xf2, 0x98, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02,
|
||||
0x00, 0x00, 0x00, 0x00, 0x0c, 0x5f, 0x78, 0x6d,
|
||||
0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69, 0x65, 0x6e,
|
||||
0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a,
|
||||
0x61, 0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72,
|
||||
0x67, 0x00, 0x00, 0x21, 0x00, 0x01, 0xc0, 0x0c,
|
||||
0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, 0x83,
|
||||
0x00, 0x07, 0x00, 0x1e, 0x00, 0x1e, 0x14, 0x66,
|
||||
0x00, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00,
|
||||
0x00, 0x03, 0x83, 0x00, 0x08, 0x00, 0x1f, 0x00,
|
||||
0x1e, 0x14, 0x66, 0xc0, 0x40,
|
||||
0xf2, 0x98, 0x81, 0x80, 0x00, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||
0x00, 0x0c, 0x5f, 0x78, 0x6d, 0x70, 0x70, 0x2d, 0x63, 0x6c, 0x69,
|
||||
0x65, 0x6e, 0x74, 0x04, 0x5f, 0x74, 0x63, 0x70, 0x06, 0x6a, 0x61,
|
||||
0x62, 0x62, 0x65, 0x72, 0x03, 0x6f, 0x72, 0x67, 0x00, 0x00, 0x21,
|
||||
0x00, 0x01, 0xc0, 0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03,
|
||||
0x83, 0x00, 0x07, 0x00, 0x1e, 0x00, 0x1e, 0x14, 0x66, 0x00, 0xc0,
|
||||
0x0c, 0x00, 0x21, 0x00, 0x01, 0x00, 0x00, 0x03, 0x83, 0x00, 0x08,
|
||||
0x00, 0x1f, 0x00, 0x1e, 0x14, 0x66, 0xc0, 0x40,
|
||||
};
|
||||
|
||||
static const struct {
|
||||
@@ -187,7 +164,8 @@ static int srv_rr_list_len(resolver_srv_rr_t *list)
|
||||
{
|
||||
int nr;
|
||||
|
||||
for (nr = 0; list != NULL; ++nr, list = list->next);
|
||||
for (nr = 0; list != NULL; ++nr, list = list->next)
|
||||
;
|
||||
|
||||
return nr;
|
||||
}
|
||||
@@ -223,8 +201,8 @@ int main(int argc, char **argv)
|
||||
port = srv_rr_list->port;
|
||||
COMPARE(tests[i].target, domain);
|
||||
if (tests[i].port != port) {
|
||||
printf("fail! got port=%u, but should be %u\n",
|
||||
(unsigned)port, (unsigned)tests[i].port);
|
||||
printf("fail! got port=%u, but should be %u\n", (unsigned)port,
|
||||
(unsigned)tests[i].port);
|
||||
return 1;
|
||||
}
|
||||
printf("ok\n");
|
||||
|
||||
@@ -21,31 +21,31 @@ static const char password[] = "secret";
|
||||
static const char response_plain[] = "AGZvb0BiYXIuY29tAHNlY3JldA==";
|
||||
|
||||
static const char challenge_md5[] =
|
||||
"cmVhbG09InNvbWVyZWFsbSIsbm9uY2U9Ik9BNk1HOXRFUUdtMmhoIixxb3A9ImF1dGgi"
|
||||
"LGNoYXJzZXQ9dXRmLTgsYWxnb3JpdGhtPW1kNS1zZXNzCg==";
|
||||
"cmVhbG09InNvbWVyZWFsbSIsbm9uY2U9Ik9BNk1HOXRFUUdtMmhoIixxb3A9ImF1dGgi"
|
||||
"LGNoYXJzZXQ9dXRmLTgsYWxnb3JpdGhtPW1kNS1zZXNzCg==";
|
||||
static const char response_md5[] =
|
||||
"dXNlcm5hbWU9InNvbWVub2RlIixyZWFsbT0ic29tZXJlYWxtIixub25jZT0i"
|
||||
"T0E2TUc5dEVRR20yaGgiLGNub25jZT0iMDBERUFEQkVFRjAwIixuYz0wMDAw"
|
||||
"MDAwMSxxb3A9YXV0aCxkaWdlc3QtdXJpPSJ4bXBwL3NvbWVyZWFsbSIscmVz"
|
||||
"cG9uc2U9NGVhNmU4N2JjMDkzMzUwNzQzZGIyOGQ3MDIwOGNhZmIsY2hhcnNl"
|
||||
"dD11dGYtOA==";
|
||||
"dXNlcm5hbWU9InNvbWVub2RlIixyZWFsbT0ic29tZXJlYWxtIixub25jZT0i"
|
||||
"T0E2TUc5dEVRR20yaGgiLGNub25jZT0iMDBERUFEQkVFRjAwIixuYz0wMDAw"
|
||||
"MDAwMSxxb3A9YXV0aCxkaWdlc3QtdXJpPSJ4bXBwL3NvbWVyZWFsbSIscmVz"
|
||||
"cG9uc2U9NGVhNmU4N2JjMDkzMzUwNzQzZGIyOGQ3MDIwOGNhZmIsY2hhcnNl"
|
||||
"dD11dGYtOA==";
|
||||
static const char response_md5_rfc[] =
|
||||
"dXNlcm5hbWU9InNvbWVub2RlIixyZWFsbT0ic29tZXJlYWxtIixub25jZT0i"
|
||||
"T0E2TUc5dEVRR20yaGgiLGNub25jZT0iT0E2TUhYaDZWcVRyUmsiLG5jPTAw"
|
||||
"MDAwMDAxLHFvcD1hdXRoLGRpZ2VzdC11cmk9InhtcHAvZXhhbXBsZS5jb20i"
|
||||
"LHJlc3BvbnNlPWQzODhkYWQ5MGQ0YmJkNzYwYTE1MjMyMWYyMTQzYWY3LGNo"
|
||||
"YXJzZXQ9dXRmLTgK";
|
||||
"dXNlcm5hbWU9InNvbWVub2RlIixyZWFsbT0ic29tZXJlYWxtIixub25jZT0i"
|
||||
"T0E2TUc5dEVRR20yaGgiLGNub25jZT0iT0E2TUhYaDZWcVRyUmsiLG5jPTAw"
|
||||
"MDAwMDAxLHFvcD1hdXRoLGRpZ2VzdC11cmk9InhtcHAvZXhhbXBsZS5jb20i"
|
||||
"LHJlc3BvbnNlPWQzODhkYWQ5MGQ0YmJkNzYwYTE1MjMyMWYyMTQzYWY3LGNo"
|
||||
"YXJzZXQ9dXRmLTgK";
|
||||
|
||||
static const char challenge_md5_2[] =
|
||||
"cmVhbG09ImVsd29vZC5pbm5vc29mdC5jb20iLG5vbmNlPSJPQTZNRzl0"
|
||||
"RVFHbTJoaCIscW9wPSJhdXRoIixhbGdvcml0aG09bWQ1LXNlc3MsY2hh"
|
||||
"cnNldD11dGYtOA==";
|
||||
"cmVhbG09ImVsd29vZC5pbm5vc29mdC5jb20iLG5vbmNlPSJPQTZNRzl0"
|
||||
"RVFHbTJoaCIscW9wPSJhdXRoIixhbGdvcml0aG09bWQ1LXNlc3MsY2hh"
|
||||
"cnNldD11dGYtOA==";
|
||||
static const char response_md5_2[] =
|
||||
"Y2hhcnNldD11dGYtOCx1c2VybmFtZT0iY2hyaXMiLHJlYWxtPSJlbHdvb2"
|
||||
"QuaW5ub3NvZnQuY29tIixub25jZT0iT0E2TUc5dEVRR20yaGgiLG5jPTAw"
|
||||
"MDAwMDAxLGNub25jZT0iT0E2TUhYaDZWcVRyUmsiLGRpZ2VzdC11cmk9Im"
|
||||
"ltYXAvZWx3b29kLmlubm9zb2Z0LmNvbSIscmVzcG9uc2U9ZDM4OGRhZDkw"
|
||||
"ZDRiYmQ3NjBhMTUyMzIxZjIxNDNhZjcscW9wPWF1dGg=";
|
||||
"Y2hhcnNldD11dGYtOCx1c2VybmFtZT0iY2hyaXMiLHJlYWxtPSJlbHdvb2"
|
||||
"QuaW5ub3NvZnQuY29tIixub25jZT0iT0E2TUc5dEVRR20yaGgiLG5jPTAw"
|
||||
"MDAwMDAxLGNub25jZT0iT0E2TUhYaDZWcVRyUmsiLGRpZ2VzdC11cmk9Im"
|
||||
"ltYXAvZWx3b29kLmlubm9zb2Z0LmNvbSIscmVzcG9uc2U9ZDM4OGRhZDkw"
|
||||
"ZDRiYmQ3NjBhMTUyMzIxZjIxNDNhZjcscW9wPWF1dGg=";
|
||||
|
||||
int test_plain(xmpp_ctx_t *ctx)
|
||||
{
|
||||
@@ -53,12 +53,12 @@ int test_plain(xmpp_ctx_t *ctx)
|
||||
|
||||
result = sasl_plain(ctx, jid, password);
|
||||
if (result == NULL) {
|
||||
/* SASL PLAIN internal failure! */
|
||||
return 1;
|
||||
/* SASL PLAIN internal failure! */
|
||||
return 1;
|
||||
}
|
||||
if (strncmp(response_plain, result, strlen(response_plain))) {
|
||||
/* SASL PLAIN returned incorrect string! */
|
||||
return 2;
|
||||
/* SASL PLAIN returned incorrect string! */
|
||||
return 2;
|
||||
}
|
||||
xmpp_free(ctx, result);
|
||||
|
||||
@@ -69,12 +69,12 @@ int test_digest_md5(xmpp_ctx_t *ctx)
|
||||
{
|
||||
char *result;
|
||||
|
||||
result = sasl_digest_md5(ctx, challenge_md5,
|
||||
"somenode@somerealm", "secret");
|
||||
result =
|
||||
sasl_digest_md5(ctx, challenge_md5, "somenode@somerealm", "secret");
|
||||
printf("response:\n%s\n", result);
|
||||
if (strcmp(response_md5, result)) {
|
||||
/* generated incorrect response to challenge */
|
||||
return 1;
|
||||
/* generated incorrect response to challenge */
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -87,20 +87,26 @@ int main(int argc, char *argv[])
|
||||
|
||||
printf("allocating context... ");
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
if (ctx == NULL) printf("failed to create context\n");
|
||||
if (ctx == NULL) return -1;
|
||||
if (ctx == NULL)
|
||||
printf("failed to create context\n");
|
||||
if (ctx == NULL)
|
||||
return -1;
|
||||
printf("ok.\n");
|
||||
|
||||
printf("testing SASL PLAIN... ");
|
||||
ret = test_plain(ctx);
|
||||
if (ret) printf("failed!\n");
|
||||
if (ret) return ret;
|
||||
if (ret)
|
||||
printf("failed!\n");
|
||||
if (ret)
|
||||
return ret;
|
||||
printf("ok.\n");
|
||||
|
||||
printf("testing SASL DIGEST-MD5... ");
|
||||
ret = test_digest_md5(ctx);
|
||||
if (ret) printf("failed!\n");
|
||||
if (ret) return ret;
|
||||
if (ret)
|
||||
printf("failed!\n");
|
||||
if (ret)
|
||||
return ret;
|
||||
printf("ok.\n");
|
||||
|
||||
printf("freeing context... ");
|
||||
|
||||
@@ -25,12 +25,12 @@
|
||||
* Test vectors for derivation function (RFC6070).
|
||||
*/
|
||||
static const struct {
|
||||
char *P; /* text */
|
||||
char *S; /* salt */
|
||||
char *P; /* text */
|
||||
char *S; /* salt */
|
||||
size_t P_len;
|
||||
size_t S_len;
|
||||
uint32_t c; /* i */
|
||||
char *DK; /* resulting digest */
|
||||
uint32_t c; /* i */
|
||||
char *DK; /* resulting digest */
|
||||
} df_vectors[] = {
|
||||
{
|
||||
.P = "password",
|
||||
@@ -115,14 +115,13 @@ static void test_scram(void)
|
||||
printf("SCRAM_SHA1_ClientKey and SCRAM_SHA1_ClientSignature tests.\n");
|
||||
for (i = 0; i < ARRAY_SIZE(scram_vectors); ++i) {
|
||||
printf("Test #%d: ", (int)i + 1);
|
||||
snprintf(auth, sizeof(auth), "%s,%s,%s",
|
||||
scram_vectors[i].initial + 3, scram_vectors[i].challenge,
|
||||
scram_vectors[i].response);
|
||||
snprintf(auth, sizeof(auth), "%s,%s,%s", scram_vectors[i].initial + 3,
|
||||
scram_vectors[i].challenge, scram_vectors[i].response);
|
||||
test_hex_to_bin(scram_vectors[i].salt, salt, &salt_len);
|
||||
|
||||
SCRAM_SHA1_ClientKey((uint8_t *)scram_vectors[i].password,
|
||||
strlen(scram_vectors[i].password),
|
||||
salt, salt_len, scram_vectors[i].i, key);
|
||||
strlen(scram_vectors[i].password), salt, salt_len,
|
||||
scram_vectors[i].i, key);
|
||||
SCRAM_SHA1_ClientSignature(key, (uint8_t *)auth, strlen(auth), sign);
|
||||
for (j = 0; j < SHA1_DIGEST_SIZE; j++) {
|
||||
sign[j] ^= key[j];
|
||||
|
||||
@@ -12,25 +12,23 @@
|
||||
|
||||
/* Test Vectors (from FIPS PUB 180-1) */
|
||||
static char *test_data[] = {
|
||||
"abc",
|
||||
"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
|
||||
"abc", "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
|
||||
"A million repetitions of 'a'",
|
||||
"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
|
||||
"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"};
|
||||
static char *test_results[] = {
|
||||
"A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D",
|
||||
"84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1",
|
||||
"34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F",
|
||||
"AD5B3FDB CB526778 C2839D2F 151EA753 995E26A0"};
|
||||
"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"};
|
||||
static char *test_results[] = {"A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D",
|
||||
"84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1",
|
||||
"34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F",
|
||||
"AD5B3FDB CB526778 C2839D2F 151EA753 995E26A0"};
|
||||
|
||||
static void digest_to_hex(const uint8_t *digest, char *output)
|
||||
{
|
||||
int i,j;
|
||||
int i, j;
|
||||
char *c = output;
|
||||
|
||||
for (i = 0; i < SHA1_DIGEST_SIZE/4; i++) {
|
||||
for (i = 0; i < SHA1_DIGEST_SIZE / 4; i++) {
|
||||
for (j = 0; j < 4; j++) {
|
||||
sprintf(c,"%02X", digest[i*4+j]);
|
||||
sprintf(c, "%02X", digest[i * 4 + j]);
|
||||
c += 2;
|
||||
}
|
||||
sprintf(c, " ");
|
||||
@@ -39,7 +37,7 @@ static void digest_to_hex(const uint8_t *digest, char *output)
|
||||
*(c - 1) = '\0';
|
||||
}
|
||||
|
||||
int main(int argc, char** argv)
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
size_t k;
|
||||
SHA1_CTX context;
|
||||
@@ -49,23 +47,23 @@ int main(int argc, char** argv)
|
||||
|
||||
fprintf(stdout, "verifying SHA-1 implementation... ");
|
||||
|
||||
for (k = 0; k < ARRAY_SIZE(test_data); k++){
|
||||
for (k = 0; k < ARRAY_SIZE(test_data); k++) {
|
||||
if (k == 2) {
|
||||
/* this case will be checked below */
|
||||
continue;
|
||||
}
|
||||
copy = strdup(test_data[k]);
|
||||
crypto_SHA1_Init(&context);
|
||||
crypto_SHA1_Update(&context, (uint8_t*)test_data[k],
|
||||
crypto_SHA1_Update(&context, (uint8_t *)test_data[k],
|
||||
strlen(test_data[k]));
|
||||
crypto_SHA1_Final(&context, digest);
|
||||
digest_to_hex(digest, output);
|
||||
|
||||
if (strcmp(output, test_results[k])) {
|
||||
fprintf(stdout, "FAIL\n");
|
||||
fprintf(stderr,"* hash of \"%s\" incorrect:\n", test_data[k]);
|
||||
fprintf(stderr,"\t%s returned\n", output);
|
||||
fprintf(stderr,"\t%s is correct\n", test_results[k]);
|
||||
fprintf(stderr, "* hash of \"%s\" incorrect:\n", test_data[k]);
|
||||
fprintf(stderr, "\t%s returned\n", output);
|
||||
fprintf(stderr, "\t%s is correct\n", test_results[k]);
|
||||
return (1);
|
||||
}
|
||||
if (strcmp(copy, test_data[k])) {
|
||||
@@ -78,18 +76,18 @@ int main(int argc, char** argv)
|
||||
/* million 'a' vector we feed separately */
|
||||
crypto_SHA1_Init(&context);
|
||||
for (k = 0; k < 1000000; k++)
|
||||
crypto_SHA1_Update(&context, (uint8_t*)"a", 1);
|
||||
crypto_SHA1_Update(&context, (uint8_t *)"a", 1);
|
||||
crypto_SHA1_Final(&context, digest);
|
||||
digest_to_hex(digest, output);
|
||||
if (strcmp(output, test_results[2])) {
|
||||
fprintf(stdout, "FAIL\n");
|
||||
fprintf(stderr,"* hash of \"%s\" incorrect:\n", test_data[2]);
|
||||
fprintf(stderr,"\t%s returned\n", output);
|
||||
fprintf(stderr,"\t%s is correct\n", test_results[2]);
|
||||
fprintf(stderr, "* hash of \"%s\" incorrect:\n", test_data[2]);
|
||||
fprintf(stderr, "\t%s returned\n", output);
|
||||
fprintf(stderr, "\t%s is correct\n", test_results[2]);
|
||||
return (1);
|
||||
}
|
||||
|
||||
/* success */
|
||||
fprintf(stdout, "ok\n");
|
||||
return(0);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@@ -16,76 +16,50 @@
|
||||
#define LONG_STRING 1024
|
||||
#endif
|
||||
|
||||
int main (void)
|
||||
int main(void)
|
||||
{
|
||||
char buf1[LONG_STRING];
|
||||
char buf2[LONG_STRING];
|
||||
char *fp_fmt[] = {
|
||||
"%-1.5f",
|
||||
"%1.5f",
|
||||
"%123.9f",
|
||||
"%10.5f",
|
||||
"% 10.5f",
|
||||
"%+22.9f",
|
||||
"%+4.9f",
|
||||
"%01.3f",
|
||||
"%4f",
|
||||
"%3.1f",
|
||||
"%3.2f",
|
||||
"%.0f",
|
||||
"%.1f",
|
||||
NULL
|
||||
};
|
||||
double fp_nums[] = { -1.5, 134.21, 91340.2, 341.1234, 0203.9, 0.96, 0.996,
|
||||
0.9996, 1.996, 4.136, 0};
|
||||
char *int_fmt[] = {
|
||||
"%-1.5d",
|
||||
"%1.5d",
|
||||
"%123.9d",
|
||||
"%5.5d",
|
||||
"%10.5d",
|
||||
"% 10.5d",
|
||||
"%+22.33d",
|
||||
"%01.3d",
|
||||
"%4d",
|
||||
"0x%x",
|
||||
"0x%04x",
|
||||
NULL
|
||||
};
|
||||
long int_nums[] = { -1, 134, 91340, 341, 0203, 0x76543210, 0};
|
||||
int x, y;
|
||||
int fail = 0;
|
||||
int num = 0;
|
||||
char buf1[LONG_STRING];
|
||||
char buf2[LONG_STRING];
|
||||
char *fp_fmt[] = {"%-1.5f", "%1.5f", "%123.9f", "%10.5f", "% 10.5f",
|
||||
"%+22.9f", "%+4.9f", "%01.3f", "%4f", "%3.1f",
|
||||
"%3.2f", "%.0f", "%.1f", NULL};
|
||||
double fp_nums[] = {-1.5, 134.21, 91340.2, 341.1234, 0203.9, 0.96,
|
||||
0.996, 0.9996, 1.996, 4.136, 0};
|
||||
char *int_fmt[] = {"%-1.5d", "%1.5d", "%123.9d", "%5.5d",
|
||||
"%10.5d", "% 10.5d", "%+22.33d", "%01.3d",
|
||||
"%4d", "0x%x", "0x%04x", NULL};
|
||||
long int_nums[] = {-1, 134, 91340, 341, 0203, 0x76543210, 0};
|
||||
int x, y;
|
||||
int fail = 0;
|
||||
int num = 0;
|
||||
|
||||
printf ("Testing xmpp_snprintf format codes against system sprintf...\n");
|
||||
printf("Testing xmpp_snprintf format codes against system sprintf...\n");
|
||||
|
||||
for (x = 0; fp_fmt[x] != NULL ; x++)
|
||||
for (y = 0; fp_nums[y] != 0 ; y++)
|
||||
{
|
||||
xmpp_snprintf (buf1, sizeof (buf1), fp_fmt[x], fp_nums[y]);
|
||||
sprintf (buf2, fp_fmt[x], fp_nums[y]);
|
||||
if (strcmp (buf1, buf2))
|
||||
{
|
||||
printf("xmpp_snprintf doesn't match Format: %s\n\txmpp_snprintf = %s\n\tsprintf = %s\n",
|
||||
fp_fmt[x], buf1, buf2);
|
||||
fail++;
|
||||
}
|
||||
num++;
|
||||
}
|
||||
for (x = 0; fp_fmt[x] != NULL; x++)
|
||||
for (y = 0; fp_nums[y] != 0; y++) {
|
||||
xmpp_snprintf(buf1, sizeof(buf1), fp_fmt[x], fp_nums[y]);
|
||||
sprintf(buf2, fp_fmt[x], fp_nums[y]);
|
||||
if (strcmp(buf1, buf2)) {
|
||||
printf("xmpp_snprintf doesn't match Format: "
|
||||
"%s\n\txmpp_snprintf = %s\n\tsprintf = %s\n",
|
||||
fp_fmt[x], buf1, buf2);
|
||||
fail++;
|
||||
}
|
||||
num++;
|
||||
}
|
||||
|
||||
for (x = 0; int_fmt[x] != NULL ; x++)
|
||||
for (y = 0; int_nums[y] != 0 ; y++)
|
||||
{
|
||||
xmpp_snprintf (buf1, sizeof (buf1), int_fmt[x], int_nums[y]);
|
||||
sprintf (buf2, int_fmt[x], int_nums[y]);
|
||||
if (strcmp (buf1, buf2))
|
||||
{
|
||||
printf("xmpp_snprintf doesn't match Format: %s\n\txmpp_snprintf = %s\n\tsprintf = %s\n",
|
||||
int_fmt[x], buf1, buf2);
|
||||
fail++;
|
||||
}
|
||||
num++;
|
||||
}
|
||||
printf ("%d tests failed out of %d.\n", fail, num);
|
||||
return fail != 0 ? 1 : 0;
|
||||
for (x = 0; int_fmt[x] != NULL; x++)
|
||||
for (y = 0; int_nums[y] != 0; y++) {
|
||||
xmpp_snprintf(buf1, sizeof(buf1), int_fmt[x], int_nums[y]);
|
||||
sprintf(buf2, int_fmt[x], int_nums[y]);
|
||||
if (strcmp(buf1, buf2)) {
|
||||
printf("xmpp_snprintf doesn't match Format: "
|
||||
"%s\n\txmpp_snprintf = %s\n\tsprintf = %s\n",
|
||||
int_fmt[x], buf1, buf2);
|
||||
fail++;
|
||||
}
|
||||
num++;
|
||||
}
|
||||
printf("%d tests failed out of %d.\n", fail, num);
|
||||
return fail != 0 ? 1 : 0;
|
||||
}
|
||||
|
||||
@@ -23,14 +23,19 @@ int wait_for_connect(sock_t sock)
|
||||
fd_set wfds, efds;
|
||||
int ret;
|
||||
|
||||
FD_ZERO(&wfds); FD_SET(sock, &wfds);
|
||||
FD_ZERO(&efds); FD_SET(sock, &efds);
|
||||
FD_ZERO(&wfds);
|
||||
FD_SET(sock, &wfds);
|
||||
FD_ZERO(&efds);
|
||||
FD_SET(sock, &efds);
|
||||
|
||||
ret = select(sock + 1, NULL, &wfds, &efds, NULL);
|
||||
if (ret <= 0) return -1;
|
||||
if (ret <= 0)
|
||||
return -1;
|
||||
|
||||
if (FD_ISSET(sock, &efds)) return 0;
|
||||
if (FD_ISSET(sock, &wfds)) return 1;
|
||||
if (FD_ISSET(sock, &efds))
|
||||
return 0;
|
||||
if (FD_ISSET(sock, &wfds))
|
||||
return 1;
|
||||
|
||||
return -1;
|
||||
}
|
||||
@@ -45,15 +50,15 @@ int main(int argc, char **argv)
|
||||
sock = sock_connect("www.google.com", 80);
|
||||
|
||||
if (sock < 0) {
|
||||
sock_shutdown();
|
||||
return 1;
|
||||
sock_shutdown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
err = wait_for_connect(sock);
|
||||
if (err < 0) {
|
||||
sock_close(sock);
|
||||
sock_shutdown();
|
||||
return 1;
|
||||
sock_close(sock);
|
||||
sock_shutdown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
sock_close(sock);
|
||||
|
||||
@@ -23,11 +23,11 @@
|
||||
/* strtok_s() has appeared in visual studio 2005.
|
||||
Use own implementation for older versions. */
|
||||
#ifdef _MSC_VER
|
||||
# if (_MSC_VER >= 1400)
|
||||
# define strtok_r strtok_s
|
||||
# else
|
||||
# define strtok_r xmpp_strtok_r
|
||||
# endif
|
||||
#if (_MSC_VER >= 1400)
|
||||
#define strtok_r strtok_s
|
||||
#else
|
||||
#define strtok_r xmpp_strtok_r
|
||||
#endif
|
||||
#endif /* _MSC_VER */
|
||||
|
||||
static int test_strtok_r(void)
|
||||
@@ -75,8 +75,8 @@ static int test_strdup_one(xmpp_ctx_t *ctx, const char *s)
|
||||
|
||||
if (!s1 || !s2 || strcmp(s1, s2) != 0) {
|
||||
rc = -1;
|
||||
printf("strdup: '%s', xmpp_strdup: '%s'\n",
|
||||
s1 ? s1 : "<NULL>", s2 ? s2 : "<NULL>");
|
||||
printf("strdup: '%s', xmpp_strdup: '%s'\n", s1 ? s1 : "<NULL>",
|
||||
s2 ? s2 : "<NULL>");
|
||||
}
|
||||
|
||||
free(s1);
|
||||
@@ -92,7 +92,7 @@ static int test_strdup(void)
|
||||
size_t i;
|
||||
int rc = 0;
|
||||
|
||||
static const char *tests[] = { "", "\0", "test", "s p a c e", "\n\r" };
|
||||
static const char *tests[] = {"", "\0", "test", "s p a c e", "\n\r"};
|
||||
|
||||
ctx = xmpp_ctx_new(NULL, NULL);
|
||||
assert(ctx != NULL);
|
||||
|
||||
Reference in New Issue
Block a user