Esempio n. 1
0
/*
 * replace ntok tokens starting at dtr->tp with the contents of str.
 * tp ends up pointing just beyond the replacement.
 * Canonical whitespace is assured on each side.
 */
void
insertrow(Tokenrow *dtr, int ntok, Tokenrow *str)
{
	int nrtok = rowlen(str);

	dtr->tp += ntok;
	adjustrow(dtr, nrtok-ntok);
	dtr->tp -= ntok;
	movetokenrow(dtr, str);
	makespace(dtr);
	dtr->tp += nrtok;
	makespace(dtr);
}
/*
解析提交的数据
返回(表单域=表单值)对的个数
*/
int get_input(FORM_VAR *nv)
{
	char *method;
	char *form_data=0;
	char *form_data_ptr;
	char tmp[250];
	int data_len,i;
	//读取环境变量”REQUEST_METHOD”,
        //获取提交数据的方式。
	method=getenv("REQUEST_METHOD");
	/*以GET方式传数据*/
	if(strcmp(method,"GET")==0)
	{
		//从环境变量UERY_STRING 中取出提交数据
		char *data_ptr=getenv("QUERY_STRING");
		data_len=strlen(data_ptr);
		form_data=(char*)malloc(sizeof(char)*(data_len+1));
		strcpy(form_data,data_ptr);
		form_data[data_len]='\0';
	}
	/*以POST方法传数据*/
	else if(strcmp(method,"POST")==0)
	{
		//从标准输入输出中读取相应的字符串,
		//读取长度有环境变量CONTENT_LENGTH 决定
		data_len=atoi(getenv("CONTENT_LENGTH"));
		form_data=(char*)malloc(sizeof(char)*(data_len+1));
		fread(form_data,1,data_len,stdin);
	}

	i=0;
	form_data_ptr=form_data;
	//分离出表单域和值
	while(form_data_ptr[0] != '\0')
	{
		//分理处表单域
		memset(tmp, 0, 250);		
		split(form_data_ptr,'=',tmp);
		makespace(tmp);
		convert(tmp);
		strcpy(nv[i].name,tmp);
		//分离出值
		split(form_data_ptr,'&',tmp);
		makespace(tmp);
		convert(tmp);
		strcpy(nv[i].value,tmp);
		i++;
	}
	free(form_data);
	return i--;
}
Esempio n. 3
0
/*
 * Find the first instance of a sub-string "pattern" in the string "str",
 * and replace it with the string "replacement".
 *   str (IN/OUT)	target string (pointer to in case of expansion)
 *   pattern (IN)	substring to look for in str
 *   replacement (IN)   string with which to replace the "pattern" string
 */
void _xstrsubstitute(char **str, const char *pattern, const char *replacement)
{
	int pat_len, rep_len;
	char *ptr, *end_copy;
	int pat_offset;

	if (*str == NULL || pattern == NULL || pattern[0] == '\0')
		return;

	if ((ptr = strstr(*str, pattern)) == NULL)
		return;
	pat_offset = ptr - (*str);
	pat_len = strlen(pattern);
	if (replacement == NULL)
		rep_len = 0;
	else
		rep_len = strlen(replacement);

	end_copy = xstrdup(ptr + pat_len);
	if (rep_len != 0) {
		makespace(str, rep_len-pat_len);
		strcpy((*str)+pat_offset, replacement);
	}
	strcpy((*str)+pat_offset+rep_len, end_copy);
	xfree(end_copy);
}
Esempio n. 4
0
/*
 * substitute the argument list into the replacement string
 *  This would be simple except for ## and #
 */
void
    substargs(Nlist * np, Tokenrow * rtr, Tokenrow ** atr)
{
    Tokenrow tatr;
    Token *tp;
    int ntok, argno;

    for (rtr->tp = rtr->bp; rtr->tp < rtr->lp;)
    {
        if (rtr->tp->type == SHARP)
        {                               /* string operator */
            tp = rtr->tp;
            rtr->tp += 1;
            if ((argno = lookuparg(np, rtr->tp)) < 0)
            {
                error(ERROR, "# not followed by macro parameter");
                continue;
            }
            ntok = 1 + (int)(rtr->tp - tp);
            rtr->tp = tp;
            insertrow(rtr, ntok, stringify(atr[argno]));
            continue;
        }
        if (rtr->tp->type == NAME
            && (argno = lookuparg(np, rtr->tp)) >= 0)
        {
            if (((rtr->tp + 1) < rtr->lp && (rtr->tp + 1)->type == DSHARP)
                || (rtr->tp != rtr->bp  && (rtr->tp - 1)->type == DSHARP))
            {
                copytokenrow(&tatr, atr[argno]);
                makespace(&tatr, rtr->tp);
                insertrow(rtr, 1, &tatr);
                dofree(tatr.bp);
            }
            else
            {
                copytokenrow(&tatr, atr[argno]);
                makespace(&tatr, rtr->tp);
                expandrow(&tatr, "<macro>");
                insertrow(rtr, 1, &tatr);
                dofree(tatr.bp);
            }
            continue;
        }
        rtr->tp++;
    }
}
Esempio n. 5
0
/*
 * Concatenate len of str2 onto str1, expanding str1 as needed.
 *   str1 (IN/OUT)	target string (pointer to in case of expansion)
 *   str2 (IN)		source string
 *   len (IN)		len of str2 to concat
 */
void _xstrncat(char **str1, const char *str2, size_t len)
{
	if (str2 == NULL)
		str2 = "(null)";

	makespace(str1, len);
	strncat(*str1, str2, len);
}
Esempio n. 6
0
/*
 * Concatenate str2 onto str1, expanding str1 as needed.
 *   str1 (IN/OUT)	target string (pointer to in case of expansion)
 *   str2 (IN)		source string
 */
void _xstrcat(char **str1, const char *str2)
{
	if (str2 == NULL)
		str2 = "(null)";

	makespace(str1, strlen(str2));
	strcat(*str1, str2);
}
Esempio n. 7
0
/* 將表單資料解碼,結果存入nv陣列中 */
int get_input(nv_set* nv) {
    char*  method;
    char*  my_data = 0;
    char*  tmp_ptr, *tmp;
    int   data_len;
    int   i;
    /* 表單以GET方法傳送資料 */
    method = getenv("REQUEST_METHOD");

    if (strcmp(method, "GET") == 0) {
        tmp_ptr = getenv("QUERY_STRING");
        data_len = strlen(tmp_ptr);
        /* 將表單編碼資料存入my_data中 */
        my_data = (char*)malloc(sizeof(char) * (data_len + 1));
        strcpy(my_data, getenv("QUERY_STRING"));
        my_data[data_len] = '\0';
    }

    /* 表單以POST方法傳送資料 */
    if (strcmp(method, "POST") == 0) {
        data_len = atoi(getenv("CONTENT_LENGTH"));
        /* 將表單編碼資料存入my_data中 */
        my_data = (char*)malloc(sizeof(char) * (data_len + 1));
        fread(my_data, 1, data_len, stdin);
    }

    i = 0;

    while (my_data[0] != '\0') {
        tmp = split(my_data, '='); // 分離資料對,取得欄位名
        makespace(tmp);     // 將+號還原成空白字元
        tmp = convert(tmp);     // 將十六進位碼還原成字元
        strcpy(nv[i].name, tmp); // 結果存入nv結構的name成員
        tmp = split(my_data, '&'); // 分離資料對,取得欄位值
        makespace(tmp);     // 將+號還原成空白字元
        tmp = convert(tmp);     // 將十六進位碼還原成字元
        strcpy(nv[i].value, tmp);   // 結果存入nv結構的value成員
        i++;
    }

    return i--;           // 傳回實際解碼的欄位數
}
Esempio n. 8
0
void Buffer::append(const char *data , size_t len)
{
    if(len > nonMakeSpaceWritable() && len <= nonAppendWritable())
	makespace();

    std::copy(data , data + len , &ibuf_[writeidx_]);

    writeidx_ += len;

    assert(readidx_ <= writeidx_ && writeidx_ < ibuf_.size());
}
Esempio n. 9
0
/*
 * Evaluate the ## operators in a tokenrow
 */
void
doconcat(Tokenrow *trp)
{
	Token *ltp, *ntp;
	STATIC Tokenrow ntr;
	int len;

	CHECKIN();
	for (trp->tp=trp->bp; trp->tp<trp->lp; trp->tp++) {
		if (trp->tp->type==DSHARP1)
			trp->tp->type = DSHARP;
		else if (trp->tp->type==DSHARP) {
			STATIC char tt[128];
			ltp = trp->tp-1;
			ntp = trp->tp+1;
			if (ltp<trp->bp || ntp>=trp->lp) {
				error(ERROR, "## occurs at border of replacement");
				continue;
			}
			len = ltp->len + ntp->len;
			strncpy((char*)tt, (char*)ltp->t, ltp->len);
			strncpy((char*)tt+ltp->len, (char*)ntp->t, ntp->len);
			tt[len] = '\0';
			setsource("<##>", -1, tt);
			maketokenrow(3, &ntr);
			gettokens(&ntr, 1);
			unsetsource();
			if (ntr.lp-ntr.bp!=2 || ntr.bp->type==UNCLASS)
				error(WARNING, "Bad token %r produced by ##", &ntr);
			ntr.lp = ntr.bp+1;
			trp->tp = ltp;
			makespace(&ntr);
			insertrow(trp, (ntp-ltp)+1, &ntr);
			dofree(ntr.bp);
			trp->tp--;
		}
	}
	CHECKOUT();
}
Esempio n. 10
0
/*
 * rmap_grab()
 *	Grab the requested range, or return failure if any of it is not free
 *
 * Returns 0 on success, 1 on failure.
 */
int
rmap_grab(struct rmap *rmap, uint off, uint size)
{
	struct rmap *r, *rlim;
	uint x, top, rtop;

	rlim = &rmap[rmap->r_off];
	for (r = &rmap[1]; r <= rlim; ++r) {
		/*
		 * If we've advanced beyond the requested offset,
		 * we can never match, so end the loop.
		 */
		if (r->r_off > off) {
			break;
		}

		/*
		 * See if this is the range which will hold our request
		 */
		top = r->r_off + r->r_size;
		if (!((r->r_off <= off) && (top > off))) {
			continue;
		}

		/*
		 * Since this run encompasses the requested range, we
		 * can either grab all of it, or none of it.
		 */

		/*
		 * The top of our request extends beyond the block; fail.
		 */
		rtop = off + size;
		if (rtop > top) {
			return(1);
		}

		/*
		 * If the requested start matches our range's start, we
		 * can simply shave it off the front.
		 */
		if (off == r->r_off) {
			r->r_off += size;
			r->r_size -= size;
			if (r->r_size == 0) {
				collapse(rmap, r);
			}
			return(0);
		}

		/*
		 * Similarly, if the end matches, we can shave the end
		 */
		if (rtop == top) {
			r->r_size -= size;

			/*
			 * We know r_size > 0, since otherwise we would've
			 * matched the previous case otherwise.
			 */
			ASSERT_DEBUG(r->r_size > 0, "phase error");

			return(0);
		}

		/*
		 * Otherwise we must split the range
		 */
		if (makespace(rmap, r)) {
			uint osize;

			/*
			 * No room for further fragmentation, so chop off
			 * to the tail.
			 */
			osize = r->r_size;
			r->r_size = top - rtop;
			lost_elems += (osize - r->r_size) - size;
			r->r_off = rtop;
			return(0);
		}

		/*
		 * The current slot is everything below us
		 */
		r->r_size = off - r->r_off;

		/*
		 * The new slot is everything above
		 */
		++r;
		r->r_off = rtop;
		r->r_size = top - rtop;

		/*
		 * OK
		 */
		return(0);
	}

	/*
	 * Nope, not in our range of free entries
	 */
	return(1);
}
Esempio n. 11
0
/*
 * rmap_free()
 *	Free some space back into the resource map
 *
 * The list is kept ordered, with the first free element flagged
 * with a size of 0.
 */
void
rmap_free(struct rmap *rmap, uint off, uint size)
{
	struct rmap *r, *rlim;

	ASSERT_DEBUG(off, "rmap_free: zero off");
	ASSERT_DEBUG(size > 0, "rmap_free: zero size");
	/*
	 * Scan forward until we find the place we should be
	 * inserted.
	 */
	rlim = &rmap[rmap->r_off];
	for (r = &rmap[1]; r <= rlim; ++r) {
		/*
		 * If the new free space abuts this entry, tack it
		 * on and return.
		 */
		if ((r->r_off + r->r_size) == off) {
			r->r_size += size;
			/*
			 * If this entry now abuts the next, coalesce
			 */
			if ((r < rlim) && ((r->r_off+r->r_size) ==
					(r[1].r_off))) {
				r->r_size += r[1].r_size;
				rmap->r_off -= 1;
				++r;
				if (r < rlim) {
					bcopy(r+1, r,
					 sizeof(struct rmap)*(rlim-r));
				}
			}
			return;
		}

		/*
		 * If this space abuts the entry, pad it onto
		 * the beginning.
		 */
		if ((off + size) == r->r_off) {
			r->r_size += size;
			r->r_off = off;
			return;
		}

		if (off < r->r_off)
			break;
	}

	/*
	 * Need to add a new element.  See if it'll fit.
	 */
	if (makespace(rmap, r)) {
		/*
		 * Nope.  Tabulate and lose the space.
		 */
		lost_elems += size;
		return;
	}

	/*
	 * Record it
	 */
	r->r_off = off;
	r->r_size = size;
}
Esempio n. 12
0
/*
 * Add a character to str, expanding str1 as needed.
 *   str1 (IN/OUT)	target string (pointer to in case of expansion)
 *   c (IN)		character to add
 */
void _xstrcatchar(char **str, char c)
{
	makespace(str, 1);
	strcatchar(*str, c);
}
Esempio n. 13
0
/*
 * Gather an arglist, starting in trp with tp pointing at the macro name.
 * Return total number of tokens passed, stash number of args found.
 * trp->tp is not changed relative to the tokenrow.
 */
int
gatherargs(Tokenrow *trp, Tokenrow **atr, int *narg)
{
	int parens = 1;
	int ntok = 0;
	Token *bp, *lp;
	Tokenrow ttr;
	int ntokp;
	int needspace;

	*narg = -1;			/* means that there is no macro call */
	/* look for the ( */
	for (;;) {
		trp->tp++;
		ntok++;
		if (trp->tp >= trp->lp) {
			gettokens(trp, 0);
			if ((trp->lp-1)->type==END) {
				trp->lp -= 1;
				trp->tp -= ntok;
				return ntok;
			}
		}
		if (trp->tp->type==LP)
			break;
		if (trp->tp->type!=NL)
			return ntok;
	}
	*narg = 0;
	ntok++;
	ntokp = ntok;
	trp->tp++;
	/* search for the terminating ), possibly extending the row */
	needspace = 0;
	while (parens>0) {
		if (trp->tp >= trp->lp)
			gettokens(trp, 0);
		if (needspace) {
			needspace = 0;
			makespace(trp);
		}
		if (trp->tp->type==END) {
			trp->lp -= 1;
			trp->tp -= ntok;
			error(ERROR, "EOF in macro arglist");
			return ntok;
		}
		if (trp->tp->type==NL) {
			trp->tp += 1;
			adjustrow(trp, -1);
			trp->tp -= 1;
			makespace(trp);
			needspace = 1;
			continue;
		}
		if (trp->tp->type==LP)
			parens++;
		else if (trp->tp->type==RP)
			parens--;
		trp->tp++;
		ntok++;
	}
	trp->tp -= ntok;
	/* Now trp->tp won't move underneath us */
	lp = bp = trp->tp+ntokp;
	for (; parens>=0; lp++) {
		if (lp->type == LP) {
			parens++;
			continue;
		}
		if (lp->type==RP)
			parens--;
		if (lp->type==DSHARP)
			lp->type = DSHARP1;	/* ## not special in arg */
		if (lp->type==COMMA && parens==0 || parens<0 && (lp-1)->type!=LP) {
			if (*narg>=NARG-1)
				error(FATAL, "Sorry, too many macro arguments");
			ttr.bp = ttr.tp = bp;
			ttr.lp = lp;
			atr[(*narg)++] = normtokenrow(&ttr);
			bp = lp+1;
		}
	}
	return ntok;
}
Esempio n. 14
0
/*
 * Evaluate the ## operators in a tokenrow
 */
void
    doconcat(Tokenrow * trp)
{
    Token *ltp, *ntp;
    Tokenrow ntr;
    size_t len;

    for (trp->tp = trp->bp; trp->tp < trp->lp; trp->tp++)
    {
        if (trp->tp->type == DSHARP1)
            trp->tp->type = DSHARP;
        else
            if (trp->tp->type == DSHARP)
            {
                int  i;
                char tt[NCONCAT];

                ltp = trp->tp - 1;
                ntp = trp->tp + 1;

                if (ltp < trp->bp || ntp >= trp->lp)
                {
                    error(ERROR, "## occurs at border of replacement");
                    continue;
                }

                ntp = ltp;
                i   = 1;
                len = 0;

                do
                {
                    if (len + ntp->len + ntp->wslen > sizeof(tt))
                    {
                        error(ERROR, "## string concatination buffer overrun");
                        break;
                    }

                    if (ntp != trp->tp + 1)
                    {
                        strncpy((char *) tt + len, (char *) ntp->t - ntp->wslen,
                                ntp->len + ntp->wslen);
                        len += ntp->len + ntp->wslen;
                    }
                    else    // Leerzeichen um ## herum entfernen:
                    {
                        strncpy((char *) tt + len, (char *) ntp->t, ntp->len);
                        len += ntp->len;
                    }

                    ntp = trp->tp + i;
                    i++;
                }
                while (ntp < trp->lp);

                tt[len] = '\0';
                setsource("<##>", -1, -1, tt, 0);
                maketokenrow(3, &ntr);
                gettokens(&ntr, 1);
                unsetsource();
                if (ntr.bp->type == UNCLASS)
                    error(WARNING, "Bad token %r produced by ##", &ntr);
                while ((ntr.lp-1)->len == 0 && ntr.lp != ntr.bp)
                    ntr.lp--;

                doconcat(&ntr);
                trp->tp = ltp;
                makespace(&ntr, ltp);
                insertrow(trp, (int)(ntp - ltp), &ntr);
                dofree(ntr.bp);
                trp->tp--;
            }
    }
}
Esempio n. 15
0
/*
 * Expand the macro whose name is np, at token trp->tp, in the tokenrow.
 * Return trp->tp at the first token next to be expanded
 * (ordinarily the beginning of the expansion)
 * I.e.: the same position as before!
 * Only one expansion is performed, then we return to the expandrow()
 * loop and start at same position.
 */
void
    expand(Tokenrow * trp, Nlist * np, MacroValidatorList * pValidators)
{
    Tokenrow ntr;
    int ntokc, narg;
    Tokenrow *atr[NARG + 1];

    if (Mflag == 2)
    {
        if (np->ap)
            error(INFO, "Macro expansion of %t with %s(%r)", trp->tp, np->name, np->ap);
        else
            error(INFO, "Macro expansion of %t with %s", trp->tp, np->name);
    }

    copytokenrow(&ntr, np->vp);         /* copy macro value */
    if (np->ap == NULL)                 /* parameterless */
        ntokc = 1;
    else
    {
        int i;

        ntokc = gatherargs(trp, atr, &narg);
        if (narg < 0)
        {                               /* not actually a call (no '(') */
            trp->tp++;
            return;
        }
        if (narg != rowlen(np->ap))
        {
            error(ERROR, "Disagreement in number of macro arguments");
            trp->tp += ntokc;
            return;
        }

        /** If gatherargs passed a macro validating token, this token
            must become valid here.
            trp->tp+0 was checked in expandrow(), so we don't need to do it
            again here:
        */
        for (i = 1; i < ntokc; i++)
        {
            mvl_check(pValidators,trp->tp+i);
        }

        substargs(np, &ntr, atr);       /* put args into replacement */
        for (i = 0; i < narg; i++)
        {
            dofree(atr[i]->bp);
            dofree(atr[i]);
        }
    }

    doconcat(&ntr);                     /* execute ## operators */
    ntr.tp = ntr.bp;
    makespace(&ntr, trp->tp);

    tokenrow_zeroTokenIdentifiers(&ntr);
    insertrow(trp, ntokc, &ntr);

        /* add validator for just invalidated macro:
        */
    np->flag |= ISACTIVE;
    if (trp->tp != trp->lp)
    {   /* tp is a valid pointer: */
        mvl_add(pValidators,np,trp->tp);
    }
    else
    {   /* tp is == lp, therefore does not point to valid memory: */
        mvl_add(pValidators,np,0);
    }
        /* reset trp->tp to original position:
        */
    trp->tp -= ntr.lp - ntr.bp;         /* so the result will be tested for macros from the same position again */

    dofree(ntr.bp);

    return;
}