wmls.c

来自「WAP browser is based on the Wireless App」· C语言 代码 · 共 1,474 行 · 第 1/3 页

C
1,474
字号
    if(s1)
        return s2 ? StrCompare(s1, s2) : 1;
    else
        return s2 ? -1 : 0;
}

///////////////////////////////////////////////////////////////////////////////

ScriptSlot *SlotToBoolean(ScriptSlot *ptr)
{
    switch(ptr->type)
    {
    case scriptTypeInteger:
        ptr->type = scriptTypeBoolean;
        break;

    case scriptTypeFloat:
        ptr->type = scriptTypeBoolean;
	ptr->value.n = ptr->value.f ? WMLS_TRUE : WMLS_FALSE;
        break;

    case scriptTypeString:
        SlotReplace(ptr, scriptTypeBoolean, ptr->value.s && StrLen(ptr->value.s));
        break;

    case scriptTypeBoolean:
        break;

    default:
        ptr->type = scriptTypeInvalid;
        break;
    }

    return ptr;
}

ScriptSlot *SlotToInteger(ScriptSlot *ptr)
{
    switch(ptr->type)
    {
    case scriptTypeInteger:
        break;

    case scriptTypeFloat:
        ptr->type = scriptTypeInvalid;
        break;

    case scriptTypeString:
        if(ptr->value.s && StrLen(ptr->value.s))
            SlotReplace(ptr, scriptTypeInteger, StrAToI(ptr->value.s));
        else
            SlotReplace(ptr, scriptTypeInvalid, 0);
        break;

    case scriptTypeBoolean:
        ptr->type = scriptTypeInteger;
        ptr->value.n = ptr->value.n ? 1 : 0;
        break;

    default:
        ptr->type = scriptTypeInvalid;
        break;
    }

    return ptr;
}

ScriptSlot *SlotToString(ScriptSlot *ptr)
{
    Char buf[12], *tmp, flp[22];

    switch(ptr->type)
    {
    case scriptTypeInteger:
        StrIToA(buf, ptr->value.n);
        
        ptr->type = scriptTypeString;
        ptr->value.s = NULL;
        SlotStrAppend(ptr, buf, StrLen(buf));
        break;

    case scriptTypeFloat:
	DoubleToString (ptr->value.f, flp);
        
        ptr->type = scriptTypeString;
        ptr->value.s = NULL;
        SlotStrAppend(ptr, flp, StrLen(flp));
        break;

    case scriptTypeString:
        break;

    case scriptTypeBoolean:
        tmp = ptr->value.n ? "true" : "false";

        ptr->type = scriptTypeString;
        ptr->value.s = NULL;
        SlotStrAppend(ptr, tmp, StrLen(tmp));
        break;

    default:
        ptr->type = scriptTypeInvalid;
        break;
    }

    return ptr;
}

ScriptSlot *SlotToFloat(ScriptSlot *ptr)
{
    switch(ptr->type)
    {
    case scriptTypeInteger:
        ptr->type = scriptTypeFloat;
        ptr->value.f = ptr->value.n;
        break;

    case scriptTypeFloat:
        break;

    case scriptTypeString:
        if(ptr->value.s && StrLen(ptr->value.s)) {
        	ptr->type = scriptTypeFloat;
        	ptr->value.f = StringToDouble(ptr->value.s);
	} else
            ptr->type = scriptTypeInvalid;
        break;

    case scriptTypeBoolean:
        ptr->type = scriptTypeFloat;
        ptr->value.f = ptr->value.n;
        break;

    default:
        ptr->type = scriptTypeInvalid;
        break;
    }

    return ptr;
}

UInt16 SlotMixedOp(ScriptSlot *arg1, ScriptSlot *arg2)
{
    if(arg1->type == scriptTypeString)
    {
        if(arg2->type == scriptTypeString || SlotToString(arg2)->type == scriptTypeString)
            return scriptTypeString;
         
    }
    else if(arg1->type == scriptTypeInteger)
    {
        if(arg2->type == scriptTypeString)
        {
            SlotToString(arg1);
            return scriptTypeString;
        }

        if(arg2->type == scriptTypeInteger)
            return scriptTypeInteger;

        if(arg2->type == scriptTypeBoolean)
        {
            SlotToInteger(arg2);
            return scriptTypeInteger;
        }

        if(arg2->type == scriptTypeFloat)
        {
            SlotToFloat(arg1);
            return scriptTypeFloat;
        }
    }
    else if(arg1->type == scriptTypeBoolean)
    {
        if(arg2->type == scriptTypeString)
        {
            SlotToString(arg1);
            return scriptTypeString;
        }

        SlotToInteger(arg1);

        if(arg2->type == scriptTypeInteger)
            return scriptTypeInteger;

        if(arg2->type == scriptTypeBoolean)
        {
            SlotToInteger(arg2);
            return scriptTypeInteger;
        }

        if(arg2->type == scriptTypeFloat)
        {
            SlotToFloat(arg1);
            return scriptTypeFloat;
        }
    }

    else if(arg1->type == scriptTypeFloat)
    {
        if(arg2->type == scriptTypeString)
        {
            SlotToString(arg1);
            return scriptTypeString;
        }

        if(arg2->type == scriptTypeInteger) {
	    SlotToFloat(arg2);
            return scriptTypeFloat;
	}

        if(arg2->type == scriptTypeBoolean)
        {
            SlotToFloat(arg1);
            return scriptTypeFloat;
        }

        if(arg2->type == scriptTypeFloat)
            return scriptTypeFloat;
    }

    SlotFree(arg1);
    SlotFree(arg2);
        
    return arg1->type = arg2->type = scriptTypeInvalid;
}

///////////////////////////////////////////////////////////////////////////////

void SlotCopy(ScriptSlot *dst, ScriptSlot *src)
{
    if((dst->type = src->type) == scriptTypeString)
        dst->value.s = ScriptStrCopy(src->value.s);
    else
        dst->value.a = src->value.a;
}

void SlotMove(ScriptSlot *dst, ScriptSlot *src)
{
    SlotFree(dst);

    dst->value.a = src->value.a;
    dst->type    = src->type;
    src->type    = scriptTypeInvalid;
}

void SlotFree(ScriptSlot *ptr)
{
    if(ptr->type == scriptTypeString)
    {
        ScriptStrFree(ptr->value.s);
        ptr->value.s = NULL;
    }
}

void SlotReplace(ScriptSlot *ptr, UInt8 type, Int32 value)
{
    SlotFree(ptr);

    ptr->type = type;
    ptr->value.n = value;
}

void SlotStrAppend(ScriptSlot *ptr, Char *str, UInt32 len1)
{
    Char *tmp;

    if(len1)
    {
        if(ptr->value.s)
        {
            UInt32 len2 = StrLen(ptr->value.s);
            UInt32 len3 = MemPtrSize(ptr->value.s);

            if(len1 + len2 >= len3)
            {
                tmp = MemPtrNew((len1 + len2 + 63) & 0xFFFFFFC0);
                ErrFatalDisplayIf(!tmp, "Out of memory [SlotStrAppend]");

                StrCopy(tmp, ptr->value.s);
                MemPtrFree(ptr->value.s);

                ptr->value.s = tmp;
            }
            
            tmp = ptr->value.s + len2;
        }
        else
        {
            ptr->value.s = tmp = MemPtrNew((len1 + 63) & 0xFFFFFFC0);
            ErrFatalDisplayIf(!tmp, "Out of memory [SlotStrAppend]");
        }

        StrNCopy(tmp, str, len1);
        tmp[len1] = 0;
    }
}

void SlotLoadConst(ScriptSlot *slot, UInt8 *src, UInt16 *offsetP)
{
    Int32 size;
    
    switch(src[(*offsetP)++])
    {
    case 0: // 8 bit signed integer
        slot->type = scriptTypeInteger;
        slot->value.n = *(Int8*)(src + *offsetP);
        *offsetP += 1;
        break;

    case 1: // 16 bit signed integer
        slot->type = scriptTypeInteger;
        slot->value.n = *(Int16*)(src + *offsetP);
        *offsetP += 2;
        break;

    case 2: // 32 bit signed integer
        slot->type = scriptTypeInteger;
        slot->value.n = *(Int32*)(src + *offsetP);
        *offsetP += 4;
        break;

    case 3: // 32 floating point
        slot->type = scriptTypeFloat;
        slot->value.f = *(double*)(src + *offsetP);
        *offsetP += 4;
        break;

    case 4: // UTF-8 string
        size = ReadIntMB(src, offsetP);

        slot->type = scriptTypeString;
        slot->value.s = MemPtrNew(size + 1);
        ErrFatalDisplayIf(slot->value.s == NULL, "MemPtrNew failed [SlotLoadConst]");
        
        MemMove(slot->value.s, src + *offsetP, size);
        slot->value.s[size] = 0;

        *offsetP += size;
        break;
        
    case 5: // empty string
        slot->type = scriptTypeString;
        slot->value.s = NULL;
        break;

    case 6: // string with external encoding
        size = ReadIntMB(src, offsetP);

        slot->type = scriptTypeString;
        slot->value.s = MemPtrNew(size + 1);
        ErrFatalDisplayIf(slot->value.s == NULL, "MemPtrNew failed [SlotLoadConst]");
        
        MemMove(slot->value.s, src + *offsetP, size);
        slot->value.s[size] = 0;

        *offsetP += size;
        break;

    default:
        ErrFatalDisplay("Unknown constant type [SlotLoadConst]");
    }
}

Char *SlotParseConst(ScriptSlot *ptr, Char *str)
{
    Int32 sign = 1, value = 0;

    if(*str == '\"' || *str == '\'')
    {
        Char *tmp = str;
        
        do {
            tmp = StrChr(tmp + 1, *str);
            if(tmp == NULL) return NULL;
        } while(*(tmp - 1) == '\\');

        ptr->type = scriptTypeString;
        ptr->value.s = NULL;

        str++;
        SlotStrAppend(ptr, str, tmp - str);
        return tmp + 1;
    }

    if(StrNCompare(str, "false", 5) == 0)
    {
        ptr->type = scriptTypeBoolean;
        ptr->value.n = WMLS_FALSE;
        return str + 5;
    }

    if(StrNCompare(str, "true", 4) == 0)
    {
        ptr->type = scriptTypeBoolean;
        ptr->value.n = WMLS_TRUE;
        return str + 4;
    }

    if(*str == '-')
    {
        while(*(++str) == ' ') ;
        sign = -1;
    }
    
    if ((StrChr(str, '.')) || (StrChr(str, 'e')) || (StrChr(str, 'E'))) { // Floating point

    	Char *tmp;
	Char *pos;

	StrCopy(tmp, str);

	if((pos = StrChr(tmp, ','))) {
		*pos = 0;
	}
	else {
		if((pos = StrChr(tmp, ')'))) {
			*pos = 0;
		}
		else {
			return NULL;
		}
	}

        ptr->type = scriptTypeFloat;
        ptr->value.f = StringToDouble(tmp);

        return str + StrLen(tmp);
    }
    else { // Integer
    	if(*str == '-')
    	{
    		while(*(++str) == ' ') ;
    		sign = -1;
    	}
    	if(*str == '+')
    	{
    		while(*(++str) == ' ') ;
    		sign = +1;
    	}

    	if(*str >= '0' && *str <= '9')
    	{
        	while(*str >= '0' && *str <= '9')
            		value = 10 * value + *str++ - '0';

		if (!value) value = 0;

        	ptr->type = scriptTypeInteger;
        	ptr->value.n = sign * value;
        	return str;
    	}
    }  
 
    return NULL;
}

static Int32 ReadIntMB(UInt8 *buf, UInt16 *offsetP)
{
    Int32 v = 0;
    UInt8 c;
    
    do {
        c = buf[(*offsetP)++];
        v = (v << 7) | (c & 0x7F);
    }
    while((c & 0x80) != 0);

    return v;
}

double StringToDouble(char *str)
{
    FlpCompDouble theCompFloat;
    double theFloat;

	// Convert a string to a float
	//theCompFloat.fd = FlpAToF(str);
	FlpBufferAToF(&theCompFloat.fd, str);
	theFloat = theCompFloat.d;
	return theFloat;
}

Err DoubleToString(double dbl, char *str)
{
    FlpCompDouble theFloat;

	theFloat.d = dbl;
	return FlpFToA(theFloat.fd, str);
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?