home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
BURKS 2
/
BURKS_AUG97.ISO
/
BURKS
/
SOFTWARE
/
LIBS
/
BPLUS11.ZIP
/
BPLUS.C
(
.txt
)
next >
Wrap
C/C++ Source or Header
|
1988-12-08
|
26KB
|
998 lines
/********************************************************************/
/* */
/* BPLUS file indexing program - Version 1.1 */
/* */
/* A "shareware program" */
/* */
/* */
/* Copyright (C) 1987 by */
/* */
/* Hunter and Associates */
/* 7050 NW Zinfandel Lane */
/* Corvallis, Oregon 97330 */
/* (503) 745 - 7186 */
/* */
/********************************************************************/
#include <stdio.h>
#include <fcntl.h>
#ifdef MSC
#include <io.h>
#endif
#include <sys/types.h> /* delete this line for Turbo C */
#include <sys/stat.h>
#include <string.h>
#include "bplus.h"
/* macros, constants, data types */
#define NULLREC (-1L)
#define FREE_BLOCK (-2)
#define ENT_ADR(pb,off) ((ENTRY*)((char*)((pb)->entries) + off))
#define ENT_SIZE(pe) strlen((pe)->key) + 1 + 2 * sizeof(RECPOS)
#define BUFDIRTY(j) (mci->cache[j].dirty)
#define BUFHANDLE(j) (mci->cache[j].handle)
#define BUFBLOCK(j) (mci->cache[j].mb)
#define BUFCOUNT(j) (mci->cache[j].count)
#define CB(j) (pci->pos[j].cblock)
#define CO(j) (pci->pos[j].coffset)
/* ATTENTION MICROSOFT USERS */
/* Microsoft changed the memcpy */
/* library routine in the C 5.0 */
/* compiler. The following macro */
/* must be used for Microsoft 5.0 */
/* and the Quick C compiler. */
#if 1
#define memcpy memmove
#endif /* if not needed */
/* declare some global variables */
IX_DESC *pci;
IX_BUFFER bt_buffer;
IX_BUFFER *mci = &bt_buffer;
BLOCK *block_ptr;
BLOCK *spare_block;
int cache_ptr = 0;
int cache_init = 0;
int split_size = IXB_SPACE;
int comb_size = (IXB_SPACE/2);
/* ================ internal procedures ================ */
static void pascal error Param((int, long));
static void pascal read_if Param((RECPOS, char *, int));
static void pascal write_if Param((int, RECPOS, char *, int));
static int pascal creat_if Param((char *));
static int pascal open_if Param((char *));
static void pascal close_if Param((int));
static void pascal update_block Param((void));
static void pascal init_cache Param((void));
static int pascal find_cache Param((RECPOS));
static int pascal new_cache Param((void));
static void pascal load_cache Param((RECPOS));
static void pascal get_cache Param((RECPOS));
static void pascal retrieve_block Param((int, RECPOS));
static int pascal prev_entry Param((int));
static int pascal next_entry Param((int));
static void pascal copy_entry Param((ENTRY *, ENTRY *));
static int pascal scan_blk Param((int));
static int pascal last_entry Param((void));
static void pascal write_free Param(( RECPOS, BLOCK *));
static RECPOS pascal get_free Param((void));
static int pascal find_block Param((ENTRY *, int *));
static void pascal movedown Param((BLOCK *, int, int));
static void pascal moveup Param((BLOCK *, int, int));
static void pascal ins_block Param((BLOCK *, ENTRY *, int));
static void pascal del_block Param((BLOCK *, int));
static void pascal split Param((int, ENTRY *, ENTRY *));
static void pascal ins_level Param((int, ENTRY *));
static int pascal insert_ix Param((ENTRY *, IX_DESC *));
static int pascal find_ix Param((ENTRY *, IX_DESC *, int));
static int pascal combineblk Param((RECPOS, int));
static void pascal replace_entry Param((ENTRY *));
static void print_blk Param((BLOCK *));
/* file I/O for B-PLUS module */
static void pascal
error(j, l)
int j;
long l;
{
static char *msg[3] = {"ERROR - CANNOT OPEN/CLOSE FILE",
"ERROR WHILE READING FILE",
"ERROR WHILE WRITING FILE"};
(void) printf("\n %s - Record Number %ld\n", msg[j], l);
exit(1);
} /* error */
static void pascal
read_if(start, buf, nwrt)
RECPOS start;
char *buf;
int nwrt;
{
long err;
err = start - lseek(pci->ixfile, start, SEEK_SET);
if (err == 0) err = nwrt - read(pci->ixfile, buf, nwrt);
if (err != 0) error(1, start);
} /* read_if */
static void pascal
write_if(handle, start, buf, nwrt)
int handle;
RECPOS start;
char *buf;
int nwrt;
{
long err;
err = start - lseek(handle, start, SEEK_SET);
if (err == 0) err = nwrt - write(handle, buf, nwrt);
if (err != 0) error(2, start);
} /* write_if */
static int pascal
creat_if(fn)
char *fn;
{
int ret;
ret = open(fn,O_RDWR|O_CREAT|O_TRUNC|O_BINARY,S_IREAD|S_IWRITE);
if (ret < 0) error(0,0L);
return (ret);
} /* creat_if */
static int pascal
open_if(fn)
char *fn;
{
int ret;
ret = open(fn,O_RDWR|O_BINARY);
if (ret < 1) error(0,0L);
return (ret);
} /* open_if */
static void pascal
close_if(handle)
int handle;
{
if(close(handle) < 0) error(2,0L);
} /* close_if */
int cdecl
open_index(name, pix, dup)
char *name;
IX_DESC *pix;
int dup;
{
pci = pix;
pci->ixfile = open_if(name);
pci->duplicate = dup;
read_if(0L,(char *)&(pix->root), (sizeof(BLOCK) + sizeof(IX_DISK)));
if (!cache_init)
{
init_cache();
cache_init = 1;
}
first_key(pix);
return ( IX_OK );
} /* open_index */
int cdecl
close_index(pix)
IX_DESC *pix;
{
int i;
write_if(pix->ixfile, 0L,(char *)&(pix->root),
(sizeof(BLOCK) + sizeof(IX_DISK)));
for (i = 0; i < NUM_BUFS; i++)
if (BUFHANDLE(i) == pix->ixfile)
{
if (BUFDIRTY(i))
{
write_if(BUFHANDLE(i),
BUFBLOCK(i).brec,
(char *) &BUFBLOCK(i),
(int) sizeof(BLOCK));
BUFDIRTY(i) = 0;
}
BUFBLOCK(i).brec = NULLREC;
}
close_if(pix->ixfile);
return( IX_OK );
} /* close_index */
int cdecl
make_index(name, pix, dup)
char *name;
IX_DESC *pix;
int dup;
{
pci = pix;
pci->ixfile = creat_if(name);
pci->duplicate = dup;
pci->dx.nl = 1;
pci->dx.ff = NULLREC;
pci->level = 0;
CO(0) = -1;
CB(0) = 0L;
pci->root.brec = 0L;
pci->root.bend = 0;
pci->root.p0 = NULLREC;
write_if(pci->ixfile, 0L,(char *)&(pix->root),
(sizeof(BLOCK) + sizeof(IX_DISK)));
if (!cache_init)
{
init_cache();
cache_init = 1;
}
first_key(pix);
return ( IX_OK );
} /* make_index */
/* cache I/O for BPLUS */
static void pascal
update_block()
{
if (block_ptr != &(pci->root))
BUFDIRTY(cache_ptr) = 1;
} /* update_block */
static void pascal
init_cache()
{
register int j;
for (j = 0; j < NUM_BUFS; j++)
{ BUFDIRTY(j) = 0;
BUFCOUNT(j) = 0;
BUFBLOCK(j).brec = NULLREC;
}
} /* init_cache */
static int pascal
find_cache(r)
RECPOS r;
{
register int j;
for (j = 0; j < NUM_BUFS; j++)
{
if((BUFBLOCK(j).brec == r) && (BUFHANDLE(j) == pci->ixfile))
{ cache_ptr = j;
return (1);
} }
return (-1);
} /* find_cache */
static int pascal
new_cache()
{
register int i;
i = (cache_ptr + 1) % NU