aboutsummaryrefslogtreecommitdiff
path: root/gcc/ada
diff options
context:
space:
mode:
authorEric Botcazou <ebotcazou@adacore.com>2024-01-09 16:25:09 +0100
committerMarc Poulhiès <poulhies@adacore.com>2024-05-07 09:55:54 +0200
commitd59f383a90487d081e1754e529a8ed41837767ec (patch)
tree568993e580f31985f39c1486fcda49ea8b2aa0f7 /gcc/ada
parentceaae63a4b4bae36eb2b693ee862f91267dfb62a (diff)
downloadgcc-d59f383a90487d081e1754e529a8ed41837767ec.zip
gcc-d59f383a90487d081e1754e529a8ed41837767ec.tar.gz
gcc-d59f383a90487d081e1754e529a8ed41837767ec.tar.bz2
ada: Fix LTO type mismatches in GNAT.Sockets.Thin
The default implementation of GNAT.Sockets.Thin is mainly used on Linux and the socklen_t type used in various routines of the BSD sockets C API is a typedef for unsigned int there, so importing it as Interface.C.int will be flagged as a type mismatch during LTO compilation. gcc/ada/ * libgnat/g-socthi.ads (C_Bind): Turn into inline function. (C_Getpeername): Likewise. (C_Getsockname): Likewise. (C_Getsockopt): Likewise. (C_Setsockopt): Likewise. (Nonreentrant_Gethostbyaddr): Likewise. * libgnat/g-socthi.adb (Syscall_Accept): Adjust profile. (Syscall_Connect): Likewise. (Syscall_Recvfrom): Likewise. (Syscall_Sendto): Likewise. (C_Bind): New function. (C_Accept): Adjust to above change for profiles. (C_Connect): Likewise. (C_Getpeername): New function. (C_Getsockname): Likewise. (C_Getsockopt): Likewise. (C_Recvfrom): Adjust to above change for profiles. (C_Setsockopt): New function. (Nonreentrant_Gethostbyaddr): Likewise.
Diffstat (limited to 'gcc/ada')
-rw-r--r--gcc/ada/libgnat/g-socthi.adb176
-rw-r--r--gcc/ada/libgnat/g-socthi.ads12
2 files changed, 170 insertions, 18 deletions
diff --git a/gcc/ada/libgnat/g-socthi.adb b/gcc/ada/libgnat/g-socthi.adb
index dce2717..f8ddcc7 100644
--- a/gcc/ada/libgnat/g-socthi.adb
+++ b/gcc/ada/libgnat/g-socthi.adb
@@ -62,13 +62,13 @@ package body GNAT.Sockets.Thin is
function Syscall_Accept
(S : C.int;
Addr : System.Address;
- Addrlen : not null access C.int) return C.int;
+ Addrlen : not null access C.unsigned) return C.int;
pragma Import (C, Syscall_Accept, "accept");
function Syscall_Connect
(S : C.int;
Name : System.Address;
- Namelen : C.int) return C.int;
+ Namelen : C.unsigned) return C.int;
pragma Import (C, Syscall_Connect, "connect");
function Syscall_Recv
@@ -84,7 +84,7 @@ package body GNAT.Sockets.Thin is
Len : C.size_t;
Flags : C.int;
From : System.Address;
- Fromlen : not null access C.int) return System.CRTL.ssize_t;
+ Fromlen : not null access C.unsigned) return System.CRTL.ssize_t;
pragma Import (C, Syscall_Recvfrom, "recvfrom");
function Syscall_Recvmsg
@@ -105,7 +105,7 @@ package body GNAT.Sockets.Thin is
Len : C.size_t;
Flags : C.int;
To : System.Address;
- Tolen : C.int) return System.CRTL.ssize_t;
+ Tolen : C.unsigned) return System.CRTL.ssize_t;
pragma Import (C, Syscall_Sendto, "sendto");
function Syscall_Socket
@@ -125,6 +125,25 @@ package body GNAT.Sockets.Thin is
function Non_Blocking_Socket (S : C.int) return Boolean;
procedure Set_Non_Blocking_Socket (S : C.int; V : Boolean);
+ ------------
+ -- C_Bind --
+ ------------
+
+ function C_Bind
+ (S : C.int;
+ Name : System.Address;
+ Namelen : C.int) return C.int
+ is
+ function Bind
+ (S : C.int;
+ Name : System.Address;
+ Namelen : C.unsigned) return C.int
+ with Import, Convention => C, External_Name => "bind";
+
+ begin
+ return Bind (S, Name, C.unsigned (Namelen));
+ end C_Bind;
+
--------------
-- C_Accept --
--------------
@@ -134,15 +153,18 @@ package body GNAT.Sockets.Thin is
Addr : System.Address;
Addrlen : not null access C.int) return C.int
is
- R : C.int;
- Val : aliased C.int := 1;
+ R : C.int;
+ U_Addrlen : aliased C.unsigned;
+ Val : aliased C.int := 1;
Discard : C.int;
pragma Warnings (Off, Discard);
begin
+ U_Addrlen := C.unsigned (Addrlen.all);
+
loop
- R := Syscall_Accept (S, Addr, Addrlen);
+ R := Syscall_Accept (S, Addr, U_Addrlen'Unchecked_Access);
exit when SOSC.Thread_Blocking_IO
or else R /= Failure
or else Non_Blocking_Socket (S)
@@ -150,6 +172,8 @@ package body GNAT.Sockets.Thin is
delay Quantum;
end loop;
+ Addrlen.all := C.int (U_Addrlen);
+
if not SOSC.Thread_Blocking_IO
and then R /= Failure
then
@@ -177,7 +201,7 @@ package body GNAT.Sockets.Thin is
Res : C.int;
begin
- Res := Syscall_Connect (S, Name, Namelen);
+ Res := Syscall_Connect (S, Name, C.unsigned (Namelen));
if SOSC.Thread_Blocking_IO
or else Res /= Failure
@@ -215,7 +239,7 @@ package body GNAT.Sockets.Thin is
end loop;
end;
- Res := Syscall_Connect (S, Name, Namelen);
+ Res := Syscall_Connect (S, Name, C.unsigned (Namelen));
if Res = Failure
and then Errno = SOSC.EISCONN
@@ -226,6 +250,85 @@ package body GNAT.Sockets.Thin is
end if;
end C_Connect;
+ -------------------
+ -- C_Getpeername --
+ -------------------
+
+ function C_Getpeername
+ (S : C.int;
+ Name : System.Address;
+ Namelen : not null access C.int) return C.int
+ is
+ function Getpeername
+ (S : C.int;
+ Name : System.Address;
+ Namelen : not null access C.unsigned) return C.int
+ with Import, Convention => C, External_Name => "getpeername";
+
+ U_Namelen : aliased C.unsigned;
+ Val : C.int;
+
+ begin
+ U_Namelen := C.unsigned (Namelen.all);
+ Val := Getpeername (S, Name, U_Namelen'Unchecked_Access);
+ Namelen.all := C.int (U_Namelen);
+ return Val;
+ end C_Getpeername;
+
+ -------------------
+ -- C_Getsockname --
+ -------------------
+
+ function C_Getsockname
+ (S : C.int;
+ Name : System.Address;
+ Namelen : not null access C.int) return C.int
+ is
+ function Getsockname
+ (S : C.int;
+ Name : System.Address;
+ Namelen : not null access C.unsigned) return C.int
+ with Import, Convention => C, External_Name => "getsockname";
+
+ U_Namelen : aliased C.unsigned;
+ Val : C.int;
+
+ begin
+ U_Namelen := C.unsigned (Namelen.all);
+ Val := Getsockname (S, Name, U_Namelen'Unchecked_Access);
+ Namelen.all := C.int (U_Namelen);
+ return Val;
+ end C_Getsockname;
+
+ -------------------
+ -- C_Getsockopt --
+ -------------------
+
+ function C_Getsockopt
+ (S : C.int;
+ Level : C.int;
+ Optname : C.int;
+ Optval : System.Address;
+ Optlen : not null access C.int) return C.int
+ is
+ function Getsockopt
+ (S : C.int;
+ Level : C.int;
+ Optname : C.int;
+ Optval : System.Address;
+ Optlen : not null access C.unsigned) return C.int
+ with Import, Convention => C, External_Name => "getsockopt";
+
+ U_Optlen : aliased C.unsigned;
+ Val : C.int;
+
+ begin
+ U_Optlen := C.unsigned (Optlen.all);
+ Val := Getsockopt (S, Level, Optname, Optval, U_Optlen'Unchecked_Access);
+ Optlen.all := C.int (U_Optlen);
+ return Val;
+ end C_Getsockopt;
+
------------------
-- Socket_Ioctl --
------------------
@@ -282,11 +385,15 @@ package body GNAT.Sockets.Thin is
From : System.Address;
Fromlen : not null access C.int) return C.int
is
- Res : C.int;
+ Res : C.int;
+ U_Fromlen : aliased C.unsigned;
begin
+ U_Fromlen := C.unsigned (Fromlen.all);
+
loop
- Res := C.int (Syscall_Recvfrom (S, Msg, Len, Flags, From, Fromlen));
+ Res := C.int (Syscall_Recvfrom (S, Msg, Len, Flags, From,
+ U_Fromlen'Unchecked_Access));
exit when SOSC.Thread_Blocking_IO
or else Res /= Failure
or else Non_Blocking_Socket (S)
@@ -294,6 +401,8 @@ package body GNAT.Sockets.Thin is
delay Quantum;
end loop;
+ Fromlen.all := C.int (U_Fromlen);
+
return Res;
end C_Recvfrom;
@@ -361,7 +470,8 @@ package body GNAT.Sockets.Thin is
begin
loop
- Res := C.int (Syscall_Sendto (S, Msg, Len, Flags, To, Tolen));
+ Res := C.int (Syscall_Sendto (S, Msg, Len, Flags, To,
+ C.unsigned (Tolen)));
exit when SOSC.Thread_Blocking_IO
or else Res /= Failure
or else Non_Blocking_Socket (S)
@@ -372,6 +482,29 @@ package body GNAT.Sockets.Thin is
return Res;
end C_Sendto;
+ ------------------
+ -- C_Setsockopt --
+ ------------------
+
+ function C_Setsockopt
+ (S : C.int;
+ Level : C.int;
+ Optname : C.int;
+ Optval : System.Address;
+ Optlen : C.int) return C.int
+ is
+ function Setsockopt
+ (S : C.int;
+ Level : C.int;
+ Optname : C.int;
+ Optval : System.Address;
+ Optlen : C.unsigned) return C.int
+ with Import, Convention => C, External_Name => "setsockopt";
+
+ begin
+ return Setsockopt (S, Level, Optname, Optval, C.unsigned (Optlen));
+ end C_Setsockopt;
+
--------------
-- C_Socket --
--------------
@@ -457,6 +590,25 @@ package body GNAT.Sockets.Thin is
Task_Lock.Unlock;
end Set_Non_Blocking_Socket;
+ --------------------------------
+ -- Nonreentrant_Gethostbyaddr --
+ --------------------------------
+
+ function Nonreentrant_Gethostbyaddr
+ (Addr : System.Address;
+ Addr_Len : C.int;
+ Addr_Type : C.int) return Hostent_Access
+ is
+ function Gethostbyaddr
+ (Addr : System.Address;
+ Addr_Len : C.unsigned;
+ Addr_Type : C.int) return Hostent_Access
+ with Import, Convention => C, External_Name => "gethostbyaddr";
+
+ begin
+ return Gethostbyaddr (Addr, C.unsigned (Addr_Len), Addr_Type);
+ end Nonreentrant_Gethostbyaddr;
+
--------------------
-- Signalling_Fds --
--------------------
diff --git a/gcc/ada/libgnat/g-socthi.ads b/gcc/ada/libgnat/g-socthi.ads
index ef53e04..b759c7e 100644
--- a/gcc/ada/libgnat/g-socthi.ads
+++ b/gcc/ada/libgnat/g-socthi.ads
@@ -249,21 +249,21 @@ package GNAT.Sockets.Thin is
procedure Finalize;
private
- pragma Import (C, C_Bind, "bind");
+ pragma Inline (C_Bind);
pragma Import (C, C_Close, "close");
pragma Import (C, C_Gethostname, "gethostname");
- pragma Import (C, C_Getpeername, "getpeername");
- pragma Import (C, C_Getsockname, "getsockname");
- pragma Import (C, C_Getsockopt, "getsockopt");
+ pragma Inline (C_Getpeername);
+ pragma Inline (C_Getsockname);
+ pragma Inline (C_Getsockopt);
pragma Import (C, C_Listen, "listen");
pragma Import (C, C_Select, "select");
- pragma Import (C, C_Setsockopt, "setsockopt");
+ pragma Inline (C_Setsockopt);
pragma Import (C, C_Shutdown, "shutdown");
pragma Import (C, C_Socketpair, "socketpair");
pragma Import (C, C_System, "system");
pragma Import (C, Nonreentrant_Gethostbyname, "gethostbyname");
- pragma Import (C, Nonreentrant_Gethostbyaddr, "gethostbyaddr");
+ pragma Inline (Nonreentrant_Gethostbyaddr);
pragma Import (C, Nonreentrant_Getservbyname, "getservbyname");
pragma Import (C, Nonreentrant_Getservbyport, "getservbyport");