コード例 #1
0
        /*
         * Python-esque sequence operations.
         */
        private static string js_concat(string target, object [] args)
        {
            int N = args.Length;

            if (N == 0)
            {
                return(target);
            }
            else if (N == 1)
            {
                string arg = ScriptConvert.ToString(args [0]);
                return(string.Concat(target, arg));
            }

            // Find total capacity for the final string to avoid unnecessary
            // re-allocations in StringBuffer
            int size = target.Length;

            string [] argsAsStrings = new string [N];
            for (int i = 0; i != N; ++i)
            {
                string s = ScriptConvert.ToString(args [i]);
                argsAsStrings [i] = s;
                size += s.Length;
            }

            System.Text.StringBuilder result = new System.Text.StringBuilder(size);
            result.Append(target);
            for (int i = 0; i != N; ++i)
            {
                result.Append(argsAsStrings [i]);
            }
            return(result.ToString());
        }
コード例 #2
0
ファイル: Namespace.cs プロジェクト: lichuan80/EcmaScript.NET
        internal static Namespace Parse(XMLLib lib, Context cx, Object uriValue)
        {
            String prefix;
            String uri;

            if (uriValue is Namespace)
            {
                Namespace ns = (Namespace)uriValue;
                prefix = ns.Prefix;
                uri    = ns.Uri;
            }
            else if (uriValue is QName)
            {
                QName qname = (QName)uriValue;
                uri = qname.Uri;
                if (uri != null)
                {
                    prefix = qname.Prefix;
                }
                else
                {
                    uri    = qname.ToString();
                    prefix = null;
                }
            }
            else
            {
                uri    = ScriptConvert.ToString(uriValue);
                prefix = (uri.Length == 0) ? "" : null;
            }

            return(new Namespace(lib, prefix, uri));
        }
コード例 #3
0
        /**
         * See E4X 13.1.2.1.
         */
        public bool IsXMLName(Context cx, object value)
        {
            string name;

            try {
                name = ScriptConvert.ToString(value);
            }
            catch (EcmaScriptError ee) {
                if ("TypeError".Equals(ee.Name))
                {
                    return(false);
                }
                throw ee;
            }

            // See http://w3.org/TR/xml-names11/#NT-NCName
            int length = name.Length;

            if (length != 0)
            {
                if (IsNCNameStartChar(name [0]))
                {
                    for (int i = 1; i != length; ++i)
                    {
                        if (!IsNCNameChar(name [i]))
                        {
                            return(false);
                        }
                    }
                    return(true);
                }
            }

            return(false);
        }
コード例 #4
0
        private static long toInteger(System.Object value, System.Type type, double min, double max)
        {
            double d = toDouble(value);

            if (System.Double.IsInfinity(d) || System.Double.IsNaN(d))
            {
                // Convert to string first, for more readable message
                reportConversionError(ScriptConvert.ToString(value), type);
            }

            if (d > 0.0)
            {
                d = Math.Floor(d);
            }
            else
            {
                d = Math.Ceiling(d);
            }

            if (d < min || d > max)
            {
                // Convert to string first, for more readable message
                reportConversionError(ScriptConvert.ToString(value), type);
            }

            return((long)d);
        }
コード例 #5
0
        public override object ExecIdCall(IdFunctionObject f, Context cx, IScriptable scope, IScriptable thisObj, object [] args)
        {
            if (!f.HasTag(NUMBER_TAG))
            {
                return(base.ExecIdCall(f, cx, scope, thisObj, args));
            }
            int id = f.MethodId;

            if (id == Id_constructor)
            {
                double val = (args.Length >= 1) ? ScriptConvert.ToNumber(args [0]) : 0.0;
                if (thisObj == null)
                {
                    // new Number(val) creates a new Number object.
                    return(new BuiltinNumber(val));
                }
                // Number(val) converts val to a number value.
                return(val);
            }

            // The rest of Number.prototype methods require thisObj to be Number
            BuiltinNumber nativeNumber = (thisObj as BuiltinNumber);

            if (nativeNumber == null)
            {
                throw IncompatibleCallError(f);
            }
            double value = nativeNumber.doubleValue;

            switch (id)
            {
            case Id_toLocaleString:
            case Id_toString:
                return(ImplToString(value, args));

            case Id_toSource:
                return("(new Number(" + ScriptConvert.ToString(value) + "))");


            case Id_valueOf:
                return(value);


            case Id_toFixed:
                return(ImplToFixed(value, args));


            case Id_toExponential:
                return(ImplToExponential(value, args));


            case Id_toPrecision:
                return(ImplToPrecision(value, args));

            default:
                throw new ArgumentException(Convert.ToString(id));
            }
        }
コード例 #6
0
 internal static int AssertValidPrecision(int precision)
 {
     if (precision < 0 || precision > MAX_PRECISION)
     {
         string msg = ScriptRuntime.GetMessage("msg.bad.precision", ScriptConvert.ToString(precision));
         throw ScriptRuntime.ConstructError("RangeError", msg);
     }
     return(precision);
 }
コード例 #7
0
        internal XMLName toQualifiedName(Context cx, Object namespaceValue,
                                         Object nameValue)
        {
            // This is duplication of constructQName(cx, namespaceValue, nameValue)
            // but for XMLName

            String uri;
            String localName;

            if (nameValue is QName)
            {
                QName qname = (QName)nameValue;
                localName = qname.LocalName;
            }
            else
            {
                localName = ScriptConvert.ToString(nameValue);
            }

            Namespace ns;

            if (namespaceValue == Undefined.Value)
            {
                if ("*".Equals(localName))
                {
                    ns = null;
                }
                else
                {
                    ns = GetDefaultNamespace(cx);
                }
            }
            else if (namespaceValue == null)
            {
                ns = null;
            }
            else if (namespaceValue is Namespace)
            {
                ns = (Namespace)namespaceValue;
            }
            else
            {
                ns = Namespace.Parse(this, cx, namespaceValue);
            }

            if (ns == null)
            {
                uri = null;
            }
            else
            {
                uri = ns.Uri;
            }

            return(XMLName.FormProperty(uri, localName));
        }
コード例 #8
0
        private static string getString(IScriptable obj, string id)
        {
            object value = ScriptableObject.GetProperty(obj, id);

            if (value == UniqueTag.NotFound)
            {
                return("");
            }
            return(ScriptConvert.ToString(value));
        }
コード例 #9
0
        internal static QName Parse(XMLLib lib, Context cx, object namespaceValue, object nameValue)
        {
            String uri;
            String localName;
            String prefix;

            if (nameValue is QName)
            {
                QName qname = (QName)nameValue;
                localName = qname.LocalName;
            }
            else
            {
                localName = ScriptConvert.ToString(nameValue);
            }

            Namespace ns;

            if (namespaceValue == Undefined.Value)
            {
                if ("*".Equals(localName))
                {
                    ns = null;
                }
                else
                {
                    ns = lib.GetDefaultNamespace(cx);
                }
            }
            else if (namespaceValue == null)
            {
                ns = null;
            }
            else if (namespaceValue is Namespace)
            {
                ns = (Namespace)namespaceValue;
            }
            else
            {
                ns = Namespace.Parse(lib, cx, namespaceValue);
            }

            if (ns == null)
            {
                uri    = null;
                prefix = null;
            }
            else
            {
                uri    = ns.Uri;
                prefix = ns.Prefix;
            }

            return(new QName(lib, uri, localName, prefix));
        }
コード例 #10
0
ファイル: Namespace.cs プロジェクト: lichuan80/EcmaScript.NET
        public static Namespace Parse(XMLLib lib, Context cx, Object prefixValue,
                                      Object uriValue)
        {
            String prefix;
            String uri;

            if (uriValue is QName)
            {
                QName qname = (QName)uriValue;
                uri = qname.Uri;
                if (uri == null)
                {
                    uri = qname.ToString();
                }
            }
            else
            {
                uri = ScriptConvert.ToString(uriValue);
            }

            if (uri.Length == 0)
            {
                if (prefixValue == Undefined.Value)
                {
                    prefix = "";
                }
                else
                {
                    prefix = ScriptConvert.ToString(prefixValue);
                    if (prefix.Length != 0)
                    {
                        throw ScriptRuntime.TypeError(
                                  "Illegal prefix '" + prefix + "' for 'no namespace'.");
                    }
                }
            }
            else if (prefixValue == Undefined.Value)
            {
                prefix = "";
            }
            else if (!lib.IsXMLName(cx, prefixValue))
            {
                prefix = "";
            }
            else
            {
                prefix = ScriptConvert.ToString(prefixValue);
            }

            return(new Namespace(lib, prefix, uri));
        }
コード例 #11
0
        public override object ExecIdCall(IdFunctionObject f, Context cx, IScriptable scope, IScriptable thisObj, object [] args)
        {
            if (!f.HasTag(SCRIPT_TAG))
            {
                return(base.ExecIdCall(f, cx, scope, thisObj, args));
            }
            int id = f.MethodId;

            switch (id)
            {
            case Id_constructor: {
                string        source  = (args.Length == 0) ? "" : ScriptConvert.ToString(args [0]);
                IScript       script  = compile(cx, source);
                BuiltinScript nscript = new BuiltinScript(script);
                ScriptRuntime.setObjectProtoAndParent(nscript, scope);
                return(nscript);
            }


            case Id_toString: {
                if (thisObj is BuiltinFunction)
                {
                    return(((BuiltinFunction)thisObj).Decompile(0, 0));
                }

                BuiltinScript real       = realThis(thisObj, f);
                IScript       realScript = real.script;
                if (realScript == null)
                {
                    return("");
                }
                return(cx.DecompileScript(realScript, 0));
            }


            case Id_exec: {
                throw Context.ReportRuntimeErrorById("msg.cant.call.indirect", "exec");
            }


            case Id_compile: {
                BuiltinScript real   = realThis(thisObj, f);
                string        source = ScriptConvert.ToString(args, 0);
                real.script = compile(cx, source);
                return(real);
            }
            }
            throw new ArgumentException(Convert.ToString(id));
        }
コード例 #12
0
        /// <summary> The global unescape method, as per ECMA-262 15.1.2.5.</summary>

        private object js_unescape(object [] args)
        {
            string s = ScriptConvert.ToString(args, 0);
            int    firstEscapePos = s.IndexOf((char)'%');

            if (firstEscapePos >= 0)
            {
                int     L           = s.Length;
                char [] buf         = s.ToCharArray();
                int     destination = firstEscapePos;
                for (int k = firstEscapePos; k != L;)
                {
                    char c = buf [k];
                    ++k;
                    if (c == '%' && k != L)
                    {
                        int end, start;
                        if (buf [k] == 'u')
                        {
                            start = k + 1;
                            end   = k + 5;
                        }
                        else
                        {
                            start = k;
                            end   = k + 2;
                        }
                        if (end <= L)
                        {
                            int x = 0;
                            for (int i = start; i != end; ++i)
                            {
                                x = ScriptConvert.XDigitToInt(buf [i], x);
                            }
                            if (x >= 0)
                            {
                                c = (char)x;
                                k = end;
                            }
                        }
                    }
                    buf [destination] = c;
                    ++destination;
                }
                s = new string (buf, 0, destination);
            }
            return(s);
        }
コード例 #13
0
        public override object ExecIdCall(IdFunctionObject f, Context cx, IScriptable scope, IScriptable thisObj, object [] args)
        {
            int id = f.MethodId;

            switch (id)
            {
            case Id_print:
                for (int i = 0; i < args.Length; i++)
                {
                    if (i > 0)
                    {
                        Console.Out.Write(" ");
                    }
                    Console.Out.Write(ScriptConvert.ToString(args [i]));
                }
                Console.Out.WriteLine();
                return(Undefined.Value);

            case Id_version:
                if (args.Length > 0)
                {
                    if (CliHelper.IsNumber(args [0]))
                    {
                        int newVer = (int)ScriptConvert.ToNumber(args [0]);
                        if (Context.IsValidLanguageVersion(newVer))
                        {
                            cx.Version = Context.ToValidLanguageVersion(newVer);
                        }
                    }
                }
                return((int)cx.Version);

            case Id_options:
                StringBuilder sb = new StringBuilder();
                if (cx.HasFeature(Context.Features.Strict))
                {
                    sb.Append("strict");
                }
                return(sb.ToString());

            case Id_gc:
                GC.Collect();
                return(Undefined.Value);
            }
            throw f.Unknown();
        }
コード例 #14
0
        internal static QName Parse(XMLLib lib, Context cx, object value)
        {
            QName result;

            if (value is QName)
            {
                QName qname = (QName)value;
                result = new QName(lib, qname.Uri, qname.LocalName,
                                   qname.Prefix);
            }
            else
            {
                result = Parse(lib, cx, ScriptConvert.ToString(value));
            }

            return(result);
        }
コード例 #15
0
        /*
         *
         * See ECMA 15.5.4.7
         *
         */
        private static int js_lastIndexOf(string target, object [] args)
        {
            string search = ScriptConvert.ToString(args, 0);
            double end    = ScriptConvert.ToNumber(args, 1);

            if (double.IsNaN(end) || end > target.Length)
            {
                end = target.Length;
            }
            else if (end < 0)
            {
                end = 0;
            }

            return(lastIndexOf(
                       target.ToCharArray(), 0, target.Length, search.ToCharArray(), 0, search.Length, (int)end));
        }
コード例 #16
0
        private static string js_toSource(Context cx, IScriptable scope, IScriptable thisObj)
        {
            // Emulation of SpiderMonkey behavior
            object name       = ScriptableObject.GetProperty(thisObj, "name");
            object message    = ScriptableObject.GetProperty(thisObj, "message");
            object fileName   = ScriptableObject.GetProperty(thisObj, "fileName");
            object lineNumber = ScriptableObject.GetProperty(thisObj, "lineNumber");

            System.Text.StringBuilder sb = new System.Text.StringBuilder();
            sb.Append("(new ");
            if (name == UniqueTag.NotFound)
            {
                name = Undefined.Value;
            }
            sb.Append(ScriptConvert.ToString(name));
            sb.Append("(");
            if (message != UniqueTag.NotFound || fileName != UniqueTag.NotFound || lineNumber != UniqueTag.NotFound)
            {
                if (message == UniqueTag.NotFound)
                {
                    message = "";
                }
                sb.Append(ScriptRuntime.uneval(cx, scope, message));
                if (fileName != UniqueTag.NotFound || lineNumber != UniqueTag.NotFound)
                {
                    sb.Append(", ");
                    if (fileName == UniqueTag.NotFound)
                    {
                        fileName = "";
                    }
                    sb.Append(ScriptRuntime.uneval(cx, scope, fileName));
                    if (lineNumber != UniqueTag.NotFound)
                    {
                        int line = ScriptConvert.ToInt32(lineNumber);
                        if (line != 0)
                        {
                            sb.Append(", ");
                            sb.Append(ScriptConvert.ToString(line));
                        }
                    }
                }
            }
            sb.Append("))");
            return(sb.ToString());
        }
コード例 #17
0
        /*
         *
         * See ECMA 15.5.4.6.  Uses Java String.indexOf()
         * OPT to add - BMH searching from jsstr.c.
         */
        private static int js_indexOf(string target, object [] args)
        {
            string search = ScriptConvert.ToString(args, 0);
            double begin  = ScriptConvert.ToInteger(args, 1);

            if (begin > target.Length)
            {
                return(-1);
            }
            else
            {
                if (begin < 0)
                {
                    begin = 0;
                }
                return(target.IndexOf(search, (int)begin));
            }
        }
コード例 #18
0
        private static string num_to(double val, object [] args, int zeroArgMode, int oneArgMode, int precisionMin, int precisionOffset)
        {
            int precision;

            if (args.Length == 0)
            {
                precision  = 0;
                oneArgMode = zeroArgMode;
            }
            else
            {
                /* We allow a larger range of precision than
                *  ECMA requires; this is permitted by ECMA. */
                precision = ScriptConvert.ToInt32(args [0]);
                if (precision < precisionMin || precision > MAX_PRECISION)
                {
                    string msg = ScriptRuntime.GetMessage("msg.bad.precision", ScriptConvert.ToString(args [0]));
                    throw ScriptRuntime.ConstructError("RangeError", msg);
                }
            }


            switch (zeroArgMode)
            {
            case DTOSTR_FIXED:
                return(val.ToString("F" + (precision + precisionOffset), NumberFormatter));

            case DTOSTR_STANDARD_EXPONENTIAL:
                return(val.ToString("e" + (precision + precisionOffset), NumberFormatter));

            case DTOSTR_STANDARD:
                if (oneArgMode == DTOSTR_PRECISION)
                {
                    return(val.ToString(precision.ToString(), NumberFormatter));
                }
                else
                {
                    return(val.ToString(NumberFormatter));
                }
            }

            Context.CodeBug();
            return(string.Empty); // Not reached
        }
コード例 #19
0
        protected internal override void SetInstanceIdValue(int id, object value)
        {
            int shifted = id - base.MaxInstanceId;

            switch (shifted)
            {
            case Id_multiline:
            case Id_STAR:
                Impl.multiline = ScriptConvert.ToBoolean(value);
                return;


            case Id_input:
            case Id_UNDERSCORE:
                Impl.input = ScriptConvert.ToString(value);
                return;
            }
            base.SetInstanceIdValue(id, value);
        }
コード例 #20
0
ファイル: XMLList.cs プロジェクト: lichuan80/EcmaScript.NET
        public XMLList(XMLLib lib, object inputObject)
            : this(lib)
        {
            string frag;
            if (inputObject == null || inputObject is Undefined)
            {
                frag = "";
            }
            else if (inputObject is XML)
            {
                XML xml = (XML)inputObject;
                Add(xml);
            }
            else if (inputObject is XMLList)
            {
                XMLList xmll = (XMLList)inputObject;
                AddRange(xmll);
            }
            else
            {
                frag = ScriptConvert.ToString(inputObject).Trim();
                if (!frag.StartsWith("<>"))
                {
                    frag = "<>" + frag + "</>";
                }
                frag = "<fragment>" + frag.Substring(2);
                if (!frag.EndsWith("</>"))
                {
                    throw ScriptRuntime.TypeError("XML with anonymous tag missing end anonymous tag");
                }
                frag = frag.Substring(0, frag.Length - 3) + "</fragment>";

                XML orgXML = XML.CreateFromJS(lib, frag);

                // Now orphan the children and add them to our XMLList.
                XMLList children = (XMLList)orgXML.Children();
                AddRange(children);
            }
        }
コード例 #21
0
        /// <summary>
        /// HTML composition aids.
        /// </summary>
        private static string Tagify(object thisObj, string tag, string attribute, object [] args)
        {
            string str = ScriptConvert.ToString(thisObj);

            System.Text.StringBuilder result = new System.Text.StringBuilder();
            result.Append('<');
            result.Append(tag);
            if (attribute != null)
            {
                result.Append(' ');
                result.Append(attribute);
                result.Append("=\"");
                result.Append(ScriptConvert.ToString(args, 0));
                result.Append('"');
            }
            result.Append('>');
            result.Append(str);
            result.Append("</");
            result.Append(tag);
            result.Append('>');
            return(result.ToString());
        }
コード例 #22
0
        internal static EcmaScriptError BadXMLName(object value)
        {
            String msg;

            if (CliHelper.IsNumber(value))
            {
                msg = "Can not construct XML name from number: ";
            }
            else if (value is Boolean)
            {
                msg = "Can not construct XML name from boolean: ";
            }
            else if (value == Undefined.Value || value == null)
            {
                msg = "Can not construct XML name from ";
            }
            else
            {
                throw new ArgumentException(value.ToString());
            }
            return(ScriptRuntime.TypeError(msg + ScriptConvert.ToString(value)));
        }
コード例 #23
0
        internal static BuiltinError make(Context cx, IScriptable scope, IdFunctionObject ctorObj, object [] args)
        {
            IScriptable proto = (IScriptable)(ctorObj.Get("prototype", ctorObj));

            BuiltinError obj = new BuiltinError();

            obj.SetPrototype(proto);
            obj.ParentScope = scope;

            if (args.Length >= 1)
            {
                ScriptableObject.PutProperty(obj, "message", ScriptConvert.ToString(args [0]));
                if (args.Length >= 2)
                {
                    ScriptableObject.PutProperty(obj, "fileName", args [1]);
                    if (args.Length >= 3)
                    {
                        int line = ScriptConvert.ToInt32(args [2]);
                        ScriptableObject.PutProperty(obj, "lineNumber", (object)line);
                    }
                }
            }
            return(obj);
        }
コード例 #24
0
        /// <summary> Type-munging for field setting and method invocation.
        /// Conforms to LC3 specification
        /// </summary>
        internal static System.Object CoerceType(System.Type type, System.Object value)
        {
            if (value != null && value.GetType() == type)
            {
                return(value);
            }

            switch (GetJSTypeCode(value))
            {
            case JSTYPE_NULL:
                // raise error if type.isPrimitive()
                if (type.IsPrimitive)
                {
                    reportConversionError(value, type);
                }
                return(null);


            case JSTYPE_UNDEFINED:
                if (type == typeof(string) || type == typeof(object))
                {
                    return("undefined");
                }
                else
                {
                    reportConversionError("undefined", type);
                }
                break;


            case JSTYPE_BOOLEAN:
                // Under LC3, only JS Booleans can be coerced into a Boolean value
                if (type == typeof(bool) || type == typeof(bool) || type == typeof(object))
                {
                    return(value);
                }
                else if (type == typeof(string))
                {
                    return(value.ToString());
                }
                else
                {
                    reportConversionError(value, type);
                }
                break;


            case JSTYPE_NUMBER:
                if (type == typeof(string))
                {
                    return(ScriptConvert.ToString(value));
                }
                else if (type == typeof(object))
                {
                    return(CoerceToNumber(typeof(double), value));
                }
                else if ((type.IsPrimitive && type != typeof(bool)) || CliHelper.IsNumberType(type))
                {
                    return(CoerceToNumber(type, value));
                }
                else
                {
                    reportConversionError(value, type);
                }
                break;


            case JSTYPE_STRING:
                if (type == typeof(string) || type.IsInstanceOfType(value))
                {
                    return(value);
                }
                else if (type == typeof(char))
                {
                    // Special case for converting a single char string to a
                    // character
                    // Placed here because it applies *only* to JS strings,
                    // not other JS objects converted to strings
                    if (((System.String)value).Length == 1)
                    {
                        return(((System.String)value) [0]);
                    }
                    else
                    {
                        return(CoerceToNumber(type, value));
                    }
                }
                else if ((type.IsPrimitive && type != typeof(bool)) || CliHelper.IsNumberType(type))
                {
                    return(CoerceToNumber(type, value));
                }
                else
                {
                    reportConversionError(value, type);
                }
                break;


            case JSTYPE_CLI_CLASS:
                if (value is Wrapper)
                {
                    value = ((Wrapper)value).Unwrap();
                }

                if (type == typeof(Type) || type == typeof(object))
                {
                    return(value);
                }
                else if (type == typeof(string))
                {
                    return(value.ToString());
                }
                else
                {
                    reportConversionError(value, type);
                }
                break;


            case JSTYPE_CLI_OBJECT:
            case JSTYPE_CLI_ARRAY:
                if (type.IsPrimitive)
                {
                    if (type == typeof(bool))
                    {
                        reportConversionError(value, type);
                    }
                    return(CoerceToNumber(type, value));
                }
                else
                {
                    if (value is Wrapper)
                    {
                        value = ((Wrapper)value).Unwrap();
                    }
                    if (type == typeof(string))
                    {
                        return(value.ToString());
                    }
                    else
                    {
                        if (type.IsInstanceOfType(value))
                        {
                            return(value);
                        }
                        else
                        {
                            reportConversionError(value, type);
                        }
                    }
                }
                break;


            case JSTYPE_OBJECT:
                if (type == typeof(string))
                {
                    return(ScriptConvert.ToString(value));
                }
                else if (type.IsPrimitive)
                {
                    if (type == typeof(bool))
                    {
                        reportConversionError(value, type);
                    }
                    return(CoerceToNumber(type, value));
                }
                else if (type.IsInstanceOfType(value))
                {
                    return(value);
                }
                else if (type == typeof(DateTime) && value is BuiltinDate)
                {
                    double time = ((BuiltinDate)value).JSTimeValue;
                    // TODO: This will replace NaN by 0
                    return(BuiltinDate.FromMilliseconds((long)time));
                }
                else if (type.IsArray && value is BuiltinArray)
                {
                    // Make a new java array, and coerce the JS array components
                    // to the target (component) type.
                    BuiltinArray  array     = (BuiltinArray)value;
                    long          length    = array.getLength();
                    System.Type   arrayType = type.GetElementType();
                    System.Object Result    = System.Array.CreateInstance(arrayType, (int)length);
                    for (int i = 0; i < length; ++i)
                    {
                        try {
                            ((System.Array)Result).SetValue(CoerceType(arrayType, array.Get(i, array)), i);
                        }
                        catch (EcmaScriptException) {
                            reportConversionError(value, type);
                        }
                    }

                    return(Result);
                }
                else if (value is Wrapper)
                {
                    value = ((Wrapper)value).Unwrap();
                    if (type.IsInstanceOfType(value))
                    {
                        return(value);
                    }
                    reportConversionError(value, type);
                }
                else
                {
                    reportConversionError(value, type);
                }
                break;
            }

            return(value);
        }
コード例 #25
0
        public override object Call(Context cx, IScriptable scope, IScriptable thisObj, object [] args)
        {
            if (m_MethodInfos.Length == 0)
            {
                throw new ApplicationException("No methods defined for call");
            }

            int index = FindFunction(cx, m_MethodInfos, args, paramsParameters);

            if (index < 0)
            {
                Type   c   = m_MethodInfos [0].DeclaringType;
                string sig = c.FullName + '.' + FunctionName + '(' + ScriptSignature(args) + ')';
                throw Context.ReportRuntimeErrorById("msg.java.no_such_method", sig);
            }

            MethodBase meth = (MethodBase)m_MethodInfos [index];

            ParameterInfo [] pis = meth.GetParameters();

            // First, we marshall the args.
            object [] origArgs = args;
            for (int i = 0; i < args.Length; i++)
            {
                object arg = args [i];

                if (paramsParameters [index] && i >= pis.Length - 1)
                {
                    // params[] arg is always an array type
                    Type arrayType        = pis [pis.Length - 1].ParameterType;
                    Type arrayElementType = arrayType.GetElementType();

                    object [] dummyArg = new object [args.Length - i];
                    for (int e = i; e < args.Length; e++)
                    {
                        dummyArg [e - i] = Context.JsToCli(arg, arrayElementType);
                    }
                    args = new object [i + 1];
                    args.CopyTo(args, 0);
                    args [i] = dummyArg;
                }
                else
                {
                    Type   argType = pis [i].ParameterType;
                    object coerced = Context.JsToCli(arg, argType);
                    if (coerced != arg)
                    {
                        if (origArgs == args)
                        {
                            args = new object [args.Length];
                            args.CopyTo(args, 0);
                        }
                        args [i] = coerced;
                    }
                }
            }
            object cliObject;

            if (meth.IsStatic)
            {
                cliObject = null; // don't need an object
            }
            else
            {
                IScriptable o = thisObj;
                Type        c = meth.DeclaringType;
                for (; ;)
                {
                    if (o == null)
                    {
                        throw Context.ReportRuntimeErrorById("msg.nonjava.method", FunctionName, ScriptConvert.ToString(thisObj), c.FullName);
                    }
                    if (o is Wrapper)
                    {
                        cliObject = ((Wrapper)o).Unwrap();
                        if (c.IsInstanceOfType(cliObject))
                        {
                            break;
                        }
                    }
                    o = o.GetPrototype();
                }
            }

            object retval = null;

            try {
                retval = (meth as MethodBase).Invoke(cliObject, args);
            }
            catch (Exception ex) {
                Context.ThrowAsScriptRuntimeEx(ex);
            }

            Type staticType = meth.DeclaringType;

            if (meth is MethodInfo)
            {
                staticType = ((MethodInfo)meth).ReturnType;
            }

            object wrapped = cx.Wrap(scope, retval, staticType);

            if (wrapped == null && staticType == Type.GetType("System.Void"))
            {
                wrapped = Undefined.Value;
            }
            return(wrapped);
        }
コード例 #26
0
        internal static XMLName Parse(XMLLib lib, Context cx, Object value)
        {
            XMLName result;

            if (value is XMLName)
            {
                result = (XMLName)value;
            }
            else if (value is String)
            {
                String str  = (String)value;
                long   test = ScriptRuntime.testUint32String(str);
                if (test >= 0)
                {
                    ScriptRuntime.storeUint32Result(cx, test);
                    result = null;
                }
                else
                {
                    result = Parse(lib, cx, str);
                }
            }
            else if (CliHelper.IsNumber(value))
            {
                double d = ScriptConvert.ToNumber(value);
                long   l = (long)d;
                if (l == d && 0 <= l && l <= 0xFFFFFFFFL)
                {
                    ScriptRuntime.storeUint32Result(cx, l);
                    result = null;
                }
                else
                {
                    throw XMLLib.BadXMLName(value);
                }
            }
            else if (value is QName)
            {
                QName  qname  = (QName)value;
                String uri    = qname.Uri;
                bool   number = false;
                result = null;
                if (uri != null && uri.Length == 0)
                {
                    // Only in this case qname.toString() can resemble uint32
                    long test = ScriptRuntime.testUint32String(uri);
                    if (test >= 0)
                    {
                        ScriptRuntime.storeUint32Result(cx, test);
                        number = true;
                    }
                }
                if (!number)
                {
                    result = XMLName.FormProperty(uri, qname.LocalName);
                }
            }
            else if (value is Boolean ||
                     value == Undefined.Value ||
                     value == null)
            {
                throw XMLLib.BadXMLName(value);
            }
            else
            {
                String str  = ScriptConvert.ToString(value);
                long   test = ScriptRuntime.testUint32String(str);
                if (test >= 0)
                {
                    ScriptRuntime.storeUint32Result(cx, test);
                    result = null;
                }
                else
                {
                    result = Parse(lib, cx, str);
                }
            }

            return(result);
        }
コード例 #27
0
        public virtual object ExecIdCall(IdFunctionObject f, Context cx, IScriptable scope, IScriptable thisObj, object [] args)
        {
            if (f.HasTag(FTAG))
            {
                int methodId = f.MethodId;
                switch (methodId)
                {
                case Id_decodeURI:
                case Id_decodeURIComponent: {
                    string str = ScriptConvert.ToString(args, 0);
                    return(decode(str, methodId == Id_decodeURI));
                }


                case Id_encodeURI:
                case Id_encodeURIComponent: {
                    string str = ScriptConvert.ToString(args, 0);
                    return(encode(str, methodId == Id_encodeURI));
                }


                case Id_escape:
                    return(js_escape(args));


                case Id_eval:
                    return(ImplEval(cx, scope, thisObj, args));


                case Id_isFinite: {
                    bool result;
                    if (args.Length < 1)
                    {
                        result = false;
                    }
                    else
                    {
                        double d = ScriptConvert.ToNumber(args [0]);
                        result = (!double.IsNaN(d) && d != System.Double.PositiveInfinity && d != System.Double.NegativeInfinity);
                    }
                    return(result);
                }


                case Id_isNaN: {
                    // The global method isNaN, as per ECMA-262 15.1.2.6.
                    bool result;
                    if (args.Length < 1)
                    {
                        result = true;
                    }
                    else
                    {
                        double d = ScriptConvert.ToNumber(args [0]);
                        result = (double.IsNaN(d));
                    }
                    return(result);
                }


                case Id_isXMLName: {
                    object name   = (args.Length == 0) ? Undefined.Value : args [0];
                    XMLLib xmlLib = XMLLib.ExtractFromScope(scope);
                    return(xmlLib.IsXMLName(cx, name));
                }


                case Id_parseFloat:
                    return(js_parseFloat(args));


                case Id_parseInt:
                    return(js_parseInt(args));


                case Id_unescape:
                    return(js_unescape(args));


                case Id_uneval: {
                    object value = (args.Length != 0) ? args [0] : Undefined.Value;
                    return(ScriptRuntime.uneval(cx, scope, value));
                }


                case Id_new_CommonError:
                    // The implementation of all the ECMA error constructors
                    // (SyntaxError, TypeError, etc.)
                    return(BuiltinError.make(cx, scope, f, args));
                }
            }
            throw f.Unknown();
        }
コード例 #28
0
        /// <summary> The global method parseInt, as per ECMA-262 15.1.2.2.</summary>
        private object js_parseInt(object [] args)
        {
            string s     = ScriptConvert.ToString(args, 0);
            int    radix = ScriptConvert.ToInt32(args, 1);

            int len = s.Length;

            if (len == 0)
            {
                return(double.NaN);
            }

            bool negative = false;
            int  start    = 0;
            char c;

            do
            {
                c = s [start];
                if (!char.IsWhiteSpace(c))
                {
                    break;
                }
                start++;
            }while (start < len);

            if (c == '+' || (negative = (c == '-')))
            {
                start++;
            }

            const int NO_RADIX = -1;

            if (radix == 0)
            {
                radix = NO_RADIX;
            }
            else if (radix < 2 || radix > 36)
            {
                return(double.NaN);
            }
            else if (radix == 16 && len - start > 1 && s [start] == '0')
            {
                c = s [start + 1];
                if (c == 'x' || c == 'X')
                {
                    start += 2;
                }
            }

            if (radix == NO_RADIX)
            {
                radix = 10;
                if (len - start > 1 && s [start] == '0')
                {
                    c = s [start + 1];
                    if (c == 'x' || c == 'X')
                    {
                        radix  = 16;
                        start += 2;
                    }
                    else if ('0' <= c && c <= '9')
                    {
                        radix = 8;
                        start++;
                    }
                }
            }

            double d = ScriptConvert.ToNumber(s, start, radix);

            return(negative ? -d : d);
        }
コード例 #29
0
        /// <summary> The global method parseFloat, as per ECMA-262 15.1.2.3.
        ///
        /// </summary>
        /// <param name="cx">unused
        /// </param>
        /// <param name="thisObj">unused
        /// </param>
        /// <param name="args">the arguments to parseFloat, ignoring args[>=1]
        /// </param>
        /// <param name="funObj">unused
        /// </param>
        private object js_parseFloat(object [] args)
        {
            if (args.Length < 1)
            {
                return(double.NaN);
            }

            string s     = ScriptConvert.ToString(args [0]);
            int    len   = s.Length;
            int    start = 0;
            // Scan forward to skip whitespace
            char c;

            for (; ;)
            {
                if (start == len)
                {
                    return(double.NaN);
                }
                c = s [start];
                if (!TokenStream.isJSSpace(c))
                {
                    break;
                }
                ++start;
            }

            int i = start;

            if (c == '+' || c == '-')
            {
                ++i;
                if (i == len)
                {
                    return(double.NaN);
                }
                c = s [i];
            }

            if (c == 'I')
            {
                // check for "Infinity"
                if (i + 8 <= len && String.Compare(s, i, "Infinity", 0, 8) == 0)
                {
                    double d;
                    if (s [start] == '-')
                    {
                        d = System.Double.NegativeInfinity;
                    }
                    else
                    {
                        d = System.Double.PositiveInfinity;
                    }
                    return(d);
                }
                return(double.NaN);
            }

            // Find the end of the legal bit
            int dec      = -1;
            int exponent = -1;

            for (; i < len; i++)
            {
                switch (s [i])
                {
                case '.':
                    if (dec != -1)
                    {
                        // Only allow a single decimal point.
                        break;
                    }
                    dec = i;
                    continue;


                case 'e':
                case 'E':
                    if (exponent != -1)
                    {
                        break;
                    }
                    exponent = i;
                    continue;


                case '+':
                case '-':
                    // Only allow '+' or '-' after 'e' or 'E'
                    if (exponent != i - 1)
                    {
                        break;
                    }
                    continue;


                case '0':
                case '1':
                case '2':
                case '3':
                case '4':
                case '5':
                case '6':
                case '7':
                case '8':
                case '9':
                    continue;


                default:
                    break;
                }
                break;
            }
            s = s.Substring(start, (i) - (start));
            try {
                return(System.Double.Parse(s, BuiltinNumber.NumberFormatter));
            }
            catch (OverflowException) {
                // HACK
                if (s [0] == '-')
                {
                    return(double.NegativeInfinity);
                }
                else
                {
                    return(double.PositiveInfinity);
                }
            }
            catch (Exception) {
                return(double.NaN);
            }
        }
コード例 #30
0
        /// <summary> The global method escape, as per ECMA-262 15.1.2.4.
        /// Includes code for the 'mask' argument supported by the C escape
        /// method, which used to be part of the browser imbedding.  Blame
        /// for the strange constant names should be directed there.
        /// </summary>

        private object js_escape(object [] args)
        {
            const int URL_XALPHAS  = 1;
            const int URL_XPALPHAS = 2;
            const int URL_PATH     = 4;

            string s = ScriptConvert.ToString(args, 0);

            int mask = URL_XALPHAS | URL_XPALPHAS | URL_PATH;

            if (args.Length > 1)
            {
                // the 'mask' argument.  Non-ECMA.
                double d = ScriptConvert.ToNumber(args [1]);
                if (double.IsNaN(d) || ((mask = (int)d) != d) || 0 != (mask & ~(URL_XALPHAS | URL_XPALPHAS | URL_PATH)))
                {
                    throw Context.ReportRuntimeErrorById("msg.bad.esc.mask");
                }
            }

            System.Text.StringBuilder sb = null;
            for (int k = 0, L = s.Length; k != L; ++k)
            {
                int c = s [k];
                if (mask != 0 && ((c >= '0' && c <= '9') || (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || c == '@' || c == '*' || c == '_' || c == '-' || c == '.' || (0 != (mask & URL_PATH) && (c == '/' || c == '+'))))
                {
                    if (sb != null)
                    {
                        sb.Append((char)c);
                    }
                }
                else
                {
                    if (sb == null)
                    {
                        sb = new System.Text.StringBuilder(L + 3);
                        sb.Append(s);
                        sb.Length = k;
                    }

                    int hexSize;
                    if (c < 256)
                    {
                        if (c == ' ' && mask == URL_XPALPHAS)
                        {
                            sb.Append('+');
                            continue;
                        }
                        sb.Append('%');
                        hexSize = 2;
                    }
                    else
                    {
                        sb.Append('%');
                        sb.Append('u');
                        hexSize = 4;
                    }

                    // append hexadecimal form of c left-padded with 0
                    for (int shift = (hexSize - 1) * 4; shift >= 0; shift -= 4)
                    {
                        int digit = 0xf & (c >> shift);
                        int hc    = (digit < 10) ? '0' + digit : 'A' - 10 + digit;
                        sb.Append((char)hc);
                    }
                }
            }

            return((sb == null) ? s : sb.ToString());
        }