diff options
author | charlet <charlet@138bc75d-0d04-0410-961f-82ee72b054a4> | 2007-04-06 09:15:09 +0000 |
---|---|---|
committer | charlet <charlet@138bc75d-0d04-0410-961f-82ee72b054a4> | 2007-04-06 09:15:09 +0000 |
commit | 232e4d04f0263022b1379a7886e28e7f082f7eb8 (patch) | |
tree | d2a9f2de1b4f8ce5a655a929362077213fa220da /gcc/ada/g-socket.adb | |
parent | 32c07c22100b9a6f342e6a5825ac36b1b72d036b (diff) | |
download | gcc-232e4d04f0263022b1379a7886e28e7f082f7eb8.tar.gz |
2007-04-06 Thomas Quinot <quinot@adacore.com>
Pat Rogers <rogers@adacore.com>
Pascal Obry <obry@adacore.com>
* g-stsifd-sockets.adb: New file.
* g-socthi.ads, g-socket.adb, g-socthi-vxworks.adb,
g-socthi-vxworks.ads, g-socthi-mingw.ads, g-socthi-vms.ads,
g-socthi-vms.adb: Move signalling
fd management to a nested package, so that they can conveniently be
moved to a subunit that is shared across Windows, VMS, and VxWorks
(Ada implementation) or completed with imported bodies from socket.c
(UNIX case).
(Read_Signalling_Fd, Write_Signalling_Fd, Create_Signalling_Fds): New
subprograms.
(Check_Selector): Use Read_Signalling_Fd to read and discard data from
the signalling file descriptor.
(Abort_Selector): Use Write_Signalling_Fd to write dummy data to the
signalling file descriptor.
(Create_Selector): Use new C-imported subprogram Create_Signalling_Fds
instead of creating a pair of sockets for signalling here.
* g-socthi.adb: Ditto.
Set the runtime process to ignore SIGPIPEs on platforms that support
neither SO_NOSIGPIPE nor MSG_NOSIGNAL functionality.
* g-socthi-mingw.adb: Ditto.
(WS_Version): Use Windows 2.2.
Use Winsock 2.2 (instead of 1.1) for the GNAT.Socket API.
* g-soliop-mingw.ads: Link with ws2_32 for Windows 2.x support.
Use Winsock 2.2 (instead of 1.1) for the GNAT.Socket API.
* Makefile.in: New libgnat pair g-stsifd.adb<g-stsifd-sockets.adb.
added GNAT byte swapping facility
Update FreeBSD THREADSLIB from -lc_r to -lpthread, for FreeBSD 6.
* g-bytswa.adb, g-bytswa-x86.adb, g-bytswa.ads: New files.
* socket.c (__gnat_read_signalling_fd, __gnat_write_controlling_fd):
New subprograms.
(__gnat_create_signalling_fds): New subprogram.
Set the runtime process to ignore SIGPIPEs on platforms that support
neither SO_NOSIGPIPE nor MSG_NOSIGNAL functionality.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@123542 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/ada/g-socket.adb')
-rw-r--r-- | gcc/ada/g-socket.adb | 122 |
1 files changed, 17 insertions, 105 deletions
diff --git a/gcc/ada/g-socket.adb b/gcc/ada/g-socket.adb index 01765a70715..2773b7ab036 100644 --- a/gcc/ada/g-socket.adb +++ b/gcc/ada/g-socket.adb @@ -236,14 +236,13 @@ package body GNAT.Sockets is -------------------- procedure Abort_Selector (Selector : Selector_Type) is - Buf : aliased Character := ASCII.NUL; Res : C.int; begin - -- Send an empty array to unblock C select system call + -- Send one byte to unblock select system call + + Res := Signalling_Fds.Write (C.int (Selector.W_Sig_Socket)); - Res := C_Send (C.int (Selector.W_Sig_Socket), Buf'Address, 1, - Constants.MSG_Forced_Flags); if Res = Failure then Raise_Socket_Error (Socket_Errno); end if; @@ -454,16 +453,11 @@ package body GNAT.Sockets is if Is_Set (RSet, RSig) then Clear (RSet, RSig); - declare - Buf : Character; - - begin - Res := C_Recv (C.int (RSig), Buf'Address, 1, 0); + Res := Signalling_Fds.Read (C.int (RSig)); - if Res = Failure then - Raise_Socket_Error (Socket_Errno); - end if; - end; + if Res = Failure then + Raise_Socket_Error (Socket_Errno); + end if; Status := Aborted; @@ -674,105 +668,23 @@ package body GNAT.Sockets is --------------------- procedure Create_Selector (Selector : out Selector_Type) is - S0 : C.int; - S1 : C.int; - S2 : C.int; - Res : C.int; - Sin : aliased Sockaddr_In; - Len : aliased C.int := Sin'Size / 8; - Err : Integer; + Two_Fds : aliased Fd_Pair; + Res : C.int; begin - -- We open two signalling sockets. One of them is used to send data to - -- the other, which is included in a C_Select socket set. The - -- communication is used to force the call to C_Select to complete, and + -- We open two signalling file descriptors. One of them is used to send + -- data to the other, which is included in a C_Select socket set. The + -- communication is used to force a call to C_Select to complete, and -- the waiting task to resume its execution. - -- Create a listening socket - - S0 := C_Socket (Constants.AF_INET, Constants.SOCK_STREAM, 0); - - if S0 = Failure then - Raise_Socket_Error (Socket_Errno); - end if; - - -- Bind the socket to any unused port on localhost - - Sin.Sin_Addr.S_B1 := 127; - Sin.Sin_Addr.S_B2 := 0; - Sin.Sin_Addr.S_B3 := 0; - Sin.Sin_Addr.S_B4 := 1; - Sin.Sin_Port := 0; - - Res := C_Bind (S0, Sin'Address, Len); - - if Res = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Raise_Socket_Error (Err); - end if; - - -- Get the port used by the socket - - Res := C_Getsockname (S0, Sin'Address, Len'Access); - - if Res = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Raise_Socket_Error (Err); - end if; - - -- Set backlog to 1 to guarantee that exactly one call to connect(2) - -- can succeed. - - Res := C_Listen (S0, 1); - - if Res = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Raise_Socket_Error (Err); - end if; - - S1 := C_Socket (Constants.AF_INET, Constants.SOCK_STREAM, 0); - - if S1 = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Raise_Socket_Error (Err); - end if; - - -- Do a connect and accept the connection - - Res := C_Connect (S1, Sin'Address, Len); - - if Res = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Res := C_Close (S1); - Raise_Socket_Error (Err); - end if; - - -- Since the call to connect(2) has suceeded and the backlog limit on - -- the listening socket is 1, we know that there is now exactly one - -- pending connection on S0, which is the one from S1. - - S2 := C_Accept (S0, Sin'Address, Len'Access); - - if S2 = Failure then - Err := Socket_Errno; - Res := C_Close (S0); - Res := C_Close (S1); - Raise_Socket_Error (Err); - end if; - - Res := C_Close (S0); + Res := Signalling_Fds.Create (Two_Fds'Access); if Res = Failure then Raise_Socket_Error (Socket_Errno); end if; - Selector.R_Sig_Socket := Socket_Type (S1); - Selector.W_Sig_Socket := Socket_Type (S2); + Selector.R_Sig_Socket := Socket_Type (Two_Fds (Read_End)); + Selector.W_Sig_Socket := Socket_Type (Two_Fds (Write_End)); end Create_Selector; ------------------- @@ -1073,7 +985,7 @@ package body GNAT.Sockets is is use type C.unsigned_char; - V8 : aliased Two_Int; + V8 : aliased Two_Ints; V4 : aliased C.int; V1 : aliased C.unsigned_char; VT : aliased Timeval; @@ -1899,7 +1811,7 @@ package body GNAT.Sockets is Level : Level_Type := Socket_Level; Option : Option_Type) is - V8 : aliased Two_Int; + V8 : aliased Two_Ints; V4 : aliased C.int; V1 : aliased C.unsigned_char; VT : aliased Timeval; |