Example #1
0
*/	void *Use_Port_State(REBSER *port, REBCNT device, REBCNT size)
/*
**		Use private state area in a port. Create if necessary.
**		The size is that of a binary structure used by
**		the port for storing internal information.
**
***********************************************************************/
{
	REBVAL *state = BLK_SKIP(port, STD_PORT_STATE);

	// If state is not a binary structure, create it:
	if (!IS_BINARY(state)) {
		REBSER *data = Make_Binary(size);
		REBREQ *req = (REBREQ*)STR_HEAD(data);
		req->clen = size;
		CLEAR(STR_HEAD(data), size);
		//data->tail = size; // makes it easier for ACCEPT to clone the port
		SET_FLAG(req->flags, RRF_ALLOC); // not on stack
		req->port = port;
		req->device = device;
		Val_Init_Binary(state, data);
	}

	return (void *)VAL_BIN(state);
}
Example #2
0
*/	RL_API int RL_Do_Binary(REBYTE *bin, REBINT length, REBCNT flags, REBCNT key, RXIARG *result)
/*
**	Evaluate an encoded binary script such as compressed text.
**
**	Returns:
**		The datatype of the result or zero if error in the encoding.
**	Arguments:
**		bin - by default, a REBOL compressed UTF-8 (or ASCII) script.
**		length - the length of the data.
**		flags - special flags (set to zero at this time).
**		key - encoding, encryption, or signature key.
**		result - value returned from evaluation.
**	Notes:
**		As of A104, only compressed scripts are supported, however,
**		rebin, cloaked, signed, and encrypted formats will be supported.
**
***********************************************************************/
{
	REBSER spec = {0};
	REBSER *text;
	REBVAL *val;
#ifdef DUMP_INIT_SCRIPT
	int f;
#endif

	//Cloak(TRUE, code, NAT_SPEC_SIZE, &key[0], 20, TRUE);
	spec.data = bin;
	spec.tail = length;
	text = Decompress(&spec, 0, -1, 10000000, 0);
	if (!text) return FALSE;
	Append_Byte(text, 0);

#ifdef DUMP_INIT_SCRIPT
	f = _open("host-boot.r", _O_CREAT | _O_RDWR, _S_IREAD | _S_IWRITE );
	_write(f, STR_HEAD(text), LEN_BYTES(STR_HEAD(text)));
	_close(f);
#endif

	SAVE_SERIES(text);
	val = Do_String(text->data, flags);
	UNSAVE_SERIES(text);
	if (IS_ERROR(val)) // && (VAL_ERR_NUM(val) != RE_QUIT)) {
		Print_Value(val, 1000, FALSE);

	if (result) {
		*result = Value_To_RXI(val);
		return Reb_To_RXT[VAL_TYPE(val)];
	}
	return 0;
}
Example #3
0
STOID Sniff_String(REBSER *ser, REBCNT idx, REB_STRF *sf)
{
	// Scan to find out what special chars the string contains?
	REBYTE *bp = STR_HEAD(ser);
	REBUNI *up = (REBUNI*)bp;
	REBUNI c;
	REBCNT n;

	for (n = idx; n < SERIES_TAIL(ser); n++) {
		c = (BYTE_SIZE(ser)) ? (REBUNI)(bp[n]) : up[n];
		switch (c) {
		case '{':
			sf->brace_in++;
			break;
		case '}':
			sf->brace_out++;
			if (sf->brace_out > sf->brace_in) sf->malign++;
			break;
		case '"':
			sf->quote++;
			break;
		case '\n':
			sf->newline++;
			break;
		default:
			if (c == 0x1e) sf->chr1e += 4; // special case of ^(1e)
			else if (IS_CHR_ESC(c)) sf->escape++;
			else if (c >= 0x1000) sf->paren += 6; // ^(1234)
			else if (c >= 0x100)  sf->paren += 5; // ^(123)
			else if (c >= 0x80)   sf->paren += 4; // ^(12)
		}
	}
	if (sf->brace_in != sf->brace_out) sf->malign++;
}
Example #4
0
//
//  Dump_Stack: C
//
// Prints stack counting levels from the passed in number.  Pass 0 to start.
//
void Dump_Stack(REBFRM *f, REBCNT level)
{
    REBINT n;
    REBVAL *arg;
    REBVAL *param;

    Debug_Fmt(""); // newline.

    if (f == NULL) f = FS_TOP;
    if (f == NULL) {
        Debug_Fmt("*STACK[] - NO FRAMES*");
        return;
    }

    Debug_Fmt(
        "STACK[%d](%s) - %d",
        level,
        STR_HEAD(FRM_LABEL(f)),
        f->eval_type // note: this is now an ordinary Reb_Kind, stringify it
    );

    if (NOT(Is_Any_Function_Frame(f))) {
        Debug_Fmt("(no function call pending or in progress)");
        return;
    }

    n = 1;
    arg = FRM_ARG(f, 1);
    param = FUNC_PARAMS_HEAD(f->func);

    for (; NOT_END(param); ++param, ++arg, ++n) {
        Debug_Fmt(
            "    %s: %72r",
            STR_HEAD(VAL_PARAM_SPELLING(param)),
            arg
        );
    }

    if (f->prior)
        Dump_Stack(f->prior, level + 1);
}
Example #5
0
*/	RL_API int RL_Do_Binary(int *exit_status, const REBYTE *bin, REBINT length, REBCNT flags, REBCNT key, RXIARG *result)
/*
**	Evaluate an encoded binary script such as compressed text.
**
**	Returns:
**		The datatype of the result or zero if error in the encoding.
**	Arguments:
**		bin - by default, a REBOL compressed UTF-8 (or ASCII) script.
**		length - the length of the data.
**		flags - special flags (set to zero at this time).
**		key - encoding, encryption, or signature key.
**		result - value returned from evaluation.
**	Notes:
**		As of A104, only compressed scripts are supported, however,
**		rebin, cloaked, signed, and encrypted formats will be supported.
**
***********************************************************************/
{
	REBSER *text;
#ifdef DUMP_INIT_SCRIPT
	int f;
#endif
	int do_result;

	text = Decompress(bin, length, -1, FALSE, FALSE);
	if (!text) return FALSE;
	Append_Codepoint_Raw(text, 0);

#ifdef DUMP_INIT_SCRIPT
	f = _open("host-boot.r", _O_CREAT | _O_RDWR, _S_IREAD | _S_IWRITE );
	_write(f, STR_HEAD(text), LEN_BYTES(STR_HEAD(text)));
	_close(f);
#endif

	PUSH_GUARD_SERIES(text);
	do_result = RL_Do_String(exit_status, text->data, flags, result);
	DROP_GUARD_SERIES(text);

	Free_Series(text);
	return do_result;
}
Example #6
0
File: f-enbase.c Project: mbk/ren-c
*/	static REBSER *Decode_Base16(const REBYTE **src, REBCNT len, REBYTE delim)
/*
***********************************************************************/
{
	REBYTE *bp;
	const REBYTE *cp;
	REBCNT count = 0;
	REBINT accum = 0;
	REBYTE lex;
	REBINT val;
	REBSER *ser;

	ser = Make_Binary(len / 2);
	bp = STR_HEAD(ser);
	cp = *src;

	for (; len > 0; cp++, len--) {

		if (delim && *cp == delim) break;

		lex = Lex_Map[*cp];

		if (lex > LEX_WORD) {
			val = lex & LEX_VALUE; // char num encoded into lex
			if (!val && lex < LEX_NUMBER) goto err;  // invalid char (word but no val)
			accum = (accum << 4) + val;
			if (count++ & 1) *bp++ = (REBYTE)accum;
		}
		else if (!*cp || lex > LEX_DELIMIT_RETURN) goto err;
	}
	if (count & 1) goto err; // improper modulus

	*bp = 0;
	ser->tail = bp - STR_HEAD(ser);
	return ser;

err:
	Free_Series(ser);
	*src = cp;
	return 0;
}
Example #7
0
xx*/  void Print_Dump_Value(REBVAL *value, REBYTE *label)
/*
**		Dump a value's contents for debugging purposes.
**
***********************************************************************/
{
	REBSER *series;
	series = Copy_Bytes(label, -1);
	SAVE_SERIES(series);
	series = Dump_Value(value, series);
	Debug_Str(STR_HEAD(series));
	UNSAVE_SERIES(series);
}
Example #8
0
File: f-enbase.c Project: mbk/ren-c
*/	static REBSER *Decode_Base2(const REBYTE **src, REBCNT len, REBYTE delim)
/*
***********************************************************************/
{
	REBYTE *bp;
	const REBYTE *cp;
	REBCNT count = 0;
	REBINT accum = 0;
	REBYTE lex;
	REBSER *ser;

	ser = Make_Binary(len >> 3);
	bp = BIN_HEAD(ser);
	cp = *src;

	for (; len > 0; cp++, len--) {

		if (delim && *cp == delim) break;

		lex = Lex_Map[*cp];

		if (lex >= LEX_NUMBER) {

			if (*cp == '0') accum *= 2;
			else if (*cp == '1') accum = (accum * 2) + 1;
			else goto err;

			if (count++ >= 7) {
				*bp++ = (REBYTE)accum;
				count = 0;
				accum = 0;
			}
		}
		else if (!*cp || lex > LEX_DELIMIT_RETURN) goto err;
	}
	if (count) goto err; // improper modulus

	*bp = 0;
	ser->tail = bp - STR_HEAD(ser);
	return ser;

err:
	Free_Series(ser);
	*src = cp;
	return 0;
}
Example #9
0
File: f-enbase.c Project: mbk/ren-c
*/	static REBSER *Decode_Base64(const REBYTE **src, REBCNT len, REBYTE delim)
/*
***********************************************************************/
{
	REBYTE *bp;
	const REBYTE *cp;
	REBCNT flip = 0;
	REBINT accum = 0;
	REBYTE lex;
	REBSER *ser;

	// Allocate buffer large enough to hold result:
	// Accounts for e bytes decoding into 3 bytes.
	ser = Make_Binary(((len + 3) * 3) / 4);
	bp = STR_HEAD(ser);
	cp = *src;

	for (; len > 0; cp++, len--) {

		// Check for terminating delimiter (optional):
		if (delim && *cp == delim) break;

		// Check for char out of range:
		if (*cp > 127) {
			if (*cp == 0xA0) continue;  // hard space
			goto err;
		}

		lex = Debase64[*cp];

		if (lex < BIN_SPACE) {

			if (*cp != '=')	{
				accum = (accum << 6) + lex;
				if (flip++ == 3) {
					*bp++ = (REBYTE)(accum >> 16);
					*bp++ = (REBYTE)(accum >> 8);
					*bp++ = (REBYTE)(accum);
					accum = 0;
					flip = 0;
				}
			} else {
Example #10
0
*/  REBSER *Prep_String(REBSER *series, REBYTE **str, REBCNT len)
/*
**		Helper function for the string related Mold functions below.
**		Creates or expands the series and provides the location to
**		copy text into.
**
***********************************************************************/
{
	REBCNT tail;

	if (!series) {
		series = Make_Binary(len);
		series->tail = len;
		*str = STR_HEAD(series);
	}
	else {
		tail = SERIES_TAIL(series);
		EXPAND_SERIES_TAIL(series, len);
		*str = STR_SKIP(series, tail);
	}
	return series;
}
Example #11
0
//
//  Dump_Values: C
// 
// Print values in raw hex; If memory is corrupted this still needs to work.
//
void Dump_Values(RELVAL *vp, REBCNT count)
{
    REBYTE buf[2048];
    REBYTE *cp;
    REBCNT l, n;
    REBCNT *bp = (REBCNT*)vp;
    const REBYTE *type;

    cp = buf;
    for (l = 0; l < count; l++) {
        REBVAL *val = cast(REBVAL*, bp);
        cp = Form_Hex_Pad(cp, l, 8);

        *cp++ = ':';
        *cp++ = ' ';

        type = Get_Type_Name((REBVAL*)bp);
        for (n = 0; n < 11; n++) {
            if (*type) *cp++ = *type++;
            else *cp++ = ' ';
        }
        *cp++ = ' ';
        for (n = 0; n < sizeof(REBVAL) / sizeof(REBCNT); n++) {
            cp = Form_Hex_Pad(cp, *bp++, 8);
            *cp++ = ' ';
        }
        n = 0;
        if (IS_WORD(val) || IS_GET_WORD(val) || IS_SET_WORD(val)) {
            const REBYTE *name = STR_HEAD(VAL_WORD_SPELLING(val));
            n = snprintf(
                s_cast(cp), sizeof(buf) - (cp - buf), " (%s)", cs_cast(name)
            );
        }

        *(cp + n) = 0;
        Debug_Str(s_cast(buf));
        cp = buf;
    }
}
Example #12
0
xx*/  void Dump_Block(REBVAL *blk, REBINT len)
/*
**		Dump a block's contents for debugging purposes.
**
***********************************************************************/
{
	REBSER *series;
	//REBVAL *blk = BLK_HEAD(block);

	//Print("BLOCK: %x Tail: %d Size: %d", block, block->tail, block->rest);
	// change to a make string!!!  no need to append to a series, this is a debug function
	series = Make_Binary(100);
	Append_Bytes(series, "[\n");
	while (NOT_END(blk) && len-- > 0) {
		Append_Byte(series, '\t');
		Dump_Value(blk, series);
		Append_Byte(series, '\n');
		blk++;
	}
	Append_Byte(series, ']');
	*STR_TAIL(series) = 0;
	Debug_Str(STR_HEAD(series));
}
Example #13
0
STOID Mold_String_Series(REBVAL *value, REB_MOLD *mold)
{
	REBCNT len = VAL_LEN(value);
	REBSER *ser = VAL_SERIES(value);
	REBCNT idx = VAL_INDEX(value);
	REB_STRF sf = {0};
	REBYTE *bp;
	REBUNI *up;
	REBUNI *dp;
	REBOOL uni = !BYTE_SIZE(ser);
	REBCNT n;
	REBUNI c;

	// Empty string:
	if (idx >= VAL_TAIL(value)) {
		Append_Bytes(mold->series, "\"\"");  //Trap0(RE_PAST_END);
		return;
	}

	Sniff_String(ser, idx, &sf);
	if (!GET_MOPT(mold, MOPT_ANSI_ONLY)) sf.paren = 0;

	// Source can be 8 or 16 bits:
	if (uni) up = UNI_HEAD(ser);
	else bp = STR_HEAD(ser);

	// If it is a short quoted string, emit it as "string":
	if (len <= MAX_QUOTED_STR && sf.quote == 0 && sf.newline < 3) {

		dp = Prep_Uni_Series(mold, len + sf.newline + sf.escape + sf.paren + sf.chr1e + 2);

		*dp++ = '"';

		for (n = idx; n < VAL_TAIL(value); n++) {
			c = uni ? up[n] : (REBUNI)(bp[n]);
			dp = Emit_Uni_Char(dp, c, (REBOOL)GET_MOPT(mold, MOPT_ANSI_ONLY)); // parened
		}

		*dp++ = '"';
		*dp = 0;
		return;
	}

	// It is a braced string, emit it as {string}:
	if (!sf.malign) sf.brace_in = sf.brace_out = 0;

	dp = Prep_Uni_Series(mold, len + sf.brace_in + sf.brace_out + sf.escape + sf.paren + sf.chr1e + 2);

	*dp++ = '{';

	for (n = idx; n < VAL_TAIL(value); n++) {

		c = uni ? up[n] : (REBUNI)(bp[n]);
		switch (c) {
		case '{':
		case '}':
			if (sf.malign) {
				*dp++ = '^';
				*dp++ = c;
				break;
			}
		case '\n':
		case '"':
			*dp++ = c;
			break;
		default:
			dp = Emit_Uni_Char(dp, c, (REBOOL)GET_MOPT(mold, MOPT_ANSI_ONLY)); // parened
		}
	}

	*dp++ = '}';
	*dp = 0;
}
Example #14
0
//
//  MAKE_Tuple: C
//
REB_R MAKE_Tuple(
    REBVAL *out,
    enum Reb_Kind kind,
    const REBVAL *opt_parent,
    const REBVAL *arg
){
    assert(kind == REB_TUPLE);
    if (opt_parent)
        fail (Error_Bad_Make_Parent(kind, opt_parent));

    if (IS_TUPLE(arg))
        return Move_Value(out, arg);

    RESET_CELL(out, REB_TUPLE, CELL_MASK_NONE);
    REBYTE *vp = VAL_TUPLE(out);

    // !!! Net lookup parses IP addresses out of `tcp://93.184.216.34` or
    // similar URL!s.  In Rebol3 these captures come back the same type
    // as the input instead of as STRING!, which was a latent bug in the
    // network code of the 12-Dec-2012 release:
    //
    // https://github.com/rebol/rebol/blob/master/src/mezz/sys-ports.r#L110
    //
    // All attempts to convert a URL!-flavored IP address failed.  Taking
    // URL! here fixes it, though there are still open questions.
    //
    if (IS_TEXT(arg) or IS_URL(arg)) {
        REBSIZ size;
        const REBYTE *bp
            = Analyze_String_For_Scan(&size, arg, MAX_SCAN_TUPLE);

        if (Scan_Tuple(out, bp, size) == nullptr)
            fail (arg);
        return out;
    }

    if (ANY_ARRAY(arg)) {
        REBCNT len = 0;
        REBINT n;

        RELVAL *item = VAL_ARRAY_AT(arg);

        for (; NOT_END(item); ++item, ++vp, ++len) {
            if (len >= MAX_TUPLE)
                goto bad_make;
            if (IS_INTEGER(item)) {
                n = Int32(item);
            }
            else if (IS_CHAR(item)) {
                n = VAL_CHAR(item);
            }
            else
                goto bad_make;

            if (n > 255 || n < 0)
                goto bad_make;
            *vp = n;
        }

        VAL_TUPLE_LEN(out) = len;

        for (; len < MAX_TUPLE; len++) *vp++ = 0;
        return out;
    }

    REBCNT alen;

    if (IS_ISSUE(arg)) {
        REBSTR *spelling = VAL_STRING(arg);
        const REBYTE *ap = STR_HEAD(spelling);
        size_t size = STR_SIZE(spelling); // UTF-8 len
        if (size & 1)
            fail (arg); // must have even # of chars
        size /= 2;
        if (size > MAX_TUPLE)
            fail (arg); // valid even for UTF-8
        VAL_TUPLE_LEN(out) = size;
        for (alen = 0; alen < size; alen++) {
            REBYTE decoded;
            if ((ap = Scan_Hex2(&decoded, ap)) == NULL)
                fail (arg);
            *vp++ = decoded;
        }
    }
    else if (IS_BINARY(arg)) {
        REBYTE *ap = VAL_BIN_AT(arg);
        REBCNT len = VAL_LEN_AT(arg);
        if (len > MAX_TUPLE) len = MAX_TUPLE;
        VAL_TUPLE_LEN(out) = len;
        for (alen = 0; alen < len; alen++) *vp++ = *ap++;
    }
    else
        fail (arg);

    for (; alen < MAX_TUPLE; alen++) *vp++ = 0;
    return out;

  bad_make:
    fail (Error_Bad_Make(REB_TUPLE, arg));
}