SQLite

Check-in [d7dae06fb2]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Fix issue with mem5 allocator when min request size is larger thatn 2^30.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: d7dae06fb2d57ed6b9555b774712f42077ae4155
User & Date: shaneh 2011-03-09 21:36:17.288
Context
2011-03-10
03:54
Minor clean-up of previous mem5 allocator fix. (check-in: 3643842316 user: shaneh tags: trunk)
2011-03-09
21:36
Fix issue with mem5 allocator when min request size is larger thatn 2^30. (check-in: d7dae06fb2 user: shaneh tags: trunk)
21:02
Omit unnecessary OP_Next and OP_Prev operators when uniqueness constraints guarantee that the code will only make one pass through the loop. (check-in: f000c9b2b7 user: drh tags: trunk)
Changes
Side-by-Side Diff Ignore Whitespace Patch
Changes to src/main.c.
370
371
372
373
374
375
376







377
378
379
380
381
382
383
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390







+
+
+
+
+
+
+








#if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5)
    case SQLITE_CONFIG_HEAP: {
      /* Designate a buffer for heap memory space */
      sqlite3GlobalConfig.pHeap = va_arg(ap, void*);
      sqlite3GlobalConfig.nHeap = va_arg(ap, int);
      sqlite3GlobalConfig.mnReq = va_arg(ap, int);

      if( sqlite3GlobalConfig.mnReq<1 ){
        sqlite3GlobalConfig.mnReq = 1;
      }else if( sqlite3GlobalConfig.mnReq>(1<<12) ){
        /* cap min request size at 2^12 */
        sqlite3GlobalConfig.mnReq = (1<<12);
      }

      if( sqlite3GlobalConfig.pHeap==0 ){
        /* If the heap pointer is NULL, then restore the malloc implementation
        ** back to NULL pointers too.  This will cause the malloc to go
        ** back to its default implementation when sqlite3_initialize() is
        ** run.
        */
Changes to src/mem5.c.
438
439
440
441
442
443
444
445

446
447
448
449
450
451
452
438
439
440
441
442
443
444

445
446
447
448
449
450
451
452







-
+







**             memsys5Log(4) -> 2
**             memsys5Log(5) -> 3
**             memsys5Log(8) -> 3
**             memsys5Log(9) -> 4
*/
static int memsys5Log(int iValue){
  int iLog;
  for(iLog=0; (1<<iLog)<iValue; iLog++);
  for(iLog=0; (iLog<((sizeof(int)*8)-2)) && (1<<iLog)<iValue; iLog++);
  return iLog;
}

/*
** Initialize the memory allocator.
**
** This routine is not threadsafe.  The caller must be holding a mutex
469
470
471
472
473
474
475



476

477
478
479
480
481
482
483
469
470
471
472
473
474
475
476
477
478

479
480
481
482
483
484
485
486







+
+
+
-
+







  */
  assert( (sizeof(Mem5Link)&(sizeof(Mem5Link)-1))==0 );

  nByte = sqlite3GlobalConfig.nHeap;
  zByte = (u8*)sqlite3GlobalConfig.pHeap;
  assert( zByte!=0 );  /* sqlite3_config() does not allow otherwise */

  /* boundaries on sqlite3GlobalConfig.mnReq are enforced in sqlite3_config() */
  nMinLog = sqlite3GlobalConfig.mnReq;
  assert( nMinLog>0 && nMinLog<=(1<<12) );
  nMinLog = memsys5Log(sqlite3GlobalConfig.mnReq);
  nMinLog = memsys5Log(nMinLog);
  mem5.szAtom = (1<<nMinLog);
  while( (int)sizeof(Mem5Link)>mem5.szAtom ){
    mem5.szAtom = mem5.szAtom << 1;
  }

  mem5.nBlock = (nByte / (mem5.szAtom+sizeof(u8)));
  mem5.zPool = zByte;
Changes to src/sqlite.h.in.
1356
1357
1358
1359
1360
1361
1362
1363



1364
1365
1366
1367
1368
1369
1370
1356
1357
1358
1359
1360
1361
1362

1363
1364
1365
1366
1367
1368
1369
1370
1371
1372







-
+
+
+







** ^If the first pointer (the memory pointer) is NULL, then SQLite reverts
** to using its default memory allocator (the system malloc() implementation),
** undoing any prior invocation of [SQLITE_CONFIG_MALLOC].  ^If the
** memory pointer is not NULL and either [SQLITE_ENABLE_MEMSYS3] or
** [SQLITE_ENABLE_MEMSYS5] are defined, then the alternative memory
** allocator is engaged to handle all of SQLites memory allocation needs.
** The first pointer (the memory pointer) must be aligned to an 8-byte
** boundary or subsequent behavior of SQLite will be undefined.</dd>
** boundary or subsequent behavior of SQLite will be undefined.
** The minimum allocation size is capped at 2^12. Reasonable values
** for the minimum allocation size are 2^5 through 2^8.</dd>
**
** <dt>SQLITE_CONFIG_MUTEX</dt>
** <dd> ^(This option takes a single argument which is a pointer to an
** instance of the [sqlite3_mutex_methods] structure.  The argument specifies
** alternative low-level mutex routines to be used in place
** the mutex routines built into SQLite.)^  ^SQLite makes a copy of the
** content of the [sqlite3_mutex_methods] structure before the call to
Added test/mem5.test.


































































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
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
# 2011 March 9
#
# The author disclaims copyright to this source code.  In place of
# a legal notice, here is a blessing:
#
#    May you do good and not evil.
#    May you find forgiveness for yourself and forgive others.
#    May you share freely, never taking more than you give.
#
#***********************************************************************
#
# This file contains tests of the mem5 allocation subsystem.
#

set testdir [file dirname $argv0]
source $testdir/tester.tcl

ifcapable !mem5 {
  finish_test
  return
}

# The tests in this file configure the lookaside allocator after a 
# connection is opened. This will not work if there is any "presql"
# configured (SQL run within the [sqlite3] wrapper in tester.tcl).
if {[info exists ::G(perm:presql)]} {
  finish_test
  return
}

do_test mem5-1.1 {
  catch {db close}
  sqlite3_shutdown
  sqlite3_config_heap 25000000 0
  sqlite3_config_lookaside 0 0
  sqlite3_initialize
} {SQLITE_OK}

# try with min request size = 2^30
do_test mem5-1.2 {
  catch {db close}
  sqlite3_shutdown
  sqlite3_config_heap 1 1073741824
  sqlite3_config_lookaside 0 0
  sqlite3_initialize
} {SQLITE_NOMEM}

# try with min request size = 2^30+1
# previously this was causing the memsys5Log() func to infinitely loop.
do_test mem5-1.3 {
  catch {db close}
  sqlite3_shutdown
  sqlite3_config_heap 1 1073741825
  sqlite3_config_lookaside 0 0
  sqlite3_initialize
} {SQLITE_NOMEM}

do_test mem5-1.4 {
  catch {db close}
  sqlite3_shutdown
  sqlite3_config_heap 0 0
  sqlite3_config_lookaside 0 0
  sqlite3_initialize
} {SQLITE_OK}

finish_test