diff mbox series

PR fortran/81509 and fortran/45513

Message ID 20181223184920.GA87482@troutmask.apl.washington.edu
State New
Headers show
Series PR fortran/81509 and fortran/45513 | expand

Commit Message

Steve Kargl Dec. 23, 2018, 6:49 p.m. UTC
This is a re-submission of a patch I submitted 15 months ago.
See https://gcc.gnu.org/ml/fortran/2017-09/msg00124.html

At that time one reviewer OK'd the patch for committing,
and one reviewer raised objections to the patch as I
chose to remove dubious extensions to the Fortran standard.
I withdrew that patch with the expection that Someone
would fix the bug.  Well, Someone has not materialized.

The patch has been retested on i586-*-freebsd and x86_64-*-freebsd.

OK to commit as-is?

Here's the text from the above URL. 

In short, F2008 now allows boz-literal-constants in IAND, IOR, IEOR,
DSHIFTL, DSHIFTR, and MERGE_BITS.  gfortran currently allows a BOZ
argument, but she was not enforcing restrictions in F2008.  The
attach patch causes gfortran to conform to F2008.

As a side effect, the patch removes a questionable GNU Fortran
extension that allowed arguments to IAND, IOR, and IEOR to have
different kind type parameters.  The behavior of this extension
was not documented.

2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>

	PR fortran/45513
	PR fortran/81509
	* check.c: Rename function gfc_check_iand to gfc_check_iand_ieor_ior.
	* check.c (boz_args_check): New function.  Check I and J not both BOZ.
	(gfc_check_dshift,gfc_check_iand_ieor_ior, gfc_check_ishft,
	 gfc_check_and, gfc_check_merge_bits): Use it.
	* check.c (gfc_check_iand_ieor_ior): Force conversion of BOZ to kind
	type of other agrument.  Remove silly GNU extension.
	(gfc_check_ieor, gfc_check_ior): Delete now unused functions.
	* intrinsic.c (add_functions): Use gfc_check_iand_ieor_ior. Wrap long
	line.
	* intrinsic.h: Rename gfc_check_iand to gfc_check_iand_ieor_ior.
	Delete prototype for bool gfc_check_ieor and gfc_check_ior
	* intrinsic.texi: Update documentation for boz-literal-constant.

2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>

	PR fortran/45513
	PR fortran/81509
	* gfortran.dg/graphite/id-26.f03: Fix non-conforming use of IAND.
	* gfortran.dg/pr81509_1.f90: New test.
	* gfortran.dg/pr81509_2.f90: New test.

Comments

Jerry DeLisle Dec. 24, 2018, 12:40 a.m. UTC | #1
On 12/23/18 10:49 AM, Steve Kargl wrote:
> This is a re-submission of a patch I submitted 15 months ago.
> See https://gcc.gnu.org/ml/fortran/2017-09/msg00124.html
> 
> At that time one reviewer OK'd the patch for committing,
> and one reviewer raised objections to the patch as I
> chose to remove dubious extensions to the Fortran standard.
> I withdrew that patch with the expection that Someone
> would fix the bug.  Well, Someone has not materialized.
> 
> The patch has been retested on i586-*-freebsd and x86_64-*-freebsd.
> 
> OK to commit as-is?

I say OK to commit.

> 
> Here's the text from the above URL.
> 
> In short, F2008 now allows boz-literal-constants in IAND, IOR, IEOR,
> DSHIFTL, DSHIFTR, and MERGE_BITS.  gfortran currently allows a BOZ
> argument, but she was not enforcing restrictions in F2008.  The
> attach patch causes gfortran to conform to F2008.
> 
> As a side effect, the patch removes a questionable GNU Fortran
> extension that allowed arguments to IAND, IOR, and IEOR to have
> different kind type parameters.  The behavior of this extension
> was not documented.
> 
> 2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>
> 
> 	PR fortran/45513
> 	PR fortran/81509
> 	* check.c: Rename function gfc_check_iand to gfc_check_iand_ieor_ior.
> 	* check.c (boz_args_check): New function.  Check I and J not both BOZ.
> 	(gfc_check_dshift,gfc_check_iand_ieor_ior, gfc_check_ishft,
> 	 gfc_check_and, gfc_check_merge_bits): Use it.
> 	* check.c (gfc_check_iand_ieor_ior): Force conversion of BOZ to kind
> 	type of other agrument.  Remove silly GNU extension.
> 	(gfc_check_ieor, gfc_check_ior): Delete now unused functions.
> 	* intrinsic.c (add_functions): Use gfc_check_iand_ieor_ior. Wrap long
> 	line.
> 	* intrinsic.h: Rename gfc_check_iand to gfc_check_iand_ieor_ior.
> 	Delete prototype for bool gfc_check_ieor and gfc_check_ior
> 	* intrinsic.texi: Update documentation for boz-literal-constant.
> 
> 2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>
> 
> 	PR fortran/45513
> 	PR fortran/81509
> 	* gfortran.dg/graphite/id-26.f03: Fix non-conforming use of IAND.
> 	* gfortran.dg/pr81509_1.f90: New test.
> 	* gfortran.dg/pr81509_2.f90: New test.
>
Sudakshina Das Dec. 27, 2018, 11:24 a.m. UTC | #2
Hi Steve

On 23/12/18 6:49 PM, Steve Kargl wrote:
> This is a re-submission of a patch I submitted 15 months ago.
> See https://gcc.gnu.org/ml/fortran/2017-09/msg00124.html
>
> At that time one reviewer OK'd the patch for committing,
> and one reviewer raised objections to the patch as I
> chose to remove dubious extensions to the Fortran standard.
> I withdrew that patch with the expection that Someone
> would fix the bug.  Well, Someone has not materialized.
>
> The patch has been retested on i586-*-freebsd and x86_64-*-freebsd.
>
> OK to commit as-is?
>
> Here's the text from the above URL.
>
> In short, F2008 now allows boz-literal-constants in IAND, IOR, IEOR,
> DSHIFTL, DSHIFTR, and MERGE_BITS.  gfortran currently allows a BOZ
> argument, but she was not enforcing restrictions in F2008.  The
> attach patch causes gfortran to conform to F2008.
>
> As a side effect, the patch removes a questionable GNU Fortran
> extension that allowed arguments to IAND, IOR, and IEOR to have
> different kind type parameters.  The behavior of this extension
> was not documented.
>
> 2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>
>
> 	PR fortran/45513
> 	PR fortran/81509
> 	* check.c: Rename function gfc_check_iand to gfc_check_iand_ieor_ior.
> 	* check.c (boz_args_check): New function.  Check I and J not both BOZ.
> 	(gfc_check_dshift,gfc_check_iand_ieor_ior, gfc_check_ishft,
> 	 gfc_check_and, gfc_check_merge_bits): Use it.
> 	* check.c (gfc_check_iand_ieor_ior): Force conversion of BOZ to kind
> 	type of other agrument.  Remove silly GNU extension.
> 	(gfc_check_ieor, gfc_check_ior): Delete now unused functions.
> 	* intrinsic.c (add_functions): Use gfc_check_iand_ieor_ior. Wrap long
> 	line.
> 	* intrinsic.h: Rename gfc_check_iand to gfc_check_iand_ieor_ior.
> 	Delete prototype for bool gfc_check_ieor and gfc_check_ior
> 	* intrinsic.texi: Update documentation for boz-literal-constant.
>
> 2017-09-27  Steven G. Kargl  <kargl@gcc.gnu.org>
>
> 	PR fortran/45513
> 	PR fortran/81509
> 	* gfortran.dg/graphite/id-26.f03: Fix non-conforming use of IAND.
> 	* gfortran.dg/pr81509_1.f90: New test.
> 	* gfortran.dg/pr81509_2.f90: New test.
>
This patch has caused the following failures on aarch64-none-linux-gnu:

FAIL: libgomp.fortran/aligned1.f03   -O0  (test for excess errors)
FAIL: libgomp.fortran/aligned1.f03   -O1  (test for excess errors)
FAIL: libgomp.fortran/aligned1.f03   -O2  (test for excess errors)
FAIL: libgomp.fortran/aligned1.f03   -O3 -fomit-frame-pointer 
-funroll-loops -fpeel-loops -ftracer -finline-functions  (test for 
excess errors)
FAIL: libgomp.fortran/aligned1.f03   -O3 -g  (test for excess errors)
FAIL: libgomp.fortran/aligned1.f03   -Os  (test for excess errors)

With the failure as:

Excess errors:
/build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:55:14: 
Error: Arguments of 'iand' have different kind type parameters at (1)
/build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:59:14: 
Error: Arguments of 'iand' have different kind type parameters at (1)

Thanks

Sudi
Steve Kargl Dec. 27, 2018, 5:20 p.m. UTC | #3
On Thu, Dec 27, 2018 at 11:24:07AM +0000, Sudakshina Das wrote:
> > 	PR fortran/45513
> > 	PR fortran/81509
> > 	* gfortran.dg/graphite/id-26.f03: Fix non-conforming use of IAND.
> > 	* gfortran.dg/pr81509_1.f90: New test.
> > 	* gfortran.dg/pr81509_2.f90: New test.
> >
> This patch has caused the following failures on aarch64-none-linux-gnu:
> 
> FAIL: libgomp.fortran/aligned1.f03   -O0  (test for excess errors)
> FAIL: libgomp.fortran/aligned1.f03   -O1  (test for excess errors)
> FAIL: libgomp.fortran/aligned1.f03   -O2  (test for excess errors)
> FAIL: libgomp.fortran/aligned1.f03   -O3 -fomit-frame-pointer 
> -funroll-loops -fpeel-loops -ftracer -finline-functions  (test for 
> excess errors)
> FAIL: libgomp.fortran/aligned1.f03   -O3 -g  (test for excess errors)
> FAIL: libgomp.fortran/aligned1.f03   -Os  (test for excess errors)
> 
> With the failure as:
> 
> Excess errors:
> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:55:14: 
> Error: Arguments of 'iand' have different kind type parameters at (1)
> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:59:14: 
> Error: Arguments of 'iand' have different kind type parameters at (1)
> 

Well, it nice to see that the patch is catching invalid Fortran.
Can you test this patch?

Index: libgomp/testsuite/libgomp.fortran/aligned1.f03
===================================================================
--- libgomp/testsuite/libgomp.fortran/aligned1.f03      (revision 267418)
+++ libgomp/testsuite/libgomp.fortran/aligned1.f03      (working copy)
@@ -52,11 +52,11 @@
   ! Attempt to create 64-byte aligned allocatable
   do i = 1, 64
     allocate (c(1023 + i))
-    if (iand (loc (c(1)), 63) == 0) exit
+    if (iand (int(loc (c(1)), 8), int(63, 8)) == 0) exit
     deallocate (c)
     allocate (b(i)%a(1023 + i))
     allocate (c(1023 + i))
-    if (iand (loc (c(1)), 63) == 0) exit
+    if (iand (int(loc (c(1)), 8), int(63, 8)) == 0) exit
     deallocate (c)
   end do
   if (allocated (c)) then
Steve Kargl Dec. 27, 2018, 8:58 p.m. UTC | #4
On Thu, Dec 27, 2018 at 11:24:07AM +0000, Sudakshina Das wrote:
> With the failure as:
> 
> Excess errors:
> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:55:14: 
> Error: Arguments of 'iand' have different kind type parameters at (1)
> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:59:14: 
> Error: Arguments of 'iand' have different kind type parameters at (1)
> 

This should be fixed, now.  Sorry about the breakage.
Sudakshina Das Dec. 28, 2018, 8:54 a.m. UTC | #5
Hi Steve

On 27/12/18 8:58 PM, Steve Kargl wrote:
> On Thu, Dec 27, 2018 at 11:24:07AM +0000, Sudakshina Das wrote:
>> With the failure as:
>>
>> Excess errors:
>> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:55:14:
>> Error: Arguments of 'iand' have different kind type parameters at (1)
>> /build/src/gcc/libgomp/testsuite/libgomp.fortran/aligned1.f03:59:14:
>> Error: Arguments of 'iand' have different kind type parameters at (1)
>>
> This should be fixed, now.  Sorry about the breakage.

Thanks for the quick fix!

Sudi
diff mbox series

Patch

Index: gcc/fortran/check.c
===================================================================
--- gcc/fortran/check.c	(revision 267379)
+++ gcc/fortran/check.c	(working copy)
@@ -2168,6 +2168,21 @@  gfc_check_dprod (gfc_expr *x, gfc_expr *y)
 }
 
 
+static bool
+boz_args_check(gfc_expr *i, gfc_expr *j)
+{
+  if (i->is_boz && j->is_boz)
+    {
+      gfc_error ("Arguments of %qs at %L and %L cannot both be BOZ "
+		 "literal constants", gfc_current_intrinsic, &i->where,
+		 &j->where);
+      return false;
+
+    }
+  return true;
+}
+
+
 bool
 gfc_check_dshift (gfc_expr *i, gfc_expr *j, gfc_expr *shift)
 {
@@ -2177,12 +2192,8 @@  gfc_check_dshift (gfc_expr *i, gfc_expr *j, gfc_expr *
   if (!type_check (j, 1, BT_INTEGER))
     return false;
 
-  if (i->is_boz && j->is_boz)
-    {
-      gfc_error ("%<I%> at %L and %<J%>' at %L cannot both be BOZ literal "
-		   "constants", &i->where, &j->where);
-      return false;
-    }
+  if (!boz_args_check (i, j))
+    return false;
 
   if (!i->is_boz && !j->is_boz && !same_type_check (i, 0, j, 1))
     return false;
@@ -2482,7 +2493,7 @@  gfc_check_i (gfc_expr *i)
 
 
 bool
-gfc_check_iand (gfc_expr *i, gfc_expr *j)
+gfc_check_iand_ieor_ior (gfc_expr *i, gfc_expr *j)
 {
   if (!type_check (i, 0, BT_INTEGER))
     return false;
@@ -2490,10 +2501,16 @@  gfc_check_iand (gfc_expr *i, gfc_expr *j)
   if (!type_check (j, 1, BT_INTEGER))
     return false;
 
+  if (!boz_args_check (i, j))
+    return false;
+
+  if (i->is_boz) i->ts.kind = j->ts.kind;
+  if (j->is_boz) j->ts.kind = i->ts.kind;
+
   if (i->ts.kind != j->ts.kind)
     {
-      if (!gfc_notify_std (GFC_STD_GNU, "Different type kinds at %L",
-			   &i->where))
+      gfc_error ("Arguments of %qs have different kind type parameters "
+		 "at %L", gfc_current_intrinsic, &i->where);
 	return false;
     }
 
@@ -2608,26 +2625,6 @@  gfc_check_idnint (gfc_expr *a)
 
 
 bool
-gfc_check_ieor (gfc_expr *i, gfc_expr *j)
-{
-  if (!type_check (i, 0, BT_INTEGER))
-    return false;
-
-  if (!type_check (j, 1, BT_INTEGER))
-    return false;
-
-  if (i->ts.kind != j->ts.kind)
-    {
-      if (!gfc_notify_std (GFC_STD_GNU, "Different type kinds at %L",
-			   &i->where))
-	return false;
-    }
-
-  return true;
-}
-
-
-bool
 gfc_check_index (gfc_expr *string, gfc_expr *substring, gfc_expr *back,
 		 gfc_expr *kind)
 {
@@ -2680,28 +2677,7 @@  gfc_check_intconv (gfc_expr *x)
   return true;
 }
 
-
 bool
-gfc_check_ior (gfc_expr *i, gfc_expr *j)
-{
-  if (!type_check (i, 0, BT_INTEGER))
-    return false;
-
-  if (!type_check (j, 1, BT_INTEGER))
-    return false;
-
-  if (i->ts.kind != j->ts.kind)
-    {
-      if (!gfc_notify_std (GFC_STD_GNU, "Different type kinds at %L",
-			   &i->where))
-	return false;
-    }
-
-  return true;
-}
-
-
-bool
 gfc_check_ishft (gfc_expr *i, gfc_expr *shift)
 {
   if (!type_check (i, 0, BT_INTEGER)
@@ -3584,6 +3560,12 @@  gfc_check_merge_bits (gfc_expr *i, gfc_expr *j, gfc_ex
   if (!type_check (j, 1, BT_INTEGER))
     return false;
 
+  if (!boz_args_check (i, j))
+    return false;
+
+  if (i->is_boz) i->ts.kind = j->ts.kind;
+  if (j->is_boz) j->ts.kind = i->ts.kind;
+
   if (!type_check (mask, 2, BT_INTEGER))
     return false;
 
@@ -3593,6 +3575,8 @@  gfc_check_merge_bits (gfc_expr *i, gfc_expr *j, gfc_ex
   if (!same_type_check (i, 0, mask, 2))
     return false;
 
+  if (mask->is_boz) mask->ts.kind = i->ts.kind;
+
   return true;
 }
 
@@ -6718,6 +6702,12 @@  gfc_check_and (gfc_expr *i, gfc_expr *j)
 
   if (!scalar_check (j, 1))
     return false;
+
+  if (!boz_args_check (i, j))
+    return false;
+
+  if (i->is_boz) i->ts.kind = j->ts.kind;
+  if (j->is_boz) j->ts.kind = i->ts.kind;
 
   return true;
 }
Index: gcc/fortran/intrinsic.c
===================================================================
--- gcc/fortran/intrinsic.c	(revision 267379)
+++ gcc/fortran/intrinsic.c	(working copy)
@@ -2025,8 +2025,9 @@  add_functions (void)
 
   make_generic ("iachar", GFC_ISYM_IACHAR, GFC_STD_F95);
 
-  add_sym_2 ("iand", GFC_ISYM_IAND, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F95,
-	     gfc_check_iand, gfc_simplify_iand, gfc_resolve_iand,
+  add_sym_2 ("iand", GFC_ISYM_IAND, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di,
+	     GFC_STD_F95,
+	     gfc_check_iand_ieor_ior, gfc_simplify_iand, gfc_resolve_iand,
 	     i, BT_INTEGER, di, REQUIRED, j, BT_INTEGER, di, REQUIRED);
 
   if (flag_dec_intrinsic_ints)
@@ -2114,8 +2115,9 @@  add_functions (void)
 
   make_generic ("ichar", GFC_ISYM_ICHAR, GFC_STD_F77);
 
-  add_sym_2 ("ieor", GFC_ISYM_IEOR, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F95,
-	     gfc_check_ieor, gfc_simplify_ieor, gfc_resolve_ieor,
+  add_sym_2 ("ieor", GFC_ISYM_IEOR, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di,
+	     GFC_STD_F95,
+	     gfc_check_iand_ieor_ior, gfc_simplify_ieor, gfc_resolve_ieor,
 	     i, BT_INTEGER, di, REQUIRED, j, BT_INTEGER, di, REQUIRED);
 
   if (flag_dec_intrinsic_ints)
@@ -2192,8 +2194,9 @@  add_functions (void)
 
   make_generic ("long", GFC_ISYM_LONG, GFC_STD_GNU);
 
-  add_sym_2 ("ior", GFC_ISYM_IOR, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F95,
-	     gfc_check_ior, gfc_simplify_ior, gfc_resolve_ior,
+  add_sym_2 ("ior", GFC_ISYM_IOR, CLASS_ELEMENTAL, ACTUAL_NO, BT_INTEGER, di,
+	     GFC_STD_F95,
+	     gfc_check_iand_ieor_ior, gfc_simplify_ior, gfc_resolve_ior,
 	     i, BT_INTEGER, di, REQUIRED, j, BT_INTEGER, di, REQUIRED);
 
   if (flag_dec_intrinsic_ints)
Index: gcc/fortran/intrinsic.h
===================================================================
--- gcc/fortran/intrinsic.h	(revision 267379)
+++ gcc/fortran/intrinsic.h	(working copy)
@@ -89,17 +89,15 @@  bool gfc_check_hostnm (gfc_expr *);
 bool gfc_check_huge (gfc_expr *);
 bool gfc_check_hypot (gfc_expr *, gfc_expr *);
 bool gfc_check_i (gfc_expr *);
-bool gfc_check_iand (gfc_expr *, gfc_expr *);
+bool gfc_check_iand_ieor_ior (gfc_expr *, gfc_expr *);
 bool gfc_check_and (gfc_expr *, gfc_expr *);
 bool gfc_check_ibits (gfc_expr *, gfc_expr *, gfc_expr *);
 bool gfc_check_ichar_iachar (gfc_expr *, gfc_expr *);
 bool gfc_check_idnint (gfc_expr *);
-bool gfc_check_ieor (gfc_expr *, gfc_expr *);
 bool gfc_check_image_status (gfc_expr *, gfc_expr *);
 bool gfc_check_index (gfc_expr *, gfc_expr *, gfc_expr *, gfc_expr *);
 bool gfc_check_int (gfc_expr *, gfc_expr *);
 bool gfc_check_intconv (gfc_expr *);
-bool gfc_check_ior (gfc_expr *, gfc_expr *);
 bool gfc_check_irand (gfc_expr *);
 bool gfc_check_isatty (gfc_expr *);
 bool gfc_check_isnan (gfc_expr *);
Index: gcc/fortran/intrinsic.texi
===================================================================
--- gcc/fortran/intrinsic.texi	(revision 267379)
+++ gcc/fortran/intrinsic.texi	(working copy)
@@ -1144,15 +1144,20 @@  Function
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
 @item @var{I} @tab The type shall be either a scalar @code{INTEGER}
-type or a scalar @code{LOGICAL} type.
-@item @var{J} @tab The type shall be the same as the type of @var{I}.
+type or a scalar @code{LOGICAL} type or a boz-literal-constant.
+@item @var{J} @tab The type shall be the same as the type of @var{I} or
+a boz-literal-constant. @var{I} and @var{J} shall not both be
+boz-literal-constants.  If either @var{I} or @var{J} is a
+boz-literal-constant, then the other argument must be a scalar @code{INTEGER}.
 @end multitable
 
 @item @emph{Return value}:
 The return type is either a scalar @code{INTEGER} or a scalar
 @code{LOGICAL}.  If the kind type parameters differ, then the
 smaller kind type is implicitly converted to larger kind, and the 
-return has the larger kind.
+return has the larger kind.  A boz-literal-constant is 
+converted to an @code{INTEGER} with the kind type parameter of
+the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Example}:
 @smallexample
@@ -7523,16 +7528,17 @@  Elemental function
 
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
-@item @var{I} @tab The type shall be @code{INTEGER}.
-@item @var{J} @tab The type shall be @code{INTEGER}, of the same
-kind as @var{I}.  (As a GNU extension, different kinds are also 
-permitted.)
+@item @var{I} @tab The type shall be @code{INTEGER} or a boz-literal-constant.
+@item @var{J} @tab The type shall be @code{INTEGER} with the same
+kind type parameter as @var{I} or a boz-literal-constant.
+@var{I} and @var{J} shall not both be boz-literal-constants.
 @end multitable
 
 @item @emph{Return value}:
-The return type is @code{INTEGER}, of the same kind as the
-arguments.  (If the argument kinds differ, it is of the same kind as
-the larger argument.)
+The return type is @code{INTEGER} with the kind type parameter of the
+arguments.
+A boz-literal-constant is converted to an @code{INTEGER} with the kind
+type parameter of the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Example}:
 @smallexample
@@ -7973,16 +7979,17 @@  Elemental function
 
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
-@item @var{I} @tab The type shall be @code{INTEGER}.
-@item @var{J} @tab The type shall be @code{INTEGER}, of the same
-kind as @var{I}.  (As a GNU extension, different kinds are also 
-permitted.)
+@item @var{I} @tab The type shall be @code{INTEGER} or a boz-literal-constant.
+@item @var{J} @tab The type shall be @code{INTEGER} with the same
+kind type parameter as @var{I} or a boz-literal-constant.
+@var{I} and @var{J} shall not both be boz-literal-constants.
 @end multitable
 
 @item @emph{Return value}:
-The return type is @code{INTEGER}, of the same kind as the
-arguments.  (If the argument kinds differ, it is of the same kind as
-the larger argument.)
+The return type is @code{INTEGER} with the kind type parameter of the
+arguments.
+A boz-literal-constant is converted to an @code{INTEGER} with the kind
+type parameter of the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Specific names}:
 @multitable @columnfractions .20 .20 .20 .25
@@ -8291,16 +8298,17 @@  Elemental function
 
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
-@item @var{I} @tab The type shall be @code{INTEGER}.
-@item @var{J} @tab The type shall be @code{INTEGER}, of the same
-kind as @var{I}.  (As a GNU extension, different kinds are also 
-permitted.)
+@item @var{I} @tab The type shall be @code{INTEGER} or a boz-literal-constant.
+@item @var{J} @tab The type shall be @code{INTEGER} with the same
+kind type parameter as @var{I} or a boz-literal-constant.
+@var{I} and @var{J} shall not both be boz-literal-constants.
 @end multitable
 
 @item @emph{Return value}:
-The return type is @code{INTEGER}, of the same kind as the
-arguments.  (If the argument kinds differ, it is of the same kind as
-the larger argument.)
+The return type is @code{INTEGER} with the kind type parameter of the
+arguments.
+A boz-literal-constant is converted to an @code{INTEGER} with the kind
+type parameter of the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Specific names}:
 @multitable @columnfractions .20 .20 .20 .25
@@ -10296,11 +10304,12 @@  Elemental function
 
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
-@item @var{I}    @tab Shall be of type @code{INTEGER}.
-@item @var{J}    @tab Shall be of type @code{INTEGER} and of the same
-kind as @var{I}.
-@item @var{MASK} @tab Shall be of type @code{INTEGER} and of the same
-kind as @var{I}.
+@item @var{I} @tab Shall be of type @code{INTEGER} or a boz-literal-constant.
+@item @var{J} @tab Shall be of type @code{INTEGER} with the same
+kind type parameter as @var{I} or a boz-literal-constant.
+@var{I} and @var{J} shall not both be boz-literal-constants.
+@item @var{MASK} @tab Shall be of type @code{INTEGER} or a boz-literal-constant
+and of the same kind as @var{I}.
 @end multitable
 
 @item @emph{Return value}:
@@ -11125,15 +11134,20 @@  Function
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
 @item @var{I} @tab The type shall be either a scalar @code{INTEGER}
-type or a scalar @code{LOGICAL} type.
-@item @var{J} @tab The type shall be the same as the type of @var{J}.
+type or a scalar @code{LOGICAL} type or a boz-literal-constant.
+@item @var{J} @tab The type shall be the same as the type of @var{I} or
+a boz-literal-constant. @var{I} and @var{J} shall not both be
+boz-literal-constants.  If either @var{I} and @var{J} is a
+boz-literal-constant, then the other argument must be a scalar @code{INTEGER}.
 @end multitable
 
 @item @emph{Return value}:
 The return type is either a scalar @code{INTEGER} or a scalar
 @code{LOGICAL}.  If the kind type parameters differ, then the
 smaller kind type is implicitly converted to larger kind, and the 
-return has the larger kind.
+return has the larger kind.  A boz-literal-constant is 
+converted to an @code{INTEGER} with the kind type parameter of
+the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Example}:
 @smallexample
@@ -14639,16 +14653,21 @@  Function
 
 @item @emph{Arguments}:
 @multitable @columnfractions .15 .70
-@item @var{I} @tab The type shall be either  a scalar @code{INTEGER}
-type or a scalar @code{LOGICAL} type.
-@item @var{J} @tab The type shall be the same as the type of @var{I}.
+@item @var{I} @tab The type shall be either a scalar @code{INTEGER}
+type or a scalar @code{LOGICAL} type or a boz-literal-constant.
+@item @var{J} @tab The type shall be the same as the type of @var{I} or
+a boz-literal-constant. @var{I} and @var{J} shall not both be
+boz-literal-constants.  If either @var{I} and @var{J} is a
+boz-literal-constant, then the other argument must be a scalar @code{INTEGER}.
 @end multitable
 
 @item @emph{Return value}:
 The return type is either a scalar @code{INTEGER} or a scalar
 @code{LOGICAL}.  If the kind type parameters differ, then the
 smaller kind type is implicitly converted to larger kind, and the 
-return has the larger kind.
+return has the larger kind.  A boz-literal-constant is 
+converted to an @code{INTEGER} with the kind type parameter of
+the other argument as-if a call to @ref{INT} occurred.
 
 @item @emph{Example}:
 @smallexample
Index: gcc/testsuite/gfortran.dg/graphite/id-26.f03
===================================================================
--- gcc/testsuite/gfortran.dg/graphite/id-26.f03	(revision 267379)
+++ gcc/testsuite/gfortran.dg/graphite/id-26.f03	(working copy)
@@ -51,11 +51,11 @@ 
   ! Attempt to create 64-byte aligned allocatable
   do i = 1, 64
     allocate (c(1023 + i))
-    if (iand (loc (c(1)), 63) == 0) exit
+    if (iand(int(loc(c(1)), 8), 63_8) == 0) exit
     deallocate (c)
     allocate (b(i)%a(1023 + i))
     allocate (c(1023 + i))
-    if (iand (loc (c(1)), 63) == 0) exit
+    if (iand(int(loc(c(1)), 8), 63_8) == 0) exit
     deallocate (c)
   end do
   if (allocated (c)) then
Index: gcc/testsuite/gfortran.dg/pr81509_1.f90
===================================================================
--- gcc/testsuite/gfortran.dg/pr81509_1.f90	(nonexistent)
+++ gcc/testsuite/gfortran.dg/pr81509_1.f90	(working copy)
@@ -0,0 +1,12 @@ 
+! { dg-do run }
+! https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81509
+program foo
+logical :: a = .false.
+integer :: i = 42
+integer(8) :: k = 42
+if (kind(ieor(z'ade',i)) /= 4) call abort
+if (kind(ior(i,z'1111')) /= 4) call abort
+if (kind(ior(1_8,k)) /= 8) call abort
+if (kind(iand(k,b'1111')) /= 8) call abort
+end program foo
+
Index: gcc/testsuite/gfortran.dg/pr81509_2.f90
===================================================================
--- gcc/testsuite/gfortran.dg/pr81509_2.f90	(nonexistent)
+++ gcc/testsuite/gfortran.dg/pr81509_2.f90	(working copy)
@@ -0,0 +1,18 @@ 
+! { dg-do compile }
+! https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81509
+!
+program foo
+logical :: a = .false.
+integer :: i = 42
+integer(8) :: k
+k = iand(z'aaaa', z'1234')    ! { dg-error "cannot both be BOZ literal" }
+k = and(z'aaaa', z'1234')     ! { dg-error "cannot both be BOZ literal" }
+k = and(1, z'1234')
+k = and(i, z'1234')
+k = ieor(z'ade',i)
+k = ior(i,z'1111')
+k = ior(i,k)                  ! { dg-error "different kind type parameters" }
+k = and(i,k)
+k = and(a,z'1234')            ! { dg-error "must have the same type" }
+end program foo
+