[F-E, patch]: bug fixes for type components, etc.

Christopher D. Rickett crickett@lanl.gov
Fri Jun 8 01:01:00 GMT 2007


hi all,

the attached patch mainly fixes bugs found by Tobias for bind(c) derived 
types that have pointer/allocatable components.

bootstrapped and regtested on x86 with no new failures.

ChangeLog entry:
2007-06-07  Christopher D. Rickett  <crickett@lanl.gov>
 	* trans-expr.c (gfc_conv_initializer): Combined if statements.
 	* symbol.c (verify_bind_c_derived_type): Fixed bugs with POINTER
 	and ALLOCATABLE components.  Add check to prevent duplicate
 	checking of a C interoperable derived type.  Change "can not" to
 	"cannot".
 	* gfortran.dg/bind_c_dts_3.f03: Added new tests for POINTER and
 	ALLOCATABLE components.

Chris
-------------- next part --------------
Index: gcc/testsuite/gfortran.dg/bind_c_dts_3.f03
===================================================================
--- gcc/testsuite/gfortran.dg/bind_c_dts_3.f03	(revision 125544)
+++ gcc/testsuite/gfortran.dg/bind_c_dts_3.f03	(working copy)
@@ -3,6 +3,10 @@ module bind_c_dts_3
 use, intrinsic :: iso_c_binding
 implicit none
 
+TYPE, bind(c) :: t
+  integer(c_int) :: i
+end type t
+
 type :: my_c_type_0 ! { dg-error "must have the BIND attribute" }
    integer(c_int) :: i
 end type my_c_type_0
@@ -13,6 +17,14 @@ type, bind(c) :: my_c_type_1 ! { dg-erro
    integer(c_int), pointer :: j ! { dg-error "cannot have the POINTER" }
 end type my_c_type_1
 
+type, bind(c) :: t2 ! { dg-error "BIND.C. derived type" }
+   type (t2), pointer :: next ! { dg-error "cannot have the POINTER" }
+end type t2
+
+type, bind(c):: t3 ! { dg-error "BIND.C. derived type" }
+  type(t), allocatable :: c(:) ! { dg-error "cannot have the ALLOCATABLE" }
+end type t3
+
 contains
   subroutine sub0(my_type, expected_value) bind(c) ! { dg-error "is not C interoperable" }
     type(my_c_type_1) :: my_type
Index: gcc/fortran/trans-expr.c
===================================================================
--- gcc/fortran/trans-expr.c	(revision 125544)
+++ gcc/fortran/trans-expr.c	(working copy)
@@ -2755,9 +2755,9 @@ gfc_conv_initializer (gfc_expr * expr, g
     return NULL_TREE;
 
   if (expr != NULL && expr->ts.type == BT_DERIVED
-      && expr->ts.is_iso_c && expr->ts.derived)
-    if (expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_PTR
-        || expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_FUNPTR)
+      && expr->ts.is_iso_c && expr->ts.derived
+      && (expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_PTR
+	  || expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_FUNPTR))
       expr = gfc_int_expr (0);
   
   if (array)
@@ -3159,8 +3159,8 @@ gfc_conv_expr (gfc_se * se, gfc_expr * e
       if (expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_PTR
           || expr->symtree->n.sym->intmod_sym_id == ISOCBINDING_NULL_FUNPTR)
         {
-          /* Try simply setting expr_type to EXPR_NULL, which should result
-             in null_pointer_node being used below.  */
+	  /* Set expr_type to EXPR_NULL, which will result in
+	     null_pointer_node being used below.  */
           expr->expr_type = EXPR_NULL;
         }
       else
Index: gcc/fortran/symbol.c
===================================================================
--- gcc/fortran/symbol.c	(revision 125544)
+++ gcc/fortran/symbol.c	(working copy)
@@ -27,6 +27,7 @@ Software Foundation, 51 Franklin Street,
 #include "gfortran.h"
 #include "parse.h"
 
+
 /* Strings for all symbol attributes.  We use these for dumping the
    parse tree, in error messages, and also when reading and writing
    modules.  */
@@ -3006,6 +3007,11 @@ verify_bind_c_derived_type (gfc_symbol *
     gfc_internal_error ("verify_bind_c_derived_type(): Given symbol is "
                         "unexpectedly NULL");
 
+  /* If we've already looked at this derived symbol, do not look at it again
+     so we don't repeat warnings/errors.  */
+  if (derived_sym->ts.is_c_interop)
+    return SUCCESS;
+  
   /* The derived type must have the BIND attribute to be interoperable
      J3/04-007, Section 15.2.3.  */
   if (derived_sym->attr.is_bind_c != 1)
@@ -3035,10 +3041,34 @@ verify_bind_c_derived_type (gfc_symbol *
      each is a C interoperable type.  */
   do
     {
-      /* BIND(C) derived types can't have derived types in them unless
-	 they're c_ptr or c_funptr. J3/04-007, Section 15.2.3, C1502.  */
+      /* The components cannot be pointers (fortran sense).  
+         J3/04-007, Section 15.2.3, C1505.	*/
+      if (curr_comp->pointer != 0)
+        {
+          gfc_error ("Component '%s' at %L cannot have the "
+                     "POINTER attribute because it is a member "
+                     "of the BIND(C) derived type '%s' at %L",
+                     curr_comp->name, &(curr_comp->loc),
+                     derived_sym->name, &(derived_sym->declared_at));
+          retval = FAILURE;
+        }
+
+      /* The components cannot be allocatable.
+         J3/04-007, Section 15.2.3, C1505.	*/
+      if (curr_comp->allocatable != 0)
+        {
+          gfc_error ("Component '%s' at %L cannot have the "
+                     "ALLOCATABLE attribute because it is a member "
+                     "of the BIND(C) derived type '%s' at %L",
+                     curr_comp->name, &(curr_comp->loc),
+                     derived_sym->name, &(derived_sym->declared_at));
+          retval = FAILURE;
+        }
+      
+      /* BIND(C) derived types must have interoperable components.  */
       if (curr_comp->ts.type == BT_DERIVED
-	  && curr_comp->ts.derived->ts.is_iso_c != 1)
+	  && curr_comp->ts.derived->ts.is_iso_c != 1 
+          && curr_comp->ts.derived != derived_sym)
         {
           /* This should be allowed; the draft says a derived-type can not
              have type parameters if it is has the BIND attribute.  Type
@@ -3080,30 +3110,6 @@ verify_bind_c_derived_type (gfc_symbol *
                              curr_comp->name, derived_sym->name,
                              &(curr_comp->loc));
 	    }
-	  
-	  /* The components can not be pointers (fortran sense).  
-	     J3/04-007, Section 15.2.3, C1505.	*/
-	  if (curr_comp->pointer != 0)
-	    {
-	      gfc_error ("Component '%s' at %L cannot have the "
-                         "POINTER attribute because it is a member "
-                         "of the BIND(C) derived type '%s' at %L",
-                         curr_comp->name, &(curr_comp->loc),
-                         derived_sym->name, &(derived_sym->declared_at));
-	      retval = FAILURE;
-	    }
-
-	  /* The components can not be allocatable.
-	     J3/04-007, Section 15.2.3, C1505.	*/
-	  if (curr_comp->allocatable != 0)
-	    {
-	      gfc_error ("Component '%s' at %L cannot have the "
-			 "ALLOCATABLE attribute because it is a member "
-			 "of the BIND(C) derived type '%s' at %L",
-			 curr_comp->name, &(curr_comp->loc),
-			 derived_sym->name, &(derived_sym->declared_at));
-	      retval = FAILURE;
-	    }
 	}
       
       curr_comp = curr_comp->next;
@@ -3181,8 +3187,8 @@ gen_special_c_interop_ptr (int ptr_id, c
       generate_isocbinding_symbol (module_name, ptr_id == ISOCBINDING_NULL_PTR 
                                    ? ISOCBINDING_PTR : ISOCBINDING_FUNPTR,
                                    (char *) (ptr_id == ISOCBINDING_NULL_PTR 
-				   ? "_gfortran_iso_c_binding_c_ptr"
-				   : "_gfortran_iso_c_binding_c_funptr"));
+				   ? "_gfortran_iso_c_binding_c_ptr" :
+				   "_gfortran_iso_c_binding_c_funptr"));
 
       tmp_sym->ts.derived =
         get_iso_c_binding_dt (ptr_id == ISOCBINDING_NULL_PTR
@@ -3723,8 +3729,8 @@ generate_isocbinding_symbol (const char 
                       (mod_name, s == ISOCBINDING_FUNLOC
                        ? ISOCBINDING_FUNPTR : ISOCBINDING_FUNPTR,
                        (char *)(s == ISOCBINDING_FUNLOC 
-                                ? "_gfortran_iso_c_binding_c_funptr"
-				: "_gfortran_iso_c_binding_c_ptr"));
+				? "_gfortran_iso_c_binding_c_funptr" :
+				"_gfortran_iso_c_binding_c_ptr"));
                     tmp_sym->ts.derived =
                       get_iso_c_binding_dt (s == ISOCBINDING_FUNLOC
                                             ? ISOCBINDING_FUNPTR


More information about the Fortran mailing list