1"""Definitions for constants exported by OpenLDAP 2 3This file lists all constants we know about, even those that aren't 4available in the OpenLDAP version python-ldap is compiled against. 5 6The information serves two purposes: 7 8- Generate a C header with the constants 9- Provide support for building documentation without compiling python-ldap 10 11""" 12 13# This module cannot import anything from ldap. 14# When building documentation, it is used to initialize ldap.__init__. 15 16 17class Constant: 18 """Base class for a definition of an OpenLDAP constant 19 """ 20 21 def __init__(self, name, optional=False, requirements=(), doc=None): 22 self.name = name 23 if optional: 24 self_requirement = f'defined(LDAP_{self.name})' 25 requirements = list(requirements) + [self_requirement] 26 self.requirements = requirements 27 self.doc = self.__doc__ = doc 28 29 30class Error(Constant): 31 """Definition for an OpenLDAP error code 32 33 This is a constant at the C level; in Python errors are provided as 34 exception classes. 35 """ 36 37 c_template = 'add_err({self.name});' 38 39 40class Int(Constant): 41 """Definition for an OpenLDAP integer constant""" 42 43 c_template = 'add_int({self.name});' 44 45 46class TLSInt(Int): 47 """Definition for a TLS integer constant -- requires HAVE_TLS""" 48 49 def __init__(self, *args, **kwargs): 50 requrements = list(kwargs.get('requirements', ())) 51 kwargs['requirements'] = ['HAVE_TLS'] + requrements 52 super().__init__(*args, **kwargs) 53 54 55class Feature(Constant): 56 """Definition for a feature: 0 or 1 based on a C #ifdef 57 58 """ 59 60 c_template = '\n'.join([ 61 '', 62 '#ifdef {self.c_feature}', 63 'if (PyModule_AddIntConstant(m, "{self.name}", 1) != 0) return -1;', 64 '#else', 65 'if (PyModule_AddIntConstant(m, "{self.name}", 0) != 0) return -1;', 66 '#endif', 67 '', 68 ]) 69 70 71 def __init__(self, name, c_feature, **kwargs): 72 super().__init__(name, **kwargs) 73 self.c_feature = c_feature 74 75 76class Str(Constant): 77 c_template = 'add_string({self.name});' 78 79 80API_2004 = 'LDAP_API_VERSION >= 2004' 81 82CONSTANTS = ( 83 Error('ADMINLIMIT_EXCEEDED'), 84 Error('AFFECTS_MULTIPLE_DSAS'), 85 Error('ALIAS_DEREF_PROBLEM'), 86 Error('ALIAS_PROBLEM'), 87 Error('ALREADY_EXISTS'), 88 Error('AUTH_METHOD_NOT_SUPPORTED'), 89 Error('AUTH_UNKNOWN'), 90 Error('BUSY'), 91 Error('CLIENT_LOOP'), 92 Error('COMPARE_FALSE'), 93 Error('COMPARE_TRUE'), 94 Error('CONFIDENTIALITY_REQUIRED'), 95 Error('CONNECT_ERROR'), 96 Error('CONSTRAINT_VIOLATION'), 97 Error('CONTROL_NOT_FOUND'), 98 Error('DECODING_ERROR'), 99 Error('ENCODING_ERROR'), 100 Error('FILTER_ERROR'), 101 Error('INAPPROPRIATE_AUTH'), 102 Error('INAPPROPRIATE_MATCHING'), 103 Error('INSUFFICIENT_ACCESS'), 104 Error('INVALID_CREDENTIALS'), 105 Error('INVALID_DN_SYNTAX'), 106 Error('INVALID_SYNTAX'), 107 Error('IS_LEAF'), 108 Error('LOCAL_ERROR'), 109 Error('LOOP_DETECT'), 110 Error('MORE_RESULTS_TO_RETURN'), 111 Error('NAMING_VIOLATION'), 112 Error('NO_MEMORY'), 113 Error('NO_OBJECT_CLASS_MODS'), 114 Error('NO_OBJECT_CLASS_MODS'), 115 Error('NO_RESULTS_RETURNED'), 116 Error('NO_SUCH_ATTRIBUTE'), 117 Error('NO_SUCH_OBJECT'), 118 Error('NOT_ALLOWED_ON_NONLEAF'), 119 Error('NOT_ALLOWED_ON_RDN'), 120 Error('NOT_SUPPORTED'), 121 Error('OBJECT_CLASS_VIOLATION'), 122 Error('OPERATIONS_ERROR'), 123 Error('OTHER'), 124 Error('PARAM_ERROR'), 125 Error('PARTIAL_RESULTS'), 126 Error('PROTOCOL_ERROR'), 127 Error('REFERRAL'), 128 Error('REFERRAL_LIMIT_EXCEEDED'), 129 Error('RESULTS_TOO_LARGE'), 130 Error('SASL_BIND_IN_PROGRESS'), 131 Error('SERVER_DOWN'), 132 Error('SIZELIMIT_EXCEEDED'), 133 Error('STRONG_AUTH_NOT_SUPPORTED'), 134 Error('STRONG_AUTH_REQUIRED'), 135 Error('SUCCESS'), 136 Error('TIMELIMIT_EXCEEDED'), 137 Error('TIMEOUT'), 138 Error('TYPE_OR_VALUE_EXISTS'), 139 Error('UNAVAILABLE'), 140 Error('UNAVAILABLE_CRITICAL_EXTENSION'), 141 Error('UNDEFINED_TYPE'), 142 Error('UNWILLING_TO_PERFORM'), 143 Error('USER_CANCELLED'), 144 Error('VLV_ERROR'), 145 Error('X_PROXY_AUTHZ_FAILURE'), 146 147 Error('CANCELLED', requirements=['defined(LDAP_API_FEATURE_CANCEL)']), 148 Error('NO_SUCH_OPERATION', requirements=['defined(LDAP_API_FEATURE_CANCEL)']), 149 Error('TOO_LATE', requirements=['defined(LDAP_API_FEATURE_CANCEL)']), 150 Error('CANNOT_CANCEL', requirements=['defined(LDAP_API_FEATURE_CANCEL)']), 151 152 Error('ASSERTION_FAILED', optional=True), 153 154 Error('PROXIED_AUTHORIZATION_DENIED', optional=True), 155 156 # simple constants 157 158 Int('API_VERSION'), 159 Int('VENDOR_VERSION'), 160 161 Int('PORT'), 162 Int('VERSION1'), 163 Int('VERSION2'), 164 Int('VERSION3'), 165 Int('VERSION_MIN'), 166 Int('VERSION'), 167 Int('VERSION_MAX'), 168 Int('TAG_MESSAGE'), 169 Int('TAG_MSGID'), 170 171 Int('REQ_BIND'), 172 Int('REQ_UNBIND'), 173 Int('REQ_SEARCH'), 174 Int('REQ_MODIFY'), 175 Int('REQ_ADD'), 176 Int('REQ_DELETE'), 177 Int('REQ_MODRDN'), 178 Int('REQ_COMPARE'), 179 Int('REQ_ABANDON'), 180 181 Int('TAG_LDAPDN'), 182 Int('TAG_LDAPCRED'), 183 Int('TAG_CONTROLS'), 184 Int('TAG_REFERRAL'), 185 186 Int('REQ_EXTENDED'), 187 Int('TAG_NEWSUPERIOR', requirements=[API_2004]), 188 Int('TAG_EXOP_REQ_OID', requirements=[API_2004]), 189 Int('TAG_EXOP_REQ_VALUE', requirements=[API_2004]), 190 Int('TAG_EXOP_RES_OID', requirements=[API_2004]), 191 Int('TAG_EXOP_RES_VALUE', requirements=[API_2004]), 192 Int('TAG_SASL_RES_CREDS', requirements=[API_2004, 'defined(HAVE_SASL)']), 193 194 Int('SASL_AUTOMATIC'), 195 Int('SASL_INTERACTIVE'), 196 Int('SASL_QUIET'), 197 198 # reversibles 199 200 Int('RES_BIND'), 201 Int('RES_SEARCH_ENTRY'), 202 Int('RES_SEARCH_RESULT'), 203 Int('RES_MODIFY'), 204 Int('RES_ADD'), 205 Int('RES_DELETE'), 206 Int('RES_MODRDN'), 207 Int('RES_COMPARE'), 208 Int('RES_ANY'), 209 210 Int('RES_SEARCH_REFERENCE'), 211 Int('RES_EXTENDED'), 212 Int('RES_UNSOLICITED'), 213 214 Int('RES_INTERMEDIATE'), 215 216 # non-reversibles 217 218 Int('AUTH_NONE'), 219 Int('AUTH_SIMPLE'), 220 Int('SCOPE_BASE'), 221 Int('SCOPE_ONELEVEL'), 222 Int('SCOPE_SUBTREE'), 223 Int('SCOPE_SUBORDINATE', optional=True), 224 Int('MOD_ADD'), 225 Int('MOD_DELETE'), 226 Int('MOD_REPLACE'), 227 Int('MOD_INCREMENT'), 228 Int('MOD_BVALUES'), 229 230 Int('MSG_ONE'), 231 Int('MSG_ALL'), 232 Int('MSG_RECEIVED'), 233 234 # (error constants handled above) 235 236 Int('DEREF_NEVER'), 237 Int('DEREF_SEARCHING'), 238 Int('DEREF_FINDING'), 239 Int('DEREF_ALWAYS'), 240 Int('NO_LIMIT'), 241 242 Int('OPT_API_INFO'), 243 Int('OPT_DEREF'), 244 Int('OPT_SIZELIMIT'), 245 Int('OPT_TIMELIMIT'), 246 Int('OPT_REFERRALS', optional=True), 247 Int('OPT_ERROR_NUMBER'), 248 Int('OPT_RESTART'), 249 Int('OPT_PROTOCOL_VERSION'), 250 Int('OPT_SERVER_CONTROLS'), 251 Int('OPT_CLIENT_CONTROLS'), 252 Int('OPT_API_FEATURE_INFO'), 253 Int('OPT_HOST_NAME'), 254 255 Int('OPT_DESC'), 256 Int('OPT_DIAGNOSTIC_MESSAGE'), 257 258 Int('OPT_ERROR_STRING'), 259 Int('OPT_MATCHED_DN'), 260 Int('OPT_DEBUG_LEVEL'), 261 Int('OPT_TIMEOUT'), 262 Int('OPT_REFHOPLIMIT'), 263 Int('OPT_NETWORK_TIMEOUT'), 264 Int('OPT_URI'), 265 266 Int('OPT_DEFBASE', optional=True), 267 268 TLSInt('OPT_X_TLS', optional=True), 269 TLSInt('OPT_X_TLS_CTX'), 270 TLSInt('OPT_X_TLS_CACERTFILE'), 271 TLSInt('OPT_X_TLS_CACERTDIR'), 272 TLSInt('OPT_X_TLS_CERTFILE'), 273 TLSInt('OPT_X_TLS_KEYFILE'), 274 TLSInt('OPT_X_TLS_REQUIRE_CERT'), 275 TLSInt('OPT_X_TLS_CIPHER_SUITE'), 276 TLSInt('OPT_X_TLS_RANDOM_FILE'), 277 TLSInt('OPT_X_TLS_DHFILE'), 278 TLSInt('OPT_X_TLS_NEVER'), 279 TLSInt('OPT_X_TLS_HARD'), 280 TLSInt('OPT_X_TLS_DEMAND'), 281 TLSInt('OPT_X_TLS_ALLOW'), 282 TLSInt('OPT_X_TLS_TRY'), 283 284 TLSInt('OPT_X_TLS_VERSION', optional=True), 285 TLSInt('OPT_X_TLS_CIPHER', optional=True), 286 TLSInt('OPT_X_TLS_PEERCERT', optional=True), 287 288 # only available if OpenSSL supports it => might cause 289 # backward compatibility problems 290 TLSInt('OPT_X_TLS_CRLCHECK', optional=True), 291 292 TLSInt('OPT_X_TLS_CRLFILE', optional=True), 293 294 TLSInt('OPT_X_TLS_CRL_NONE'), 295 TLSInt('OPT_X_TLS_CRL_PEER'), 296 TLSInt('OPT_X_TLS_CRL_ALL'), 297 TLSInt('OPT_X_TLS_NEWCTX', optional=True), 298 TLSInt('OPT_X_TLS_PROTOCOL_MIN', optional=True), 299 TLSInt('OPT_X_TLS_PACKAGE', optional=True), 300 301 # Added in OpenLDAP 2.4.52 302 TLSInt('OPT_X_TLS_REQUIRE_SAN', optional=True), 303 304 Int('OPT_X_SASL_MECH'), 305 Int('OPT_X_SASL_REALM'), 306 Int('OPT_X_SASL_AUTHCID'), 307 Int('OPT_X_SASL_AUTHZID'), 308 Int('OPT_X_SASL_SSF'), 309 Int('OPT_X_SASL_SSF_EXTERNAL'), 310 Int('OPT_X_SASL_SECPROPS'), 311 Int('OPT_X_SASL_SSF_MIN'), 312 Int('OPT_X_SASL_SSF_MAX'), 313 Int('OPT_X_SASL_NOCANON', optional=True), 314 Int('OPT_X_SASL_USERNAME', optional=True), 315 Int('OPT_CONNECT_ASYNC', optional=True), 316 Int('OPT_X_KEEPALIVE_IDLE', optional=True), 317 Int('OPT_X_KEEPALIVE_PROBES', optional=True), 318 Int('OPT_X_KEEPALIVE_INTERVAL', optional=True), 319 320 Int('DN_FORMAT_LDAP'), 321 Int('DN_FORMAT_LDAPV3'), 322 Int('DN_FORMAT_LDAPV2'), 323 Int('DN_FORMAT_DCE'), 324 Int('DN_FORMAT_UFN'), 325 Int('DN_FORMAT_AD_CANONICAL'), 326 # Int('DN_FORMAT_LBER'), # for testing only 327 Int('DN_FORMAT_MASK'), 328 Int('DN_PRETTY'), 329 Int('DN_SKIP'), 330 Int('DN_P_NOLEADTRAILSPACES'), 331 Int('DN_P_NOSPACEAFTERRDN'), 332 Int('DN_PEDANTIC'), 333 334 Int('AVA_NULL'), 335 Int('AVA_STRING'), 336 Int('AVA_BINARY'), 337 Int('AVA_NONPRINTABLE'), 338 339 Int('OPT_SUCCESS'), 340 341 # XXX - these should be errors 342 Int('URL_ERR_BADSCOPE'), 343 Int('URL_ERR_MEM'), 344 # Int('LIBLDAP_R'), 345 346 Feature('LIBLDAP_R', 'HAVE_LIBLDAP_R'), 347 Feature('SASL_AVAIL', 'HAVE_SASL'), 348 Feature('TLS_AVAIL', 'HAVE_TLS'), 349 Feature('INIT_FD_AVAIL', 'HAVE_LDAP_INIT_FD'), 350 351 Str("CONTROL_MANAGEDSAIT"), 352 Str("CONTROL_PROXY_AUTHZ"), 353 Str("CONTROL_SUBENTRIES"), 354 Str("CONTROL_VALUESRETURNFILTER"), 355 Str("CONTROL_ASSERT"), 356 Str("CONTROL_PRE_READ"), 357 Str("CONTROL_POST_READ"), 358 Str("CONTROL_SORTREQUEST"), 359 Str("CONTROL_SORTRESPONSE"), 360 Str("CONTROL_PAGEDRESULTS"), 361 Str("CONTROL_SYNC"), 362 Str("CONTROL_SYNC_STATE"), 363 Str("CONTROL_SYNC_DONE"), 364 Str("SYNC_INFO"), 365 Str("CONTROL_PASSWORDPOLICYREQUEST"), 366 Str("CONTROL_PASSWORDPOLICYRESPONSE"), 367 Str("CONTROL_RELAX"), 368) 369 370 371def print_header(): # pragma: no cover 372 """Print the C header file to standard output""" 373 374 print('/*') 375 print(' * Generated with:') 376 print(' * python Lib/ldap/constants.py > Modules/constants_generated.h') 377 print(' *') 378 print(' * Please do any modifications there, then re-generate this file') 379 print(' */') 380 print('') 381 382 current_requirements = [] 383 384 def pop_requirement(): 385 popped = current_requirements.pop() 386 print('#endif') 387 print() 388 389 for definition in CONSTANTS: 390 while not set(current_requirements).issubset(definition.requirements): 391 pop_requirement() 392 393 for requirement in definition.requirements: 394 if requirement not in current_requirements: 395 current_requirements.append(requirement) 396 print() 397 print(f'#if {requirement}') 398 399 print(definition.c_template.format(self=definition)) 400 401 while current_requirements: 402 pop_requirement() 403 404 405if __name__ == '__main__': 406 print_header() 407