From ed2fe1a5b0cd2bde359e85d928fe2c01ab308cac Mon Sep 17 00:00:00 2001 From: Patsy Griffin Date: Mon, 20 May 2024 17:35:34 -0400 Subject: [PATCH] Improve test coverage for connect() Resolves: RHEL-32681 --- glibc-RHEL-32681-1.patch | 142 +++++++++++++++++++++++++++++++++++++++ glibc-RHEL-32681-2.patch | 66 ++++++++++++++++++ glibc.spec | 7 +- 3 files changed, 214 insertions(+), 1 deletion(-) create mode 100644 glibc-RHEL-32681-1.patch create mode 100644 glibc-RHEL-32681-2.patch diff --git a/glibc-RHEL-32681-1.patch b/glibc-RHEL-32681-1.patch new file mode 100644 index 0000000..c416a97 --- /dev/null +++ b/glibc-RHEL-32681-1.patch @@ -0,0 +1,142 @@ +commit 3a83f79024cc023a74c3892a1673542e8e972485 +Author: Sergey Kolosov +Date: Wed Apr 10 17:58:05 2024 +0200 + + socket: Add new test for connect + + This commit adds a simple bind/accept/connect test for an IPv4 TCP + connection to a local process via the loopback interface. + + Reviewed-by: Arjun Shankar + +diff -Nrup a/socket/Makefile b/socket/Makefile +--- a/socket/Makefile 2024-05-19 21:52:59.775055152 -0400 ++++ b/socket/Makefile 2024-05-19 22:05:27.717703460 -0400 +@@ -33,8 +33,9 @@ routines := accept bind connect getpeern + + tests := \ + tst-accept4 \ +- tst-sockopt \ + tst-cmsghdr \ ++ tst-connect \ ++ tst-sockopt \ + # tests + + tests-internal := \ +diff -Nrup a/socket/tst-connect.c b/socket/tst-connect.c +--- a/socket/tst-connect.c 1969-12-31 19:00:00.000000000 -0500 ++++ b/socket/tst-connect.c 2024-05-19 21:58:22.069058144 -0400 +@@ -0,0 +1,113 @@ ++/* Test the connect function. ++ Copyright (C) 2024 Free Software Foundation, Inc. ++ This file is part of the GNU C Library. ++ ++ The GNU C Library is free software; you can redistribute it and/or ++ modify it under the terms of the GNU Lesser General Public ++ License as published by the Free Software Foundation; either ++ version 2.1 of the License, or (at your option) any later version. ++ ++ The GNU C Library 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 ++ Lesser General Public License for more details. ++ ++ You should have received a copy of the GNU Lesser General Public ++ License along with the GNU C Library; if not, see ++ . */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++static struct sockaddr_in server_address; ++ ++int ++open_socket_inet_tcp (void) ++{ ++ int fd = socket (AF_INET, SOCK_STREAM, IPPROTO_TCP); ++ if (fd < 0) ++ { ++ if (errno == EAFNOSUPPORT) ++ FAIL_UNSUPPORTED ("The host does not support IPv4"); ++ else ++ FAIL_EXIT1 ("socket (AF_INET, SOCK_STREAM, IPPROTO_TCP): %m\n"); ++ } ++ return fd; ++} ++ ++static pid_t ++start_server (void) ++{ ++ server_address.sin_family = AF_INET; ++ server_address.sin_port = 0; ++ server_address.sin_addr.s_addr = htonl (INADDR_LOOPBACK); ++ ++ int server_sock = open_socket_inet_tcp (); ++ ++ xbind (server_sock, (struct sockaddr *) &server_address, ++ sizeof (server_address)); ++ ++ socklen_t sa_len = sizeof (server_address); ++ xgetsockname (server_sock, (struct sockaddr *) &server_address, &sa_len); ++ xlisten (server_sock, 5); ++ ++ pid_t my_pid = xfork (); ++ if (my_pid > 0) ++ { ++ xclose (server_sock); ++ return my_pid; ++ } ++ ++ struct sockaddr_in client_address; ++ socklen_t ca_len = sizeof (server_address); ++ int client_sock = xaccept (server_sock, (struct sockaddr *) &client_address, ++ &ca_len); ++ printf ("socket accepted %d\n", client_sock); ++ ++ _exit (0); ++} ++ ++static int ++do_test (void) ++{ ++ pid_t serv_pid; ++ struct sockaddr_in peer; ++ socklen_t peer_len; ++ ++ serv_pid = start_server (); ++ int client_sock = open_socket_inet_tcp (); ++ xconnect (client_sock, (const struct sockaddr *) &server_address, ++ sizeof (server_address)); ++ ++ /* A second connect with same arguments should fail with EISCONN. */ ++ int result = connect (client_sock, ++ (const struct sockaddr *) &server_address, ++ sizeof (server_address)); ++ if (result == 0 || errno != EISCONN) ++ FAIL_EXIT1 ("Second connect (%d), should fail with EISCONN: %m", ++ client_sock); ++ ++ peer_len = sizeof (peer); ++ xgetpeername (client_sock, (struct sockaddr *) &peer, &peer_len); ++ TEST_COMPARE (peer_len, sizeof (peer)); ++ TEST_COMPARE (peer.sin_port, server_address.sin_port); ++ TEST_COMPARE_BLOB (&peer.sin_addr, sizeof (peer.sin_addr), ++ &server_address.sin_addr, ++ sizeof (server_address.sin_addr)); ++ ++ int status; ++ xwaitpid (serv_pid, &status, 0); ++ TEST_COMPARE (status, 0); ++ ++ return 0; ++} ++ ++#include diff --git a/glibc-RHEL-32681-2.patch b/glibc-RHEL-32681-2.patch new file mode 100644 index 0000000..1f669ff --- /dev/null +++ b/glibc-RHEL-32681-2.patch @@ -0,0 +1,66 @@ +commit 6687a6e3f962759536a8019d31c68c1009ccd6eb +Author: Sergey Kolosov +Date: Wed Apr 10 17:58:04 2024 +0200 + + libsupport: Add xgetpeername + + The patch adds redirections for getpeername. + + Reviewed-by: Arjun Shankar + +diff -Nrup a/support/Makefile b/support/Makefile +--- a/support/Makefile 2024-05-19 23:27:12.379362736 -0400 ++++ b/support/Makefile 2024-05-19 23:29:28.668182089 -0400 +@@ -126,6 +126,7 @@ libsupport-routines = \ + xfork \ + xftruncate \ + xgetline \ ++ xgetpeername \ + xgetsockname \ + xlisten \ + xlseek \ +diff -Nrup a/support/xgetpeername.c b/support/xgetpeername.c +--- a/support/xgetpeername.c 1969-12-31 19:00:00.000000000 -0500 ++++ b/support/xgetpeername.c 2024-05-19 23:30:31.852561947 -0400 +@@ -0,0 +1,30 @@ ++/* getpeername with error checking. ++ Copyright (C) 2024 Free Software Foundation, Inc. ++ This file is part of the GNU C Library. ++ ++ The GNU C Library is free software; you can redistribute it and/or ++ modify it under the terms of the GNU Lesser General Public ++ License as published by the Free Software Foundation; either ++ version 2.1 of the License, or (at your option) any later version. ++ ++ The GNU C Library 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 ++ Lesser General Public License for more details. ++ ++ You should have received a copy of the GNU Lesser General Public ++ License along with the GNU C Library; if not, see ++ . */ ++ ++#include ++ ++#include ++#include ++#include ++ ++void ++xgetpeername (int fd, struct sockaddr *sa, socklen_t *plen) ++{ ++ if (getpeername (fd, sa, plen) != 0) ++ FAIL_EXIT1 ("getpeername (%d): %m", fd); ++} +diff -Nrup a/support/xsocket.h b/support/xsocket.h +--- a/support/xsocket.h 2021-08-01 21:33:43.000000000 -0400 ++++ b/support/xsocket.h 2024-05-19 23:31:24.541878715 -0400 +@@ -26,6 +26,7 @@ + int xsocket (int, int, int); + void xsetsockopt (int, int, int, const void *, socklen_t); + void xgetsockname (int, struct sockaddr *, socklen_t *); ++void xgetpeername (int, struct sockaddr *, socklen_t *); + void xconnect (int, const struct sockaddr *, socklen_t); + void xbind (int, const struct sockaddr *, socklen_t); + void xlisten (int, int); diff --git a/glibc.spec b/glibc.spec index 32db246..7e06d68 100644 --- a/glibc.spec +++ b/glibc.spec @@ -155,7 +155,7 @@ end \ Summary: The GNU libc libraries Name: glibc Version: %{glibcversion} -Release: 105%{?dist} +Release: 106%{?dist} # In general, GPLv2+ is used by programs, LGPLv2+ is used for # libraries. @@ -817,6 +817,8 @@ Patch580: glibc-RHEL-25531-2.patch Patch581: glibc-RHEL-25531-3.patch Patch582: glibc-RHEL-25531-4.patch Patch583: glibc-RHEL-25046.patch +Patch584: glibc-RHEL-32681-1.patch +Patch585: glibc-RHEL-32681-2.patch ############################################################################## # Continued list of core "glibc" package information: @@ -2975,6 +2977,9 @@ update_gconv_modules_cache () %endif %changelog +* Sun May 19 2024 Patsy Griffin - 2.34-106 +- Improve test coverage for connect() (RHEL-32681) + * Wed Apr 3 2024 DJ Delorie - 2.34-105 - x86-64: Save APX registers in ld.so trampoline (RHEL-25046)