]> git.pld-linux.org Git - packages/rpm.git/blob - rpm-db_buffer_small.patch
- release 48 (by relup.sh)
[packages/rpm.git] / rpm-db_buffer_small.patch
1 In certain cases with BerkleyDB 5.3.x we are getting the error:
2
3 db3.c:1443: dbcursor->pget(-30999): BDB0063 DB_BUFFER_SMALL: User memory too small for return value
4
5 See https://bugs.launchpad.net/rpm/+bug/934420 for more information.
6
7 It appears to be some type of a bug in the BerkleyDB 5.3.x.  In an attempt
8 to workaround the problem, when we encounter this situation we attempt
9 to adjust the size of the mmap buffer until the call works, or we
10 end up trying 25 times.  The new size is either the updated vp->size
11 from the failed pget call, or the previous size + 4096.
12
13 If DBI debugging is enabled, additional diagnostics are printed, otherwise
14 a basic retry and success message is added to show that the failure was
15 resolved.
16
17 Signed-off-by: Mark Hatle <mark.hatle@windriver.com>
18
19 Index: rpm-5.4.9/rpmdb/rpmdb.c
20 ===================================================================
21 --- rpm-5.4.9.orig/rpmdb/rpmdb.c
22 +++ rpm-5.4.9/rpmdb/rpmdb.c
23 @@ -2212,8 +2212,12 @@ static int rpmmiGet(dbiIndex dbi, DBC * 
24         vp->flags |= DB_DBT_USERMEM;
25         rc = dbiGet(dbi, dbcursor, kp, vp, flags);
26         if (rc == DB_BUFFER_SMALL) {
27 +           int retry = 0;
28 +           size_t origlen = vp->size;
29             size_t uhlen = vp->size;
30 -           void * uh = mmap(NULL, uhlen, _prot, _flags, _fdno, _off);
31 +           void * uh;
32 +retry_get:
33 +           uh = mmap(NULL, uhlen, _prot, _flags, _fdno, _off);
34             if (uh == NULL || uh == (void *)-1)
35                 fprintf(stderr,
36                     "==> mmap(%p[%u], 0x%x, 0x%x, %d, 0x%x) error(%d): %s\n",
37 @@ -2235,6 +2239,25 @@ static int rpmmiGet(dbiIndex dbi, DBC * 
38                 if (munmap(uh, uhlen) != 0)
39                     fprintf(stderr, "==> munmap(%p[%u]) error(%d): %s\n",
40                         uh, (unsigned)uhlen, errno, strerror(errno));
41 +               /* We want to be sure to limit the number of retry attempts to avoid a loop! */
42 +               if (rc == DB_BUFFER_SMALL && retry < 25) {
43 +                  /* If we got a largr vp-size back, use that, otherwise increment the size by 1k */
44 +                  uhlen = vp->size > uhlen ? vp->size : uhlen + 4096;
45 +                  retry++;
46 +                  if (_rpmmi_debug || (dbi)->dbi_debug)
47 +                      fprintf(stderr, "==> DB_BUFFER_SMALL orig requested (%d), configured (%d), forcing larger buffer (%d), new size (%d)\n",
48 +                           origlen, vp->ulen, uhlen, vp->size);
49 +                  else
50 +                      fprintf(stderr, "==> retry (%d) db3cpget (%d)\n", retry, uhlen);
51 +                  goto retry_get;
52 +               }
53 +           }
54 +           if (retry) {
55 +               if (_rpmmi_debug || (dbi)->dbi_debug)
56 +                  fprintf(stderr, "==> success orig requested (%d), configured buffer (%d), buffer (%d), size after dbiGet (%d)\n",
57 +                       origlen, vp->ulen, uhlen, vp->size);
58 +               else
59 +                  fprintf(stderr, "==> success\n");
60             }
61         }
62      } else
63 Index: rpm-5.4.9/rpmdb/db3.c
64 ===================================================================
65 --- rpm-5.4.9.orig/rpmdb/db3.c
66 +++ rpm-5.4.9/rpmdb/db3.c
67 @@ -1442,6 +1442,8 @@
68         rc = dbcursor->pget(dbcursor, key, pkey, data, flags);
69         /* XXX DB_NOTFOUND can be returned */
70         _printit = (rc == DB_NOTFOUND ? 0 : _debug);
71 +//     /* XXX Permit DB_BUFFER_SMALL to be returned (more restrictive?) */
72 +//     _printit = (rc == DB_BUFFER_SMALL ? 0 : _printit);
73         rc = cvtdberr(dbi, "dbcursor->pget", rc, _printit);
74  #else
75         /* XXX db3 does DB_FIRST on uninitialized cursor */
76 @@ -1452,7 +1452,7 @@ assert(db != NULL);
77  #endif
78      }
79  
80 -DBIDEBUG(dbi, (stderr, "<-- %s(%p,%p,%p,%p,%p,0x%x) rc %d %s%s\n", __FUNCTION__, dbi, dbcursor, key, pkey, data, flags, rc, _DBCFLAGS(flags), _KEYDATA(key, pkey, data, NULL)));
81 +DBIDEBUG(dbi, (stderr, "<-- %s(%p,%p,%p,%p,%p,0x%x) rc %d %s%s\n", __FUNCTION__, dbi, dbcursor, key, pkey, data, flags, rc, _DBCFLAGS(flags), _KEYDATA(key, pkey, rc == DB_BUFFER_SMALL ? NULL : data, NULL)));
82      return rc;
83  }
84  /*@=mustmod@*/
This page took 0.028628 seconds and 3 git commands to generate.