1/* $NetBSD: id2entry.c,v 1.2 2021/08/14 16:15:02 christos Exp $ */ 2 3/* OpenLDAP WiredTiger backend */ 4/* $OpenLDAP$ */ 5/* This work is part of OpenLDAP Software <http://www.openldap.org/>. 6 * 7 * Copyright 2002-2021 The OpenLDAP Foundation. 8 * All rights reserved. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted only as authorized by the OpenLDAP 12 * Public License. 13 * 14 * A copy of this license is available in the file LICENSE in the 15 * top-level directory of the distribution or, alternatively, at 16 * <http://www.OpenLDAP.org/license.html>. 17 */ 18/* ACKNOWLEDGEMENTS: 19 * This work was developed by HAMANO Tsukasa <hamano@osstech.co.jp> 20 * based on back-bdb for inclusion in OpenLDAP Software. 21 * WiredTiger is a product of MongoDB Inc. 22 */ 23 24#include "back-wt.h" 25#include "slap-config.h" 26 27static int wt_id2entry_put( 28 Operation *op, 29 WT_SESSION *session, 30 Entry *e, 31 const char *config ) 32{ 33 struct berval bv; 34 WT_CURSOR *cursor = NULL; 35 WT_ITEM item; 36 int rc; 37 38 rc = entry_encode( e, &bv ); 39 if(rc != LDAP_SUCCESS){ 40 return -1; 41 } 42 item.size = bv.bv_len; 43 item.data = bv.bv_val; 44 45 rc = session->open_cursor(session, WT_TABLE_ID2ENTRY, NULL, 46 config, &cursor); 47 if ( rc ) { 48 Debug( LDAP_DEBUG_ANY, 49 LDAP_XSTRING(wt_id2entry_put) 50 ": open_cursor failed: %s (%d)\n", 51 wiredtiger_strerror(rc), rc ); 52 goto done; 53 } 54 cursor->set_key(cursor, e->e_id); 55 cursor->set_value(cursor, e->e_ndn, &item); 56 rc = cursor->insert(cursor); 57 if ( rc ) { 58 Debug( LDAP_DEBUG_ANY, 59 LDAP_XSTRING(wt_id2entry_put) 60 ": insert failed: %s (%d)\n", 61 wiredtiger_strerror(rc), rc ); 62 goto done; 63 } 64 65done: 66 ch_free( bv.bv_val ); 67 if(cursor){ 68 cursor->close(cursor); 69 } 70 return rc; 71} 72 73int wt_id2entry_add( 74 Operation *op, 75 WT_SESSION *session, 76 Entry *e ) 77{ 78 return wt_id2entry_put(op, session, e, "overwrite=false"); 79} 80 81int wt_id2entry_update( 82 Operation *op, 83 WT_SESSION *session, 84 Entry *e ) 85{ 86 return wt_id2entry_put(op, session, e, "overwrite=true"); 87} 88 89int wt_id2entry_delete( 90 Operation *op, 91 WT_SESSION *session, 92 Entry *e ) 93{ 94 int rc; 95 WT_CURSOR *cursor = NULL; 96 rc = session->open_cursor(session, WT_TABLE_ID2ENTRY, NULL, 97 NULL, &cursor); 98 if ( rc ) { 99 Debug( LDAP_DEBUG_ANY, 100 LDAP_XSTRING(wt_id2entry_delete) 101 ": open_cursor failed: %s (%d)\n", 102 wiredtiger_strerror(rc), rc ); 103 goto done; 104 } 105 cursor->set_key(cursor, e->e_id); 106 rc = cursor->remove(cursor); 107 if ( rc ) { 108 Debug( LDAP_DEBUG_ANY, 109 LDAP_XSTRING(wt_id2entry_delete) 110 ": remove failed: %s (%d)\n", 111 wiredtiger_strerror(rc), rc ); 112 goto done; 113 } 114 115done: 116 if(cursor){ 117 cursor->close(cursor); 118 } 119 return rc; 120} 121 122int wt_id2entry( BackendDB *be, 123 WT_SESSION *session, 124 ID id, 125 Entry **ep ){ 126 int rc; 127 WT_CURSOR *cursor = NULL; 128 WT_ITEM item; 129 EntryHeader eh; 130 int eoff; 131 Entry *e = NULL; 132 133 rc = session->open_cursor(session, WT_TABLE_ID2ENTRY"(entry)", NULL, 134 NULL, &cursor); 135 if ( rc ) { 136 Debug( LDAP_DEBUG_ANY, 137 LDAP_XSTRING(wt_id2entry) 138 ": open_cursor failed: %s (%d)\n", 139 wiredtiger_strerror(rc), rc ); 140 goto done; 141 } 142 143 cursor->set_key(cursor, id); 144 rc = cursor->search(cursor); 145 if ( rc ) { 146 goto done; 147 } 148 149 cursor->get_value(cursor, &item); 150 rc = wt_entry_header( &item, &eh ); 151 eoff = eh.data - (char *)item.data; 152 eh.bv.bv_len = eh.nvals * sizeof( struct berval ) + item.size; 153 eh.bv.bv_val = ch_malloc( eh.bv.bv_len ); 154 memset(eh.bv.bv_val, 0xff, eh.bv.bv_len); 155 eh.data = eh.bv.bv_val + eh.nvals * sizeof( struct berval ); 156 memcpy(eh.data, item.data, item.size); 157 eh.data += eoff; 158 rc = entry_decode( &eh, &e ); 159 if ( rc ) { 160 Debug( LDAP_DEBUG_ANY, 161 LDAP_XSTRING(wt_id2entry) 162 ": entry decode error: %d\n", 163 rc ); 164 goto done; 165 } 166 e->e_id = id; 167 *ep = e; 168 169done: 170 if(cursor){ 171 cursor->close(cursor); 172 } 173 return rc; 174} 175 176int wt_entry_return( 177 Entry *e 178 ) 179{ 180 if ( !e ) { 181 return 0; 182 } 183 184 /* Our entries are allocated in two blocks; the data comes from 185 * the db itself and the Entry structure and associated pointers 186 * are allocated in entry_decode. The db data pointer is saved 187 * in e_bv. 188 */ 189 if ( e->e_bv.bv_val ) { 190#if 0 191 /* See if the DNs were changed by modrdn */ 192 if( e->e_nname.bv_val < e->e_bv.bv_val || e->e_nname.bv_val > 193 e->e_bv.bv_val + e->e_bv.bv_len ) { 194 ch_free(e->e_name.bv_val); 195 ch_free(e->e_nname.bv_val); 196 } 197#endif 198 e->e_name.bv_val = NULL; 199 e->e_nname.bv_val = NULL; 200 /* In tool mode the e_bv buffer is realloc'd, leave it alone */ 201 if( !(slapMode & SLAP_TOOL_MODE) ) { 202 free( e->e_bv.bv_val ); 203 } 204 BER_BVZERO( &e->e_bv ); 205 } 206 207 entry_free( e ); 208} 209 210int wt_entry_release( 211 Operation *op, 212 Entry *e, 213 int rw ) 214{ 215 struct wt_info *wi = (struct wt_info *) op->o_bd->be_private; 216 return wt_entry_return( e ); 217} 218 219/* 220 * return LDAP_SUCCESS IFF we can retrieve the specified entry. 221 */ 222int wt_entry_get( 223 Operation *op, 224 struct berval *ndn, 225 ObjectClass *oc, 226 AttributeDescription *at, 227 int rw, 228 Entry **ent ) 229{ 230 return 0; 231} 232 233/* 234 * Local variables: 235 * indent-tabs-mode: t 236 * tab-width: 4 237 * c-basic-offset: 4 238 * End: 239 */ 240