package.xml 100644 1750 0 3656 10005423475 6332
sasl
Cyrus SASL Extension
SASL is the Simple Authentication and Security Layer (as defined by RFC 2222). It provides a system for adding plugable authenticating support to connection-based protocols. The SASL Extension for PHP makes the Cyrus SASL library functions available to PHP. It aims to provide a 1-to-1 wrapper around the SASL library to provide the greatest amount of implementation flexibility. To that end, it is possible to build both a client-side and server-side SASL implementation entirely in PHP.
jon
Jon Parise
jon@php.net
lead
0.1.0
2004-01-27
PHP License
alpha
Initial preview release.
0.1.0
2004-01-27
PHP License
alpha
Initial preview release. This package is far from complete, but the basic functionality is available for testing and feedback.
sasl-0.1.0/docs/TODO 100644 1750 24 367 10004160233 7220 SASL Extension TODO List
------------------------
- Write a basic users guide.
- Write some unit tests.
- Support the SASL callback mechanism using PHP userland functions.
- Provide an object-oriented interface (e.g., SASLClient and SASLServer).
sasl-0.1.0/tests/sasl.phpt 100644 1750 24 300 10003440120 10557 --TEST--
sasl: sasl extension
--SKIPIF--
--FILE--
--FILE--
0) {
echo "OK";
}
--EXPECT--
OK
sasl-0.1.0/config.m4 100755 1750 24 3116 10004156224 7332 dnl $Id: config.m4,v 1.2 2004/01/23 08:34:28 jon Exp $
dnl vim: expandtab
PHP_ARG_WITH(sasl, whether to enable SASL functions,
[ --with-sasl[=DIR] Enable support for SASL functions])
if test "$PHP_SASL" != "no"; then
SEARCH_DIRS="/usr/local /usr"
SEARCH_SUBS="sasl sasl1 sasl2"
SEARCH_LIBS="sasl2 sasl"
if test -r $PHP_SASL; then
SASL_DIR=$PHP_SASL;
else
AC_MSG_CHECKING(for SASL files in default path)
for i in $SEARCH_DIRS; do
for j in $SEARCH_SUBS; do
if test -r $i/include/$j/sasl.h; then
SASL_DIR=$i
SASL_SUB=$j
AC_MSG_RESULT(found in $i)
fi
done
done
fi
if test -z "$SASL_DIR"; then
AC_MSG_RESULT(not found)
AC_MSG_ERROR(Please specify path to SASL installation)
fi
AC_MSG_CHECKING(for SASL library in $SASL_DIR/lib)
for i in $SEARCH_LIBS; do
if test -r $SASL_DIR/lib/lib$i.a; then
SASL_LIB=$i
AC_MSG_RESULT(found -l$i)
fi
done
if test -z "$SASL_LIB"; then
AC_MSG_RESULT(not found)
AC_MSG_ERROR(Failed to locate a compatible SASL library in $SASL_DIR/lib)
fi
LIBSYMBOL=sasl_server_init
old_LIBS=$LIBS
LIBS="$LIBS -L$SASL_DIR/lib"
AC_CHECK_LIB($SASL_LIB, $LIBSYMBOL, [AC_DEFINE(HAVE_SASL_LIB,1,[ ])],
[AC_MSG_ERROR(unknown SASL library or library not found)])
LIBS=$old_LIBS
AC_DEFINE(HAVE_SASL,1,[ ])
PHP_SUBST(SASL_SHARED_LIBADD)
PHP_ADD_LIBRARY_WITH_PATH($SASL_LIB, $SASL_DIR/lib, SASL_SHARED_LIBADD)
PHP_ADD_INCLUDE($SASL_DIR/include/$SASL_SUB)
PHP_NEW_EXTENSION(sasl, sasl.c, $ext_shared)
fi
sasl-0.1.0/config.w32 100644 1750 24 716 10003707034 7405 // $Id: config.w32,v 1.1 2004/01/22 08:47:24 jon Exp $
// vim:ft=javascript
ARG_WITH("sasl", "Cyrus SASL support", "no");
if (PHP_SASL != "no") {
if (CHECK_HEADER_ADD_INCLUDE("sasl.h", "CFLAGS_SASL",
PHP_SASL + "\\include") &&
CHECK_LIB("libsasl.lib", "sasl", PHP_SASL + "\\lib")) {
EXTENSION("sasl", "sasl.c", null, "/D SASL_EXPORTS");
AC_DEFINE("HAVE_SASL", 1);
} else {
WARNING("sasl not enabled; libraries and headers not found");
}
}
sasl-0.1.0/Makefile.in 100644 1750 24 362 10003432502 7640 # $Id: Makefile.in,v 1.1 2004/01/21 08:16:02 jon Exp $
LTLIBRARY_NAME = libsasl.la
LTLIBRARY_SOURCES = sasl.c
LTLIBRARY_SHARED_NAME = sasl.la
LTLIBRARY_SHARED_LIBADD = $(SASL_SHARED_LIBADD)
include $(top_srcdir)/build/dynlib.mk
sasl-0.1.0/php_sasl.h 100644 1750 24 4344 10004156224 7606 /*
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
| Copyright (c) 1997-2004 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
| available at through the world-wide-web at |
| http://www.php.net/license/3_0.txt. |
| If you did not receive a copy of the PHP license and are unable to |
| obtain it through the world-wide-web, please send a note to |
| license@php.net so we can mail you a copy immediately. |
+----------------------------------------------------------------------+
| Author: Jon Parise |
+----------------------------------------------------------------------+
*/
/* $Id: php_sasl.h,v 1.2 2004/01/23 08:34:28 jon Exp $ */
#ifndef PHP_SASL_H
#define PHP_SASL_H
#include
extern zend_module_entry sasl_module_entry;
#define phpext_sasl_ptr &sasl_module_entry
#ifdef PHP_WIN32
#define PHP_SASL_API __declspec(dllexport)
#else
#define PHP_SASL_API
#endif
#ifdef ZTS
#include "TSRM.h"
#endif
PHP_MINIT_FUNCTION(sasl);
PHP_MSHUTDOWN_FUNCTION(sasl);
PHP_MINFO_FUNCTION(sasl);
/* Common Functions */
PHP_FUNCTION(sasl_version);
PHP_FUNCTION(sasl_errstring);
#if SASL_VERSION_MAJOR >= 2
PHP_FUNCTION(sasl_errdetail);
#endif
PHP_FUNCTION(sasl_encode);
PHP_FUNCTION(sasl_decode);
/* Client Functions */
PHP_FUNCTION(sasl_client_init);
PHP_FUNCTION(sasl_client_new);
PHP_FUNCTION(sasl_client_start);
PHP_FUNCTION(sasl_client_step);
/* Server Functions */
PHP_FUNCTION(sasl_server_init);
PHP_FUNCTION(sasl_server_new);
PHP_FUNCTION(sasl_server_start);
PHP_FUNCTION(sasl_server_step);
PHP_FUNCTION(sasl_listmech);
PHP_FUNCTION(sasl_checkpass);
#if 0
#ifdef ZTS
#define SASLG(v) TSRMG(sasl_globals_id, zend_sasl_globals *, v)
#else
#define SASLG(v) (sasl_globals.v)
#endif
#endif
#endif /* PHP_SASL_H */
sasl-0.1.0/sasl.c 100644 1750 24 43562 10004156224 6757 /*
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
| Copyright (c) 1997-2004 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
| available at through the world-wide-web at |
| http://www.php.net/license/3_0.txt. |
| If you did not receive a copy of the PHP license and are unable to |
| obtain it through the world-wide-web, please send a note to |
| license@php.net so we can mail you a copy immediately. |
+----------------------------------------------------------------------+
| Author: Jon Parise |
+----------------------------------------------------------------------+
*/
/* $Id: sasl.c,v 1.3 2004/01/23 08:34:28 jon Exp $ */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "php.h"
#include "php_ini.h"
#include "php_sasl.h"
#include "ext/standard/info.h"
#define SASL_CONSTANT(c) REGISTER_LONG_CONSTANT(#c, c, \
CONST_CS | CONST_PERSISTENT)
#if SASL_VERSION_MAJOR < 2
typedef char php_sasl_char;
#define PHP_SASL_FREE(p) if (p) free(p);
#else
typedef const char php_sasl_char;
#define PHP_SASL_FREE(p)
#endif
#define le_conn_name "SASL Connection Context"
static int le_conn;
/* {{{ sasl_callbacks[]
Global callbacks. These have no per-session context. */
static sasl_callback_t sasl_callbacks[] = {
{ SASL_CB_LIST_END, 0, 0 }
};
/* }}}*/
/* {{{ php_sasl_error(int level, int reason)
*/
static void php_sasl_error(int level, int code TSRMLS_DC)
{
php_error_docref(NULL TSRMLS_CC, level,
"%s", sasl_errstring(code, NULL, NULL));
}
/* }}} */
/* {{{ php_sasl_destroy_conn(zend_rsrc_list_entry *rsrc TSRMLS_DC)
*/
static void php_sasl_destroy_conn(zend_rsrc_list_entry *rsrc TSRMLS_DC)
{
sasl_conn_t *conn = (sasl_conn_t *)rsrc->ptr;
sasl_dispose(&conn);
}
/* }}} */
/* {{{ sasl_functions[]
*/
function_entry sasl_functions[] = {
/* Common Functions */
PHP_FE(sasl_version, NULL)
PHP_FE(sasl_errstring, NULL)
#if SASL_VERSION_MAJOR >= 2
PHP_FE(sasl_errdetail, NULL)
#endif
PHP_FE(sasl_encode, NULL)
PHP_FE(sasl_decode, NULL)
/* Client Functions */
PHP_FE(sasl_client_init, NULL)
PHP_FE(sasl_client_new, NULL)
PHP_FE(sasl_client_start, NULL)
PHP_FE(sasl_client_step, NULL)
/* Server Functions */
PHP_FE(sasl_server_init, NULL)
PHP_FE(sasl_server_new, NULL)
PHP_FE(sasl_server_start, NULL)
PHP_FE(sasl_server_step, NULL)
PHP_FE(sasl_listmech, NULL)
PHP_FE(sasl_checkpass, NULL)
{NULL, NULL, NULL}
};
/* }}} */
/* {{{ sasl_module_entry
*/
zend_module_entry sasl_module_entry = {
STANDARD_MODULE_HEADER,
"sasl",
sasl_functions,
PHP_MINIT(sasl),
PHP_MSHUTDOWN(sasl),
NULL,
NULL,
PHP_MINFO(sasl),
NO_VERSION_YET,
STANDARD_MODULE_PROPERTIES
};
#ifdef COMPILE_DL_SASL
ZEND_GET_MODULE(sasl)
#endif
/* }}} */
/* {{{ PHP_MINIT_FUNCTION
*/
PHP_MINIT_FUNCTION(sasl)
{
le_conn = zend_register_list_destructors_ex(php_sasl_destroy_conn, NULL,
le_conn_name, module_number);
/* SASL result codes */
SASL_CONSTANT(SASL_CONTINUE);
SASL_CONSTANT(SASL_OK);
SASL_CONSTANT(SASL_FAIL);
SASL_CONSTANT(SASL_NOMEM);
SASL_CONSTANT(SASL_BUFOVER);
SASL_CONSTANT(SASL_NOMECH);
SASL_CONSTANT(SASL_BADPROT);
SASL_CONSTANT(SASL_NOTDONE);
SASL_CONSTANT(SASL_BADPARAM);
SASL_CONSTANT(SASL_TRYAGAIN);
SASL_CONSTANT(SASL_BADMAC);
#if SASL_VERSION_MAJOR >= 2
SASL_CONSTANT(SASL_NOTINIT);
#endif
/* Client only: */
SASL_CONSTANT(SASL_INTERACT);
SASL_CONSTANT(SASL_BADSERV);
SASL_CONSTANT(SASL_WRONGMECH);
/* Server only: */
SASL_CONSTANT(SASL_BADAUTH);
SASL_CONSTANT(SASL_NOAUTHZ);
SASL_CONSTANT(SASL_TOOWEAK);
SASL_CONSTANT(SASL_ENCRYPT);
SASL_CONSTANT(SASL_TRANS);
SASL_CONSTANT(SASL_EXPIRED);
SASL_CONSTANT(SASL_DISABLED);
SASL_CONSTANT(SASL_NOUSER);
SASL_CONSTANT(SASL_BADVERS);
#if SASL_VERSION_MAJOR >= 2
SASL_CONSTANT(SASL_UNAVAIL);
SASL_CONSTANT(SASL_NOVERIFY);
#endif
/* SASL usage flags (for sasl_server_new and sasl_client_new) */
#if SASL_VERSION_MAJOR >= 2
SASL_CONSTANT(SASL_SUCCESS_DATA);
SASL_CONSTANT(SASL_NEED_PROXY);
#endif
/* SASL security flags */
SASL_CONSTANT(SASL_SEC_NOPLAINTEXT);
SASL_CONSTANT(SASL_SEC_NOACTIVE);
SASL_CONSTANT(SASL_SEC_NODICTIONARY);
SASL_CONSTANT(SASL_SEC_FORWARD_SECRECY);
SASL_CONSTANT(SASL_SEC_NOANONYMOUS);
SASL_CONSTANT(SASL_SEC_PASS_CREDENTIALS);
#if SASL_VERSION_MAJOR >= 2
SASL_CONSTANT(SASL_SEC_MUTUAL_AUTH);
SASL_CONSTANT(SASL_SEC_MAXIMUM);
#endif
return SUCCESS;
}
/* }}} */
/* {{{ PHP_MSHUTDOWN_FUNCTION
*/
PHP_MSHUTDOWN_FUNCTION(sasl)
{
sasl_done();
return SUCCESS;
}
/* }}} */
/* {{{ PHP_MINFO_FUNCTION
*/
PHP_MINFO_FUNCTION(sasl)
{
char api_version[16], lib_version[64];
const char *sasl_implementation = "Unknown";
int libsasl_version;
int libsasl_major = SASL_VERSION_MAJOR;
int libsasl_minor = SASL_VERSION_MINOR;
int libsasl_step = SASL_VERSION_STEP;
#if SASL_VERSION_MAJOR >= 2
/* Grab the version information from the SASL library. */
sasl_version(&sasl_implementation, &libsasl_version);
libsasl_major = libsasl_version >> 24;
libsasl_minor = (libsasl_version >> 16) & 0xFF;
libsasl_step = libsasl_version & 0xFFFF;
#endif
/* Build the version strings. */
snprintf(api_version, 16, "%u.%u.%u",
SASL_VERSION_MAJOR, SASL_VERSION_MINOR, SASL_VERSION_STEP);
snprintf(lib_version, 64, "%u.%u.%u (%s)",
libsasl_major, libsasl_minor, libsasl_step, sasl_implementation);
php_info_print_table_start();
php_info_print_table_row(2, "SASL Support", "enabled");
php_info_print_table_row(2, "SASL API Version", api_version);
php_info_print_table_row(2, "SASL Library Version", lib_version);
php_info_print_table_row(2, "Extension Version", "$Revision: 1.3 $");
php_info_print_table_end();
}
/* }}} */
/* Common Functions */
/* {{{ proto string sasl_version()
Return the SASL library version information. */
PHP_FUNCTION(sasl_version)
{
char version[64];
const char *sasl_implementation = "Unknown";
int libsasl_version;
int libsasl_major = SASL_VERSION_MAJOR;
int libsasl_minor = SASL_VERSION_MINOR;
int libsasl_step = SASL_VERSION_STEP;
#if SASL_VERSION_MAJOR >= 2
/* Grab the version information from the SASL library. */
sasl_version(&sasl_implementation, &libsasl_version);
libsasl_major = libsasl_version >> 24;
libsasl_minor = (libsasl_version >> 16) & 0xFF;
libsasl_step = libsasl_version & 0xFFFF;
#endif
snprintf(version, 64, "%u.%u.%u (%s)",
libsasl_major, libsasl_minor, libsasl_step, sasl_implementation);
RETURN_STRING(version, 1);
}
/* }}} */
/* {{{ proto string sasl_errdetail(resource conn)
Returns detail about the last error that occured on the given connection. */
#if SASL_VERSION_MAJOR >= 2
PHP_FUNCTION(sasl_errdetail)
{
zval *rsrc;
sasl_conn_t *conn;
if (zend_parse_parameters(1 TSRMLS_CC, "r", &rsrc) == FAILURE) {
return;
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
RETURN_STRING((char *)sasl_errdetail(conn), 1);
}
#endif
/* }}} */
/* {{{ proto string sasl_errstring(int code [, string languages])
Returns the string translation of the given error code. */
PHP_FUNCTION(sasl_errstring)
{
long code;
char *languages = NULL;
int languages_len;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l|s",
&code, &languages, &languages_len) == FAILURE) {
return;
}
RETURN_STRING((char *)sasl_errstring(code, languages, NULL), 1);
}
/* }}} */
/* {{{ proto string sasl_encode(resource conn, string input)
Encodes a block of data for tranmission using the security layer. */
PHP_FUNCTION(sasl_encode)
{
zval *rsrc;
sasl_conn_t *conn;
char *input;
int input_len;
php_sasl_char *output = NULL;
unsigned output_len = 0;
int r = SASL_FAIL;
if (zend_parse_parameters(2 TSRMLS_CC, "rs",
&rsrc, &input, &input_len) == FAILURE) {
return;
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
r = sasl_encode(conn, input, input_len, &output, &output_len);
if (r != SASL_OK) {
php_sasl_error(E_NOTICE, r TSRMLS_CC);
PHP_SASL_FREE(output);
RETURN_EMPTY_STRING();
}
RETVAL_STRINGL((char *)output, output_len, 1);
PHP_SASL_FREE(output);
}
/* }}} */
/* {{{ proto string sasl_decode(resource conn, string input)
Decode a block of data received using the security layer. */
PHP_FUNCTION(sasl_decode)
{
zval *rsrc;
sasl_conn_t *conn;
char *input;
int input_len;
php_sasl_char *output = NULL;
unsigned output_len = 0;
int r = SASL_FAIL;
if (zend_parse_parameters(2 TSRMLS_CC, "rs",
&rsrc, &input, &input_len) == FAILURE) {
return;
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
r = sasl_decode(conn, input, input_len, &output, &output_len);
if (r != SASL_OK) {
php_sasl_error(E_NOTICE, r TSRMLS_CC);
PHP_SASL_FREE(output);
RETURN_EMPTY_STRING();
}
RETVAL_STRINGL((char *)output, output_len, 1);
PHP_SASL_FREE(output);
}
/* }}} */
/* Client Functions */
/* {{{ proto bool sasl_client_init()
Initializes the SASL client drivers. */
PHP_FUNCTION(sasl_client_init)
{
if (sasl_client_init(NULL) != SASL_OK) {
RETURN_FALSE;
}
RETURN_TRUE;
}
/* }}} */
/* {{{ proto resource sasl_client_new(string service [, string hostname [, int flags]])
Creates a new SASL client connection context. */
PHP_FUNCTION(sasl_client_new)
{
char *service, *hostname = NULL;
int server_len, hostname_len;
long flags = 0;
sasl_conn_t *conn = NULL;
int r = SASL_FAIL;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|sl",
&service, &server_len,
&hostname, &hostname_len,
&flags) == FAILURE) {
return;
}
#if SASL_VERSION_MAJOR < 2
r = sasl_client_new(service, hostname, NULL, flags, &conn);
#else
r = sasl_client_new(service, hostname, NULL, NULL, NULL, flags, &conn);
#endif
/* If sasl_client_new() failed, print an error and return false. */
if (r != SASL_OK) {
php_sasl_error(E_ERROR, r TSRMLS_CC);
RETURN_FALSE;
}
ZEND_REGISTER_RESOURCE(return_value, conn, le_conn);
}
/* }}} */
/* {{{ proto bool sasl_client_start(resource conn, string mechlist [, string &$output [, string &$mech]])
Starts an authentication session. */
PHP_FUNCTION(sasl_client_start)
{
zval *rsrc, *output = NULL, *mech = NULL;
sasl_conn_t *conn;
char *mechlist;
int mechlist_len;
php_sasl_char *data = NULL;
unsigned data_len = 0;
const char *chosenmech = NULL;
int r = SASL_FAIL;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs|z/z/",
&rsrc,
&mechlist, &mechlist_len,
&output, &mech) == FAILURE) {
return;
}
if (output) {
zval_dtor(output);
}
if (mech) {
zval_dtor(mech);
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
#if SASL_VERSION_MAJOR < 2
r = sasl_client_start(conn, mechlist, NULL, NULL, &data, &data_len,
&chosenmech);
#else
r = sasl_client_start(conn, mechlist, NULL, &data, &data_len, &chosenmech);
#endif
/* Print a warning and return false if we receive an unexpected result. */
if ((r != SASL_OK) && (r != SASL_CONTINUE)) {
php_sasl_error(E_WARNING, r TSRMLS_CC);
RETURN_FALSE;
}
/* Store the output in the "output" parameter (by reference). */
ZVAL_STRINGL(output, (char *)data, data_len, 1);
PHP_SASL_FREE(data);
/* Store the chosen mechanism in the "mech" parameter (by reference). */
ZVAL_STRING(mech, (char *)chosenmech, 1);
RETURN_TRUE;
}
/* }}} */
/* {{{ proto int sasl_client_step(resource conn, string input, string &$output)
Performs a step in the authentication process. */
PHP_FUNCTION(sasl_client_step)
{
zval *rsrc, *output = NULL;
sasl_conn_t *conn;
char *input;
int input_len;
php_sasl_char *data = NULL;
unsigned data_len = 0;
int r = SASL_FAIL;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rsz/",
&rsrc,
&input, &input_len,
&output) == FAILURE) {
return;
}
if (output) {
zval_dtor(output);
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
r = sasl_client_step(conn, input, input_len, NULL, &data, &data_len);
/* Print a warning if we receive an unexpected result. */
if ((r != SASL_OK) && (r != SASL_CONTINUE)) {
php_sasl_error(r, E_WARNING TSRMLS_CC);
}
/* Store the output in the "output" parameter (passed by reference). */
ZVAL_STRINGL(output, (char *)data, data_len, 1);
PHP_SASL_FREE(data);
/* Simply return the result code from sasl_server_step(). */
RETURN_LONG(r);
}
/* }}} */
/* Server Functions */
/* {{{ proto bool sasl_server_init(string name)
Initializes the session and loads the shared authentication mechanisms. */
PHP_FUNCTION(sasl_server_init)
{
char *name;
int name_len;
if (zend_parse_parameters(1 TSRMLS_CC, "s", &name, &name_len) == FAILURE) {
return;
}
if (sasl_server_init(NULL, name) != SASL_OK) {
RETURN_FALSE;
}
RETURN_TRUE;
}
/* }}} */
/* {{{ proto resource sasl_server_new(string service [, string hostname [, string realm]])
Creates a new SASL server connection context. */
PHP_FUNCTION(sasl_server_new)
{
char *service, *hostname = NULL, *realm = NULL;
int server_len, hostname_len, realm_len;
sasl_conn_t *conn = NULL;
int r = SASL_FAIL;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|ss",
&service, &server_len,
&hostname, &hostname_len,
&realm, &realm_len) == FAILURE) {
return;
}
#if SASL_VERSION_MAJOR < 2
r = sasl_server_new(service, hostname, realm, NULL, 0, &conn);
#else
r = sasl_server_new(service, hostname, realm, NULL, NULL, NULL, 0, &conn);
#endif
/* If sasl_server_new() failed, print an error and return false. */
if (r != SASL_OK) {
php_sasl_error(E_ERROR, r TSRMLS_CC);
RETURN_FALSE;
}
ZEND_REGISTER_RESOURCE(return_value, conn, le_conn);
}
/* }}} */
/* {{{ proto int sasl_server_start(resource conn, string mech, string input, string &$output)
Begins the auhentication process with a client. */
PHP_FUNCTION(sasl_server_start)
{
zval *rsrc, *output;
sasl_conn_t *conn;
char *mech, *input;
int mech_len, input_len;
php_sasl_char *data = NULL;
unsigned data_len = 0;
int r = SASL_FAIL;
if (zend_parse_parameters(4 TSRMLS_CC, "rssz/",
&rsrc,
&mech, &mech_len,
&input, &input_len,
&output) == FAILURE) {
return;
}
if (mech_len > SASL_MECHNAMEMAX) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,
"mechanism name exceeds maximum length (%u chars)",
SASL_MECHNAMEMAX);
RETURN_FALSE;
}
if (output) {
zval_dtor(output);
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
#if SASL_VERSION_MAJOR < 2
r = sasl_server_start(conn, mech, input, input_len, &data, &data_len, NULL);
#else
r = sasl_server_start(conn, mech, input, input_len, &data, &data_len);
#endif
/* Print a warning if we receive an unexpected result. */
if ((r != SASL_OK) && (r != SASL_CONTINUE)) {
php_sasl_error(E_WARNING, r TSRMLS_CC);
}
/* Store the output in the "output" parameter (passed by reference). */
ZVAL_STRINGL(output, (char *)data, data_len, 1);
PHP_SASL_FREE(data);
/* Simply return the result code from sasl_server_start(). */
RETURN_LONG(r);
}
/* }}} */
/* {{{ proto int sasl_server_step(resource conn, string input, string &$output)
Performs a step of the authentication. */
PHP_FUNCTION(sasl_server_step)
{
zval *rsrc, *output = NULL;
sasl_conn_t *conn;
char *input;
int input_len;
php_sasl_char *data = NULL;
unsigned data_len = 0;
int r = SASL_FAIL;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rsz/",
&rsrc,
&input, &input_len,
&output) == FAILURE) {
return;
}
if (output) {
zval_dtor(output);
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
#if SASL_VERSION_MAJOR < 2
r = sasl_server_step(conn, input, input_len, &data, &data_len, NULL);
#else
r = sasl_server_step(conn, input, input_len, &data, &data_len);
#endif
/* Print a warning if we receive an unexpected result. */
if ((r != SASL_OK) && (r != SASL_CONTINUE)) {
php_sasl_error(r, E_WARNING TSRMLS_CC);
}
/* Store the output in the "output" parameter (passed by reference). */
ZVAL_STRINGL(output, (char *)data, data_len, 1);
PHP_SASL_FREE(data);
/* Simply return the result code from sasl_server_step(). */
RETURN_LONG(r);
}
/* }}} */
/* {{{ proto string sasl_listmech(resource conn)
Creates a string with a list of SASL mechanism support by the server. */
PHP_FUNCTION(sasl_listmech)
{
zval *rsrc;
sasl_conn_t *conn;
php_sasl_char *data = NULL;
unsigned data_len = 0, count;
int r = SASL_FAIL;
if (zend_parse_parameters(1 TSRMLS_CC, "r", &rsrc) == FAILURE) {
return;
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
r = sasl_listmech(conn, NULL, NULL, " ", NULL, &data, &data_len, &count);
/* If sasl_listmech() failed, print an error and return an empty string. */
if (r != SASL_OK) {
php_sasl_error(E_WARNING, r TSRMLS_CC);
PHP_SASL_FREE(data);
RETURN_EMPTY_STRING();
}
RETVAL_STRINGL((char *)data, data_len, 1);
PHP_SASL_FREE(data);
}
/* }}} */
/* {{{ proto bool sasl_checkpass(resource conn, string user, string pass)
Checks a plaintext password for the given user. */
PHP_FUNCTION(sasl_checkpass)
{
zval *rsrc;
sasl_conn_t *conn;
char *user, *pass;
int user_len, pass_len;
int r = SASL_FAIL;
if (zend_parse_parameters(3 TSRMLS_CC, "rss",
&rsrc,
&user, &user_len,
&pass, &pass_len) == FAILURE) {
return;
}
ZEND_FETCH_RESOURCE(conn, sasl_conn_t *, &rsrc, -1, le_conn_name, le_conn);
#if SASL_VERSION_MAJOR < 2
r = sasl_checkpass(conn, user, user_len, pass, pass_len, NULL);
#else
r = sasl_checkpass(conn, user, user_len, pass, pass_len);
#endif
if (r != SASL_OK) {
RETURN_FALSE;
}
RETURN_TRUE;
}
/* }}} */
/*
* Local variables:
* c-basic-offset: 4
* tab-width: 4
* End:
* vim600: fdm=marker
* vim: sw=4 ts=4 noet
*/