⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 gdk_bbp.mx

📁 这个是内存数据库中的一个管理工具
💻 MX
📖 第 1 页 / 共 5 页
字号:
	s[--len] = 't';	return s + len;}static int recover_dir(int direxists) {	if (direxists) {		/* just try; don't care about these nonvital files */		GDKunlink(BATDIR, "BBP", "bak");		GDKmove(BATDIR, "BBP", "dir", BATDIR, "BBP", "bak");	} 	return GDKmove(BAKDIR, "BBP", "dir", BATDIR, "BBP", "dir");}#define CONTINUE_IF_NO_SIZES_IN_BBP 1 /* provide backward compatibility */static int BBPrecover_subdir(void);voidBBPinit(void){	FILE *fp = GDKfilelocate("BBP", "rb", "dir");	int i = 0, max_stamp = 0, min_stamp = 0x7fffffff;	char *s, logical[1024], batname[1024], path[1024];	char *c, buf[3000];	struct stat st;	oid BBPoid = 0;	/* first move everything from SUBDIR to the BAKDIR (its parent) */	if (BBPrecover_subdir() < 0) {		GDKfatal("BBPinit: cannot properly process %s.\n", SUBDIR);	}	/* try to obtain a BBP.dir frokm bakdir */	GDKfilepath(path, BAKDIR, "BBP", "dir");	if (stat(path, &st) == 0) {		/* backup exists: *must* use it */		if (fp) fclose(fp);		fp = recover_dir(fp != NULL)?			NULL:GDKfilelocate("BBP", "rb", "dir");	} else if (fp == NULL) {		/* there was no BBP.dir either. Panic! try to use a BBP.bak */		GDKfilepath(path, BAKDIR, "BBP", "bak");		if (stat(path, &st)) {			/* no BBP.bak (nor BBP.dir or BACKUP/BBP.dir): create a new one */			GDKwarning("BBPdir: initializing BBP.\n");			if (BBPdir(0, NULL) == 0)				fp = GDKfilelocate("BBP", "rb", "dir");		} else if (GDKmove(BATDIR, "BBP", "bak", BATDIR, "BBP", "dir") == 0) {			GDKwarning("BBPinit: reverting to dir saved in BBP.bak.\n");			fp = GDKfilelocate("BBP", "rb", "dir");		}	}	if (fp == NULL) {		/* now it is time for real panic */		GDKfatal("BBPinit: could not write %s%cBBP.dir\n", BATDIR, DIR_SEP);	}	/* scan the BBP.dir to obtain its current size */	BBPlimit = BBPINIT;	BBPsize = 1;	if ((c = fgets(buf, sizeof(buf), fp)) != NULL) {		int ptrsize, oidsize;		if (sscanf(c, "%d %d", &ptrsize, &oidsize) != 2) {#ifdef CONTINUE_IF_NO_SIZES_IN_BBP			GDKwarning("old BBP without size indications: assuming compatible with current server");			GDKwarning("if this assumption is not correct, quit() immediately!");			GDKwarning("otherwise, first commit() to write a new BBP");			ptrsize = SIZEOF_SIZE_T;			oidsize = SIZEOF_OID;#else			GDKerror("old BBP without size indications");			GDKerror("add a line to the top of the BBP file with two numbers:");			GDKerror("the size (in bytes) of pointers and the size (in bytes) of OIDs\nfor the server the BBP was created with");			exit(1);#endif		} else {			c = fgets(buf, sizeof(buf), fp);		}		if (ptrsize != SIZEOF_SIZE_T || oidsize != SIZEOF_OID) {			GDKerror("database created with incompatible Mserver");			exit(1);		}		if (c != NULL) {			BBPoid = OIDread(c);			if ((c = strstr(c, "BBPsize")) != NULL) {				sscanf(c, "BBPsize=%d", &i);				i = (int) (i * BATMARGIN);				if (i > BBPlimit)					BBPlimit = i;			}		}	}	/* alloc structures; try to reserve as much space as possible */	for (;;) {		size_t size = (size_t) BBPlimit * sizeof(BBPrec);		size_t maxsize = (size_t) BBPmaxsize * sizeof(BBPrec);		BBP = (BBPrec *) GDKvmalloc(size, &maxsize, 1);		MT_alloc_register(BBP, maxsize, 'P');		if (BBP && maxsize >= BBPmaxsize * sizeof(BBPrec)) {			BBPmaxsize = (int) (maxsize / sizeof(BBPrec));			break;		}		MT_alloc_register(BBP, maxsize, 'p');		if (BBP)			GDKvmfree(BBP, size, maxsize);		if ((BBPmaxsize /= 2) < BBPlimit) {			GDKfatal("BBPinit: could not alloc arena\n");		}	}	memset(BBP, 0, BBPlimit * sizeof(BBPrec));	MT_mmap_pin(BBP, BBPlimit * sizeof(BBPrec));	/* scan the BBP.dir, and insert the BATs into the BBP */	while ((c = fgets(buf, sizeof(buf), fp)) != NULL) {		int j = 0;		while (*c != '[')			c++;		for (c++; GDKisspace(*c); c++)			;		i = atoi(c);		if (GDKisdigit(*c) && i > 0) {			for (c++; *c != ','; c++)				;			for (c++; GDKisspace(*c); c++)				;			j = atoi(c);			if (!GDKisdigit(*c))				c--;			else				for (c++; *c != ','; c++)					;		} else {			GDKerror("BBPinit: ignore line %s\n", buf);			continue;		}		if (i >= BBPsize) {			BBPsize = i + 1;			if (BBPsize >= BBPlimit)				BBPextend(BATMARGIN, FALSE);		}		strcpy(batname, BBPparse(&c));		BBP_status_set(i, BBPEXISTING | (j & ~(BBPLOADED | BBPNEW)), "BBPinit");		BBP_physical(i) = GDKstrdup(BBPparse(&c));		BBP_lastused(i) = BBPLASTUSED(atoi(BBPparse(&c)));		if (BBP_lastused(i) > max_stamp)			max_stamp = BBP_lastused(i);		if (BBP_lastused(i) < min_stamp)			min_stamp = BBP_lastused(i);		BBP_refs(i) = 0;		BBP_lrefs(i) = 1;	/* any BAT we encounter here is persistent, so has a logical reference */		c = strchr(batname, '~');		if (c && c == batname) {			s = BBPtmpname(logical, 64, i);		} else {			if (c)				*c = 0;			strcpy(logical, batname);			s = logical;			j++;		}		/* the backup of the logical name is set too */		BBP_logical(i) = GDKstrdup(s);		BBP[ABS(i)].bak[0] = NULL;		BBP[ABS(i)].bak[1] = NULL;		if (BBPtmpcheck(s)) /* only backup temp names */			BBP[ABS(i)].bak[(i)<0] = BBP_logical(i);		i = -i;		if (c && c[1]) {			BBP_logical(i) = GDKstrdup(c + 1);			/* only backup temp names */			if (BBPtmpcheck(BBP_logical(i))) 				BBP[ABS(i)].bak[(i)<0] = BBP_logical(i);			j++;		} else {			BBP_logical(i) = NULL;		}	}	fclose(fp);	/* normalize saved LRU stamps */	if (min_stamp <= max_stamp) {		for (i = 1; i < BBPsize; i++)			if (BBPvalid(i))				BBP_lastused(i) -= min_stamp;		BBPsetstamp(max_stamp - min_stamp);	}	BBPinitcache();	/* init hash table */	BBPinithash();	BBP_notrim = 0;	if (BBPoid == 0) {		OIDseed(OIDrand());	/* if not yet done, init oid */	}	OIDbase(BBPoid);	/* will call BBPrecover if needed */	if (BBPprepare(0)) {		GDKfatal("BBPinit: cannot properly process %s.\n", BAKDIR);	}	/* cleanup any leftovers (must be done after BBPrecover) */	BBPdiskscan();}@}@- During the exit phase all non-persistent BATs are removed.Upon exit the status of the BBP tables is saved on disk.This function is called once and during the shutdown of theserver. Since shutdown may be issued from any thread (dangerous)it may lead to interference in a parallel session.@{@cvoidBBPexit(void){	bat i;	if (!BBP)		return;		/* AARGH */	BBPlock("BBPexit");	/* stop all threads ever touching more descriptors */	/* free all memory (just for leak-checking in Purify) */	for (i = 0; i < BBPsize; i++) {		if (BBPvalid(i)) {			BAT *b = BBP_cache(i);			if (b) {				if (VIEWparent(b))					VIEWdestroy(b);				else					BATfree(b);			}			BBPuncacheit_(i, TRUE);			if (BBP_logical(i) != BBP[ABS(i)].bak[(i)<0])				GDKfree(BBP[ABS(i)].bak[(i)<0]);			BBP[ABS(i)].bak[(i)<0] = NULL;			GDKfree(BBP_logical(i));			BBP_logical(i) = NULL;		}		if (BBP_physical(i)) {			GDKfree(BBP_physical(i));			BBP_physical(i) = NULL;		}	}	GDKfree(BBP_hash);	BBP_hash = 0;}@}@-The routine @%BBPdir@ creates the BAT pool dictionary file. It includes some information about the current state of affair in the pool.The location in the buffer pool is saved for later use as well.This is merely done for ease of debugging and of no importance to front-ends.The tail of non-used entries is reclaimed as well. @{@cstatic intnew_bbpentry(stream *s, bat i){	int r = stream_printf(s, "[  %d, %d, %s",			      (int) i, BBP_status(i) & BBPPERSISTENT, BBPname(i));	if (r < 0)		return r;	if (BBPvalid(-i)) {		r = stream_printf(s, "~%s", BBPname(-i));		if (r < 0)			return r;	}	return stream_printf(s, ", %s, %d ]\n", BBP_physical(i), BBP_lastused(i));}intBBPdir(int cnt, bat *subcommit){	FILE *fp = NULL;	stream *s = NULL;	bat i=0, j=1;	if (GDKdebug & 17)		THRprintf(GDKout, "#BBPdir: writing BBP.dir (%d bats).\n", (int) BBPsize);	IODEBUG {		THRprintf(GDKout, "#BBPdir start oid=");		OIDwrite(GDKout);		THRprintf(GDKout, "\n");	}	fp = (FILE *) GDKfilelocate("BBP", "wb", "dir");	if (fp)		s = file_wastream(fp, "BBP.dir");	if (s && 	    stream_printf(s, "%d %d\n", SIZEOF_SIZE_T, SIZEOF_OID) >= 0 &&	    OIDwrite(s) == 0 &&	    stream_printf(s, " BBPsize=%d\n", (int) BBPsize) >= 0)	{		for (i = 1; i < BBPsize; i++) {			int mask = BBPPERSISTENT; /* BBP.dir consists of all persisnet bats */			/* but for subcommits, all except the bats in the list retain their existent mode */			if (subcommit) {				while(j < cnt && subcommit[j] < i) j++;  				if (j < cnt && subcommit[j] != i) mask = BBPEXISTING;			}			/* write the entry */			if (BBP_status(i) & mask) { 				if (new_bbpentry(s, i) < 0) break;				IODEBUG new_bbpentry(GDKerr, i);			}		}	}	if (s) {		stream_close(s);		stream_destroy(s);	} else if (fp) {		fclose(fp);	}	IODEBUG THRprintf(GDKout, "#BBPdir end\n");	if (i < BBPsize) {		GDKsyserror("BBPdir failed:\n");		return -1;	}	return 0;}@}@+ BBP Readonly InterfaceThese interface functions do not change the BBP tables. If they onlyaccess one specific BAT, the called must have ensured that no other threadis modifying that BAT, therefore such functions do not need locking.@{@- BBP index lookup by BAT name:@cstatic INLINE batBBP_find(str nme, int lock){	bat i = BBPnamecheck(nme);	if (i > 0) {		/* for tmp_X BATs, we already know X */		str s = BBP_logical(i);		if (i >= BBPsize || s == NULL || strcmp(s, nme)) {			i = 0;		}	} else if (*nme != '.') {		/* must lock since hash-lookup traverses other BATs */		if (lock)			gdk_set_lock(GDKcacheLock, "BBPindex");		for (i = BBP_hash[strHash(nme) & BBP_mask]; i; i = BBP_next(i)) {			if (strcmp(BBP_logical(i), nme) == 0)				break;		}		if (lock)			gdk_unset_lock(GDKcacheLock, "BBPindex");	}	return i;}batBBPindex(str nme){	return BBP_find(nme, TRUE);}BATstore *BBPgetdesc(bat i){	BAT *b = NULL;	if (i < 0)		i = -i;	if (i != bat_nil && i < BBPsize && i && BBP_logical(i)) {		str nme = BBP_physical(i);		b = BBP_cache(i);		if (b == NULL) 			b = (BAT *) BBP_desc(i);		if (b == NULL && nme) {			int lock = locked_by ? BBP_getpid() != locked_by : 1;			b = BATloaddesc(nme);			IODEBUG THRprintf(GDKout, "#BATloaddesc(%s) = %d\n", nme, (b==NULL)?-1:0); 			if (b == NULL) {				GDKerror("BBPgetdesc: deleting illegal bat(%d) %s\n", i, nme);				BBPclear(i);			} else if (BBP_desc(i) == NULL) {				if (lock)					gdk_set_lock(GDKswapLock[i & BBPLOCKMASK], "BBPgetdesc");				BBP_desc(i) = (BATstore *) b;				if (lock)					gdk_unset_lock(GDKswapLock[i & BBPLOCKMASK], "BBPgetdesc");			}		}		if (b)			BBP_lastused(i) = BBPLASTUSED(BBPstamp());	}	return (BATstore *) b;}strBBPlogical(bat bid, str buf){	if (buf == NULL) {		return NULL;	} else if (BBPcheck(bid, "BBPlogical")) {		if (bid < 0 && BBP_logical(bid) == NULL)			bid = -bid;		strcpy(buf, BBP_logical(bid));	} else {		*buf = 0;	}	return buf;}strBBPphysical(bat bid, str buf){	if (buf == NULL) {		return NULL;	} else if (BBPcheck(bid, "BBPphysical")) {		strcpy(buf, BBP_physical(ABS(bid)));	} else {		*buf = 0;	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -