1*f95714a4Smartijn /* $Id: aldap.h,v 1.1 2020/09/12 15:06:12 martijn Exp $ */ 2*f95714a4Smartijn /* $OpenBSD: aldap.h,v 1.1 2020/09/12 15:06:12 martijn Exp $ */ 3*f95714a4Smartijn 4*f95714a4Smartijn /* 5*f95714a4Smartijn * Copyright (c) 2008 Alexander Schrijver <aschrijver@openbsd.org> 6*f95714a4Smartijn * Copyright (c) 2006, 2007 Marc Balmer <mbalmer@openbsd.org> 7*f95714a4Smartijn * 8*f95714a4Smartijn * Permission to use, copy, modify, and distribute this software for any 9*f95714a4Smartijn * purpose with or without fee is hereby granted, provided that the above 10*f95714a4Smartijn * copyright notice and this permission notice appear in all copies. 11*f95714a4Smartijn * 12*f95714a4Smartijn * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 13*f95714a4Smartijn * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 14*f95714a4Smartijn * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 15*f95714a4Smartijn * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 16*f95714a4Smartijn * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 17*f95714a4Smartijn * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 18*f95714a4Smartijn * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 19*f95714a4Smartijn */ 20*f95714a4Smartijn 21*f95714a4Smartijn #include <stdio.h> 22*f95714a4Smartijn 23*f95714a4Smartijn #include <ber.h> 24*f95714a4Smartijn #include <tls.h> 25*f95714a4Smartijn 26*f95714a4Smartijn #define LDAP_URL "ldap://" 27*f95714a4Smartijn #define LDAPS_URL "ldaps://" 28*f95714a4Smartijn #define LDAPTLS_URL "ldap+tls://" 29*f95714a4Smartijn #define LDAPI_URL "ldapi://" 30*f95714a4Smartijn 31*f95714a4Smartijn #define LDAP_PORT 389 32*f95714a4Smartijn #define LDAPS_PORT 636 33*f95714a4Smartijn #define LDAP_PAGED_OID "1.2.840.113556.1.4.319" 34*f95714a4Smartijn #define LDAP_STARTTLS_OID "1.3.6.1.4.1.1466.20037" 35*f95714a4Smartijn 36*f95714a4Smartijn struct aldap { 37*f95714a4Smartijn #define ALDAP_ERR_SUCCESS 0 38*f95714a4Smartijn #define ALDAP_ERR_PARSER_ERROR 1 39*f95714a4Smartijn #define ALDAP_ERR_INVALID_FILTER 2 40*f95714a4Smartijn #define ALDAP_ERR_OPERATION_FAILED 3 41*f95714a4Smartijn #define ALDAP_ERR_TLS_ERROR 4 42*f95714a4Smartijn u_int8_t err; 43*f95714a4Smartijn int msgid; 44*f95714a4Smartijn struct ber ber; 45*f95714a4Smartijn 46*f95714a4Smartijn int fd; 47*f95714a4Smartijn struct tls *tls; 48*f95714a4Smartijn 49*f95714a4Smartijn struct evbuffer *buf; 50*f95714a4Smartijn }; 51*f95714a4Smartijn 52*f95714a4Smartijn struct aldap_page_control { 53*f95714a4Smartijn int size; 54*f95714a4Smartijn char *cookie; 55*f95714a4Smartijn unsigned int cookie_len; 56*f95714a4Smartijn }; 57*f95714a4Smartijn 58*f95714a4Smartijn struct aldap_message { 59*f95714a4Smartijn int msgid; 60*f95714a4Smartijn int message_type; 61*f95714a4Smartijn 62*f95714a4Smartijn struct ber_element *msg; 63*f95714a4Smartijn 64*f95714a4Smartijn struct ber_element *header; 65*f95714a4Smartijn struct ber_element *protocol_op; 66*f95714a4Smartijn 67*f95714a4Smartijn struct ber_element *dn; 68*f95714a4Smartijn 69*f95714a4Smartijn union { 70*f95714a4Smartijn struct { 71*f95714a4Smartijn long long rescode; 72*f95714a4Smartijn struct ber_element *diagmsg; 73*f95714a4Smartijn } res; 74*f95714a4Smartijn struct { 75*f95714a4Smartijn struct ber_element *iter; 76*f95714a4Smartijn struct ber_element *attrs; 77*f95714a4Smartijn } search; 78*f95714a4Smartijn } body; 79*f95714a4Smartijn struct ber_element *references; 80*f95714a4Smartijn struct aldap_page_control *page; 81*f95714a4Smartijn }; 82*f95714a4Smartijn 83*f95714a4Smartijn enum aldap_protocol { 84*f95714a4Smartijn LDAP, 85*f95714a4Smartijn LDAPS, 86*f95714a4Smartijn LDAPTLS, 87*f95714a4Smartijn LDAPI 88*f95714a4Smartijn }; 89*f95714a4Smartijn 90*f95714a4Smartijn struct aldap_stringset { 91*f95714a4Smartijn size_t len; 92*f95714a4Smartijn struct ber_octetstring *str; 93*f95714a4Smartijn }; 94*f95714a4Smartijn 95*f95714a4Smartijn struct aldap_url { 96*f95714a4Smartijn int protocol; 97*f95714a4Smartijn char *host; 98*f95714a4Smartijn in_port_t port; 99*f95714a4Smartijn char *dn; 100*f95714a4Smartijn #define MAXATTR 1024 101*f95714a4Smartijn char *attributes[MAXATTR]; 102*f95714a4Smartijn int scope; 103*f95714a4Smartijn char *filter; 104*f95714a4Smartijn char *buffer; 105*f95714a4Smartijn }; 106*f95714a4Smartijn 107*f95714a4Smartijn enum protocol_op { 108*f95714a4Smartijn LDAP_REQ_BIND = 0, 109*f95714a4Smartijn LDAP_RES_BIND = 1, 110*f95714a4Smartijn LDAP_REQ_UNBIND_30 = 2, 111*f95714a4Smartijn LDAP_REQ_SEARCH = 3, 112*f95714a4Smartijn LDAP_RES_SEARCH_ENTRY = 4, 113*f95714a4Smartijn LDAP_RES_SEARCH_RESULT = 5, 114*f95714a4Smartijn LDAP_REQ_MODIFY = 6, 115*f95714a4Smartijn LDAP_RES_MODIFY = 7, 116*f95714a4Smartijn LDAP_REQ_ADD = 8, 117*f95714a4Smartijn LDAP_RES_ADD = 9, 118*f95714a4Smartijn LDAP_REQ_DELETE_30 = 10, 119*f95714a4Smartijn LDAP_RES_DELETE = 11, 120*f95714a4Smartijn LDAP_REQ_MODRDN = 12, 121*f95714a4Smartijn LDAP_RES_MODRDN = 13, 122*f95714a4Smartijn LDAP_REQ_COMPARE = 14, 123*f95714a4Smartijn LDAP_RES_COMPARE = 15, 124*f95714a4Smartijn LDAP_REQ_ABANDON_30 = 16, 125*f95714a4Smartijn 126*f95714a4Smartijn LDAP_RES_SEARCH_REFERENCE = 19, 127*f95714a4Smartijn 128*f95714a4Smartijn LDAP_REQ_EXTENDED = 23, 129*f95714a4Smartijn LDAP_RES_EXTENDED = 24 130*f95714a4Smartijn }; 131*f95714a4Smartijn 132*f95714a4Smartijn enum deref_aliases { 133*f95714a4Smartijn LDAP_DEREF_NEVER = 0, 134*f95714a4Smartijn LDAP_DEREF_SEARCHING = 1, 135*f95714a4Smartijn LDAP_DEREF_FINDING = 2, 136*f95714a4Smartijn LDAP_DEREF_ALWAYS = 3, 137*f95714a4Smartijn }; 138*f95714a4Smartijn 139*f95714a4Smartijn enum authentication_choice { 140*f95714a4Smartijn LDAP_AUTH_SIMPLE = 0, 141*f95714a4Smartijn }; 142*f95714a4Smartijn 143*f95714a4Smartijn enum scope { 144*f95714a4Smartijn LDAP_SCOPE_BASE = 0, 145*f95714a4Smartijn LDAP_SCOPE_ONELEVEL = 1, 146*f95714a4Smartijn LDAP_SCOPE_SUBTREE = 2, 147*f95714a4Smartijn }; 148*f95714a4Smartijn 149*f95714a4Smartijn enum result_code { 150*f95714a4Smartijn LDAP_SUCCESS = 0, 151*f95714a4Smartijn LDAP_OPERATIONS_ERROR = 1, 152*f95714a4Smartijn LDAP_PROTOCOL_ERROR = 2, 153*f95714a4Smartijn LDAP_TIMELIMIT_EXCEEDED = 3, 154*f95714a4Smartijn LDAP_SIZELIMIT_EXCEEDED = 4, 155*f95714a4Smartijn LDAP_COMPARE_FALSE = 5, 156*f95714a4Smartijn LDAP_COMPARE_TRUE = 6, 157*f95714a4Smartijn LDAP_STRONG_AUTH_NOT_SUPPORTED = 7, 158*f95714a4Smartijn LDAP_STRONG_AUTH_REQUIRED = 8, 159*f95714a4Smartijn 160*f95714a4Smartijn LDAP_REFERRAL = 10, 161*f95714a4Smartijn LDAP_ADMINLIMIT_EXCEEDED = 11, 162*f95714a4Smartijn LDAP_UNAVAILABLE_CRITICAL_EXTENSION = 12, 163*f95714a4Smartijn LDAP_CONFIDENTIALITY_REQUIRED = 13, 164*f95714a4Smartijn LDAP_SASL_BIND_IN_PROGRESS = 14, 165*f95714a4Smartijn LDAP_NO_SUCH_ATTRIBUTE = 16, 166*f95714a4Smartijn LDAP_UNDEFINED_TYPE = 17, 167*f95714a4Smartijn LDAP_INAPPROPRIATE_MATCHING = 18, 168*f95714a4Smartijn LDAP_CONSTRAINT_VIOLATION = 19, 169*f95714a4Smartijn LDAP_TYPE_OR_VALUE_EXISTS = 20, 170*f95714a4Smartijn LDAP_INVALID_SYNTAX = 21, 171*f95714a4Smartijn 172*f95714a4Smartijn LDAP_NO_SUCH_OBJECT = 32, 173*f95714a4Smartijn LDAP_ALIAS_PROBLEM = 33, 174*f95714a4Smartijn LDAP_INVALID_DN_SYNTAX = 34, 175*f95714a4Smartijn 176*f95714a4Smartijn LDAP_ALIAS_DEREF_PROBLEM = 36, 177*f95714a4Smartijn 178*f95714a4Smartijn LDAP_INAPPROPRIATE_AUTH = 48, 179*f95714a4Smartijn LDAP_INVALID_CREDENTIALS = 49, 180*f95714a4Smartijn LDAP_INSUFFICIENT_ACCESS = 50, 181*f95714a4Smartijn LDAP_BUSY = 51, 182*f95714a4Smartijn LDAP_UNAVAILABLE = 52, 183*f95714a4Smartijn LDAP_UNWILLING_TO_PERFORM = 53, 184*f95714a4Smartijn LDAP_LOOP_DETECT = 54, 185*f95714a4Smartijn 186*f95714a4Smartijn LDAP_NAMING_VIOLATION = 64, 187*f95714a4Smartijn LDAP_OBJECT_CLASS_VIOLATION = 65, 188*f95714a4Smartijn LDAP_NOT_ALLOWED_ON_NONLEAF = 66, 189*f95714a4Smartijn LDAP_NOT_ALLOWED_ON_RDN = 67, 190*f95714a4Smartijn LDAP_ALREADY_EXISTS = 68, 191*f95714a4Smartijn LDAP_NO_OBJECT_CLASS_MODS = 69, 192*f95714a4Smartijn 193*f95714a4Smartijn LDAP_AFFECTS_MULTIPLE_DSAS = 71, 194*f95714a4Smartijn 195*f95714a4Smartijn LDAP_OTHER = 80, 196*f95714a4Smartijn }; 197*f95714a4Smartijn 198*f95714a4Smartijn enum filter { 199*f95714a4Smartijn LDAP_FILT_AND = 0, 200*f95714a4Smartijn LDAP_FILT_OR = 1, 201*f95714a4Smartijn LDAP_FILT_NOT = 2, 202*f95714a4Smartijn LDAP_FILT_EQ = 3, 203*f95714a4Smartijn LDAP_FILT_SUBS = 4, 204*f95714a4Smartijn LDAP_FILT_GE = 5, 205*f95714a4Smartijn LDAP_FILT_LE = 6, 206*f95714a4Smartijn LDAP_FILT_PRES = 7, 207*f95714a4Smartijn LDAP_FILT_APPR = 8, 208*f95714a4Smartijn }; 209*f95714a4Smartijn 210*f95714a4Smartijn enum subfilter { 211*f95714a4Smartijn LDAP_FILT_SUBS_INIT = 0, 212*f95714a4Smartijn LDAP_FILT_SUBS_ANY = 1, 213*f95714a4Smartijn LDAP_FILT_SUBS_FIN = 2, 214*f95714a4Smartijn }; 215*f95714a4Smartijn 216*f95714a4Smartijn struct aldap *aldap_init(int); 217*f95714a4Smartijn int aldap_tls(struct aldap *, struct tls_config *, 218*f95714a4Smartijn const char *); 219*f95714a4Smartijn int aldap_close(struct aldap *); 220*f95714a4Smartijn struct aldap_message *aldap_parse(struct aldap *); 221*f95714a4Smartijn void aldap_freemsg(struct aldap_message *); 222*f95714a4Smartijn 223*f95714a4Smartijn int aldap_req_starttls(struct aldap *); 224*f95714a4Smartijn 225*f95714a4Smartijn int aldap_bind(struct aldap *, char *, char *); 226*f95714a4Smartijn int aldap_unbind(struct aldap *); 227*f95714a4Smartijn int aldap_search(struct aldap *, char *, enum scope, char *, char **, int, int, int, struct aldap_page_control *); 228*f95714a4Smartijn int aldap_get_errno(struct aldap *, const char **); 229*f95714a4Smartijn 230*f95714a4Smartijn int aldap_get_resultcode(struct aldap_message *); 231*f95714a4Smartijn char *aldap_get_dn(struct aldap_message *); 232*f95714a4Smartijn char *aldap_get_diagmsg(struct aldap_message *); 233*f95714a4Smartijn struct aldap_stringset *aldap_get_references(struct aldap_message *); 234*f95714a4Smartijn void aldap_free_references(char **values); 235*f95714a4Smartijn int aldap_parse_url(const char *, struct aldap_url *); 236*f95714a4Smartijn void aldap_free_url(struct aldap_url *); 237*f95714a4Smartijn int aldap_search_url(struct aldap *, char *, int, int, int, 238*f95714a4Smartijn struct aldap_page_control *); 239*f95714a4Smartijn 240*f95714a4Smartijn int aldap_count_attrs(struct aldap_message *); 241*f95714a4Smartijn int aldap_match_attr(struct aldap_message *, char *, 242*f95714a4Smartijn struct aldap_stringset **); 243*f95714a4Smartijn int aldap_first_attr(struct aldap_message *, char **, struct 244*f95714a4Smartijn aldap_stringset **); 245*f95714a4Smartijn int aldap_next_attr(struct aldap_message *, char **, 246*f95714a4Smartijn struct aldap_stringset **); 247*f95714a4Smartijn int aldap_free_attr(struct aldap_stringset *); 248*f95714a4Smartijn 249*f95714a4Smartijn struct aldap_page_control *aldap_parse_page_control(struct ber_element *, size_t len); 250*f95714a4Smartijn void aldap_freepage(struct aldap_page_control *); 251