Implement implicit conversions on function return expressions to the function's type.
authorJohn Kessenich <cepheus@frii.com>
Tue, 6 May 2014 06:02:01 +0000 (06:02 +0000)
committerJohn Kessenich <cepheus@frii.com>
Tue, 6 May 2014 06:02:01 +0000 (06:02 +0000)
git-svn-id: https://cvs.khronos.org/svn/repos/ogl/trunk/ecosystem/public/sdk/tools/glslang@26501 e7fa87d3-cd2b-0410-9028-fcbf551c1848

Test/410.geom
Test/420.geom
Test/baseResults/120.frag.out
Test/baseResults/300scope.vert.out
Test/baseResults/410.geom.out
Test/baseResults/420.geom.out
Test/baseResults/array.frag.out
Todo.txt
glslang/MachineIndependent/Intermediate.cpp
glslang/MachineIndependent/glslang.y

index 116d6fe..8775aeb 100644 (file)
@@ -32,3 +32,8 @@ void foo()
     vec4 v = gl_in[1].gl_Position;    // ERROR, not included in the redeclaration\r
     gl_Position = vec4(1.0);          // ERROR, not included in the redeclaration\r
 }\r
+\r
+float foo5()\r
+{\r
+    return 4;  // implicit conversion of return type\r
+}\r
index e883f0b..43903bc 100644 (file)
@@ -48,3 +48,8 @@ out gl_PerVertex {
     float gl_PointSize[1];  // ERROR, adding array\r
     float gl_ClipDistance;  // ERROR, removing array\r
 };\r
+\r
+float foo5()\r
+{\r
+    return i;  // implicit conversion of return type\r
+}\r
index 2c14ba3..fcd749b 100644 (file)
@@ -27,7 +27,7 @@ ERROR: 0:91: 'int' :  main function cannot return a value
 ERROR: 0:92: 'main' : function cannot take any parameter(s) \r
 ERROR: 0:94: 'a' : variables with qualifier 'const' must be initialized \r
 ERROR: 0:97: 'out' : overloaded functions must have the same parameter storage qualifiers for argument 1\r
-ERROR: 0:99: 'return' : function return is not matching type: \r
+ERROR: 0:99: 'return' : type does not match, or is not convertible to, the function's return type \r
 ERROR: 0:115: 'return' : void function cannot return a value \r
 ERROR: 0:125: 'gl_TexCoord' : redeclaration of array with size \r
 ERROR: 0:152: 'matrixCompMult' : no matching overloaded function found \r
@@ -291,8 +291,7 @@ ERROR: node is still EOpNull!
 0:113  Function Definition: v2( (void)\r
 0:113    Function Parameters: \r
 0:115    Sequence\r
-0:115      Branch: Return with expression\r
-0:115        Function Call: v1( (void)\r
+0:115      Branch: Return\r
 0:118  Function Definition: atest( (void)\r
 0:118    Function Parameters: \r
 0:120    Sequence\r
@@ -650,8 +649,7 @@ ERROR: node is still EOpNull!
 0:113  Function Definition: v2( (void)\r
 0:113    Function Parameters: \r
 0:115    Sequence\r
-0:115      Branch: Return with expression\r
-0:115        Function Call: v1( (void)\r
+0:115      Branch: Return\r
 0:118  Function Definition: atest( (void)\r
 0:118    Function Parameters: \r
 0:120    Sequence\r
index 00c7460..a6e40ba 100644 (file)
@@ -44,16 +44,12 @@ ERROR: node is still EOpNull!
 0:25    Function Parameters: \r
 0:25      'x' (in highp float)\r
 0:27    Sequence\r
-0:27      Branch: Return with expression\r
-0:27        Constant:\r
-0:27          1.000000\r
+0:27      Branch: Return\r
 0:29  Function Definition: radians(b1; (bool)\r
 0:29    Function Parameters: \r
 0:29      'x' (in bool)\r
 0:31    Sequence\r
-0:31      Branch: Return with expression\r
-0:31        Constant:\r
-0:31          true (const bool)\r
+0:31      Branch: Return\r
 0:36  Function Definition: main( (void)\r
 0:36    Function Parameters: \r
 0:?     Sequence\r
@@ -157,16 +153,12 @@ ERROR: node is still EOpNull!
 0:25    Function Parameters: \r
 0:25      'x' (in highp float)\r
 0:27    Sequence\r
-0:27      Branch: Return with expression\r
-0:27        Constant:\r
-0:27          1.000000\r
+0:27      Branch: Return\r
 0:29  Function Definition: radians(b1; (bool)\r
 0:29    Function Parameters: \r
 0:29      'x' (in bool)\r
 0:31    Sequence\r
-0:31      Branch: Return with expression\r
-0:31        Constant:\r
-0:31          true (const bool)\r
+0:31      Branch: Return\r
 0:36  Function Definition: main( (void)\r
 0:36    Function Parameters: \r
 0:?     Sequence\r
index ae3c81e..0e7c7cc 100644 (file)
@@ -7,6 +7,7 @@ ERROR: 0:32: 'gl_Position' :  no such field in structure
 ERROR: 0:32: '=' :  cannot convert from 'block{in float gl_PointSize}' to '4-component vector of float'\r
 ERROR: 0:33: 'gl_Position' : member of nameless block was not redeclared \r
 ERROR: 0:33: 'assign' :  cannot convert from 'const 4-component vector of float' to 'layout(stream=0 ) gl_Position void'\r
+WARNING: 0:38: 'return' : type conversion on return values was not explicitly allowed until version 420 \r
 ERROR: 7 compilation errors.  No code generated.\r
 \r
 \r
@@ -46,6 +47,12 @@ ERROR: node is still EOpNull!
 0:33        'anon@0' (layout(stream=0 ) out block{layout(stream=0 ) gl_PointSize float gl_PointSize, })\r
 0:33        Constant:\r
 0:33          0 (const uint)\r
+0:36  Function Definition: foo5( (float)\r
+0:36    Function Parameters: \r
+0:38    Sequence\r
+0:38      Branch: Return with expression\r
+0:38        Constant:\r
+0:38          4.000000\r
 0:?   Linker Objects\r
 0:?     'gl_in' (in implicitly-sized array of block{in float gl_PointSize})\r
 0:?     'anon@0' (layout(stream=0 ) out block{layout(stream=0 ) gl_PointSize float gl_PointSize, })\r
@@ -93,6 +100,12 @@ ERROR: node is still EOpNull!
 0:33        'anon@0' (layout(stream=0 ) out block{layout(stream=0 ) gl_PointSize float gl_PointSize, })\r
 0:33        Constant:\r
 0:33          0 (const uint)\r
+0:36  Function Definition: foo5( (float)\r
+0:36    Function Parameters: \r
+0:38    Sequence\r
+0:38      Branch: Return with expression\r
+0:38        Constant:\r
+0:38          4.000000\r
 0:?   Linker Objects\r
 0:?     'gl_in' (in 2-element array of block{in float gl_PointSize})\r
 0:?     'anon@0' (layout(stream=0 ) out block{layout(stream=0 ) gl_PointSize float gl_PointSize, })\r
index 6ed558b..1b927b8 100644 (file)
@@ -114,6 +114,12 @@ ERROR: node is still EOpNull!
 0:44            0 (const int)\r
 0:44          Constant:\r
 0:44            1 (const int)\r
+0:52  Function Definition: foo5( (float)\r
+0:52    Function Parameters: \r
+0:54    Sequence\r
+0:54      Branch: Return with expression\r
+0:54        Convert int to float (float)\r
+0:54          'i' (int)\r
 0:?   Linker Objects\r
 0:?     'i' (int)\r
 0:?     'gl_in' (in 3-element array of block{in 4-component vector of float gl_Position, in float gl_PointSize, in implicitly-sized array of float gl_ClipDistance})\r
@@ -235,6 +241,12 @@ ERROR: node is still EOpNull!
 0:44            0 (const int)\r
 0:44          Constant:\r
 0:44            1 (const int)\r
+0:52  Function Definition: foo5( (float)\r
+0:52    Function Parameters: \r
+0:54    Sequence\r
+0:54      Branch: Return with expression\r
+0:54        Convert int to float (float)\r
+0:54          'i' (int)\r
 0:?   Linker Objects\r
 0:?     'i' (int)\r
 0:?     'gl_in' (in 3-element array of block{in 4-component vector of float gl_Position, in float gl_PointSize, in 1-element array of float gl_ClipDistance})\r
index f4c167b..f20b967 100644 (file)
@@ -19,7 +19,7 @@ ERROR: 0:63: '' : array size required
 ERROR: 0:66: '=' :  cannot convert from '3-component vector of float' to 'float'\r
 ERROR: 0:76: 'bar' : no matching overloaded function found \r
 ERROR: 0:79: '' : array size required \r
-ERROR: 0:84: 'return' : function return is not matching type: \r
+ERROR: 0:84: 'return' : type does not match, or is not convertible to, the function's return type \r
 ERROR: 0:93: 'length' :  array must be declared with a size before using this method\r
 ERROR: 0:101: '[' :  array index out of range '5'\r
 ERROR: 23 compilation errors.  No code generated.\r
index 125a8e5..a516949 100644 (file)
--- a/Todo.txt
+++ b/Todo.txt
@@ -115,20 +115,21 @@ Shader Functionality to Implement/Finish
         + layout qualifiers for primitive types
       - Polymorphic functions: Run-time selection of what function gets called, through the new keyword subroutine.
       - 64bit floating point numbers with the new type keyword double.  Built-in functions extended for doubles, and new function matching rules are added to both allow implicit conversions when calling a function and preserve most existing function matching once doubles are included. 
-      + More implicit conversions
+      + More implicit conversions 
          + float to double, and similarly for all floating-point vector and matrix types
          + int to uint, and similarly for all integer vector types
          + int to double, and similarly for all vectors of integers and doubles.
          + uint to double, and similarly for all vectors of integers and doubles.
-      - Cube map array textures and texture functions texture(), textureSize(), textureLod(), and textureGrad().
-      - Sampler arrays can take a variable index now, as long as it's value is uniform for all uses.
+      + Cube map array textures and texture functions texture(), textureSize(), textureLod(), and textureGrad().
+      + Sampler arrays can take a variable index now, as long as it's value is uniform for all uses.
       - Per-sample shading. Including sample input mask gl_SampleMaskIn[] and per-sample interpolation, with explicit interpolation built-ins interpolateAtCentroid(), interpolateAtSample(), and interpolateAtOffset().
       - New precise qualifier to disallow optimizations that re-order operations or treat different instances of the same operator with different precision.
       - Add a fused multiply and add built-in, fma(), in relation to the new precise qualifier. (Because \93a * b + c\94 will require two operations under new rules for precise.)
       - Added new built-in floating-point functions 
          - frexp() and ldexp()
-         - packUnorm2x16(), packUnorm4x8(),packSnorm4x8(), and packDouble2x32()
-         - unpackUnorm2x16(), unpackUnorm4x8(),unpackSnorm4x8(), and unpackDouble2x32()
+         + packUnorm2x16(), unpackUnorm2x16(),
+         - packUnorm4x8(),packSnorm4x8(), and packDouble2x32()
+         - unpackUnorm4x8(),unpackSnorm4x8(), and unpackDouble2x32()
       - Add new built-in integer functions
          - uaddCarry() andusubBorrow()
          - umulExtended() andimulExtended()
@@ -186,8 +187,7 @@ Shader Functionality to Implement/Finish
       - Allow .length() to be applied to vectors and matrices, returning the number of components or columns.
       + Clarify that .length() returns an int type and can be used as a constant integer expression.
       + Allow swizzle operations on scalars.
-      - Positive signed decimal literals, as well as octal and hexadecimal, can set all 32 bits. This includes setting the sign bit to create a negative value.
-      - Make GLSL consistent with the API regarding user clipping, by no longer referring to gl_Position when gl_ClipVertex is not written. Rather, user clipping becomes undefined.
+      + Positive signed decimal literals, as well as octal and hexadecimal, can set all 32 bits. This includes setting the sign bit to create a negative value.
       - Clarified that a comma sequence-operator expression cannot be a constant expression. E.g., \93(2,3)\94 is not allowed, semantically, 
             as a valid constant expression 3, even though it is an expression that will evaluate to 3.
       + Use vec2 instead of vec3 for coordinate in textureGather*(sampler2DRect,...).
index f02e120..8cdde85 100644 (file)
@@ -372,7 +372,7 @@ TIntermTyped* TIntermediate::setAggregateOperator(TIntermNode* node, TOperator o
 // For implicit conversions, 'op' is not the requested conversion, it is the explicit 
 // operation requiring the implicit conversion.
 //
-// Returns the node representing the conversion, which could be the same
+// Returns a node representing the conversion, which could be the same
 // node passed in if no conversion was needed.
 //
 // Return 0 if a conversion can't be done.
@@ -455,6 +455,7 @@ TIntermTyped* TIntermediate::addConversion(TOperator op, const TType& type, TInt
     case EOpMatrixTimesScalar:
 
     case EOpFunctionCall:
+    case EOpReturn:
     case EOpAssign:
     case EOpAddAssign:
     case EOpSubAssign:
index a2157bc..0105070 100644 (file)
@@ -2395,12 +2395,22 @@ jump_statement
             parseContext.error($1.loc, "non-void function must return a value", "return", "");\r
     }\r
     | RETURN expression SEMICOLON {\r
-        $$ = parseContext.intermediate.addBranch(EOpReturn, $2, $1.loc);\r
         parseContext.functionReturnsValue = true;\r
-        if (parseContext.currentFunctionType->getBasicType() == EbtVoid)\r
+        if (parseContext.currentFunctionType->getBasicType() == EbtVoid) {\r
             parseContext.error($1.loc, "void function cannot return a value", "return", "");\r
-        else if (*(parseContext.currentFunctionType) != $2->getType())\r
-            parseContext.error($1.loc, "function return is not matching type:", "return", "");\r
+            $$ = parseContext.intermediate.addBranch(EOpReturn, $1.loc);\r
+        } else if (*(parseContext.currentFunctionType) != $2->getType()) {\r
+            TIntermTyped* converted = parseContext.intermediate.addConversion(EOpReturn, *parseContext.currentFunctionType, $2);\r
+            if (converted) {\r
+                if (parseContext.version < 420)\r
+                    parseContext.warn($1.loc, "type conversion on return values was not explicitly allowed until version 420", "return", "");\r
+                $$ = parseContext.intermediate.addBranch(EOpReturn, converted, $1.loc);\r
+            } else {\r
+                parseContext.error($1.loc, "type does not match, or is not convertible to, the function's return type", "return", "");\r
+                $$ = parseContext.intermediate.addBranch(EOpReturn, $2, $1.loc);\r
+            }\r
+        } else\r
+                   $$ = parseContext.intermediate.addBranch(EOpReturn, $2, $1.loc);\r
     }\r
     | DISCARD SEMICOLON {\r
         parseContext.requireStage($1.loc, EShLangFragment, "discard");\r