#include "libtest/yatlcon.h"
#include <libtest/common.h>
#include <cassert>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <fnmatch.h>
#include <iostream>
#include <fstream>
#include <memory>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <signal.h>
#ifndef __INTEL_COMPILER
#pragma GCC diagnostic ignored "-Wold-style-cast"
#endif
using
namespace
libtest;
static
void
stats_print(libtest::Framework *frame)
{
if
(frame->failed() == 0 and frame->success() == 0)
{
return
;
}
Outn();
Out <<
"Collections\t\t\t\t\t"
<< frame->total();
Out <<
"\tFailed\t\t\t\t\t"
<< frame->failed();
Out <<
"\tSkipped\t\t\t\t\t"
<< frame->skipped();
Out <<
"\tSucceeded\t\t\t\t"
<< frame->success();
Outn();
Out <<
"Tests\t\t\t\t\t"
<< frame->sum_total();
Out <<
"\tFailed\t\t\t\t"
<< frame->sum_failed();
Out <<
"\tSkipped\t\t\t\t"
<< frame->sum_skipped();
Out <<
"\tSucceeded\t\t\t"
<< frame->sum_success();
}
#include <getopt.h>
#include <unistd.h>
int
main(
int
argc,
char
*argv[])
{
bool
opt_massive=
false
;
unsigned
long
int
opt_repeat= 1;
bool
opt_quiet=
false
;
std::string collection_to_run;
std::string wildcard;
std::string binary_name;
const
char
*just_filename= rindex(argv[0],
'/'
);
if
(just_filename)
{
just_filename++;
}
else
{
just_filename= argv[0];
}
if
(just_filename[0] ==
'l'
and just_filename[1] ==
't'
and just_filename[2] ==
'-'
)
{
just_filename+= 3;
}
binary_name.append(just_filename);
#if defined(TARGET_OS_OSX) && TARGET_OS_OSX
if
(valgrind_is_caller())
{
return
EXIT_SKIP;
}
#endif
{
enum
long_option_t {
OPT_LIBYATL_VERSION,
OPT_LIBYATL_MATCH_COLLECTION,
OPT_LIBYATL_MASSIVE,
OPT_LIBYATL_QUIET,
OPT_LIBYATL_MATCH_WILDCARD,
OPT_LIBYATL_REPEAT
};
static
struct
option long_options[]=
{
{
"version"
, no_argument, NULL, OPT_LIBYATL_VERSION },
{
"quiet"
, no_argument, NULL, OPT_LIBYATL_QUIET },
{
"repeat"
, required_argument, NULL, OPT_LIBYATL_REPEAT },
{
"collection"
, required_argument, NULL, OPT_LIBYATL_MATCH_COLLECTION },
{
"wildcard"
, required_argument, NULL, OPT_LIBYATL_MATCH_WILDCARD },
{
"massive"
, no_argument, NULL, OPT_LIBYATL_MASSIVE },
{ 0, 0, 0, 0 }
};
int
option_index= 0;
while
(1)
{
int
option_rv= getopt_long(argc, argv,
""
, long_options, &option_index);
if
(option_rv == -1)
{
break
;
}
switch
(option_rv)
{
case
OPT_LIBYATL_VERSION:
break
;
case
OPT_LIBYATL_QUIET:
opt_quiet=
true
;
break
;
case
OPT_LIBYATL_REPEAT:
errno
= 0;
opt_repeat=
strtoul
(optarg, (
char
**) NULL, 10);
if
(
errno
!= 0)
{
Error <<
"unknown value passed to --repeat: `"
<< optarg <<
"`"
;
exit
(EXIT_FAILURE);
}
break
;
case
OPT_LIBYATL_MATCH_COLLECTION:
collection_to_run= optarg;
break
;
case
OPT_LIBYATL_MATCH_WILDCARD:
wildcard= optarg;
break
;
case
OPT_LIBYATL_MASSIVE:
opt_massive=
true
;
break
;
case
'?'
:
Error <<
"unknown option to getopt_long()"
;
exit
(EXIT_FAILURE);
default
:
break
;
}
}
}
srandom((unsigned
int
)
time
(NULL));
errno
= 0;
if
(
bool
(
getenv
(
"YATL_REPEAT"
)))
{
errno
= 0;
opt_repeat=
strtoul
(
getenv
(
"YATL_REPEAT"
), (
char
**) NULL, 10);
if
(
errno
!= 0)
{
Error <<
"ENV YATL_REPEAT passed an invalid value: `"
<<
getenv
(
"YATL_REPEAT"
) <<
"`"
;
exit
(EXIT_FAILURE);
}
}
if
((
bool
(
getenv
(
"YATL_QUIET"
)) and (
strcmp
(
getenv
(
"YATL_QUIET"
),
"0"
) == 0)) or opt_quiet)
{
opt_quiet=
true
;
}
else
if
(
getenv
(
"JENKINS_URL"
))
{
if
(
bool
(
getenv
(
"YATL_QUIET"
)) and (
strcmp
(
getenv
(
"YATL_QUIET"
),
"1"
) == 0))
{ }
else
{
opt_quiet=
true
;
}
}
if
((
bool
(
getenv
(
"YATL_RUN_MASSIVE_TESTS"
))) or opt_massive)
{
opt_massive=
true
;
}
if
(opt_quiet)
{
close(STDOUT_FILENO);
}
if
(opt_massive)
{
is_massive(opt_massive);
}
libtest::vchar_t tmp_directory;
tmp_directory.resize(1024);
if
(
getenv
(
"LIBTEST_TMP"
))
{
snprintf(&tmp_directory[0], tmp_directory.size(),
"%s"
,
getenv
(
"LIBTEST_TMP"
));
}
else
{
snprintf(&tmp_directory[0], tmp_directory.size(),
"%s"
, LIBTEST_TEMP);
}
if
(chdir(&tmp_directory[0]) == -1)
{
libtest::vchar_t getcwd_buffer;
getcwd_buffer.resize(1024);
char
*dir= getcwd(&getcwd_buffer[0], getcwd_buffer.size());
Error <<
"Unable to chdir() from "
<< dir <<
" to "
<< &tmp_directory[0] <<
" errno:"
<<
strerror
(
errno
);
return
EXIT_FAILURE;
}
if
(libtest::libtool() == NULL)
{
Error <<
"Failed to locate libtool"
;
return
EXIT_FAILURE;
}
if
(
getenv
(
"YATL_COLLECTION_TO_RUN"
))
{
if
(
strlen
(
getenv
(
"YATL_COLLECTION_TO_RUN"
)))
{
collection_to_run=
getenv
(
"YATL_COLLECTION_TO_RUN"
);
}
}
if
(collection_to_run.compare(
"none"
) == 0)
{
return
EXIT_SUCCESS;
}
if
(collection_to_run.empty() ==
false
)
{
Out <<
"Only testing "
<< collection_to_run;
}
int
exit_code;
try
{
do
{
exit_code= EXIT_SUCCESS;
fatal_assert(sigignore(SIGPIPE) == 0);
libtest::SignalThread
signal
;
if
(
signal
.setup() ==
false
)
{
Error <<
"Failed to setup signals"
;
return
EXIT_FAILURE;
}
std::auto_ptr<libtest::Framework> frame(
new
libtest::Framework(
signal
, binary_name, collection_to_run, wildcard));
try
{
switch
(frame->create())
{
case
TEST_SUCCESS:
break
;
case
TEST_SKIPPED:
return
EXIT_SKIP;
case
TEST_FAILURE:
std::cerr <<
"Could not call frame->create()"
<< std::endl;
return
EXIT_FAILURE;
}
}
catch
(
const
libtest::__skipped& e)
{
return
EXIT_SKIP;
}
frame->exec();
if
(
signal
.is_shutdown() ==
false
)
{
signal
.set_shutdown(SHUTDOWN_GRACEFUL);
}
shutdown_t status=
signal
.get_shutdown();
if
(status == SHUTDOWN_FORCED)
{
Out <<
"Tests were aborted."
;
exit_code= EXIT_FAILURE;
}
else
if
(frame->failed())
{
Out <<
"Some test failed."
;
exit_code= EXIT_FAILURE;
}
else
if
(frame->skipped() and frame->failed() and frame->success())
{
Out <<
"Some tests were skipped."
;
}
else
if
(frame->success() and (frame->failed() == 0))
{
Out;
Out <<
"All tests completed successfully."
;
}
stats_print(frame.get());
std::ofstream xml_file;
std::string file_name;
file_name.append(&tmp_directory[0]);
file_name.append(frame->name());
file_name.append(
".xml"
);
xml_file.open(file_name.c_str(), std::ios::trunc);
libtest::Formatter::xml(*frame, xml_file);
Outn();
}
while
(exit_code == EXIT_SUCCESS and --opt_repeat);
}
catch
(
const
libtest::__skipped& e)
{
return
EXIT_SKIP;
}
catch
(
const
libtest::__failure& e)
{
libtest::stream::make_cout(e.file(), e.line(), e.func()) << e.what();
exit_code= EXIT_FAILURE;
}
catch
(
const
libtest::fatal& e)
{
std::cerr <<
"FATAL:"
<< e.what() << std::endl;
exit_code= EXIT_FAILURE;
}
catch
(
const
libtest::disconnected& e)
{
std::cerr <<
"Unhandled disconnection occurred:"
<< e.what() << std::endl;
exit_code= EXIT_FAILURE;
}
catch
(
const
std::exception& e)
{
std::cerr <<
"std::exception:"
<< e.what() << std::endl;
exit_code= EXIT_FAILURE;
}
catch
(
char
const
*)
{
std::cerr <<
"Exception:"
<< std::endl;
exit_code= EXIT_FAILURE;
}
catch
(...)
{
std::cerr <<
"Unknown exception halted execution."
<< std::endl;
exit_code= EXIT_FAILURE;
}
return
exit_code;
}