Beispiel #1
0
void fxBuildKeys(txMachine* the)
{
	txArchive* archive = the->archive;
	if (archive && archive->keys)
		(*archive->keys)(the);
	else {
	#ifdef mxParse
		txSlot* code = &mxIDs;
		txID c, i;
		if (archive) {
			c = archive->symbolCount;
			code->value.code = (txByte *)fxNewChunk(the, c * sizeof(txID));
			code->kind = XS_CODE_KIND;	
			for (i = 0; i < XS_SYMBOL_ID_COUNT; i++) {
				txString string = archive->symbols[i];
				txID id = the->keyIndex;
				txSlot* description = fxNewSlot(the);
				description->flag = XS_DONT_ENUM_FLAG;
				fxCopyStringC(the, description, string);
				the->keyArray[id] = description;
				the->keyIndex++;
				mxID(i) = 0x8000 | id;
			}
			for (; i < c; i++) {
				txString string = archive->symbols[i];
				mxID(i) = fxNewNameX(the, string)->ID;
			}
		}
		else {
			code->value.code = (txByte *)fxNewChunk(the, XS_ID_COUNT * sizeof(txID));
			code->kind = XS_CODE_KIND;	
			for (i = 0; i < XS_SYMBOL_ID_COUNT; i++) {
				txID id = the->keyIndex;
				txSlot* description = fxNewSlot(the);
				description->flag = XS_DONT_ENUM_FLAG;
				fxCopyStringC(the, description, gxIDStrings[i]);
				the->keyArray[id] = description;
				the->keyIndex++;
				mxID(i) = 0x8000 | id;
			}
			for (; i < XS_ID_COUNT; i++) {
				mxID(i) = fxID(the, gxIDStrings[i]);
			}
		}
	#else
		fxCheck(the, __FILE__, __LINE__);
	#endif
	}
}
Beispiel #2
0
void fx_String_charAt(txMachine* the)
{
	txString aString;
	txInteger aLength;
	txInteger anOffset;

	aString = fxCoerceToString(the, mxThis);
	if (!aString)
		mxDebug0(the, XS_TYPE_ERROR, "String.prototype.charAt: this is null or undefined");
	aLength = fxUnicodeLength(aString);
	if ((mxArgc > 0) && (mxArgv(0)->kind != XS_UNDEFINED_KIND))
		anOffset = fxToInteger(the, mxArgv(0));
	else
		anOffset = -1;
	if ((0 <= anOffset) && (anOffset < aLength)) {
		anOffset = fxUnicodeToUTF8Offset(aString, anOffset);
		aLength = fxUnicodeToUTF8Offset(aString + anOffset, 1);
		if ((anOffset >= 0) && (aLength > 0)) {
			mxResult->value.string = (txString)fxNewChunk(the, aLength + 1);
			c_memcpy(mxResult->value.string, mxThis->value.string + anOffset, aLength);
			mxResult->value.string[aLength] = 0;
			mxResult->kind = XS_STRING_KIND;
		}
		else {
			mxResult->value.string = mxEmptyString.value.string;
			mxResult->kind = mxEmptyString.kind;
		}
	}
	else {
		mxResult->value.string = mxEmptyString.value.string;
		mxResult->kind = mxEmptyString.kind;
	}
}
Beispiel #3
0
void fx_Error_toString(txMachine* the)
{
	txInteger aLength;
	
	mxPushSlot(mxThis);
	fxGetID(the, mxID(_name));
	if (the->stack->kind == XS_UNDEFINED_KIND) 
		fxCopyStringC(the, the->stack, "Error");
	else	
		fxToString(the, the->stack);
	mxPushSlot(mxThis);
	fxGetID(the, mxID(_message));
	if (the->stack->kind == XS_UNDEFINED_KIND) 
		fxCopyStringC(the, the->stack, "");
	else	
		fxToString(the, the->stack);
	aLength = c_strlen(the->stack->value.string);
	if (aLength) {
		aLength += c_strlen((the->stack + 1)->value.string) + 2;
		mxResult->value.string = (txString)fxNewChunk(the, aLength + 1);
		mxResult->kind = XS_STRING_KIND;
		c_strcpy(mxResult->value.string, (the->stack + 1)->value.string);
		c_strcat(mxResult->value.string, ": ");
		c_strcat(mxResult->value.string, the->stack->value.string);
		the->stack++;
		the->stack++;
	}
	else {
		the->stack++;
		mxPullSlot(mxResult);
	}
}
Beispiel #4
0
void fx_String_fromCharCode(txMachine* the)
{
	txInteger aLength;
	txInteger aCount;
	txInteger anIndex;
	txU4 c; 
	txU1* p;
	
	aLength = 0;
	aCount = mxArgc;
	for (anIndex = 0; anIndex < aCount; anIndex++) {
		c = fxToInteger(the, mxArgv(anIndex)) & 0x0000FFFF;
		if (c < 0x80)
			aLength++;
		else if (c < 0x800)
			aLength += 2;
		else if (c < 0x10000)
			aLength += 3;
		else
			aLength += 4;
	}
	mxResult->value.string = (txString)fxNewChunk(the, aLength + 1);
	mxResult->kind = XS_STRING_KIND;
	p = (txU1*)mxResult->value.string;
	for (anIndex = 0; anIndex < aCount; anIndex++) {
		c = fxToInteger(the, mxArgv(anIndex)) & 0x0000FFFF;
		if (c < 0x80) {
			*p++ = (txU1)c;
		}
		else if (c < 0x800) {
			*p++ = (txU1)(0xC0 | (c >> 6));
			*p++ = (txU1)(0x80 | (c & 0x3F));
		}
		else if (c < 0x10000) {
Beispiel #5
0
txString fxCopyStringC(txMachine* the, txSlot* a, txString b)
{
	txSize bSize = c_strlen(b);
	txString result = (txString)fxNewChunk(the, bSize + 1);
	c_memcpy(result, b, bSize + 1);
	a->value.string = result;
	a->kind = XS_STRING_KIND;
	return result;
}
Beispiel #6
0
void fxStringBuffer(txMachine* the, txSlot* theSlot, txString theValue, txSize theSize)
{
	theSlot->value.string = (txString)fxNewChunk(the, theSize + 1);
	if (theValue)
		c_memcpy(theSlot->value.string, theValue, theSize);
	else
		theSlot->value.string[0] = 0;
	theSlot->value.string[theSize] = 0;
	theSlot->kind = XS_STRING_KIND;
}
Beispiel #7
0
void fxIDs(txMachine* the, txInteger count, txString* names)
{
	txInteger i;
	txID* IDs = fxNewChunk(the, count * sizeof(txID));
	mxFunction->value.reference->next->value.callback.IDs = IDs;
	the->code = (txByte*)IDs;
	for (i = 0; i < count; i++) {
		((txID*)the->code)[i] = fxID(the, names[i]);
	}
}
Beispiel #8
0
txString fxConcatString(txMachine* the, txSlot* a, txSlot* b)
{
	txSize aSize = c_strlen(a->value.string);
	txSize bSize = c_strlen(b->value.string);
	txString result = (txString)fxNewChunk(the, aSize + bSize + 1);
	c_memcpy(result, a->value.string, aSize);
	c_memcpy(result + aSize, b->value.string, bSize + 1);
	a->value.string = result;
	a->kind = XS_STRING_KIND;
	return result;
}
Beispiel #9
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++;
		}
	}
}
Beispiel #10
0
txSlot* fxNewGlobalInstance(txMachine* the)
{
	txSlot* instance;
	txSlot* property;
	instance = fxNewInstance(the);
	instance->flag |= XS_VALUE_FLAG;
	property = instance->next = fxNewSlot(the);
	property->value.table.address = (txSlot**)fxNewChunk(the, the->keyCount * sizeof(txSlot*));
	c_memset(property->value.table.address, 0, the->keyCount * sizeof(txSlot*));
	property->value.table.length = the->keyCount;
	property->kind = XS_GLOBAL_KIND;
	return instance;
}
Beispiel #11
0
txString fxConcatStringC(txMachine* the, txSlot* a, txString b)
{
	txSize aSize = c_strlen(a->value.string);
	txSize bSize = c_strlen(b);
	txSize resultSize = aSize + bSize + 1;
	txString result = C_NULL;
	if (a->kind == XS_STRING_KIND)
		result = (txString)fxRenewChunk(the, a->value.string, resultSize);
	if (!result) {
		result = (txString)fxNewChunk(the, resultSize);
		c_memcpy(result, a->value.string, aSize);
		a->value.string = result;
		a->kind = XS_STRING_KIND;
	}
	c_memcpy(result + aSize, b, bSize + 1);
	return result;
}
Beispiel #12
0
txString fxResizeString(txMachine* the, txSlot* a, txSize theSize)
{
	txString result = C_NULL;
	if (a->kind == XS_STRING_KIND)
		result = (txString)fxRenewChunk(the, a->value.string, theSize);
	if (!result) {
		txChunk* aChunk = (txChunk*)(a->value.string - sizeof(txChunk));
		txSize aSize = aChunk->size - sizeof(txChunk); 
		result = (txString)fxNewChunk(the, theSize);
		aChunk = (txChunk*)(result - sizeof(txChunk));
		theSize = aChunk->size - sizeof(txChunk);
		c_memcpy(result, a->value.string, (aSize < theSize) ? aSize : theSize);
		a->value.string = result;
		a->kind = XS_STRING_KIND;
	}
	return result;
}
Beispiel #13
0
void fxQueuePattern(txMachine* the, txKind theKind, 
		txID theNamespaceID, txID theNameID, 
		txID theID, txFlag theFlag)
{
	txPatternData* aPatternData;

	aPatternData = fxNewChunk(the, sizeof(txPatternData));
	aPatternData->alias = the->stack->value.alias;
	aPatternData->count = 1;
	aPatternData->parts[0].namespaceID = theNamespaceID;
	aPatternData->parts[0].nameID = theNameID;
	the->stack->value.pattern = aPatternData;
	the->stack->kind = theKind;
	if (theID == XS_SAME_ID)
		fxQueueID(the, theNameID, theFlag);
	else
		fxQueueID(the, theID, theFlag);
}
Beispiel #14
0
txString fxAdornStringC(txMachine* the, txString prefix, txSlot* string, txString suffix)
{
	txSize stringSize = c_strlen(string->value.string);
	txSize prefixSize = prefix ? c_strlen(prefix) : 0;
	txSize suffixSize = suffix ? c_strlen(suffix) : 0;
	txSize resultSize = stringSize + prefixSize + suffixSize + 1;
	txString result = (txString)fxNewChunk(the, resultSize);
	if (prefix && prefixSize)
		c_memcpy(result, prefix, prefixSize);
	if (stringSize)
		c_memcpy(result + prefixSize, string->value.string, stringSize);
	if (suffix && suffixSize)
		c_memcpy(result + prefixSize + stringSize, suffix, suffixSize);
	result[prefixSize + stringSize + suffixSize] = 0;
	string->kind = XS_STRING_KIND;
	string->value.string = result;
	return result;
}
Beispiel #15
0
void fxArrayCacheEnd(txMachine* the, txSlot* reference)
{
	txSlot* array = reference->value.reference->next;
	txInteger length = array->value.array.length;
	if (length) {
		txSlot *srcSlot, *dstSlot;
		array->value.array.address = (txSlot*)fxNewChunk(the, length * sizeof(txSlot));
		srcSlot = array->next;
		dstSlot = array->value.array.address + length;
		while (srcSlot) {
			dstSlot--;
			dstSlot->ID = XS_NO_ID;
			dstSlot->flag = XS_NO_FLAG;
			dstSlot->kind = srcSlot->kind;
			dstSlot->value = srcSlot->value;
			srcSlot = srcSlot->next;
		}
		array->next = C_NULL;
	}
}
Beispiel #16
0
void fx_JSON_stringify(txMachine* the)
{
	volatile txJSONSerializer aSerializer;
	mxTry(the) {
		c_memset((txJSONSerializer*)&aSerializer, 0, sizeof(aSerializer));
		fxSerializeJSON(the, (txJSONSerializer*)&aSerializer);
		if (aSerializer.offset) {
			fxSerializeJSONChar(the, (txJSONSerializer*)&aSerializer, 0);
			mxResult->value.string = (txString)fxNewChunk(the, aSerializer.offset);
			c_memcpy(mxResult->value.string, aSerializer.buffer, aSerializer.offset);
			mxResult->kind = XS_STRING_KIND;
		}
		c_free(aSerializer.buffer);
	}
	mxCatch(the) {
		if (aSerializer.buffer)
			c_free(aSerializer.buffer);
		fxJump(the);
	}
}
Beispiel #17
0
void fxCacheArray(txMachine* the, txSlot* instance)
{
	txSlot* array = instance->next;
	txIndex length = array->value.array.length;
	if (length) {
		txSlot* address = (txSlot *)fxNewChunk(the, length * sizeof(txSlot));
		txSlot* srcSlot = instance->next->next;
		txSlot* dstSlot = address;
		while (srcSlot) {
			dstSlot->ID = XS_NO_ID;
			dstSlot->flag = XS_NO_FLAG;
			dstSlot->kind = srcSlot->kind;
			dstSlot->value = srcSlot->value;
			srcSlot = srcSlot->next;
			dstSlot++;
		}
		instance->next->value.array.address = address;
		instance->next->next = C_NULL;
	}
}
Beispiel #18
0
void fx_String_concat(txMachine* the)
{
	txString aString;
	txInteger aCount;
	txInteger aLength;
	txInteger anIndex;
	
	aString = fxCoerceToString(the, mxThis);
	if (!aString)
		mxDebug0(the, XS_TYPE_ERROR, "String.prototype.concat: this is null or undefined");
	aCount = mxArgc;
	aLength = c_strlen(mxThis->value.string);
	for (anIndex = 0; anIndex < aCount; anIndex++)
		aLength += c_strlen(fxToString(the, mxArgv(anIndex)));
	mxResult->value.string = (txString)fxNewChunk(the, aLength + 1);
	mxResult->kind = XS_STRING_KIND;
	c_strcpy(mxResult->value.string, mxThis->value.string);
	for (anIndex = 0; anIndex < aCount; anIndex++)
		c_strcat(mxResult->value.string, mxArgv(anIndex)->value.string);
}
Beispiel #19
0
txSlot* fxNewNameC(txMachine* the, txString theString)
{
    txU1* string;
    txU4 sum;
    txU4 modulo;
    txSlot* result;
    txID index;

    string = (txU1*)theString;
    sum = 0;
    while(*string != 0) {
        sum = (sum << 1) + *string++;
    }
    sum &= 0x7FFFFFFF;
    modulo = sum % the->nameModulo;
    result = the->nameTable[modulo];
    while (result != C_NULL) {
        if (result->value.key.sum == sum)
            if (c_strcmp(result->value.key.string, theString) == 0)
                break;
        result = result->next;
    }
    if (result == C_NULL) {
        index = the->keyIndex;
        if (index == the->keyCount)
            mxUnknownError("not enough IDs");
        result = fxNewSlot(the);
        result->next = the->nameTable[modulo];
        result->flag = XS_DONT_ENUM_FLAG;
        result->kind = XS_KEY_KIND;
        result->ID = 0x8000 | index;
        result->value.key.string = C_NULL;
        result->value.key.sum = sum;
        the->keyArray[index] = result;
        the->keyIndex++;
        the->nameTable[modulo] = result;
        result->value.key.string = (txString)fxNewChunk(the, c_strlen(theString) + 1);
        c_strcpy(result->value.key.string, theString);
    }
    return result;
}
Beispiel #20
0
void fx_Error_toString(txMachine* the)
{
	txSlot* anError;
	txSlot* aProperty;
	txInteger aLength;
	
	anError = fxGetInstance(the, mxThis);
	aProperty = fxGetProperty(the, anError, fxID(the, "name"));
	--the->stack;
	the->stack->kind = aProperty->kind;
	the->stack->value = aProperty->value;
	if (the->stack->kind == XS_UNDEFINED_KIND) 
		fxCopyStringC(the, the->stack, "Error");
	else	
		fxToString(the, the->stack);
	aProperty = fxGetProperty(the, anError, fxID(the, "message"));
	--the->stack;
	the->stack->kind = aProperty->kind;
	the->stack->value = aProperty->value;
	if (the->stack->kind == XS_UNDEFINED_KIND) 
		fxCopyStringC(the, the->stack, "");
	else	
		fxToString(the, the->stack);
	aLength = c_strlen(the->stack->value.string);
	if (aLength) {
		aLength += c_strlen((the->stack + 1)->value.string) + 2;
		mxResult->value.string = (txString)fxNewChunk(the, aLength + 1);
		mxResult->kind = XS_STRING_KIND;
		c_strcpy(mxResult->value.string, (the->stack + 1)->value.string);
		c_strcat(mxResult->value.string, ": ");
		c_strcat(mxResult->value.string, the->stack->value.string);
		the->stack++;
		the->stack++;
	}
	else {
		the->stack++;
		*mxResult = *(the->stack++);
	}
}
Beispiel #21
0
void fxSetArrayLength(txMachine* the, txSlot* array, txIndex target)
{
	txIndex length = array->value.array.length;
	txSlot* address = array->value.array.address;
	if (length != target) {
		if (address)
			address = (txSlot*)fxRenewChunk(the, address, target * sizeof(txSlot));
		if (address) {
			if (length < target)
				c_memset(address + length, 0, (target - length) * sizeof(txSlot));
		}
		else {
			address = (txSlot*)fxNewChunk(the, target * sizeof(txSlot));
			if (length < target) {
				c_memcpy(address, array->value.array.address, length * sizeof(txSlot));
				c_memset(address + length, 0, (target - length) * sizeof(txSlot));
			}
			else
				c_memcpy(address, array->value.array.address, target * sizeof(txSlot));
		}
		array->value.array.length = target;
		array->value.array.address = address;
	}
}
Beispiel #22
0
txMachine* fxCloneMachine(txCreation* theCreation, txMachine* theMachine, txString theName, void* theContext)
{
	txMachine* the = (txMachine *)c_calloc(sizeof(txMachine), 1);
	if (the) {
		txJump aJump;

		aJump.nextJump = C_NULL;
		aJump.stack = C_NULL;
		aJump.scope = C_NULL;
		aJump.frame = C_NULL;
		aJump.code = C_NULL;
		aJump.flag = 0;
		the->firstJump = &aJump;
		if (c_setjmp(aJump.buffer) == 0) {
			txInteger anIndex;
			txSlot* aSlot;
			txSlot** aSlotAddress;
			txSlot* aSharedSlot;
			txSlot* aTemporarySlot;
			txID anID;

		#if __FSK_LAYER__
			FskInstrumentedItemNew(the, theName, &gXSTypeInstrumentation);
		#endif

		#ifdef mxDebug
			the->echoSize = 1 * 1024;
			the->echoBuffer = (txString)c_malloc(the->echoSize);
			if (!the->echoBuffer)
				fxJump(the);
			//fxConnect(the);
			the->name = theName;
			the->sorter = (txSlot**)c_malloc(theCreation->keyCount * sizeof(txSlot*));
			if (!the->sorter)
				fxJump(the);
			the->breakOnExceptionFlag = 1;
		#endif
		#ifdef mxProfile
			the->profileID = theMachine->profileID;
			the->profileBottom = c_malloc(XS_PROFILE_COUNT * sizeof(txProfileRecord));
			if (!the->profileBottom)
				fxJump(the);
			the->profileCurrent = the->profileBottom;
			the->profileTop = the->profileBottom + XS_PROFILE_COUNT;
		#endif

			the->archive = theMachine->archive;

			the->dtoa = fxNew_dtoa();
			if (!the->dtoa)
				fxJump(the);
			theCreation->keyCount = theMachine->keyCount;
			theCreation->nameModulo = theMachine->nameModulo;
			theCreation->symbolModulo = theMachine->symbolModulo;

			fxAllocate(the, theCreation);

			the->sharedMachine = theMachine;

            c_memcpy(the->nameTable, theMachine->nameTable, the->nameModulo * sizeof(txSlot *));
			c_memcpy(the->symbolTable, theMachine->symbolTable, the->symbolModulo * sizeof(txSlot *));
			c_memcpy(the->keyArray, theMachine->keyArray, the->keyCount * sizeof(txSlot *));
			the->keyIndex = theMachine->keyIndex;
			the->keyOffset = the->keyIndex;
		
			the->aliasCount = theMachine->aliasCount;
			the->aliasArray = (txSlot **)c_calloc(the->aliasCount, sizeof(txSlot*));
			if (!the->aliasArray)
				fxJump(the);

			/* mxGlobal */
			fxNewInstance(the);
			aSlot = the->stack->value.reference;
			aSlot->flag = XS_VALUE_FLAG;
			aSlot->next = fxNewSlot(the);
			aSlot = aSlot->next;
			aSlot->value.table.address = (txSlot**)fxNewChunk(the, theCreation->keyCount * sizeof(txSlot*));
			aSlot->value.table.length = theCreation->keyCount;
			aSlot->kind = XS_GLOBAL_KIND;
			c_memset(aSlot->value.table.address, 0, theCreation->keyCount * sizeof(txSlot*));
			aSlotAddress = aSlot->value.table.address;
			aSharedSlot = theMachine->stackTop[-1].value.reference->next->next;
			while (aSharedSlot) {
				aSlot->next = aTemporarySlot = fxDuplicateSlot(the, aSharedSlot);
				anID = aTemporarySlot->ID & 0x7FFF;
				aSlotAddress[anID] = aTemporarySlot;
				aSharedSlot = aSharedSlot->next;
				aSlot = aSlot->next;
			}
			/* mxException */
			mxPushUndefined();
			for (anIndex = mxObjectPrototypeStackIndex; anIndex < mxModulePathsStackIndex; anIndex++)
				*(--the->stack) = theMachine->stackTop[-1 - anIndex];
			
			/* mxModulePaths */
			mxPushUndefined();
			/* mxImportingModules */
			fxNewInstance(the);
			/* mxLoadingModules */
			fxNewInstance(the);
			/* mxLoadedModules */
			fxNewInstance(the);
			/* mxResolvingModules */
			fxNewInstance(the);
			/* mxRunningModules */
			fxNewInstance(the);
			/* mxRequiredModules */
			fxNewInstance(the);
			/* mxModules */
			mxPushUndefined();
			/* mxPendingJobs */
			fxNewInstance(the);
			/* mxRunningJobs */
			fxNewInstance(the);
			/* mxFiles */
			mxPushList();
		#ifdef mxDebug
			aSharedSlot = theMachine->stackTop[-1 - mxFilesStackIndex].value.list.first;
			aSlotAddress = &(the->stack->value.list.first);
			while (aSharedSlot) {
				*aSlotAddress = fxDuplicateSlot(the, aSharedSlot);
				aSharedSlot = aSharedSlot->next;
				aSlotAddress = &((*aSlotAddress)->next);
			}
		#endif
			/* mxBreakpoints */
			mxPushList();
			/* shared */
			for (anIndex = mxHostsStackIndex; anIndex < mxStackIndexCount; anIndex++)
				*(--the->stack) = theMachine->stackTop[-1 - anIndex];
			
			mxPush(mxSetPrototype);
			fxNewSetInstance(the);
			mxPull(mxModulePaths);
			
			mxPush(mxObjectPrototype);
			fxNewWeakSetInstance(the);
			mxPull(mxModules);

			the->collectFlag = XS_COLLECTING_FLAG;
			the->context = theContext;

		#ifdef mxDebug
			if (fxGetAutomatic(the))
				fxLogin(the);
		#endif

			the->firstJump = C_NULL;

		}
		else {
		#if __FSK_LAYER__
			FskInstrumentedItemDispose(the);
		#endif

			fxFree(the);
			c_free(the);
			the = NULL;
		}
	}
	return the;
}
Beispiel #23
0
void fx_JSON_stringify(txMachine* the)
{
	txSlot* aSlot;
	volatile txJSONSerializer aSerializer;
	txFlag aFlag;
	
	mxTry(the) {
		aSlot = fxGetInstance(the, mxThis);
		if (aSlot->flag & XS_SANDBOX_FLAG)
			the->frame->flag |= XS_SANDBOX_FLAG;
		else
			the->frame->flag |= the->frame->next->flag & XS_SANDBOX_FLAG;
		c_memset((txJSONSerializer*)&aSerializer, 0, sizeof(aSerializer));
		aSerializer.offset = 0;
		aSerializer.size = 1024;
		aSerializer.buffer = c_malloc(1024);
		if (!aSerializer.buffer)
			fxThrowError(the, XS_RANGE_ERROR);
	
		if (mxArgc > 1) {
			aSlot = mxArgv(1);
			if (mxIsReference(aSlot)) {
				aSlot = fxGetInstance(the, aSlot);
				if (mxIsFunction(aSlot))
					aSerializer.replacer = mxArgv(1);
				else if (mxIsArray(aSlot))
					mxDebug0(the, XS_SYNTAX_ERROR, "not yet implememented");
			}
		}
		if (mxArgc > 2) {
			aSlot = mxArgv(2);
			if (mxIsReference(aSlot)) {
				aSlot = fxGetInstance(the, aSlot);
				if (mxIsNumber(aSlot) || mxIsString(aSlot))
					aSlot = aSlot->next;
			}
			if ((aSlot->kind == XS_INTEGER_KIND) || (aSlot->kind == XS_NUMBER_KIND)) {
				txInteger aCount = fxToInteger(the, aSlot), anIndex;
				if (aCount < 0)
					aCount = 0;
				else if (aCount > 10)
					aCount = 10;
				for (anIndex = 0; anIndex < aCount; anIndex++)
					aSerializer.indent[anIndex] = ' ';
			}
			else if (aSlot->kind == XS_STRING_KIND)
				c_strncpy((char *)aSerializer.indent, aSlot->value.string, 10);
		}
	
		aSerializer.stack = the->stack;
		*(--the->stack) = mxObjectPrototype;
		fxNewObjectInstance(the);
		aFlag = 0;
		if (mxArgc > 0)
			*(--the->stack) = *mxArgv(0);
		else
			mxZeroSlot(--the->stack);
		*(--the->stack) = mxEmptyString;
		fxSerializeJSONProperty(the, (txJSONSerializer*)&aSerializer, &aFlag);
		the->stack++;
		
		if (aSerializer.offset) {
			mxResult->value.string = (txString)fxNewChunk(the, aSerializer.offset + 1);
			c_memcpy(mxResult->value.string, aSerializer.buffer, aSerializer.offset);
			mxResult->value.string[aSerializer.offset] = 0;
			mxResult->kind = XS_STRING_KIND;
		}
		c_free(aSerializer.buffer);
	}
	mxCatch(the) {
		if (aSerializer.buffer)
			c_free(aSerializer.buffer);
		fxJump(the);
	}
}
Beispiel #24
0
void fxGetNextJSONToken(txMachine* the, txJSONParser* theParser)
{
	txString p;
	txString q;
	txString r;
	txString s;
	char c;
	txInteger i;
	txBoolean escaped;
	txNumber number;
	txU4 size;
	txU4 value;
	const txUTF8Sequence* sequence;
	txString string;

	theParser->integer = 0;
	theParser->number = 0;
	theParser->string->value.string = mxEmptyString.value.string;
	theParser->token = XS_NO_JSON_TOKEN;
	r = (theParser->data) ? theParser->data : theParser->slot->value.string;
	p = r + theParser->offset;
	q = r + theParser->size;
	c = (p < q) ? *p : 0;
	while (theParser->token == XS_NO_JSON_TOKEN) {
		switch (c) {
		case 0:
			theParser->token = XS_JSON_TOKEN_EOF;
			break;
		case '\n':	
		case '\r':	
		case '\t':
		case ' ':
			c = (++p < q) ? *p : 0;
			break;
			
		case '-':
		case '0':
		case '1':
		case '2':
		case '3':
		case '4':
		case '5':
		case '6':
		case '7':
		case '8':
		case '9':
			s = p;
			if (c == '-')
				c = (++p < q) ? *p : 0;
			if (('0' <= c) && (c <= '9')) {
				if (c == '0') {
					c = (++p < q) ? *p : 0;
				}
				else {
					c = (++p < q) ? *p : 0;
					while (('0' <= c) && (c <= '9')) {
						c = (++p < q) ? *p : 0;
					}
				}
				if (c == '.') {
					c = (++p < q) ? *p : 0;
					if (('0' <= c) && (c <= '9')) {
						c = (++p < q) ? *p : 0;
						while (('0' <= c) && (c <= '9')) {
							c = (++p < q) ? *p : 0;
						}
					}
					else
						mxSyntaxError("invalid character in number");
				}
				if ((c == 'e') || (c == 'E')) {
					c = (++p < q) ? *p : 0;
					if ((c== '+') || (c == '-')) {
						c = (++p < q) ? *p : 0;
					}
					if (('0' <= c) && (c <= '9')) {
						c = (++p < q) ? *p : 0;
						while (('0' <= c) && (c <= '9')) {
							c = (++p < q) ? *p : 0;
						}
					}
					else
						mxSyntaxError("invalid character in number");
				}
				size = p - s;
				if ((size + 1) > sizeof(the->nameBuffer))
					mxSyntaxError("number overflow");
				c_memcpy(the->nameBuffer, s, size);
				the->nameBuffer[size] = 0;
				theParser->number = fxStringToNumber(the->dtoa, the->nameBuffer, 0);
				theParser->integer = (txInteger)theParser->number;
				number = theParser->integer;
				if (theParser->number == number)
					theParser->token = XS_JSON_TOKEN_INTEGER;
				else
					theParser->token = XS_JSON_TOKEN_NUMBER;
			}
			else
				mxSyntaxError("invalid character in number");
			break;
		case ',':
			p++;
			theParser->token = XS_JSON_TOKEN_COMMA;
			break;	
		case ':':
			p++;
			theParser->token = XS_JSON_TOKEN_COLON;
			break;	
		case '[':
			p++;
			theParser->token = XS_JSON_TOKEN_LEFT_BRACKET;
			break;	
		case ']':
			p++;
			theParser->token = XS_JSON_TOKEN_RIGHT_BRACKET;
			break;	
		case '{':
			p++;
			theParser->token = XS_JSON_TOKEN_LEFT_BRACE;
			break;	
		case '}':
			p++;
			theParser->token = XS_JSON_TOKEN_RIGHT_BRACE;
			break;	
		case '"':
			c = (++p < q) ? *p : 0;
			s = p;
			escaped = 0;
			size = 0;
			for (;;) {
				if ((0 <= c) && (c < 32)) {
					mxSyntaxError("invalid character in string");				
					break;
				}
				else if (c == '"') {
					break;
				}
				else if (c == '\\') {
					escaped = 1;
					c = (++p < q) ? *p : 0;
					switch (c) {
					case '"':
					case '/':
					case '\\':
					case 'b':
					case 'f':
					case 'n':
					case 'r':
					case 't':
						size++;
						c = (++p < q) ? *p : 0;
						break;
					case 'u':
						value = 0;
						for (i = 0; i < 4; i++) {
							c = (++p < q) ? *p : 0;
							if (('0' <= c) && (c <= '9'))
								value = (value * 16) + (c - '0');
							else if (('a' <= c) && (c <= 'f'))
								value = (value * 16) + (10 + c - 'a');
							else if (('A' <= c) && (c <= 'F'))
								value = (value * 16) + (10 + c - 'A');
							else
								mxSyntaxError("invalid character in string");
						}
						// surrogate pair?
						for (sequence = gxUTF8Sequences; sequence->size; sequence++)
							if (value <= sequence->lmask)
								break;
						size += sequence->size;
						c = (++p < q) ? *p : 0;
						break;
					default:
						mxSyntaxError("invalid character in string");
						break;
					}
				}
				else {
					size++;
					c = (++p < q) ? *p : 0;
				}
			}
			{
				txSize after = p - r;
				txSize before = s - r;
				string = theParser->string->value.string = (txString)fxNewChunk(the, size + 1);
				r = (theParser->data) ? theParser->data : theParser->slot->value.string;
				p = r + after;
				q = r + theParser->size;
				s = r + before;
			}
			if (escaped) {
				p = s;
				c = *p;
				for (;;) {
					if (c == '"') {
						break;
					}
					else if (c == '\\') {
						p++; c = *p;
						switch (c) {
						case '"':
						case '/':
						case '\\':
							*string++ = c;
							p++; c = *p;
							break;
						case 'b':
							*string++ = '\b';
							p++; c = *p;
							break;
						case 'f':
							*string++ = '\f';
							p++; c = *p;
							break;
						case 'n':
							*string++ = '\n';
							p++; c = *p;
							break;
						case 'r':
							*string++ = '\r';
							p++; c = *p;
							break;
						case 't':
							*string++ = '\t';
							p++; c = *p;
							break;
						case 'u':
							value = 0;
							for (i = 0; i < 4; i++) {
								p++; c = *p;
								if (('0' <= c) && (c <= '9'))
									value = (value * 16) + (c - '0');
								else if (('a' <= c) && (c <= 'f'))
									value = (value * 16) + (10 + c - 'a');
								else
									value = (value * 16) + (10 + c - 'A');
							}
							// surrogate pair?
							string = (txString)fsX2UTF8(value, (txU1*)string, 0x7FFFFFFF);
							p++; c = *p;
							break;
						}
					}
					else {
						*string++ = c;
						p++; c = *p;
					}
				}
				*string = 0;
			}
			else {
				c_memcpy(string, s, size);
				string[size] = 0;
			}
			p++;
			theParser->token = XS_JSON_TOKEN_STRING;
			break;
		default:
			if ((q - p >= 5) && (!c_strncmp(p, "false", 5))) {
				p += 5;
				theParser->token = XS_JSON_TOKEN_FALSE;
			}
			else if ((q - p >= 4) && (!c_strncmp(p, "null", 4))) {
				p += 4;
				theParser->token = XS_JSON_TOKEN_NULL;
			}
			else if ((q - p >= 4) && (!c_strncmp(p, "true", 4))) {
				p += 4;
				theParser->token = XS_JSON_TOKEN_TRUE;
			}
			else
				mxSyntaxError("invalid character");	
			break;
		}
	}
	theParser->offset = p - r;
}
Beispiel #25
0
txMachine* fxCreateMachine(txCreation* theCreation, void* theArchive, txString theName, void* theContext)
{
	txMachine* the = (txMachine* )c_calloc(sizeof(txMachine), 1);
	if (the) {
		txJump aJump;

		aJump.nextJump = C_NULL;
		aJump.stack = C_NULL;
		aJump.scope = C_NULL;
		aJump.frame = C_NULL;
		aJump.code = C_NULL;
		aJump.flag = 0;
		the->firstJump = &aJump;
		if (c_setjmp(aJump.buffer) == 0) {
			txInteger anIndex;

		#if __FSK_LAYER__
			FskInstrumentedItemNew(the, NULL, &gXSTypeInstrumentation);
		#endif

		#ifdef mxDebug
			the->echoSize = 1 * 1024;
			the->echoBuffer = (txString)c_malloc(the->echoSize);
			if (!the->echoBuffer)
				fxJump(the);
			//fxConnect(the);
			the->connection = mxNoSocket;
			the->name = theName;
			the->sorter = (txSlot**)c_malloc(theCreation->keyCount * sizeof(txSlot*));
			if (!the->sorter)
				fxJump(the);
			the->breakOnExceptionFlag = 1;
		#endif
		#ifdef mxProfile
			the->profileID = 1;
			the->profileBottom = c_malloc(XS_PROFILE_COUNT * sizeof(txProfileRecord));
			if (!the->profileBottom)
				fxJump(the);
			the->profileCurrent = the->profileBottom;
			the->profileTop = the->profileBottom + XS_PROFILE_COUNT;
		#endif

			the->archive = theArchive;
			
			the->dtoa = fxNew_dtoa();
			if (!the->dtoa)
				fxJump(the);
				
			fxAllocate(the, theCreation);

			/* mxGLobal */
			mxPushUndefined();
			/* mxException */
			mxPushUndefined();
			for (anIndex = mxObjectPrototypeStackIndex; anIndex < mxModulePathsStackIndex; anIndex++)
				mxPushUndefined();
			/* mxModulePaths */
			mxPushUndefined();
			/* mxImportingModules */
			fxNewInstance(the);
			/* mxLoadingModules */
			fxNewInstance(the);
			/* mxLoadedModules */
			fxNewInstance(the);
			/* mxResolvingModules */
			fxNewInstance(the);
			/* mxRunningModules */
			fxNewInstance(the);
			/* mxRequiredModules */
			fxNewInstance(the);
			/* mxModules */
			mxPushUndefined();
			/* mxPendingJobs */
			fxNewInstance(the);
			/* mxRunningJobs */
			fxNewInstance(the);
			/* mxFiles */
			mxPushList();
			/* mxBreakpoints */
			mxPushList();
			
			/* mxHosts */
			mxPushUndefined();
			/* mxIDs */
			mxPushUndefined();
			/* mxEmptyCode */
			mxPushUndefined();
			the->stack->value.code = (txByte *)fxNewChunk(the, sizeof(gxNoCode));
			c_memcpy(the->stack->value.code, gxNoCode, sizeof(gxNoCode));
			the->stack->kind = XS_CODE_KIND;	
			/* mxEmptyString */
			mxPushStringC("");
			/* mxBooleanString */
			mxPushStringC("boolean");
			/* mxDefaultString */
			mxPushStringC("default");
			/* mxFunctionString */
			mxPushStringC("function");
			/* mxNumberString */
			mxPushStringC("number");
			/* mxObjectString */
			mxPushStringC("object");
			/* mxStringString */
			mxPushStringC("string");
			/* mxSymbolString */
			mxPushStringC("symbol");
			/* mxUndefinedString */
			mxPushStringC("undefined");
			for (anIndex = mxGetArgumentFunctionStackIndex; anIndex < mxStackIndexCount; anIndex++) 
				mxPushUndefined();
			
			fxBuildKeys(the);
			fxBuildGlobal(the);
			fxBuildObject(the);
			fxBuildFunction(the);
			fxBuildGenerator(the);
			fxBuildArray(the);
			fxBuildString(the);
			fxBuildBoolean(the);
			fxBuildNumber(the);
			fxBuildDate(the);
			fxBuildMath(the);
			fxBuildRegExp(the);
			fxBuildError(the);
			fxBuildJSON(the);
			fxBuildDataView(the);
			fxBuildPromise(the);
			fxBuildSymbol(the);
			fxBuildProxy(the);
			fxBuildMapSet(the);
			fxBuildModule(the);
			fxBuildHost(the);
			
			mxPush(mxSetPrototype);
			fxNewSetInstance(the);
			mxPull(mxModulePaths);
			
			mxPush(mxObjectPrototype);
			fxNewWeakSetInstance(the);
			mxPull(mxModules);
			
            the->collectFlag = XS_COLLECTING_FLAG;
			
            /*{
				int c = 32;
				while (--c)
					fxCollectGarbage(the);
			}*/
			the->context = theContext;

		#ifdef mxDebug
			if (fxGetAutomatic(the))
				fxLogin(the);
		#endif

			the->firstJump = C_NULL;
		}
		else {
		#if __FSK_LAYER__
			FskInstrumentedItemDispose(the);
		#endif
			fxFree(the);
			c_free(the);
			the = NULL;
		}
	}
	return the;
}
Beispiel #26
0
void fx_escape(txMachine* the)
{
	static char gxSet[128] = {
	  /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */
		 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,	/* 0x                    */
		 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,	/* 1x                    */
		 0,0,0,0,0,0,0,0,0,0,1,1,0,1,1,1,	/* 2x   !"#$%&'()*+,-./  */
		 1,1,1,1,1,1,1,1,1,1,1,0,0,0,0,0,	/* 3x  0123456789:;<=>?  */
		 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,	/* 4x  @ABCDEFGHIJKLMNO  */
		 1,1,1,1,1,1,1,1,1,1,1,0,0,0,0,1,	/* 5X  PQRSTUVWXYZ[\]^_  */
		 0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,	/* 6x  `abcdefghijklmno  */
		 1,1,1,1,1,1,1,1,1,1,1,0,0,0,0,0 	/* 7X  pqrstuvwxyz{|}~   */
	};
	txString string;
	txU1 *src;
	txInteger length;
	txU4 c;
	const txUTF8Sequence *sequence;
	txInteger size;
	txString result;
	txU1 *dst;
	
	if (mxArgc < 1)
		string = mxUndefinedString.value.string;
	else {
		string = fxToString(the, mxArgv(0));
	}
	src = (txU1*)string;
	length = 0;
	while ((c = *src++)) {
		for (sequence = gxUTF8Sequences; sequence->size; sequence++) {
			if ((c & sequence->cmask) == sequence->cval)
				break;
		}
		size = sequence->size - 1;
		while (size > 0) {
			size--;
			c = (c << 6) | (*src++ & 0x3F);
		}
		c &= sequence->lmask;
		if ((c < 128) && (gxSet[(int)c]))
			length += 1;
		else if (c < 256)
			length += 3;
		else
			length += 6;
	}
	length += 1;
	if (length == (src - (txU1*)string)) {
		mxResult->value.string = string;
		mxResult->kind = XS_STRING_KIND;
		return;
	}
	result = fxNewChunk(the, length);
	src = (txU1*)string;
	dst = (txU1*)result;
	while ((c = *src++)) {
		for (sequence = gxUTF8Sequences; sequence->size; sequence++) {
			if ((c & sequence->cmask) == sequence->cval)
				break;
		}
		size = sequence->size - 1;
		while (size > 0) {
			size--;
			c = (c << 6) | (*src++ & 0x3F);
		}
		c &= sequence->lmask;
		if ((c < 128) && (gxSet[(int)c]))
			*dst++ = (txU1)c;
		else if (c < 256) {
			*dst++ = '%';
			*dst++ = gxURIHexa[c >> 4];
			*dst++ = gxURIHexa[c & 15];
		}
		else {