[3/4] sunrpc: Test case for clnt_create "unix" buffer overflow (bug 22542)

Message ID 5e6f9d7240e55d438438d457f169132cf89fb8a0.1642148513.git.fweimer@redhat.com
State New
Headers show
Series
  • CVE-2022-23218, CVE-2022-23219: sunrpc buffer overflows
Related show

Commit Message

Adhemerval Zanella via Libc-alpha Jan. 14, 2022, 8:24 a.m.
From: Martin Sebor <msebor@redhat.com>


---
 sunrpc/Makefile       |  5 ++++-
 sunrpc/tst-bug22542.c | 44 +++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 48 insertions(+), 1 deletion(-)
 create mode 100644 sunrpc/tst-bug22542.c

-- 
2.34.1

Comments

Siddhesh Poyarekar Jan. 17, 2022, 3:31 a.m. | #1
On 14/01/2022 13:54, Florian Weimer via Libc-alpha wrote:
> From: Martin Sebor <msebor@redhat.com>

> 

> ---

>   sunrpc/Makefile       |  5 ++++-

>   sunrpc/tst-bug22542.c | 44 +++++++++++++++++++++++++++++++++++++++++++

>   2 files changed, 48 insertions(+), 1 deletion(-)

>   create mode 100644 sunrpc/tst-bug22542.c


LGTM.

Reviewed-by: Siddhesh Poyarekar <siddhesh@sourceware.org>


> 

> diff --git a/sunrpc/Makefile b/sunrpc/Makefile

> index 9a31fe48b9..183ef3dc55 100644

> --- a/sunrpc/Makefile

> +++ b/sunrpc/Makefile

> @@ -65,7 +65,8 @@ shared-only-routines = $(routines)

>   endif

>   

>   tests = tst-xdrmem tst-xdrmem2 test-rpcent tst-udp-error tst-udp-timeout \

> -  tst-udp-nonblocking

> +  tst-udp-nonblocking tst-bug22542

> +

>   xtests := tst-getmyaddr

>   

>   ifeq ($(have-thread-library),yes)

> @@ -110,6 +111,8 @@ $(objpfx)tst-udp-nonblocking: $(common-objpfx)linkobj/libc.so

>   $(objpfx)tst-udp-garbage: \

>     $(common-objpfx)linkobj/libc.so $(shared-thread-library)

>   

> +$(objpfx)tst-bug22542: $(common-objpfx)linkobj/libc.so

> +

>   else # !have-GLIBC_2.31

>   

>   routines = $(routines-for-nss)

> diff --git a/sunrpc/tst-bug22542.c b/sunrpc/tst-bug22542.c

> new file mode 100644

> index 0000000000..d6cd79787b

> --- /dev/null

> +++ b/sunrpc/tst-bug22542.c

> @@ -0,0 +1,44 @@

> +/* Test to verify that overlong hostname is rejected by clnt_create

> +   and doesn't cause a buffer overflow (bug  22542).

> +

> +   Copyright (C) 2022 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

> +   <http://www.gnu.org/licenses/>.  */

> +

> +#include <errno.h>

> +#include <rpc/clnt.h>

> +#include <string.h>

> +#include <support/check.h>

> +#include <sys/socket.h>

> +#include <sys/un.h>

> +

> +static int

> +do_test (void)

> +{

> +  /* Create an arbitrary hostname that's longer than fits in sun_path.  */

> +  char name [sizeof ((struct sockaddr_un*)0)->sun_path * 2];

> +  memset (name, 'x', sizeof name - 1);

> +  name [sizeof name - 1] = '\0';

> +

> +  errno = 0;

> +  CLIENT *clnt = clnt_create (name, 0, 0, "unix");

> +

> +  TEST_VERIFY (clnt == NULL);

> +  TEST_COMPARE (errno, EINVAL);

> +  return 0;

> +}

> +

> +#include <support/test-driver.c>
Siddhesh Poyarekar Jan. 17, 2022, 3:35 a.m. | #2
On 17/01/2022 09:01, Siddhesh Poyarekar wrote:
> On 14/01/2022 13:54, Florian Weimer via Libc-alpha wrote:

>> From: Martin Sebor <msebor@redhat.com>

>>

>> ---

>>   sunrpc/Makefile       |  5 ++++-

>>   sunrpc/tst-bug22542.c | 44 +++++++++++++++++++++++++++++++++++++++++++

>>   2 files changed, 48 insertions(+), 1 deletion(-)

>>   create mode 100644 sunrpc/tst-bug22542.c

> 

> LGTM.

> 

> Reviewed-by: Siddhesh Poyarekar <siddhesh@sourceware.org>


Oh wait...

> 

>>

>> diff --git a/sunrpc/Makefile b/sunrpc/Makefile

>> index 9a31fe48b9..183ef3dc55 100644

>> --- a/sunrpc/Makefile

>> +++ b/sunrpc/Makefile

>> @@ -65,7 +65,8 @@ shared-only-routines = $(routines)

>>   endif

>>   tests = tst-xdrmem tst-xdrmem2 test-rpcent tst-udp-error 

>> tst-udp-timeout \

>> -  tst-udp-nonblocking

>> +  tst-udp-nonblocking tst-bug22542

>> +

>>   xtests := tst-getmyaddr

>>   ifeq ($(have-thread-library),yes)

>> @@ -110,6 +111,8 @@ $(objpfx)tst-udp-nonblocking: 

>> $(common-objpfx)linkobj/libc.so

>>   $(objpfx)tst-udp-garbage: \

>>     $(common-objpfx)linkobj/libc.so $(shared-thread-library)

>> +$(objpfx)tst-bug22542: $(common-objpfx)linkobj/libc.so

>> +

>>   else # !have-GLIBC_2.31

>>   routines = $(routines-for-nss)

>> diff --git a/sunrpc/tst-bug22542.c b/sunrpc/tst-bug22542.c

>> new file mode 100644

>> index 0000000000..d6cd79787b

>> --- /dev/null

>> +++ b/sunrpc/tst-bug22542.c

>> @@ -0,0 +1,44 @@

>> +/* Test to verify that overlong hostname is rejected by clnt_create

>> +   and doesn't cause a buffer overflow (bug  22542).

>> +

>> +   Copyright (C) 2022 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

>> +   <http://www.gnu.org/licenses/>.  */

>> +

>> +#include <errno.h>

>> +#include <rpc/clnt.h>

>> +#include <string.h>

>> +#include <support/check.h>

>> +#include <sys/socket.h>

>> +#include <sys/un.h>

>> +

>> +static int

>> +do_test (void)

>> +{

>> +  /* Create an arbitrary hostname that's longer than fits in 

>> sun_path.  */

>> +  char name [sizeof ((struct sockaddr_un*)0)->sun_path * 2];

>> +  memset (name, 'x', sizeof name - 1);

>> +  name [sizeof name - 1] = '\0';

>> +

>> +  errno = 0;

>> +  CLIENT *clnt = clnt_create (name, 0, 0, "unix");


Does this link?  clnt_create doesn't have a default version in libc.so 
AFAICT.

>> +

>> +  TEST_VERIFY (clnt == NULL);

>> +  TEST_COMPARE (errno, EINVAL);

>> +  return 0;

>> +}

>> +

>> +#include <support/test-driver.c>

>
Adhemerval Zanella via Libc-alpha Jan. 17, 2022, 9:15 a.m. | #3
* Siddhesh Poyarekar:

> On 17/01/2022 09:01, Siddhesh Poyarekar wrote:

>> On 14/01/2022 13:54, Florian Weimer via Libc-alpha wrote:

>>> From: Martin Sebor <msebor@redhat.com>

>>>

>>> ---

>>>   sunrpc/Makefile       |  5 ++++-

>>>   sunrpc/tst-bug22542.c | 44 +++++++++++++++++++++++++++++++++++++++++++

>>>   2 files changed, 48 insertions(+), 1 deletion(-)

>>>   create mode 100644 sunrpc/tst-bug22542.c

>> LGTM.

>> Reviewed-by: Siddhesh Poyarekar <siddhesh@sourceware.org>

>

> Oh wait...

>

>> 

>>>

>>> diff --git a/sunrpc/Makefile b/sunrpc/Makefile

>>> index 9a31fe48b9..183ef3dc55 100644

>>> --- a/sunrpc/Makefile

>>> +++ b/sunrpc/Makefile

>>> @@ -65,7 +65,8 @@ shared-only-routines = $(routines)

>>>   endif

>>>   tests = tst-xdrmem tst-xdrmem2 test-rpcent tst-udp-error

>>> tst-udp-timeout \

>>> -  tst-udp-nonblocking

>>> +  tst-udp-nonblocking tst-bug22542

>>> +

>>>   xtests := tst-getmyaddr

>>>   ifeq ($(have-thread-library),yes)

>>> @@ -110,6 +111,8 @@ $(objpfx)tst-udp-nonblocking:

>>> $(common-objpfx)linkobj/libc.so

>>>   $(objpfx)tst-udp-garbage: \

>>>     $(common-objpfx)linkobj/libc.so $(shared-thread-library)

>>> +$(objpfx)tst-bug22542: $(common-objpfx)linkobj/libc.so

>>> +

>>>   else # !have-GLIBC_2.31

>>>   routines = $(routines-for-nss)

>>> diff --git a/sunrpc/tst-bug22542.c b/sunrpc/tst-bug22542.c

>>> new file mode 100644

>>> index 0000000000..d6cd79787b

>>> --- /dev/null

>>> +++ b/sunrpc/tst-bug22542.c

>>> @@ -0,0 +1,44 @@

>>> +/* Test to verify that overlong hostname is rejected by clnt_create

>>> +   and doesn't cause a buffer overflow (bug  22542).

>>> +

>>> +   Copyright (C) 2022 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

>>> +   <http://www.gnu.org/licenses/>.  */

>>> +

>>> +#include <errno.h>

>>> +#include <rpc/clnt.h>

>>> +#include <string.h>

>>> +#include <support/check.h>

>>> +#include <sys/socket.h>

>>> +#include <sys/un.h>

>>> +

>>> +static int

>>> +do_test (void)

>>> +{

>>> +  /* Create an arbitrary hostname that's longer than fits in

>>> sun_path.  */

>>> +  char name [sizeof ((struct sockaddr_un*)0)->sun_path * 2];

>>> +  memset (name, 'x', sizeof name - 1);

>>> +  name [sizeof name - 1] = '\0';

>>> +

>>> +  errno = 0;

>>> +  CLIENT *clnt = clnt_create (name, 0, 0, "unix");

>

> Does this link?  clnt_create doesn't have a default version in libc.so

> AFAICT.


It has in linkobj/libc.so:

$ eu-readelf --symbols=.dynsym linkobj/libc.so | grep clnt_create
 3126: 000387a0    465 FUNC    GLOBAL DEFAULT       14 clnt_create@@GLIBC_2.0

Thanks,
Florian
Siddhesh Poyarekar Jan. 17, 2022, 9:30 a.m. | #4
On 17/01/2022 14:45, Florian Weimer wrote:
> It has in linkobj/libc.so:

> 

> $ eu-readelf --symbols=.dynsym linkobj/libc.so | grep clnt_create

>   3126: 000387a0    465 FUNC    GLOBAL DEFAULT       14 clnt_create@@GLIBC_2.0


That's weird, shouldn't it be non-default given that it is deprecated? 
Why is it needed for internal linking?  For tests?

Siddhesh
Adhemerval Zanella via Libc-alpha Jan. 17, 2022, 9:32 a.m. | #5
* Siddhesh Poyarekar:

> On 17/01/2022 14:45, Florian Weimer wrote:

>> It has in linkobj/libc.so:

>> $ eu-readelf --symbols=.dynsym linkobj/libc.so | grep clnt_create

>>   3126: 000387a0    465 FUNC    GLOBAL DEFAULT       14 clnt_create@@GLIBC_2.0

>

> That's weird, shouldn't it be non-default given that it is deprecated?

> Why is it needed for internal linking?  For tests?


Yes.  linkobj/libc.so and libc.so are different.  It's a compatibility
symbol in libc.so.

Thanks,
Florian
Siddhesh Poyarekar Jan. 17, 2022, 9:42 a.m. | #6
On 17/01/2022 15:02, Florian Weimer wrote:
> * Siddhesh Poyarekar:

> 

>> On 17/01/2022 14:45, Florian Weimer wrote:

>>> It has in linkobj/libc.so:

>>> $ eu-readelf --symbols=.dynsym linkobj/libc.so | grep clnt_create

>>>    3126: 000387a0    465 FUNC    GLOBAL DEFAULT       14 clnt_create@@GLIBC_2.0

>>

>> That's weird, shouldn't it be non-default given that it is deprecated?

>> Why is it needed for internal linking?  For tests?

> 

> Yes.  linkobj/libc.so and libc.so are different.  It's a compatibility

> symbol in libc.so.


OK then.

Reviewed-by: Siddhesh Poyarekar <siddhesh@sourceware.org>

Patch

diff --git a/sunrpc/Makefile b/sunrpc/Makefile
index 9a31fe48b9..183ef3dc55 100644
--- a/sunrpc/Makefile
+++ b/sunrpc/Makefile
@@ -65,7 +65,8 @@  shared-only-routines = $(routines)
 endif
 
 tests = tst-xdrmem tst-xdrmem2 test-rpcent tst-udp-error tst-udp-timeout \
-  tst-udp-nonblocking
+  tst-udp-nonblocking tst-bug22542
+
 xtests := tst-getmyaddr
 
 ifeq ($(have-thread-library),yes)
@@ -110,6 +111,8 @@  $(objpfx)tst-udp-nonblocking: $(common-objpfx)linkobj/libc.so
 $(objpfx)tst-udp-garbage: \
   $(common-objpfx)linkobj/libc.so $(shared-thread-library)
 
+$(objpfx)tst-bug22542: $(common-objpfx)linkobj/libc.so
+
 else # !have-GLIBC_2.31
 
 routines = $(routines-for-nss)
diff --git a/sunrpc/tst-bug22542.c b/sunrpc/tst-bug22542.c
new file mode 100644
index 0000000000..d6cd79787b
--- /dev/null
+++ b/sunrpc/tst-bug22542.c
@@ -0,0 +1,44 @@ 
+/* Test to verify that overlong hostname is rejected by clnt_create
+   and doesn't cause a buffer overflow (bug  22542).
+
+   Copyright (C) 2022 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
+   <http://www.gnu.org/licenses/>.  */
+
+#include <errno.h>
+#include <rpc/clnt.h>
+#include <string.h>
+#include <support/check.h>
+#include <sys/socket.h>
+#include <sys/un.h>
+
+static int
+do_test (void)
+{
+  /* Create an arbitrary hostname that's longer than fits in sun_path.  */
+  char name [sizeof ((struct sockaddr_un*)0)->sun_path * 2];
+  memset (name, 'x', sizeof name - 1);
+  name [sizeof name - 1] = '\0';
+
+  errno = 0;
+  CLIENT *clnt = clnt_create (name, 0, 0, "unix");
+
+  TEST_VERIFY (clnt == NULL);
+  TEST_COMPARE (errno, EINVAL);
+  return 0;
+}
+
+#include <support/test-driver.c>