char *sasl_host = NULL;
int sasl_ssf = 0;
#endif
+ char *host;
int port;
long addr;
port = htons( (short) srv->lud_port );
addr = 0;
- if ( srv->lud_host == NULL || *srv->lud_host == 0 )
+ if ( srv->lud_host == NULL || *srv->lud_host == 0 ) {
+ host = NULL;
addr = htonl( INADDR_LOOPBACK );
+ } else {
+ host = srv->lud_host;
+ }
rc = ldap_connect_to_host( ld, conn->lconn_sb, 0,
- srv->lud_host, addr, port, async );
+ host, addr, port, async );
if ( rc == -1 ) return rc;
{
int so_errno;
int dummy = sizeof(so_errno);
- if ( getsockopt( s, SOL_SOCKET, SO_ERROR, &so_errno, &dummy ) == -1 ) {
+ if ( getsockopt( s, SOL_SOCKET, SO_ERROR, &so_errno, &dummy )
+ == AC_SOCKET_ERROR )
+ {
return -1;
}
if ( so_errno ) {
struct sockaddr_in sin;
char ch;
int dummy = sizeof(sin);
- if ( getpeername( s, (struct sockaddr *) &sin, &dummy ) == -1 ) {
+ if ( getpeername( s, (struct sockaddr *) &sin, &dummy )
+ == AC_SOCKET_ERROR )
+ {
/* XXX: needs to be replace with ber_stream_read() */
read(s, &ch, 1);
#ifdef HAVE_WINSOCK
if ( ldap_pvt_ndelay_on(ld, s) == -1 )
return ( -1 );
- if ( connect(s, sin, addrlen) == 0 )
+ if ( connect(s, sin, addrlen) != AC_SOCKET_ERROR )
{
if ( ldap_pvt_ndelay_off(ld, s) == -1 )
return ( -1 );
#else
z,
#endif
- opt_tv ? &tv : NULL) == -1)
+ opt_tv ? &tv : NULL) == AC_SOCKET_ERROR )
+ {
return ( -1 );
+ }
#ifdef HAVE_WINSOCK
/* This means the connection failed */
- if (FD_ISSET(s, &efds))
- {
+ if ( FD_ISSET(s, &efds) ) {
ldap_pvt_set_errno(WSAECONNREFUSED);
osip_debug(ld, "ldap_pvt_connect: error on socket %d: "
"errno: %d (%s)\n", s, errno, sock_errstr(errno));
if (host != NULL) {
#ifdef HAVE_GETADDRINFO
char serv[7];
+ int err;
struct addrinfo hints, *res, *sai;
memset( &hints, '\0', sizeof(hints) );
hints.ai_socktype = SOCK_STREAM;
snprintf(serv, sizeof serv, "%d", ntohs(port));
- if ( getaddrinfo(host, serv, &hints, &res) ) {
- osip_debug(ld, "ldap_connect_to_host:getaddrinfo failed\n",0,0,0);
+ if ( err = getaddrinfo(host, serv, &hints, &res) ) {
+ osip_debug(ld, "ldap_connect_to_host: getaddrinfo failed: %s\n", AC_GAI_STRERROR(err), 0, 0);
return -1;
}
sai = res;
do {
/* we assume AF_x and PF_x are equal for all x */
s = ldap_int_socket( ld, sai->ai_family, SOCK_STREAM );
- if ( s == -1 ) {
+ if ( s == AC_SOCKET_INVALID ) {
continue;
}
for ( i = 0; !use_hp || (hp->h_addr_list[i] != 0); ++i, rc = -1 ) {
s = ldap_int_socket( ld, PF_INET, SOCK_STREAM );
- if ( s == -1 ) {
+ if ( s == AC_SOCKET_INVALID ) {
/* use_hp ? continue : break; */
break;
}
{
int so_errno;
int dummy = sizeof(so_errno);
- if ( getsockopt( s, SOL_SOCKET, SO_ERROR, &so_errno, &dummy ) == -1 ) {
+ if ( getsockopt( s, SOL_SOCKET, SO_ERROR, &so_errno, &dummy )
+ == AC_SOCKET_ERROR )
+ {
return -1;
}
if ( so_errno ) {
struct sockaddr_un sa;
char ch;
int dummy = sizeof(sa);
- if ( getpeername( s, (struct sockaddr *) &sa, &dummy ) == -1 ) {
+ if ( getpeername( s, (struct sockaddr *) &sa, &dummy )
+ == AC_SOCKET_ERROR )
+ {
/* XXX: needs to be replace with ber_stream_read() */
read(s, &ch, 1);
TRACE;
if ( ldap_pvt_ndelay_on(ld, s) == -1 )
return ( -1 );
- if ( connect(s, (struct sockaddr *) sa, sizeof(struct sockaddr_un)) == 0 )
+ if ( connect(s, (struct sockaddr *) sa, sizeof(struct sockaddr_un))
+ != AC_SOCKET_ERROR )
{
- if ( ldap_pvt_ndelay_off(ld, s) == -1 )
+ if ( ldap_pvt_ndelay_off(ld, s) == -1 ) {
return ( -1 );
+ }
return ( 0 );
}
FD_ZERO(&wfds);
FD_SET(s, &wfds );
- if ( select(ldap_int_tblsize, z, &wfds, z, opt_tv ? &tv : NULL) == -1)
+ if ( select(ldap_int_tblsize, z, &wfds, z, opt_tv ? &tv : NULL)
+ == AC_SOCKET_ERROR )
+ {
return ( -1 );
+ }
if ( FD_ISSET(s, &wfds) ) {
if ( ldap_pvt_is_socket_ready(ld, s) == -1 )
ldap_connect_to_path(LDAP *ld, Sockbuf *sb, const char *path, int async)
{
struct sockaddr_un server;
- ber_socket_t s = AC_SOCKET_INVALID;
+ ber_socket_t s;
int rc;
oslocal_debug(ld, "ldap_connect_to_path\n",0,0,0);
- if ( (s = ldap_pvt_socket( ld )) == -1 ) {
+ s = ldap_pvt_socket( ld );
+ if ( s == AC_SOCKET_INVALID ) {
return -1;
}
for ( lc = ld->ld_conns; lc != NULL; lc = lc->lconn_next ) {
for ( ls = srv; ls != NULL; ls = ls->lud_next ) {
if ( lc->lconn_server->lud_host != NULL &&
- ls->lud_host != NULL && strcasecmp(
- ls->lud_host, lc->lconn_server->lud_host ) == 0
+ *lc->lconn_server->lud_host != '\0' &&
+ ls->lud_host != NULL && *ls->lud_host != '\0' &&
+ strcasecmp( ls->lud_host, lc->lconn_server->lud_host ) == 0
&& ls->lud_port == lc->lconn_server->lud_port ) {
- return( lc );
+ return lc;
}
if ( !any ) {
break;
}
}
- return( NULL );
+ return NULL;
}
goto done;
}
+ if( srv->lud_crit_exts ) {
+ /* we do not support any extensions */
+ ld->ld_errno = LDAP_NOT_SUPPORTED;
+ rc = -1;
+ goto done;
+ }
+
/* treat ldap://hostpart and ldap://hostpart/ the same */
if ( srv->lud_dn && srv->lud_dn[0] == '\0' ) {
LDAP_FREE( srv->lud_dn );
* with msgid. If all is LDAP_MSG_ONE (0) the first message with id
* msgid will be accepted, otherwise, ldap_result will wait for all
* responses with id msgid and then return a pointer to the entire list
- * of messages. This is only useful for search responses, which can be
- * of two message types (zero or more entries, followed by an
- * ldap result). The type of the first message received is returned.
+ * of messages. In general, this is only useful for search responses,
+ * which can be of three message types (zero or more entries, zero or
+ * search references, followed by an ldap result). An extension to
+ * LDAPv3 allows partial extended responses to be returned in response
+ * to any request. The type of the first message received is returned.
* When waiting, any messages that have been abandoned are discarded.
*
* Example:
}
static LDAPMessage *
-chkResponseList( LDAP *ld,
- int msgid,
- int all)
+chkResponseList(
+ LDAP *ld,
+ int msgid,
+ int all)
{
LDAPMessage *lm, *lastlm, *nextlm;
/*
* wait until it arrives or timeout occurs.
*/
- Debug( LDAP_DEBUG_TRACE, "chkResponseList for msgid %d, all %d\n",
+ Debug( LDAP_DEBUG_TRACE,
+ "ldap_chkResponseList for msgid=%d, all=%d\n",
msgid, all, 0 );
lastlm = NULL;
for ( lm = ld->ld_responses; lm != NULL; lm = nextlm ) {
nextlm = lm->lm_next;
if ( ldap_abandoned( ld, lm->lm_msgid ) ) {
- Debug( LDAP_DEBUG_TRACE, "chkResponseList msg abandoned, msgid %d\n",
+ Debug( LDAP_DEBUG_TRACE,
+ "ldap_chkResponseList msg abandoned, msgid %d\n",
msgid, 0, 0 );
ldap_mark_abandoned( ld, lm->lm_msgid );
if ( msgid == LDAP_RES_ANY || lm->lm_msgid == msgid ) {
LDAPMessage *tmp;
- if ( all == LDAP_MSG_ONE
- || (lm->lm_msgtype != LDAP_RES_SEARCH_RESULT
- && lm->lm_msgtype != LDAP_RES_SEARCH_REFERENCE /* LDAPv3 */
- && lm->lm_msgtype != LDAP_RES_SEARCH_ENTRY
- && lm->lm_msgtype != LDAP_RES_EXTENDED_PARTIAL) )
+ if ( all == LDAP_MSG_ONE || msgid == LDAP_RES_UNSOLICITED ) {
break;
+ }
for ( tmp = lm; tmp != NULL; tmp = tmp->lm_chain ) {
- if ( tmp->lm_msgtype == LDAP_RES_SEARCH_RESULT )
+ if ( lm->lm_msgtype != LDAP_RES_SEARCH_ENTRY
+ && lm->lm_msgtype != LDAP_RES_SEARCH_REFERENCE
+ && lm->lm_msgtype != LDAP_RES_EXTENDED_PARTIAL )
+ {
break;
+ }
}
if ( tmp == NULL ) {
}
lastlm = lm;
}
+
if ( lm != NULL ) {
/* Found an entry, remove it from the list */
if ( lastlm == NULL ) {
lastlm->lm_next = (all == LDAP_MSG_ONE && lm->lm_chain != NULL
? lm->lm_chain : lm->lm_next);
}
- if ( all == LDAP_MSG_ONE && lm->lm_chain != NULL )
- {
+ if ( all == LDAP_MSG_ONE && lm->lm_chain != NULL ) {
lm->lm_chain->lm_next = lm->lm_next;
lm->lm_chain = NULL;
}
#ifdef LDAP_DEBUG
if( lm == NULL) {
- Debug( LDAP_DEBUG_TRACE, "chkResponseList returns NULL\n", 0, 0, 0);
+ Debug( LDAP_DEBUG_TRACE,
+ "ldap_chkResponseList returns NULL\n", 0, 0, 0);
} else {
- Debug( LDAP_DEBUG_TRACE, "chkResponseList returns msgid %d, type %lu\n",
- lm->lm_msgid, (unsigned long) lm->lm_msgtype, 0);
+ Debug( LDAP_DEBUG_TRACE,
+ "ldap_chkResponseList returns msgid %d, type 0x%02lu\n",
+ lm->lm_msgid, (unsigned long) lm->lm_msgtype, 0);
}
#endif
return lm;
Debug( LDAP_DEBUG_TRACE, "ldap_search_ext\n", 0, 0, 0 );
+ assert( ld != NULL );
+ assert( LDAP_VALID( ld ) );
+
/*
* if timeout is provided, both tv_sec and tv_usec must
* be non-zero
Debug( LDAP_DEBUG_TRACE, "ldap_search\n", 0, 0, 0 );
+ assert( ld != NULL );
+ assert( LDAP_VALID( ld ) );
+
ber = ldap_build_search_req( ld, base, scope, filter, attrs,
attrsonly, NULL, NULL, -1, -1 );
if( dn == NULL ) {
if(! ldap_is_attr_desc( str ) ) goto done;
- break;
- }
+ } else {
- *dn++ = '\0';
- rule = strchr( dn, ':' );
+ *dn++ = '\0';
+ rule = strchr( dn, ':' );
- if( rule == NULL ) {
- /* one colon */
- if ( strcmp(dn, "dn") == 0 ) {
- /* must have attribute */
- if( !ldap_is_attr_desc( str ) ) {
- goto done;
- }
+ if( rule == NULL ) {
+ /* one colon */
+ if ( strcmp(dn, "dn") == 0 ) {
+ /* must have attribute */
+ if( !ldap_is_attr_desc( str ) ) {
+ goto done;
+ }
- rule = "";
+ rule = "";
- } else {
- rule = dn;
- dn = NULL;
- }
+ } else {
+ rule = dn;
+ dn = NULL;
+ }
- } else {
- /* two colons */
- *rule++ = '\0';
+ } else {
+ /* two colons */
+ *rule++ = '\0';
- if ( strcmp(dn, "dn") != 0 ) {
- /* must have "dn" */
- goto done;
+ if ( strcmp(dn, "dn") != 0 ) {
+ /* must have "dn" */
+ goto done;
+ }
}
+
}
- if ( *str == '\0' && *rule == '\0' ) {
+ if ( *str == '\0' && ( !rule || *rule == '\0' ) ) {
/* must have either type or rule */
goto done;
}
goto done;
}
- if ( *rule != '\0' && !ldap_is_attr_oid( rule ) ) {
+ if ( rule && *rule != '\0' && !ldap_is_attr_oid( rule ) ) {
goto done;
}
rc = ber_printf( ber, "t{" /*}*/, ftype );
- if( rc != -1 && *rule != '\0' ) {
+ if( rc != -1 && rule && *rule != '\0' ) {
rc = ber_printf( ber, "ts", LDAP_FILTER_EXT_OID, rule );
}
if( rc != -1 && *str != '\0' ) {
}
}
}
- break;
+ goto done;
default:
if ( ldap_pvt_find_wildcard( value ) == NULL ) {
ludp->lud_filter = NULL;
ludp->lud_scope = LDAP_SCOPE_BASE;
ludp->lud_filter = NULL;
+ ludp->lud_exts = NULL;
ludp->lud_scheme = LDAP_STRDUP( scheme );
for( i=0; ludp->lud_exts[i] != NULL; i++ ) {
ldap_pvt_hex_unescape( ludp->lud_exts[i] );
+
+ if( *ludp->lud_exts[i] == '!' ) {
+ /* count the number of critical extensions */
+ ludp->lud_crit_exts++;
+ }
}
if( i == 0 ) {
BerElement *ber;
LDAPreqinfo bind;
+ assert( ld != NULL );
+ assert( LDAP_VALID( ld ) );
+
if ( ldap_url_parse( url, &ludp ) != 0 ) {
ld->ld_errno = LDAP_PARAM_ERROR;
return( -1 );
}
+ if( ludp->lud_crit_exts ) {
+ /* we don't support any extension (yet) */
+ ld->ld_errno = LDAP_NOT_SUPPORTED;
+ return( -1 );
+ }
+
ber = ldap_build_search_req( ld, ludp->lud_dn, ludp->lud_scope,
ludp->lud_filter, ludp->lud_attrs, attrsonly, NULL, NULL,
-1, -1 );