• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1/*
2 * Copyright (c) 2021-2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16package std.core;
17
18export final class Runtime {
19    internal constructor() {}
20
21    /**
22     * Returns a hash code for the Object.
23     *
24     * @param o to calculate hash code from
25     *
26     * @returns hash code
27     */
28    public native getHashCode(o: Object): int;
29
30     /**
31      * Checks if two items are equal.
32      *
33      * @param o1 first object to compare
34      *
35      * @param o2 second object to compare
36      *
37      * @returns true if items are equal
38      */
39    public equals(o1: NullishType, o2: NullishType): boolean {
40        if (this.isSameReference(o1, null)) {
41            return this.isSameReference(o2, null)
42        }
43        if (this.isSameReference(o1, undefined)) {
44            return this.isSameReference(o2, undefined)
45        }
46        if (this.isSameReference(o2, null) || this.isSameReference(o2, undefined)) {
47            return false;
48        }
49
50        return o1 == o2
51    }
52
53    /**
54     * Checks if two items are equal 'by value'
55     *
56     * @param o1 first object to compare
57     *
58     * @param o2 second object to compare
59     *
60     * @returns true if items are equal 'by value'
61     */
62    public sameValue(o1: NullishType, o2: NullishType): boolean {
63        if (this.isSameReference(o1, null)) {
64            return this.isSameReference(o2, null)
65        }
66        if (this.isSameReference(o1, undefined)) {
67            return this.isSameReference(o2, undefined)
68        }
69        if (this.isSameReference(o2, null) || this.isSameReference(o2, undefined)) {
70            return false;
71        }
72
73        if (o1 instanceof Number && o2 instanceof Number) {
74            return this.sameNumberValue(o1 as Number, o2 as Number)
75        } else if (o1 instanceof Float && o2 instanceof Float) {
76            return this.sameFloatValue(o1 as Float, o2 as Float)
77        }
78
79        return o1 == o2
80    }
81
82    private sameNumberValue(n1: Number, n2: Number): boolean {
83        const n1val = n1.valueOf()
84        const n2val = n2.valueOf()
85        if (n1val == 0 || n2val == 0) {
86            return Double.bitCastToLong(n1val) == Double.bitCastToLong(n2val);
87        }
88        if (isNaN(n1val) != isNaN(n2val)) {
89            return false;
90        } else if (isNaN(n1val)) {
91            return true;
92        } else {
93            return n1val == n2val
94        }
95    }
96
97    private sameFloatValue(f1: Float, f2: Float): boolean {
98        const f1val = f1.unboxed()
99        const f2val = f2.unboxed()
100
101        if (f1val == 0 || f2val == 0) {
102            return Float.bitCastToInt(f1val) == Float.bitCastToInt(f2val)
103        }
104
105        if (isNaN(f1val) != isNaN(f2val)) {
106            return false
107        } else if (isNaN(f1val)) {
108            return true
109        } else {
110            return f1val == f2val
111        }
112    }
113
114    public sameValueZero(o1: NullishType, o2: NullishType): boolean {
115        if (this.sameValue(o1, o2)) {
116            return true;
117        }
118        if (o1 instanceof Number && o2 instanceof Number) {
119            const n1 = (o1 as Number).valueOf()
120            const n2 = (o2 as Number).valueOf()
121            return n1 == 0 && n2 == 0;
122        }
123        return false;
124    }
125
126    /**
127     * Checks if two references point to a same object/value.
128     *
129     * @param o1 first object to compare
130     *
131     * @param o2 second object to compare
132     *
133     * @returns true if Objects are equal
134     */
135    public native isSameReference(o1: NullishType, o2: NullishType): boolean;
136
137    /**
138     * Internal entrypoint to create exception for failed type cast
139     *
140     * @param src source value
141     *
142     * @param dstStr target type string
143     *
144     * @returns exception object to throw
145     */
146    internal static failedTypeCastException(src: NullishType, dstStr: string): ClassCastError {
147        let srcStr = src === null ? "null" :
148            (src === undefined ? "undefined" :
149                TypeAPIGetTypeDescriptor(src));
150        return new ClassCastError(srcStr + " cannot be cast to " + dstStr);
151    }
152
153    /**
154     * Return a string with the name of the type kind of the object
155     *
156     * @param o an object
157     *
158     * @returns a string with the name of the type kind of the object
159     */
160    internal native static typeOf(o: Object): String;
161}
162
163export const runtime = new Runtime();
164
165export function __runtimeEquals(o1: NullishType, o2: NullishType): boolean {
166    return runtime.equals(o1, o2)
167}
168
169export function __runtimeSameValueZero(o1: NullishType, o2: NullishType): boolean {
170    return runtime.sameValueZero(o1, o2)
171}
172
173export function __runtimeSameValue(o1: NullishType, o2: NullishType): boolean {
174    return runtime.sameValue(o1, o2)
175}
176
177export function __runtimeIsSameReference(o1: NullishType, o2: NullishType): boolean {
178    return runtime.isSameReference(o1, o2)
179}
180