Bug 819845. Update WebIDL bindings to spec change: sequences/arrays are no longer distinguishable from dictionaries, and conversion to a sequence works on arbitrary objects. r=khuey

This commit is contained in:
Boris Zbarsky 2013-01-02 22:03:25 -05:00
Родитель b323555284
Коммит eabd327329
4 изменённых файлов: 113 добавлений и 15 удалений

Просмотреть файл

@ -210,9 +210,8 @@ IsArrayLike(JSContext* cx, JSObject* obj)
ac.construct(cx, obj);
}
// XXXbz need to detect platform objects (including listbinding
// ones) with indexGetters here!
return JS_IsArrayObject(cx, obj) || JS_IsTypedArrayObject(obj);
// Everything except dates and regexps is arraylike
return !JS_ObjectIsDate(cx, obj) && !JS_ObjectIsRegExp(cx, obj);
}
inline bool

Просмотреть файл

@ -2313,9 +2313,6 @@ for (uint32_t i = 0; i < length; ++i) {
memberType = arrayObjectMemberTypes[0]
name = memberType.name
arrayObject = CGGeneric("done = (failed = !%s.TrySetTo%s(cx, ${obj}, ${val}, ${valPtr}, tryNext)) || !tryNext;" % (unionArgumentObj, name))
# XXX Now we're supposed to check for an array or a platform object
# that supports indexed properties... skip that last for now. It's a
# bit of a pain.
arrayObject = CGWrapper(CGIndenter(arrayObject),
pre="if (IsArrayLike(cx, &argObj)) {\n",
post="}")

Просмотреть файл

@ -1287,8 +1287,7 @@ class IDLSequenceType(IDLType):
# Just forward to the union; it'll deal
return other.isDistinguishableFrom(self)
return (other.isPrimitive() or other.isString() or other.isEnum() or
other.isDictionary() or other.isDate() or
other.isNonCallbackInterface())
other.isDate() or other.isNonCallbackInterface())
class IDLUnionType(IDLType):
def __init__(self, location, memberTypes):
@ -1452,8 +1451,7 @@ class IDLArrayType(IDLType):
# Just forward to the union; it'll deal
return other.isDistinguishableFrom(self)
return (other.isPrimitive() or other.isString() or other.isEnum() or
other.isDictionary() or other.isDate() or
other.isNonCallbackInterface())
other.isDate() or other.isNonCallbackInterface())
class IDLTypedefType(IDLType, IDLObjectWithIdentifier):
def __init__(self, location, innerType, name):
@ -1618,16 +1616,14 @@ class IDLWrapperType(IDLType):
other.isCallback() or other.isDictionary() or
other.isSequence() or other.isArray() or
other.isDate())
if self.isDictionary() and other.nullable():
return False
if other.isPrimitive() or other.isString() or other.isEnum() or other.isDate():
return True
if self.isDictionary():
return (not other.nullable() and
(other.isNonCallbackInterface() or other.isSequence() or
other.isArray()))
return other.isNonCallbackInterface()
assert self.isInterface()
# XXXbz need to check that the interfaces can't be implemented
# by the same object
if other.isInterface():
if other.isSpiderMonkeyInterface():
# Just let |other| handle things

Просмотреть файл

@ -148,3 +148,109 @@ def WebIDLTest(parser, harness):
threw = True
harness.ok(threw, "Should throw when there is no distinguishing index")
# Now let's test our whole distinguishability table
argTypes = [ "long", "short", "long?", "short?", "DOMString", "Enum",
"Enum2", "Interface", "Interface?",
"AncestorInterface", "UnrelatedInterface",
"ImplementedInterface", "CallbackInterface",
"CallbackInterface?", "CallbackInterface2",
"object", "Callback", "Callback2", "optional Dict",
"optional Dict2", "sequence<long>", "sequence<short>",
"long[]", "short[]" ]
# When we can parse Date and RegExp, we need to add them here.
# Try to categorize things a bit to keep list lengths down
def allBut(list1, list2):
return [a for a in list1 if a not in list2]
primitives = [ "long", "short", "long?", "short?", "DOMString",
"Enum", "Enum2" ]
nonPrimitives = allBut(argTypes, primitives)
interfaces = [ "Interface", "Interface?", "AncestorInterface",
"UnrelatedInterface", "ImplementedInterface" ]
nullables = ["long?", "short?", "Interface?", "CallbackInterface?",
"optional Dict", "optional Dict2"]
nonUserObjects = primitives + interfaces
otherObjects = allBut(argTypes, nonUserObjects + ["object"])
notRelatedInterfaces = primitives + ["UnrelatedInterface"] + otherObjects
# Build a representation of the distinguishability table as a dict
# of dicts, holding True values where needed, holes elsewhere.
data = dict();
for type in argTypes:
data[type] = dict()
def setDistinguishable(type, types):
for other in types:
data[type][other] = True
setDistinguishable("long", nonPrimitives)
setDistinguishable("short", nonPrimitives)
setDistinguishable("long?", allBut(nonPrimitives, nullables))
setDistinguishable("short?", allBut(nonPrimitives, nullables))
setDistinguishable("DOMString", nonPrimitives)
setDistinguishable("Enum", nonPrimitives)
setDistinguishable("Enum2", nonPrimitives)
setDistinguishable("Interface", notRelatedInterfaces)
setDistinguishable("Interface?", allBut(notRelatedInterfaces, nullables))
setDistinguishable("AncestorInterface", notRelatedInterfaces)
setDistinguishable("UnrelatedInterface",
allBut(argTypes, ["object", "UnrelatedInterface"]))
setDistinguishable("ImplementedInterface", notRelatedInterfaces)
setDistinguishable("CallbackInterface", nonUserObjects)
setDistinguishable("CallbackInterface?", allBut(nonUserObjects, nullables))
setDistinguishable("CallbackInterface2", nonUserObjects)
setDistinguishable("object", primitives)
setDistinguishable("Callback", nonUserObjects)
setDistinguishable("Callback2", nonUserObjects)
setDistinguishable("optional Dict", allBut(nonUserObjects, nullables))
setDistinguishable("optional Dict2", allBut(nonUserObjects, nullables))
setDistinguishable("sequence<long>", nonUserObjects)
setDistinguishable("sequence<short>", nonUserObjects)
setDistinguishable("long[]", nonUserObjects)
setDistinguishable("short[]", nonUserObjects)
def areDistinguishable(type1, type2):
return data[type1].get(type2, False)
def checkDistinguishability(parser, type1, type2):
idlTemplate = """
enum Enum { "a", "b" };
enum Enum2 { "c", "d" };
interface Interface : AncestorInterface {};
interface AncestorInterface {};
interface UnrelatedInterface {};
interface ImplementedInterface {};
Interface implements ImplementedInterface;
callback interface CallbackInterface {};
callback interface CallbackInterface2 {};
callback Callback = any();
callback Callback2 = long(short arg);
dictionary Dict {};
dictionary Dict2 {};
interface TestInterface {%s
};
"""
methodTemplate = """
void myMethod(%s arg);"""
methods = (methodTemplate % type1) + (methodTemplate % type2)
idl = idlTemplate % methods
parser = parser.reset()
threw = False
try:
parser.parse(idl)
results = parser.finish()
except:
threw = True
if areDistinguishable(type1, type2):
harness.ok(not threw,
"Should not throw for '%s' and '%s' because they are distinguishable" % (type1, type2))
else:
harness.ok(threw,
"Should throw for '%s' and '%s' because they are not distinguishable" % (type1, type2))
# Enumerate over everything in both orders, since order matters in
# terms of our implementation of distinguishability checks
for type1 in argTypes:
for type2 in argTypes:
checkDistinguishability(parser, type1, type2)