[cfe-dev] Patch for References

Bill Wendling isanbard at gmail.com
Thu Jul 12 23:51:42 PDT 2007


On Jul 12, 2007, at 10:29 PM, Chris Lattner wrote:

> +  if (isa<ReferenceType>(TR.getCanonicalType())) // C++ 3.10p5  
> references
> +    return LV_Valid;
>
> This citation doesn't make sense, it's talking about function  
> results, not references in general.
>
True. I'll come up with a better citation. (The reason that one was  
there is because I found this error while trying to compile a call to  
a function that returns a reference.)

> +  } else if (isa<ReferenceType>(canonT1)) {
> +    // C++ 8.5.3p1: A reference to an array.
> +    baseType = canonT1;
> +    indexType = canonT2;
> +    baseExpr = static_cast<Expr *>(Base);
> +    indexExpr = static_cast<Expr *>(Idx);
> +  } else if (isa<ReferenceType>(canonT2)) { // uncommon
> +    // C++ 8.5.3p1: A reference to an array.
> +    baseType = canonT2;
> +    indexType = canonT1;
> +    baseExpr = static_cast<Expr *>(Idx);
> +    indexExpr = static_cast<Expr *>(Base);
>
> This doesn't make sense to me.  Wouldn't it be incorrect for:
>
> int *Q;
> int *&P = Q;
>
>  P[1];
>
> ?
>
True. How about this?

Index: SemaExpr.cpp
===================================================================
--- SemaExpr.cpp	(revision 39794)
+++ SemaExpr.cpp	(working copy)
@@ -291,9 +291,10 @@
    // to the expression *((e1)+(e2)). This means the array "Base"  
may actually be
    // in the subscript position. As a result, we need to derive the  
array base
    // and index from the expression types.
-
+
    Expr *baseExpr, *indexExpr;
    QualType baseType, indexType;
+  QualType resultType;
    if (isa<PointerType>(canonT1) || isa<VectorType>(canonT1)) {
      baseType = canonT1;
      indexType = canonT2;
@@ -304,6 +305,35 @@
      indexType = canonT1;
      baseExpr = static_cast<Expr *>(Idx);
      indexExpr = static_cast<Expr *>(Base);
+  } else if (isa<ReferenceType>(canonT1)) {
+    // C++ 8.5.3p1: A reference to an array.
+    ReferenceType *ref = dyn_cast<ReferenceType>(canonT1);
+
+    if (ArrayType *arr = dyn_cast<ArrayType>(ref->getReferenceeType 
())) {
+      resultType = arr->getElementType();
+      baseType = canonT1;
+    } else {
+      baseType = ref->getReferenceeType();
+    }
+
+    indexType = canonT2;
+    baseExpr = static_cast<Expr *>(Base);
+    indexExpr = static_cast<Expr *>(Idx);
+  } else if (isa<ReferenceType>(canonT2)) { // uncommon
+    // C++ 8.5.3p1: A reference to an array.
+    ReferenceType *ref = dyn_cast<ReferenceType>(canonT2);
+
+    if (ArrayType *arr = dyn_cast<ArrayType>(ref->getReferenceeType 
())) {
+      resultType = arr->getElementType();
+      baseType = canonT2;
+    } else {
+      baseType = ref->getReferenceeType();
+    }
+
+    baseType = canonT2;
+    indexType = canonT1;
+    baseExpr = static_cast<Expr *>(Idx);
+    indexExpr = static_cast<Expr *>(Base);
    } else {
      return Diag(static_cast<Expr *>(Base)->getLocStart(),
                  diag::err_typecheck_subscript_value,
@@ -314,7 +344,6 @@
      return Diag(indexExpr->getLocStart(),  
diag::err_typecheck_subscript,
                  indexExpr->getSourceRange());
    }
-  QualType resultType;
    if (PointerType *ary = dyn_cast<PointerType>(baseType)) {
      // FIXME: need to deal with const...
      resultType = ary->getPointeeType();


-bw



More information about the cfe-dev mailing list