Fix for bug 765467 (Fix special operations in the WebIDL parser). r=khuey.

--HG--
extra : rebase_source : 4186629224c5e822473de1931604970106c721a6
This commit is contained in:
Peter Van der Beken 2012-05-22 12:02:21 +02:00
parent e00ca063fb
commit 1e00518240
2 changed files with 21 additions and 100 deletions

View File

@ -1892,7 +1892,7 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
assert self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.domstring] or \ assert self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.domstring] or \
self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.unsigned_long] self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.unsigned_long]
assert not self._arguments[0][0].optional and not self._arguments[0][0].variadic assert not self._arguments[0][0].optional and not self._arguments[0][0].variadic
assert not self._returnType[0].isVoid() assert not self._getter or not self._returnType[0].isVoid()
if self._setter or self._creator: if self._setter or self._creator:
assert len(self._arguments[0]) == 2 assert len(self._arguments[0]) == 2
@ -1900,7 +1900,6 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.unsigned_long] self._arguments[0][0].type == BuiltinTypes[IDLBuiltinType.Types.unsigned_long]
assert not self._arguments[0][0].optional and not self._arguments[0][0].variadic assert not self._arguments[0][0].optional and not self._arguments[0][0].variadic
assert not self._arguments[0][1].optional and not self._arguments[0][1].variadic assert not self._arguments[0][1].optional and not self._arguments[0][1].variadic
assert self._arguments[0][1].type == self._returnType[0]
if self._stringifier: if self._stringifier:
assert len(self._arguments[0]) == 0 assert len(self._arguments[0]) == 0
@ -2573,13 +2572,6 @@ class Parser(Tokenizer):
""" """
p[0] = False p[0] = False
def p_AttributeOrOperationStringifier(self, p):
"""
AttributeOrOperation : STRINGIFIER StringifierAttributeOrOperation
"""
assert False # Not implemented
pass
def p_AttributeOrOperation(self, p): def p_AttributeOrOperation(self, p):
""" """
AttributeOrOperation : Attribute AttributeOrOperation : Attribute
@ -2587,14 +2579,6 @@ class Parser(Tokenizer):
""" """
p[0] = p[1] p[0] = p[1]
def p_StringifierAttributeOrOperation(self, p):
"""
StringifierAttributeOrOperation : Attribute
| OperationRest
| SEMICOLON
"""
pass
def p_Attribute(self, p): def p_Attribute(self, p):
""" """
Attribute : Inherit ReadOnly ATTRIBUTE AttributeType IDENTIFIER SEMICOLON Attribute : Inherit ReadOnly ATTRIBUTE AttributeType IDENTIFIER SEMICOLON
@ -2651,6 +2635,7 @@ class Parser(Tokenizer):
creator = True if IDLMethod.Special.Creator in p[1] else False creator = True if IDLMethod.Special.Creator in p[1] else False
deleter = True if IDLMethod.Special.Deleter in p[1] else False deleter = True if IDLMethod.Special.Deleter in p[1] else False
legacycaller = True if IDLMethod.Special.LegacyCaller in p[1] else False legacycaller = True if IDLMethod.Special.LegacyCaller in p[1] else False
stringifier = True if IDLMethod.Special.Stringifier in p[1] else False
if getter or deleter: if getter or deleter:
if setter or creator: if setter or creator:
@ -2682,9 +2667,9 @@ class Parser(Tokenizer):
("getter" if getter else "deleter", ("getter" if getter else "deleter",
"optional" if arguments[0].optional else "variadic"), "optional" if arguments[0].optional else "variadic"),
arguments[0].location) arguments[0].location)
if getter:
if returnType.isVoid(): if returnType.isVoid():
raise WebIDLError("%s cannot have void return type" % raise WebIDLError("getter cannot have void return type",
("getter" if getter else "deleter"),
self.getLocation(p, 2)) self.getLocation(p, 2))
if setter or creator: if setter or creator:
if len(arguments) != 2: if len(arguments) != 2:
@ -2710,13 +2695,13 @@ class Parser(Tokenizer):
("setter" if setter else "creator", ("setter" if setter else "creator",
"optional" if arguments[1].optional else "variadic"), "optional" if arguments[1].optional else "variadic"),
arguments[1].location) arguments[1].location)
if returnType.isVoid():
raise WebIDLError("%s cannot have void return type" % if stringifier:
("setter" if setter else "creator"), if len(arguments) != 0:
raise WebIDLError("stringifier has wrong number of arguments",
self.getLocation(p, 2)) self.getLocation(p, 2))
if not arguments[1].type == returnType: if not returnType.isString():
raise WebIDLError("%s return type and second argument type must match" % raise WebIDLError("stringifier must have string return type",
("setter" if setter else "creator"),
self.getLocation(p, 2)) self.getLocation(p, 2))
inOptionalArguments = False inOptionalArguments = False
@ -2735,27 +2720,27 @@ class Parser(Tokenizer):
variadicArgument = argument if argument.variadic else None variadicArgument = argument if argument.variadic else None
# identifier might be None. This is only permitted for special methods. # identifier might be None. This is only permitted for special methods.
# NB: Stringifiers are handled elsewhere.
if not identifier: if not identifier:
if not getter and not setter and not creator and \ if not getter and not setter and not creator and \
not deleter and not legacycaller: not deleter and not legacycaller and not stringifier:
raise WebIDLError("Identifier required for non-special methods", raise WebIDLError("Identifier required for non-special methods",
self.getLocation(p, 2)) self.getLocation(p, 2))
location = BuiltinLocation("<auto-generated-identifier>") location = BuiltinLocation("<auto-generated-identifier>")
identifier = IDLUnresolvedIdentifier(location, "__%s%s%s%s%s%s" % identifier = IDLUnresolvedIdentifier(location, "__%s%s%s%s%s%s%s" %
("named" if specialType == IDLMethod.NamedOrIndexed.Named else \ ("named" if specialType == IDLMethod.NamedOrIndexed.Named else \
"indexed" if specialType == IDLMethod.NamedOrIndexed.Indexed else "", "indexed" if specialType == IDLMethod.NamedOrIndexed.Indexed else "",
"getter" if getter else "", "getter" if getter else "",
"setter" if setter else "", "setter" if setter else "",
"deleter" if deleter else "", "deleter" if deleter else "",
"creator" if creator else "", "creator" if creator else "",
"legacycaller" if legacycaller else ""), allowDoubleUnderscore=True) "legacycaller" if legacycaller else "",
"stringifier" if stringifier else ""), allowDoubleUnderscore=True)
method = IDLMethod(self.getLocation(p, 2), identifier, returnType, arguments, method = IDLMethod(self.getLocation(p, 2), identifier, returnType, arguments,
static=static, getter=getter, setter=setter, creator=creator, static=static, getter=getter, setter=setter, creator=creator,
deleter=deleter, specialType=specialType, deleter=deleter, specialType=specialType,
legacycaller=legacycaller, stringifier=False) legacycaller=legacycaller, stringifier=stringifier)
p[0] = method p[0] = method
def p_QualifiersStatic(self, p): def p_QualifiersStatic(self, p):
@ -2813,6 +2798,12 @@ class Parser(Tokenizer):
""" """
p[0] = IDLMethod.Special.LegacyCaller p[0] = IDLMethod.Special.LegacyCaller
def p_SpecialStringifier(self, p):
"""
Special : STRINGIFIER
"""
p[0] = IDLMethod.Special.Stringifier
def p_OperationRest(self, p): def p_OperationRest(self, p):
""" """
OperationRest : ReturnType OptionalIdentifier LPAREN ArgumentList RPAREN SEMICOLON OperationRest : ReturnType OptionalIdentifier LPAREN ArgumentList RPAREN SEMICOLON

View File

@ -97,20 +97,6 @@ def WebIDLTest(parser, harness):
harness.ok(threw, "Should have thrown.") harness.ok(threw, "Should have thrown.")
threw = False
try:
parser.parse("""
interface SpecialMethodSignatureMismatch8 {
deleter void foo(unsigned long index);
};
""")
results = parser.finish()
except:
threw = True
harness.ok(threw, "Should have thrown.")
threw = False threw = False
try: try:
parser.parse(""" parser.parse("""
@ -181,20 +167,6 @@ def WebIDLTest(parser, harness):
harness.ok(threw, "Should have thrown.") harness.ok(threw, "Should have thrown.")
threw = False
try:
parser.parse("""
interface SpecialMethodSignatureMismatch14 {
setter void foo(unsigned long index, long long value);
};
""")
results = parser.finish()
except:
threw = True
harness.ok(threw, "Should have thrown.")
threw = False threw = False
try: try:
parser.parse(""" parser.parse("""
@ -251,20 +223,6 @@ def WebIDLTest(parser, harness):
harness.ok(threw, "Should have thrown.") harness.ok(threw, "Should have thrown.")
threw = False
try:
parser.parse("""
interface SpecialMethodSignatureMismatch19 {
setter boolean foo(unsigned long index, long long value);
};
""")
results = parser.finish()
except:
threw = True
harness.ok(threw, "Should have thrown.")
threw = False threw = False
try: try:
parser.parse(""" parser.parse("""
@ -279,20 +237,6 @@ def WebIDLTest(parser, harness):
harness.ok(threw, "Should have thrown.") harness.ok(threw, "Should have thrown.")
threw = False
try:
parser.parse("""
interface SpecialMethodSignatureMismatch21 {
creator void foo(unsigned long index, long long value);
};
""")
results = parser.finish()
except:
threw = True
harness.ok(threw, "Should have thrown.")
threw = False threw = False
try: try:
parser.parse(""" parser.parse("""
@ -348,17 +292,3 @@ def WebIDLTest(parser, harness):
threw = True threw = True
harness.ok(threw, "Should have thrown.") harness.ok(threw, "Should have thrown.")
threw = False
try:
parser.parse("""
interface SpecialMethodSignatureMismatch26 {
creator boolean foo(unsigned long index, long long value);
};
""")
results = parser.finish()
except:
threw = True
harness.ok(threw, "Should have thrown.")