X-Git-Url: https://git.m6w6.name/?a=blobdiff_plain;f=libmemcached%2Fsasl.cc;h=3d93b78686b880f7cc20b4376565191f5b783eab;hb=ca663a567bc8d3facb22b035bcad19349e42a9b1;hp=f1de41eaec4fe30f86416da7714f625e169c0ba6;hpb=58c279d58e2a44562f729e93e301dfedf42f530b;p=m6w6%2Flibmemcached diff --git a/libmemcached/sasl.cc b/libmemcached/sasl.cc index f1de41ea..3d93b786 100644 --- a/libmemcached/sasl.cc +++ b/libmemcached/sasl.cc @@ -40,7 +40,10 @@ #if defined(LIBMEMCACHED_WITH_SASL_SUPPORT) && LIBMEMCACHED_WITH_SASL_SUPPORT +#if defined(HAVE_LIBSASL) && HAVE_LIBSASL #include +#endif + #include void memcached_set_sasl_callbacks(memcached_st *ptr, @@ -62,7 +65,7 @@ sasl_callback_t *memcached_get_sasl_callbacks(memcached_st *ptr) * @param raddr remote address (out) * @return true on success false otherwise (errno contains more info) */ -static memcached_return_t resolve_names(memcached_server_st& server, char *laddr, size_t laddr_length, char *raddr, size_t raddr_length) +static memcached_return_t resolve_names(memcached_instance_st& server, char *laddr, size_t laddr_length, char *raddr, size_t raddr_length) { char host[NI_MAXHOST]; char port[NI_MAXSERV]; @@ -98,12 +101,15 @@ static memcached_return_t resolve_names(memcached_server_st& server, char *laddr return MEMCACHED_SUCCESS; } +extern "C" { + static void sasl_shutdown_function() { sasl_done(); } -static int sasl_startup_state= SASL_OK; +static volatile int sasl_startup_state= SASL_OK; +pthread_mutex_t sasl_startup_state_LOCK= PTHREAD_MUTEX_INITIALIZER; static pthread_once_t sasl_startup_once= PTHREAD_ONCE_INIT; static void sasl_startup_function(void) { @@ -115,7 +121,9 @@ static void sasl_startup_function(void) } } -memcached_return_t memcached_sasl_authenticate_connection(memcached_server_st *server) +} // extern "C" + +memcached_return_t memcached_sasl_authenticate_connection(memcached_instance_st *server) { if (LIBMEMCACHED_WITH_SASL_SUPPORT == 0) { @@ -128,9 +136,10 @@ memcached_return_t memcached_sasl_authenticate_connection(memcached_server_st *s } /* SANITY CHECK: SASL can only be used with the binary protocol */ - if (server->root->flags.binary_protocol == false) + if (memcached_is_binary(server->root) == false) { - return MEMCACHED_PROTOCOL_ERROR; + return memcached_set_error(*server, MEMCACHED_INVALID_ARGUMENTS, MEMCACHED_AT, + memcached_literal_param("memcached_sasl_authenticate_connection() is not supported via the ASCII protocol")); } /* Try to get the supported mech from the server. Servers without SASL @@ -138,7 +147,9 @@ memcached_return_t memcached_sasl_authenticate_connection(memcached_server_st *s * as authenticated */ protocol_binary_request_no_extras request= { }; - request.message.header.request.magic= PROTOCOL_BINARY_REQ; + + initialize_binary_request(ptr, request.message.header); + request.message.header.request.opcode= PROTOCOL_BINARY_CMD_SASL_LIST_MECHS; if (memcached_io_write(server, request.bytes, @@ -182,12 +193,14 @@ memcached_return_t memcached_sasl_authenticate_connection(memcached_server_st *s return memcached_set_errno(*server, pthread_error, MEMCACHED_AT); } + (void)pthread_mutex_lock(&sasl_startup_state_LOCK); if (sasl_startup_state != SASL_OK) { const char *sasl_error_msg= sasl_errstring(sasl_startup_state, NULL, NULL); return memcached_set_error(*server, MEMCACHED_AUTH_PROBLEM, MEMCACHED_AT, memcached_string_make_from_cstr(sasl_error_msg)); } + (void)pthread_mutex_unlock(&sasl_startup_state_LOCK); sasl_conn_t *conn; int ret; @@ -222,14 +235,14 @@ memcached_return_t memcached_sasl_authenticate_connection(memcached_server_st *s do { /* send the packet */ - struct libmemcached_io_vector_st vector[]= + libmemcached_io_vector_st vector[]= { - { sizeof(request.bytes), request.bytes }, - { keylen, chosenmech }, - { len, data } + { request.bytes, sizeof(request.bytes) }, + { chosenmech, keylen }, + { data, len } }; - if (memcached_io_writev(server, vector, 3, true) == -1) + if (memcached_io_writev(server, vector, 3, true) == false) { rc= MEMCACHED_WRITE_FAILURE; break; @@ -314,7 +327,7 @@ memcached_return_t memcached_set_sasl_auth_data(memcached_st *ptr, memcached_destroy_sasl_auth_data(ptr); - sasl_callback_t *callbacks= (sasl_callback_t*)libmemcached_calloc(ptr, 4, sizeof(sasl_callback_t)); + sasl_callback_t *callbacks= libmemcached_xcalloc(ptr, 4, sasl_callback_t); size_t password_length= strlen(password); size_t username_length= strlen(username); char *name= (char *)libmemcached_malloc(ptr, username_length +1); @@ -416,7 +429,7 @@ memcached_return_t memcached_clone_sasl(memcached_st *clone, const memcached_st * into the list, but if we don't know the ID we don't know how to handle * the context... */ - size_t total= 0; + ptrdiff_t total= 0; while (source->sasl.callbacks[total].id != SASL_CB_LIST_END) { @@ -434,7 +447,7 @@ memcached_return_t memcached_clone_sasl(memcached_st *clone, const memcached_st ++total; } - sasl_callback_t *callbacks= (sasl_callback_t*)libmemcached_calloc(clone, total +1, sizeof(sasl_callback_t)); + sasl_callback_t *callbacks= libmemcached_xcalloc(clone, total +1, sasl_callback_t); if (callbacks == NULL) { return MEMCACHED_MEMORY_ALLOCATION_FAILURE; @@ -442,7 +455,7 @@ memcached_return_t memcached_clone_sasl(memcached_st *clone, const memcached_st memcpy(callbacks, source->sasl.callbacks, (total + 1) * sizeof(sasl_callback_t)); /* Now update the context... */ - for (size_t x= 0; x < total; ++x) + for (ptrdiff_t x= 0; x < total; ++x) { if (callbacks[x].id == SASL_CB_USER || callbacks[x].id == SASL_CB_AUTHNAME) { @@ -451,7 +464,7 @@ memcached_return_t memcached_clone_sasl(memcached_st *clone, const memcached_st if (callbacks[x].context == NULL) { /* Failed to allocate memory, clean up previously allocated memory */ - for (size_t y= 0; y < x; ++y) + for (ptrdiff_t y= 0; y < x; ++y) { libmemcached_free(clone, clone->sasl.callbacks[y].context); } @@ -468,7 +481,7 @@ memcached_return_t memcached_clone_sasl(memcached_st *clone, const memcached_st if (n == NULL) { /* Failed to allocate memory, clean up previously allocated memory */ - for (size_t y= 0; y < x; ++y) + for (ptrdiff_t y= 0; y < x; ++y) { libmemcached_free(clone, clone->sasl.callbacks[y].context); }