1 /* $OpenLDAP: pkg/ldap/servers/slapd/slapi/slapi_utils.c,v 1.189.2.9 2008/02/11 23:26:50 kurt Exp $ */ 2 /* This work is part of OpenLDAP Software <http://www.openldap.org/>. 3 * 4 * Copyright 2002-2008 The OpenLDAP Foundation. 5 * Portions Copyright 1997,2002-2003 IBM Corporation. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted only as authorized by the OpenLDAP 10 * Public License. 11 * 12 * A copy of this license is available in the file LICENSE in the 13 * top-level directory of the distribution or, alternatively, at 14 * <http://www.OpenLDAP.org/license.html>. 15 */ 16 /* ACKNOWLEDGEMENTS: 17 * This work was initially developed by IBM Corporation for use in 18 * IBM products and subsequently ported to OpenLDAP Software by 19 * Steve Omrani. Additional significant contributors include: 20 * Luke Howard 21 */ 22 23 #include "portable.h" 24 25 #include <ac/string.h> 26 #include <ac/stdarg.h> 27 #include <ac/ctype.h> 28 #include <ac/unistd.h> 29 30 #include <slap.h> 31 #include <slapi.h> 32 33 #include <netdb.h> 34 35 #ifdef LDAP_SLAPI 36 37 /* 38 * server start time (should we use a struct timeval also in slapd? 39 */ 40 static struct timeval base_time; 41 ldap_pvt_thread_mutex_t slapi_hn_mutex; 42 ldap_pvt_thread_mutex_t slapi_time_mutex; 43 44 struct slapi_mutex { 45 ldap_pvt_thread_mutex_t mutex; 46 }; 47 48 struct slapi_condvar { 49 ldap_pvt_thread_cond_t cond; 50 ldap_pvt_thread_mutex_t mutex; 51 }; 52 53 static int checkBVString(const struct berval *bv) 54 { 55 int i; 56 57 for ( i = 0; i < bv->bv_len; i++ ) { 58 if ( bv->bv_val[i] == '\0' ) 59 return 0; 60 } 61 if ( bv->bv_val[i] != '\0' ) 62 return 0; 63 64 return 1; 65 } 66 67 /* 68 * This function converts an array of pointers to berval objects to 69 * an array of berval objects. 70 */ 71 72 int 73 bvptr2obj( 74 struct berval **bvptr, 75 BerVarray *bvobj, 76 unsigned *num ) 77 { 78 int rc = LDAP_SUCCESS; 79 int i; 80 BerVarray tmpberval; 81 82 if ( bvptr == NULL || *bvptr == NULL ) { 83 return LDAP_OTHER; 84 } 85 86 for ( i = 0; bvptr != NULL && bvptr[i] != NULL; i++ ) { 87 ; /* EMPTY */ 88 } 89 if ( num ) 90 *num = i; 91 92 tmpberval = (BerVarray)slapi_ch_malloc( (i + 1)*sizeof(struct berval)); 93 if ( tmpberval == NULL ) { 94 return LDAP_NO_MEMORY; 95 } 96 97 for ( i = 0; bvptr[i] != NULL; i++ ) { 98 tmpberval[i].bv_val = bvptr[i]->bv_val; 99 tmpberval[i].bv_len = bvptr[i]->bv_len; 100 } 101 tmpberval[i].bv_val = NULL; 102 tmpberval[i].bv_len = 0; 103 104 if ( rc == LDAP_SUCCESS ) { 105 *bvobj = tmpberval; 106 } 107 108 return rc; 109 } 110 111 Slapi_Entry * 112 slapi_str2entry( 113 char *s, 114 int flags ) 115 { 116 return str2entry( s ); 117 } 118 119 char * 120 slapi_entry2str( 121 Slapi_Entry *e, 122 int *len ) 123 { 124 char *ret = NULL; 125 char *s; 126 127 ldap_pvt_thread_mutex_lock( &entry2str_mutex ); 128 s = entry2str( e, len ); 129 if ( s != NULL ) 130 ret = slapi_ch_strdup( s ); 131 ldap_pvt_thread_mutex_unlock( &entry2str_mutex ); 132 133 return ret; 134 } 135 136 char * 137 slapi_entry_get_dn( Slapi_Entry *e ) 138 { 139 return e->e_name.bv_val; 140 } 141 142 int 143 slapi_x_entry_get_id( Slapi_Entry *e ) 144 { 145 return e->e_id; 146 } 147 148 static int 149 slapi_int_dn_pretty( struct berval *in, struct berval *out ) 150 { 151 Syntax *syntax = slap_schema.si_syn_distinguishedName; 152 153 assert( syntax != NULL ); 154 155 return (syntax->ssyn_pretty)( syntax, in, out, NULL ); 156 } 157 158 static int 159 slapi_int_dn_normalize( struct berval *in, struct berval *out ) 160 { 161 MatchingRule *mr = slap_schema.si_mr_distinguishedNameMatch; 162 Syntax *syntax = slap_schema.si_syn_distinguishedName; 163 164 assert( mr != NULL ); 165 166 return (mr->smr_normalize)( 0, syntax, mr, in, out, NULL ); 167 } 168 169 void 170 slapi_entry_set_dn( 171 Slapi_Entry *e, 172 char *ldn ) 173 { 174 struct berval dn = BER_BVNULL; 175 176 dn.bv_val = ldn; 177 dn.bv_len = strlen( ldn ); 178 179 slapi_int_dn_pretty( &dn, &e->e_name ); 180 slapi_int_dn_normalize( &dn, &e->e_nname ); 181 } 182 183 Slapi_Entry * 184 slapi_entry_dup( Slapi_Entry *e ) 185 { 186 return entry_dup( e ); 187 } 188 189 int 190 slapi_entry_attr_delete( 191 Slapi_Entry *e, 192 char *type ) 193 { 194 AttributeDescription *ad = NULL; 195 const char *text; 196 197 if ( slap_str2ad( type, &ad, &text ) != LDAP_SUCCESS ) { 198 return 1; /* LDAP_NO_SUCH_ATTRIBUTE */ 199 } 200 201 if ( attr_delete( &e->e_attrs, ad ) == LDAP_SUCCESS ) { 202 return 0; /* attribute is deleted */ 203 } else { 204 return -1; /* something went wrong */ 205 } 206 } 207 208 Slapi_Entry * 209 slapi_entry_alloc( void ) 210 { 211 return (Slapi_Entry *)entry_alloc(); 212 } 213 214 void 215 slapi_entry_free( Slapi_Entry *e ) 216 { 217 if ( e != NULL ) 218 entry_free( e ); 219 } 220 221 int 222 slapi_entry_attr_merge( 223 Slapi_Entry *e, 224 char *type, 225 struct berval **vals ) 226 { 227 AttributeDescription *ad = NULL; 228 const char *text; 229 BerVarray bv; 230 int rc; 231 232 rc = slap_str2ad( type, &ad, &text ); 233 if ( rc != LDAP_SUCCESS ) { 234 return -1; 235 } 236 237 rc = bvptr2obj( vals, &bv, NULL ); 238 if ( rc != LDAP_SUCCESS ) { 239 return -1; 240 } 241 242 rc = attr_merge_normalize( e, ad, bv, NULL ); 243 ch_free( bv ); 244 245 return rc; 246 } 247 248 int 249 slapi_entry_attr_find( 250 Slapi_Entry *e, 251 char *type, 252 Slapi_Attr **attr ) 253 { 254 AttributeDescription *ad = NULL; 255 const char *text; 256 int rc; 257 258 rc = slap_str2ad( type, &ad, &text ); 259 if ( rc != LDAP_SUCCESS ) { 260 return -1; 261 } 262 263 *attr = attr_find( e->e_attrs, ad ); 264 if ( *attr == NULL ) { 265 return -1; 266 } 267 268 return 0; 269 } 270 271 char * 272 slapi_entry_attr_get_charptr( const Slapi_Entry *e, const char *type ) 273 { 274 AttributeDescription *ad = NULL; 275 const char *text; 276 int rc; 277 Attribute *attr; 278 279 rc = slap_str2ad( type, &ad, &text ); 280 if ( rc != LDAP_SUCCESS ) { 281 return NULL; 282 } 283 284 attr = attr_find( e->e_attrs, ad ); 285 if ( attr == NULL ) { 286 return NULL; 287 } 288 289 if ( attr->a_vals != NULL && attr->a_vals[0].bv_len != 0 ) { 290 const char *p; 291 292 p = slapi_value_get_string( &attr->a_vals[0] ); 293 if ( p != NULL ) { 294 return slapi_ch_strdup( p ); 295 } 296 } 297 298 return NULL; 299 } 300 301 int 302 slapi_entry_attr_get_int( const Slapi_Entry *e, const char *type ) 303 { 304 AttributeDescription *ad = NULL; 305 const char *text; 306 int rc; 307 Attribute *attr; 308 309 rc = slap_str2ad( type, &ad, &text ); 310 if ( rc != LDAP_SUCCESS ) { 311 return 0; 312 } 313 314 attr = attr_find( e->e_attrs, ad ); 315 if ( attr == NULL ) { 316 return 0; 317 } 318 319 return slapi_value_get_int( attr->a_vals ); 320 } 321 322 long 323 slapi_entry_attr_get_long( const Slapi_Entry *e, const char *type ) 324 { 325 AttributeDescription *ad = NULL; 326 const char *text; 327 int rc; 328 Attribute *attr; 329 330 rc = slap_str2ad( type, &ad, &text ); 331 if ( rc != LDAP_SUCCESS ) { 332 return 0; 333 } 334 335 attr = attr_find( e->e_attrs, ad ); 336 if ( attr == NULL ) { 337 return 0; 338 } 339 340 return slapi_value_get_long( attr->a_vals ); 341 } 342 343 unsigned int 344 slapi_entry_attr_get_uint( const Slapi_Entry *e, const char *type ) 345 { 346 AttributeDescription *ad = NULL; 347 const char *text; 348 int rc; 349 Attribute *attr; 350 351 rc = slap_str2ad( type, &ad, &text ); 352 if ( rc != LDAP_SUCCESS ) { 353 return 0; 354 } 355 356 attr = attr_find( e->e_attrs, ad ); 357 if ( attr == NULL ) { 358 return 0; 359 } 360 361 return slapi_value_get_uint( attr->a_vals ); 362 } 363 364 unsigned long 365 slapi_entry_attr_get_ulong( const Slapi_Entry *e, const char *type ) 366 { 367 AttributeDescription *ad = NULL; 368 const char *text; 369 int rc; 370 Attribute *attr; 371 372 rc = slap_str2ad( type, &ad, &text ); 373 if ( rc != LDAP_SUCCESS ) { 374 return 0; 375 } 376 377 attr = attr_find( e->e_attrs, ad ); 378 if ( attr == NULL ) { 379 return 0; 380 } 381 382 return slapi_value_get_ulong( attr->a_vals ); 383 } 384 385 int 386 slapi_entry_attr_hasvalue( Slapi_Entry *e, const char *type, const char *value ) 387 { 388 struct berval bv; 389 AttributeDescription *ad = NULL; 390 const char *text; 391 int rc; 392 Attribute *attr; 393 394 rc = slap_str2ad( type, &ad, &text ); 395 if ( rc != LDAP_SUCCESS ) { 396 return 0; 397 } 398 399 attr = attr_find( e->e_attrs, ad ); 400 if ( attr == NULL ) { 401 return 0; 402 } 403 404 bv.bv_val = (char *)value; 405 bv.bv_len = strlen( value ); 406 407 return ( slapi_attr_value_find( attr, &bv ) != -1 ); 408 } 409 410 void 411 slapi_entry_attr_set_charptr(Slapi_Entry* e, const char *type, const char *value) 412 { 413 AttributeDescription *ad = NULL; 414 const char *text; 415 int rc; 416 struct berval bv; 417 418 rc = slap_str2ad( type, &ad, &text ); 419 if ( rc != LDAP_SUCCESS ) { 420 return; 421 } 422 423 attr_delete ( &e->e_attrs, ad ); 424 if ( value != NULL ) { 425 bv.bv_val = (char *)value; 426 bv.bv_len = strlen(value); 427 attr_merge_normalize_one( e, ad, &bv, NULL ); 428 } 429 } 430 431 void 432 slapi_entry_attr_set_int( Slapi_Entry* e, const char *type, int l) 433 { 434 char buf[64]; 435 436 snprintf( buf, sizeof( buf ), "%d", l ); 437 slapi_entry_attr_set_charptr( e, type, buf ); 438 } 439 440 void 441 slapi_entry_attr_set_uint( Slapi_Entry* e, const char *type, unsigned int l) 442 { 443 char buf[64]; 444 445 snprintf( buf, sizeof( buf ), "%u", l ); 446 slapi_entry_attr_set_charptr( e, type, buf ); 447 } 448 449 void 450 slapi_entry_attr_set_long(Slapi_Entry* e, const char *type, long l) 451 { 452 char buf[64]; 453 454 snprintf( buf, sizeof( buf ), "%ld", l ); 455 slapi_entry_attr_set_charptr( e, type, buf ); 456 } 457 458 void 459 slapi_entry_attr_set_ulong(Slapi_Entry* e, const char *type, unsigned long l) 460 { 461 char buf[64]; 462 463 snprintf( buf, sizeof( buf ), "%lu", l ); 464 slapi_entry_attr_set_charptr( e, type, buf ); 465 } 466 467 int 468 slapi_is_rootdse( const char *dn ) 469 { 470 return ( dn == NULL || dn[0] == '\0' ); 471 } 472 473 int 474 slapi_entry_has_children( const Slapi_Entry *e ) 475 { 476 Slapi_PBlock *pb; 477 int hasSubordinates = 0; 478 479 pb = slapi_pblock_new(); 480 slapi_int_connection_init_pb( pb, LDAP_REQ_SEARCH ); 481 482 slapi_pblock_set( pb, SLAPI_TARGET_DN, slapi_entry_get_dn( (Entry *)e ) ); 483 484 pb->pb_op->o_bd = select_backend( (struct berval *)&e->e_nname, 0 ); 485 if ( pb->pb_op->o_bd != NULL ) { 486 pb->pb_op->o_bd->be_has_subordinates( pb->pb_op, (Entry *)e, &hasSubordinates ); 487 } 488 489 slapi_pblock_destroy( pb ); 490 491 return ( hasSubordinates == LDAP_COMPARE_TRUE ); 492 } 493 494 /* 495 * Return approximate size of the entry rounded to the nearest 496 * 1K. Only the size of the attribute values are counted in the 497 * Sun implementation. 498 * 499 * http://docs.sun.com/source/816-6701-10/funcref.html#1017388 500 */ 501 size_t slapi_entry_size(Slapi_Entry *e) 502 { 503 size_t size; 504 Attribute *a; 505 int i; 506 507 for ( size = 0, a = e->e_attrs; a != NULL; a = a->a_next ) { 508 for ( i = 0; a->a_vals[i].bv_val != NULL; i++ ) { 509 size += a->a_vals[i].bv_len + 1; 510 } 511 } 512 513 size += 1023; 514 size -= (size % 1024); 515 516 return size; 517 } 518 519 /* 520 * Add values to entry. 521 * 522 * Returns: 523 * LDAP_SUCCESS Values added to entry 524 * LDAP_TYPE_OR_VALUE_EXISTS One or more values exist in entry already 525 * LDAP_CONSTRAINT_VIOLATION Any other error (odd, but it's the spec) 526 */ 527 int 528 slapi_entry_add_values( Slapi_Entry *e, const char *type, struct berval **vals ) 529 { 530 Modification mod; 531 const char *text; 532 int rc; 533 char textbuf[SLAP_TEXT_BUFLEN]; 534 535 mod.sm_op = LDAP_MOD_ADD; 536 mod.sm_flags = 0; 537 mod.sm_desc = NULL; 538 mod.sm_type.bv_val = (char *)type; 539 mod.sm_type.bv_len = strlen( type ); 540 541 rc = slap_str2ad( type, &mod.sm_desc, &text ); 542 if ( rc != LDAP_SUCCESS ) { 543 return rc; 544 } 545 546 if ( vals == NULL ) { 547 /* Apparently vals can be NULL 548 * FIXME: sm_values = NULL ? */ 549 mod.sm_values = (BerVarray)ch_malloc( sizeof(struct berval) ); 550 mod.sm_values->bv_val = NULL; 551 mod.sm_numvals = 0; 552 553 } else { 554 rc = bvptr2obj( vals, &mod.sm_values, &mod.sm_numvals ); 555 if ( rc != LDAP_SUCCESS ) { 556 return LDAP_CONSTRAINT_VIOLATION; 557 } 558 } 559 mod.sm_nvalues = NULL; 560 561 rc = modify_add_values( e, &mod, 0, &text, textbuf, sizeof(textbuf) ); 562 563 slapi_ch_free( (void **)&mod.sm_values ); 564 565 return (rc == LDAP_SUCCESS) ? LDAP_SUCCESS : LDAP_CONSTRAINT_VIOLATION; 566 } 567 568 int 569 slapi_entry_add_values_sv( Slapi_Entry *e, const char *type, Slapi_Value **vals ) 570 { 571 return slapi_entry_add_values( e, type, vals ); 572 } 573 574 int 575 slapi_entry_add_valueset(Slapi_Entry *e, const char *type, Slapi_ValueSet *vs) 576 { 577 AttributeDescription *ad = NULL; 578 const char *text; 579 int rc; 580 581 rc = slap_str2ad( type, &ad, &text ); 582 if ( rc != LDAP_SUCCESS ) { 583 return -1; 584 } 585 586 return attr_merge_normalize( e, ad, *vs, NULL ); 587 } 588 589 int 590 slapi_entry_delete_values( Slapi_Entry *e, const char *type, struct berval **vals ) 591 { 592 Modification mod; 593 const char *text; 594 int rc; 595 char textbuf[SLAP_TEXT_BUFLEN]; 596 597 mod.sm_op = LDAP_MOD_DELETE; 598 mod.sm_flags = 0; 599 mod.sm_desc = NULL; 600 mod.sm_type.bv_val = (char *)type; 601 mod.sm_type.bv_len = strlen( type ); 602 603 if ( vals == NULL ) { 604 /* If vals is NULL, this is a NOOP. */ 605 return LDAP_SUCCESS; 606 } 607 608 rc = slap_str2ad( type, &mod.sm_desc, &text ); 609 if ( rc != LDAP_SUCCESS ) { 610 return rc; 611 } 612 613 if ( vals[0] == NULL ) { 614 /* SLAPI doco says LDApb_opERATIONS_ERROR but LDAP_OTHER is better */ 615 return attr_delete( &e->e_attrs, mod.sm_desc ) ? LDAP_OTHER : LDAP_SUCCESS; 616 } 617 618 rc = bvptr2obj( vals, &mod.sm_values, &mod.sm_numvals ); 619 if ( rc != LDAP_SUCCESS ) { 620 return LDAP_CONSTRAINT_VIOLATION; 621 } 622 mod.sm_nvalues = NULL; 623 624 rc = modify_delete_values( e, &mod, 0, &text, textbuf, sizeof(textbuf) ); 625 626 slapi_ch_free( (void **)&mod.sm_values ); 627 628 return rc; 629 } 630 631 int 632 slapi_entry_delete_values_sv( Slapi_Entry *e, const char *type, Slapi_Value **vals ) 633 { 634 return slapi_entry_delete_values( e, type, vals ); 635 } 636 637 int 638 slapi_entry_merge_values_sv( Slapi_Entry *e, const char *type, Slapi_Value **vals ) 639 { 640 return slapi_entry_attr_merge( e, (char *)type, vals ); 641 } 642 643 int 644 slapi_entry_add_value(Slapi_Entry *e, const char *type, const Slapi_Value *value) 645 { 646 AttributeDescription *ad = NULL; 647 int rc; 648 const char *text; 649 650 rc = slap_str2ad( type, &ad, &text ); 651 if ( rc != LDAP_SUCCESS ) { 652 return -1; 653 } 654 655 rc = attr_merge_normalize_one( e, ad, (Slapi_Value *)value, NULL ); 656 if ( rc != LDAP_SUCCESS ) { 657 return -1; 658 } 659 660 return 0; 661 } 662 663 int 664 slapi_entry_add_string(Slapi_Entry *e, const char *type, const char *value) 665 { 666 Slapi_Value val; 667 668 val.bv_val = (char *)value; 669 val.bv_len = strlen( value ); 670 671 return slapi_entry_add_value( e, type, &val ); 672 } 673 674 int 675 slapi_entry_delete_string(Slapi_Entry *e, const char *type, const char *value) 676 { 677 Slapi_Value *vals[2]; 678 Slapi_Value val; 679 680 val.bv_val = (char *)value; 681 val.bv_len = strlen( value ); 682 vals[0] = &val; 683 vals[1] = NULL; 684 685 return slapi_entry_delete_values_sv( e, type, vals ); 686 } 687 688 int 689 slapi_entry_attr_merge_sv( Slapi_Entry *e, const char *type, Slapi_Value **vals ) 690 { 691 return slapi_entry_attr_merge( e, (char *)type, vals ); 692 } 693 694 int 695 slapi_entry_first_attr( const Slapi_Entry *e, Slapi_Attr **attr ) 696 { 697 if ( e == NULL ) { 698 return -1; 699 } 700 701 *attr = e->e_attrs; 702 703 return ( *attr != NULL ) ? 0 : -1; 704 } 705 706 int 707 slapi_entry_next_attr( const Slapi_Entry *e, Slapi_Attr *prevattr, Slapi_Attr **attr ) 708 { 709 if ( e == NULL ) { 710 return -1; 711 } 712 713 if ( prevattr == NULL ) { 714 return -1; 715 } 716 717 *attr = prevattr->a_next; 718 719 return ( *attr != NULL ) ? 0 : -1; 720 } 721 722 int 723 slapi_entry_attr_replace_sv( Slapi_Entry *e, const char *type, Slapi_Value **vals ) 724 { 725 AttributeDescription *ad = NULL; 726 const char *text; 727 int rc; 728 BerVarray bv; 729 730 rc = slap_str2ad( type, &ad, &text ); 731 if ( rc != LDAP_SUCCESS ) { 732 return 0; 733 } 734 735 attr_delete( &e->e_attrs, ad ); 736 737 rc = bvptr2obj( vals, &bv, NULL ); 738 if ( rc != LDAP_SUCCESS ) { 739 return -1; 740 } 741 742 rc = attr_merge_normalize( e, ad, bv, NULL ); 743 slapi_ch_free( (void **)&bv ); 744 if ( rc != LDAP_SUCCESS ) { 745 return -1; 746 } 747 748 return 0; 749 } 750 751 /* 752 * FIXME -- The caller must free the allocated memory. 753 * In Netscape they do not have to. 754 */ 755 int 756 slapi_attr_get_values( 757 Slapi_Attr *attr, 758 struct berval ***vals ) 759 { 760 int i, j; 761 struct berval **bv; 762 763 if ( attr == NULL ) { 764 return 1; 765 } 766 767 for ( i = 0; attr->a_vals[i].bv_val != NULL; i++ ) { 768 ; /* EMPTY */ 769 } 770 771 bv = (struct berval **)ch_malloc( (i + 1) * sizeof(struct berval *) ); 772 for ( j = 0; j < i; j++ ) { 773 bv[j] = ber_dupbv( NULL, &attr->a_vals[j] ); 774 } 775 bv[j] = NULL; 776 777 *vals = (struct berval **)bv; 778 779 return 0; 780 } 781 782 char * 783 slapi_dn_normalize( char *dn ) 784 { 785 struct berval bdn; 786 struct berval pdn; 787 788 assert( dn != NULL ); 789 790 bdn.bv_val = dn; 791 bdn.bv_len = strlen( dn ); 792 793 if ( slapi_int_dn_pretty( &bdn, &pdn ) != LDAP_SUCCESS ) { 794 return NULL; 795 } 796 797 return pdn.bv_val; 798 } 799 800 char * 801 slapi_dn_normalize_case( char *dn ) 802 { 803 struct berval bdn; 804 struct berval ndn; 805 806 assert( dn != NULL ); 807 808 bdn.bv_val = dn; 809 bdn.bv_len = strlen( dn ); 810 811 if ( slapi_int_dn_normalize( &bdn, &ndn ) != LDAP_SUCCESS ) { 812 return NULL; 813 } 814 815 return ndn.bv_val; 816 } 817 818 int 819 slapi_dn_issuffix( 820 char *dn, 821 char *suffix ) 822 { 823 struct berval bdn, ndn; 824 struct berval bsuffix, nsuffix; 825 int rc; 826 827 assert( dn != NULL ); 828 assert( suffix != NULL ); 829 830 bdn.bv_val = dn; 831 bdn.bv_len = strlen( dn ); 832 833 bsuffix.bv_val = suffix; 834 bsuffix.bv_len = strlen( suffix ); 835 836 if ( dnNormalize( 0, NULL, NULL, &bdn, &ndn, NULL ) != LDAP_SUCCESS ) { 837 return 0; 838 } 839 840 if ( dnNormalize( 0, NULL, NULL, &bsuffix, &nsuffix, NULL ) 841 != LDAP_SUCCESS ) 842 { 843 slapi_ch_free( (void **)&ndn.bv_val ); 844 return 0; 845 } 846 847 rc = dnIsSuffix( &ndn, &nsuffix ); 848 849 slapi_ch_free( (void **)&ndn.bv_val ); 850 slapi_ch_free( (void **)&nsuffix.bv_val ); 851 852 return rc; 853 } 854 855 int 856 slapi_dn_isparent( 857 const char *parentdn, 858 const char *childdn ) 859 { 860 struct berval assertedParentDN, normalizedAssertedParentDN; 861 struct berval childDN, normalizedChildDN; 862 struct berval normalizedParentDN; 863 int match; 864 865 assert( parentdn != NULL ); 866 assert( childdn != NULL ); 867 868 assertedParentDN.bv_val = (char *)parentdn; 869 assertedParentDN.bv_len = strlen( parentdn ); 870 871 if ( dnNormalize( 0, NULL, NULL, &assertedParentDN, 872 &normalizedAssertedParentDN, NULL ) != LDAP_SUCCESS ) 873 { 874 return 0; 875 } 876 877 childDN.bv_val = (char *)childdn; 878 childDN.bv_len = strlen( childdn ); 879 880 if ( dnNormalize( 0, NULL, NULL, &childDN, 881 &normalizedChildDN, NULL ) != LDAP_SUCCESS ) 882 { 883 slapi_ch_free( (void **)&normalizedAssertedParentDN.bv_val ); 884 return 0; 885 } 886 887 dnParent( &normalizedChildDN, &normalizedParentDN ); 888 889 if ( dnMatch( &match, 0, slap_schema.si_syn_distinguishedName, NULL, 890 &normalizedParentDN, (void *)&normalizedAssertedParentDN ) != LDAP_SUCCESS ) 891 { 892 match = -1; 893 } 894 895 slapi_ch_free( (void **)&normalizedAssertedParentDN.bv_val ); 896 slapi_ch_free( (void **)&normalizedChildDN.bv_val ); 897 898 return ( match == 0 ); 899 } 900 901 /* 902 * Returns DN of the parent entry, or NULL if the DN is 903 * an empty string or NULL, or has no parent. 904 */ 905 char * 906 slapi_dn_parent( const char *_dn ) 907 { 908 struct berval dn, prettyDN; 909 struct berval parentDN; 910 char *ret; 911 912 if ( _dn == NULL ) { 913 return NULL; 914 } 915 916 dn.bv_val = (char *)_dn; 917 dn.bv_len = strlen( _dn ); 918 919 if ( dn.bv_len == 0 ) { 920 return NULL; 921 } 922 923 if ( dnPretty( NULL, &dn, &prettyDN, NULL ) != LDAP_SUCCESS ) { 924 return NULL; 925 } 926 927 dnParent( &prettyDN, &parentDN ); /* in-place */ 928 929 if ( parentDN.bv_len == 0 ) { 930 slapi_ch_free_string( &prettyDN.bv_val ); 931 return NULL; 932 } 933 934 ret = slapi_ch_strdup( parentDN.bv_val ); 935 slapi_ch_free_string( &prettyDN.bv_val ); 936 937 return ret; 938 } 939 940 int slapi_dn_isbesuffix( Slapi_PBlock *pb, char *ldn ) 941 { 942 struct berval ndn; 943 Backend *be; 944 945 if ( slapi_is_rootdse( ldn ) ) { 946 return 0; 947 } 948 949 /* according to spec should already be normalized */ 950 ndn.bv_len = strlen( ldn ); 951 ndn.bv_val = ldn; 952 953 be = select_backend( &pb->pb_op->o_req_ndn, 0 ); 954 if ( be == NULL ) { 955 return 0; 956 } 957 958 return be_issuffix( be, &ndn ); 959 } 960 961 /* 962 * Returns DN of the parent entry; or NULL if the DN is 963 * an empty string, if the DN has no parent, or if the 964 * DN is the suffix of the backend database 965 */ 966 char *slapi_dn_beparent( Slapi_PBlock *pb, const char *ldn ) 967 { 968 Backend *be; 969 struct berval dn, prettyDN; 970 struct berval normalizedDN, parentDN; 971 char *parent = NULL; 972 973 if ( pb == NULL ) { 974 return NULL; 975 } 976 977 PBLOCK_ASSERT_OP( pb, 0 ); 978 979 if ( slapi_is_rootdse( ldn ) ) { 980 return NULL; 981 } 982 983 dn.bv_val = (char *)ldn; 984 dn.bv_len = strlen( ldn ); 985 986 if ( dnPrettyNormal( NULL, &dn, &prettyDN, &normalizedDN, NULL ) != LDAP_SUCCESS ) { 987 return NULL; 988 } 989 990 be = select_backend( &pb->pb_op->o_req_ndn, 0 ); 991 992 if ( be == NULL || be_issuffix( be, &normalizedDN ) == 0 ) { 993 dnParent( &prettyDN, &parentDN ); 994 995 if ( parentDN.bv_len != 0 ) 996 parent = slapi_ch_strdup( parentDN.bv_val ); 997 } 998 999 slapi_ch_free_string( &prettyDN.bv_val ); 1000 slapi_ch_free_string( &normalizedDN.bv_val ); 1001 1002 return parent; 1003 } 1004 1005 char * 1006 slapi_dn_ignore_case( char *dn ) 1007 { 1008 return slapi_dn_normalize_case( dn ); 1009 } 1010 1011 char * 1012 slapi_ch_malloc( unsigned long size ) 1013 { 1014 return ch_malloc( size ); 1015 } 1016 1017 void 1018 slapi_ch_free( void **ptr ) 1019 { 1020 if ( ptr == NULL || *ptr == NULL ) 1021 return; 1022 ch_free( *ptr ); 1023 *ptr = NULL; 1024 } 1025 1026 void 1027 slapi_ch_free_string( char **ptr ) 1028 { 1029 slapi_ch_free( (void **)ptr ); 1030 } 1031 1032 void 1033 slapi_ch_array_free( char **arrayp ) 1034 { 1035 char **p; 1036 1037 if ( arrayp != NULL ) { 1038 for ( p = arrayp; *p != NULL; p++ ) { 1039 slapi_ch_free( (void **)p ); 1040 } 1041 slapi_ch_free( (void **)&arrayp ); 1042 } 1043 } 1044 1045 struct berval * 1046 slapi_ch_bvdup(const struct berval *v) 1047 { 1048 return ber_dupbv(NULL, (struct berval *)v); 1049 } 1050 1051 struct berval ** 1052 slapi_ch_bvecdup(const struct berval **v) 1053 { 1054 int i; 1055 struct berval **rv; 1056 1057 if ( v == NULL ) { 1058 return NULL; 1059 } 1060 1061 for ( i = 0; v[i] != NULL; i++ ) 1062 ; 1063 1064 rv = (struct berval **) slapi_ch_malloc( (i + 1) * sizeof(struct berval *) ); 1065 1066 for ( i = 0; v[i] != NULL; i++ ) { 1067 rv[i] = slapi_ch_bvdup( v[i] ); 1068 } 1069 rv[i] = NULL; 1070 1071 return rv; 1072 } 1073 1074 char * 1075 slapi_ch_calloc( 1076 unsigned long nelem, 1077 unsigned long size ) 1078 { 1079 return ch_calloc( nelem, size ); 1080 } 1081 1082 char * 1083 slapi_ch_realloc( 1084 char *block, 1085 unsigned long size ) 1086 { 1087 return ch_realloc( block, size ); 1088 } 1089 1090 char * 1091 slapi_ch_strdup( const char *s ) 1092 { 1093 return ch_strdup( s ); 1094 } 1095 1096 size_t 1097 slapi_ch_stlen( const char *s ) 1098 { 1099 return strlen( s ); 1100 } 1101 1102 int 1103 slapi_control_present( 1104 LDAPControl **controls, 1105 char *oid, 1106 struct berval **val, 1107 int *iscritical ) 1108 { 1109 int i; 1110 int rc = 0; 1111 1112 if ( val ) { 1113 *val = NULL; 1114 } 1115 1116 if ( iscritical ) { 1117 *iscritical = 0; 1118 } 1119 1120 for ( i = 0; controls != NULL && controls[i] != NULL; i++ ) { 1121 if ( strcmp( controls[i]->ldctl_oid, oid ) != 0 ) { 1122 continue; 1123 } 1124 1125 rc = 1; 1126 if ( controls[i]->ldctl_value.bv_len != 0 ) { 1127 if ( val ) { 1128 *val = &controls[i]->ldctl_value; 1129 } 1130 } 1131 1132 if ( iscritical ) { 1133 *iscritical = controls[i]->ldctl_iscritical; 1134 } 1135 1136 break; 1137 } 1138 1139 return rc; 1140 } 1141 1142 static void 1143 slapControlMask2SlapiControlOp(slap_mask_t slap_mask, 1144 unsigned long *slapi_mask) 1145 { 1146 *slapi_mask = SLAPI_OPERATION_NONE; 1147 1148 if ( slap_mask & SLAP_CTRL_ABANDON ) 1149 *slapi_mask |= SLAPI_OPERATION_ABANDON; 1150 1151 if ( slap_mask & SLAP_CTRL_ADD ) 1152 *slapi_mask |= SLAPI_OPERATION_ADD; 1153 1154 if ( slap_mask & SLAP_CTRL_BIND ) 1155 *slapi_mask |= SLAPI_OPERATION_BIND; 1156 1157 if ( slap_mask & SLAP_CTRL_COMPARE ) 1158 *slapi_mask |= SLAPI_OPERATION_COMPARE; 1159 1160 if ( slap_mask & SLAP_CTRL_DELETE ) 1161 *slapi_mask |= SLAPI_OPERATION_DELETE; 1162 1163 if ( slap_mask & SLAP_CTRL_MODIFY ) 1164 *slapi_mask |= SLAPI_OPERATION_MODIFY; 1165 1166 if ( slap_mask & SLAP_CTRL_RENAME ) 1167 *slapi_mask |= SLAPI_OPERATION_MODDN; 1168 1169 if ( slap_mask & SLAP_CTRL_SEARCH ) 1170 *slapi_mask |= SLAPI_OPERATION_SEARCH; 1171 1172 if ( slap_mask & SLAP_CTRL_UNBIND ) 1173 *slapi_mask |= SLAPI_OPERATION_UNBIND; 1174 } 1175 1176 static void 1177 slapiControlOp2SlapControlMask(unsigned long slapi_mask, 1178 slap_mask_t *slap_mask) 1179 { 1180 *slap_mask = 0; 1181 1182 if ( slapi_mask & SLAPI_OPERATION_BIND ) 1183 *slap_mask |= SLAP_CTRL_BIND; 1184 1185 if ( slapi_mask & SLAPI_OPERATION_UNBIND ) 1186 *slap_mask |= SLAP_CTRL_UNBIND; 1187 1188 if ( slapi_mask & SLAPI_OPERATION_SEARCH ) 1189 *slap_mask |= SLAP_CTRL_SEARCH; 1190 1191 if ( slapi_mask & SLAPI_OPERATION_MODIFY ) 1192 *slap_mask |= SLAP_CTRL_MODIFY; 1193 1194 if ( slapi_mask & SLAPI_OPERATION_ADD ) 1195 *slap_mask |= SLAP_CTRL_ADD; 1196 1197 if ( slapi_mask & SLAPI_OPERATION_DELETE ) 1198 *slap_mask |= SLAP_CTRL_DELETE; 1199 1200 if ( slapi_mask & SLAPI_OPERATION_MODDN ) 1201 *slap_mask |= SLAP_CTRL_RENAME; 1202 1203 if ( slapi_mask & SLAPI_OPERATION_COMPARE ) 1204 *slap_mask |= SLAP_CTRL_COMPARE; 1205 1206 if ( slapi_mask & SLAPI_OPERATION_ABANDON ) 1207 *slap_mask |= SLAP_CTRL_ABANDON; 1208 1209 *slap_mask |= SLAP_CTRL_GLOBAL; 1210 } 1211 1212 static int 1213 slapi_int_parse_control( 1214 Operation *op, 1215 SlapReply *rs, 1216 LDAPControl *ctrl ) 1217 { 1218 /* Plugins must deal with controls themselves. */ 1219 1220 return LDAP_SUCCESS; 1221 } 1222 1223 void 1224 slapi_register_supported_control( 1225 char *controloid, 1226 unsigned long controlops ) 1227 { 1228 slap_mask_t controlmask; 1229 1230 slapiControlOp2SlapControlMask( controlops, &controlmask ); 1231 1232 register_supported_control( controloid, controlmask, NULL, slapi_int_parse_control, NULL ); 1233 } 1234 1235 int 1236 slapi_get_supported_controls( 1237 char ***ctrloidsp, 1238 unsigned long **ctrlopsp ) 1239 { 1240 int i, rc; 1241 1242 rc = get_supported_controls( ctrloidsp, (slap_mask_t **)ctrlopsp ); 1243 if ( rc != LDAP_SUCCESS ) { 1244 return rc; 1245 } 1246 1247 for ( i = 0; (*ctrloidsp)[i] != NULL; i++ ) { 1248 /* In place, naughty. */ 1249 slapControlMask2SlapiControlOp( (*ctrlopsp)[i], &((*ctrlopsp)[i]) ); 1250 } 1251 1252 return LDAP_SUCCESS; 1253 } 1254 1255 LDAPControl * 1256 slapi_dup_control( LDAPControl *ctrl ) 1257 { 1258 LDAPControl *ret; 1259 1260 ret = (LDAPControl *)slapi_ch_malloc( sizeof(*ret) ); 1261 ret->ldctl_oid = slapi_ch_strdup( ctrl->ldctl_oid ); 1262 ber_dupbv( &ret->ldctl_value, &ctrl->ldctl_value ); 1263 ret->ldctl_iscritical = ctrl->ldctl_iscritical; 1264 1265 return ret; 1266 } 1267 1268 void 1269 slapi_register_supported_saslmechanism( char *mechanism ) 1270 { 1271 /* FIXME -- can not add saslmechanism to OpenLDAP dynamically */ 1272 slapi_log_error( SLAPI_LOG_FATAL, "slapi_register_supported_saslmechanism", 1273 "OpenLDAP does not support dynamic registration of SASL mechanisms\n" ); 1274 } 1275 1276 char ** 1277 slapi_get_supported_saslmechanisms( void ) 1278 { 1279 /* FIXME -- can not get the saslmechanism without a connection. */ 1280 slapi_log_error( SLAPI_LOG_FATAL, "slapi_get_supported_saslmechanisms", 1281 "can not get the SASL mechanism list " 1282 "without a connection\n" ); 1283 return NULL; 1284 } 1285 1286 char ** 1287 slapi_get_supported_extended_ops( void ) 1288 { 1289 int i, j, k; 1290 char **ppExtOpOID = NULL; 1291 int numExtOps = 0; 1292 1293 for ( i = 0; get_supported_extop( i ) != NULL; i++ ) { 1294 ; 1295 } 1296 1297 for ( j = 0; slapi_int_get_supported_extop( j ) != NULL; j++ ) { 1298 ; 1299 } 1300 1301 numExtOps = i + j; 1302 if ( numExtOps == 0 ) { 1303 return NULL; 1304 } 1305 1306 ppExtOpOID = (char **)slapi_ch_malloc( (numExtOps + 1) * sizeof(char *) ); 1307 for ( k = 0; k < i; k++ ) { 1308 struct berval *bv; 1309 1310 bv = get_supported_extop( k ); 1311 assert( bv != NULL ); 1312 1313 ppExtOpOID[ k ] = bv->bv_val; 1314 } 1315 1316 for ( ; k < j; k++ ) { 1317 struct berval *bv; 1318 1319 bv = slapi_int_get_supported_extop( k ); 1320 assert( bv != NULL ); 1321 1322 ppExtOpOID[ i + k ] = bv->bv_val; 1323 } 1324 ppExtOpOID[ i + k ] = NULL; 1325 1326 return ppExtOpOID; 1327 } 1328 1329 void 1330 slapi_send_ldap_result( 1331 Slapi_PBlock *pb, 1332 int err, 1333 char *matched, 1334 char *text, 1335 int nentries, 1336 struct berval **urls ) 1337 { 1338 SlapReply *rs; 1339 1340 PBLOCK_ASSERT_OP( pb, 0 ); 1341 1342 rs = pb->pb_rs; 1343 1344 rs->sr_err = err; 1345 rs->sr_matched = matched; 1346 rs->sr_text = text; 1347 rs->sr_ref = NULL; 1348 1349 if ( err == LDAP_SASL_BIND_IN_PROGRESS ) { 1350 send_ldap_sasl( pb->pb_op, rs ); 1351 } else if ( rs->sr_rspoid != NULL ) { 1352 send_ldap_extended( pb->pb_op, rs ); 1353 } else { 1354 if ( pb->pb_op->o_tag == LDAP_REQ_SEARCH ) 1355 rs->sr_nentries = nentries; 1356 if ( urls != NULL ) 1357 bvptr2obj( urls, &rs->sr_ref, NULL ); 1358 1359 send_ldap_result( pb->pb_op, rs ); 1360 1361 if ( urls != NULL ) 1362 slapi_ch_free( (void **)&rs->sr_ref ); 1363 } 1364 } 1365 1366 int 1367 slapi_send_ldap_search_entry( 1368 Slapi_PBlock *pb, 1369 Slapi_Entry *e, 1370 LDAPControl **ectrls, 1371 char **attrs, 1372 int attrsonly ) 1373 { 1374 SlapReply rs = { REP_SEARCH }; 1375 int i = 0, j = 0; 1376 AttributeName *an = NULL; 1377 const char *text; 1378 int rc; 1379 1380 assert( pb->pb_op != NULL ); 1381 1382 if ( attrs != NULL ) { 1383 for ( i = 0; attrs[ i ] != NULL; i++ ) { 1384 ; /* empty */ 1385 } 1386 } 1387 1388 if ( i ) { 1389 an = (AttributeName *) slapi_ch_calloc( i + 1, sizeof(AttributeName) ); 1390 for ( i = 0; attrs[i] != NULL; i++ ) { 1391 an[j].an_name.bv_val = attrs[i]; 1392 an[j].an_name.bv_len = strlen( attrs[i] ); 1393 an[j].an_desc = NULL; 1394 if ( slap_bv2ad( &an[j].an_name, &an[j].an_desc, &text ) == LDAP_SUCCESS) { 1395 j++; 1396 } 1397 } 1398 an[j].an_name.bv_len = 0; 1399 an[j].an_name.bv_val = NULL; 1400 } 1401 1402 rs.sr_err = LDAP_SUCCESS; 1403 rs.sr_matched = NULL; 1404 rs.sr_text = NULL; 1405 rs.sr_ref = NULL; 1406 rs.sr_ctrls = ectrls; 1407 rs.sr_attrs = an; 1408 rs.sr_operational_attrs = NULL; 1409 rs.sr_entry = e; 1410 rs.sr_v2ref = NULL; 1411 rs.sr_flags = 0; 1412 1413 rc = send_search_entry( pb->pb_op, &rs ); 1414 1415 slapi_ch_free( (void **)&an ); 1416 1417 return rc; 1418 } 1419 1420 int 1421 slapi_send_ldap_search_reference( 1422 Slapi_PBlock *pb, 1423 Slapi_Entry *e, 1424 struct berval **references, 1425 LDAPControl **ectrls, 1426 struct berval **v2refs 1427 ) 1428 { 1429 SlapReply rs = { REP_SEARCHREF }; 1430 int rc; 1431 1432 rs.sr_err = LDAP_SUCCESS; 1433 rs.sr_matched = NULL; 1434 rs.sr_text = NULL; 1435 1436 rc = bvptr2obj( references, &rs.sr_ref, NULL ); 1437 if ( rc != LDAP_SUCCESS ) { 1438 return rc; 1439 } 1440 1441 rs.sr_ctrls = ectrls; 1442 rs.sr_attrs = NULL; 1443 rs.sr_operational_attrs = NULL; 1444 rs.sr_entry = e; 1445 1446 if ( v2refs != NULL ) { 1447 rc = bvptr2obj( v2refs, &rs.sr_v2ref, NULL ); 1448 if ( rc != LDAP_SUCCESS ) { 1449 slapi_ch_free( (void **)&rs.sr_ref ); 1450 return rc; 1451 } 1452 } else { 1453 rs.sr_v2ref = NULL; 1454 } 1455 1456 rc = send_search_reference( pb->pb_op, &rs ); 1457 1458 slapi_ch_free( (void **)&rs.sr_ref ); 1459 slapi_ch_free( (void **)&rs.sr_v2ref ); 1460 1461 return rc; 1462 } 1463 1464 Slapi_Filter * 1465 slapi_str2filter( char *str ) 1466 { 1467 return str2filter( str ); 1468 } 1469 1470 void 1471 slapi_filter_free( 1472 Slapi_Filter *f, 1473 int recurse ) 1474 { 1475 filter_free( f ); 1476 } 1477 1478 Slapi_Filter * 1479 slapi_filter_dup( Slapi_Filter *filter ) 1480 { 1481 return filter_dup( filter, NULL ); 1482 } 1483 1484 int 1485 slapi_filter_get_choice( Slapi_Filter *f ) 1486 { 1487 int rc; 1488 1489 if ( f != NULL ) { 1490 rc = f->f_choice; 1491 } else { 1492 rc = 0; 1493 } 1494 1495 return rc; 1496 } 1497 1498 int 1499 slapi_filter_get_ava( 1500 Slapi_Filter *f, 1501 char **type, 1502 struct berval **bval ) 1503 { 1504 int ftype; 1505 int rc = LDAP_SUCCESS; 1506 1507 assert( type != NULL ); 1508 assert( bval != NULL ); 1509 1510 *type = NULL; 1511 *bval = NULL; 1512 1513 ftype = f->f_choice; 1514 if ( ftype == LDAP_FILTER_EQUALITY 1515 || ftype == LDAP_FILTER_GE 1516 || ftype == LDAP_FILTER_LE 1517 || ftype == LDAP_FILTER_APPROX ) { 1518 /* 1519 * According to the SLAPI Reference Manual these are 1520 * not duplicated. 1521 */ 1522 *type = f->f_un.f_un_ava->aa_desc->ad_cname.bv_val; 1523 *bval = &f->f_un.f_un_ava->aa_value; 1524 } else { /* filter type not supported */ 1525 rc = -1; 1526 } 1527 1528 return rc; 1529 } 1530 1531 Slapi_Filter * 1532 slapi_filter_list_first( Slapi_Filter *f ) 1533 { 1534 int ftype; 1535 1536 if ( f == NULL ) { 1537 return NULL; 1538 } 1539 1540 ftype = f->f_choice; 1541 if ( ftype == LDAP_FILTER_AND 1542 || ftype == LDAP_FILTER_OR 1543 || ftype == LDAP_FILTER_NOT ) { 1544 return (Slapi_Filter *)f->f_list; 1545 } else { 1546 return NULL; 1547 } 1548 } 1549 1550 Slapi_Filter * 1551 slapi_filter_list_next( 1552 Slapi_Filter *f, 1553 Slapi_Filter *fprev ) 1554 { 1555 int ftype; 1556 1557 if ( f == NULL ) { 1558 return NULL; 1559 } 1560 1561 ftype = f->f_choice; 1562 if ( ftype == LDAP_FILTER_AND 1563 || ftype == LDAP_FILTER_OR 1564 || ftype == LDAP_FILTER_NOT ) 1565 { 1566 return fprev->f_next; 1567 } 1568 1569 return NULL; 1570 } 1571 1572 int 1573 slapi_filter_get_attribute_type( Slapi_Filter *f, char **type ) 1574 { 1575 if ( f == NULL ) { 1576 return -1; 1577 } 1578 1579 switch ( f->f_choice ) { 1580 case LDAP_FILTER_GE: 1581 case LDAP_FILTER_LE: 1582 case LDAP_FILTER_EQUALITY: 1583 case LDAP_FILTER_APPROX: 1584 *type = f->f_av_desc->ad_cname.bv_val; 1585 break; 1586 case LDAP_FILTER_SUBSTRINGS: 1587 *type = f->f_sub_desc->ad_cname.bv_val; 1588 break; 1589 case LDAP_FILTER_PRESENT: 1590 *type = f->f_desc->ad_cname.bv_val; 1591 break; 1592 case LDAP_FILTER_EXT: 1593 *type = f->f_mr_desc->ad_cname.bv_val; 1594 break; 1595 default: 1596 /* Complex filters need not apply. */ 1597 *type = NULL; 1598 return -1; 1599 } 1600 1601 return 0; 1602 } 1603 1604 int 1605 slapi_x_filter_set_attribute_type( Slapi_Filter *f, const char *type ) 1606 { 1607 AttributeDescription **adp, *ad = NULL; 1608 const char *text; 1609 int rc; 1610 1611 if ( f == NULL ) { 1612 return -1; 1613 } 1614 1615 switch ( f->f_choice ) { 1616 case LDAP_FILTER_GE: 1617 case LDAP_FILTER_LE: 1618 case LDAP_FILTER_EQUALITY: 1619 case LDAP_FILTER_APPROX: 1620 adp = &f->f_av_desc; 1621 break; 1622 case LDAP_FILTER_SUBSTRINGS: 1623 adp = &f->f_sub_desc; 1624 break; 1625 case LDAP_FILTER_PRESENT: 1626 adp = &f->f_desc; 1627 break; 1628 case LDAP_FILTER_EXT: 1629 adp = &f->f_mr_desc; 1630 break; 1631 default: 1632 /* Complex filters need not apply. */ 1633 return -1; 1634 } 1635 1636 rc = slap_str2ad( type, &ad, &text ); 1637 if ( rc == LDAP_SUCCESS ) 1638 *adp = ad; 1639 1640 return ( rc == LDAP_SUCCESS ) ? 0 : -1; 1641 } 1642 1643 int 1644 slapi_filter_get_subfilt( Slapi_Filter *f, char **type, char **initial, 1645 char ***any, char **final ) 1646 { 1647 int i; 1648 1649 if ( f->f_choice != LDAP_FILTER_SUBSTRINGS ) { 1650 return -1; 1651 } 1652 1653 /* 1654 * The caller shouldn't free but we can't return an 1655 * array of char *s from an array of bervals without 1656 * allocating memory, so we may as well be consistent. 1657 * XXX 1658 */ 1659 *type = f->f_sub_desc->ad_cname.bv_val; 1660 *initial = f->f_sub_initial.bv_val ? slapi_ch_strdup(f->f_sub_initial.bv_val) : NULL; 1661 if ( f->f_sub_any != NULL ) { 1662 for ( i = 0; f->f_sub_any[i].bv_val != NULL; i++ ) 1663 ; 1664 *any = (char **)slapi_ch_malloc( (i + 1) * sizeof(char *) ); 1665 for ( i = 0; f->f_sub_any[i].bv_val != NULL; i++ ) { 1666 (*any)[i] = slapi_ch_strdup(f->f_sub_any[i].bv_val); 1667 } 1668 (*any)[i] = NULL; 1669 } else { 1670 *any = NULL; 1671 } 1672 *final = f->f_sub_final.bv_val ? slapi_ch_strdup(f->f_sub_final.bv_val) : NULL; 1673 1674 return 0; 1675 } 1676 1677 Slapi_Filter * 1678 slapi_filter_join( int ftype, Slapi_Filter *f1, Slapi_Filter *f2 ) 1679 { 1680 Slapi_Filter *f = NULL; 1681 1682 if ( ftype == LDAP_FILTER_AND || 1683 ftype == LDAP_FILTER_OR || 1684 ftype == LDAP_FILTER_NOT ) 1685 { 1686 f = (Slapi_Filter *)slapi_ch_malloc( sizeof(*f) ); 1687 f->f_choice = ftype; 1688 f->f_list = f1; 1689 f->f_list->f_next = f2; 1690 f->f_next = NULL; 1691 } 1692 1693 return f; 1694 } 1695 1696 int 1697 slapi_x_filter_append( int ftype, 1698 Slapi_Filter **pContainingFilter, /* NULL on first call */ 1699 Slapi_Filter **pNextFilter, 1700 Slapi_Filter *filterToAppend ) 1701 { 1702 if ( ftype == LDAP_FILTER_AND || 1703 ftype == LDAP_FILTER_OR || 1704 ftype == LDAP_FILTER_NOT ) 1705 { 1706 if ( *pContainingFilter == NULL ) { 1707 *pContainingFilter = (Slapi_Filter *)slapi_ch_malloc( sizeof(Slapi_Filter) ); 1708 (*pContainingFilter)->f_choice = ftype; 1709 (*pContainingFilter)->f_list = filterToAppend; 1710 (*pContainingFilter)->f_next = NULL; 1711 } else { 1712 if ( (*pContainingFilter)->f_choice != ftype ) { 1713 /* Sanity check */ 1714 return -1; 1715 } 1716 (*pNextFilter)->f_next = filterToAppend; 1717 } 1718 *pNextFilter = filterToAppend; 1719 1720 return 0; 1721 } 1722 return -1; 1723 } 1724 1725 int 1726 slapi_filter_test( Slapi_PBlock *pb, Slapi_Entry *e, Slapi_Filter *f, 1727 int verify_access ) 1728 { 1729 Operation *op; 1730 int rc; 1731 1732 if ( f == NULL ) { 1733 /* spec says return zero if no filter. */ 1734 return 0; 1735 } 1736 1737 if ( verify_access ) { 1738 op = pb->pb_op; 1739 if ( op == NULL ) 1740 return LDAP_PARAM_ERROR; 1741 } else { 1742 op = NULL; 1743 } 1744 1745 /* 1746 * According to acl.c it is safe to call test_filter() with 1747 * NULL arguments... 1748 */ 1749 rc = test_filter( op, e, f ); 1750 switch (rc) { 1751 case LDAP_COMPARE_TRUE: 1752 rc = 0; 1753 break; 1754 case LDAP_COMPARE_FALSE: 1755 break; 1756 case SLAPD_COMPARE_UNDEFINED: 1757 rc = LDAP_OTHER; 1758 break; 1759 case LDAP_PROTOCOL_ERROR: 1760 /* filter type unknown: spec says return -1 */ 1761 rc = -1; 1762 break; 1763 } 1764 1765 return rc; 1766 } 1767 1768 int 1769 slapi_filter_test_simple( Slapi_Entry *e, Slapi_Filter *f) 1770 { 1771 return slapi_filter_test( NULL, e, f, 0 ); 1772 } 1773 1774 int 1775 slapi_filter_apply( Slapi_Filter *f, FILTER_APPLY_FN fn, void *arg, int *error_code ) 1776 { 1777 switch ( f->f_choice ) { 1778 case LDAP_FILTER_AND: 1779 case LDAP_FILTER_NOT: 1780 case LDAP_FILTER_OR: { 1781 int rc; 1782 1783 /* 1784 * FIXME: altering f; should we use a temporary? 1785 */ 1786 for ( f = f->f_list; f != NULL; f = f->f_next ) { 1787 rc = slapi_filter_apply( f, fn, arg, error_code ); 1788 if ( rc != 0 ) { 1789 return rc; 1790 } 1791 if ( *error_code == SLAPI_FILTER_SCAN_NOMORE ) { 1792 break; 1793 } 1794 } 1795 break; 1796 } 1797 case LDAP_FILTER_EQUALITY: 1798 case LDAP_FILTER_SUBSTRINGS: 1799 case LDAP_FILTER_GE: 1800 case LDAP_FILTER_LE: 1801 case LDAP_FILTER_PRESENT: 1802 case LDAP_FILTER_APPROX: 1803 case LDAP_FILTER_EXT: 1804 *error_code = fn( f, arg ); 1805 break; 1806 default: 1807 *error_code = SLAPI_FILTER_UNKNOWN_FILTER_TYPE; 1808 } 1809 1810 if ( *error_code == SLAPI_FILTER_SCAN_NOMORE || 1811 *error_code == SLAPI_FILTER_SCAN_CONTINUE ) { 1812 return 0; 1813 } 1814 1815 return -1; 1816 } 1817 1818 int 1819 slapi_pw_find( 1820 struct berval **vals, 1821 struct berval *v ) 1822 { 1823 /* 1824 * FIXME: what's the point? 1825 */ 1826 return 1; 1827 } 1828 1829 #define MAX_HOSTNAME 512 1830 1831 char * 1832 slapi_get_hostname( void ) 1833 { 1834 char *hn = NULL; 1835 static int been_here = 0; 1836 static char *static_hn = NULL; 1837 1838 ldap_pvt_thread_mutex_lock( &slapi_hn_mutex ); 1839 if ( !been_here ) { 1840 static_hn = (char *)slapi_ch_malloc( MAX_HOSTNAME ); 1841 if ( static_hn == NULL) { 1842 slapi_log_error( SLAPI_LOG_FATAL, "slapi_get_hostname", 1843 "Cannot allocate memory for hostname\n" ); 1844 static_hn = NULL; 1845 ldap_pvt_thread_mutex_unlock( &slapi_hn_mutex ); 1846 1847 return hn; 1848 1849 } else { 1850 if ( gethostname( static_hn, MAX_HOSTNAME ) != 0 ) { 1851 slapi_log_error( SLAPI_LOG_FATAL, 1852 "SLAPI", 1853 "can't get hostname\n" ); 1854 slapi_ch_free( (void **)&static_hn ); 1855 static_hn = NULL; 1856 ldap_pvt_thread_mutex_unlock( &slapi_hn_mutex ); 1857 1858 return hn; 1859 1860 } else { 1861 been_here = 1; 1862 } 1863 } 1864 } 1865 ldap_pvt_thread_mutex_unlock( &slapi_hn_mutex ); 1866 1867 hn = ch_strdup( static_hn ); 1868 1869 return hn; 1870 } 1871 1872 /* 1873 * FIXME: this should go in an appropriate header ... 1874 */ 1875 extern int slapi_int_log_error( int level, char *subsystem, char *fmt, va_list arglist ); 1876 1877 int 1878 slapi_log_error( 1879 int severity, 1880 char *subsystem, 1881 char *fmt, 1882 ... ) 1883 { 1884 int rc = LDAP_SUCCESS; 1885 va_list arglist; 1886 1887 va_start( arglist, fmt ); 1888 rc = slapi_int_log_error( severity, subsystem, fmt, arglist ); 1889 va_end( arglist ); 1890 1891 return rc; 1892 } 1893 1894 1895 unsigned long 1896 slapi_timer_current_time( void ) 1897 { 1898 static int first_time = 1; 1899 #if !defined (_WIN32) 1900 struct timeval now; 1901 unsigned long ret; 1902 1903 ldap_pvt_thread_mutex_lock( &slapi_time_mutex ); 1904 if (first_time) { 1905 first_time = 0; 1906 gettimeofday( &base_time, NULL ); 1907 } 1908 gettimeofday( &now, NULL ); 1909 ret = ( now.tv_sec - base_time.tv_sec ) * 1000000 + 1910 (now.tv_usec - base_time.tv_usec); 1911 ldap_pvt_thread_mutex_unlock( &slapi_time_mutex ); 1912 1913 return ret; 1914 1915 /* 1916 * Ain't it better? 1917 return (slap_get_time() - starttime) * 1000000; 1918 */ 1919 #else /* _WIN32 */ 1920 LARGE_INTEGER now; 1921 1922 if ( first_time ) { 1923 first_time = 0; 1924 performance_counter_present = QueryPerformanceCounter( &base_time ); 1925 QueryPerformanceFrequency( &performance_freq ); 1926 } 1927 1928 if ( !performance_counter_present ) 1929 return 0; 1930 1931 QueryPerformanceCounter( &now ); 1932 return (1000000*(now.QuadPart-base_time.QuadPart))/performance_freq.QuadPart; 1933 #endif /* _WIN32 */ 1934 } 1935 1936 /* 1937 * FIXME ? 1938 */ 1939 unsigned long 1940 slapi_timer_get_time( char *label ) 1941 { 1942 unsigned long start = slapi_timer_current_time(); 1943 printf("%10ld %10d usec %s\n", start, 0, label); 1944 return start; 1945 } 1946 1947 /* 1948 * FIXME ? 1949 */ 1950 void 1951 slapi_timer_elapsed_time( 1952 char *label, 1953 unsigned long start ) 1954 { 1955 unsigned long stop = slapi_timer_current_time(); 1956 printf ("%10ld %10ld usec %s\n", stop, stop - start, label); 1957 } 1958 1959 void 1960 slapi_free_search_results_internal( Slapi_PBlock *pb ) 1961 { 1962 Slapi_Entry **entries; 1963 int k = 0, nEnt = 0; 1964 1965 slapi_pblock_get( pb, SLAPI_NENTRIES, &nEnt ); 1966 slapi_pblock_get( pb, SLAPI_PLUGIN_INTOP_SEARCH_ENTRIES, &entries ); 1967 if ( nEnt == 0 || entries == NULL ) { 1968 return; 1969 } 1970 1971 for ( k = 0; k < nEnt; k++ ) { 1972 slapi_entry_free( entries[k] ); 1973 entries[k] = NULL; 1974 } 1975 1976 slapi_ch_free( (void **)&entries ); 1977 } 1978 1979 int slapi_is_connection_ssl( Slapi_PBlock *pb, int *isSSL ) 1980 { 1981 if ( pb == NULL ) 1982 return LDAP_PARAM_ERROR; 1983 1984 if ( pb->pb_conn == NULL ) 1985 return LDAP_PARAM_ERROR; 1986 1987 #ifdef HAVE_TLS 1988 *isSSL = pb->pb_conn->c_is_tls; 1989 #else 1990 *isSSL = 0; 1991 #endif 1992 1993 return LDAP_SUCCESS; 1994 } 1995 1996 /* 1997 * DS 5.x compatability API follow 1998 */ 1999 2000 int slapi_attr_get_flags( const Slapi_Attr *attr, unsigned long *flags ) 2001 { 2002 AttributeType *at; 2003 2004 if ( attr == NULL ) 2005 return LDAP_PARAM_ERROR; 2006 2007 at = attr->a_desc->ad_type; 2008 2009 *flags = SLAPI_ATTR_FLAG_STD_ATTR; 2010 2011 if ( is_at_single_value( at ) ) 2012 *flags |= SLAPI_ATTR_FLAG_SINGLE; 2013 if ( is_at_operational( at ) ) 2014 *flags |= SLAPI_ATTR_FLAG_OPATTR; 2015 if ( is_at_obsolete( at ) ) 2016 *flags |= SLAPI_ATTR_FLAG_OBSOLETE; 2017 if ( is_at_collective( at ) ) 2018 *flags |= SLAPI_ATTR_FLAG_COLLECTIVE; 2019 if ( is_at_no_user_mod( at ) ) 2020 *flags |= SLAPI_ATTR_FLAG_NOUSERMOD; 2021 2022 return LDAP_SUCCESS; 2023 } 2024 2025 int slapi_attr_flag_is_set( const Slapi_Attr *attr, unsigned long flag ) 2026 { 2027 unsigned long flags; 2028 2029 if ( slapi_attr_get_flags( attr, &flags ) != 0 ) 2030 return 0; 2031 return (flags & flag) ? 1 : 0; 2032 } 2033 2034 Slapi_Attr *slapi_attr_new( void ) 2035 { 2036 Attribute *ad; 2037 2038 ad = (Attribute *)slapi_ch_calloc( 1, sizeof(*ad) ); 2039 2040 return ad; 2041 } 2042 2043 Slapi_Attr *slapi_attr_init( Slapi_Attr *a, const char *type ) 2044 { 2045 const char *text; 2046 AttributeDescription *ad = NULL; 2047 2048 if( slap_str2ad( type, &ad, &text ) != LDAP_SUCCESS ) { 2049 return NULL; 2050 } 2051 2052 a->a_desc = ad; 2053 a->a_vals = NULL; 2054 a->a_nvals = NULL; 2055 a->a_next = NULL; 2056 a->a_flags = 0; 2057 2058 return a; 2059 } 2060 2061 void slapi_attr_free( Slapi_Attr **a ) 2062 { 2063 attr_free( *a ); 2064 *a = NULL; 2065 } 2066 2067 Slapi_Attr *slapi_attr_dup( const Slapi_Attr *attr ) 2068 { 2069 return attr_dup( (Slapi_Attr *)attr ); 2070 } 2071 2072 int slapi_attr_add_value( Slapi_Attr *a, const Slapi_Value *v ) 2073 { 2074 struct berval nval; 2075 struct berval *nvalp; 2076 int rc; 2077 AttributeDescription *desc = a->a_desc; 2078 2079 if ( desc->ad_type->sat_equality && 2080 desc->ad_type->sat_equality->smr_normalize ) { 2081 rc = (*desc->ad_type->sat_equality->smr_normalize)( 2082 SLAP_MR_VALUE_OF_ATTRIBUTE_SYNTAX, 2083 desc->ad_type->sat_syntax, 2084 desc->ad_type->sat_equality, 2085 (Slapi_Value *)v, &nval, NULL ); 2086 if ( rc != LDAP_SUCCESS ) { 2087 return rc; 2088 } 2089 nvalp = &nval; 2090 } else { 2091 nvalp = NULL; 2092 } 2093 2094 rc = value_add_one( &a->a_vals, (Slapi_Value *)v ); 2095 if ( rc == 0 && nvalp != NULL ) { 2096 rc = value_add_one( &a->a_nvals, nvalp ); 2097 } else { 2098 a->a_nvals = a->a_vals; 2099 } 2100 2101 if ( nvalp != NULL ) { 2102 slapi_ch_free_string( &nval.bv_val ); 2103 } 2104 2105 return rc; 2106 } 2107 2108 int slapi_attr_type2plugin( const char *type, void **pi ) 2109 { 2110 *pi = NULL; 2111 2112 return LDAP_OTHER; 2113 } 2114 2115 int slapi_attr_get_type( const Slapi_Attr *attr, char **type ) 2116 { 2117 if ( attr == NULL ) { 2118 return LDAP_PARAM_ERROR; 2119 } 2120 2121 *type = attr->a_desc->ad_cname.bv_val; 2122 2123 return LDAP_SUCCESS; 2124 } 2125 2126 int slapi_attr_get_oid_copy( const Slapi_Attr *attr, char **oidp ) 2127 { 2128 if ( attr == NULL ) { 2129 return LDAP_PARAM_ERROR; 2130 } 2131 *oidp = attr->a_desc->ad_type->sat_oid; 2132 2133 return LDAP_SUCCESS; 2134 } 2135 2136 int slapi_attr_value_cmp( const Slapi_Attr *a, const struct berval *v1, const struct berval *v2 ) 2137 { 2138 MatchingRule *mr; 2139 int ret; 2140 int rc; 2141 const char *text; 2142 2143 mr = a->a_desc->ad_type->sat_equality; 2144 rc = value_match( &ret, a->a_desc, mr, 2145 SLAP_MR_VALUE_OF_ASSERTION_SYNTAX, 2146 (struct berval *)v1, (void *)v2, &text ); 2147 if ( rc != LDAP_SUCCESS ) 2148 return -1; 2149 2150 return ( ret == 0 ) ? 0 : -1; 2151 } 2152 2153 int slapi_attr_value_find( const Slapi_Attr *a, struct berval *v ) 2154 { 2155 int rc; 2156 2157 if ( a ->a_vals == NULL ) { 2158 return -1; 2159 } 2160 rc = attr_valfind( (Attribute *)a, SLAP_MR_VALUE_OF_ASSERTION_SYNTAX, v, 2161 NULL, NULL ); 2162 return rc == 0 ? 0 : -1; 2163 } 2164 2165 int slapi_attr_type_cmp( const char *t1, const char *t2, int opt ) 2166 { 2167 AttributeDescription *a1 = NULL; 2168 AttributeDescription *a2 = NULL; 2169 const char *text; 2170 int ret; 2171 2172 if ( slap_str2ad( t1, &a1, &text ) != LDAP_SUCCESS ) { 2173 return -1; 2174 } 2175 2176 if ( slap_str2ad( t2, &a2, &text ) != LDAP_SUCCESS ) { 2177 return 1; 2178 } 2179 2180 #define ad_base_cmp(l,r) (((l)->ad_type->sat_cname.bv_len < (r)->ad_type->sat_cname.bv_len) \ 2181 ? -1 : (((l)->ad_type->sat_cname.bv_len > (r)->ad_type->sat_cname.bv_len) \ 2182 ? 1 : strcasecmp((l)->ad_type->sat_cname.bv_val, (r)->ad_type->sat_cname.bv_val ))) 2183 2184 switch ( opt ) { 2185 case SLAPI_TYPE_CMP_EXACT: 2186 ret = ad_cmp( a1, a2 ); 2187 break; 2188 case SLAPI_TYPE_CMP_BASE: 2189 ret = ad_base_cmp( a1, a2 ); 2190 break; 2191 case SLAPI_TYPE_CMP_SUBTYPE: 2192 ret = is_ad_subtype( a2, a2 ); 2193 break; 2194 default: 2195 ret = -1; 2196 break; 2197 } 2198 2199 return ret; 2200 } 2201 2202 int slapi_attr_types_equivalent( const char *t1, const char *t2 ) 2203 { 2204 return ( slapi_attr_type_cmp( t1, t2, SLAPI_TYPE_CMP_EXACT ) == 0 ); 2205 } 2206 2207 int slapi_attr_first_value( Slapi_Attr *a, Slapi_Value **v ) 2208 { 2209 return slapi_valueset_first_value( &a->a_vals, v ); 2210 } 2211 2212 int slapi_attr_next_value( Slapi_Attr *a, int hint, Slapi_Value **v ) 2213 { 2214 return slapi_valueset_next_value( &a->a_vals, hint, v ); 2215 } 2216 2217 int slapi_attr_get_numvalues( const Slapi_Attr *a, int *numValues ) 2218 { 2219 *numValues = slapi_valueset_count( &a->a_vals ); 2220 2221 return 0; 2222 } 2223 2224 int slapi_attr_get_valueset( const Slapi_Attr *a, Slapi_ValueSet **vs ) 2225 { 2226 *vs = &((Slapi_Attr *)a)->a_vals; 2227 2228 return 0; 2229 } 2230 2231 int slapi_attr_get_bervals_copy( Slapi_Attr *a, struct berval ***vals ) 2232 { 2233 return slapi_attr_get_values( a, vals ); 2234 } 2235 2236 char *slapi_attr_syntax_normalize( const char *s ) 2237 { 2238 AttributeDescription *ad = NULL; 2239 const char *text; 2240 2241 if ( slap_str2ad( s, &ad, &text ) != LDAP_SUCCESS ) { 2242 return NULL; 2243 } 2244 2245 return ad->ad_cname.bv_val; 2246 } 2247 2248 Slapi_Value *slapi_value_new( void ) 2249 { 2250 struct berval *bv; 2251 2252 bv = (struct berval *)slapi_ch_malloc( sizeof(*bv) ); 2253 2254 return bv; 2255 } 2256 2257 Slapi_Value *slapi_value_new_berval(const struct berval *bval) 2258 { 2259 return ber_dupbv( NULL, (struct berval *)bval ); 2260 } 2261 2262 Slapi_Value *slapi_value_new_value(const Slapi_Value *v) 2263 { 2264 return slapi_value_new_berval( v ); 2265 } 2266 2267 Slapi_Value *slapi_value_new_string(const char *s) 2268 { 2269 struct berval bv; 2270 2271 bv.bv_val = (char *)s; 2272 bv.bv_len = strlen( s ); 2273 2274 return slapi_value_new_berval( &bv ); 2275 } 2276 2277 Slapi_Value *slapi_value_init(Slapi_Value *val) 2278 { 2279 val->bv_val = NULL; 2280 val->bv_len = 0; 2281 2282 return val; 2283 } 2284 2285 Slapi_Value *slapi_value_init_berval(Slapi_Value *v, struct berval *bval) 2286 { 2287 return ber_dupbv( v, bval ); 2288 } 2289 2290 Slapi_Value *slapi_value_init_string(Slapi_Value *v, const char *s) 2291 { 2292 v->bv_val = slapi_ch_strdup( s ); 2293 v->bv_len = strlen( s ); 2294 2295 return v; 2296 } 2297 2298 Slapi_Value *slapi_value_dup(const Slapi_Value *v) 2299 { 2300 return slapi_value_new_value( v ); 2301 } 2302 2303 void slapi_value_free(Slapi_Value **value) 2304 { 2305 if ( value == NULL ) { 2306 return; 2307 } 2308 2309 if ( (*value) != NULL ) { 2310 slapi_ch_free( (void **)&(*value)->bv_val ); 2311 slapi_ch_free( (void **)value ); 2312 } 2313 } 2314 2315 const struct berval *slapi_value_get_berval( const Slapi_Value *value ) 2316 { 2317 return value; 2318 } 2319 2320 Slapi_Value *slapi_value_set_berval( Slapi_Value *value, const struct berval *bval ) 2321 { 2322 if ( value == NULL ) { 2323 return NULL; 2324 } 2325 if ( value->bv_val != NULL ) { 2326 slapi_ch_free( (void **)&value->bv_val ); 2327 } 2328 slapi_value_init_berval( value, (struct berval *)bval ); 2329 2330 return value; 2331 } 2332 2333 Slapi_Value *slapi_value_set_value( Slapi_Value *value, const Slapi_Value *vfrom) 2334 { 2335 if ( value == NULL ) { 2336 return NULL; 2337 } 2338 return slapi_value_set_berval( value, vfrom ); 2339 } 2340 2341 Slapi_Value *slapi_value_set( Slapi_Value *value, void *val, unsigned long len) 2342 { 2343 if ( value == NULL ) { 2344 return NULL; 2345 } 2346 if ( value->bv_val != NULL ) { 2347 slapi_ch_free( (void **)&value->bv_val ); 2348 } 2349 value->bv_val = slapi_ch_malloc( len ); 2350 value->bv_len = len; 2351 AC_MEMCPY( value->bv_val, val, len ); 2352 2353 return value; 2354 } 2355 2356 int slapi_value_set_string(Slapi_Value *value, const char *strVal) 2357 { 2358 if ( value == NULL ) { 2359 return -1; 2360 } 2361 slapi_value_set( value, (void *)strVal, strlen( strVal ) ); 2362 return 0; 2363 } 2364 2365 int slapi_value_set_int(Slapi_Value *value, int intVal) 2366 { 2367 char buf[64]; 2368 2369 snprintf( buf, sizeof( buf ), "%d", intVal ); 2370 2371 return slapi_value_set_string( value, buf ); 2372 } 2373 2374 const char *slapi_value_get_string(const Slapi_Value *value) 2375 { 2376 if ( value == NULL ) return NULL; 2377 if ( value->bv_val == NULL ) return NULL; 2378 if ( !checkBVString( value ) ) return NULL; 2379 2380 return value->bv_val; 2381 } 2382 2383 int slapi_value_get_int(const Slapi_Value *value) 2384 { 2385 if ( value == NULL ) return 0; 2386 if ( value->bv_val == NULL ) return 0; 2387 if ( !checkBVString( value ) ) return 0; 2388 2389 return (int)strtol( value->bv_val, NULL, 10 ); 2390 } 2391 2392 unsigned int slapi_value_get_uint(const Slapi_Value *value) 2393 { 2394 if ( value == NULL ) return 0; 2395 if ( value->bv_val == NULL ) return 0; 2396 if ( !checkBVString( value ) ) return 0; 2397 2398 return (unsigned int)strtoul( value->bv_val, NULL, 10 ); 2399 } 2400 2401 long slapi_value_get_long(const Slapi_Value *value) 2402 { 2403 if ( value == NULL ) return 0; 2404 if ( value->bv_val == NULL ) return 0; 2405 if ( !checkBVString( value ) ) return 0; 2406 2407 return strtol( value->bv_val, NULL, 10 ); 2408 } 2409 2410 unsigned long slapi_value_get_ulong(const Slapi_Value *value) 2411 { 2412 if ( value == NULL ) return 0; 2413 if ( value->bv_val == NULL ) return 0; 2414 if ( !checkBVString( value ) ) return 0; 2415 2416 return strtoul( value->bv_val, NULL, 10 ); 2417 } 2418 2419 size_t slapi_value_get_length(const Slapi_Value *value) 2420 { 2421 if ( value == NULL ) 2422 return 0; 2423 2424 return (size_t) value->bv_len; 2425 } 2426 2427 int slapi_value_compare(const Slapi_Attr *a, const Slapi_Value *v1, const Slapi_Value *v2) 2428 { 2429 return slapi_attr_value_cmp( a, v1, v2 ); 2430 } 2431 2432 /* A ValueSet is a container for a BerVarray. */ 2433 Slapi_ValueSet *slapi_valueset_new( void ) 2434 { 2435 Slapi_ValueSet *vs; 2436 2437 vs = (Slapi_ValueSet *)slapi_ch_malloc( sizeof( *vs ) ); 2438 *vs = NULL; 2439 2440 return vs; 2441 } 2442 2443 void slapi_valueset_free(Slapi_ValueSet *vs) 2444 { 2445 if ( vs != NULL ) { 2446 BerVarray vp = *vs; 2447 2448 ber_bvarray_free( vp ); 2449 vp = NULL; 2450 2451 slapi_ch_free( (void **)&vp ); 2452 } 2453 } 2454 2455 void slapi_valueset_init(Slapi_ValueSet *vs) 2456 { 2457 if ( vs != NULL && *vs == NULL ) { 2458 *vs = (Slapi_ValueSet)slapi_ch_calloc( 1, sizeof(struct berval) ); 2459 (*vs)->bv_val = NULL; 2460 (*vs)->bv_len = 0; 2461 } 2462 } 2463 2464 void slapi_valueset_done(Slapi_ValueSet *vs) 2465 { 2466 BerVarray vp; 2467 2468 if ( vs == NULL ) 2469 return; 2470 2471 for ( vp = *vs; vp->bv_val != NULL; vp++ ) { 2472 vp->bv_len = 0; 2473 slapi_ch_free( (void **)&vp->bv_val ); 2474 } 2475 /* but don't free *vs or vs */ 2476 } 2477 2478 void slapi_valueset_add_value(Slapi_ValueSet *vs, const Slapi_Value *addval) 2479 { 2480 struct berval bv; 2481 2482 ber_dupbv( &bv, (Slapi_Value *)addval ); 2483 ber_bvarray_add( vs, &bv ); 2484 } 2485 2486 int slapi_valueset_first_value( Slapi_ValueSet *vs, Slapi_Value **v ) 2487 { 2488 return slapi_valueset_next_value( vs, 0, v ); 2489 } 2490 2491 int slapi_valueset_next_value( Slapi_ValueSet *vs, int index, Slapi_Value **v) 2492 { 2493 int i; 2494 BerVarray vp; 2495 2496 if ( vs == NULL ) 2497 return -1; 2498 2499 vp = *vs; 2500 2501 for ( i = 0; vp[i].bv_val != NULL; i++ ) { 2502 if ( i == index ) { 2503 *v = &vp[i]; 2504 return index + 1; 2505 } 2506 } 2507 2508 return -1; 2509 } 2510 2511 int slapi_valueset_count( const Slapi_ValueSet *vs ) 2512 { 2513 int i; 2514 BerVarray vp; 2515 2516 if ( vs == NULL ) 2517 return 0; 2518 2519 vp = *vs; 2520 2521 if ( vp == NULL ) 2522 return 0; 2523 2524 for ( i = 0; vp[i].bv_val != NULL; i++ ) 2525 ; 2526 2527 return i; 2528 2529 } 2530 2531 void slapi_valueset_set_valueset(Slapi_ValueSet *vs1, const Slapi_ValueSet *vs2) 2532 { 2533 BerVarray vp; 2534 2535 for ( vp = *vs2; vp->bv_val != NULL; vp++ ) { 2536 slapi_valueset_add_value( vs1, vp ); 2537 } 2538 } 2539 2540 int slapi_access_allowed( Slapi_PBlock *pb, Slapi_Entry *e, char *attr, 2541 struct berval *val, int access ) 2542 { 2543 int rc; 2544 slap_access_t slap_access; 2545 AttributeDescription *ad = NULL; 2546 const char *text; 2547 2548 rc = slap_str2ad( attr, &ad, &text ); 2549 if ( rc != LDAP_SUCCESS ) { 2550 return rc; 2551 } 2552 2553 /* 2554 * Whilst the SLAPI access types are arranged as a bitmask, the 2555 * documentation indicates that they are to be used separately. 2556 */ 2557 switch ( access & SLAPI_ACL_ALL ) { 2558 case SLAPI_ACL_COMPARE: 2559 slap_access = ACL_COMPARE; 2560 break; 2561 case SLAPI_ACL_SEARCH: 2562 slap_access = ACL_SEARCH; 2563 break; 2564 case SLAPI_ACL_READ: 2565 slap_access = ACL_READ; 2566 break; 2567 case SLAPI_ACL_WRITE: 2568 slap_access = ACL_WRITE; 2569 break; 2570 case SLAPI_ACL_DELETE: 2571 slap_access = ACL_WDEL; 2572 break; 2573 case SLAPI_ACL_ADD: 2574 slap_access = ACL_WADD; 2575 break; 2576 case SLAPI_ACL_SELF: /* not documented */ 2577 case SLAPI_ACL_PROXY: /* not documented */ 2578 default: 2579 return LDAP_INSUFFICIENT_ACCESS; 2580 break; 2581 } 2582 2583 assert( pb->pb_op != NULL ); 2584 2585 if ( access_allowed( pb->pb_op, e, ad, val, slap_access, NULL ) ) { 2586 return LDAP_SUCCESS; 2587 } 2588 2589 return LDAP_INSUFFICIENT_ACCESS; 2590 } 2591 2592 int slapi_acl_check_mods(Slapi_PBlock *pb, Slapi_Entry *e, LDAPMod **mods, char **errbuf) 2593 { 2594 int rc = LDAP_SUCCESS; 2595 Modifications *ml; 2596 2597 if ( pb == NULL || pb->pb_op == NULL ) 2598 return LDAP_PARAM_ERROR; 2599 2600 ml = slapi_int_ldapmods2modifications( pb->pb_op, mods ); 2601 if ( ml == NULL ) { 2602 return LDAP_OTHER; 2603 } 2604 2605 if ( rc == LDAP_SUCCESS ) { 2606 rc = acl_check_modlist( pb->pb_op, e, ml ) ? LDAP_SUCCESS : LDAP_INSUFFICIENT_ACCESS; 2607 } 2608 2609 slap_mods_free( ml, 1 ); 2610 2611 return rc; 2612 } 2613 2614 /* 2615 * Synthesise an LDAPMod array from a Modifications list to pass 2616 * to SLAPI. 2617 */ 2618 LDAPMod **slapi_int_modifications2ldapmods( Modifications *modlist ) 2619 { 2620 Modifications *ml; 2621 LDAPMod **mods, *modp; 2622 int i, j; 2623 2624 for( i = 0, ml = modlist; ml != NULL; i++, ml = ml->sml_next ) 2625 ; 2626 2627 mods = (LDAPMod **)slapi_ch_malloc( (i + 1) * sizeof(LDAPMod *) ); 2628 2629 for( i = 0, ml = modlist; ml != NULL; ml = ml->sml_next ) { 2630 mods[i] = (LDAPMod *)slapi_ch_malloc( sizeof(LDAPMod) ); 2631 modp = mods[i]; 2632 modp->mod_op = ml->sml_op | LDAP_MOD_BVALUES; 2633 if ( BER_BVISNULL( &ml->sml_type ) ) { 2634 /* may happen for internally generated mods */ 2635 assert( ml->sml_desc != NULL ); 2636 modp->mod_type = slapi_ch_strdup( ml->sml_desc->ad_cname.bv_val ); 2637 } else { 2638 modp->mod_type = slapi_ch_strdup( ml->sml_type.bv_val ); 2639 } 2640 2641 if ( ml->sml_values != NULL ) { 2642 for( j = 0; ml->sml_values[j].bv_val != NULL; j++ ) 2643 ; 2644 modp->mod_bvalues = (struct berval **)slapi_ch_malloc( (j + 1) * 2645 sizeof(struct berval *) ); 2646 for( j = 0; ml->sml_values[j].bv_val != NULL; j++ ) { 2647 modp->mod_bvalues[j] = (struct berval *)slapi_ch_malloc( 2648 sizeof(struct berval) ); 2649 ber_dupbv( modp->mod_bvalues[j], &ml->sml_values[j] ); 2650 } 2651 modp->mod_bvalues[j] = NULL; 2652 } else { 2653 modp->mod_bvalues = NULL; 2654 } 2655 i++; 2656 } 2657 2658 mods[i] = NULL; 2659 2660 return mods; 2661 } 2662 2663 /* 2664 * Convert a potentially modified array of LDAPMods back to a 2665 * Modification list. Unfortunately the values need to be 2666 * duplicated because slap_mods_check() will try to free them 2667 * before prettying (and we can't easily get out of calling 2668 * slap_mods_check() because we need normalized values). 2669 */ 2670 Modifications *slapi_int_ldapmods2modifications ( Operation *op, LDAPMod **mods ) 2671 { 2672 Modifications *modlist = NULL, **modtail; 2673 LDAPMod **modp; 2674 char textbuf[SLAP_TEXT_BUFLEN]; 2675 const char *text; 2676 2677 if ( mods == NULL ) { 2678 return NULL; 2679 } 2680 2681 modtail = &modlist; 2682 2683 for ( modp = mods; *modp != NULL; modp++ ) { 2684 Modifications *mod; 2685 LDAPMod *lmod = *modp; 2686 int i; 2687 const char *text; 2688 AttributeDescription *ad = NULL; 2689 2690 if ( slap_str2ad( lmod->mod_type, &ad, &text ) != LDAP_SUCCESS ) { 2691 continue; 2692 } 2693 2694 mod = (Modifications *) slapi_ch_malloc( sizeof(Modifications) ); 2695 mod->sml_op = lmod->mod_op & ~(LDAP_MOD_BVALUES); 2696 mod->sml_flags = 0; 2697 mod->sml_type = ad->ad_cname; 2698 mod->sml_desc = ad; 2699 mod->sml_next = NULL; 2700 2701 i = 0; 2702 if ( lmod->mod_op & LDAP_MOD_BVALUES ) { 2703 if ( lmod->mod_bvalues != NULL ) { 2704 while ( lmod->mod_bvalues[i] != NULL ) 2705 i++; 2706 } 2707 } else { 2708 if ( lmod->mod_values != NULL ) { 2709 while ( lmod->mod_values[i] != NULL ) 2710 i++; 2711 } 2712 } 2713 mod->sml_numvals = i; 2714 2715 if ( i == 0 ) { 2716 mod->sml_values = NULL; 2717 } else { 2718 mod->sml_values = (BerVarray) slapi_ch_malloc( (i + 1) * sizeof(struct berval) ); 2719 2720 /* NB: This implicitly trusts a plugin to return valid modifications. */ 2721 if ( lmod->mod_op & LDAP_MOD_BVALUES ) { 2722 for ( i = 0; lmod->mod_bvalues[i] != NULL; i++ ) { 2723 ber_dupbv( &mod->sml_values[i], lmod->mod_bvalues[i] ); 2724 } 2725 } else { 2726 for ( i = 0; lmod->mod_values[i] != NULL; i++ ) { 2727 mod->sml_values[i].bv_val = slapi_ch_strdup( lmod->mod_values[i] ); 2728 mod->sml_values[i].bv_len = strlen( lmod->mod_values[i] ); 2729 } 2730 } 2731 mod->sml_values[i].bv_val = NULL; 2732 mod->sml_values[i].bv_len = 0; 2733 } 2734 mod->sml_nvalues = NULL; 2735 2736 *modtail = mod; 2737 modtail = &mod->sml_next; 2738 } 2739 2740 if ( slap_mods_check( op, modlist, &text, textbuf, sizeof( textbuf ), NULL ) != LDAP_SUCCESS ) { 2741 slap_mods_free( modlist, 1 ); 2742 modlist = NULL; 2743 } 2744 2745 return modlist; 2746 } 2747 2748 /* 2749 * Sun ONE DS 5.x computed attribute support. Computed attributes 2750 * allow for dynamically generated operational attributes, a very 2751 * useful thing indeed. 2752 */ 2753 2754 /* 2755 * For some reason Sun don't use the normal plugin mechanism 2756 * registration path to register an "evaluator" function (an 2757 * "evaluator" is responsible for adding computed attributes; 2758 * the nomenclature is somewhat confusing). 2759 * 2760 * As such slapi_compute_add_evaluator() registers the 2761 * function directly. 2762 */ 2763 int slapi_compute_add_evaluator(slapi_compute_callback_t function) 2764 { 2765 Slapi_PBlock *pPlugin = NULL; 2766 int rc; 2767 int type = SLAPI_PLUGIN_OBJECT; 2768 2769 pPlugin = slapi_pblock_new(); 2770 if ( pPlugin == NULL ) { 2771 rc = LDAP_NO_MEMORY; 2772 goto done; 2773 } 2774 2775 rc = slapi_pblock_set( pPlugin, SLAPI_PLUGIN_TYPE, (void *)&type ); 2776 if ( rc != LDAP_SUCCESS ) { 2777 goto done; 2778 } 2779 2780 rc = slapi_pblock_set( pPlugin, SLAPI_PLUGIN_COMPUTE_EVALUATOR_FN, (void *)function ); 2781 if ( rc != LDAP_SUCCESS ) { 2782 goto done; 2783 } 2784 2785 rc = slapi_int_register_plugin( frontendDB, pPlugin ); 2786 if ( rc != 0 ) { 2787 rc = LDAP_OTHER; 2788 goto done; 2789 } 2790 2791 done: 2792 if ( rc != LDAP_SUCCESS ) { 2793 if ( pPlugin != NULL ) { 2794 slapi_pblock_destroy( pPlugin ); 2795 } 2796 return -1; 2797 } 2798 2799 return 0; 2800 } 2801 2802 /* 2803 * See notes above regarding slapi_compute_add_evaluator(). 2804 */ 2805 int slapi_compute_add_search_rewriter(slapi_search_rewrite_callback_t function) 2806 { 2807 Slapi_PBlock *pPlugin = NULL; 2808 int rc; 2809 int type = SLAPI_PLUGIN_OBJECT; 2810 2811 pPlugin = slapi_pblock_new(); 2812 if ( pPlugin == NULL ) { 2813 rc = LDAP_NO_MEMORY; 2814 goto done; 2815 } 2816 2817 rc = slapi_pblock_set( pPlugin, SLAPI_PLUGIN_TYPE, (void *)&type ); 2818 if ( rc != LDAP_SUCCESS ) { 2819 goto done; 2820 } 2821 2822 rc = slapi_pblock_set( pPlugin, SLAPI_PLUGIN_COMPUTE_SEARCH_REWRITER_FN, (void *)function ); 2823 if ( rc != LDAP_SUCCESS ) { 2824 goto done; 2825 } 2826 2827 rc = slapi_int_register_plugin( frontendDB, pPlugin ); 2828 if ( rc != 0 ) { 2829 rc = LDAP_OTHER; 2830 goto done; 2831 } 2832 2833 done: 2834 if ( rc != LDAP_SUCCESS ) { 2835 if ( pPlugin != NULL ) { 2836 slapi_pblock_destroy( pPlugin ); 2837 } 2838 return -1; 2839 } 2840 2841 return 0; 2842 } 2843 2844 /* 2845 * Call compute evaluators 2846 */ 2847 int compute_evaluator(computed_attr_context *c, char *type, Slapi_Entry *e, slapi_compute_output_t outputfn) 2848 { 2849 int rc = 0; 2850 slapi_compute_callback_t *pGetPlugin, *tmpPlugin; 2851 2852 rc = slapi_int_get_plugins( frontendDB, SLAPI_PLUGIN_COMPUTE_EVALUATOR_FN, (SLAPI_FUNC **)&tmpPlugin ); 2853 if ( rc != LDAP_SUCCESS || tmpPlugin == NULL ) { 2854 /* Nothing to do; front-end should ignore. */ 2855 return 0; 2856 } 2857 2858 for ( pGetPlugin = tmpPlugin; *pGetPlugin != NULL; pGetPlugin++ ) { 2859 /* 2860 * -1: no attribute matched requested type 2861 * 0: one attribute matched 2862 * >0: error happened 2863 */ 2864 rc = (*pGetPlugin)( c, type, e, outputfn ); 2865 if ( rc > 0 ) { 2866 break; 2867 } 2868 } 2869 2870 slapi_ch_free( (void **)&tmpPlugin ); 2871 2872 return rc; 2873 } 2874 2875 int 2876 compute_rewrite_search_filter( Slapi_PBlock *pb ) 2877 { 2878 if ( pb == NULL || pb->pb_op == NULL ) 2879 return LDAP_PARAM_ERROR; 2880 2881 return slapi_int_call_plugins( pb->pb_op->o_bd, SLAPI_PLUGIN_COMPUTE_SEARCH_REWRITER_FN, pb ); 2882 } 2883 2884 /* 2885 * New API to provide the plugin with access to the search 2886 * pblock. Have informed Sun DS team. 2887 */ 2888 int 2889 slapi_x_compute_get_pblock(computed_attr_context *c, Slapi_PBlock **pb) 2890 { 2891 if ( c == NULL ) 2892 return -1; 2893 2894 if ( c->cac_pb == NULL ) 2895 return -1; 2896 2897 *pb = c->cac_pb; 2898 2899 return 0; 2900 } 2901 2902 Slapi_Mutex *slapi_new_mutex( void ) 2903 { 2904 Slapi_Mutex *m; 2905 2906 m = (Slapi_Mutex *)slapi_ch_malloc( sizeof(*m) ); 2907 if ( ldap_pvt_thread_mutex_init( &m->mutex ) != 0 ) { 2908 slapi_ch_free( (void **)&m ); 2909 return NULL; 2910 } 2911 2912 return m; 2913 } 2914 2915 void slapi_destroy_mutex( Slapi_Mutex *mutex ) 2916 { 2917 if ( mutex != NULL ) { 2918 ldap_pvt_thread_mutex_destroy( &mutex->mutex ); 2919 slapi_ch_free( (void **)&mutex); 2920 } 2921 } 2922 2923 void slapi_lock_mutex( Slapi_Mutex *mutex ) 2924 { 2925 ldap_pvt_thread_mutex_lock( &mutex->mutex ); 2926 } 2927 2928 int slapi_unlock_mutex( Slapi_Mutex *mutex ) 2929 { 2930 return ldap_pvt_thread_mutex_unlock( &mutex->mutex ); 2931 } 2932 2933 Slapi_CondVar *slapi_new_condvar( Slapi_Mutex *mutex ) 2934 { 2935 Slapi_CondVar *cv; 2936 2937 if ( mutex == NULL ) { 2938 return NULL; 2939 } 2940 2941 cv = (Slapi_CondVar *)slapi_ch_malloc( sizeof(*cv) ); 2942 if ( ldap_pvt_thread_cond_init( &cv->cond ) != 0 ) { 2943 slapi_ch_free( (void **)&cv ); 2944 return NULL; 2945 } 2946 2947 cv->mutex = mutex->mutex; 2948 2949 return cv; 2950 } 2951 2952 void slapi_destroy_condvar( Slapi_CondVar *cvar ) 2953 { 2954 if ( cvar != NULL ) { 2955 ldap_pvt_thread_cond_destroy( &cvar->cond ); 2956 slapi_ch_free( (void **)&cvar ); 2957 } 2958 } 2959 2960 int slapi_wait_condvar( Slapi_CondVar *cvar, struct timeval *timeout ) 2961 { 2962 if ( cvar == NULL ) { 2963 return -1; 2964 } 2965 2966 return ldap_pvt_thread_cond_wait( &cvar->cond, &cvar->mutex ); 2967 } 2968 2969 int slapi_notify_condvar( Slapi_CondVar *cvar, int notify_all ) 2970 { 2971 if ( cvar == NULL ) { 2972 return -1; 2973 } 2974 2975 if ( notify_all ) { 2976 return ldap_pvt_thread_cond_broadcast( &cvar->cond ); 2977 } 2978 2979 return ldap_pvt_thread_cond_signal( &cvar->cond ); 2980 } 2981 2982 int slapi_int_access_allowed( Operation *op, 2983 Entry *entry, 2984 AttributeDescription *desc, 2985 struct berval *val, 2986 slap_access_t access, 2987 AccessControlState *state ) 2988 { 2989 int rc, slap_access = 0; 2990 slapi_acl_callback_t *pGetPlugin, *tmpPlugin; 2991 Slapi_PBlock *pb; 2992 2993 pb = SLAPI_OPERATION_PBLOCK( op ); 2994 if ( pb == NULL ) { 2995 /* internal operation */ 2996 return 1; 2997 } 2998 2999 switch ( access ) { 3000 case ACL_COMPARE: 3001 slap_access |= SLAPI_ACL_COMPARE; 3002 break; 3003 case ACL_SEARCH: 3004 slap_access |= SLAPI_ACL_SEARCH; 3005 break; 3006 case ACL_READ: 3007 slap_access |= SLAPI_ACL_READ; 3008 break; 3009 case ACL_WRITE: 3010 slap_access |= SLAPI_ACL_WRITE; 3011 break; 3012 case ACL_WDEL: 3013 slap_access |= SLAPI_ACL_DELETE; 3014 break; 3015 case ACL_WADD: 3016 slap_access |= SLAPI_ACL_ADD; 3017 break; 3018 default: 3019 break; 3020 } 3021 3022 rc = slapi_int_get_plugins( frontendDB, SLAPI_PLUGIN_ACL_ALLOW_ACCESS, (SLAPI_FUNC **)&tmpPlugin ); 3023 if ( rc != LDAP_SUCCESS || tmpPlugin == NULL ) { 3024 /* nothing to do; allowed access */ 3025 return 1; 3026 } 3027 3028 rc = 1; /* default allow policy */ 3029 3030 for ( pGetPlugin = tmpPlugin; *pGetPlugin != NULL; pGetPlugin++ ) { 3031 /* 3032 * 0 access denied 3033 * 1 access granted 3034 */ 3035 rc = (*pGetPlugin)( pb, entry, desc->ad_cname.bv_val, 3036 val, slap_access, (void *)state ); 3037 if ( rc == 0 ) { 3038 break; 3039 } 3040 } 3041 3042 slapi_ch_free( (void **)&tmpPlugin ); 3043 3044 return rc; 3045 } 3046 3047 /* 3048 * There is no documentation for this. 3049 */ 3050 int slapi_rdn2typeval( char *rdn, char **type, struct berval *bv ) 3051 { 3052 LDAPRDN lrdn; 3053 LDAPAVA *ava; 3054 int rc; 3055 char *p; 3056 3057 *type = NULL; 3058 3059 bv->bv_len = 0; 3060 bv->bv_val = NULL; 3061 3062 rc = ldap_str2rdn( rdn, &lrdn, &p, LDAP_DN_FORMAT_LDAPV3 ); 3063 if ( rc != LDAP_SUCCESS ) { 3064 return -1; 3065 } 3066 3067 if ( lrdn[1] != NULL ) { 3068 return -1; /* not single valued */ 3069 } 3070 3071 ava = lrdn[0]; 3072 3073 *type = slapi_ch_strdup( ava->la_attr.bv_val ); 3074 ber_dupbv( bv, &ava->la_value ); 3075 3076 ldap_rdnfree(lrdn); 3077 3078 return 0; 3079 } 3080 3081 char *slapi_dn_plus_rdn( const char *dn, const char *rdn ) 3082 { 3083 struct berval new_dn, parent_dn, newrdn; 3084 3085 new_dn.bv_val = NULL; 3086 3087 parent_dn.bv_val = (char *)dn; 3088 parent_dn.bv_len = strlen( dn ); 3089 3090 newrdn.bv_val = (char *)rdn; 3091 newrdn.bv_len = strlen( rdn ); 3092 3093 build_new_dn( &new_dn, &parent_dn, &newrdn, NULL ); 3094 3095 return new_dn.bv_val; 3096 } 3097 3098 int slapi_entry_schema_check( Slapi_PBlock *pb, Slapi_Entry *e ) 3099 { 3100 Backend *be_orig; 3101 const char *text; 3102 char textbuf[SLAP_TEXT_BUFLEN] = { '\0' }; 3103 size_t textlen = sizeof textbuf; 3104 int rc = LDAP_SUCCESS; 3105 3106 PBLOCK_ASSERT_OP( pb, 0 ); 3107 3108 be_orig = pb->pb_op->o_bd; 3109 3110 pb->pb_op->o_bd = select_backend( &e->e_nname, 0 ); 3111 if ( pb->pb_op->o_bd != NULL ) { 3112 rc = entry_schema_check( pb->pb_op, e, NULL, 0, 0, 3113 &text, textbuf, textlen ); 3114 } 3115 pb->pb_op->o_bd = be_orig; 3116 3117 return ( rc == LDAP_SUCCESS ) ? 0 : 1; 3118 } 3119 3120 int slapi_entry_rdn_values_present( const Slapi_Entry *e ) 3121 { 3122 LDAPDN dn; 3123 int rc; 3124 int i = 0, match = 0; 3125 3126 rc = ldap_bv2dn( &((Entry *)e)->e_name, &dn, LDAP_DN_FORMAT_LDAPV3 ); 3127 if ( rc != LDAP_SUCCESS ) { 3128 return 0; 3129 } 3130 3131 if ( dn[0] != NULL ) { 3132 LDAPRDN rdn = dn[0]; 3133 3134 for ( i = 0; rdn[i] != NULL; i++ ) { 3135 LDAPAVA *ava = &rdn[0][i]; 3136 Slapi_Attr *a = NULL; 3137 3138 if ( slapi_entry_attr_find( (Slapi_Entry *)e, ava->la_attr.bv_val, &a ) == 0 && 3139 slapi_attr_value_find( a, &ava->la_value ) == 0 ) 3140 match++; 3141 } 3142 } 3143 3144 ldap_dnfree( dn ); 3145 3146 return ( i == match ); 3147 } 3148 3149 int slapi_entry_add_rdn_values( Slapi_Entry *e ) 3150 { 3151 LDAPDN dn; 3152 int i, rc; 3153 3154 rc = ldap_bv2dn( &e->e_name, &dn, LDAP_DN_FORMAT_LDAPV3 ); 3155 if ( rc != LDAP_SUCCESS ) { 3156 return rc; 3157 } 3158 3159 if ( dn[0] != NULL ) { 3160 LDAPRDN rdn = dn[0]; 3161 struct berval *vals[2]; 3162 3163 for ( i = 0; rdn[i] != NULL; i++ ) { 3164 LDAPAVA *ava = &rdn[0][i]; 3165 Slapi_Attr *a = NULL; 3166 3167 if ( slapi_entry_attr_find( e, ava->la_attr.bv_val, &a ) == 0 && 3168 slapi_attr_value_find( a, &ava->la_value ) == 0 ) 3169 continue; 3170 3171 vals[0] = &ava->la_value; 3172 vals[1] = NULL; 3173 3174 slapi_entry_attr_merge( e, ava->la_attr.bv_val, vals ); 3175 } 3176 } 3177 3178 ldap_dnfree( dn ); 3179 3180 return LDAP_SUCCESS; 3181 } 3182 3183 const char *slapi_entry_get_uniqueid( const Slapi_Entry *e ) 3184 { 3185 Attribute *attr; 3186 3187 attr = attr_find( e->e_attrs, slap_schema.si_ad_entryUUID ); 3188 if ( attr == NULL ) { 3189 return NULL; 3190 } 3191 3192 if ( attr->a_vals != NULL && attr->a_vals[0].bv_len != 0 ) { 3193 return slapi_value_get_string( &attr->a_vals[0] ); 3194 } 3195 3196 return NULL; 3197 } 3198 3199 void slapi_entry_set_uniqueid( Slapi_Entry *e, char *uniqueid ) 3200 { 3201 struct berval bv; 3202 3203 attr_delete ( &e->e_attrs, slap_schema.si_ad_entryUUID ); 3204 3205 bv.bv_val = uniqueid; 3206 bv.bv_len = strlen( uniqueid ); 3207 attr_merge_normalize_one( e, slap_schema.si_ad_entryUUID, &bv, NULL ); 3208 } 3209 3210 LDAP *slapi_ldap_init( char *ldaphost, int ldapport, int secure, int shared ) 3211 { 3212 LDAP *ld; 3213 char *url; 3214 size_t size; 3215 int rc; 3216 3217 size = sizeof("ldap:///"); 3218 if ( secure ) { 3219 size++; 3220 } 3221 size += strlen( ldaphost ); 3222 if ( ldapport != 0 ) { 3223 size += 32; 3224 } 3225 3226 url = slapi_ch_malloc( size ); 3227 3228 if ( ldapport != 0 ) { 3229 rc = snprintf( url, size, "ldap%s://%s:%d/", ( secure ? "s" : "" ), ldaphost, ldapport ); 3230 } else { 3231 rc = snprintf( url, size, "ldap%s://%s/", ( secure ? "s" : "" ), ldaphost ); 3232 } 3233 3234 if ( rc > 0 && rc < size ) { 3235 rc = ldap_initialize( &ld, url ); 3236 } else { 3237 ld = NULL; 3238 } 3239 3240 slapi_ch_free_string( &url ); 3241 3242 return ( rc == LDAP_SUCCESS ) ? ld : NULL; 3243 } 3244 3245 void slapi_ldap_unbind( LDAP *ld ) 3246 { 3247 ldap_unbind_ext_s( ld, NULL, NULL ); 3248 } 3249 3250 int slapi_x_backend_get_flags( const Slapi_Backend *be, unsigned long *flags ) 3251 { 3252 if ( be == NULL ) 3253 return LDAP_PARAM_ERROR; 3254 3255 *flags = SLAP_DBFLAGS(be); 3256 3257 return LDAP_SUCCESS; 3258 } 3259 3260 int 3261 slapi_int_count_controls( LDAPControl **ctrls ) 3262 { 3263 size_t i; 3264 3265 if ( ctrls == NULL ) 3266 return 0; 3267 3268 for ( i = 0; ctrls[i] != NULL; i++ ) 3269 ; 3270 3271 return i; 3272 } 3273 3274 int 3275 slapi_op_abandoned( Slapi_PBlock *pb ) 3276 { 3277 if ( pb->pb_op == NULL ) 3278 return 0; 3279 3280 return ( pb->pb_op->o_abandon ); 3281 } 3282 3283 char * 3284 slapi_op_type_to_string(unsigned long type) 3285 { 3286 char *str; 3287 3288 switch (type) { 3289 case SLAPI_OPERATION_BIND: 3290 str = "bind"; 3291 break; 3292 case SLAPI_OPERATION_UNBIND: 3293 str = "unbind"; 3294 break; 3295 case SLAPI_OPERATION_SEARCH: 3296 str = "search"; 3297 break; 3298 case SLAPI_OPERATION_MODIFY: 3299 str = "modify"; 3300 break; 3301 case SLAPI_OPERATION_ADD: 3302 str = "add"; 3303 break; 3304 case SLAPI_OPERATION_DELETE: 3305 str = "delete"; 3306 break; 3307 case SLAPI_OPERATION_MODDN: 3308 str = "modrdn"; 3309 break; 3310 case SLAPI_OPERATION_COMPARE: 3311 str = "compare"; 3312 break; 3313 case SLAPI_OPERATION_ABANDON: 3314 str = "abandon"; 3315 break; 3316 case SLAPI_OPERATION_EXTENDED: 3317 str = "extended"; 3318 break; 3319 default: 3320 str = "unknown operation type"; 3321 break; 3322 } 3323 return str; 3324 } 3325 3326 unsigned long 3327 slapi_op_get_type(Slapi_Operation * op) 3328 { 3329 unsigned long type; 3330 3331 switch ( op->o_tag ) { 3332 case LDAP_REQ_BIND: 3333 type = SLAPI_OPERATION_BIND; 3334 break; 3335 case LDAP_REQ_UNBIND: 3336 type = SLAPI_OPERATION_UNBIND; 3337 break; 3338 case LDAP_REQ_SEARCH: 3339 type = SLAPI_OPERATION_SEARCH; 3340 break; 3341 case LDAP_REQ_MODIFY: 3342 type = SLAPI_OPERATION_MODIFY; 3343 break; 3344 case LDAP_REQ_ADD: 3345 type = SLAPI_OPERATION_ADD; 3346 break; 3347 case LDAP_REQ_DELETE: 3348 type = SLAPI_OPERATION_DELETE; 3349 break; 3350 case LDAP_REQ_MODRDN: 3351 type = SLAPI_OPERATION_MODDN; 3352 break; 3353 case LDAP_REQ_COMPARE: 3354 type = SLAPI_OPERATION_COMPARE; 3355 break; 3356 case LDAP_REQ_ABANDON: 3357 type = SLAPI_OPERATION_ABANDON; 3358 break; 3359 case LDAP_REQ_EXTENDED: 3360 type = SLAPI_OPERATION_EXTENDED; 3361 break; 3362 default: 3363 type = SLAPI_OPERATION_NONE; 3364 break; 3365 } 3366 return type; 3367 } 3368 3369 void slapi_be_set_readonly( Slapi_Backend *be, int readonly ) 3370 { 3371 if ( be == NULL ) 3372 return; 3373 3374 if ( readonly ) 3375 be->be_restrictops |= SLAP_RESTRICT_OP_WRITES; 3376 else 3377 be->be_restrictops &= ~(SLAP_RESTRICT_OP_WRITES); 3378 } 3379 3380 int slapi_be_get_readonly( Slapi_Backend *be ) 3381 { 3382 if ( be == NULL ) 3383 return 0; 3384 3385 return ( (be->be_restrictops & SLAP_RESTRICT_OP_WRITES) == SLAP_RESTRICT_OP_WRITES ); 3386 } 3387 3388 const char *slapi_x_be_get_updatedn( Slapi_Backend *be ) 3389 { 3390 if ( be == NULL ) 3391 return NULL; 3392 3393 return be->be_update_ndn.bv_val; 3394 } 3395 3396 Slapi_Backend *slapi_be_select( const Slapi_DN *sdn ) 3397 { 3398 Slapi_Backend *be; 3399 3400 slapi_sdn_get_ndn( sdn ); 3401 3402 be = select_backend( (struct berval *)&sdn->ndn, 0 ); 3403 3404 return be; 3405 } 3406 3407 #if 0 3408 void 3409 slapi_operation_set_flag(Slapi_Operation *op, unsigned long flag) 3410 { 3411 } 3412 3413 void 3414 slapi_operation_clear_flag(Slapi_Operation *op, unsigned long flag) 3415 { 3416 } 3417 3418 int 3419 slapi_operation_is_flag_set(Slapi_Operation *op, unsigned long flag) 3420 { 3421 } 3422 #endif 3423 3424 #endif /* LDAP_SLAPI */ 3425 3426