Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in / Register
Toggle navigation
L
libzmq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Packages
Packages
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
submodule
libzmq
Commits
12a2f817
Unverified
Commit
12a2f817
authored
Apr 27, 2020
by
Luca Boccassi
Committed by
GitHub
Apr 27, 2020
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #3885 from bluca/fuzzers
Problem: no fuzz testing
parents
b56195e9
96787c35
Hide whitespace changes
Inline
Side-by-side
Showing
24 changed files
with
962 additions
and
341 deletions
+962
-341
Makefile.am
Makefile.am
+111
-0
configure.ac
configure.ac
+19
-0
CMakeLists.txt
tests/CMakeLists.txt
+4
-1
test_bind_curve_fuzzer.cpp
tests/test_bind_curve_fuzzer.cpp
+82
-0
test_bind_fuzzer.cpp
tests/test_bind_fuzzer.cpp
+71
-0
test_bind_null_fuzzer.cpp
tests/test_bind_null_fuzzer.cpp
+76
-0
test_connect_curve_fuzzer.cpp
tests/test_connect_curve_fuzzer.cpp
+85
-0
test_connect_fuzzer.cpp
tests/test_connect_fuzzer.cpp
+71
-0
test_connect_null_fuzzer.cpp
tests/test_connect_null_fuzzer.cpp
+80
-0
test_heartbeats.cpp
tests/test_heartbeats.cpp
+11
-30
test_mock_pub_sub.cpp
tests/test_mock_pub_sub.cpp
+13
-44
test_security_curve.cpp
tests/test_security_curve.cpp
+11
-51
test_security_gssapi.cpp
tests/test_security_gssapi.cpp
+1
-28
test_security_null.cpp
tests/test_security_null.cpp
+1
-18
test_security_plain.cpp
tests/test_security_plain.cpp
+1
-31
test_shutdown_stress_tipc.cpp
tests/test_shutdown_stress_tipc.cpp
+5
-6
test_socks.cpp
tests/test_socks.cpp
+4
-15
test_stream_exceeds_buffer.cpp
tests/test_stream_exceeds_buffer.cpp
+1
-16
test_use_fd.cpp
tests/test_use_fd.cpp
+9
-89
test_z85_decode_fuzzer.cpp
tests/test_z85_decode_fuzzer.cpp
+75
-0
testutil.cpp
tests/testutil.cpp
+146
-0
testutil.hpp
tests/testutil.hpp
+49
-0
testutil_unity.cpp
tests/testutil_unity.cpp
+16
-8
testutil_unity.hpp
tests/testutil_unity.hpp
+20
-4
No files found.
Makefile.am
View file @
12a2f817
...
...
@@ -1106,6 +1106,117 @@ tests_test_disconnect_msg_LDADD = ${TESTUTIL_LIBS} src/libzmq.la
tests_test_disconnect_msg_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
endif
if
FUZZING_ENGINE_LIB
fuzzer_apps
=
tests/test_bind_null_fuzzer
\
tests/test_connect_null_fuzzer
\
tests/test_bind_fuzzer
\
tests/test_connect_fuzzer
tests_test_bind_null_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_bind_null_fuzzer_SOURCES
=
tests/test_bind_null_fuzzer.cpp
tests_test_bind_null_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_bind_null_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_bind_null_fuzzer_CXXFLAGS
=
-std
=
c++11
tests_test_connect_null_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_connect_null_fuzzer_SOURCES
=
tests/test_connect_null_fuzzer.cpp
tests_test_connect_null_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_connect_null_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_null_fuzzer_CXXFLAGS
=
-std
=
c++11
tests_test_bind_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_bind_fuzzer_SOURCES
=
tests/test_bind_fuzzer.cpp
tests_test_bind_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_bind_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_bind_fuzzer_CXXFLAGS
=
-std
=
c++11
tests_test_connect_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_connect_fuzzer_SOURCES
=
tests/test_connect_fuzzer.cpp
tests_test_connect_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_connect_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_fuzzer_CXXFLAGS
=
-std
=
c++11
if
HAVE_CURVE
fuzzer_apps
+=
tests/test_bind_curve_fuzzer
\
tests/test_connect_curve_fuzzer
\
tests/test_z85_decode_fuzzer
tests_test_bind_curve_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_bind_curve_fuzzer_SOURCES
=
tests/test_bind_curve_fuzzer.cpp
tests_test_bind_curve_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_bind_curve_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_bind_curve_fuzzer_CXXFLAGS
=
-std
=
c++11
tests_test_connect_curve_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_connect_curve_fuzzer_SOURCES
=
tests/test_connect_curve_fuzzer.cpp
tests_test_connect_curve_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_connect_curve_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_curve_fuzzer_CXXFLAGS
=
-std
=
c++11
tests_test_z85_decode_fuzzer_DEPENDENCIES
=
src/libzmq.la
tests_test_z85_decode_fuzzer_SOURCES
=
tests/test_z85_decode_fuzzer.cpp
tests_test_z85_decode_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
${
FUZZING_ENGINE_LIB
}
\
$(top_builddir)
/src/.libs/libzmq.a
\
${
src_libzmq_la_LIBADD
}
tests_test_z85_decode_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_z85_decode_fuzzer_CXXFLAGS
=
-std
=
c++11
endif
FUZZINGdir
=
${
prefix
}
/
${
FUZZING_INSTALLDIR
}
FUZZING_PROGRAMS
=
${
fuzzer_apps
}
else
test_apps
+=
tests/test_bind_null_fuzzer
\
tests/test_connect_null_fuzzer
\
tests/test_bind_fuzzer
\
tests/test_connect_fuzzer
tests_test_bind_null_fuzzer_SOURCES
=
tests/test_bind_null_fuzzer.cpp
tests_test_bind_null_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_bind_null_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_null_fuzzer_SOURCES
=
tests/test_connect_null_fuzzer.cpp
tests_test_connect_null_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_connect_null_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_bind_fuzzer_SOURCES
=
tests/test_bind_fuzzer.cpp
tests_test_bind_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_bind_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_fuzzer_SOURCES
=
tests/test_connect_fuzzer.cpp
tests_test_connect_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_connect_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
if
HAVE_CURVE
test_apps
+=
tests/test_bind_curve_fuzzer
\
tests/test_connect_curve_fuzzer
\
tests/test_z85_decode_fuzzer
tests_test_bind_curve_fuzzer_SOURCES
=
tests/test_bind_curve_fuzzer.cpp
tests_test_bind_curve_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_bind_curve_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_connect_curve_fuzzer_SOURCES
=
tests/test_connect_curve_fuzzer.cpp
tests_test_connect_curve_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_connect_curve_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
tests_test_z85_decode_fuzzer_SOURCES
=
tests/test_z85_decode_fuzzer.cpp
tests_test_z85_decode_fuzzer_LDADD
=
${
TESTUTIL_LIBS
}
src/libzmq.la
tests_test_z85_decode_fuzzer_CPPFLAGS
=
${
TESTUTIL_CPPFLAGS
}
endif
endif
if
ENABLE_STATIC
# unit tests - these include individual source files and test the internal functions
test_apps
+=
\
...
...
configure.ac
View file @
12a2f817
...
...
@@ -1005,6 +1005,25 @@ AM_CONDITIONAL([WITH_CLANG_FORMAT], [$WITH_CLANG_FORMAT])
# unittests will not build without the static libzmq.a
AM_CONDITIONAL(ENABLE_STATIC, test "x$enable_static" = "xyes")
# build using a fuzzing engine - fuzzers will be built separately and statically
AC_ARG_WITH([fuzzing-engine], [AS_HELP_STRING([--with-fuzzing-engine],
[build libzmq with an exernal fuzzing engine [default=no]])],
[have_fuzzing_engine_ext=$withval],
[have_fuzzing_engine_ext=no])
AC_ARG_WITH([fuzzing-installdir],
AS_HELP_STRING([--with-fuzzing-installdir=PATH],
[Path where to install fuzzer binaries]),
[fuzzing_installdir="$withval"])
if test "x$have_fuzzing_engine_ext" != "xno" && test "x$fuzzing_installdir" != "x" && test "x$enable_static" = "xyes"; then
FUZZING_ENGINE_LIB="${have_fuzzing_engine_ext}"
FUZZING_INSTALLDIR="${fuzzing_installdir}"
AC_SUBST(FUZZING_ENGINE_LIB)
AC_SUBST(FUZZING_INSTALLDIR)
AC_DEFINE(ZMQ_USE_FUZZING_ENGINE, 1, [fuzz tests will be built with fuzzing engine])
fi
AM_CONDITIONAL(FUZZING_ENGINE_LIB, test "x$FUZZING_ENGINE_LIB" != "x")
# clang 6 has a warning that does not make sense on multi-platform code
AC_LANG_PUSH([C])
AX_CHECK_COMPILE_FLAG([-Wno-tautological-constant-compare],
...
...
tests/CMakeLists.txt
View file @
12a2f817
...
...
@@ -75,11 +75,14 @@ set(tests
test_mock_pub_sub
)
if
(
NOT WIN32
)
list
(
APPEND tests test_security_gssapi test_socks
)
list
(
APPEND tests test_security_gssapi test_socks
test_connect_null_fuzzer test_bind_null_fuzzer test_connect_fuzzer test_bind_fuzzer
)
endif
()
if
(
ZMQ_HAVE_CURVE
)
list
(
APPEND tests test_security_curve
)
if
(
NOT WIN32
)
list
(
APPEND tests test_connect_curve_fuzzer test_bind_curve_fuzzer test_z85_decode_fuzzer
)
endif
()
endif
()
option
(
ENABLE_CAPSH
"Run tests that require sudo and capsh (for cap_net_admin)"
OFF
)
...
...
tests/test_bind_curve_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include "testutil.hpp"
#include "testutil_security.hpp"
// Test that the ZMTP engine handles invalid handshake when binding
// https://rfc.zeromq.org/spec/37/
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
void
*
handler
;
void
*
zap_thread
;
void
*
server
;
void
*
server_mon
;
char
my_endpoint
[
MAX_SOCKET_STRING
];
setup_test_context
();
setup_testutil_security_curve
();
setup_context_and_server_side
(
&
handler
,
&
zap_thread
,
&
server
,
&
server_mon
,
my_endpoint
);
fd_t
client
=
connect_socket
(
my_endpoint
);
for
(
ssize_t
sent
=
0
;
size
>
0
&&
(
sent
!=
-
1
||
errno
==
EINTR
);
size
-=
sent
>
0
?
sent
:
0
,
data
+=
sent
>
0
?
sent
:
0
)
sent
=
send
(
client
,
(
const
char
*
)
data
,
size
,
MSG_NOSIGNAL
);
msleep
(
250
);
close
(
client
);
shutdown_context_and_server_side
(
zap_thread
,
server
,
server_mon
,
handler
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_bind_curve_fuzzer
()
{
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
zmtp_greeting_curve
,
sizeof
(
zmtp_greeting_curve
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_bind_curve_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_bind_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include <string>
#include "testutil.hpp"
#include "testutil_unity.hpp"
// Test that zmq_bind can handle malformed strings
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
setup_test_context
();
std
::
string
my_endpoint
(
reinterpret_cast
<
const
char
*>
(
data
),
size
);
void
*
socket
=
test_context_socket
(
ZMQ_PUB
);
zmq_bind
(
socket
,
my_endpoint
.
c_str
());
test_context_socket_close_zero_linger
(
socket
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_bind_fuzzer
()
{
uint8_t
buffer
[
32
]
=
{
0
};
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
buffer
,
sizeof
(
buffer
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_bind_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_bind_null_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include "testutil.hpp"
#include "testutil_unity.hpp"
// Test that the ZMTP engine handles invalid handshake when binding
// https://rfc.zeromq.org/spec/37/
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
setup_test_context
();
char
my_endpoint
[
MAX_SOCKET_STRING
];
void
*
server
=
test_context_socket
(
ZMQ_PUB
);
bind_loopback_ipv4
(
server
,
my_endpoint
,
sizeof
(
my_endpoint
));
fd_t
client
=
connect_socket
(
my_endpoint
);
for
(
ssize_t
sent
=
0
;
size
>
0
&&
(
sent
!=
-
1
||
errno
==
EINTR
);
size
-=
sent
>
0
?
sent
:
0
,
data
+=
sent
>
0
?
sent
:
0
)
sent
=
send
(
client
,
(
const
char
*
)
data
,
size
,
MSG_NOSIGNAL
);
msleep
(
250
);
close
(
client
);
test_context_socket_close_zero_linger
(
server
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_bind_null_fuzzer
()
{
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
zmtp_greeting_null
,
sizeof
(
zmtp_greeting_null
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_bind_null_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_connect_curve_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include "testutil.hpp"
#include "testutil_security.hpp"
// Test that the ZMTP engine handles invalid handshake when connecting
// https://rfc.zeromq.org/spec/37/
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
setup_test_context
();
setup_testutil_security_curve
();
char
my_endpoint
[
MAX_SOCKET_STRING
];
fd_t
server
=
bind_socket_resolve_port
(
"127.0.0.1"
,
"0"
,
my_endpoint
);
curve_client_data_t
curve_client_data
=
{
valid_server_public
,
valid_client_public
,
valid_client_secret
};
void
*
client_mon
;
void
*
client
=
create_and_connect_client
(
my_endpoint
,
socket_config_curve_client
,
&
curve_client_data
,
&
client_mon
);
fd_t
server_accept
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
accept
(
server
,
NULL
,
NULL
));
for
(
ssize_t
sent
=
0
;
size
>
0
&&
(
sent
!=
-
1
||
errno
==
EINTR
);
size
-=
sent
>
0
?
sent
:
0
,
data
+=
sent
>
0
?
sent
:
0
)
sent
=
send
(
server_accept
,
(
const
char
*
)
data
,
size
,
MSG_NOSIGNAL
);
msleep
(
250
);
close
(
server_accept
);
close
(
server
);
test_context_socket_close_zero_linger
(
client
);
test_context_socket_close_zero_linger
(
client_mon
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_connect_curve_fuzzer
()
{
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
zmtp_greeting_curve
,
sizeof
(
zmtp_greeting_curve
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_connect_curve_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_connect_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include <string>
#include "testutil.hpp"
#include "testutil_unity.hpp"
// Test that zmq_connect can handle malformed strings
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
setup_test_context
();
std
::
string
my_endpoint
(
reinterpret_cast
<
const
char
*>
(
data
),
size
);
void
*
socket
=
test_context_socket
(
ZMQ_PUB
);
zmq_connect
(
socket
,
my_endpoint
.
c_str
());
test_context_socket_close_zero_linger
(
socket
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_connect_fuzzer
()
{
uint8_t
buffer
[
32
]
=
{
0
};
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
buffer
,
sizeof
(
buffer
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_connect_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_connect_null_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include "testutil.hpp"
#include "testutil_unity.hpp"
// Test that the ZMTP engine handles invalid handshake when connecting
// https://rfc.zeromq.org/spec/37/
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
setup_test_context
();
char
my_endpoint
[
MAX_SOCKET_STRING
];
fd_t
server
=
bind_socket_resolve_port
(
"127.0.0.1"
,
"0"
,
my_endpoint
);
void
*
client
=
test_context_socket
(
ZMQ_PUB
);
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_connect
(
client
,
my_endpoint
));
fd_t
server_accept
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
accept
(
server
,
NULL
,
NULL
));
for
(
ssize_t
sent
=
0
;
size
>
0
&&
(
sent
!=
-
1
||
errno
==
EINTR
);
size
-=
sent
>
0
?
sent
:
0
,
data
+=
sent
>
0
?
sent
:
0
)
sent
=
send
(
server_accept
,
(
const
char
*
)
data
,
size
,
MSG_NOSIGNAL
);
msleep
(
250
);
close
(
server_accept
);
close
(
server
);
test_context_socket_close_zero_linger
(
client
);
teardown_test_context
();
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_connect_null_fuzzer
()
{
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
zmtp_greeting_null
,
sizeof
(
zmtp_greeting_null
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_connect_null_fuzzer
);
return
UNITY_END
();
}
#endif
tests/test_heartbeats.cpp
View file @
12a2f817
...
...
@@ -91,29 +91,24 @@ static void recv_with_retry (raw_socket fd_, char *buffer_, int bytes_)
static
void
mock_handshake
(
raw_socket
fd_
,
int
mock_ping_
)
{
const
uint8_t
zmtp_greeting
[
33
]
=
{
0xff
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0x7f
,
3
,
0
,
'N'
,
'U'
,
'L'
,
'L'
,
0
};
char
buffer
[
128
];
memset
(
buffer
,
0
,
sizeof
(
buffer
));
memcpy
(
buffer
,
zmtp_greeting
,
sizeof
(
zmtp_greeting
));
memcpy
(
buffer
,
zmtp_greeting
_null
,
sizeof
(
zmtp_greeting_null
));
int
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
buffer
,
64
,
0
));
TEST_ASSERT_EQUAL_INT
(
64
,
rc
);
int
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
buffer
,
sizeof
(
zmtp_greeting_null
),
0
));
TEST_ASSERT_EQUAL_INT
(
sizeof
(
zmtp_greeting_null
),
rc
);
recv_with_retry
(
fd_
,
buffer
,
64
);
const
uint8_t
zmtp_ready
[
43
]
=
{
4
,
41
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
6
,
'D'
,
'E'
,
'A'
,
'L'
,
'E'
,
'R'
,
8
,
'I'
,
'd'
,
'e'
,
'n'
,
't'
,
'i'
,
't'
,
'y'
,
0
,
0
,
0
,
0
};
recv_with_retry
(
fd_
,
buffer
,
sizeof
(
zmtp_greeting_null
));
memset
(
buffer
,
0
,
sizeof
(
buffer
));
memcpy
(
buffer
,
zmtp_ready
,
43
);
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
buffer
,
43
,
0
));
TEST_ASSERT_EQUAL_INT
(
43
,
rc
);
memcpy
(
buffer
,
zmtp_ready_dealer
,
sizeof
(
zmtp_ready_dealer
));
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
buffer
,
sizeof
(
zmtp_ready_dealer
),
0
));
TEST_ASSERT_EQUAL_INT
(
sizeof
(
zmtp_ready_dealer
),
rc
);
// greeting
recv_with_retry
(
fd_
,
buffer
,
43
);
recv_with_retry
(
fd_
,
buffer
,
sizeof
(
zmtp_ready_dealer
)
);
if
(
mock_ping_
)
{
// test PING context - should be replicated in the PONG
...
...
@@ -226,21 +221,7 @@ static void test_heartbeat_timeout (int server_type_, int mock_ping_)
prep_server_socket
(
!
mock_ping_
,
0
,
&
server
,
&
server_mon
,
my_endpoint
,
MAX_SOCKET_STRING
,
server_type_
);
struct
sockaddr_in
ip4addr
;
raw_socket
s
;
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
atoi
(
strrchr
(
my_endpoint
,
':'
)
+
1
));
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
connect
(
s
,
(
struct
sockaddr
*
)
&
ip4addr
,
sizeof
ip4addr
));
TEST_ASSERT_GREATER_THAN_INT
(
-
1
,
rc
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// Mock a ZMTP 3 client so we can forcibly time out a connection
mock_handshake
(
s
,
mock_ping_
);
...
...
tests/test_mock_pub_sub.cpp
View file @
12a2f817
...
...
@@ -19,17 +19,6 @@
#include "testutil.hpp"
#include "testutil_unity.hpp"
#if defined(ZMQ_HAVE_WINDOWS)
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdexcept>
#define close closesocket
typedef
SOCKET
raw_socket
;
#else
#include <arpa/inet.h>
#include <unistd.h>
typedef
int
raw_socket
;
#endif
#include <stdlib.h>
#include <string.h>
...
...
@@ -67,7 +56,7 @@ static int get_monitor_event (void *monitor_)
return
-
1
;
}
static
void
recv_with_retry
(
raw_socke
t
fd_
,
char
*
buffer_
,
int
bytes_
)
static
void
recv_with_retry
(
fd_
t
fd_
,
char
*
buffer_
,
int
bytes_
)
{
int
received
=
0
;
while
(
true
)
{
...
...
@@ -81,13 +70,11 @@ static void recv_with_retry (raw_socket fd_, char *buffer_, int bytes_)
}
}
static
void
mock_handshake
(
raw_socke
t
fd_
,
bool
sub_command
,
bool
mock_pub
)
static
void
mock_handshake
(
fd_
t
fd_
,
bool
sub_command
,
bool
mock_pub
)
{
const
uint8_t
zmtp_greeting
[
33
]
=
{
0xff
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0x7f
,
3
,
0
,
'N'
,
'U'
,
'L'
,
'L'
,
0
};
char
buffer
[
128
];
memset
(
buffer
,
0
,
sizeof
(
buffer
));
memcpy
(
buffer
,
zmtp_greeting
,
sizeof
(
zmtp_greeting
));
memcpy
(
buffer
,
zmtp_greeting
_null
,
sizeof
(
zmtp_greeting_null
));
// Mock ZMTP 3.1 which uses commands
if
(
sub_command
)
{
...
...
@@ -99,24 +86,20 @@ static void mock_handshake (raw_socket fd_, bool sub_command, bool mock_pub)
recv_with_retry
(
fd_
,
buffer
,
64
);
if
(
!
mock_pub
)
{
const
uint8_t
zmtp_ready
[
27
]
=
{
4
,
25
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
3
,
'S'
,
'U'
,
'B'
};
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
(
const
char
*
)
zmtp_ready
,
27
,
0
));
TEST_ASSERT_EQUAL_INT
(
27
,
rc
);
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
(
const
char
*
)
zmtp_ready_sub
,
sizeof
(
zmtp_ready_sub
),
0
));
TEST_ASSERT_EQUAL_INT
(
sizeof
(
zmtp_ready_sub
),
rc
);
}
else
{
const
uint8_t
zmtp_ready
[
28
]
=
{
4
,
26
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
4
,
'X'
,
'P'
,
'U'
,
'B'
};
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
(
const
char
*
)
zmtp_ready
,
28
,
0
));
TEST_ASSERT_EQUAL_INT
(
28
,
rc
);
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
send
(
fd_
,
(
const
char
*
)
zmtp_ready_xpub
,
sizeof
(
zmtp_ready_xpub
),
0
));
TEST_ASSERT_EQUAL_INT
(
sizeof
(
zmtp_ready_xpub
),
rc
);
}
// greeting - XPUB has one extra byte
memset
(
buffer
,
0
,
sizeof
(
buffer
));
recv_with_retry
(
fd_
,
buffer
,
mock_pub
?
27
:
28
);
recv_with_retry
(
fd_
,
buffer
,
mock_pub
?
sizeof
(
zmtp_ready_sub
)
:
sizeof
(
zmtp_ready_xpub
));
}
static
void
prep_server_socket
(
void
**
server_out_
,
...
...
@@ -158,21 +141,7 @@ static void test_mock_pub_sub (bool sub_command_, bool mock_pub_)
prep_server_socket
(
&
server
,
&
server_mon
,
my_endpoint
,
MAX_SOCKET_STRING
,
mock_pub_
?
ZMQ_SUB
:
ZMQ_XPUB
);
struct
sockaddr_in
ip4addr
;
raw_socket
s
;
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
atoi
(
strrchr
(
my_endpoint
,
':'
)
+
1
));
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
connect
(
s
,
(
struct
sockaddr
*
)
&
ip4addr
,
sizeof
ip4addr
));
TEST_ASSERT_GREATER_THAN_INT
(
-
1
,
rc
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// Mock a ZMTP 3 client so we can forcibly try sub commands
mock_handshake
(
s
,
sub_command_
,
mock_pub_
);
...
...
tests/test_security_curve.cpp
View file @
12a2f817
...
...
@@ -47,17 +47,6 @@
#include "testutil.hpp"
#include "testutil_security.hpp"
#if defined(ZMQ_HAVE_WINDOWS)
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdexcept>
#define close closesocket
#else
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#endif
#include <unity.h>
#include "../src/tweetnacl.h"
...
...
@@ -223,34 +212,10 @@ void test_curve_security_with_plain_client_credentials ()
expect_zmtp_mechanism_mismatch
(
client
,
my_endpoint
,
server
,
server_mon
);
}
fd_t
connect_vanilla_socket
(
char
*
my_endpoint_
)
{
fd_t
s
;
struct
sockaddr_in
ip4addr
;
unsigned
short
int
port
;
int
rc
=
sscanf
(
my_endpoint_
,
"tcp://127.0.0.1:%hu"
,
&
port
);
TEST_ASSERT_EQUAL_INT
(
1
,
rc
);
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
port
);
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
connect
(
s
,
reinterpret_cast
<
struct
sockaddr
*>
(
&
ip4addr
),
sizeof
(
ip4addr
));
TEST_ASSERT_GREATER_THAN_INT
(
-
1
,
rc
);
return
s
;
}
void
test_curve_security_unauthenticated_message
()
{
// Unauthenticated messages from a vanilla socket shouldn't be received
fd_t
s
=
connect_
vanilla_
socket
(
my_endpoint
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// send anonymous ZMTP/1.0 greeting
send
(
s
,
"
\x01\x00
"
,
2
,
0
);
// send sneaky message that shouldn't be received
...
...
@@ -277,21 +242,16 @@ template <size_t N> void send (fd_t fd_, const char (&data_)[N])
send_all
(
fd_
,
data_
,
N
-
1
);
}
void
send_greeting
(
fd_t
s_
)
template
<
size_t
N
>
void
send
(
fd_t
fd_
,
const
uint8_t
(
&
data_
)[
N
]
)
{
send
(
s_
,
"
\xff\0\0\0\0\0\0\0\0\x7f
"
);
// signature
send
(
s_
,
"
\x03\x00
"
);
// version 3.0
send
(
s_
,
"CURVE
\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0
"
);
// mechanism CURVE
send
(
s_
,
"
\0
"
);
// as-server == false
send
(
s_
,
"
\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0
"
);
send_all
(
fd_
,
reinterpret_cast
<
const
char
*>
(
&
data_
),
N
);
}
void
test_curve_security_invalid_hello_wrong_length
()
{
fd_t
s
=
connect_
vanilla_
socket
(
my_endpoint
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// send GREETING
send_greeting
(
s
);
send
(
s
,
zmtp_greeting_curve
);
// send CURVE HELLO of wrong size
send
(
s
,
"
\x04\x06\x05
HELLO"
);
...
...
@@ -355,9 +315,9 @@ template <size_t N> void send_command (fd_t s_, char (&command_)[N])
void
test_curve_security_invalid_hello_command_name
()
{
fd_t
s
=
connect_
vanilla_
socket
(
my_endpoint
);
fd_t
s
=
connect_socket
(
my_endpoint
);
send
_greeting
(
s
);
send
(
s
,
zmtp_greeting_curve
);
zmq
::
curve_client_tools_t
tools
=
make_curve_client_tools
();
...
...
@@ -377,9 +337,9 @@ void test_curve_security_invalid_hello_command_name ()
void
test_curve_security_invalid_hello_version
()
{
fd_t
s
=
connect_
vanilla_
socket
(
my_endpoint
);
fd_t
s
=
connect_socket
(
my_endpoint
);
send
_greeting
(
s
);
send
(
s
,
zmtp_greeting_curve
);
zmq
::
curve_client_tools_t
tools
=
make_curve_client_tools
();
...
...
@@ -429,9 +389,9 @@ void recv_greeting (fd_t fd_)
fd_t
connect_exchange_greeting_and_send_hello
(
char
*
my_endpoint_
,
zmq
::
curve_client_tools_t
&
tools_
)
{
fd_t
s
=
connect_
vanilla_
socket
(
my_endpoint_
);
fd_t
s
=
connect_socket
(
my_endpoint_
);
send
_greeting
(
s
);
send
(
s
,
zmtp_greeting_curve
);
recv_greeting
(
s
);
// send valid CURVE HELLO
...
...
tests/test_security_gssapi.cpp
View file @
12a2f817
...
...
@@ -30,17 +30,6 @@
#include "testutil.hpp"
#include "testutil_monitoring.hpp"
#include "testutil_unity.hpp"
#if defined(ZMQ_HAVE_WINDOWS)
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdexcept>
#define close closesocket
#else
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#endif
#include <stdlib.h>
#include <string.h>
...
...
@@ -253,23 +242,7 @@ void test_plain_creds ()
// Unauthenticated messages from a vanilla socket shouldn't be received
void
test_vanilla_socket
()
{
struct
sockaddr_in
ip4addr
;
int
s
;
unsigned
short
int
port
;
int
rc
=
sscanf
(
my_endpoint
,
"tcp://127.0.0.1:%hu"
,
&
port
);
TEST_ASSERT_EQUAL_INT
(
1
,
rc
);
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
port
);
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
connect
(
s
,
reinterpret_cast
<
struct
sockaddr
*>
(
&
ip4addr
),
sizeof
(
ip4addr
));
TEST_ASSERT_GREATER_THAN
(
-
1
,
rc
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// send anonymous ZMTP/1.0 greeting
send
(
s
,
"
\x01\x00
"
,
2
,
0
);
// send sneaky message that shouldn't be received
...
...
tests/test_security_null.cpp
View file @
12a2f817
...
...
@@ -169,25 +169,8 @@ void test_vanilla_socket ()
char
my_endpoint
[
MAX_SOCKET_STRING
];
bind_loopback_ipv4
(
server
,
my_endpoint
,
sizeof
my_endpoint
);
struct
sockaddr_in
ip4addr
;
fd_t
s
;
fd_t
s
=
connect_socket
(
my_endpoint
);
unsigned
short
int
port
;
int
rc
=
sscanf
(
my_endpoint
,
"tcp://127.0.0.1:%hu"
,
&
port
);
TEST_ASSERT_EQUAL_INT
(
1
,
rc
);
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
port
);
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
connect
(
s
,
reinterpret_cast
<
struct
sockaddr
*>
(
&
ip4addr
),
sizeof
ip4addr
);
TEST_ASSERT_GREATER_THAN_INT
(
-
1
,
rc
);
// send anonymous ZMTP/1.0 greeting
send
(
s
,
"
\x01\x00
"
,
2
,
0
);
// send sneaky message that shouldn't be received
...
...
tests/test_security_plain.cpp
View file @
12a2f817
...
...
@@ -30,18 +30,6 @@
#include "testutil.hpp"
#include "testutil_unity.hpp"
#if defined(ZMQ_HAVE_WINDOWS)
#include <winsock2.h>
#include <ws2tcpip.h>
#include <stdexcept>
#define close closesocket
#else
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#endif
#include <stdlib.h>
#include <string.h>
...
...
@@ -195,25 +183,7 @@ void test_plain_wrong_credentials_fails ()
void
test_plain_vanilla_socket
()
{
// Unauthenticated messages from a vanilla socket shouldn't be received
struct
sockaddr_in
ip4addr
;
fd_t
s
;
unsigned
short
int
port
;
int
rc
=
sscanf
(
my_endpoint
,
"tcp://127.0.0.1:%hu"
,
&
port
);
TEST_ASSERT_EQUAL_INT
(
1
,
rc
);
ip4addr
.
sin_family
=
AF_INET
;
ip4addr
.
sin_port
=
htons
(
port
);
#if defined(ZMQ_HAVE_WINDOWS) && (_WIN32_WINNT < 0x0600)
ip4addr
.
sin_addr
.
s_addr
=
inet_addr
(
"127.0.0.1"
);
#else
inet_pton
(
AF_INET
,
"127.0.0.1"
,
&
ip4addr
.
sin_addr
);
#endif
s
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
rc
=
connect
(
s
,
reinterpret_cast
<
struct
sockaddr
*>
(
&
ip4addr
),
sizeof
(
ip4addr
));
TEST_ASSERT_GREATER_THAN_INT
(
-
1
,
rc
);
fd_t
s
=
connect_socket
(
my_endpoint
);
// send anonymous ZMTP/1.0 greeting
send
(
s
,
"
\x01\x00
"
,
2
,
0
);
// send sneaky message that shouldn't be received
...
...
tests/test_shutdown_stress_tipc.cpp
View file @
12a2f817
...
...
@@ -43,12 +43,13 @@ void tearDown ()
#define THREAD_COUNT 100
extern
"C"
{
static
void
*
worker
(
void
*
s_
)
static
void
*
worker
(
void
*
ctx
)
{
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_connect
(
s_
,
"tipc://{5560,0}@0.0.0"
));
void
*
s
=
zmq_socket
(
ctx
,
ZMQ_SUB
);
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_connect
(
s
,
"tipc://{5560,0}@0.0.0"
));
// Start closing the socket while the connecting process is underway.
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_close
(
s
_
));
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_close
(
s
));
return
NULL
;
}
...
...
@@ -57,7 +58,6 @@ static void *worker (void *s_)
void
test_shutdown_stress_tipc
()
{
void
*
s1
;
void
*
s2
;
int
i
;
int
j
;
pthread_t
threads
[
THREAD_COUNT
];
...
...
@@ -72,9 +72,8 @@ void test_shutdown_stress_tipc ()
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_bind
(
s1
,
"tipc://{5560,0,0}"
));
for
(
i
=
0
;
i
!=
THREAD_COUNT
;
i
++
)
{
s2
=
zmq_socket
(
get_test_context
(),
ZMQ_SUB
);
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
pthread_create
(
&
threads
[
i
],
NULL
,
worker
,
s2
));
pthread_create
(
&
threads
[
i
],
NULL
,
worker
,
get_test_context
()
));
}
for
(
i
=
0
;
i
!=
THREAD_COUNT
;
i
++
)
{
...
...
tests/test_socks.cpp
View file @
12a2f817
...
...
@@ -105,21 +105,10 @@ void *setup_socks_server (char *socks_server_address,
int
socks_server_address_len
)
{
fprintf
(
stderr
,
"socks_server: setup socks server
\n
"
);
int
server_fd
=
socket
(
AF_INET
,
SOCK_STREAM
,
IPPROTO_TCP
);
TEST_ASSERT_NOT_EQUAL
(
-
1
,
server_fd
);
int
flag
=
1
;
int
res
;
#ifdef _WIN32
res
=
setsockopt
(
server_fd
,
SOL_SOCKET
,
SO_REUSEADDR
,
(
const
char
*
)
&
flag
,
sizeof
(
int
));
#else
res
=
setsockopt
(
server_fd
,
SOL_SOCKET
,
SO_REUSEADDR
,
&
flag
,
sizeof
(
int
));
#endif
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
res
);
struct
sockaddr_in
saddr
=
bind_bsd_socket
(
server_fd
);
int
nbytes
=
snprintf
(
socks_server_address
,
socks_server_address_len
,
"127.0.0.1:%d"
,
ntohs
(
saddr
.
sin_port
));
TEST_ASSERT
(
nbytes
>=
0
&&
nbytes
<
socks_server_address_len
);
int
server_fd
=
bind_socket_resolve_port
(
"127.0.0.1"
,
"0"
,
socks_server_address
);
memmove
(
socks_server_address
,
strchr
(
socks_server_address
,
'/'
)
+
2
,
strlen
(
strchr
(
socks_server_address
,
'/'
)
+
1
));
fprintf
(
stderr
,
"socks_server: bound to: tcp://%s
\n
"
,
socks_server_address
);
return
(
void
*
)
(
intptr_t
)
server_fd
;
...
...
tests/test_stream_exceeds_buffer.cpp
View file @
12a2f817
...
...
@@ -32,12 +32,6 @@
#include <string.h>
#ifndef _WIN32
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#endif
SETUP_TEARDOWN_TESTCONTEXT
void
test_stream_exceeds_buffer
()
...
...
@@ -47,16 +41,7 @@ void test_stream_exceeds_buffer ()
unsigned
char
rcvbuf
[
msgsize
];
char
my_endpoint
[
MAX_SOCKET_STRING
];
int
server_sock
=
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
socket
(
AF_INET
,
SOCK_STREAM
,
0
));
int
enable
=
1
;
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
setsockopt
(
server_sock
,
SOL_SOCKET
,
SO_REUSEADDR
,
(
char
*
)
&
enable
,
sizeof
(
enable
)));
struct
sockaddr_in
saddr
=
bind_bsd_socket
(
server_sock
);
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
listen
(
server_sock
,
1
));
sprintf
(
my_endpoint
,
"tcp://127.0.0.1:%d"
,
ntohs
(
saddr
.
sin_port
));
int
server_sock
=
bind_socket_resolve_port
(
"127.0.0.1"
,
"0"
,
my_endpoint
);
void
*
zsock
=
test_context_socket
(
ZMQ_STREAM
);
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_connect
(
zsock
,
my_endpoint
));
...
...
tests/test_use_fd.cpp
View file @
12a2f817
...
...
@@ -37,33 +37,12 @@
SETUP_TEARDOWN_TESTCONTEXT
#if !defined(ZMQ_HAVE_WINDOWS)
#include <sys/socket.h>
#include <sys/un.h>
#include <netdb.h>
#include <unistd.h>
int
setup_socket_and_set_fd
(
void
*
zmq_socket_
,
int
af_
,
int
protocol_
,
const
sockaddr
*
addr_
,
size_t
addr_len_
)
void
pre_allocate_sock_tcp
(
void
*
socket_
,
char
*
my_endpoint_
)
{
const
int
s_pre
=
TEST_ASSERT_SUCCESS_ERRNO
(
socket
(
af_
,
SOCK_STREAM
,
protocol_
));
if
(
af_
==
AF_INET
)
{
int
flag
=
1
;
TEST_ASSERT_SUCCESS_ERRNO
(
setsockopt
(
s_pre
,
SOL_SOCKET
,
SO_REUSEADDR
,
&
flag
,
sizeof
(
int
)));
}
TEST_ASSERT_SUCCESS_ERRNO
(
bind
(
s_pre
,
addr_
,
addr_len_
));
TEST_ASSERT_SUCCESS_ERRNO
(
listen
(
s_pre
,
SOMAXCONN
));
fd_t
s
=
bind_socket_resolve_port
(
"127.0.0.1"
,
"0"
,
my_endpoint_
);
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_setsockopt
(
zmq_socket_
,
ZMQ_USE_FD
,
&
s_pre
,
sizeof
(
s_pre
)));
return
s_pre
;
zmq_setsockopt
(
socket_
,
ZMQ_USE_FD
,
&
s
,
sizeof
(
s
)));
}
typedef
void
(
*
pre_allocate_sock_fun_t
)
(
void
*
,
char
*
);
...
...
@@ -166,41 +145,6 @@ void test_client_server (pre_allocate_sock_fun_t pre_allocate_sock_fun_)
#endif
}
uint16_t
pre_allocate_sock_tcp_int
(
void
*
zmq_socket_
,
const
char
*
address_
,
const
char
*
port_
)
{
struct
addrinfo
*
addr
,
hint
;
hint
.
ai_flags
=
0
;
hint
.
ai_family
=
AF_INET
;
hint
.
ai_socktype
=
SOCK_STREAM
;
hint
.
ai_protocol
=
IPPROTO_TCP
;
hint
.
ai_addrlen
=
0
;
hint
.
ai_canonname
=
NULL
;
hint
.
ai_addr
=
NULL
;
hint
.
ai_next
=
NULL
;
TEST_ASSERT_SUCCESS_ERRNO
(
getaddrinfo
(
address_
,
port_
,
&
hint
,
&
addr
));
const
int
s_pre
=
setup_socket_and_set_fd
(
zmq_socket_
,
AF_INET
,
IPPROTO_TCP
,
addr
->
ai_addr
,
addr
->
ai_addrlen
);
struct
sockaddr_in
sin
;
socklen_t
len
=
sizeof
(
sin
);
TEST_ASSERT_SUCCESS_ERRNO
(
getsockname
(
s_pre
,
(
struct
sockaddr
*
)
&
sin
,
&
len
));
freeaddrinfo
(
addr
);
return
ntohs
(
sin
.
sin_port
);
}
void
pre_allocate_sock_tcp
(
void
*
socket_
,
char
*
my_endpoint_
)
{
const
uint16_t
port
=
pre_allocate_sock_tcp_int
(
socket_
,
"127.0.0.1"
,
"0"
);
sprintf
(
my_endpoint_
,
"tcp://127.0.0.1:%u"
,
port
);
}
void
test_req_rep_tcp
()
{
test_req_rep
(
pre_allocate_sock_tcp
);
...
...
@@ -218,38 +162,14 @@ void test_client_server_tcp ()
#endif
}
void
pre_allocate_sock_ipc_int
(
void
*
zmq_socket_
,
const
char
*
path_
)
{
struct
sockaddr_un
addr
;
addr
.
sun_family
=
AF_UNIX
;
strcpy
(
addr
.
sun_path
,
path_
);
// TODO check return value of unlink
unlink
(
path_
);
setup_socket_and_set_fd
(
zmq_socket_
,
AF_UNIX
,
0
,
reinterpret_cast
<
struct
sockaddr
*>
(
&
addr
),
sizeof
(
struct
sockaddr_un
));
}
char
ipc_endpoint
[
16
];
char
ipc_endpoint
[
MAX_SOCKET_STRING
]
=
""
;
void
pre_allocate_sock_ipc
(
void
*
sb_
,
char
*
my_endpoint_
)
{
strcpy
(
ipc_endpoint
,
"tmpXXXXXX"
);
#ifdef HAVE_MKDTEMP
TEST_ASSERT_TRUE
(
mkdtemp
(
ipc_endpoint
));
strcat
(
ipc_endpoint
,
"/ipc"
);
#else
int
fd
=
mkstemp
(
ipc_endpoint
);
TEST_ASSERT_TRUE
(
fd
!=
-
1
);
close
(
fd
);
#endif
pre_allocate_sock_ipc_int
(
sb_
,
ipc_endpoint
);
strcpy
(
my_endpoint_
,
"ipc://"
);
strcat
(
my_endpoint_
,
ipc_endpoint
);
fd_t
s
=
bind_socket_resolve_port
(
""
,
""
,
my_endpoint_
,
AF_UNIX
,
0
);
TEST_ASSERT_SUCCESS_ERRNO
(
zmq_setsockopt
(
sb_
,
ZMQ_USE_FD
,
&
s
,
sizeof
(
s
)));
strcpy
(
ipc_endpoint
,
strchr
(
my_endpoint_
,
'/'
)
+
2
);
}
void
test_req_rep_ipc
()
...
...
@@ -277,7 +197,7 @@ void test_client_server_ipc ()
int
main
()
{
setup_test_environment
();
setup_test_environment
(
0
);
UNITY_BEGIN
();
RUN_TEST
(
test_req_rep_tcp
);
...
...
tests/test_z85_decode_fuzzer.cpp
0 → 100644
View file @
12a2f817
/*
Copyright (c) 2020 Contributors as noted in the AUTHORS file
This file is part of libzmq, the ZeroMQ core engine in C++.
libzmq is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License (LGPL) as published
by the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
As a special exception, the Contributors give you permission to link
this library with independent modules to produce an executable,
regardless of the license terms of these independent modules, and to
copy and distribute the resulting executable under terms of your choice,
provided that you also meet, for each linked independent module, the
terms and conditions of the license of that module. An independent
module is a module which is not derived from or based on this library.
If you modify this library, you must extend this exception to your
version of the library.
libzmq 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifdef ZMQ_USE_FUZZING_ENGINE
#include <fuzzer/FuzzedDataProvider.h>
#endif
#include <string>
#include <stdlib.h>
#include "testutil.hpp"
#include "testutil_unity.hpp"
extern
"C"
int
LLVMFuzzerTestOneInput
(
const
uint8_t
*
data
,
size_t
size
)
{
uint8_t
*
secret_key
;
// As per API definition, input must be divisible by 5, so truncate it if it's not
size
-=
size
%
5
;
// As per API definition, the destination must be at least 0.8 times the input data
TEST_ASSERT_NOT_NULL
(
secret_key
=
(
uint8_t
*
)
malloc
(
size
*
4
/
5
));
std
::
string
z85_secret_key
(
reinterpret_cast
<
const
char
*>
(
data
),
size
);
TEST_ASSERT_NOT_NULL
(
zmq_z85_decode
(
secret_key
,
z85_secret_key
.
c_str
()));
free
(
secret_key
);
return
0
;
}
#ifndef ZMQ_USE_FUZZING_ENGINE
void
test_bind_null_fuzzer
()
{
uint8_t
buffer
[
32
]
=
{
0
};
TEST_ASSERT_SUCCESS_ERRNO
(
LLVMFuzzerTestOneInput
(
buffer
,
sizeof
(
buffer
)));
}
int
main
(
int
argc
,
char
**
argv
)
{
setup_test_environment
();
UNITY_BEGIN
();
RUN_TEST
(
test_bind_null_fuzzer
);
return
UNITY_END
();
}
#endif
tests/testutil.cpp
View file @
12a2f817
...
...
@@ -35,6 +35,10 @@
#if defined _WIN32
#include "../src/windows.hpp"
#if defined _MSC_VER
#if defined ZMQ_HAVE_IPC
#include <direct.h>
#include <afunix.h>
#endif
#include <crtdbg.h>
#pragma warning(disable : 4996)
// iphlpapi is needed for if_nametoindex (not on Windows XP)
...
...
@@ -55,6 +59,7 @@
#include <arpa/inet.h>
#include <net/if.h>
#include <netdb.h>
#include <sys/un.h>
#if defined(ZMQ_HAVE_AIX)
#include <sys/types.h>
#include <sys/socketvar.h>
...
...
@@ -365,6 +370,147 @@ sockaddr_in bind_bsd_socket (int socket_)
return
saddr
;
}
fd_t
connect_socket
(
const
char
*
endpoint_
,
const
int
af_
,
const
int
protocol_
)
{
struct
sockaddr_storage
addr
;
// OSX is very opinionated and wants the size to match the AF family type
socklen_t
addr_len
=
sizeof
(
addr
);
const
fd_t
s_pre
=
socket
(
af_
,
SOCK_STREAM
,
protocol_
);
TEST_ASSERT_NOT_EQUAL
(
-
1
,
s_pre
);
if
(
af_
==
AF_INET
||
af_
==
AF_INET6
)
{
const
char
*
port
=
strrchr
(
endpoint_
,
':'
)
+
1
;
char
address
[
MAX_SOCKET_STRING
];
// getaddrinfo does not like [x:y::z]
if
(
*
strchr
(
endpoint_
,
'/'
)
+
2
==
'['
)
{
strcpy
(
address
,
strchr
(
endpoint_
,
'['
)
+
1
);
address
[
strlen
(
address
)
-
strlen
(
port
)
-
2
]
=
'\0'
;
}
else
{
strcpy
(
address
,
strchr
(
endpoint_
,
'/'
)
+
2
);
address
[
strlen
(
address
)
-
strlen
(
port
)
-
1
]
=
'\0'
;
}
struct
addrinfo
*
in
,
hint
;
hint
.
ai_flags
=
AI_NUMERICSERV
;
hint
.
ai_family
=
af_
;
hint
.
ai_socktype
=
SOCK_STREAM
;
hint
.
ai_protocol
=
protocol_
;
hint
.
ai_addrlen
=
0
;
hint
.
ai_canonname
=
NULL
;
hint
.
ai_addr
=
NULL
;
hint
.
ai_next
=
NULL
;
TEST_ASSERT_SUCCESS_RAW_ZERO_ERRNO
(
getaddrinfo
(
address
,
port
,
&
hint
,
&
in
));
TEST_ASSERT_NOT_NULL
(
in
);
memcpy
(
&
addr
,
in
->
ai_addr
,
in
->
ai_addrlen
);
addr_len
=
(
socklen_t
)
in
->
ai_addrlen
;
freeaddrinfo
(
in
);
}
#if defined(ZMQ_HAVE_IPC)
else
{
struct
sockaddr_un
*
un_addr
=
(
struct
sockaddr_un
*
)
&
addr
;
addr_len
=
sizeof
(
struct
sockaddr_un
);
un_addr
->
sun_family
=
AF_UNIX
;
strcpy
(
un_addr
->
sun_path
,
endpoint_
);
}
#endif
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
connect
(
s_pre
,
(
struct
sockaddr
*
)
&
addr
,
addr_len
));
return
s_pre
;
}
fd_t
bind_socket_resolve_port
(
const
char
*
address_
,
const
char
*
port_
,
char
*
my_endpoint_
,
const
int
af_
,
const
int
protocol_
)
{
struct
sockaddr_storage
addr
;
// OSX is very opinionated and wants the size to match the AF family type
socklen_t
addr_len
=
sizeof
(
addr
);
const
fd_t
s_pre
=
socket
(
af_
,
SOCK_STREAM
,
protocol_
);
TEST_ASSERT_NOT_EQUAL
(
-
1
,
s_pre
);
if
(
af_
==
AF_INET
||
af_
==
AF_INET6
)
{
#ifdef ZMQ_HAVE_WINDOWS
const
char
flag
=
'\1'
;
#elif defined ZMQ_HAVE_VXWORKS
char
flag
=
'\1'
;
#else
int
flag
=
1
;
#endif
struct
addrinfo
*
in
,
hint
;
hint
.
ai_flags
=
AI_NUMERICSERV
;
hint
.
ai_family
=
af_
;
hint
.
ai_socktype
=
protocol_
==
IPPROTO_UDP
?
SOCK_DGRAM
:
SOCK_STREAM
;
hint
.
ai_protocol
=
protocol_
;
hint
.
ai_addrlen
=
0
;
hint
.
ai_canonname
=
NULL
;
hint
.
ai_addr
=
NULL
;
hint
.
ai_next
=
NULL
;
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
setsockopt
(
s_pre
,
SOL_SOCKET
,
SO_REUSEADDR
,
&
flag
,
sizeof
(
int
)));
TEST_ASSERT_SUCCESS_RAW_ZERO_ERRNO
(
getaddrinfo
(
address_
,
port_
,
&
hint
,
&
in
));
TEST_ASSERT_NOT_NULL
(
in
);
memcpy
(
&
addr
,
in
->
ai_addr
,
in
->
ai_addrlen
);
addr_len
=
(
socklen_t
)
in
->
ai_addrlen
;
freeaddrinfo
(
in
);
}
#if defined(ZMQ_HAVE_IPC)
else
{
struct
sockaddr_un
*
un_addr
=
(
struct
sockaddr_un
*
)
&
addr
;
addr_len
=
sizeof
(
struct
sockaddr_un
);
un_addr
->
sun_family
=
AF_UNIX
;
#if defined ZMQ_HAVE_WINDOWS
char
buffer
[
MAX_PATH
]
=
""
;
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
tmpnam_s
(
buffer
));
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
_mkdir
(
buffer
));
strcat
(
buffer
,
"/ipc"
);
#else
char
buffer
[
PATH_MAX
]
=
""
;
strcpy
(
buffer
,
"tmpXXXXXX"
);
#ifdef HAVE_MKDTEMP
TEST_ASSERT_TRUE
(
mkdtemp
(
buffer
));
strcat
(
buffer
,
"/socket"
);
#else
int
fd
=
mkstemp
(
buffer
);
TEST_ASSERT_TRUE
(
fd
!=
-
1
);
close
(
fd
);
#endif
#endif
strcpy
(
un_addr
->
sun_path
,
buffer
);
memcpy
(
my_endpoint_
,
"ipc://"
,
7
);
strcat
(
my_endpoint_
,
buffer
);
// TODO check return value of unlink
unlink
(
buffer
);
}
#endif
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
bind
(
s_pre
,
(
struct
sockaddr
*
)
&
addr
,
addr_len
));
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
listen
(
s_pre
,
SOMAXCONN
));
if
(
af_
==
AF_INET
||
af_
==
AF_INET6
)
{
addr_len
=
sizeof
(
struct
sockaddr_storage
);
TEST_ASSERT_SUCCESS_RAW_ERRNO
(
getsockname
(
s_pre
,
(
struct
sockaddr
*
)
&
addr
,
&
addr_len
));
sprintf
(
my_endpoint_
,
"%s://%s:%u"
,
protocol_
==
IPPROTO_TCP
?
"tcp"
:
"udp"
,
address_
,
af_
==
AF_INET
?
ntohs
(((
struct
sockaddr_in
*
)
&
addr
)
->
sin_port
)
:
ntohs
(((
struct
sockaddr_in6
*
)
&
addr
)
->
sin6_port
));
}
return
s_pre
;
}
bool
streq
(
const
char
*
lhs_
,
const
char
*
rhs_
)
{
return
strcmp
(
lhs_
,
rhs_
)
==
0
;
...
...
tests/testutil.hpp
View file @
12a2f817
...
...
@@ -38,6 +38,14 @@
#include "../include/zmq.h"
#include "../src/stdint.hpp"
// For AF_INET and IPPROTO_TCP
#if defined _WIN32
#include "../src/windows.hpp"
#else
#include <arpa/inet.h>
#include <unistd.h>
#endif
// This defines the settle time used in tests; raise this if we
// get test failures on slower systems due to binds/connects not
// settled. Tested to work reliably at 1 msec on a fast PC.
...
...
@@ -57,8 +65,33 @@
#define ENDPOINT_5 "udp://127.0.0.1:5560"
#define PORT_6 5561
// For tests that mock ZMTP
const
uint8_t
zmtp_greeting_null
[
64
]
=
{
0xff
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0x7f
,
3
,
0
,
'N'
,
'U'
,
'L'
,
'L'
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
};
const
uint8_t
zmtp_greeting_curve
[
64
]
=
{
0xff
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0x7f
,
3
,
0
,
'C'
,
'U'
,
'R'
,
'V'
,
'E'
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
,
0
};
const
uint8_t
zmtp_ready_dealer
[
43
]
=
{
4
,
41
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
6
,
'D'
,
'E'
,
'A'
,
'L'
,
'E'
,
'R'
,
8
,
'I'
,
'd'
,
'e'
,
'n'
,
't'
,
'i'
,
't'
,
'y'
,
0
,
0
,
0
,
0
};
const
uint8_t
zmtp_ready_xpub
[
28
]
=
{
4
,
26
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
4
,
'X'
,
'P'
,
'U'
,
'B'
};
const
uint8_t
zmtp_ready_sub
[
27
]
=
{
4
,
25
,
5
,
'R'
,
'E'
,
'A'
,
'D'
,
'Y'
,
11
,
'S'
,
'o'
,
'c'
,
'k'
,
'e'
,
't'
,
'-'
,
'T'
,
'y'
,
'p'
,
'e'
,
0
,
0
,
0
,
3
,
'S'
,
'U'
,
'B'
};
#undef NDEBUG
#ifndef MSG_NOSIGNAL
#define MSG_NOSIGNAL 0
#endif
// duplicated from fd.hpp
#ifdef ZMQ_HAVE_WINDOWS
#ifndef NOMINMAX
...
...
@@ -172,4 +205,20 @@ int test_inet_pton (int af_, const char *src_, void *dst_);
// Binds an ipv4 BSD socket to an ephemeral port, returns the compiled sockaddr
struct
sockaddr_in
bind_bsd_socket
(
int
socket
);
// Connects a BSD socket to the ZMQ endpoint. Works with ipv4/ipv6/unix.
fd_t
connect_socket
(
const
char
*
endpoint_
,
const
int
af_
=
AF_INET
,
const
int
protocol_
=
IPPROTO_TCP
);
// Binds a BSD socket to an ephemeral port, returns the file descriptor.
// The resulting ZMQ endpoint will be stored in my_endpoint, including the protocol
// prefix, so ensure it is writable and of appropriate size.
// Works with ipv4/ipv6/unix. With unix sockets address_/port_ can be empty and
// my_endpoint_ will contain a random path.
fd_t
bind_socket_resolve_port
(
const
char
*
address_
,
const
char
*
port_
,
char
*
my_endpoint_
,
const
int
af_
=
AF_INET
,
const
int
protocol_
=
IPPROTO_TCP
);
#endif
tests/testutil_unity.cpp
View file @
12a2f817
...
...
@@ -55,12 +55,10 @@ int test_assert_success_message_errno_helper (int rc_,
return
rc_
;
}
int
test_assert_success_message_raw_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line_
)
int
test_assert_success_message_raw_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line_
,
bool
zero
)
{
if
(
rc_
==
-
1
)
{
if
(
rc_
==
-
1
||
(
zero
&&
rc_
!=
0
)
)
{
#if defined ZMQ_HAVE_WINDOWS
int
current_errno
=
WSAGetLastError
();
#else
...
...
@@ -70,14 +68,24 @@ int test_assert_success_message_raw_errno_helper (int rc_,
char
buffer
[
512
];
buffer
[
sizeof
(
buffer
)
-
1
]
=
0
;
// to ensure defined behavior with VC++ <= 2013
snprintf
(
buffer
,
sizeof
(
buffer
)
-
1
,
"%s failed%s%s%s, errno = %i"
,
expr_
,
msg_
?
" (additional info: "
:
""
,
msg_
?
msg_
:
""
,
msg_
?
")"
:
""
,
current_errno
);
snprintf
(
buffer
,
sizeof
(
buffer
)
-
1
,
"%s failed%s%s%s with %d, errno = %i/%s"
,
expr_
,
msg_
?
" (additional info: "
:
""
,
msg_
?
msg_
:
""
,
msg_
?
")"
:
""
,
rc_
,
current_errno
,
strerror
(
current_errno
));
UNITY_TEST_FAIL
(
line_
,
buffer
);
}
return
rc_
;
}
int
test_assert_success_message_raw_zero_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line_
)
{
return
test_assert_success_message_raw_errno_helper
(
rc_
,
msg_
,
expr_
,
line_
,
true
);
}
int
test_assert_failure_message_raw_errno_helper
(
int
rc_
,
int
expected_errno_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line_
)
{
...
...
tests/testutil_unity.hpp
View file @
12a2f817
...
...
@@ -43,10 +43,13 @@ int test_assert_success_message_errno_helper (int rc_,
const
char
*
expr_
,
int
line
);
int
test_assert_success_message_raw_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line
);
int
test_assert_success_message_raw_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line
,
bool
zero_
=
false
);
int
test_assert_success_message_raw_zero_errno_helper
(
int
rc_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line
);
int
test_assert_failure_message_raw_errno_helper
(
int
rc_
,
int
expected_errno_
,
const
char
*
msg_
,
const
char
*
expr_
,
int
line
);
...
...
@@ -88,9 +91,22 @@ int test_assert_failure_message_raw_errno_helper (
// A typical use would be:
// TEST_ASSERT_SUCCESS_RAW_ERRNO (send (fd, buffer, 64, 0));
// In case of success, the result of the macro is the result of 'expr'.
// Success is strictly defined by a return value different from -1, as opposed
// to checking that it is 0, like TEST_ASSERT_FAILURE_RAW_ZERO_ERRNO does.
#define TEST_ASSERT_SUCCESS_RAW_ERRNO(expr) \
test_assert_success_message_raw_errno_helper (expr, NULL, #expr, __LINE__)
// Asserts that the socket API 'expr' is successful. In case of a failure, the
// assertion message includes the literal 'expr' and the error code.
// A typical use would be:
// TEST_ASSERT_SUCCESS_RAW_ZERO_ERRNO (send (fd, buffer, 64, 0));
// In case of success, the result of the macro is the result of 'expr'.
// Success is strictly defined by a return value of 0, as opposed to checking
// that it is not -1, like TEST_ASSERT_FAILURE_RAW_ERRNO does.
#define TEST_ASSERT_SUCCESS_RAW_ZERO_ERRNO(expr) \
test_assert_success_message_raw_zero_errno_helper (expr, NULL, #expr, \
__LINE__)
// Asserts that the socket API 'expr' is not successful, and the error code is
// 'error_code'. In case of an unexpected succces, or a failure with an
// unexpected error code, the assertion message includes the literal 'expr'
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment