As complement to #1262 and #1718, this PR solves part of both issues.
One does the migration from `ascii` to `code_point` since Unicode is a bit more than ASCII, let's try to use the right vocabulary when dealing with it.
The `ascii` service is however kept alive, but its contract is changed from Int to Byte to be used directly on a `Char` without the need to have the old `'c'.ascii.to_b`, now a simple `'c'.ascii` will do the exact same.
A further PR will be submitted later to prevent the use of `ascii` on non-ASCII literal characters.
Pull-Request: #1726
Reviewed-by: Alexis Laferrière <alexis.laf@xymus.net>
Reviewed-by: Jean Privat <jean@pryen.org>
# use some Huffman coding.
if t.name == "Int" then
class_info[1] = t
+ t.mclass_type.tag_value = 1
else if t.name == "Char" then
class_info[2] = t
+ t.mclass_type.tag_value = 2
else if t.name == "Bool" then
class_info[3] = t
+ t.mclass_type.tag_value = 3
else
continue
end
else
var mtype1 = value1.mtype.as(MClassType)
self.require_declaration("class_{mtype1.c_name}")
- self.add("{res} = ({value2} != NULL) && ({value2}->class == &class_{mtype1.c_name}); /* is_same_type_test */")
+ self.add("{res} = ({value2} != NULL) && ({class_info(value2)} == &class_{mtype1.c_name}); /* is_same_type_test */")
end
else
self.add("{res} = ({value1} == {value2}) || ({value1} != NULL && {value2} != NULL && {class_info(value1)} == {class_info(value2)}); /* is_same_type_test */")
value2 = tmp
end
if value1.mtype.is_c_primitive then
- if value2.mtype == value1.mtype then
+ var t1 = value1.mtype
+ assert t1 == value1.mcasttype
+
+ # Fast case: same C type.
+ if value2.mtype == t1 then
+ # Same exact C primitive representation.
self.add("{res} = {value1} == {value2};")
- else if value2.mtype.is_c_primitive then
- self.add("{res} = 0; /* incompatible types {value1.mtype} vs. {value2.mtype}*/")
- else if value1.mtype.is_tagged then
- self.add("{res} = ({value2} != NULL) && ({self.autobox(value2, value1.mtype)} == {value1});")
+ return res
+ end
+
+ # Complex case: value2 has a different representation
+ # Thus, it should be checked if `value2` is type-compatible with `value1`
+ # This compatibility is done statically if possible and dynamically else
+
+ # Conjunction (ands) of dynamic tests according to the static knowledge
+ var tests = new Array[String]
+
+ var t2 = value2.mcasttype
+ if t2 isa MNullableType then
+ # The destination type cannot be null
+ tests.add("({value2} != NULL)")
+ t2 = t2.mtype
+ else if t2 isa MNullType then
+ # `value2` is known to be null, thus incompatible with a primitive
+ self.add("{res} = 0; /* incompatible types {t1} vs. {t2}*/")
+ return res
+ end
+
+ if t2 == t1 then
+ # Same type but different representation.
+ else if t2.is_c_primitive then
+ # Type of `value2` is a different primitive type, thus incompatible
+ self.add("{res} = 0; /* incompatible types {t1} vs. {t2}*/")
+ return res
+ else if t1.is_tagged then
+ # To be equal, `value2` should also be correctly tagged
+ tests.add("({extract_tag(value2)} == {t1.tag_value})")
else
- var mtype1 = value1.mtype.as(MClassType)
- self.require_declaration("class_{mtype1.c_name}")
- self.add("{res} = ({value2} != NULL) && ({value2}->class == &class_{mtype1.c_name});")
- self.add("if ({res}) \{")
- self.add("{res} = ({self.autobox(value2, value1.mtype)} == {value1});")
- self.add("\}")
+ # To be equal, `value2` should also be boxed with the same class
+ self.require_declaration("class_{t1.c_name}")
+ tests.add "({class_info(value2)} == &class_{t1.c_name})"
end
+
+ # Compare the unboxed `value2` with `value1`
+ if tests.not_empty then
+ self.add "if ({tests.join(" && ")}) \{"
+ end
+ self.add "{res} = {self.autobox(value2, t1)} == {value1};"
+ if tests.not_empty then
+ self.add "\} else {res} = 0;"
+ end
+
return res
end
var maybe_null = true
# Are values of `self` tagged?
# If false, it means that the type is not primitive, or is boxed.
var is_tagged = false
+
+ # The tag value of the type
+ #
+ # ENSURE `is_tagged == (tag_value > 0)`
+ # ENSURE `not is_tagged == (tag_value == 0)`
+ var tag_value = 0
end
redef class MEntity
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import kernel
+
+var i = 1
+var b = true
+var f = 1u8
+var ni: nullable Int = 1
+var nb: nullable Bool = true
+var nf: nullable Byte = 1u8
+var oi: nullable Object = 1
+var ob: nullable Object = true
+var of: nullable Object = 1u8
+
+
+(i == i).output
+(b == i).output
+(f == i).output
+
+'\n'.output
+
+(i == ni).output
+(b == ni).output
+(f == ni).output
+
+'\n'.output
+
+(i == oi).output
+(b == oi).output
+(f == oi).output
+
+'\n'.output
+'\n'.output
+
+(ni == i).output
+(nb == i).output
+(nf == i).output
+
+'\n'.output
+
+(ni == ni).output
+(nb == ni).output
+(nf == ni).output
+
+'\n'.output
+
+(ni == oi).output
+(nb == oi).output
+(nf == oi).output
+
+'\n'.output
+'\n'.output
+
+(oi == i).output
+(ob == i).output
+(of == i).output
+
+'\n'.output
+
+(oi == ni).output
+(ob == ni).output
+(of == ni).output
+
+'\n'.output
+
+(oi == oi).output
+(ob == oi).output
+(of == oi).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i == b).output
+(b == b).output
+(f == b).output
+
+'\n'.output
+
+(i == nb).output
+(b == nb).output
+(f == nb).output
+
+'\n'.output
+
+(i == ob).output
+(b == ob).output
+(f == ob).output
+
+'\n'.output
+'\n'.output
+
+(ni == b).output
+(nb == b).output
+(nf == b).output
+
+'\n'.output
+
+(ni == nb).output
+(nb == nb).output
+(nf == nb).output
+
+'\n'.output
+
+(ni == ob).output
+(nb == ob).output
+(nf == ob).output
+
+'\n'.output
+'\n'.output
+
+(oi == b).output
+(ob == b).output
+(of == b).output
+
+'\n'.output
+
+(oi == nb).output
+(ob == nb).output
+(of == nb).output
+
+'\n'.output
+
+(oi == ob).output
+(ob == ob).output
+(of == ob).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i == f).output
+(b == f).output
+(f == f).output
+
+'\n'.output
+
+(i == nf).output
+(b == nf).output
+(f == nf).output
+
+'\n'.output
+
+(i == of).output
+(b == of).output
+(f == of).output
+
+'\n'.output
+'\n'.output
+
+(ni == f).output
+(nb == f).output
+(nf == f).output
+
+'\n'.output
+
+(ni == nf).output
+(nb == nf).output
+(nf == nf).output
+
+'\n'.output
+
+(ni == of).output
+(nb == of).output
+(nf == of).output
+
+'\n'.output
+'\n'.output
+
+(oi == f).output
+(ob == f).output
+(of == f).output
+
+'\n'.output
+
+(oi == nf).output
+(ob == nf).output
+(of == nf).output
+
+'\n'.output
+
+(oi == of).output
+(ob == of).output
+(of == of).output
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import kernel
+
+var i = 1
+var b = true
+var f = 1u8
+var ni: nullable Int = 1
+var nb: nullable Bool = true
+var nf: nullable Byte = 1u8
+var oi: nullable Object = 1
+var ob: nullable Object = true
+var of: nullable Object = 1u8
+
+
+(i.is_same_instance(i)).output
+(b.is_same_instance(i)).output
+(f.is_same_instance(i)).output
+
+'\n'.output
+
+(i.is_same_instance(ni)).output
+(b.is_same_instance(ni)).output
+(f.is_same_instance(ni)).output
+
+'\n'.output
+
+(i.is_same_instance(oi)).output
+(b.is_same_instance(oi)).output
+(f.is_same_instance(oi)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_instance(i)).output
+(nb.is_same_instance(i)).output
+(nf.is_same_instance(i)).output
+
+'\n'.output
+
+(ni.is_same_instance(ni)).output
+(nb.is_same_instance(ni)).output
+(nf.is_same_instance(ni)).output
+
+'\n'.output
+
+(ni.is_same_instance(oi)).output
+(nb.is_same_instance(oi)).output
+(nf.is_same_instance(oi)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_instance(i)).output
+(ob.is_same_instance(i)).output
+(of.is_same_instance(i)).output
+
+'\n'.output
+
+(oi.is_same_instance(ni)).output
+(ob.is_same_instance(ni)).output
+(of.is_same_instance(ni)).output
+
+'\n'.output
+
+(oi.is_same_instance(oi)).output
+(ob.is_same_instance(oi)).output
+(of.is_same_instance(oi)).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i.is_same_instance(b)).output
+(b.is_same_instance(b)).output
+(f.is_same_instance(b)).output
+
+'\n'.output
+
+(i.is_same_instance(nb)).output
+(b.is_same_instance(nb)).output
+(f.is_same_instance(nb)).output
+
+'\n'.output
+
+(i.is_same_instance(ob)).output
+(b.is_same_instance(ob)).output
+(f.is_same_instance(ob)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_instance(b)).output
+(nb.is_same_instance(b)).output
+(nf.is_same_instance(b)).output
+
+'\n'.output
+
+(ni.is_same_instance(nb)).output
+(nb.is_same_instance(nb)).output
+(nf.is_same_instance(nb)).output
+
+'\n'.output
+
+(ni.is_same_instance(ob)).output
+(nb.is_same_instance(ob)).output
+(nf.is_same_instance(ob)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_instance(b)).output
+(ob.is_same_instance(b)).output
+(of.is_same_instance(b)).output
+
+'\n'.output
+
+(oi.is_same_instance(nb)).output
+(ob.is_same_instance(nb)).output
+(of.is_same_instance(nb)).output
+
+'\n'.output
+
+(oi.is_same_instance(ob)).output
+(ob.is_same_instance(ob)).output
+(of.is_same_instance(ob)).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i.is_same_instance(f)).output
+(b.is_same_instance(f)).output
+(f.is_same_instance(f)).output
+
+'\n'.output
+
+(i.is_same_instance(nf)).output
+(b.is_same_instance(nf)).output
+(f.is_same_instance(nf)).output
+
+'\n'.output
+
+(i.is_same_instance(of)).output
+(b.is_same_instance(of)).output
+(f.is_same_instance(of)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_instance(f)).output
+(nb.is_same_instance(f)).output
+(nf.is_same_instance(f)).output
+
+'\n'.output
+
+(ni.is_same_instance(nf)).output
+(nb.is_same_instance(nf)).output
+(nf.is_same_instance(nf)).output
+
+'\n'.output
+
+(ni.is_same_instance(of)).output
+(nb.is_same_instance(of)).output
+(nf.is_same_instance(of)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_instance(f)).output
+(ob.is_same_instance(f)).output
+(of.is_same_instance(f)).output
+
+'\n'.output
+
+(oi.is_same_instance(nf)).output
+(ob.is_same_instance(nf)).output
+(of.is_same_instance(nf)).output
+
+'\n'.output
+
+(oi.is_same_instance(of)).output
+(ob.is_same_instance(of)).output
+(of.is_same_instance(of)).output
--- /dev/null
+# This file is part of NIT ( http://www.nitlanguage.org ).
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import kernel
+
+var i = 1
+var b = true
+var f = 1u8
+var ni: Int = 0
+var nb: Bool = false
+var nf: Byte = 0u8
+var oi: Object = 1
+var ob: Object = true
+var of: Object = 1u8
+
+
+(i.is_same_type(i)).output
+(b.is_same_type(i)).output
+(f.is_same_type(i)).output
+
+'\n'.output
+
+(i.is_same_type(ni)).output
+(b.is_same_type(ni)).output
+(f.is_same_type(ni)).output
+
+'\n'.output
+
+(i.is_same_type(oi)).output
+(b.is_same_type(oi)).output
+(f.is_same_type(oi)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_type(i)).output
+(nb.is_same_type(i)).output
+(nf.is_same_type(i)).output
+
+'\n'.output
+
+(ni.is_same_type(ni)).output
+(nb.is_same_type(ni)).output
+(nf.is_same_type(ni)).output
+
+'\n'.output
+
+(ni.is_same_type(oi)).output
+(nb.is_same_type(oi)).output
+(nf.is_same_type(oi)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_type(i)).output
+(ob.is_same_type(i)).output
+(of.is_same_type(i)).output
+
+'\n'.output
+
+(oi.is_same_type(ni)).output
+(ob.is_same_type(ni)).output
+(of.is_same_type(ni)).output
+
+'\n'.output
+
+(oi.is_same_type(oi)).output
+(ob.is_same_type(oi)).output
+(of.is_same_type(oi)).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i.is_same_type(b)).output
+(b.is_same_type(b)).output
+(f.is_same_type(b)).output
+
+'\n'.output
+
+(i.is_same_type(nb)).output
+(b.is_same_type(nb)).output
+(f.is_same_type(nb)).output
+
+'\n'.output
+
+(i.is_same_type(ob)).output
+(b.is_same_type(ob)).output
+(f.is_same_type(ob)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_type(b)).output
+(nb.is_same_type(b)).output
+(nf.is_same_type(b)).output
+
+'\n'.output
+
+(ni.is_same_type(nb)).output
+(nb.is_same_type(nb)).output
+(nf.is_same_type(nb)).output
+
+'\n'.output
+
+(ni.is_same_type(ob)).output
+(nb.is_same_type(ob)).output
+(nf.is_same_type(ob)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_type(b)).output
+(ob.is_same_type(b)).output
+(of.is_same_type(b)).output
+
+'\n'.output
+
+(oi.is_same_type(nb)).output
+(ob.is_same_type(nb)).output
+(of.is_same_type(nb)).output
+
+'\n'.output
+
+(oi.is_same_type(ob)).output
+(ob.is_same_type(ob)).output
+(of.is_same_type(ob)).output
+
+'\n'.output
+'\n'.output
+'\n'.output
+
+(i.is_same_type(f)).output
+(b.is_same_type(f)).output
+(f.is_same_type(f)).output
+
+'\n'.output
+
+(i.is_same_type(nf)).output
+(b.is_same_type(nf)).output
+(f.is_same_type(nf)).output
+
+'\n'.output
+
+(i.is_same_type(of)).output
+(b.is_same_type(of)).output
+(f.is_same_type(of)).output
+
+'\n'.output
+'\n'.output
+
+(ni.is_same_type(f)).output
+(nb.is_same_type(f)).output
+(nf.is_same_type(f)).output
+
+'\n'.output
+
+(ni.is_same_type(nf)).output
+(nb.is_same_type(nf)).output
+(nf.is_same_type(nf)).output
+
+'\n'.output
+
+(ni.is_same_type(of)).output
+(nb.is_same_type(of)).output
+(nf.is_same_type(of)).output
+
+'\n'.output
+'\n'.output
+
+(oi.is_same_type(f)).output
+(ob.is_same_type(f)).output
+(of.is_same_type(f)).output
+
+'\n'.output
+
+(oi.is_same_type(nf)).output
+(ob.is_same_type(nf)).output
+(of.is_same_type(nf)).output
+
+'\n'.output
+
+(oi.is_same_type(of)).output
+(ob.is_same_type(of)).output
+(of.is_same_type(of)).output
--- /dev/null
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
--- /dev/null
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
--- /dev/null
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+true
+false
+false
+
+true
+false
+false
+
+true
+false
+false
+
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+false
+true
+false
+
+false
+true
+false
+
+false
+true
+false
+
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true
+
+
+false
+false
+true
+
+false
+false
+true
+
+false
+false
+true