コード例 #1
0
ファイル: op_indglvn.c プロジェクト: 5HT/mumps
void	op_indglvn(mval *v,mval *dst)
{
	bool		rval;
	mstr		*obj, object;
	oprtype		x;
	lv_val 		*a;
	icode_str	indir_src;
	lv_val		*lv;
	var_tabent	targ_key;
	ht_ent_mname	*tabent;

	error_def(ERR_INDMAXNEST);
	error_def(ERR_UNDEF);

	MV_FORCE_STR(v);
	indir_src.str = v->str;
	indir_src.code = indir_glvn;
	if (NULL == (obj = cache_get(&indir_src)))
	{
		if (valid_mname(&v->str))
		{
			targ_key.var_name = v->str;
			COMPUTE_HASH_MNAME(&targ_key);
			tabent = lookup_hashtab_mname(&curr_symval->h_symtab, &targ_key);
			assert(NULL == tabent ||  NULL != tabent->value);
			if (!tabent || !MV_DEFINED(&((lv_val *)tabent->value)->v))
			{
				if (undef_inhibit)
				{
					*dst = literal_null;
					return;
				}
				else
					rts_error(VARLSTCNT(4) ERR_UNDEF, 2, v->str.len, v->str.addr);
			}
			a = (lv_val *)tabent->value;
			*dst = a->v;
			return;
		}
		comp_init(&v->str);
		rval = glvn(&x);
		if (comp_fini(rval, &object, OC_IRETMVAL, &x, v->str.len))
		{
			indir_src.str.addr = v->str.addr;
			cache_put(&indir_src, &object);
			*ind_result_sp++ = dst;
			if (ind_result_sp >= ind_result_top)
				rts_error(VARLSTCNT(1) ERR_INDMAXNEST);
			comp_indr(&object);
		}
	}
	else
	{
		*ind_result_sp++ = dst;
		if (ind_result_sp >= ind_result_top)
			rts_error(VARLSTCNT(1) ERR_INDMAXNEST);
		comp_indr(obj);
	}
}
コード例 #2
0
ファイル: op_indlvarg.c プロジェクト: h4ck3rm1k3/fis-gtm
void	op_indlvarg(mval *v, mval *dst)
{
	bool		rval;
	mstr		*obj, object;
	oprtype		x;
	triple		*ref;
	icode_str	indir_src;

	error_def(ERR_INDMAXNEST);
	error_def(ERR_VAREXPECTED);

	MV_FORCE_STR(v);
	if (v->str.len < 1)
		rts_error(VARLSTCNT(1) ERR_VAREXPECTED);
	if (valid_mname(&v->str))
	{
		*dst = *v;
		dst->mvtype &= ~MV_ALIASCONT;	/* Make sure alias container property does not pass */
		return;
	}
	if (*v->str.addr == '@')
	{
		indir_src.str = v->str;
		indir_src.code = indir_lvarg;
		if (NULL == (obj = cache_get(&indir_src)))
		{
			object.addr = v->str.addr;
			object.len  = v->str.len;
			comp_init(&object);
			if (rval = indirection(&x))
			{
				ref = newtriple(OC_INDLVARG);
				ref->operand[0] = x;
				x = put_tref(ref);
			}
			if (comp_fini(rval, &object, OC_IRETMVAL, &x, object.len))
			{
				indir_src.str.addr = v->str.addr;
				cache_put(&indir_src, &object);
				*ind_result_sp++ = dst;
				if (ind_result_sp >= ind_result_top)
					rts_error(VARLSTCNT(1) ERR_INDMAXNEST);
				comp_indr(&object);
				return;
			}
		} else
		{
			*ind_result_sp++ = dst;
			if (ind_result_sp >= ind_result_top)
				rts_error(VARLSTCNT(1) ERR_INDMAXNEST);
			comp_indr(obj);
			return;
		}
	}
	rts_error(VARLSTCNT(1) ERR_VAREXPECTED);
}
コード例 #3
0
ファイル: op_indlvarg.c プロジェクト: CeperaCPP/fis-gtm
void	op_indlvarg(mval *v, mval *dst)
{
	icode_str	indir_src;
	int		rval;
	mstr		*obj, object;
	oprtype		x;
	triple		*ref;
	DCL_THREADGBL_ACCESS;

	SETUP_THREADGBL_ACCESS;
	if (TREF(ind_result_sp) >= TREF(ind_result_top))
		rts_error(VARLSTCNT(1) ERR_INDMAXNEST); /* mdbcondition_handler resets ind_result_sp */
	MV_FORCE_STR(v);
	if (v->str.len < 1)
		rts_error(VARLSTCNT(1) ERR_VAREXPECTED);
	if (valid_mname(&v->str))
	{
		*dst = *v;
		dst->mvtype &= ~MV_ALIASCONT;	/* Make sure alias container property does not pass */
		return;
	}
	if (*v->str.addr != '@')
		rts_error(VARLSTCNT(1) ERR_VAREXPECTED);
	indir_src.str = v->str;
	indir_src.code = indir_lvarg;
	if (NULL == (obj = cache_get(&indir_src)))
	{
		obj = &object;
		obj->addr = v->str.addr;
		obj->len  = v->str.len;
		comp_init(obj);
		if (EXPR_FAIL != (rval = indirection(&x)))	/* NOTE assignment */
		{
			ref = newtriple(OC_INDLVARG);
			ref->operand[0] = x;
			x = put_tref(ref);
		}
		if (EXPR_FAIL == comp_fini(rval, obj, OC_IRETMVAL, &x, obj->len))
			return;
		indir_src.str.addr = v->str.addr;
		cache_put(&indir_src, obj);
		/* Fall into code activation below */
	}
	*(TREF(ind_result_sp))++ = dst;				/* Where to store return value */
	comp_indr(obj);
	return;
}
コード例 #4
0
void op_zrupdate(int argcnt, ...)
{
	mval			*objfilespec;
	va_list			var;
	mval			objpath;
	char			tranbuf[MAX_FBUFF + 1], *chptr, chr;
	open_relinkctl_sgm 	*linkctl;
	relinkrec_t		*rec;
	plength			plen;
	int			status, fextlen, fnamlen, fcnt;
	parse_blk		pblk;
	struct stat		outbuf;
        int			stat_res;
	boolean_t		seenfext, fileexists;
	mstr			objdir, rtnname;
	uint4			hash, prev_hash_index;

	/* Currently only expecting one value per invocation right now. That will change in phase 2 hence the stdarg setup */
	va_start(var, argcnt);
	assert(1 == argcnt);
	objfilespec = va_arg(var, mval *);
	va_end(var);
	MV_FORCE_STR(objfilespec);
	/* First some pre-processing to determine if an explicit file name or type was specified. If so, it must be ".o" for
	 * this phase of implementation. Later phases may allow ".m" to be specified but not initially. Use parse_file() to
	 * parse everything out and isolate any extention.
	 */
	memset(&pblk, 0, SIZEOF(pblk));
        pblk.buffer = tranbuf;
	pblk.buff_size = (unsigned char)(MAX_FBUFF);	/* Pass size of buffer - 1 (standard protocol for parse_file) */
	pblk.def1_buf = DOTOBJEXT;			/* Default .o file type if not specified */
	pblk.def1_size = SIZEOF(DOTOBJEXT) - 1;
	pblk.fop = F_SYNTAXO;				/* Syntax check only - bypass directory existence check */
	status = parse_file(&objfilespec->str, &pblk);
	if (ERR_PARNORMAL != status)
		rts_error_csa(CSA_ARG(NULL) VARLSTCNT(5) ERR_FILEPARSE, 2, objfilespec->str.len, objfilespec->str.addr, status);
	tranbuf[pblk.b_esl] = '\0';			/* Needed for subsequent STAT_FILE */
	seenfext = FALSE;
	if (0 != pblk.b_ext)
	{	/* If a file extension was specified - get the extension sans any potential wildcard character */
		for (chptr = pblk.l_ext + 1, fextlen = pblk.b_ext - 1; 0 < fextlen; chptr++, fextlen--)
		{	/* Check each character in the extension except first which is the dot if ext exists at all */
			if (WILDCARD != *chptr)
			{	/* We see a char that isn't a wildcard character. If we've already seen our "o" file extension,
				 * this char makes our requirement filetype impossible so raise an error.
				 */
				if (seenfext || (OBJEXT != *chptr))
					/* No return from this error */
					rts_error_csa(CSA_ARG(NULL) VARLSTCNT(8) ERR_FILEPARSE,
						      2, objfilespec->str.len, objfilespec->str.addr,
						      ERR_TEXT, 2, RTS_ERROR_TEXT("Unsupported filetype specified"));
				seenfext = TRUE;
			}
		}
	}
	/* Do a simlar check for the file type */
	if (0 != pblk.b_name)
	{	/* A file name was specified (if not, tiz probably hard to find the file but that can be dealt with later).
		 * Like in the above, the name must be comprised of valid chars for routine names.
		 */
		for (chptr = pblk.l_name, fnamlen = pblk.b_name; 0 < fnamlen; chptr++, fnamlen--)
		{
			if (WILDCARD != *chptr)
			{	/* Substitute '%' for '_'. While this substitution is really only valid on the first char, only the
				 * first char check allows "%" so a 2nd or later char check would fail the '%' substitution anyway.
				 */
				chr = ('_' == *chptr) ? '%' : *chptr;
				/* We see a char that isn't a wildcard character. If this is the first character, it can be
				 * alpha or percent. If the second or later character, it can be alphanumeric.
				 */
				if (((fnamlen != pblk.b_name) && !VALID_MNAME_NFCHAR(chr))	/* 2nd char or later check */
				    || ((fnamlen == pblk.b_name) && !VALID_MNAME_FCHAR(chr)))	/* 1st char check */
				{
					rts_error_csa(CSA_ARG(NULL) VARLSTCNT(8) ERR_FILEPARSE,
						      2, objfilespec->str.len, objfilespec->str.addr,
						      ERR_TEXT, 2, RTS_ERROR_TEXT("Filename is not a valid routine name"));
				}
			}
		}
	}
	/* When specifying a non-wildcarded object file, it is possible for the file to have been removed, in which case we still
	 * need to update its relinkctl entry (if exists) to notify other processes about the object's deletion.
	 */
	if (!(pblk.fnb & F_WILD) & seenfext)
	{	/* If no wildcards in path and saw the extension we want - no need to wash through zsearch() */
		objdir.addr = pblk.l_dir;
		objdir.len = pblk.b_dir;
		linkctl = relinkctl_attach(&objdir);		/* Create/attach/open relinkctl file */
		if (NULL == linkctl)				/* Non-existant path and no associated relinkctl file */
			/* Note this reference to errno depends on nothing in relinkctl_attach() doing anything to modify
			 * errno after the realpath() call. No return from this error.
			 */
			rts_error_csa(CSA_ARG(NULL) VARLSTCNT(5) ERR_FILEPARSE, 2, objfilespec->str.len, objfilespec->str.addr,
				      errno);
		/* What we do at this point depends on the following conditions:
		 *
		 * 1) If the specified file exists, we can add it to relinkctl file and/or update its cycle.
		 * 2) If the file doesn't exist on disk but the routine is found in the relinkctl file, update cycle.
		 * 3) If no file and no entry, just ignore it and do nothing (info error removed by request).
		 */
		STAT_FILE(tranbuf, &outbuf, stat_res);
		if (-1 == stat_res)
		{
			if (ENOENT != errno)
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(5) ERR_FILEPARSE, 2, objfilespec->str.len,
					      objfilespec->str.addr, errno);
			fileexists = FALSE;
		} else
			fileexists = TRUE;
		rtnname.len = pblk.b_name;
		rtnname.addr = pblk.l_name;
		CONVERT_FILENAME_TO_RTNNAME(rtnname);	/* Set rtnname right before searching in relinkctl file */
		assert(valid_mname(&rtnname));
		COMPUTE_RELINKCTL_HASH(&rtnname, hash);
		rec = relinkctl_find_record(linkctl, &rtnname, hash, &prev_hash_index);
		if ((NULL == rec) && !fileexists)
			return;					/* No file and no entry - ignore */
		/* Either the file exists or the entry exists so add or update it */
		rec = relinkctl_insert_record(linkctl, &rtnname);
		RELINKCTL_CYCLE_INCR(rec, linkctl); 		/* Increment cycle indicating change to world */
		return;
	}
	/* If we have a wildcarded request or one without the object filetype, reprocess the string with $ZSEARCH using our
	 * defined stream to resolve wildcards. Then loop through processing each file returned. In this loop, we just ignore
	 * any file that doesn't have a ".o" extension.
	 */
	op_fnzsearch((mval *)&literal_null, STRM_ZRUPDATE, 0, &objpath);	/* Clear any existing cache */
	for (fcnt = 0; ; fcnt++)
	{
		plen.p.pint = op_fnzsearch(objfilespec, STRM_ZRUPDATE, 0, &objpath);
		if (0 == objpath.str.len)
		{	/* End of file list */
			if (0 == fcnt)
				/* Still looking to process our first file - give no objects found message as a "soft" message
				 * (INFO level message - supressed in other than direct mode)
				 */
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(8) MAKE_MSG_INFO(ERR_FILEPARSE), 2, objfilespec->str.len,
					      objfilespec->str.addr, ERR_TEXT, 2, RTS_ERROR_TEXT("No object files found"));
			break;
		}
		/* The extension contains the extension-start character ('.') so we are looking for the extension '.o' hence
		 * the length must be 2 and the 2nd char must be OBJEXT.
		 */
		if ((2 == plen.p.pblk.b_ext) && (OBJEXT == *(objpath.str.addr + plen.p.pblk.b_dir + plen.p.pblk.b_name + 1)))
		{			/* This is (probably) an object file. Double check file is a file and not a directory */
			memcpy(tranbuf, objpath.str.addr, objpath.str.len);	/* Need null terminated version for STAT */
			tranbuf[objpath.str.len] = '\0';		/* Not guaranteed null termination from op_fnzsearch */
			STAT_FILE(tranbuf, &outbuf, stat_res);
			/* If either something happened to the file since op_fnzsearch() saw it or the file is not a file, then
			 * ignore it.
			 */
			if ((-1 == stat_res) || !S_ISREG(outbuf.st_mode))
			{
				fcnt--;					/* Don't count files not found for whatever reason */
				continue;
			}
			/* Before opening the relinkctl file, verify we actually do have a valid routine name */
			rtnname.len = plen.p.pblk.b_name;
			rtnname.addr = objpath.str.addr + plen.p.pblk.b_dir;
			CONVERT_FILENAME_TO_RTNNAME(rtnname);		/* Set rtnname right before searching in relinkctl file */
			if (!valid_mname(&rtnname))
			{
				fcnt--;
				continue;				/* Ignore files that are invalid wildcard matches */
			}
			objdir.addr = objpath.str.addr;
			objdir.len = plen.p.pblk.b_dir;
			linkctl = relinkctl_attach(&objdir);		/* Create/attach/open relinkctl file */
			if (NULL == linkctl)
			{
				fcnt--;					/* Path disappeared - don't count it */
				continue;
			}
			rec = relinkctl_insert_record(linkctl, &rtnname);
			RELINKCTL_CYCLE_INCR(rec, linkctl); 		/* Increment cycle indicating change to world */
		} else
			fcnt--;						/* Don't count ignored files */

	}
}
コード例 #5
0
ファイル: view_arg_convert.c プロジェクト: shabiel/YottaDB
void view_arg_convert(viewtab_entry *vtp, int vtp_parm, mval *parm, viewparm *parmblk, boolean_t is_dollar_view)
{
	static	int4		first_time = TRUE;
	char			*cptr;
	char			*strtokptr;
	gd_binding		*gd_map;
	gd_region		*gd_reg_start, *r_ptr, *r_top;
	gvnh_reg_t		*gvnh_reg;
	gvnh_spanreg_t		*gvspan;
	gv_namehead		*tmp_gvt;
	ht_ent_mname		*tabent;
	int			n, reg_index;
	mident_fixed		lcl_buff;
	mname_entry		gvent, lvent;
	mstr			namestr, tmpstr;
	unsigned char 		*c, *c_top, *dst, *dst_top, global_names[1024], *nextsrc, *src, *src_top, stashed, y;

	switch (vtp_parm)
	{
		case VTP_NULL:
			if (parm != 0)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			break;
		case (VTP_NULL | VTP_VALUE):
			if (NULL == parm)
			{
				parmblk->value = (mval *)&literal_one;
				break;
			}
			/* caution:  fall through */
		case VTP_VALUE:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			parmblk->value = parm;
			break;
		case (VTP_NULL | VTP_DBREGION):
			if (!is_dollar_view && ((NULL == parm) || ((1 == parm->str.len) && ('*' == *parm->str.addr))))
			{
				parmblk->gv_ptr = NULL;
				break;
			}
			/* caution:  fall through */
		case VTP_DBREGION:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			if (!gd_header)		/* IF GD_HEADER ==0 THEN OPEN GBLDIR */
				gvinit();
			r_ptr = gd_header->regions;
			if (!parm->str.len && vtp->keycode == VTK_GVNEXT)	/* "" => 1st region */
				parmblk->gv_ptr = r_ptr;
			else
			{
				for (cptr = parm->str.addr, n = 0; n < parm->str.len; cptr++, n++)
					lcl_buff.c[n] = TOUPPER(*cptr);		/* Region names are upper-case ASCII */
				namestr.len = n;
				namestr.addr = &lcl_buff.c[0];
				for (r_top = r_ptr + gd_header->n_regions; ; r_ptr++)
				{
					if (r_ptr >= r_top)
					{
						format2zwr((sm_uc_ptr_t)parm->str.addr, parm->str.len, global_names, &n);
						rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_NOREGION,2, n, global_names);
					}
					tmpstr.len = r_ptr->rname_len;
					tmpstr.addr = (char *)r_ptr->rname;
					MSTR_CMP(tmpstr, namestr, n);
					if (0 == n)
						break;
				}
				parmblk->gv_ptr = r_ptr;
			}
			break;
		case VTP_DBKEY:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			if (!parm->str.len)
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_NOTGBL, 2, parm->str.len, NULL);
			if (!gd_header)		/* IF GD_HEADER ==0 THEN OPEN GBLDIR */
				gvinit();
			c = (unsigned char *)parm->str.addr;
			if ('^' != *c)
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_NOTGBL, 2, parm->str.len, c);
			c_top = c + parm->str.len;
			c++;				/* skip initial '^' */
			parmblk->str.addr = (char *)c;
			for ( ; (c < c_top) && ('(' != *c); c++)
				;
			parmblk->str.len = (char *)c - parmblk->str.addr;
			if (MAX_MIDENT_LEN < parmblk->str.len)
				parmblk->str.len = MAX_MIDENT_LEN;
			if (!valid_mname(&parmblk->str))
			{
				format2zwr((sm_uc_ptr_t)parm->str.addr, parm->str.len, global_names, &n);
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWGVN, 2, n, global_names);
			}
			break;
		case VTP_RTNAME:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			memset(&parmblk->ident.c[0], 0, SIZEOF(parmblk->ident));
			if (parm->str.len > 0)
				memcpy(&parmblk->ident.c[0], parm->str.addr,
				       (parm->str.len <= MAX_MIDENT_LEN ? parm->str.len : MAX_MIDENT_LEN));
			break;
		case VTP_NULL | VTP_DBKEYLIST:
			if (NULL == parm || 0 == parm->str.len)
			{
				parmblk->ni_list.gvnh_list = NULL;
				parmblk->ni_list.type = NOISOLATION_NULL;
				break;
			}
			/* caution : explicit fall through */
		case VTP_DBKEYLIST:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			if (!gd_header)
				gvinit();
			if (first_time)
			{
				noisolation_buddy_list = (buddy_list *)malloc(SIZEOF(buddy_list));
				initialize_list(noisolation_buddy_list, SIZEOF(noisolation_element), NOISOLATION_INIT_ALLOC);
				gvt_pending_buddy_list = (buddy_list *)malloc(SIZEOF(buddy_list));
				initialize_list(gvt_pending_buddy_list, SIZEOF(gvt_container), NOISOLATION_INIT_ALLOC);
				first_time = FALSE;
			}
			assertpro(SIZEOF(global_names) > parm->str.len);
			tmpstr.len = parm->str.len;	/* we need to change len and should not change parm->str, so take a copy */
			tmpstr.addr = parm->str.addr;
			if (0 != tmpstr.len)
			{
				switch (*tmpstr.addr)
				{
					case '+' :
						parmblk->ni_list.type = NOISOLATION_PLUS;
						tmpstr.addr++;
						tmpstr.len--;
						break;
					case '-' :
						parmblk->ni_list.type = NOISOLATION_MINUS;
						tmpstr.addr++;
						tmpstr.len--;
						break;
					default :
						parmblk->ni_list.type = NOISOLATION_NULL;
						break;
				}
				if (!tmpstr.len)
					rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWGVN, 2, tmpstr.len, NULL);
				memcpy(global_names, tmpstr.addr, tmpstr.len);
				global_names[tmpstr.len] = '\0';
				src = (unsigned char *)STRTOK_R((char *)global_names, ",", &strtokptr);
				REINITIALIZE_LIST(noisolation_buddy_list);	/* reinitialize the noisolation buddy_list */
				parmblk->ni_list.gvnh_list = NULL;
				for ( ; src < &global_names[tmpstr.len + 1]; src = nextsrc)
				{
					nextsrc = (unsigned char *)STRTOK_R(NULL, ",", &strtokptr);
					if (NULL == nextsrc)
						nextsrc = &global_names[tmpstr.len + 1];
					if (nextsrc - src >= 2 && '^' == *src)
					{
						namestr.addr = (char *)src + 1;		/* skip initial '^' */
						namestr.len = INTCAST(nextsrc - src - 2); /* don't count initial ^ and trailing 0 */
						if (namestr.len > MAX_MIDENT_LEN)
							namestr.len = MAX_MIDENT_LEN;
						if (valid_mname(&namestr))
						{
							memcpy(&lcl_buff.c[0], namestr.addr, namestr.len);
							gvent.var_name.len = namestr.len;
						} else
						{
							memcpy(&lcl_buff.c[0], src, nextsrc - src - 1);
							format2zwr((sm_uc_ptr_t)&lcl_buff.c, nextsrc - src - 1, global_names, &n);
							rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWGVN, 2, n, global_names);
						}
					} else
					{
						memcpy(&lcl_buff.c[0], src, nextsrc - src - 1);
						format2zwr((sm_uc_ptr_t)&lcl_buff.c, nextsrc - src - 1, global_names, &n);
						rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWGVN, 2, n, global_names);
					}
					tmp_gvt = NULL;
					gvent.var_name.addr = &lcl_buff.c[0];
					COMPUTE_HASH_MNAME(&gvent);
					if (NULL != (tabent = lookup_hashtab_mname(gd_header->tab_ptr, &gvent)))
					{
						gvnh_reg = (gvnh_reg_t *)tabent->value;
						assert(NULL != gvnh_reg);
						tmp_gvt = gvnh_reg->gvt;
					} else
					{
						gd_map = gv_srch_map(gd_header, gvent.var_name.addr, gvent.var_name.len,
													SKIP_BASEDB_OPEN_FALSE);
						r_ptr = gd_map->reg.addr;
						tmp_gvt = (gv_namehead *)targ_alloc(r_ptr->max_key_size, &gvent, r_ptr);
						GVNH_REG_INIT(gd_header, gd_header->tab_ptr, gd_map, tmp_gvt,
											r_ptr, gvnh_reg, tabent);
						/* In case of a global spanning multiple regions, the gvt pointer corresponding to
						 * the region where the unsubscripted global reference maps to is stored in TWO
						 * locations (one in gvnh_reg->gvspan->gvt_array[index] and one in gvnh_reg->gvt.
						 * So pass in both these pointer addresses to be stored in the pending list in
						 * case this gvt gets reallocated (due to different keysizes between gld and db).
						 */
						if (NULL == (gvspan = gvnh_reg->gvspan))
						{
							ADD_TO_GVT_PENDING_LIST_IF_REG_NOT_OPEN(r_ptr, &gvnh_reg->gvt, NULL);
						} else
						{
							gd_reg_start = &gd_header->regions[0];
							GET_REG_INDEX(gd_header, gd_reg_start, r_ptr, reg_index);
								/* the above sets "reg_index" */
							assert(reg_index >= gvspan->min_reg_index);
							assert(reg_index <= gvspan->max_reg_index);
							reg_index -= gvspan->min_reg_index;
							ADD_TO_GVT_PENDING_LIST_IF_REG_NOT_OPEN(r_ptr,
								&gvspan->gvt_array[reg_index], &gvnh_reg->gvt);
						}
					}
					ADD_GVT_TO_VIEW_NOISOLATION_LIST(tmp_gvt, parmblk);
					if (!is_dollar_view && (NULL != gvnh_reg->gvspan))
					{	/* Global spans multiple regions. Make sure gv_targets corresponding to ALL
						 * spanned regions are allocated so NOISOLATION status can be set in all of
						 * them even if the corresponding regions are not open yet. Do this only for
						 * VIEW "NOISOLATION" commands which change the noisolation characteristic.
						 * $VIEW("NOISOLATION") only examines the characteristics and so no need to
						 * allocate all the gv-targets in that case. Just one is enough.
						 */
						gvnh_spanreg_subs_gvt_init(gvnh_reg, gd_header, parmblk);
					}
				}
			} else
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWGVN, 2, tmpstr.len, tmpstr.addr);
			break;
		case VTP_LVN:
			if (NULL == parm)
				rts_error_csa(CSA_ARG(NULL)
					VARLSTCNT(4) ERR_VIEWARGCNT, 2, strlen((const char *)vtp->keyword), vtp->keyword);
			if (0 < parm->str.len)
			{
				lvent.var_name.addr = parm->str.addr;
				lvent.var_name.len = parm->str.len;
				if (lvent.var_name.len > MAX_MIDENT_LEN)
					lvent.var_name.len = MAX_MIDENT_LEN;
				if (!valid_mname(&lvent.var_name))
				{
					format2zwr((sm_uc_ptr_t)parm->str.addr, parm->str.len, global_names, &n);
					rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWLVN, 2, n, global_names);
				}
			} else
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWLVN, 2, parm->str.len, parm->str.addr);
			/* Now look up the name.. */
			COMPUTE_HASH_MNAME(&lvent);
			if ((tabent = lookup_hashtab_mname(&curr_symval->h_symtab, &lvent)) && (NULL != tabent->value))
				parmblk->value = (mval *)tabent->value;	/* Return lv_val ptr */
			else
				rts_error_csa(CSA_ARG(NULL) VARLSTCNT(4) ERR_VIEWLVN, 2, parm->str.len, parm->str.addr);
			break;
		default:
			assertpro(FALSE && vtp_parm);
	}
}
コード例 #6
0
ファイル: op_indget.c プロジェクト: duck57/fis-gtm-freebsd
void	op_indget(mval *dst, mval *target, mval *value)
{
	icode_str	indir_src;
	int		rval;
	ht_ent_mname	*tabent;
	mstr		*obj, object;
	oprtype		v;
	triple		*s, *src, *oldchain, tmpchain, *r, *triptr;
	var_tabent	targ_key;
	DCL_THREADGBL_ACCESS;

	SETUP_THREADGBL_ACCESS;
	if ((TREF(ind_source_sp) >= TREF(ind_source_top)) || (TREF(ind_result_sp) >= TREF(ind_result_top)))
		rts_error(VARLSTCNT(1) ERR_INDMAXNEST); /* mdbcondition_handler resets ind_result_sp & ind_source_sp */
	MV_FORCE_DEFINED(value);
	MV_FORCE_STR(target);
	indir_src.str = target->str;
	indir_src.code = indir_get;
	if (NULL == (obj = cache_get(&indir_src)))
	{
		obj = &object;
		if (valid_mname(&target->str))
		{
			targ_key.var_name = target->str;
			COMPUTE_HASH_MNAME(&targ_key);
			tabent = lookup_hashtab_mname(&curr_symval->h_symtab, &targ_key);
			if (!tabent || !LV_IS_VAL_DEFINED(tabent->value))
				*dst = *value;
			else
				*dst = ((lv_val *)tabent->value)->v;
			dst->mvtype &= ~MV_ALIASCONT;	/* Make sure alias container property does not pass */
			return;
		}
		comp_init(&target->str);
		src = newtriple(OC_IGETSRC);
		switch (TREF(window_token))
		{
		case TK_IDENT:
			if (EXPR_FAIL != (rval = lvn(&v, OC_SRCHINDX, 0)))	/* NOTE assignment */
			{
				s = newtriple(OC_FNGET2);
				s->operand[0] = v;
				s->operand[1] = put_tref(src);
			}
			break;
		case TK_CIRCUMFLEX:
			if (EXPR_FAIL != (rval = gvn()))			/* NOTE assignment */
			{
				r = newtriple(OC_FNGVGET1);
				s = newtriple(OC_FNGVGET2);
				s->operand[0] = put_tref(r);
				s->operand[1] = put_tref(src);
			}
			break;
		case TK_ATSIGN:
			TREF(saw_side_effect) = TREF(shift_side_effects);
			if (TREF(shift_side_effects) && (GTM_BOOL == TREF(gtm_fullbool)))
			{
				dqinit(&tmpchain, exorder);
				oldchain = setcurtchain(&tmpchain);
				if (EXPR_FAIL != (rval = indirection(&v)))	/* NOTE assignment */
				{
					s = newtriple(OC_INDGET);
					s->operand[0] = v;
					s->operand[1] = put_tref(src);
					newtriple(OC_GVSAVTARG);
					setcurtchain(oldchain);
					dqadd(TREF(expr_start), &tmpchain, exorder);
					TREF(expr_start) = tmpchain.exorder.bl;
					triptr = newtriple(OC_GVRECTARG);
					triptr->operand[0] = put_tref(TREF(expr_start));
				} else
					setcurtchain(oldchain);
			} else
			{
				if (EXPR_FAIL != (rval = indirection(&v)))	/* NOTE assignment */
				{
					s = newtriple(OC_INDGET);
					s->operand[0] = v;
					s->operand[1] = put_tref(src);
				}
			}
			break;
		default:
			stx_error(ERR_VAREXPECTED);
			rval = EXPR_FAIL;
			break;
		}
		v = put_tref(s);
		if (EXPR_FAIL == comp_fini(rval, obj, OC_IRETMVAL, &v, target->str.len))
			return;
		indir_src.str.addr = target->str.addr;
		cache_put(&indir_src, obj);
		/* Fall into code activation below */
	}
	*(TREF(ind_result_sp))++ = dst;
	*(TREF(ind_source_sp))++ = value;
	comp_indr(obj);
	return;
}