/**************************************************************************
 * Source Id :
 *
 * $Id: mserv.h,v 1.1 2001/04/03 20:10:26 aleksandras Exp $
 *-------------------------------------------------------------------------
 * Project Notes :
 *
 *  Diamond Base
 *  ============
 *      A solid database implementation, spurred on by the continuing
 *  Metal (Lead) Base saga.
 *
 *  Project Team :
 *        A. Davison
 *        K. Lentin
 *        D. Platt
 *
 *	Project Commenced : 05-02-1993
 *
 *-------------------------------------------------------------------------
 *  Module Notes :
 *
 *  mserv.h: Header file for...
 *     A memory server. Effectively a malloc style space allocator in
 *     a file to provide variable length records.
 *
 *  Original Author : Kev
 *
 **************************************************************************/

#ifndef __MSERV_H
#define __MSERV_H

#include <fcntl.h>
#if !defined(__SASC)
#	if defined(__BORLANDC__) || defined (_MSC_VER)
#   	include <io.h>
#		include <stdio.h>
#	else
#		include <unistd.h>
#	endif
#endif
#include <iostream.h>
//#include <stdio.h>
#include <diamond/mystring.h>
#include <diamond/defs.h>
#include <diamond/dberr.h>

#define D(x) "  "#x": " << x

// The memory server is effectively a file based malloc

class memServer {
	static	const	uint32 GRAN; // = 1<<3;
	static	const	int32 END_HEADER; // = 12;
							// Size of header info at front
							// (2 del pointers + lastEntry)
	static	const	int32 EXTRA; // = 8;
							// Amount of info needed in each block
							// (size, back)
	int32		startDelChain;	// First position in delete chain
	int32		endDelChain;	// Last position in delete chain
	int32		lastEntry;		// Last block in chain
	int32		nextFree;		// End of file - needs to be signed.
	int			fd;

	void		readHeader(void);
	void		writeHeader(void);
	void		setNextFree(void);
	void		deleteBlock(int32 off);
	dbError		removeDel(const int32 off);
	int32		getChunk(int32& newSize, int32& back);

	inline
	void		checkHead(void)
				{
					if (lastEntry == -2) {
						readHeader();
						setNextFree();
					}
				}
public:
	// open constructor
	memServer(const char* name);

	// empty constructor
	memServer(void) { fd = -1; }

	bool		isOpen(void) { return (fd==-1)?false:true; }
	dbError 	createMem(const char* name);
	dbError		getString(dbData& st, const int32 off);
	dbError		putString(dbData& s, int32& off);
	dbError		delString(dbData& s, const int32 off);
	bool		checkChain(ostream& o, const bool dump = false);
	bool		checkDeleteChain(ostream& o);
	inline	void invalidate(void)
		{
			lastEntry = -2;
		}
	inline	int32 mSeek(const int32 off)
		{
			return lseek(fd, off, SEEK_SET);
		}
	inline	void mRead(int32& data, const int32 off = -1)
		{
			if (off != -1) {
				mSeek(off);
			}
			read(fd, (char*)&data, sizeof(int32));
		}
	inline	void mWrite(int32& data, const int32 off = -1)
		{
			if (off != -1) {
				mSeek(off);
			}
			write(fd, (char*)&data, sizeof(int32));
		}
};

#endif

///////////////////////////////////////////////////////////////////////////
// Revision History:
//
// $Log: mserv.h,v $
// Revision 1.1  2001/04/03 20:10:26  aleksandras
// big one 3.1 (comments later)
//
// Revision 1.20  1996/08/06  10:46:07  daz
// Changes to incorporate the 'byte' type and the Windows NT patches.
//
// Revision 1.19  1996/03/05  22:04:29  dmb
// removed ^M.
//
// Revision 1.18  1996/03/05  21:42:35  dmb
// Preliminary modifications to get Dos/Windows 0.4 portability.
//
// Revision 1.17  1996/02/01  23:02:25  dmb
// int32.
//
// Revision 1.16  1995/01/22  11:39:18  kevinl
// Fixed up invalidating. Weren't setting nextFree.
// Added #include protection.
// Added some tabs
//
// Revision 1.15  1995/01/21  06:43:55  kevinl
// Fixed up flushing/invalidating and some size issues
//
// Revision 1.14  1994/05/15  13:12:41  kevinl
// Fixed bug with empty strings being deleted in putString but off not
//     being set to 0 at the same time.
//
// Revision 1.13  1994/02/25  03:15:56  darrenp
// Changes for DOS binary compatibility.
//
// Revision 1.11  1994/02/03  05:54:19  kevinl
// Moved include files to diamond/ and fixed HAVE_MALLOC_H
//
// Revision 1.10  1993/12/23  22:58:48  kevinl
// dbErr uses dbString, autoconf stuff, moved logs, added const and size_t
//
// Revision 1.9  1993/10/24  09:14:11  kevinl
// Fixed empty string problem
//
// Revision 1.8  1993/09/26  06:40:32  kevinl
// Added dbData support
//
// Revision 1.7  1993/08/29  10:46:31  kevinl
// Include file fixes
//
// Revision 1.6  1993/07/19  11:57:13  kevinl
// Fixed up constant initialisation
//
// Revision 1.5  1993/07/11  09:42:05  kevinl
// Changed String to dbString
//
// Revision 1.4  1993/07/02  05:18:37  kevinl
// delString added
//
// Revision 1.3  1993/06/23  05:21:22  kevinl
// Mallocs are now in angular brackets
//
// Revision 1.2  1993/06/20  13:38:11  kevinl
// strclass now called mystring
//
// Revision 1.1  1993/06/18  12:28:43  kevinl
// Initial revision
//
///////////////////////////////////////////////////////////////////////////
