Bug 1009675 - Part 1: Change the return value of getRetvalDeclarationForType to allow more than two states for the outparam bit. r=peterv, a=sledru
authorBoris Zbarsky <bzbarsky@mit.edu>
Wed, 11 Jun 2014 16:26:51 -0400
changeset 206946 1d4e44c323837f93f2d03664e5de27a9f1a1fd35
parent 206945 04c3fc11907f6a609698d5180ad9bc1f486ab755
child 206947 e993e93566fefbab6196d76a8876c282fe5f971e
push id3741
push userasasaki@mozilla.com
push dateMon, 21 Jul 2014 20:25:18 +0000
treeherdermozilla-beta@4d6f46f5af68 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerspeterv, sledru
bugs1009675
milestone32.0a2
Bug 1009675 - Part 1: Change the return value of getRetvalDeclarationForType to allow more than two states for the outparam bit. r=peterv, a=sledru
dom/bindings/Codegen.py
--- a/dom/bindings/Codegen.py
+++ b/dom/bindings/Codegen.py
@@ -5589,62 +5589,64 @@ def getRetvalDeclarationForType(returnTy
                                 resultAlreadyAddRefed,
                                 isMember=False):
     """
     Returns a tuple containing four things:
 
     1) A CGThing for the type of the return value, or None if there is no need
        for a return value.
 
-    2) A boolean indicating whether the return value is passed as an out
-       parameter.
+    2) A value indicating the kind of ourparam to pass the value as.  Valid
+       options are None to not pass as an out param at all, "ref" (to pass a
+       reference as an out param), and "ptr" (to pass a pointer as an out
+       param).
 
     3) A CGThing for a tracer for the return value, or None if no tracing is
        needed.
 
     4) An argument string to pass to the retval declaration
        constructor or None if there are no arguments.
     """
     if returnType is None or returnType.isVoid():
         # Nothing to declare
-        return None, False, None, None
+        return None, None, None, None
     if returnType.isPrimitive() and returnType.tag() in builtinNames:
         result = CGGeneric(builtinNames[returnType.tag()])
         if returnType.nullable():
             result = CGTemplatedType("Nullable", result)
-        return result, False, None, None
+        return result, None, None, None
     if returnType.isDOMString():
         if isMember:
-            return CGGeneric("nsString"), True, None, None
-        return CGGeneric("DOMString"), True, None, None
+            return CGGeneric("nsString"), "ref", None, None
+        return CGGeneric("DOMString"), "ref", None, None
     if returnType.isByteString():
-        return CGGeneric("nsCString"), True, None, None
+        return CGGeneric("nsCString"), "ref", None, None
     if returnType.isEnum():
         result = CGGeneric(returnType.unroll().inner.identifier.name)
         if returnType.nullable():
             result = CGTemplatedType("Nullable", result)
-        return result, False, None, None
+        return result, None, None, None
     if returnType.isGeckoInterface():
         result = CGGeneric(descriptorProvider.getDescriptor(
             returnType.unroll().inner.identifier.name).nativeType)
         if descriptorProvider.getDescriptor(
                 returnType.unroll().inner.identifier.name).nativeOwnership == 'owned':
             result = CGTemplatedType("nsAutoPtr", result)
         elif resultAlreadyAddRefed:
             result = CGTemplatedType("nsRefPtr", result)
         else:
             result = CGWrapper(result, post="*")
-        return result, False, None, None
+        return result, None, None, None
     if returnType.isCallback():
         name = returnType.unroll().identifier.name
-        return CGGeneric("nsRefPtr<%s>" % name), False, None, None
+        return CGGeneric("nsRefPtr<%s>" % name), None, None, None
     if returnType.isAny():
-        return CGGeneric("JS::Value"), False, None, None
+        return CGGeneric("JS::Value"), None, None, None
     if returnType.isObject() or returnType.isSpiderMonkeyInterface():
-        return CGGeneric("JSObject*"), False, None, None
+        return CGGeneric("JSObject*"), None, None, None
     if returnType.isSequence():
         nullable = returnType.nullable()
         if nullable:
             returnType = returnType.inner
         # If our result is already addrefed, use the right type in the
         # sequence argument here.
         result, _, _, _ = getRetvalDeclarationForType(returnType.inner,
                                                       descriptorProvider,
@@ -5654,17 +5656,17 @@ def getRetvalDeclarationForType(returnTy
         if not isMember and typeNeedsRooting(returnType):
             rooter = CGGeneric("SequenceRooter<%s > resultRooter(cx, &result);\n" %
                                result.define())
         else:
             rooter = None
         result = CGTemplatedType("nsTArray", result)
         if nullable:
             result = CGTemplatedType("Nullable", result)
-        return result, True, rooter, None
+        return result, "ref", rooter, None
     if returnType.isMozMap():
         nullable = returnType.nullable()
         if nullable:
             returnType = returnType.inner
         # If our result is already addrefed, use the right type in the
         # MozMap argument here.
         result, _, _, _ = getRetvalDeclarationForType(returnType.inner,
                                                       descriptorProvider,
@@ -5674,50 +5676,50 @@ def getRetvalDeclarationForType(returnTy
         if not isMember and typeNeedsRooting(returnType):
             rooter = CGGeneric("MozMapRooter<%s> resultRooter(cx, &result);\n" %
                                result.define())
         else:
             rooter = None
         result = CGTemplatedType("MozMap", result)
         if nullable:
             result = CGTemplatedType("Nullable", result)
-        return result, True, rooter, None
+        return result, "ref", rooter, None
     if returnType.isDictionary():
         nullable = returnType.nullable()
         dictName = CGDictionary.makeDictionaryName(returnType.unroll().inner)
         result = CGGeneric(dictName)
         if not isMember and typeNeedsRooting(returnType):
             if nullable:
                 result = CGTemplatedType("NullableRootedDictionary", result)
             else:
                 result = CGTemplatedType("RootedDictionary", result)
             resultArgs = "cx"
         else:
             if nullable:
                 result = CGTemplatedType("Nullable", result)
             resultArgs = None
-        return result, True, None, resultArgs
+        return result, "ref", None, resultArgs
     if returnType.isUnion():
         result = CGGeneric(CGUnionStruct.unionTypeName(returnType.unroll(), True))
         if not isMember and typeNeedsRooting(returnType):
             if returnType.nullable():
                 result = CGTemplatedType("NullableRootedUnion", result)
             else:
                 result = CGTemplatedType("RootedUnion", result)
             resultArgs = "cx"
         else:
             if returnType.nullable():
                 result = CGTemplatedType("Nullable", result)
             resultArgs = None
-        return result, True, None, resultArgs
+        return result, "ref", None, resultArgs
     if returnType.isDate():
         result = CGGeneric("Date")
         if returnType.nullable():
             result = CGTemplatedType("Nullable", result)
-        return result, False, None, None
+        return result, None, None, None
     raise TypeError("Don't know how to declare return value for %s" %
                     returnType)
 
 
 def isResultAlreadyAddRefed(extendedAttributes):
     return 'resultNotAddRefed' not in extendedAttributes
 
 
@@ -5796,18 +5798,23 @@ class CGCallGenerator(CGThing):
                 arg = CGWrapper(arg, pre="Constify(", post=")")
             # And convert NonNull<T> to T&
             if (((a.type.isGeckoInterface() or a.type.isCallback()) and not a.type.nullable()) or
                 a.type.isDOMString()):
                 arg = CGWrapper(arg, pre="NonNullHelper(", post=")")
             args.append(arg)
 
         # Return values that go in outparams go here
-        if resultOutParam:
-            args.append(CGGeneric("result"))
+        if resultOutParam is not None:
+            if resultOutParam is "ref":
+                args.append(CGGeneric("result"))
+            else:
+                assert resultOutParam is "ptr"
+                args.append(CGGeneric("&result"))
+
         if isFallible:
             args.append(CGGeneric("rv"))
         args.extend(CGGeneric(arg) for arg in argsPost)
 
         # Build up our actual call
         self.cgRoot = CGList([])
 
         call = CGGeneric(nativeMethodName)