Esempio n. 1
0
void fxParseJSONArray(txMachine* the, txJSONParser* theParser)
{
	txSlot* anArray;
	txIndex aLength;
	txSlot* anItem;

	fxGetNextJSONToken(the, theParser);
	mxPush(mxArrayPrototype);
	anArray = fxNewArrayInstance(the);
	aLength = 0;
	anItem = fxLastProperty(the, anArray);
	for (;;) {
		if (theParser->token == XS_JSON_TOKEN_RIGHT_BRACKET)
			break;
		fxParseJSONValue(the, theParser);
		aLength++;
		anItem->next = fxNewSlot(the);
		anItem = anItem->next;
		anItem->kind = the->stack->kind;
		anItem->value = the->stack->value;
		the->stack++;
		if (theParser->token != XS_JSON_TOKEN_COMMA)
			break;
		fxGetNextJSONToken(the, theParser);
	}
	anArray->next->value.array.length = aLength;
	fxCacheArray(the, anArray);
	if (theParser->token != XS_JSON_TOKEN_RIGHT_BRACKET)
		mxSyntaxError("missing ]");
	fxGetNextJSONToken(the, theParser);
}
Esempio n. 2
0
void fxParseJSONArray(txScriptParser* theParser)
{
	txMachine* the = theParser->the;
	txSlot* anArray;
	txIndex aLength;
	txSlot* anItem;

	fxGetNextJSONToken(theParser);
	*(--the->stack) = mxArrayPrototype;
	anArray = fxNewArrayInstance(the);
	aLength = 0;
	anItem = anArray->next;
	for (;;) {
		if (theParser->token == XS_TOKEN_RIGHT_BRACKET)
			break;
		fxParseJSONValue(theParser);
		aLength++;
		anItem->next = fxNewSlot(the);
		anItem = anItem->next;
		anItem->kind = the->stack->kind;
		anItem->value = the->stack->value;
		the->stack++;
		if (theParser->token != XS_TOKEN_COMMA)
			break;
		fxGetNextJSONToken(theParser);
	}
	anArray->next->value.array.length = aLength;
	fxCacheArray(the, anArray);
	if (theParser->token != XS_TOKEN_RIGHT_BRACKET)
		fxReportParserError(theParser, "missing ]");
	fxGetNextJSONToken(theParser);
}
Esempio n. 3
0
void fx_Function_bind(txMachine* the)
{
	txSlot* aFunction;
	txSlot* aProperty;
	txSlot* anArray;
	txSlot* anItem;
	txSize aCount, anIndex;

	aFunction = fxGetInstance(the, mxThis);
	if (!mxIsFunction(aFunction))
		mxDebug0(the, XS_TYPE_ERROR, "this is no Function");
	if (mxArgc < 1)
		mxDebug0(the, XS_SYNTAX_ERROR, "Function.prototype.bind: no this parameter");
		
	aProperty = aFunction->next;
	if (aProperty->kind == XS_CODE_KIND)
		aCount = *(aProperty->value.code + 4);
	else
		aCount = aProperty->value.callback.length;
	aCount -= mxArgc - 1;
	if (aCount < 0)
		aCount = 0;
		
	mxPush(mxFunctionPrototype);
	aFunction = fxNewFunctionInstance(the);
	*mxResult = *(the->stack++);
	aProperty = aFunction->next;
	aProperty->kind = XS_CALLBACK_KIND;
	aProperty->value.callback.address = fx_Function_bound;
	aProperty->value.callback.length = aCount;
	
	aProperty = fxSetProperty(the, aFunction, fxID(the, "boundFunction"), C_NULL);
	aProperty->kind = mxThis->kind;
	aProperty->value = mxThis->value;
	aProperty = fxSetProperty(the, aFunction, fxID(the, "boundThis"), C_NULL);
	aProperty->kind = mxArgv(0)->kind;
	aProperty->value = mxArgv(0)->value;
	aProperty = fxSetProperty(the, aFunction, fxID(the, "boundArguments"), C_NULL);
	mxPush(mxArrayPrototype);
	anArray = fxNewArrayInstance(the);
	aProperty->kind = the->stack->kind;
	aProperty->value = the->stack->value;
	the->stack++;
	anItem = anArray->next;
	for (anIndex = 1; anIndex < mxArgc; anIndex++) {
		anItem->next = fxNewSlot(the);
		anItem = anItem->next;
		anItem->kind = mxArgv(anIndex)->kind;
		anItem->value = mxArgv(anIndex)->value;
	}
	anArray->next->value.array.length = mxArgc - 1;
	fxCacheArray(the, anArray);
}
Esempio n. 4
0
void fx_Array(txMachine* the)
{
	txIndex count = (txIndex)mxArgc;
	txBoolean flag = 0;
	txSlot* instance;
	txSlot* array;
	txSlot* argument;
	txSlot* slot;
	if (mxTarget->kind == XS_UNDEFINED_KIND) {
		mxPush(mxArrayPrototype);
		instance = fxNewArrayInstance(the);
		mxPullSlot(mxResult);
		array = instance->next;	
	}
	else
		array = fxCoerceToArray(the, mxThis);
	flag = 0;
	if (count == 1) {
		argument = mxArgv(0);
		if (argument->kind == XS_INTEGER_KIND) {
			flag = 1;
			if ((0 <= argument->value.integer) && (argument->value.integer < XS_MAX_INDEX))
				count = (txIndex)argument->value.integer;
			else
				mxRangeError("invalid length");
		}
		else if (mxArgv(0)->kind == XS_NUMBER_KIND) {
			flag = 1;
			if ((0 <= argument->value.number) && (argument->value.number < XS_MAX_INDEX))
				count = (txIndex)argument->value.number;
			else
				mxRangeError("invalid length");
		}
	}
	array->value.array.address = (txSlot *)fxNewChunk(the, count * sizeof(txSlot));
	array->value.array.length = count;
	slot = array->value.array.address;
	if (flag) {
		c_memset(slot, 0, count * sizeof(txSlot));
	}
	else {
		txIndex index = 0;
		while (index < count) {
			txSlot* argument = mxArgv(index);
			slot->ID = XS_NO_ID;
			slot->kind = argument->kind;
			slot->value = argument->value;
			slot++;
			index++;
		}
	}
}
Esempio n. 5
0
void fxBuildHosts(txMachine* the, txInteger c, txHostFunctionBuilder* builder)
{
	mxPushInteger(c);
	mxPushInteger(1);
	mxPush(mxArrayPrototype);
	fxNewArrayInstance(the);
	fxArrayCacheBegin(the, the->stack);
	while (c) {
		if (builder->length >= 0)
			fxNewHostFunction(the, builder->callback, builder->length, (builder->id >= 0) ? ((txID*)(the->code))[builder->id] : XS_NO_ID);
		else
			fxNewHostObject(the, (txDestructor)builder->callback);
		fxArrayCacheItem(the, the->stack + 1, the->stack);
		the->stack++;
		c--;
		builder++;
	}
	fxArrayCacheEnd(the, the->stack);
}
Esempio n. 6
0
void fxConstructArrayEntry(txMachine* the, txSlot* entry)
{
	txSlot* value = the->stack;
	txSlot* key = the->stack + 1;
	txSlot* instance;
	txSlot* array;
	txSlot* item;
	mxPush(mxArrayPrototype);
	instance = fxNewArrayInstance(the);
	array = instance->next;
	fxSetArrayLength(the, array, 2);
	item = array->value.array.address;
	item->ID = XS_NO_ID;
	item->kind = key->kind;
	item->value = key->value;
	item++;
	item->ID = XS_NO_ID;
	item->kind = value->kind;
	item->value = value->value;
	entry->kind = the->stack->kind;
	entry->value = the->stack->value;
	the->stack += 3;
}
Esempio n. 7
0
void fx_Function_prototype_bind(txMachine* the)
{
    txSlot* instance = fxToInstance(the, mxThis);
    txSize length;
    txSlot* slot;
    txID id;
    txSlot* arguments;
    txSlot* argument;
    txSize c = mxArgc, i;

    if (!fxIsFunction(the, instance))
        mxTypeError("this is no Function instance");

    if (fxHasOwnProperty(the, instance, mxID(_length))) {
        mxPushSlot(mxThis);
        fxGetID(the, mxID(_length));
        length = fxToInteger(the, the->stack++);
        if (c > 1)
            length -= c - 1;
        if (length < 0)
            length = 0;
        mxPop();
    }
    else
        length = 0;

    mxPushSlot(mxThis);
    fxGetID(the, mxID(_name));
    mxPushStringC("bound ");
    fxConcatString(the, the->stack, the->stack + 1);
    slot = fxNewName(the, the->stack);
    id = slot->ID;
    mxPop();
    mxPop();

    mxPushReference(instance->value.instance.prototype);
    instance = fxNewFunctionInstance(the, id);
    mxPullSlot(mxResult);

    slot = mxFunctionInstanceCode(instance);
    slot->kind = XS_CALLBACK_KIND;
    slot->value.callback.address = fx_Function_prototype_bound;
    slot->value.callback.IDs = (txID*)mxIDs.value.code;

    slot = mxFunctionInstanceInfo(instance);
    slot->value.info.length = (txID)length;

    slot = fxLastProperty(the, instance);
    slot = fxNextSlotProperty(the, slot, mxThis, mxID(_boundFunction), XS_GET_ONLY);
    if (c > 0)
        slot = fxNextSlotProperty(the, slot, mxArgv(0), mxID(_boundThis), XS_GET_ONLY);
    else
        slot = fxNextUndefinedProperty(the, slot, mxID(_boundThis), XS_GET_ONLY);

    mxPush(mxArrayPrototype);
    arguments = fxNewArrayInstance(the);
    argument = arguments->next;
    for (i = 1; i < c; i++) {
        argument->next = fxNewSlot(the);
        argument = argument->next;
        argument->kind = mxArgv(i)->kind;
        argument->value = mxArgv(i)->value;
    }
    arguments->next->value.array.length = mxArgc - 1;
    fxCacheArray(the, arguments);
    slot = fxNextSlotProperty(the, slot, the->stack, mxID(_boundArguments), XS_GET_ONLY);
    mxPop();
}
Esempio n. 8
0
void fxNewInstanceOf(txMachine* the)
{
	txSlot* aParent;

	if (the->stack->kind == XS_NULL_KIND) {
		txSlot* instance = fxNewSlot(the);
		instance->kind = XS_INSTANCE_KIND;
		instance->value.instance.garbage = C_NULL;
		instance->value.instance.prototype = C_NULL;
		the->stack->value.reference = instance;
		the->stack->kind = XS_REFERENCE_KIND;
	}
	else {
		fxToInstance(the, the->stack);
		aParent = fxGetInstance(the, the->stack);
		if (aParent->flag & XS_VALUE_FLAG) {
			switch (aParent->next->kind) {
			case XS_CALLBACK_KIND:
			case XS_CODE_KIND:
				fxNewFunctionInstance(the, XS_NO_ID);
				break;
			case XS_ARRAY_KIND:
				fxNewArrayInstance(the);
				break;
			case XS_STRING_KIND:
			case XS_STRING_X_KIND:
				fxNewStringInstance(the);
				break;
			case XS_BOOLEAN_KIND:
				fxNewBooleanInstance(the);
				break;
			case XS_NUMBER_KIND:
				fxNewNumberInstance(the);
				break;
			case XS_DATE_KIND:
				fxNewDateInstance(the);
				break;
			case XS_REGEXP_KIND:
				fxNewRegExpInstance(the);
				break;
			case XS_SYMBOL_KIND:
				fxNewSymbolInstance(the);
				break;
			case XS_HOST_KIND:
				fxNewHostInstance(the);
				break;
			case XS_PROMISE_KIND:
				fxNewPromiseInstance(the);
				break;
			case XS_PROXY_KIND:
				fxNewProxyInstance(the);
				break;
			case XS_MAP_KIND:
				fxNewMapInstance(the);
				break;
			case XS_SET_KIND:
				fxNewSetInstance(the);
				break;
			case XS_WEAK_MAP_KIND:
				fxNewWeakMapInstance(the);
				break;
			case XS_WEAK_SET_KIND:
				fxNewWeakSetInstance(the);
				break;
			case XS_ARRAY_BUFFER_KIND:
				fxNewArrayBufferInstance(the);
				break;
			case XS_DATA_VIEW_KIND:
				fxNewDataViewInstance(the);
				break;
			case XS_TYPED_ARRAY_KIND:
				fxNewTypedArrayInstance(the, aParent->next->value.typedArray);
				break;
			case XS_STACK_KIND:
				fxNewGeneratorInstance(the);
				break;
			default:
				mxSyntaxError("C: xsNewInstanceOf: invalid prototype");
				break;
			}
		}
		else
			fxNewObjectInstance(the);
	}
}
Esempio n. 9
0
void fxBuildArray(txMachine* the)
{
    static const txHostFunctionBuilder gx_Array_prototype_builders[] = {
		{ fx_Array_prototype_concat, 1, _concat },
		{ fx_Array_prototype_copyWithin, 2, _copyWithin },
		{ fx_Array_prototype_entries, 0, _entries },
		{ fx_Array_prototype_every, 1, _every },
		{ fx_Array_prototype_fill, 1, _fill },
		{ fx_Array_prototype_filter, 1, _filter },
		{ fx_Array_prototype_find, 1, _find },
		{ fx_Array_prototype_findIndex, 1, _findIndex },
		{ fx_Array_prototype_forEach, 1, _forEach },
		{ fx_Array_prototype_indexOf, 1, _indexOf },
		{ fx_Array_prototype_join, 1, _join },
		{ fx_Array_prototype_keys, 0, _keys },
		{ fx_Array_prototype_lastIndexOf, 1, _lastIndexOf },
		{ fx_Array_prototype_map, 1, _map },
		{ fx_Array_prototype_pop, 0, _pop },
		{ fx_Array_prototype_push, 1, _push },
		{ fx_Array_prototype_reduce, 1, _reduce },
		{ fx_Array_prototype_reduceRight, 1, _reduceRight },
		{ fx_Array_prototype_reverse, 0, _reverse },
		{ fx_Array_prototype_shift, 0, _shift },
		{ fx_Array_prototype_slice, 2, _slice },
		{ fx_Array_prototype_some, 1, _some },
		{ fx_Array_prototype_sort, 1, _sort },
		{ fx_Array_prototype_splice, 2, _splice },
		{ fx_Array_prototype_join, 0, _toString },
		{ fx_Array_prototype_join, 0, _toLocaleString },
		{ fx_Array_prototype_unshift, 1, _unshift },
		{ fx_Array_prototype_values, 0, _values },
		{ fx_Array_prototype_values, 0, _Symbol_iterator },
		{ C_NULL, 0, 0 },
    };
    static const txHostFunctionBuilder gx_Array_builders[] = {
		{ fx_Array_from, 1, _from },
		{ fx_Array_isArray, 1, _isArray },
		{ fx_Array_of, 1, _of },
		{ C_NULL, 0, 0 },
    };
    const txHostFunctionBuilder* builder;
	txSlot* slot;
	txSlot* unscopable;
	mxPush(mxObjectPrototype);
	slot = fxLastProperty(the, fxNewArrayInstance(the));
	slot = fxNextHostAccessorProperty(the, slot, fx_Array_prototype_length_get, fx_Array_prototype_length_set, mxID(_length), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG);
	for (builder = gx_Array_prototype_builders; builder->callback; builder++)
		slot = fxNextHostFunctionProperty(the, slot, builder->callback, builder->length, mxID(builder->id), XS_DONT_ENUM_FLAG);
	slot = fxNextBooleanProperty(the, slot, 1, mxID(_Symbol_isConcatSpreadable), XS_DONT_ENUM_FLAG);
	slot = fxNextStringProperty(the, slot, "Array", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxPush(mxObjectPrototype);
	unscopable = fxLastProperty(the, fxNewObjectInstance(the));
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_find), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_findIndex), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_fill), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_copyWithin), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_entries), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_keys), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	unscopable = fxNextBooleanProperty(the, unscopable, 1, mxID(_values), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	slot = fxNextSlotProperty(the, slot, the->stack++, mxID(_Symbol_unscopables), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxArrayPrototype = *the->stack;
	slot = fxLastProperty(the, fxNewHostConstructorGlobal(the, fx_Array, 1, mxID(_Array), XS_GET_ONLY));
	for (builder = gx_Array_builders; builder->callback; builder++)
		slot = fxNextHostFunctionProperty(the, slot, builder->callback, builder->length, mxID(builder->id), XS_DONT_ENUM_FLAG);
	slot = fxNextHostAccessorProperty(the, slot, fx_species_get, C_NULL, mxID(_Symbol_species), XS_DONT_ENUM_FLAG);
	the->stack++;
	
	mxPush(mxIteratorPrototype);
	slot = fxLastProperty(the, fxNewObjectInstance(the));
	slot = fxNextHostFunctionProperty(the, slot, fx_Array_prototype_entries_next, 0, mxID(_next), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG);
	slot = fxNextStringProperty(the, slot, "Array Iterator", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxPull(mxArrayEntriesIteratorPrototype);
	mxPush(mxIteratorPrototype);
	slot = fxLastProperty(the, fxNewObjectInstance(the));
	slot = fxNextHostFunctionProperty(the, slot, fx_Array_prototype_keys_next, 0, mxID(_next), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG);
	slot = fxNextStringProperty(the, slot, "Array Iterator", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxPull(mxArrayKeysIteratorPrototype);
	mxPush(mxIteratorPrototype);
	slot = fxLastProperty(the, fxNewObjectInstance(the));
	slot = fxNextHostFunctionProperty(the, slot, fx_Array_prototype_values_next, 0, mxID(_next), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG);
	slot = fxNextStringProperty(the, slot, "Array Iterator", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxPull(mxArrayValuesIteratorPrototype);
	
	mxPush(mxObjectPrototype);
	slot = fxLastProperty(the, fxNewObjectInstance(the));
	slot = fxNextStringProperty(the, slot, "Arguments", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxParametersPrototype = *the->stack;
	the->stack++;
	
	mxPush(mxObjectPrototype);
	slot = fxLastProperty(the, fxNewObjectInstance(the));
	slot = fxNextHostAccessorProperty(the, slot, fx_Arguments_prototype_callee, fx_Arguments_prototype_callee, mxID(_callee), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	slot = fxNextHostAccessorProperty(the, slot, fx_Arguments_prototype_caller, fx_Arguments_prototype_caller, mxID(_caller), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	slot = fxNextHostFunctionProperty(the, slot, fx_Array_prototype_values, 0, mxID(_Symbol_iterator), XS_DONT_DELETE_FLAG | XS_DONT_ENUM_FLAG);
	slot = fxNextStringProperty(the, slot, "Arguments", mxID(_Symbol_toStringTag), XS_DONT_ENUM_FLAG | XS_DONT_SET_FLAG);
	mxArgumentsStrictPrototype = *the->stack;
	the->stack++;
}