Main Page | Class Hierarchy | Data Structures | Directories | File List | Data Fields | Related Pages

qam_stat.c

00001 /*-
00002  * See the file LICENSE for redistribution information.
00003  *
00004  * Copyright (c) 1999-2005
00005  *      Sleepycat Software.  All rights reserved.
00006  *
00007  * $Id: qam_stat.c,v 12.1 2005/06/16 20:23:33 bostic Exp $
00008  */
00009 
00010 #include "db_config.h"
00011 
00012 #ifndef NO_SYSTEM_INCLUDES
00013 #include <sys/types.h>
00014 
00015 #include <ctype.h>
00016 #include <string.h>
00017 #endif
00018 
00019 #include "db_int.h"
00020 #include "dbinc/db_page.h"
00021 #include "dbinc/db_shash.h"
00022 #include "dbinc/db_am.h"
00023 #include "dbinc/lock.h"
00024 #include "dbinc/mp.h"
00025 #include "dbinc/qam.h"
00026 
00027 #ifdef HAVE_STATISTICS
00028 /*
00029  * __qam_stat --
00030  *      Gather/print the qam statistics
00031  *
00032  * PUBLIC: int __qam_stat __P((DBC *, void *, u_int32_t));
00033  */
00034 int
00035 __qam_stat(dbc, spp, flags)
00036         DBC *dbc;
00037         void *spp;
00038         u_int32_t flags;
00039 {
00040         DB *dbp;
00041         DB_LOCK lock;
00042         DB_MPOOLFILE *mpf;
00043         DB_QUEUE_STAT *sp;
00044         PAGE *h;
00045         QAMDATA *qp, *ep;
00046         QMETA *meta;
00047         QUEUE *t;
00048         db_indx_t indx;
00049         db_pgno_t first, last, pgno, pg_ext, stop;
00050         u_int32_t re_len;
00051         int ret, t_ret;
00052 
00053         dbp = dbc->dbp;
00054 
00055         LOCK_INIT(lock);
00056         mpf = dbp->mpf;
00057         sp = NULL;
00058         t = dbp->q_internal;
00059 
00060         if (spp == NULL)
00061                 return (0);
00062 
00063         /* Allocate and clear the structure. */
00064         if ((ret = __os_umalloc(dbp->dbenv, sizeof(*sp), &sp)) != 0)
00065                 goto err;
00066         memset(sp, 0, sizeof(*sp));
00067 
00068         re_len = ((QUEUE *)dbp->q_internal)->re_len;
00069 
00070         /* Determine the last page of the database. */
00071         if ((ret = __db_lget(dbc, 0, t->q_meta, DB_LOCK_READ, 0, &lock)) != 0)
00072                 goto err;
00073         if ((ret = __memp_fget(mpf, &t->q_meta, 0, &meta)) != 0)
00074                 goto err;
00075 
00076         if (flags == DB_FAST_STAT || flags == DB_CACHED_COUNTS) {
00077                 sp->qs_nkeys = meta->dbmeta.key_count;
00078                 sp->qs_ndata = meta->dbmeta.record_count;
00079                 goto meta_only;
00080         }
00081 
00082         first = QAM_RECNO_PAGE(dbp, meta->first_recno);
00083         last = QAM_RECNO_PAGE(dbp, meta->cur_recno);
00084 
00085         ret = __memp_fput(mpf, meta, 0);
00086         if ((t_ret = __LPUT(dbc, lock)) != 0 && ret == 0)
00087                 ret = t_ret;
00088         if (ret != 0)
00089                 goto err;
00090 
00091         pgno = first;
00092         if (first > last)
00093                 stop = QAM_RECNO_PAGE(dbp, UINT32_MAX);
00094         else
00095                 stop = last;
00096 
00097         /* Dump each page. */
00098         pg_ext = ((QUEUE *)dbp->q_internal)->page_ext;
00099 begin:
00100         /* Walk through the pages and count. */
00101         for (; pgno <= stop; ++pgno) {
00102                 if ((ret =
00103                     __db_lget(dbc, 0, pgno, DB_LOCK_READ, 0, &lock)) != 0)
00104                         goto err;
00105                 ret = __qam_fget(dbp, &pgno, 0, &h);
00106                 if (ret == ENOENT) {
00107                         pgno += pg_ext - 1;
00108                         continue;
00109                 }
00110                 if (ret == DB_PAGE_NOTFOUND) {
00111                         if (pg_ext == 0) {
00112                                 if (pgno != stop && first != last)
00113                                         goto err;
00114                                 ret = 0;
00115                                 break;
00116                         }
00117                         pgno += (pg_ext - ((pgno - 1) % pg_ext)) - 1;
00118                         continue;
00119                 }
00120                 if (ret != 0)
00121                         goto err;
00122 
00123                 ++sp->qs_pages;
00124 
00125                 ep = (QAMDATA *)((u_int8_t *)h + dbp->pgsize - re_len);
00126                 for (indx = 0, qp = QAM_GET_RECORD(dbp, h, indx);
00127                     qp <= ep;
00128                     ++indx,  qp = QAM_GET_RECORD(dbp, h, indx)) {
00129                         if (F_ISSET(qp, QAM_VALID))
00130                                 sp->qs_ndata++;
00131                         else
00132                                 sp->qs_pgfree += re_len;
00133                 }
00134 
00135                 ret = __qam_fput(dbp, pgno, h, 0);
00136                 if ((t_ret = __LPUT(dbc, lock)) != 0 && ret == 0)
00137                         ret = t_ret;
00138                 if (ret != 0)
00139                         goto err;
00140         }
00141 
00142         if ((ret = __LPUT(dbc, lock)) != 0)
00143                 goto err;
00144         if (first > last) {
00145                 pgno = 1;
00146                 stop = last;
00147                 first = last;
00148                 goto begin;
00149         }
00150 
00151         /* Get the meta-data page. */
00152         if ((ret = __db_lget(dbc,
00153             0, t->q_meta, F_ISSET(dbp, DB_AM_RDONLY) ?
00154             DB_LOCK_READ : DB_LOCK_WRITE, 0, &lock)) != 0)
00155                 goto err;
00156         if ((ret = __memp_fget(mpf, &t->q_meta, 0, &meta)) != 0)
00157                 goto err;
00158 
00159         if (!F_ISSET(dbp, DB_AM_RDONLY))
00160                 meta->dbmeta.key_count =
00161                     meta->dbmeta.record_count = sp->qs_ndata;
00162         sp->qs_nkeys = sp->qs_ndata;
00163 
00164 meta_only:
00165         /* Get the metadata fields. */
00166         sp->qs_magic = meta->dbmeta.magic;
00167         sp->qs_version = meta->dbmeta.version;
00168         sp->qs_metaflags = meta->dbmeta.flags;
00169         sp->qs_pagesize = meta->dbmeta.pagesize;
00170         sp->qs_extentsize = meta->page_ext;
00171         sp->qs_re_len = meta->re_len;
00172         sp->qs_re_pad = meta->re_pad;
00173         sp->qs_first_recno = meta->first_recno;
00174         sp->qs_cur_recno = meta->cur_recno;
00175 
00176         /* Discard the meta-data page. */
00177         ret = __memp_fput(mpf,
00178             meta, F_ISSET(dbp, DB_AM_RDONLY) ? 0 : DB_MPOOL_DIRTY);
00179         if ((t_ret = __LPUT(dbc, lock)) != 0 && ret == 0)
00180                 ret = t_ret;
00181         if (ret != 0)
00182                 goto err;
00183 
00184         *(DB_QUEUE_STAT **)spp = sp;
00185 
00186         if (0) {
00187 err:            if (sp != NULL)
00188                         __os_ufree(dbp->dbenv, sp);
00189         }
00190 
00191         if ((t_ret = __LPUT(dbc, lock)) != 0 && ret == 0)
00192                 ret = t_ret;
00193 
00194         return (ret);
00195 }
00196 
00197 /*
00198  * __qam_stat_print --
00199  *      Display queue statistics.
00200  *
00201  * PUBLIC: int __qam_stat_print __P((DBC *, u_int32_t));
00202  */
00203 int
00204 __qam_stat_print(dbc, flags)
00205         DBC *dbc;
00206         u_int32_t flags;
00207 {
00208         DB *dbp;
00209         DB_ENV *dbenv;
00210         DB_QUEUE_STAT *sp;
00211         int ret;
00212 
00213         dbp = dbc->dbp;
00214         dbenv = dbp->dbenv;
00215 
00216         if ((ret = __qam_stat(dbc, &sp, 0)) != 0)
00217                 return (ret);
00218 
00219         if (LF_ISSET(DB_STAT_ALL)) {
00220                 __db_msg(dbenv, "%s", DB_GLOBAL(db_line));
00221                 __db_msg(dbenv, "Default Queue database information:");
00222         }
00223         __db_msg(dbenv, "%lx\tQueue magic number", (u_long)sp->qs_magic);
00224         __db_msg(dbenv, "%lu\tQueue version number", (u_long)sp->qs_version);
00225         __db_dl(dbenv, "Fixed-length record size", (u_long)sp->qs_re_len);
00226         __db_msg(dbenv, "%#x\tFixed-length record pad", (int)sp->qs_re_pad);
00227         __db_dl(dbenv,
00228             "Underlying database page size", (u_long)sp->qs_pagesize);
00229         __db_dl(dbenv,
00230             "Underlying database extent size", (u_long)sp->qs_extentsize);
00231         __db_dl(dbenv,
00232             "Number of records in the database", (u_long)sp->qs_nkeys);
00233         __db_dl(dbenv, "Number of database pages", (u_long)sp->qs_pages);
00234         __db_dl_pct(dbenv,
00235             "Number of bytes free in database pages",
00236             (u_long)sp->qs_pgfree,
00237             DB_PCT_PG(sp->qs_pgfree, sp->qs_pages, sp->qs_pagesize), "ff");
00238         __db_msg(dbenv,
00239             "%lu\tFirst undeleted record", (u_long)sp->qs_first_recno);
00240         __db_msg(dbenv,
00241             "%lu\tNext available record number", (u_long)sp->qs_cur_recno);
00242 
00243         __os_ufree(dbenv, sp);
00244 
00245         return (0);
00246 }
00247 
00248 #else /* !HAVE_STATISTICS */
00249 
00250 int
00251 __qam_stat(dbc, spp, flags)
00252         DBC *dbc;
00253         void *spp;
00254         u_int32_t flags;
00255 {
00256         COMPQUIET(spp, NULL);
00257         COMPQUIET(flags, 0);
00258 
00259         return (__db_stat_not_built(dbc->dbp->dbenv));
00260 }
00261 #endif

Generated on Sun Dec 25 12:14:44 2005 for Berkeley DB 4.4.16 by  doxygen 1.4.2