1/* Do not edit: automatically built by gen_rec.awk. */
2
3#include "db_config.h"
4#include "db_int.h"
5#include "dbinc/crypto.h"
6#include "dbinc/db_page.h"
7#include "dbinc/db_dispatch.h"
8#include "dbinc/db_am.h"
9#include "dbinc/log.h"
10#include "dbinc/txn.h"
11
12/*
13 * PUBLIC: int __crdel_metasub_read __P((ENV *, DB **, void *,
14 * PUBLIC:     void *, __crdel_metasub_args **));
15 */
16int
17__crdel_metasub_read(env, dbpp, td, recbuf, argpp)
18	ENV *env;
19	DB **dbpp;
20	void *td;
21	void *recbuf;
22	__crdel_metasub_args **argpp;
23{
24	__crdel_metasub_args *argp;
25	u_int32_t uinttmp;
26	u_int8_t *bp;
27	int ret;
28
29	if ((ret = __os_malloc(env,
30	    sizeof(__crdel_metasub_args) + sizeof(DB_TXN), &argp)) != 0)
31		return (ret);
32	bp = recbuf;
33	argp->txnp = (DB_TXN *)&argp[1];
34	memset(argp->txnp, 0, sizeof(DB_TXN));
35
36	argp->txnp->td = td;
37	LOGCOPY_32(env, &argp->type, bp);
38	bp += sizeof(argp->type);
39
40	LOGCOPY_32(env, &argp->txnp->txnid, bp);
41	bp += sizeof(argp->txnp->txnid);
42
43	LOGCOPY_TOLSN(env, &argp->prev_lsn, bp);
44	bp += sizeof(DB_LSN);
45
46	LOGCOPY_32(env, &uinttmp, bp);
47	argp->fileid = (int32_t)uinttmp;
48	bp += sizeof(uinttmp);
49	if (dbpp != NULL) {
50		*dbpp = NULL;
51		ret = __dbreg_id_to_db(
52		    env, argp->txnp, dbpp, argp->fileid, 1);
53	}
54
55	LOGCOPY_32(env, &uinttmp, bp);
56	argp->pgno = (db_pgno_t)uinttmp;
57	bp += sizeof(uinttmp);
58
59	memset(&argp->page, 0, sizeof(argp->page));
60	LOGCOPY_32(env,&argp->page.size, bp);
61	bp += sizeof(u_int32_t);
62	argp->page.data = bp;
63	bp += argp->page.size;
64	if (LOG_SWAPPED(env) && dbpp != NULL && *dbpp != NULL) {
65		int t_ret;
66		if ((t_ret = __db_pageswap(*dbpp, (PAGE *)argp->page.data,
67		    (size_t)argp->page.size, NULL, 1)) != 0)
68			return (t_ret);
69	}
70
71	LOGCOPY_TOLSN(env, &argp->lsn, bp);
72	bp += sizeof(DB_LSN);
73
74	*argpp = argp;
75	return (ret);
76}
77
78/*
79 * PUBLIC: int __crdel_metasub_log __P((DB *, DB_TXN *, DB_LSN *,
80 * PUBLIC:     u_int32_t, db_pgno_t, const DBT *, DB_LSN *));
81 */
82int
83__crdel_metasub_log(dbp, txnp, ret_lsnp, flags, pgno, page, lsn)
84	DB *dbp;
85	DB_TXN *txnp;
86	DB_LSN *ret_lsnp;
87	u_int32_t flags;
88	db_pgno_t pgno;
89	const DBT *page;
90	DB_LSN * lsn;
91{
92	DBT logrec;
93	DB_LSN *lsnp, null_lsn, *rlsnp;
94	DB_TXNLOGREC *lr;
95	ENV *env;
96	u_int32_t zero, uinttmp, rectype, txn_num;
97	u_int npad;
98	u_int8_t *bp;
99	int is_durable, ret;
100
101	COMPQUIET(lr, NULL);
102
103	env = dbp->env;
104	rlsnp = ret_lsnp;
105	rectype = DB___crdel_metasub;
106	npad = 0;
107	ret = 0;
108
109	if (LF_ISSET(DB_LOG_NOT_DURABLE) ||
110	    F_ISSET(dbp, DB_AM_NOT_DURABLE)) {
111		if (txnp == NULL)
112			return (0);
113		is_durable = 0;
114	} else
115		is_durable = 1;
116
117	if (txnp == NULL) {
118		txn_num = 0;
119		lsnp = &null_lsn;
120		null_lsn.file = null_lsn.offset = 0;
121	} else {
122		if (TAILQ_FIRST(&txnp->kids) != NULL &&
123		    (ret = __txn_activekids(env, rectype, txnp)) != 0)
124			return (ret);
125		/*
126		 * We need to assign begin_lsn while holding region mutex.
127		 * That assignment is done inside the DbEnv->log_put call,
128		 * so pass in the appropriate memory location to be filled
129		 * in by the log_put code.
130		 */
131		DB_SET_TXN_LSNP(txnp, &rlsnp, &lsnp);
132		txn_num = txnp->txnid;
133	}
134
135	DB_ASSERT(env, dbp->log_filename != NULL);
136	if (dbp->log_filename->id == DB_LOGFILEID_INVALID &&
137	    (ret = __dbreg_lazy_id(dbp)) != 0)
138		return (ret);
139
140	logrec.size = sizeof(rectype) + sizeof(txn_num) + sizeof(DB_LSN)
141	    + sizeof(u_int32_t)
142	    + sizeof(u_int32_t)
143	    + sizeof(u_int32_t) + (page == NULL ? 0 : page->size)
144	    + sizeof(*lsn);
145	if (CRYPTO_ON(env)) {
146		npad = env->crypto_handle->adj_size(logrec.size);
147		logrec.size += npad;
148	}
149
150	if (is_durable || txnp == NULL) {
151		if ((ret =
152		    __os_malloc(env, logrec.size, &logrec.data)) != 0)
153			return (ret);
154	} else {
155		if ((ret = __os_malloc(env,
156		    logrec.size + sizeof(DB_TXNLOGREC), &lr)) != 0)
157			return (ret);
158#ifdef DIAGNOSTIC
159		if ((ret =
160		    __os_malloc(env, logrec.size, &logrec.data)) != 0) {
161			__os_free(env, lr);
162			return (ret);
163		}
164#else
165		logrec.data = lr->data;
166#endif
167	}
168	if (npad > 0)
169		memset((u_int8_t *)logrec.data + logrec.size - npad, 0, npad);
170
171	bp = logrec.data;
172
173	LOGCOPY_32(env, bp, &rectype);
174	bp += sizeof(rectype);
175
176	LOGCOPY_32(env, bp, &txn_num);
177	bp += sizeof(txn_num);
178
179	LOGCOPY_FROMLSN(env, bp, lsnp);
180	bp += sizeof(DB_LSN);
181
182	uinttmp = (u_int32_t)dbp->log_filename->id;
183	LOGCOPY_32(env, bp, &uinttmp);
184	bp += sizeof(uinttmp);
185
186	uinttmp = (u_int32_t)pgno;
187	LOGCOPY_32(env,bp, &uinttmp);
188	bp += sizeof(uinttmp);
189
190	if (page == NULL) {
191		zero = 0;
192		LOGCOPY_32(env, bp, &zero);
193		bp += sizeof(u_int32_t);
194	} else {
195		LOGCOPY_32(env, bp, &page->size);
196		bp += sizeof(page->size);
197		memcpy(bp, page->data, page->size);
198		if (LOG_SWAPPED(env))
199			if ((ret = __db_pageswap(dbp,
200			    (PAGE *)bp, (size_t)page->size, (DBT *)NULL, 0)) != 0)
201				return (ret);
202		bp += page->size;
203	}
204
205	if (lsn != NULL) {
206		if (txnp != NULL) {
207			LOG *lp = env->lg_handle->reginfo.primary;
208			if (LOG_COMPARE(lsn, &lp->lsn) >= 0 && (ret =
209			    __log_check_page_lsn(env, dbp, lsn)) != 0)
210				return (ret);
211		}
212		LOGCOPY_FROMLSN(env, bp, lsn);
213	} else
214		memset(bp, 0, sizeof(*lsn));
215	bp += sizeof(*lsn);
216
217	DB_ASSERT(env,
218	    (u_int32_t)(bp - (u_int8_t *)logrec.data) <= logrec.size);
219
220	if (is_durable || txnp == NULL) {
221		if ((ret = __log_put(env, rlsnp,(DBT *)&logrec,
222		    flags | DB_LOG_NOCOPY)) == 0 && txnp != NULL) {
223			*lsnp = *rlsnp;
224			if (rlsnp != ret_lsnp)
225				 *ret_lsnp = *rlsnp;
226		}
227	} else {
228		ret = 0;
229#ifdef DIAGNOSTIC
230		/*
231		 * Set the debug bit if we are going to log non-durable
232		 * transactions so they will be ignored by recovery.
233		 */
234		memcpy(lr->data, logrec.data, logrec.size);
235		rectype |= DB_debug_FLAG;
236		LOGCOPY_32(env, logrec.data, &rectype);
237
238		if (!IS_REP_CLIENT(env))
239			ret = __log_put(env,
240			    rlsnp, (DBT *)&logrec, flags | DB_LOG_NOCOPY);
241#endif
242		STAILQ_INSERT_HEAD(&txnp->logs, lr, links);
243		F_SET((TXN_DETAIL *)txnp->td, TXN_DTL_INMEMORY);
244		LSN_NOT_LOGGED(*ret_lsnp);
245	}
246
247#ifdef LOG_DIAGNOSTIC
248	if (ret != 0)
249		(void)__crdel_metasub_print(env,
250		    (DBT *)&logrec, ret_lsnp, DB_TXN_PRINT, NULL);
251#endif
252
253#ifdef DIAGNOSTIC
254	__os_free(env, logrec.data);
255#else
256	if (is_durable || txnp == NULL)
257		__os_free(env, logrec.data);
258#endif
259	return (ret);
260}
261
262/*
263 * PUBLIC: int __crdel_inmem_create_read __P((ENV *, void *,
264 * PUBLIC:     __crdel_inmem_create_args **));
265 */
266int
267__crdel_inmem_create_read(env, recbuf, argpp)
268	ENV *env;
269	void *recbuf;
270	__crdel_inmem_create_args **argpp;
271{
272	__crdel_inmem_create_args *argp;
273	u_int32_t uinttmp;
274	u_int8_t *bp;
275	int ret;
276
277	if ((ret = __os_malloc(env,
278	    sizeof(__crdel_inmem_create_args) + sizeof(DB_TXN), &argp)) != 0)
279		return (ret);
280	bp = recbuf;
281	argp->txnp = (DB_TXN *)&argp[1];
282	memset(argp->txnp, 0, sizeof(DB_TXN));
283
284	LOGCOPY_32(env, &argp->type, bp);
285	bp += sizeof(argp->type);
286
287	LOGCOPY_32(env, &argp->txnp->txnid, bp);
288	bp += sizeof(argp->txnp->txnid);
289
290	LOGCOPY_TOLSN(env, &argp->prev_lsn, bp);
291	bp += sizeof(DB_LSN);
292
293	LOGCOPY_32(env, &uinttmp, bp);
294	argp->fileid = (int32_t)uinttmp;
295	bp += sizeof(uinttmp);
296
297	memset(&argp->name, 0, sizeof(argp->name));
298	LOGCOPY_32(env,&argp->name.size, bp);
299	bp += sizeof(u_int32_t);
300	argp->name.data = bp;
301	bp += argp->name.size;
302
303	memset(&argp->fid, 0, sizeof(argp->fid));
304	LOGCOPY_32(env,&argp->fid.size, bp);
305	bp += sizeof(u_int32_t);
306	argp->fid.data = bp;
307	bp += argp->fid.size;
308
309	LOGCOPY_32(env, &argp->pgsize, bp);
310	bp += sizeof(argp->pgsize);
311
312	*argpp = argp;
313	return (ret);
314}
315
316/*
317 * PUBLIC: int __crdel_inmem_create_log __P((ENV *, DB_TXN *,
318 * PUBLIC:     DB_LSN *, u_int32_t, int32_t, const DBT *, const DBT *,
319 * PUBLIC:     u_int32_t));
320 */
321int
322__crdel_inmem_create_log(env, txnp, ret_lsnp, flags,
323    fileid, name, fid, pgsize)
324	ENV *env;
325	DB_TXN *txnp;
326	DB_LSN *ret_lsnp;
327	u_int32_t flags;
328	int32_t fileid;
329	const DBT *name;
330	const DBT *fid;
331	u_int32_t pgsize;
332{
333	DBT logrec;
334	DB_LSN *lsnp, null_lsn, *rlsnp;
335	DB_TXNLOGREC *lr;
336	u_int32_t zero, uinttmp, rectype, txn_num;
337	u_int npad;
338	u_int8_t *bp;
339	int is_durable, ret;
340
341	COMPQUIET(lr, NULL);
342
343	rlsnp = ret_lsnp;
344	rectype = DB___crdel_inmem_create;
345	npad = 0;
346	ret = 0;
347
348	if (LF_ISSET(DB_LOG_NOT_DURABLE)) {
349		if (txnp == NULL)
350			return (0);
351		is_durable = 0;
352	} else
353		is_durable = 1;
354
355	if (txnp == NULL) {
356		txn_num = 0;
357		lsnp = &null_lsn;
358		null_lsn.file = null_lsn.offset = 0;
359	} else {
360		if (TAILQ_FIRST(&txnp->kids) != NULL &&
361		    (ret = __txn_activekids(env, rectype, txnp)) != 0)
362			return (ret);
363		/*
364		 * We need to assign begin_lsn while holding region mutex.
365		 * That assignment is done inside the DbEnv->log_put call,
366		 * so pass in the appropriate memory location to be filled
367		 * in by the log_put code.
368		 */
369		DB_SET_TXN_LSNP(txnp, &rlsnp, &lsnp);
370		txn_num = txnp->txnid;
371	}
372
373	logrec.size = sizeof(rectype) + sizeof(txn_num) + sizeof(DB_LSN)
374	    + sizeof(u_int32_t)
375	    + sizeof(u_int32_t) + (name == NULL ? 0 : name->size)
376	    + sizeof(u_int32_t) + (fid == NULL ? 0 : fid->size)
377	    + sizeof(u_int32_t);
378	if (CRYPTO_ON(env)) {
379		npad = env->crypto_handle->adj_size(logrec.size);
380		logrec.size += npad;
381	}
382
383	if (is_durable || txnp == NULL) {
384		if ((ret =
385		    __os_malloc(env, logrec.size, &logrec.data)) != 0)
386			return (ret);
387	} else {
388		if ((ret = __os_malloc(env,
389		    logrec.size + sizeof(DB_TXNLOGREC), &lr)) != 0)
390			return (ret);
391#ifdef DIAGNOSTIC
392		if ((ret =
393		    __os_malloc(env, logrec.size, &logrec.data)) != 0) {
394			__os_free(env, lr);
395			return (ret);
396		}
397#else
398		logrec.data = lr->data;
399#endif
400	}
401	if (npad > 0)
402		memset((u_int8_t *)logrec.data + logrec.size - npad, 0, npad);
403
404	bp = logrec.data;
405
406	LOGCOPY_32(env, bp, &rectype);
407	bp += sizeof(rectype);
408
409	LOGCOPY_32(env, bp, &txn_num);
410	bp += sizeof(txn_num);
411
412	LOGCOPY_FROMLSN(env, bp, lsnp);
413	bp += sizeof(DB_LSN);
414
415	uinttmp = (u_int32_t)fileid;
416	LOGCOPY_32(env,bp, &uinttmp);
417	bp += sizeof(uinttmp);
418
419	if (name == NULL) {
420		zero = 0;
421		LOGCOPY_32(env, bp, &zero);
422		bp += sizeof(u_int32_t);
423	} else {
424		LOGCOPY_32(env, bp, &name->size);
425		bp += sizeof(name->size);
426		memcpy(bp, name->data, name->size);
427		bp += name->size;
428	}
429
430	if (fid == NULL) {
431		zero = 0;
432		LOGCOPY_32(env, bp, &zero);
433		bp += sizeof(u_int32_t);
434	} else {
435		LOGCOPY_32(env, bp, &fid->size);
436		bp += sizeof(fid->size);
437		memcpy(bp, fid->data, fid->size);
438		bp += fid->size;
439	}
440
441	LOGCOPY_32(env, bp, &pgsize);
442	bp += sizeof(pgsize);
443
444	DB_ASSERT(env,
445	    (u_int32_t)(bp - (u_int8_t *)logrec.data) <= logrec.size);
446
447	if (is_durable || txnp == NULL) {
448		if ((ret = __log_put(env, rlsnp,(DBT *)&logrec,
449		    flags | DB_LOG_NOCOPY)) == 0 && txnp != NULL) {
450			*lsnp = *rlsnp;
451			if (rlsnp != ret_lsnp)
452				 *ret_lsnp = *rlsnp;
453		}
454	} else {
455		ret = 0;
456#ifdef DIAGNOSTIC
457		/*
458		 * Set the debug bit if we are going to log non-durable
459		 * transactions so they will be ignored by recovery.
460		 */
461		memcpy(lr->data, logrec.data, logrec.size);
462		rectype |= DB_debug_FLAG;
463		LOGCOPY_32(env, logrec.data, &rectype);
464
465		if (!IS_REP_CLIENT(env))
466			ret = __log_put(env,
467			    rlsnp, (DBT *)&logrec, flags | DB_LOG_NOCOPY);
468#endif
469		STAILQ_INSERT_HEAD(&txnp->logs, lr, links);
470		F_SET((TXN_DETAIL *)txnp->td, TXN_DTL_INMEMORY);
471		LSN_NOT_LOGGED(*ret_lsnp);
472	}
473
474#ifdef LOG_DIAGNOSTIC
475	if (ret != 0)
476		(void)__crdel_inmem_create_print(env,
477		    (DBT *)&logrec, ret_lsnp, DB_TXN_PRINT, NULL);
478#endif
479
480#ifdef DIAGNOSTIC
481	__os_free(env, logrec.data);
482#else
483	if (is_durable || txnp == NULL)
484		__os_free(env, logrec.data);
485#endif
486	return (ret);
487}
488
489/*
490 * PUBLIC: int __crdel_inmem_rename_read __P((ENV *, void *,
491 * PUBLIC:     __crdel_inmem_rename_args **));
492 */
493int
494__crdel_inmem_rename_read(env, recbuf, argpp)
495	ENV *env;
496	void *recbuf;
497	__crdel_inmem_rename_args **argpp;
498{
499	__crdel_inmem_rename_args *argp;
500	u_int8_t *bp;
501	int ret;
502
503	if ((ret = __os_malloc(env,
504	    sizeof(__crdel_inmem_rename_args) + sizeof(DB_TXN), &argp)) != 0)
505		return (ret);
506	bp = recbuf;
507	argp->txnp = (DB_TXN *)&argp[1];
508	memset(argp->txnp, 0, sizeof(DB_TXN));
509
510	LOGCOPY_32(env, &argp->type, bp);
511	bp += sizeof(argp->type);
512
513	LOGCOPY_32(env, &argp->txnp->txnid, bp);
514	bp += sizeof(argp->txnp->txnid);
515
516	LOGCOPY_TOLSN(env, &argp->prev_lsn, bp);
517	bp += sizeof(DB_LSN);
518
519	memset(&argp->oldname, 0, sizeof(argp->oldname));
520	LOGCOPY_32(env,&argp->oldname.size, bp);
521	bp += sizeof(u_int32_t);
522	argp->oldname.data = bp;
523	bp += argp->oldname.size;
524
525	memset(&argp->newname, 0, sizeof(argp->newname));
526	LOGCOPY_32(env,&argp->newname.size, bp);
527	bp += sizeof(u_int32_t);
528	argp->newname.data = bp;
529	bp += argp->newname.size;
530
531	memset(&argp->fid, 0, sizeof(argp->fid));
532	LOGCOPY_32(env,&argp->fid.size, bp);
533	bp += sizeof(u_int32_t);
534	argp->fid.data = bp;
535	bp += argp->fid.size;
536
537	*argpp = argp;
538	return (ret);
539}
540
541/*
542 * PUBLIC: int __crdel_inmem_rename_log __P((ENV *, DB_TXN *,
543 * PUBLIC:     DB_LSN *, u_int32_t, const DBT *, const DBT *, const DBT *));
544 */
545int
546__crdel_inmem_rename_log(env, txnp, ret_lsnp, flags,
547    oldname, newname, fid)
548	ENV *env;
549	DB_TXN *txnp;
550	DB_LSN *ret_lsnp;
551	u_int32_t flags;
552	const DBT *oldname;
553	const DBT *newname;
554	const DBT *fid;
555{
556	DBT logrec;
557	DB_LSN *lsnp, null_lsn, *rlsnp;
558	DB_TXNLOGREC *lr;
559	u_int32_t zero, rectype, txn_num;
560	u_int npad;
561	u_int8_t *bp;
562	int is_durable, ret;
563
564	COMPQUIET(lr, NULL);
565
566	rlsnp = ret_lsnp;
567	rectype = DB___crdel_inmem_rename;
568	npad = 0;
569	ret = 0;
570
571	if (LF_ISSET(DB_LOG_NOT_DURABLE)) {
572		if (txnp == NULL)
573			return (0);
574		is_durable = 0;
575	} else
576		is_durable = 1;
577
578	if (txnp == NULL) {
579		txn_num = 0;
580		lsnp = &null_lsn;
581		null_lsn.file = null_lsn.offset = 0;
582	} else {
583		if (TAILQ_FIRST(&txnp->kids) != NULL &&
584		    (ret = __txn_activekids(env, rectype, txnp)) != 0)
585			return (ret);
586		/*
587		 * We need to assign begin_lsn while holding region mutex.
588		 * That assignment is done inside the DbEnv->log_put call,
589		 * so pass in the appropriate memory location to be filled
590		 * in by the log_put code.
591		 */
592		DB_SET_TXN_LSNP(txnp, &rlsnp, &lsnp);
593		txn_num = txnp->txnid;
594	}
595
596	logrec.size = sizeof(rectype) + sizeof(txn_num) + sizeof(DB_LSN)
597	    + sizeof(u_int32_t) + (oldname == NULL ? 0 : oldname->size)
598	    + sizeof(u_int32_t) + (newname == NULL ? 0 : newname->size)
599	    + sizeof(u_int32_t) + (fid == NULL ? 0 : fid->size);
600	if (CRYPTO_ON(env)) {
601		npad = env->crypto_handle->adj_size(logrec.size);
602		logrec.size += npad;
603	}
604
605	if (is_durable || txnp == NULL) {
606		if ((ret =
607		    __os_malloc(env, logrec.size, &logrec.data)) != 0)
608			return (ret);
609	} else {
610		if ((ret = __os_malloc(env,
611		    logrec.size + sizeof(DB_TXNLOGREC), &lr)) != 0)
612			return (ret);
613#ifdef DIAGNOSTIC
614		if ((ret =
615		    __os_malloc(env, logrec.size, &logrec.data)) != 0) {
616			__os_free(env, lr);
617			return (ret);
618		}
619#else
620		logrec.data = lr->data;
621#endif
622	}
623	if (npad > 0)
624		memset((u_int8_t *)logrec.data + logrec.size - npad, 0, npad);
625
626	bp = logrec.data;
627
628	LOGCOPY_32(env, bp, &rectype);
629	bp += sizeof(rectype);
630
631	LOGCOPY_32(env, bp, &txn_num);
632	bp += sizeof(txn_num);
633
634	LOGCOPY_FROMLSN(env, bp, lsnp);
635	bp += sizeof(DB_LSN);
636
637	if (oldname == NULL) {
638		zero = 0;
639		LOGCOPY_32(env, bp, &zero);
640		bp += sizeof(u_int32_t);
641	} else {
642		LOGCOPY_32(env, bp, &oldname->size);
643		bp += sizeof(oldname->size);
644		memcpy(bp, oldname->data, oldname->size);
645		bp += oldname->size;
646	}
647
648	if (newname == NULL) {
649		zero = 0;
650		LOGCOPY_32(env, bp, &zero);
651		bp += sizeof(u_int32_t);
652	} else {
653		LOGCOPY_32(env, bp, &newname->size);
654		bp += sizeof(newname->size);
655		memcpy(bp, newname->data, newname->size);
656		bp += newname->size;
657	}
658
659	if (fid == NULL) {
660		zero = 0;
661		LOGCOPY_32(env, bp, &zero);
662		bp += sizeof(u_int32_t);
663	} else {
664		LOGCOPY_32(env, bp, &fid->size);
665		bp += sizeof(fid->size);
666		memcpy(bp, fid->data, fid->size);
667		bp += fid->size;
668	}
669
670	DB_ASSERT(env,
671	    (u_int32_t)(bp - (u_int8_t *)logrec.data) <= logrec.size);
672
673	if (is_durable || txnp == NULL) {
674		if ((ret = __log_put(env, rlsnp,(DBT *)&logrec,
675		    flags | DB_LOG_NOCOPY)) == 0 && txnp != NULL) {
676			*lsnp = *rlsnp;
677			if (rlsnp != ret_lsnp)
678				 *ret_lsnp = *rlsnp;
679		}
680	} else {
681		ret = 0;
682#ifdef DIAGNOSTIC
683		/*
684		 * Set the debug bit if we are going to log non-durable
685		 * transactions so they will be ignored by recovery.
686		 */
687		memcpy(lr->data, logrec.data, logrec.size);
688		rectype |= DB_debug_FLAG;
689		LOGCOPY_32(env, logrec.data, &rectype);
690
691		if (!IS_REP_CLIENT(env))
692			ret = __log_put(env,
693			    rlsnp, (DBT *)&logrec, flags | DB_LOG_NOCOPY);
694#endif
695		STAILQ_INSERT_HEAD(&txnp->logs, lr, links);
696		F_SET((TXN_DETAIL *)txnp->td, TXN_DTL_INMEMORY);
697		LSN_NOT_LOGGED(*ret_lsnp);
698	}
699
700#ifdef LOG_DIAGNOSTIC
701	if (ret != 0)
702		(void)__crdel_inmem_rename_print(env,
703		    (DBT *)&logrec, ret_lsnp, DB_TXN_PRINT, NULL);
704#endif
705
706#ifdef DIAGNOSTIC
707	__os_free(env, logrec.data);
708#else
709	if (is_durable || txnp == NULL)
710		__os_free(env, logrec.data);
711#endif
712	return (ret);
713}
714
715/*
716 * PUBLIC: int __crdel_inmem_remove_read __P((ENV *, void *,
717 * PUBLIC:     __crdel_inmem_remove_args **));
718 */
719int
720__crdel_inmem_remove_read(env, recbuf, argpp)
721	ENV *env;
722	void *recbuf;
723	__crdel_inmem_remove_args **argpp;
724{
725	__crdel_inmem_remove_args *argp;
726	u_int8_t *bp;
727	int ret;
728
729	if ((ret = __os_malloc(env,
730	    sizeof(__crdel_inmem_remove_args) + sizeof(DB_TXN), &argp)) != 0)
731		return (ret);
732	bp = recbuf;
733	argp->txnp = (DB_TXN *)&argp[1];
734	memset(argp->txnp, 0, sizeof(DB_TXN));
735
736	LOGCOPY_32(env, &argp->type, bp);
737	bp += sizeof(argp->type);
738
739	LOGCOPY_32(env, &argp->txnp->txnid, bp);
740	bp += sizeof(argp->txnp->txnid);
741
742	LOGCOPY_TOLSN(env, &argp->prev_lsn, bp);
743	bp += sizeof(DB_LSN);
744
745	memset(&argp->name, 0, sizeof(argp->name));
746	LOGCOPY_32(env,&argp->name.size, bp);
747	bp += sizeof(u_int32_t);
748	argp->name.data = bp;
749	bp += argp->name.size;
750
751	memset(&argp->fid, 0, sizeof(argp->fid));
752	LOGCOPY_32(env,&argp->fid.size, bp);
753	bp += sizeof(u_int32_t);
754	argp->fid.data = bp;
755	bp += argp->fid.size;
756
757	*argpp = argp;
758	return (ret);
759}
760
761/*
762 * PUBLIC: int __crdel_inmem_remove_log __P((ENV *, DB_TXN *,
763 * PUBLIC:     DB_LSN *, u_int32_t, const DBT *, const DBT *));
764 */
765int
766__crdel_inmem_remove_log(env, txnp, ret_lsnp, flags,
767    name, fid)
768	ENV *env;
769	DB_TXN *txnp;
770	DB_LSN *ret_lsnp;
771	u_int32_t flags;
772	const DBT *name;
773	const DBT *fid;
774{
775	DBT logrec;
776	DB_LSN *lsnp, null_lsn, *rlsnp;
777	DB_TXNLOGREC *lr;
778	u_int32_t zero, rectype, txn_num;
779	u_int npad;
780	u_int8_t *bp;
781	int is_durable, ret;
782
783	COMPQUIET(lr, NULL);
784
785	rlsnp = ret_lsnp;
786	rectype = DB___crdel_inmem_remove;
787	npad = 0;
788	ret = 0;
789
790	if (LF_ISSET(DB_LOG_NOT_DURABLE)) {
791		if (txnp == NULL)
792			return (0);
793		is_durable = 0;
794	} else
795		is_durable = 1;
796
797	if (txnp == NULL) {
798		txn_num = 0;
799		lsnp = &null_lsn;
800		null_lsn.file = null_lsn.offset = 0;
801	} else {
802		if (TAILQ_FIRST(&txnp->kids) != NULL &&
803		    (ret = __txn_activekids(env, rectype, txnp)) != 0)
804			return (ret);
805		/*
806		 * We need to assign begin_lsn while holding region mutex.
807		 * That assignment is done inside the DbEnv->log_put call,
808		 * so pass in the appropriate memory location to be filled
809		 * in by the log_put code.
810		 */
811		DB_SET_TXN_LSNP(txnp, &rlsnp, &lsnp);
812		txn_num = txnp->txnid;
813	}
814
815	logrec.size = sizeof(rectype) + sizeof(txn_num) + sizeof(DB_LSN)
816	    + sizeof(u_int32_t) + (name == NULL ? 0 : name->size)
817	    + sizeof(u_int32_t) + (fid == NULL ? 0 : fid->size);
818	if (CRYPTO_ON(env)) {
819		npad = env->crypto_handle->adj_size(logrec.size);
820		logrec.size += npad;
821	}
822
823	if (is_durable || txnp == NULL) {
824		if ((ret =
825		    __os_malloc(env, logrec.size, &logrec.data)) != 0)
826			return (ret);
827	} else {
828		if ((ret = __os_malloc(env,
829		    logrec.size + sizeof(DB_TXNLOGREC), &lr)) != 0)
830			return (ret);
831#ifdef DIAGNOSTIC
832		if ((ret =
833		    __os_malloc(env, logrec.size, &logrec.data)) != 0) {
834			__os_free(env, lr);
835			return (ret);
836		}
837#else
838		logrec.data = lr->data;
839#endif
840	}
841	if (npad > 0)
842		memset((u_int8_t *)logrec.data + logrec.size - npad, 0, npad);
843
844	bp = logrec.data;
845
846	LOGCOPY_32(env, bp, &rectype);
847	bp += sizeof(rectype);
848
849	LOGCOPY_32(env, bp, &txn_num);
850	bp += sizeof(txn_num);
851
852	LOGCOPY_FROMLSN(env, bp, lsnp);
853	bp += sizeof(DB_LSN);
854
855	if (name == NULL) {
856		zero = 0;
857		LOGCOPY_32(env, bp, &zero);
858		bp += sizeof(u_int32_t);
859	} else {
860		LOGCOPY_32(env, bp, &name->size);
861		bp += sizeof(name->size);
862		memcpy(bp, name->data, name->size);
863		bp += name->size;
864	}
865
866	if (fid == NULL) {
867		zero = 0;
868		LOGCOPY_32(env, bp, &zero);
869		bp += sizeof(u_int32_t);
870	} else {
871		LOGCOPY_32(env, bp, &fid->size);
872		bp += sizeof(fid->size);
873		memcpy(bp, fid->data, fid->size);
874		bp += fid->size;
875	}
876
877	DB_ASSERT(env,
878	    (u_int32_t)(bp - (u_int8_t *)logrec.data) <= logrec.size);
879
880	if (is_durable || txnp == NULL) {
881		if ((ret = __log_put(env, rlsnp,(DBT *)&logrec,
882		    flags | DB_LOG_NOCOPY)) == 0 && txnp != NULL) {
883			*lsnp = *rlsnp;
884			if (rlsnp != ret_lsnp)
885				 *ret_lsnp = *rlsnp;
886		}
887	} else {
888		ret = 0;
889#ifdef DIAGNOSTIC
890		/*
891		 * Set the debug bit if we are going to log non-durable
892		 * transactions so they will be ignored by recovery.
893		 */
894		memcpy(lr->data, logrec.data, logrec.size);
895		rectype |= DB_debug_FLAG;
896		LOGCOPY_32(env, logrec.data, &rectype);
897
898		if (!IS_REP_CLIENT(env))
899			ret = __log_put(env,
900			    rlsnp, (DBT *)&logrec, flags | DB_LOG_NOCOPY);
901#endif
902		STAILQ_INSERT_HEAD(&txnp->logs, lr, links);
903		F_SET((TXN_DETAIL *)txnp->td, TXN_DTL_INMEMORY);
904		LSN_NOT_LOGGED(*ret_lsnp);
905	}
906
907#ifdef LOG_DIAGNOSTIC
908	if (ret != 0)
909		(void)__crdel_inmem_remove_print(env,
910		    (DBT *)&logrec, ret_lsnp, DB_TXN_PRINT, NULL);
911#endif
912
913#ifdef DIAGNOSTIC
914	__os_free(env, logrec.data);
915#else
916	if (is_durable || txnp == NULL)
917		__os_free(env, logrec.data);
918#endif
919	return (ret);
920}
921
922/*
923 * PUBLIC: int __crdel_init_recover __P((ENV *, DB_DISTAB *));
924 */
925int
926__crdel_init_recover(env, dtabp)
927	ENV *env;
928	DB_DISTAB *dtabp;
929{
930	int ret;
931
932	if ((ret = __db_add_recovery_int(env, dtabp,
933	    __crdel_metasub_recover, DB___crdel_metasub)) != 0)
934		return (ret);
935	if ((ret = __db_add_recovery_int(env, dtabp,
936	    __crdel_inmem_create_recover, DB___crdel_inmem_create)) != 0)
937		return (ret);
938	if ((ret = __db_add_recovery_int(env, dtabp,
939	    __crdel_inmem_rename_recover, DB___crdel_inmem_rename)) != 0)
940		return (ret);
941	if ((ret = __db_add_recovery_int(env, dtabp,
942	    __crdel_inmem_remove_recover, DB___crdel_inmem_remove)) != 0)
943		return (ret);
944	return (0);
945}
946