summaryrefslogtreecommitdiff
path: root/net/openldap20-server/files/patch-servers::slapd::back-ldbm::idl.c
blob: b41a8d9c95fbdf1b27c11775456161922d8027bc (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
#
# ITS#2348: Index corruption and crash in back-ldbm
#
--- servers/slapd/back-ldbm/idl.c.orig	Fri Aug 23 20:09:40 2002
+++ servers/slapd/back-ldbm/idl.c	Wed Mar 12 12:42:29 2003
@@ -478,9 +478,9 @@
 	 */
 
 	/* select the block to try inserting into *//* XXX linear search XXX */
-	for ( i = 0; !ID_BLOCK_NOID(idl, i) && id > ID_BLOCK_ID(idl, i); i++ )
+	for ( i = 0; !ID_BLOCK_NOID(idl, i) && id >= ID_BLOCK_ID(idl, i); i++ )
 		;	/* NULL */
-
+	
 	if ( i != 0 ) {
 		i--;
 		first = 0;
@@ -488,6 +488,11 @@
 		first = 1;
 	}
 
+	/* At this point the following condition must be true:
+	 * ID_BLOCK_ID(idl, i) <= id && id < ID_BLOCK_ID(idl, i+1)
+	 * except when i is the first or the last block.
+	 */
+
 	/* get the block */
 	cont_alloc( &k2, &key );
 	cont_id( &k2, ID_BLOCK_ID(idl, i) );
@@ -533,15 +538,16 @@
 
 		/* is there a next block? */
 		if ( !first && !ID_BLOCK_NOID(idl, i + 1) ) {
+			Datum k3;
 			/* read it in */
-			cont_alloc( &k2, &key );
-			cont_id( &k2, ID_BLOCK_ID(idl, i + 1) );
-			if ( (tmp2 = idl_fetch_one( be, db, k2 )) == NULL ) {
+			cont_alloc( &k3, &key );
+			cont_id( &k3, ID_BLOCK_ID(idl, i + 1) );
+			if ( (tmp2 = idl_fetch_one( be, db, k3 )) == NULL ) {
 				Debug( LDAP_DEBUG_ANY,
 				    "idl_insert_key: idl_fetch_one returned NULL\n",
 				    0, 0, 0 );
 				/* split the original block */
-				cont_free( &k2 );
+				cont_free( &k3 );
 				goto split;
 			}
 
@@ -552,9 +558,6 @@
 			 */
 			if (id < ID_BLOCK_ID(tmp, ID_BLOCK_NIDS(tmp) - 1)) {
 			    ID id2 = ID_BLOCK_ID(tmp, ID_BLOCK_NIDS(tmp) - 1);
-			    Datum k3;
-
-			    ldbm_datum_init( k3 );
 
 			    --ID_BLOCK_NIDS(tmp);
 			    /* This must succeed since we just popped one
@@ -562,16 +565,11 @@
 			     */
 			    rc = idl_insert( &tmp, id, db->dbc_maxids );
 
-				k3.dptr = ch_malloc(k2.dsize);
-				k3.dsize = k2.dsize;
-				AC_MEMCPY(k3.dptr, k2.dptr, k3.dsize);
-			    if ( (rc = idl_store( be, db, k3, tmp )) != 0 ) {
+			    if ( (rc = idl_store( be, db, k2, tmp )) != 0 ) {
 				Debug( LDAP_DEBUG_ANY,
 			    "idl_insert_key: idl_store returned %d\n", rc, 0, 0 );
 			    }
 
-				free( k3.dptr );
-
 			    id = id2;
 			    /* This new id will necessarily be inserted
 			     * as the first id of the next block by the
@@ -583,7 +581,7 @@
 			    db->dbc_maxids )) ) {
 			case 1:		/* id inserted first in block */
 				rc = idl_change_first( be, db, key, idl,
-				    i + 1, k2, tmp2 );
+				    i + 1, k3, tmp2 );
 				/* FALL */
 
 			case 2:		/* id already there - how? */
@@ -598,8 +596,10 @@
 					    id, 0, 0 );
 				}
 
+				cont_free( &k3 );
 				idl_free( tmp );
 				idl_free( tmp2 );
+				cont_free( &k2 );
 				idl_free( idl );
 				return( 0 );
 
@@ -607,6 +607,7 @@
 				break;
 			}
 
+			cont_free( &k3 );
 			idl_free( tmp2 );
 		}