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

📄 heaptuple.c

📁 关系型数据库 Postgresql 6.5.2
💻 C
📖 第 1 页 / 共 2 页
字号:
/*------------------------------------------------------------------------- * * heaptuple.c *	  This file contains heap tuple accessor and mutator routines, as well *	  as a few various tuple utilities. * * Copyright (c) 1994, Regents of the University of California * * * IDENTIFICATION *	  $Header: /usr/local/cvsroot/pgsql/src/backend/access/common/heaptuple.c,v 1.53.2.1 1999/08/02 05:24:25 scrappy Exp $ * * NOTES *	  The old interface functions have been converted to macros *	  and moved to heapam.h * *------------------------------------------------------------------------- */#include "postgres.h"#include "access/heapam.h"#include "catalog/pg_type.h"/* Used by heap_getattr() macro, for speed */long		heap_sysoffset[] = {/* Only the first one is pass-by-ref, and is handled specially in the macro */	offsetof(HeapTupleHeaderData, t_ctid),	offsetof(HeapTupleHeaderData, t_oid),	offsetof(HeapTupleHeaderData, t_xmin),	offsetof(HeapTupleHeaderData, t_cmin),	offsetof(HeapTupleHeaderData, t_xmax),	offsetof(HeapTupleHeaderData, t_cmax)};/* ---------------------------------------------------------------- *						misc support routines * ---------------------------------------------------------------- *//* ---------------- *		ComputeDataSize * ---------------- */SizeComputeDataSize(TupleDesc tupleDesc,				Datum *value,				char *nulls){	uint32		data_length;	int			i;	int			numberOfAttributes = tupleDesc->natts;	Form_pg_attribute *att = tupleDesc->attrs;	for (data_length = 0, i = 0; i < numberOfAttributes; i++)	{		if (nulls[i] != ' ')			continue;		data_length = att_align(data_length, att[i]->attlen, att[i]->attalign);		data_length = att_addlength(data_length, att[i]->attlen, value[i]);	}	return data_length;}/* ---------------- *		DataFill * ---------------- */voidDataFill(char *data,		 TupleDesc tupleDesc,		 Datum *value,		 char *nulls,		 uint16 *infomask,		 bits8 *bit){	bits8	   *bitP = 0;	int			bitmask = 0;	uint32		data_length;	int			i;	int			numberOfAttributes = tupleDesc->natts;	Form_pg_attribute *att = tupleDesc->attrs;	if (bit != NULL)	{		bitP = &bit[-1];		bitmask = CSIGNBIT;	}	*infomask = 0;	for (i = 0; i < numberOfAttributes; i++)	{		if (bit != NULL)		{			if (bitmask != CSIGNBIT)				bitmask <<= 1;			else			{				bitP += 1;				*bitP = 0x0;				bitmask = 1;			}			if (nulls[i] == 'n')			{				*infomask |= HEAP_HASNULL;				continue;			}			*bitP |= bitmask;		}		data = (char *) att_align((long) data, att[i]->attlen, att[i]->attalign);		switch (att[i]->attlen)		{			case -1:				*infomask |= HEAP_HASVARLENA;				data_length = VARSIZE(DatumGetPointer(value[i]));				memmove(data, DatumGetPointer(value[i]), data_length);				break;			case sizeof(char):				*data = att[i]->attbyval ?					DatumGetChar(value[i]) : *((char *) value[i]);				break;			case sizeof(int16):				*(short *) data = (att[i]->attbyval ?								   DatumGetInt16(value[i]) :								   *((short *) value[i]));				break;			case sizeof(int32):				*(int32 *) data = (att[i]->attbyval ?								   DatumGetInt32(value[i]) :								   *((int32 *) value[i]));				break;			default:				memmove(data, DatumGetPointer(value[i]),						att[i]->attlen);				break;		}		data = (char *) att_addlength((long) data, att[i]->attlen, value[i]);	}}/* ---------------------------------------------------------------- *						heap tuple interface * ---------------------------------------------------------------- *//* ---------------- *		heap_attisnull	- returns 1 iff tuple attribute is not present * ---------------- */intheap_attisnull(HeapTuple tup, int attnum){	if (attnum > (int) tup->t_data->t_natts)		return 1;	if (HeapTupleNoNulls(tup))		return 0;	if (attnum > 0)		return att_isnull(attnum - 1, tup->t_data->t_bits);	else		switch (attnum)		{			case SelfItemPointerAttributeNumber:			case ObjectIdAttributeNumber:			case MinTransactionIdAttributeNumber:			case MinCommandIdAttributeNumber:			case MaxTransactionIdAttributeNumber:			case MaxCommandIdAttributeNumber:				break;			case 0:				elog(ERROR, "heap_attisnull: zero attnum disallowed");			default:				elog(ERROR, "heap_attisnull: undefined negative attnum");		}	return 0;}/* ---------------------------------------------------------------- *				 system attribute heap tuple support * ---------------------------------------------------------------- *//* ---------------- *		heap_sysattrlen * *		This routine returns the length of a system attribute. * ---------------- */intheap_sysattrlen(AttrNumber attno){	HeapTupleHeader f = NULL;	switch (attno)	{		case SelfItemPointerAttributeNumber:			return sizeof f->t_ctid;		case ObjectIdAttributeNumber:			return sizeof f->t_oid;		case MinTransactionIdAttributeNumber:			return sizeof f->t_xmin;		case MinCommandIdAttributeNumber:			return sizeof f->t_cmin;		case MaxTransactionIdAttributeNumber:			return sizeof f->t_xmax;		case MaxCommandIdAttributeNumber:			return sizeof f->t_cmax;		default:			elog(ERROR, "sysattrlen: System attribute number %d unknown.", attno);			return 0;	}}/* ---------------- *		heap_sysattrbyval * *		This routine returns the "by-value" property of a system attribute. * ---------------- */boolheap_sysattrbyval(AttrNumber attno){	bool		byval;	switch (attno)	{		case SelfItemPointerAttributeNumber:			byval = false;			break;		case ObjectIdAttributeNumber:			byval = true;			break;		case MinTransactionIdAttributeNumber:			byval = true;			break;		case MinCommandIdAttributeNumber:			byval = true;			break;		case MaxTransactionIdAttributeNumber:			byval = true;			break;		case MaxCommandIdAttributeNumber:			byval = true;			break;		default:			byval = true;			elog(ERROR, "sysattrbyval: System attribute number %d unknown.",				 attno);			break;	}	return byval;}#ifdef NOT_USED/* ---------------- *		heap_getsysattr * ---------------- */Datumheap_getsysattr(HeapTuple tup, Buffer b, int attnum){	switch (attnum)	{			case SelfItemPointerAttributeNumber:			return (Datum) &tup->t_ctid;		case ObjectIdAttributeNumber:			return (Datum) (long) tup->t_oid;		case MinTransactionIdAttributeNumber:			return (Datum) (long) tup->t_xmin;		case MinCommandIdAttributeNumber:			return (Datum) (long) tup->t_cmin;		case MaxTransactionIdAttributeNumber:			return (Datum) (long) tup->t_xmax;		case MaxCommandIdAttributeNumber:			return (Datum) (long) tup->t_cmax;		default:			elog(ERROR, "heap_getsysattr: undefined attnum %d", attnum);	}	return (Datum) NULL;}#endif/* ---------------- *		nocachegetattr * *		This only gets called from fastgetattr() macro, in cases where *		we can't use a cacheoffset and the value is not null. * *		This caches attribute offsets in the attribute descriptor. * *		An alternate way to speed things up would be to cache offsets *		with the tuple, but that seems more difficult unless you take *		the storage hit of actually putting those offsets into the *		tuple you send to disk.  Yuck. * *		This scheme will be slightly slower than that, but should *		perform well for queries which hit large #'s of tuples.  After *		you cache the offsets once, examining all the other tuples using *		the same attribute descriptor will go much quicker. -cim 5/4/91 * ---------------- */Datumnocachegetattr(HeapTuple tuple,			   int attnum,			   TupleDesc tupleDesc,			   bool *isnull){	char	   *tp;				/* ptr to att in tuple */	HeapTupleHeader tup = tuple->t_data;	bits8	   *bp = tup->t_bits;		/* ptr to att in tuple */	Form_pg_attribute *att = tupleDesc->attrs;	int			slow = 0;		/* do we have to walk nulls? */#if IN_MACRO/* This is handled in the macro */	Assert(attnum > 0);	if (isnull)		*isnull = false;#endif	attnum--;	/* ----------------	 *	 Three cases:	 *	 *	 1: No nulls and no variable length attributes.	 *	 2: Has a null or a varlena AFTER att.	 *	 3: Has nulls or varlenas BEFORE att.	 * ----------------	 */	if (HeapTupleNoNulls(tuple))	{#if IN_MACRO/* This is handled in the macro */		if (att[attnum]->attcacheoff != -1)		{			return (Datum)				fetchatt(&(att[attnum]),				  (char *) tup + tup->t_hoff + att[attnum]->attcacheoff);		}		else if (attnum == 0)		{			/*			 * first attribute is always at position zero			 */			return (Datum) fetchatt(&(att[0]), (char *) tup + tup->t_hoff);		}#endif	}	else	{		/*		 * there's a null somewhere in the tuple		 */		/* ----------------		 *		check to see if desired att is null		 * ----------------		 */#if IN_MACRO/* This is handled in the macro */		if (att_isnull(attnum, bp))		{			if (isnull)				*isnull = true;			return (Datum) NULL;		}#endif		/* ----------------		 *		Now check to see if any preceding bits are null...		 * ----------------		 */		{			int			byte = attnum >> 3;			int			finalbit = attnum & 0x07;			/* check for nulls "before" final bit of last byte */			if ((~bp[byte]) & ((1 << finalbit) - 1))				slow = 1;			else			{				/* check for nulls in any "earlier" bytes */				int			i;				for (i = 0; i < byte; i++)				{					if (bp[i] != 0xFF)					{						slow = 1;						break;					}				}			}		}	}

⌨️ 快捷键说明

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