[patch, fortran] Reject character lengths unequal to one in BIND(C)

2018-01-28 Thread Thomas Koenig

Hello world,

At the moment, gfortran silently accepts

  type, bind(c) :: a
 character(len=2,kind=c_char) :: b
  end type a

translating this into I don't know what. With the -fc-prototypes
option, we now get

typedef struct a {
char b;
} a;

which is clearly bogus. Any user code which has the broken code above
will then likely crash and burn when using a gfortran-generated
prototype.

The attached patch solves that particular problem by issuing errors
in this case.  OK for trunk?

Regards

Thomas

2017-01-28  Thomas Koenig  

PR fortran/84073
* resolve.c (resolve_component): Ensure BIND(C) character
components have length one.
(resolve_symbol): Likewise for variables.

2017-01-28  Thomas Koenig  

PR fortran/84073
* gfortran.dg/bind_c_usage_31.f90: New test.
Index: resolve.c
===
--- resolve.c	(Revision 257131)
+++ resolve.c	(Arbeitskopie)
@@ -13557,6 +13557,17 @@ resolve_component (gfc_component *c, gfc_symbol *s
   return false;
 }
 
+  /* F2003, 15.2.1 - length has to be one.  */
+  if (sym->attr.is_bind_c && c->ts.type == BT_CHARACTER
+  && (c->ts.u.cl == NULL || c->ts.u.cl->length == NULL
+	  || !gfc_is_constant_expr (c->ts.u.cl->length)
+	  || mpz_cmp_si (c->ts.u.cl->length->value.integer, 1) != 0))
+{
+  gfc_error ("Component %qs of BIND(C) type at %L must have length one",
+		 c->name, &c->loc);
+  return false;
+}
+
   if (c->attr.proc_pointer && c->ts.interface)
 {
   gfc_symbol *ifc = c->ts.interface;
@@ -14804,6 +14815,15 @@ resolve_symbol (gfc_symbol *sym)
 		 "module level scope", sym->name, &(sym->declared_at));
 	  t = false;
 	}
+  else if (sym->ts.type == BT_CHARACTER
+	   && (sym->ts.u.cl == NULL || sym->ts.u.cl->length == NULL
+		   || !gfc_is_constant_expr (sym->ts.u.cl->length)
+		   || mpz_cmp_si (sym->ts.u.cl->length->value.integer, 1) != 0))
+	{
+	  gfc_error ("BIND(C) Variable %qs at %L must have length one",
+		 sym->name, &sym->declared_at);
+	  t = false;
+	}
   else if (sym->common_head != NULL && sym->attr.implicit_type == 0)
 {
   t = verify_com_block_vars_c_interop (sym->common_head);
! { dg-do compile }
! PR fortran/84073 - this was accepted before.
module mod
  use iso_c_binding
  type, bind(c) :: a
 character(len=2,kind=c_char) :: b ! { dg-error "must have length one" }
  end type a
  character(len=2), bind(C) :: c ! { dg-error "must have length one" }
end module mod


Re: [PATCH] i386: Add TARGET_INDIRECT_BRANCH_REGISTER

2018-01-28 Thread H.J. Lu
On Sat, Jan 27, 2018 at 2:12 PM, H.J. Lu  wrote:
> For
>
> ---
> struct C {
>   virtual ~C();
>   virtual void f();
> };
>
> void
> f (C *p)
> {
>   p->f();
>   p->f();
> }
> ---
>
> -mindirect-branch=thunk-extern -O2 on x86-64 GNU/Linux generates:
>
> _Z1fP1C:
> .LFB0:
> .cfi_startproc
> pushq   %rbx
> .cfi_def_cfa_offset 16
> .cfi_offset 3, -16
> movq(%rdi), %rax
> movq%rdi, %rbx
> jmp .LIND1
> .LIND0:
> pushq   16(%rax)
> jmp __x86_indirect_thunk
> .LIND1:
> call.LIND0
> movq(%rbx), %rax
> movq%rbx, %rdi
> popq%rbx
> .cfi_def_cfa_offset 8
> movq16(%rax), %rax
> jmp __x86_indirect_thunk_rax
> .cfi_endproc
>
> x86-64 is supposed to have asynchronous unwind tables by default, but
> there is nothing that reflects the change in the (relative) frame
> address after .LIND0.  That region really has to be moved outside of
> the .cfi_startproc/.cfi_endproc bracket.
>
> This patch adds TARGET_INDIRECT_BRANCH_REGISTER to force indirect
> branch via register when -mindirect-branch=thunk-extern is used.  Now,
> -mindirect-branch=thunk-extern -O2 on x86-64 GNU/Linux generates:
>
> _Z1fP1C:
> .LFB0:
> .cfi_startproc
> pushq   %rbx
> .cfi_def_cfa_offset 16
> .cfi_offset 3, -16
> movq(%rdi), %rax
> movq%rdi, %rbx
> movq16(%rax), %rax
> call__x86_indirect_thunk_rax
> movq(%rbx), %rax
> movq%rbx, %rdi
> popq%rbx
> .cfi_def_cfa_offset 8
> movq16(%rax), %rax
> jmp __x86_indirect_thunk_rax
> .cfi_endproc
>
> Now "-mindirect-branch=thunk-extern" is equivalent to
> "-mindirect-branch=thunk-extern -mindirect-branch-register", which is
> used by Linux kernel.
>
> Tested on i686 and x86-64.  OK for trunk?
>
> Thanks.
>
> H.J.
> 
> gcc/
>
> PR target/84039
> * config/i386/constraints.md (Bs): Replace
> ix86_indirect_branch_register with
> TARGET_INDIRECT_BRANCH_REGISTER.
> (Bw): Likewise.
> * config/i386/i386.md (indirect_jump): Likewise.
> (tablejump): Likewise.
> (*sibcall_memory): Likewise.
> (*sibcall_value_memory): Likewise.
> Peepholes of indirect call and jump via memory: Likewise.
> * config/i386/i386.opt: Likewise.
> * config/i386/predicates.md (indirect_branch_operand): Likewise.
> (GOT_memory_operand): Likewise.
> (call_insn_operand): Likewise.
> (sibcall_insn_operand): Likewise.
> (GOT32_symbol_operand): Likewise.
> * config/i386/i386.h (TARGET_INDIRECT_BRANCH_REGISTER): New.
>

Here is the updated patch  to disallow *sibcall_GOT_32 and *sibcall_value_GOT_32
for TARGET_INDIRECT_BRANCH_REGISTER.

Tested on i686 and x86-64.  OK for trunk?


-- 
H.J.
From bef283963f2c2e067046c5ea30021a96083c3546 Mon Sep 17 00:00:00 2001
From: "H.J. Lu" 
Date: Fri, 26 Jan 2018 15:54:25 -0800
Subject: [PATCH] i386: Add TARGET_INDIRECT_BRANCH_REGISTER

For

---
struct C {
  virtual ~C();
  virtual void f();
};

void
f (C *p)
{
  p->f();
  p->f();
}
---

-mindirect-branch=thunk-extern -O2 on x86-64 GNU/Linux generates:

_Z1fP1C:
.LFB0:
.cfi_startproc
pushq   %rbx
.cfi_def_cfa_offset 16
.cfi_offset 3, -16
movq(%rdi), %rax
movq%rdi, %rbx
jmp .LIND1
.LIND0:
pushq   16(%rax)
jmp __x86_indirect_thunk
.LIND1:
call.LIND0
movq(%rbx), %rax
movq%rbx, %rdi
popq%rbx
.cfi_def_cfa_offset 8
movq16(%rax), %rax
jmp __x86_indirect_thunk_rax
.cfi_endproc

x86-64 is supposed to have asynchronous unwind tables by default, but
there is nothing that reflects the change in the (relative) frame
address after .LIND0.  That region really has to be moved outside of
the .cfi_startproc/.cfi_endproc bracket.

This patch adds TARGET_INDIRECT_BRANCH_REGISTER to force indirect
branch via register when -mindirect-branch=thunk-extern is used.  Now,
-mindirect-branch=thunk-extern -O2 on x86-64 GNU/Linux generates:

_Z1fP1C:
.LFB0:
	.cfi_startproc
	pushq	%rbx
	.cfi_def_cfa_offset 16
	.cfi_offset 3, -16
	movq	(%rdi), %rax
	movq	%rdi, %rbx
	movq	16(%rax), %rax
	call	__x86_indirect_thunk_rax
	movq	(%rbx), %rax
	movq	%rbx, %rdi
	popq	%rbx
	.cfi_def_cfa_offset 8
	movq	16(%rax), %rax
	jmp	__x86_indirect_thunk_rax
	.cfi_endproc

Now "-mindirect-branch=thunk-extern" is equivalent to
"-mindirect-branch=thunk-extern -mindirect-branch-register", which is
used by Linux kernel.

gcc/

	PR target/84039
	* config/i386/constraints.md (Bs): Replace
	ix86_indirect_branch_register with
	TARGET_INDIRECT_BRANCH_REGISTER.
	(Bw): Likewise.
	* config/i386/i386.md (indirect_jump): Likewise.
	(tablejump): Likewise.
	(*sibcall_memory): Likewise.
	(*sibcall_value_memory): 

Re: [patch, fortran] Reject character lengths unequal to one in BIND(C)

2018-01-28 Thread Steve Kargl
On Sun, Jan 28, 2018 at 05:00:21PM +0100, Thomas Koenig wrote:
> Hello world,
> 
> At the moment, gfortran silently accepts
> 
>type, bind(c) :: a
>   character(len=2,kind=c_char) :: b
>end type a
> 
> translating this into I don't know what. With the -fc-prototypes
> option, we now get
> 
> typedef struct a {
>  char b;
> } a;
> 
> which is clearly bogus. Any user code which has the broken code above
> will then likely crash and burn when using a gfortran-generated
> prototype.
> 
> The attached patch solves that particular problem by issuing errors
> in this case.  OK for trunk?
> 

yes.

-- 
steve


[PATCH] RISC-V: Support for FreeBSD

2018-01-28 Thread Kito Cheng
Hi all:

This patch enable RISC-V support FreeBSD, Ruslan (RISC-V FreeBSD
maintainer) and me has been tested on FreeBSD 12 for building kernel
and whole user space programs/libraries.

gcc/ChangeLog

2018-01-29  Ruslan Bukin  
Kito Cheng  

* config.gcc (riscv*-*-freebsd*): New.
* config/riscv/freebsd.h: New.

libgcc/ChangeLog

2018-01-29  Ruslan Bukin  

* libgcc/config.host: Support RISC-V FreeBSD.
From ccd477e26426b59eb2ec127072064e653f754276 Mon Sep 17 00:00:00 2001
From: Ruslan Bukin 
Date: Wed, 3 Jan 2018 15:59:04 +
Subject: [PATCH] RISC-V: Add support for FreeBSD

gcc/ChangeLog

2018-01-19  Ruslan Bukin  
	Kito Cheng  

	* config.gcc (riscv*-*-freebsd*): New.
	* config/riscv/freebsd.h: New.

libgcc/ChangeLog

2018-01-19  Ruslan Bukin  

	* libgcc/config.host: Support RISC-V FreeBSD.
---
 gcc/config.gcc |  7 ++
 gcc/config/riscv/freebsd.h | 54 ++
 libgcc/config.host |  4 
 3 files changed, 65 insertions(+)
 create mode 100644 gcc/config/riscv/freebsd.h

diff --git a/gcc/config.gcc b/gcc/config.gcc
index ec6822b..0389f13 100644
--- a/gcc/config.gcc
+++ b/gcc/config.gcc
@@ -2086,6 +2086,13 @@ riscv*-*-elf* | riscv*-*-rtems*)
 	  ;;
 	esac
 	;;
+riscv*-*-freebsd*)
+	tm_file="${tm_file} dbxelf.h elfos.h ${fbsd_tm_file} riscv/freebsd.h"
+	tmake_file="${tmake_file} riscv/t-riscv"
+	gnu_ld=yes
+	gas=yes
+	gcc_cv_initfini_array=yes
+	;;
 mips*-*-netbsd*)			# NetBSD/mips, either endian.
 	target_cpu_default="MASK_ABICALLS"
 	tm_file="elfos.h ${tm_file} mips/elf.h ${nbsd_tm_file} mips/netbsd.h"
diff --git a/gcc/config/riscv/freebsd.h b/gcc/config/riscv/freebsd.h
new file mode 100644
index 000..ed1ec59
--- /dev/null
+++ b/gcc/config/riscv/freebsd.h
@@ -0,0 +1,54 @@
+/* Definitions for RISC-V FreeBSD systems with ELF format.
+   Copyright (C) 1998-2018 Free Software Foundation, Inc.
+
+This file is part of GCC.
+
+GCC is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3, or (at your option)
+any later version.
+
+GCC is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GCC; see the file COPYING3.  If not see
+.  */
+
+#undef WCHAR_TYPE
+#define WCHAR_TYPE "int"
+
+#undef WCHAR_TYPE_SIZE
+#define WCHAR_TYPE_SIZE 32
+
+#undef  SUBTARGET_EXTRA_SPECS
+#define SUBTARGET_EXTRA_SPECS \
+  { "fbsd_dynamic_linker", FBSD_DYNAMIC_LINKER }
+
+#undef CC1_SPEC
+#define CC1_SPEC "%(cc1_cpu) %{profile:-p}"
+
+/* Provide a LINK_SPEC appropriate for FreeBSD.  Here we provide support
+   for the special GCC options -static and -shared, which allow us to
+   link things in one of these three modes by applying the appropriate
+   combinations of options at link-time.
+
+   When the -shared link option is used a final link is not being
+   done.  */
+
+#undef LINK_SPEC
+#define LINK_SPEC "		\
+  -melf" XLEN_SPEC "lriscv	\
+  %{p:%nconsider using `-pg' instead of `-p' with gprof (1) }	\
+  %{v:-V}			\
+  %{assert*} %{R*} %{rpath*} %{defsym*}\
+  %{shared:-Bshareable %{h*} %{soname*}}			\
+  %{symbolic:-Bsymbolic}	\
+  %{static:-Bstatic}		\
+  %{!shared:			\
+  %{!static:		\
+%{rdynamic:-export-dynamic}\
+-dynamic-linker " FBSD_DYNAMIC_LINKER "}		\
+%{static:-static}}"
diff --git a/libgcc/config.host b/libgcc/config.host
index 96d55a4..924f7f6 100644
--- a/libgcc/config.host
+++ b/libgcc/config.host
@@ -1128,6 +1128,10 @@ riscv*-*-linux*)
 	extra_parts="$extra_parts crtbegin.o crtend.o crti.o crtn.o crtendS.o crtbeginT.o"
 	md_unwind_header=riscv/linux-unwind.h
 	;;
+riscv*-*-freebsd*)
+	tmake_file="${tmake_file} riscv/t-fpbit riscv/t-dpbit riscv/t-tpbit riscv/t-elf"
+	extra_parts="$extra_parts crtbegin.o crtend.o crti.o crtn.o crtendS.o crtbeginT.o"
+	;;
 riscv*-*-*)
 	tmake_file="${tmake_file} riscv/t-softfp${host_address} t-softfp riscv/t-elf riscv/t-elf${host_address}"
 	extra_parts="$extra_parts crtbegin.o crtend.o crti.o crtn.o"
-- 
1.9.1