[PATCH weston] Added simple unit/integration test framework and corresponding test program.
Jon A. Cruz
jonc at osg.samsung.com
Wed Apr 29 15:31:45 PDT 2015
Added a simple C-based test framework and an example program
that uses it to run through some simple wayland client checks.
Signed-off-by: Jon A. Cruz <jonc at osg.samsung.com>
---
.gitignore | 3 +
Makefile.am | 34 +++
tools/Doxyfile | 318 +++++++++++++++++++++
tools/devdocs.doxyfile | 314 +++++++++++++++++++++
tools/tools.dox | 29 ++
tools/waycheck/rough_draw.c | 176 ++++++++++++
tools/waycheck/rough_draw.h | 42 +++
tools/waycheck/waycheck.c | 505 ++++++++++++++++++++++++++++++++++
tools/waycheck/waycheck.dox | 29 ++
tools/waycheck/wtst_fixtures.c | 289 +++++++++++++++++++
tools/waycheck/wtst_fixtures.h | 144 ++++++++++
tools/zunitc/doc/zunitc.dox | 67 +++++
tools/zunitc/inc/zunitc/zunitc.h | 300 ++++++++++++++++++++
tools/zunitc/inc/zunitc/zunitc_impl.h | 76 +++++
tools/zunitc/src/zunitc_impl.c | 496 +++++++++++++++++++++++++++++++++
tools/zunitc/test/zunitc_test.c | 106 +++++++
16 files changed, 2928 insertions(+)
create mode 100644 tools/Doxyfile
create mode 100644 tools/devdocs.doxyfile
create mode 100644 tools/tools.dox
create mode 100644 tools/waycheck/rough_draw.c
create mode 100644 tools/waycheck/rough_draw.h
create mode 100644 tools/waycheck/waycheck.c
create mode 100644 tools/waycheck/waycheck.dox
create mode 100644 tools/waycheck/wtst_fixtures.c
create mode 100644 tools/waycheck/wtst_fixtures.h
create mode 100644 tools/zunitc/doc/zunitc.dox
create mode 100644 tools/zunitc/inc/zunitc/zunitc.h
create mode 100644 tools/zunitc/inc/zunitc/zunitc_impl.h
create mode 100644 tools/zunitc/src/zunitc_impl.c
create mode 100644 tools/zunitc/test/zunitc_test.c
diff --git a/.gitignore b/.gitignore
index 047c386..2690bde 100644
--- a/.gitignore
+++ b/.gitignore
@@ -98,3 +98,6 @@ weston-drm.7
weston.ini.5
/tests/weston-ivi.ini
+
+waycheck
+zuctest
diff --git a/Makefile.am b/Makefile.am
index 2f16fac..073733f 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -1155,6 +1155,40 @@ setbacklight_CFLAGS = $(AM_CFLAGS) $(SETBACKLIGHT_CFLAGS)
setbacklight_LDADD = $(SETBACKLIGHT_LIBS)
endif
+# --------------------------------------------------------------------------
+
+all-local: waycheck$(EXEEXT) zuctest$(EXEEXT)
+
+noinst_PROGRAMS += zuctest$(EXEEXT)
+
+zuctest_CPPFLAGS = \
+ -I$(top_builddir)/tools/zunitc/inc
+
+zuctest_SOURCES = \
+ tools/zunitc/src/zunitc_impl.c \
+ tools/zunitc/test/zunitc_test.c
+
+#
+
+noinst_PROGRAMS += waycheck$(EXEEXT)
+
+waycheck_LDADD = \
+ $(WAYLAND_COMPOSITOR_LIBS)
+
+waycheck_CPPFLAGS = \
+ -I$(top_builddir)/tools/zunitc/inc \
+ -I$(top_builddir)/clients \
+ -I$(top_srcdir)/shared
+
+waycheck_SOURCES = \
+ tools/zunitc/src/zunitc_impl.c \
+ shared/os-compatibility.c \
+ tools/waycheck/waycheck.c \
+ tools/waycheck/rough_draw.c \
+ tools/waycheck/wtst_fixtures.c
+
+# --------------------------------------------------------------------------
+
EXTRA_DIST += tests/weston-tests-env
BUILT_SOURCES += \
diff --git a/tools/Doxyfile b/tools/Doxyfile
new file mode 100644
index 0000000..e42cdbb
--- /dev/null
+++ b/tools/Doxyfile
@@ -0,0 +1,318 @@
+# Doxyfile 1.8.8
+
+#---------------------------------------------------------------------------
+# Project related configuration options
+#---------------------------------------------------------------------------
+DOXYFILE_ENCODING = UTF-8
+PROJECT_NAME = "Tools"
+PROJECT_NUMBER =
+PROJECT_BRIEF =
+PROJECT_LOGO =
+OUTPUT_DIRECTORY = docs
+CREATE_SUBDIRS = NO
+ALLOW_UNICODE_NAMES = NO
+OUTPUT_LANGUAGE = English
+BRIEF_MEMBER_DESC = YES
+REPEAT_BRIEF = YES
+ABBREVIATE_BRIEF =
+ALWAYS_DETAILED_SEC = NO
+INLINE_INHERITED_MEMB = NO
+FULL_PATH_NAMES = YES
+STRIP_FROM_PATH =
+STRIP_FROM_INC_PATH =
+SHORT_NAMES = NO
+JAVADOC_AUTOBRIEF = YES
+QT_AUTOBRIEF = NO
+MULTILINE_CPP_IS_BRIEF = NO
+INHERIT_DOCS = YES
+SEPARATE_MEMBER_PAGES = NO
+TAB_SIZE = 4
+ALIASES =
+TCL_SUBST =
+OPTIMIZE_OUTPUT_FOR_C = YES
+OPTIMIZE_OUTPUT_JAVA = NO
+OPTIMIZE_FOR_FORTRAN = NO
+OPTIMIZE_OUTPUT_VHDL = NO
+EXTENSION_MAPPING =
+MARKDOWN_SUPPORT = YES
+AUTOLINK_SUPPORT = YES
+BUILTIN_STL_SUPPORT = NO
+CPP_CLI_SUPPORT = NO
+SIP_SUPPORT = NO
+IDL_PROPERTY_SUPPORT = YES
+DISTRIBUTE_GROUP_DOC = NO
+SUBGROUPING = YES
+INLINE_GROUPED_CLASSES = NO
+INLINE_SIMPLE_STRUCTS = NO
+TYPEDEF_HIDES_STRUCT = NO
+LOOKUP_CACHE_SIZE = 0
+#---------------------------------------------------------------------------
+# Build related configuration options
+#---------------------------------------------------------------------------
+EXTRACT_ALL = NO
+EXTRACT_PRIVATE = NO
+EXTRACT_PACKAGE = NO
+EXTRACT_STATIC = NO
+EXTRACT_LOCAL_CLASSES = YES
+EXTRACT_LOCAL_METHODS = NO
+EXTRACT_ANON_NSPACES = NO
+HIDE_UNDOC_MEMBERS = NO
+HIDE_UNDOC_CLASSES = NO
+HIDE_FRIEND_COMPOUNDS = NO
+HIDE_IN_BODY_DOCS = NO
+INTERNAL_DOCS = NO
+CASE_SENSE_NAMES = YES
+HIDE_SCOPE_NAMES = NO
+SHOW_INCLUDE_FILES = YES
+SHOW_GROUPED_MEMB_INC = NO
+FORCE_LOCAL_INCLUDES = NO
+INLINE_INFO = YES
+SORT_MEMBER_DOCS = YES
+SORT_BRIEF_DOCS = NO
+SORT_MEMBERS_CTORS_1ST = NO
+SORT_GROUP_NAMES = NO
+SORT_BY_SCOPE_NAME = NO
+STRICT_PROTO_MATCHING = NO
+GENERATE_TODOLIST = YES
+GENERATE_TESTLIST = YES
+GENERATE_BUGLIST = YES
+GENERATE_DEPRECATEDLIST= YES
+ENABLED_SECTIONS =
+MAX_INITIALIZER_LINES = 30
+SHOW_USED_FILES = YES
+SHOW_FILES = YES
+SHOW_NAMESPACES = YES
+FILE_VERSION_FILTER =
+LAYOUT_FILE =
+CITE_BIB_FILES =
+#---------------------------------------------------------------------------
+# Configuration options related to warning and progress messages
+#---------------------------------------------------------------------------
+QUIET = NO
+WARNINGS = YES
+WARN_IF_UNDOCUMENTED = YES
+WARN_IF_DOC_ERROR = YES
+WARN_NO_PARAMDOC = NO
+WARN_FORMAT = "$file:$line: $text"
+WARN_LOGFILE =
+#---------------------------------------------------------------------------
+# Configuration options related to the input files
+#---------------------------------------------------------------------------
+INPUT = \
+ tools.dox \
+ zunitc/doc/zunitc.dox \
+ zunitc/inc/zunitc/zunitc.h \
+ waycheck/waycheck.dox \
+ waycheck/wtst_fixtures.h \
+ waycheck/rough_draw.h
+INPUT_ENCODING = UTF-8
+FILE_PATTERNS =
+RECURSIVE = NO
+EXCLUDE =
+EXCLUDE_SYMLINKS = NO
+EXCLUDE_PATTERNS =
+EXCLUDE_SYMBOLS =
+EXAMPLE_PATH =
+EXAMPLE_PATTERNS =
+EXAMPLE_RECURSIVE = NO
+IMAGE_PATH =
+INPUT_FILTER =
+FILTER_PATTERNS =
+FILTER_SOURCE_FILES = NO
+FILTER_SOURCE_PATTERNS =
+USE_MDFILE_AS_MAINPAGE =
+#---------------------------------------------------------------------------
+# Configuration options related to source browsing
+#---------------------------------------------------------------------------
+SOURCE_BROWSER = NO
+INLINE_SOURCES = NO
+STRIP_CODE_COMMENTS = YES
+REFERENCED_BY_RELATION = NO
+REFERENCES_RELATION = NO
+REFERENCES_LINK_SOURCE = YES
+SOURCE_TOOLTIPS = YES
+USE_HTAGS = NO
+VERBATIM_HEADERS = YES
+CLANG_ASSISTED_PARSING = NO
+CLANG_OPTIONS =
+#---------------------------------------------------------------------------
+# Configuration options related to the alphabetical class index
+#---------------------------------------------------------------------------
+ALPHABETICAL_INDEX = YES
+COLS_IN_ALPHA_INDEX = 5
+IGNORE_PREFIX =
+#---------------------------------------------------------------------------
+# Configuration options related to the HTML output
+#---------------------------------------------------------------------------
+GENERATE_HTML = YES
+HTML_OUTPUT = html
+HTML_FILE_EXTENSION = .html
+HTML_HEADER =
+HTML_FOOTER =
+HTML_STYLESHEET =
+HTML_EXTRA_STYLESHEET =
+HTML_EXTRA_FILES =
+HTML_COLORSTYLE_HUE = 220
+HTML_COLORSTYLE_SAT = 100
+HTML_COLORSTYLE_GAMMA = 80
+HTML_TIMESTAMP = YES
+HTML_DYNAMIC_SECTIONS = NO
+HTML_INDEX_NUM_ENTRIES = 100
+GENERATE_DOCSET = NO
+DOCSET_FEEDNAME = "Doxygen generated docs"
+DOCSET_BUNDLE_ID = org.doxygen.Project
+DOCSET_PUBLISHER_ID = org.doxygen.Publisher
+DOCSET_PUBLISHER_NAME = Publisher
+GENERATE_HTMLHELP = NO
+CHM_FILE =
+HHC_LOCATION =
+GENERATE_CHI = NO
+CHM_INDEX_ENCODING =
+BINARY_TOC = NO
+TOC_EXPAND = NO
+GENERATE_QHP = NO
+QCH_FILE =
+QHP_NAMESPACE = org.doxygen.Project
+QHP_VIRTUAL_FOLDER = doc
+QHP_CUST_FILTER_NAME =
+QHP_CUST_FILTER_ATTRS =
+QHP_SECT_FILTER_ATTRS =
+QHG_LOCATION =
+GENERATE_ECLIPSEHELP = NO
+ECLIPSE_DOC_ID = org.doxygen.Project
+DISABLE_INDEX = NO
+GENERATE_TREEVIEW = NO
+ENUM_VALUES_PER_LINE = 4
+TREEVIEW_WIDTH = 250
+EXT_LINKS_IN_WINDOW = NO
+FORMULA_FONTSIZE = 10
+FORMULA_TRANSPARENT = YES
+USE_MATHJAX = NO
+MATHJAX_FORMAT = HTML-CSS
+MATHJAX_RELPATH = http://cdn.mathjax.org/mathjax/latest
+MATHJAX_EXTENSIONS =
+MATHJAX_CODEFILE =
+SEARCHENGINE = YES
+SERVER_BASED_SEARCH = NO
+EXTERNAL_SEARCH = NO
+SEARCHENGINE_URL =
+SEARCHDATA_FILE = searchdata.xml
+EXTERNAL_SEARCH_ID =
+EXTRA_SEARCH_MAPPINGS =
+#---------------------------------------------------------------------------
+# Configuration options related to the LaTeX output
+#---------------------------------------------------------------------------
+GENERATE_LATEX = YES
+LATEX_OUTPUT = latex
+LATEX_CMD_NAME = latex
+MAKEINDEX_CMD_NAME = makeindex
+COMPACT_LATEX = NO
+PAPER_TYPE = a4
+EXTRA_PACKAGES =
+LATEX_HEADER =
+LATEX_FOOTER =
+LATEX_EXTRA_FILES =
+PDF_HYPERLINKS = YES
+USE_PDFLATEX = YES
+LATEX_BATCHMODE = NO
+LATEX_HIDE_INDICES = NO
+LATEX_SOURCE_CODE = NO
+LATEX_BIB_STYLE = plain
+#---------------------------------------------------------------------------
+# Configuration options related to the RTF output
+#---------------------------------------------------------------------------
+GENERATE_RTF = NO
+RTF_OUTPUT = rtf
+COMPACT_RTF = NO
+RTF_HYPERLINKS = NO
+RTF_STYLESHEET_FILE =
+RTF_EXTENSIONS_FILE =
+#---------------------------------------------------------------------------
+# Configuration options related to the man page output
+#---------------------------------------------------------------------------
+GENERATE_MAN = NO
+MAN_OUTPUT = man
+MAN_EXTENSION = .3
+MAN_SUBDIR =
+MAN_LINKS = NO
+#---------------------------------------------------------------------------
+# Configuration options related to the XML output
+#---------------------------------------------------------------------------
+GENERATE_XML = NO
+XML_OUTPUT = xml
+XML_PROGRAMLISTING = YES
+#---------------------------------------------------------------------------
+# Configuration options related to the DOCBOOK output
+#---------------------------------------------------------------------------
+GENERATE_DOCBOOK = NO
+DOCBOOK_OUTPUT = docbook
+DOCBOOK_PROGRAMLISTING = NO
+#---------------------------------------------------------------------------
+# Configuration options for the AutoGen Definitions output
+#---------------------------------------------------------------------------
+GENERATE_AUTOGEN_DEF = NO
+#---------------------------------------------------------------------------
+# Configuration options related to the Perl module output
+#---------------------------------------------------------------------------
+GENERATE_PERLMOD = NO
+PERLMOD_LATEX = NO
+PERLMOD_PRETTY = YES
+PERLMOD_MAKEVAR_PREFIX =
+#---------------------------------------------------------------------------
+# Configuration options related to the preprocessor
+#---------------------------------------------------------------------------
+ENABLE_PREPROCESSING = YES
+MACRO_EXPANSION = NO
+EXPAND_ONLY_PREDEF = NO
+SEARCH_INCLUDES = YES
+INCLUDE_PATH =
+INCLUDE_FILE_PATTERNS =
+PREDEFINED =
+EXPAND_AS_DEFINED =
+SKIP_FUNCTION_MACROS = YES
+#---------------------------------------------------------------------------
+# Configuration options related to external references
+#---------------------------------------------------------------------------
+TAGFILES =
+GENERATE_TAGFILE =
+ALLEXTERNALS = NO
+EXTERNAL_GROUPS = YES
+EXTERNAL_PAGES = YES
+PERL_PATH = /usr/bin/perl
+#---------------------------------------------------------------------------
+# Configuration options related to the dot tool
+#---------------------------------------------------------------------------
+CLASS_DIAGRAMS = YES
+MSCGEN_PATH =
+DIA_PATH =
+HIDE_UNDOC_RELATIONS = YES
+HAVE_DOT = YES
+DOT_NUM_THREADS = 0
+DOT_FONTNAME = Helvetica
+DOT_FONTSIZE = 10
+DOT_FONTPATH =
+CLASS_GRAPH = YES
+COLLABORATION_GRAPH = YES
+GROUP_GRAPHS = YES
+UML_LOOK = NO
+UML_LIMIT_NUM_FIELDS = 10
+TEMPLATE_RELATIONS = NO
+INCLUDE_GRAPH = YES
+INCLUDED_BY_GRAPH = YES
+CALL_GRAPH = NO
+CALLER_GRAPH = NO
+GRAPHICAL_HIERARCHY = YES
+DIRECTORY_GRAPH = YES
+DOT_IMAGE_FORMAT = png
+INTERACTIVE_SVG = NO
+DOT_PATH =
+DOTFILE_DIRS =
+MSCFILE_DIRS =
+DIAFILE_DIRS =
+PLANTUML_JAR_PATH =
+DOT_GRAPH_MAX_NODES = 50
+MAX_DOT_GRAPH_DEPTH = 0
+DOT_TRANSPARENT = NO
+DOT_MULTI_TARGETS = NO
+GENERATE_LEGEND = YES
+DOT_CLEANUP = YES
diff --git a/tools/devdocs.doxyfile b/tools/devdocs.doxyfile
new file mode 100644
index 0000000..4320128
--- /dev/null
+++ b/tools/devdocs.doxyfile
@@ -0,0 +1,314 @@
+# Doxyfile 1.8.8
+
+#---------------------------------------------------------------------------
+# Project related configuration options
+#---------------------------------------------------------------------------
+DOXYFILE_ENCODING = UTF-8
+PROJECT_NAME = "Tool Internals"
+PROJECT_NUMBER =
+PROJECT_BRIEF =
+PROJECT_LOGO =
+OUTPUT_DIRECTORY = devdocs
+CREATE_SUBDIRS = NO
+ALLOW_UNICODE_NAMES = NO
+OUTPUT_LANGUAGE = English
+BRIEF_MEMBER_DESC = YES
+REPEAT_BRIEF = YES
+ABBREVIATE_BRIEF =
+ALWAYS_DETAILED_SEC = NO
+INLINE_INHERITED_MEMB = NO
+FULL_PATH_NAMES = YES
+STRIP_FROM_PATH =
+STRIP_FROM_INC_PATH =
+SHORT_NAMES = NO
+JAVADOC_AUTOBRIEF = YES
+QT_AUTOBRIEF = NO
+MULTILINE_CPP_IS_BRIEF = NO
+INHERIT_DOCS = YES
+SEPARATE_MEMBER_PAGES = NO
+TAB_SIZE = 4
+ALIASES =
+TCL_SUBST =
+OPTIMIZE_OUTPUT_FOR_C = YES
+OPTIMIZE_OUTPUT_JAVA = NO
+OPTIMIZE_FOR_FORTRAN = NO
+OPTIMIZE_OUTPUT_VHDL = NO
+EXTENSION_MAPPING =
+MARKDOWN_SUPPORT = YES
+AUTOLINK_SUPPORT = YES
+BUILTIN_STL_SUPPORT = NO
+CPP_CLI_SUPPORT = NO
+SIP_SUPPORT = NO
+IDL_PROPERTY_SUPPORT = YES
+DISTRIBUTE_GROUP_DOC = NO
+SUBGROUPING = YES
+INLINE_GROUPED_CLASSES = NO
+INLINE_SIMPLE_STRUCTS = NO
+TYPEDEF_HIDES_STRUCT = NO
+LOOKUP_CACHE_SIZE = 0
+#---------------------------------------------------------------------------
+# Build related configuration options
+#---------------------------------------------------------------------------
+EXTRACT_ALL = YES
+EXTRACT_PRIVATE = NO
+EXTRACT_PACKAGE = NO
+EXTRACT_STATIC = NO
+EXTRACT_LOCAL_CLASSES = YES
+EXTRACT_LOCAL_METHODS = NO
+EXTRACT_ANON_NSPACES = NO
+HIDE_UNDOC_MEMBERS = NO
+HIDE_UNDOC_CLASSES = NO
+HIDE_FRIEND_COMPOUNDS = NO
+HIDE_IN_BODY_DOCS = NO
+INTERNAL_DOCS = NO
+CASE_SENSE_NAMES = YES
+HIDE_SCOPE_NAMES = NO
+SHOW_INCLUDE_FILES = YES
+SHOW_GROUPED_MEMB_INC = NO
+FORCE_LOCAL_INCLUDES = NO
+INLINE_INFO = YES
+SORT_MEMBER_DOCS = YES
+SORT_BRIEF_DOCS = NO
+SORT_MEMBERS_CTORS_1ST = NO
+SORT_GROUP_NAMES = NO
+SORT_BY_SCOPE_NAME = NO
+STRICT_PROTO_MATCHING = NO
+GENERATE_TODOLIST = YES
+GENERATE_TESTLIST = YES
+GENERATE_BUGLIST = YES
+GENERATE_DEPRECATEDLIST= YES
+ENABLED_SECTIONS =
+MAX_INITIALIZER_LINES = 30
+SHOW_USED_FILES = YES
+SHOW_FILES = YES
+SHOW_NAMESPACES = YES
+FILE_VERSION_FILTER =
+LAYOUT_FILE =
+CITE_BIB_FILES =
+#---------------------------------------------------------------------------
+# Configuration options related to warning and progress messages
+#---------------------------------------------------------------------------
+QUIET = NO
+WARNINGS = YES
+WARN_IF_UNDOCUMENTED = YES
+WARN_IF_DOC_ERROR = YES
+WARN_NO_PARAMDOC = NO
+WARN_FORMAT = "$file:$line: $text"
+WARN_LOGFILE =
+#---------------------------------------------------------------------------
+# Configuration options related to the input files
+#---------------------------------------------------------------------------
+INPUT = \
+ zunitc \
+ waycheck
+INPUT_ENCODING = UTF-8
+FILE_PATTERNS =
+RECURSIVE = YES
+EXCLUDE =
+EXCLUDE_SYMLINKS = NO
+EXCLUDE_PATTERNS =
+EXCLUDE_SYMBOLS =
+EXAMPLE_PATH =
+EXAMPLE_PATTERNS =
+EXAMPLE_RECURSIVE = NO
+IMAGE_PATH =
+INPUT_FILTER =
+FILTER_PATTERNS =
+FILTER_SOURCE_FILES = NO
+FILTER_SOURCE_PATTERNS =
+USE_MDFILE_AS_MAINPAGE =
+#---------------------------------------------------------------------------
+# Configuration options related to source browsing
+#---------------------------------------------------------------------------
+SOURCE_BROWSER = NO
+INLINE_SOURCES = NO
+STRIP_CODE_COMMENTS = YES
+REFERENCED_BY_RELATION = NO
+REFERENCES_RELATION = NO
+REFERENCES_LINK_SOURCE = YES
+SOURCE_TOOLTIPS = YES
+USE_HTAGS = NO
+VERBATIM_HEADERS = YES
+CLANG_ASSISTED_PARSING = NO
+CLANG_OPTIONS =
+#---------------------------------------------------------------------------
+# Configuration options related to the alphabetical class index
+#---------------------------------------------------------------------------
+ALPHABETICAL_INDEX = YES
+COLS_IN_ALPHA_INDEX = 5
+IGNORE_PREFIX =
+#---------------------------------------------------------------------------
+# Configuration options related to the HTML output
+#---------------------------------------------------------------------------
+GENERATE_HTML = YES
+HTML_OUTPUT = html
+HTML_FILE_EXTENSION = .html
+HTML_HEADER =
+HTML_FOOTER =
+HTML_STYLESHEET =
+HTML_EXTRA_STYLESHEET =
+HTML_EXTRA_FILES =
+HTML_COLORSTYLE_HUE = 220
+HTML_COLORSTYLE_SAT = 100
+HTML_COLORSTYLE_GAMMA = 80
+HTML_TIMESTAMP = YES
+HTML_DYNAMIC_SECTIONS = NO
+HTML_INDEX_NUM_ENTRIES = 100
+GENERATE_DOCSET = NO
+DOCSET_FEEDNAME = "Doxygen generated docs"
+DOCSET_BUNDLE_ID = org.doxygen.Project
+DOCSET_PUBLISHER_ID = org.doxygen.Publisher
+DOCSET_PUBLISHER_NAME = Publisher
+GENERATE_HTMLHELP = NO
+CHM_FILE =
+HHC_LOCATION =
+GENERATE_CHI = NO
+CHM_INDEX_ENCODING =
+BINARY_TOC = NO
+TOC_EXPAND = NO
+GENERATE_QHP = NO
+QCH_FILE =
+QHP_NAMESPACE = org.doxygen.Project
+QHP_VIRTUAL_FOLDER = doc
+QHP_CUST_FILTER_NAME =
+QHP_CUST_FILTER_ATTRS =
+QHP_SECT_FILTER_ATTRS =
+QHG_LOCATION =
+GENERATE_ECLIPSEHELP = NO
+ECLIPSE_DOC_ID = org.doxygen.Project
+DISABLE_INDEX = NO
+GENERATE_TREEVIEW = NO
+ENUM_VALUES_PER_LINE = 4
+TREEVIEW_WIDTH = 250
+EXT_LINKS_IN_WINDOW = NO
+FORMULA_FONTSIZE = 10
+FORMULA_TRANSPARENT = YES
+USE_MATHJAX = NO
+MATHJAX_FORMAT = HTML-CSS
+MATHJAX_RELPATH = http://cdn.mathjax.org/mathjax/latest
+MATHJAX_EXTENSIONS =
+MATHJAX_CODEFILE =
+SEARCHENGINE = YES
+SERVER_BASED_SEARCH = NO
+EXTERNAL_SEARCH = NO
+SEARCHENGINE_URL =
+SEARCHDATA_FILE = searchdata.xml
+EXTERNAL_SEARCH_ID =
+EXTRA_SEARCH_MAPPINGS =
+#---------------------------------------------------------------------------
+# Configuration options related to the LaTeX output
+#---------------------------------------------------------------------------
+GENERATE_LATEX = YES
+LATEX_OUTPUT = latex
+LATEX_CMD_NAME = latex
+MAKEINDEX_CMD_NAME = makeindex
+COMPACT_LATEX = NO
+PAPER_TYPE = a4
+EXTRA_PACKAGES =
+LATEX_HEADER =
+LATEX_FOOTER =
+LATEX_EXTRA_FILES =
+PDF_HYPERLINKS = YES
+USE_PDFLATEX = YES
+LATEX_BATCHMODE = NO
+LATEX_HIDE_INDICES = NO
+LATEX_SOURCE_CODE = NO
+LATEX_BIB_STYLE = plain
+#---------------------------------------------------------------------------
+# Configuration options related to the RTF output
+#---------------------------------------------------------------------------
+GENERATE_RTF = NO
+RTF_OUTPUT = rtf
+COMPACT_RTF = NO
+RTF_HYPERLINKS = NO
+RTF_STYLESHEET_FILE =
+RTF_EXTENSIONS_FILE =
+#---------------------------------------------------------------------------
+# Configuration options related to the man page output
+#---------------------------------------------------------------------------
+GENERATE_MAN = NO
+MAN_OUTPUT = man
+MAN_EXTENSION = .3
+MAN_SUBDIR =
+MAN_LINKS = NO
+#---------------------------------------------------------------------------
+# Configuration options related to the XML output
+#---------------------------------------------------------------------------
+GENERATE_XML = NO
+XML_OUTPUT = xml
+XML_PROGRAMLISTING = YES
+#---------------------------------------------------------------------------
+# Configuration options related to the DOCBOOK output
+#---------------------------------------------------------------------------
+GENERATE_DOCBOOK = NO
+DOCBOOK_OUTPUT = docbook
+DOCBOOK_PROGRAMLISTING = NO
+#---------------------------------------------------------------------------
+# Configuration options for the AutoGen Definitions output
+#---------------------------------------------------------------------------
+GENERATE_AUTOGEN_DEF = NO
+#---------------------------------------------------------------------------
+# Configuration options related to the Perl module output
+#---------------------------------------------------------------------------
+GENERATE_PERLMOD = NO
+PERLMOD_LATEX = NO
+PERLMOD_PRETTY = YES
+PERLMOD_MAKEVAR_PREFIX =
+#---------------------------------------------------------------------------
+# Configuration options related to the preprocessor
+#---------------------------------------------------------------------------
+ENABLE_PREPROCESSING = YES
+MACRO_EXPANSION = NO
+EXPAND_ONLY_PREDEF = NO
+SEARCH_INCLUDES = YES
+INCLUDE_PATH =
+INCLUDE_FILE_PATTERNS =
+PREDEFINED =
+EXPAND_AS_DEFINED =
+SKIP_FUNCTION_MACROS = YES
+#---------------------------------------------------------------------------
+# Configuration options related to external references
+#---------------------------------------------------------------------------
+TAGFILES =
+GENERATE_TAGFILE =
+ALLEXTERNALS = NO
+EXTERNAL_GROUPS = YES
+EXTERNAL_PAGES = YES
+PERL_PATH = /usr/bin/perl
+#---------------------------------------------------------------------------
+# Configuration options related to the dot tool
+#---------------------------------------------------------------------------
+CLASS_DIAGRAMS = YES
+MSCGEN_PATH =
+DIA_PATH =
+HIDE_UNDOC_RELATIONS = YES
+HAVE_DOT = YES
+DOT_NUM_THREADS = 0
+DOT_FONTNAME = Helvetica
+DOT_FONTSIZE = 10
+DOT_FONTPATH =
+CLASS_GRAPH = YES
+COLLABORATION_GRAPH = YES
+GROUP_GRAPHS = YES
+UML_LOOK = NO
+UML_LIMIT_NUM_FIELDS = 10
+TEMPLATE_RELATIONS = NO
+INCLUDE_GRAPH = YES
+INCLUDED_BY_GRAPH = YES
+CALL_GRAPH = NO
+CALLER_GRAPH = NO
+GRAPHICAL_HIERARCHY = YES
+DIRECTORY_GRAPH = YES
+DOT_IMAGE_FORMAT = png
+INTERACTIVE_SVG = NO
+DOT_PATH =
+DOTFILE_DIRS =
+MSCFILE_DIRS =
+DIAFILE_DIRS =
+PLANTUML_JAR_PATH =
+DOT_GRAPH_MAX_NODES = 50
+MAX_DOT_GRAPH_DEPTH = 0
+DOT_TRANSPARENT = NO
+DOT_MULTI_TARGETS = NO
+GENERATE_LEGEND = YES
+DOT_CLEANUP = YES
diff --git a/tools/tools.dox b/tools/tools.dox
new file mode 100644
index 0000000..80c2f51
--- /dev/null
+++ b/tools/tools.dox
@@ -0,0 +1,29 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/**
+ at mainpage
+
+- @ref zunitc - Simple test framework
+
+- @ref waycheck - Simple integration/acceptance test tool
+*/
\ No newline at end of file
diff --git a/tools/waycheck/rough_draw.c b/tools/waycheck/rough_draw.c
new file mode 100644
index 0000000..5b1cbaf
--- /dev/null
+++ b/tools/waycheck/rough_draw.c
@@ -0,0 +1,176 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include <stddef.h>
+
+#include "rough_draw.h"
+
+static void fillRect(pixel *raw, pixel val, int width, int height, int stride)
+{
+ int x = 0;
+ int y = 0;
+
+ for (y = 0; y < height; ++y) {
+ pixel *ptr = raw + (y * stride);
+ for (x = 0; x < width; ++x) {
+ *(ptr++) = val;
+ }
+ }
+}
+
+static pixel meld(pixel val1, pixel val2, double factor)
+{
+ pixel result = val1;
+ unsigned char *p0 = (unsigned char *)&result;
+ unsigned char *p1 = (unsigned char *)&val2;
+ size_t i;
+ for (i = 0; i < sizeof(pixel); ++i) {
+ p0[i] = ((int)(((p0[i] << 8) * (1.0 - factor))
+ + ((p1[i] << 8) * factor))) >> 8;
+ }
+ return result;
+}
+
+static void gradRect(pixel *raw, pixel val1, pixel val2,
+ int width, int height, int stride)
+{
+ int x = 0;
+ int y = 0;
+
+ double dwidth = (double)width;
+ for (x = 0; x < width; ++x) {
+ pixel melded = meld(val1, val2, x / dwidth);
+ for (y = 0; y < height; ++y) {
+ pixel *ptr = raw + (y * stride) + x;
+ *ptr = melded;
+ }
+ }
+}
+
+void draw_bars(pixel *raw, int width, int height)
+{
+ pixel bars[] = {0xffb4b4b4, 0xffb4b410, 0xff10b4b4, 0xff10b410,
+ 0xffb410b4, 0xffb41010, 0xff1010b4};
+ if (raw) {
+ int y0 = ((height * 1.75) / 3);
+ int y1 = ((height * 2) / 3);
+ int y2 = ((height * 3) / 4);
+ int h1 = y1 - y0;
+ int h2 = height - y2;
+ int w1 = width / 8;
+ int w2 = (width * 0.75) / 7;
+ int xr = (width * 7) / 8;
+
+ fillRect(raw, 0x7f1f1f1f, width, height, width);
+
+ // left gray:
+ fillRect(raw, 0xff686868, w1, y0, width);
+ fillRect(raw + (y0 * width), 0xff10ebeb, w1, h1, width);
+ fillRect(raw + (y1 * width), 0xffebeb10, w1, h1, width);
+ fillRect(raw + (y2 * width), 0xff313131, w1, h2, width);
+
+ // right gray:
+ fillRect(raw + xr, 0xff686868, w1, y0, width);
+ fillRect(raw + xr + (y0 * width), 0xff1010eb, w1, h1, width);
+ fillRect(raw + xr + (y1 * width), 0xffeb1010, w1, h1, width);
+ fillRect(raw + xr + (y2 * width), 0xff313131, w1, h2, width);
+
+ int xoff = w1;
+ fillRect(raw + xoff + (y0 * width), 0xffebebeb, w2, h1, width);
+ fillRect(raw + xoff + (y1 * width), 0xff101010, w2, h1, width);
+
+ double barSpan = (width * 0.75);
+ size_t barCount = sizeof(bars) / sizeof(bars[0]);
+ size_t i = 0;
+ for (i = 0; i < barCount; ++i)
+ {
+ xoff = (barSpan * i) / barCount;
+ int ww = (barSpan * (i + 1)) / barCount;
+ ww -= xoff;
+ xoff += w1;
+ fillRect(raw + xoff, bars[i], ww, y0, width);
+ }
+
+ int hw = width - (w1 + w1 + w2);
+ // Gray horiz:
+ xoff = w1 + w2;
+ fillRect(raw + xoff + (y0 * width), 0xffb4b4b4, hw, h1, width);
+ gradRect(raw + xoff + (y1 * width), 0xff101010, 0xffebebeb,
+ hw, h1, width);
+
+
+ xoff = (width * 0.85625) / 3;
+ int w3 = (width * 0.64375) / 3;
+ fillRect(raw + w1 + (y2 * width), 0xff101010, width - (w1 * 2),
+ h2, width);
+ fillRect(raw + xoff + (y2 * width), 0xffebebeb, w3, h2, width);
+
+ int w4 = (width * 0.10625) / 3;
+ xoff = (width * 1.765625) / 3;
+ fillRect(raw + xoff + (y2 * width), 0xff0c0c0c, w4, h2, width);
+
+ xoff = (width * 1.98125) / 3;
+ fillRect(raw + xoff + (y2 * width), 0xff141414, w4, h2, width);
+
+ xoff = (width * 2.196875) / 3;
+ fillRect(raw + xoff + (y2 * width), 0xff191919, w4, h2, width);
+ }
+}
+
+void draw_crosshairs(pixel *raw, int width, int height)
+{
+ if (raw) {
+ pixel fg = 0x7f000000;
+ pixel bg = 0x7f7f7f7f;
+ int x = (width + 1) / 2;
+ int y = (height + 1) / 2;
+
+ fillRect(raw + ((y - 1) * width), bg,
+ width, 3, width);
+ fillRect(raw + (y * width), fg, width, 1, width);
+
+ fillRect(raw + ((y - 2) * width), bg,
+ width / 3, 5, width);
+ fillRect(raw + ((y - 1) * width), fg,
+ width / 3, 3, width);
+ fillRect(raw + ((y - 2) * width + (width * 2 / 3)), bg,
+ width / 3, 5, width);
+ fillRect(raw + ((y - 1) * width + (width * 2 / 3)), fg,
+ width / 3, 3, width);
+
+//
+
+ fillRect(raw + x - 1, bg,
+ 3, height, width);
+ fillRect(raw + x, fg,
+ 1, height, width);
+
+ fillRect(raw + x - 2, bg,
+ 5, height / 3, width);
+ fillRect(raw + x - 1, fg,
+ 3, height / 3, width);
+ fillRect(raw + x - 2 + ((height * 2 / 3) * width), bg,
+ 5, height / 3, width);
+ fillRect(raw + x - 1 + ((height * 2 / 3) * width), fg,
+ 3, height / 3, width);
+ }
+}
diff --git a/tools/waycheck/rough_draw.h b/tools/waycheck/rough_draw.h
new file mode 100644
index 0000000..7f1c847
--- /dev/null
+++ b/tools/waycheck/rough_draw.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef ROUGH_DRAW_H_SEEN_
+#define ROUGH_DRAW_H_SEEN_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdint.h>
+
+typedef uint32_t pixel;
+
+void draw_bars(pixel *raw, int width, int height);
+
+void draw_crosshairs(pixel *raw, int width, int height);
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
+
+#endif // ROUGH_DRAW_H_SEEN_
diff --git a/tools/waycheck/waycheck.c b/tools/waycheck/waycheck.c
new file mode 100644
index 0000000..2d6c6be
--- /dev/null
+++ b/tools/waycheck/waycheck.c
@@ -0,0 +1,505 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include "config.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+#include <stdbool.h>
+
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+
+#include <sys/mman.h>
+
+#include <linux/input.h>
+#include <wayland-client.h>
+
+
+#include "os-compatibility.h"
+#include "rough_draw.h"
+#include "wtst_fixtures.h"
+#include "zunitc/zunitc.h"
+
+// - - - - - - - - - -
+
+/**
+ * Baseline test to see if a connection can be made to the Wayland server.
+ */
+ZUC_TEST(BaseTest, CanConnectDisplay)
+{
+ struct wl_display *display = wl_display_connect(NULL);
+
+ ZUC_EXPECT_TRUE(display != NULL);
+
+ if (display) {
+ wl_display_disconnect(display);
+ display = NULL;
+ }
+}
+
+// A very simple case that only exercises the test fixture.
+ZUC_TEST(BaseTest, HelloWayland)
+{
+ wtst_ctx *ctx = wtst_ctx_create();
+
+ ZUC_EXPECT_TRUE(ctx != NULL);
+
+ wtst_ctx_destroy(ctx);
+}
+
+ZUC_TEST(BaseTest, AdvertisesRequired)
+{
+ char const *required[] = {
+ "wl_compositor",
+ "wl_data_device_manager",
+ //wl_drm
+ //wl_input_method
+ //wl_input_panel
+ "wl_output",
+ //wl_scaler
+ "wl_seat",
+ "wl_shell",
+ "wl_shm",
+ "wl_subcompositor",
+ //wl_text_input_manager
+ };
+
+ wtst_ctx *ctx = wtst_ctx_create();
+
+ int num_required = sizeof(required) / sizeof(required[0]);
+ int i;
+ for (i = 0; i < num_required; i++) {
+ printf("Check %s\n", required[i]);
+ ZUC_EXPECT_TRUE(wtst_is_global_advertised(ctx, required[i]));
+ }
+
+ wtst_ctx_destroy(ctx);
+}
+
+
+// Forward declaration of internal testing structs:
+typedef struct _wtst_shm_pool wtst_shm_pool;
+typedef struct _wtst_pointer wtst_pointer;
+typedef struct _wtst_shell_surface wtst_shell_surface;
+typedef struct _wtst_surface wtst_surface;
+
+typedef void (*button_cb)(uint32_t serial, uint32_t time,
+ uint32_t button, uint32_t state);
+
+// Simple testing helpers:
+static pixel *wtst_shm_pool_get_membuf(wtst_shm_pool *pool);
+static struct wl_shm_pool *wtst_shm_pool_get_pool(wtst_shm_pool *pool);
+static void wtst_shm_pool_consume(wtst_shm_pool *pool, size_t mem_used);
+static struct wl_surface *wtst_shell_surface_get_surface(wtst_shell_surface *);
+
+static wtst_shm_pool *wtst_create_mempool(struct wl_shm *shm,
+ int fd, size_t flen);
+
+static wtst_shell_surface *wtst_create_shell_surface(struct wl_compositor *
+ compositor,
+ struct wl_shell *shell);
+
+static wtst_pointer *set_pointer_with_cursor(wtst_shm_pool *pool,
+ unsigned int width,
+ unsigned int height,
+ int32_t hit_x, int32_t hit_y,
+ struct wl_compositor *compositor,
+ struct wl_pointer *pointer);
+
+static void set_button_cb(wtst_shell_surface *shell_surface,
+ button_cb callback);
+
+//
+
+static const struct wl_pointer_listener pointer_listener;
+
+static bool keep_alive = true;
+
+static void handle_button(uint32_t serial, uint32_t time,
+ uint32_t button, uint32_t state)
+{
+ keep_alive = false;
+}
+
+static const uint32_t PIXEL_FORMAT = WL_SHM_FORMAT_ARGB8888;
+
+
+ZUC_TEST(BaseTest, DoTheWork)
+{
+ wtst_ctx *ctx = wtst_ctx_create();
+
+ keep_alive = false; // Don't run the main loop for normal testing
+
+ // 320x200 == 4:3
+
+ // 320x180
+ // 355x200~
+ // 480x270
+ // 640x360
+ const int surf_width = 355;
+ const int surf_height = 200;
+
+ const int cursor_size = 45;
+
+ size_t needed = sizeof(pixel) * surf_width * surf_height;
+ needed += sizeof(pixel) * cursor_size * cursor_size;
+
+ int anon = os_create_anonymous_file(needed);
+ wtst_shm_pool *pool = wtst_create_mempool(ctx->shm, anon, needed);
+ struct wl_buffer *buffer = NULL;
+ if (pool) {
+ pixel *mem = wtst_shm_pool_get_membuf(pool);
+ draw_bars(mem, surf_width, surf_height);
+
+ struct wl_shm_pool *shpool =
+ wtst_shm_pool_get_pool(pool);
+ buffer = wl_shm_pool_create_buffer(shpool,
+ 0,
+ surf_width,
+ surf_height,
+ surf_width * sizeof(pixel),
+ PIXEL_FORMAT);
+ wtst_shm_pool_consume(pool,
+ surf_width * surf_height * sizeof(pixel));
+ }
+
+ wtst_shell_surface *sh_surface =
+ wtst_create_shell_surface(ctx->compositor, ctx->shell);
+
+ if (buffer) {
+ struct wl_surface *surface =
+ wtst_shell_surface_get_surface(sh_surface);
+
+ wl_surface_attach(surface, buffer, 0, 0);
+ wl_surface_commit(surface);
+ }
+
+ int mid_hit = cursor_size / 2;
+ wtst_pointer *pointer = set_pointer_with_cursor(pool,
+ cursor_size,
+ cursor_size,
+ mid_hit, mid_hit,
+ ctx->compositor,
+ ctx->pointer);
+
+ set_button_cb(sh_surface, handle_button);
+ wl_pointer_add_listener(ctx->pointer, &pointer_listener, pointer);
+
+ while (keep_alive) {
+ if (wl_display_dispatch(ctx->display) < 0)
+ keep_alive = false;
+ }
+
+ //hello_free_buffer(buffer);
+ wl_buffer_destroy(buffer);
+ //hello_cleanup_wayland();
+
+ wtst_ctx_destroy(ctx);
+}
+
+int main( int argc, const char* argv[] )
+{
+ ZUC_ADD_TEST(BaseTest, CanConnectDisplay);
+ ZUC_ADD_TEST(BaseTest, HelloWayland);
+ ZUC_ADD_TEST(BaseTest, AdvertisesRequired);
+ ZUC_ADD_TEST(BaseTest, DoTheWork);
+
+ ZUC_RUN_TESTS();
+
+ return 0;
+}
+
+// ========================================================================
+// ========================================================================
+// ========================================================================
+// ========================================================================
+
+struct _wtst_shm_pool {
+ struct wl_shm_pool *pool;
+ //
+ int fd;
+ pixel *membuf;
+ size_t flen;
+ size_t used;
+};
+
+struct _wtst_pointer {
+ struct wl_pointer *pointer;
+ //
+ pixel *membuf;
+ struct wl_buffer *buffer;
+ struct wl_surface *surface; /**< Surface containing the image. */
+ struct wl_surface *current_surface;
+ int32_t hit_x;
+ int32_t hit_y;
+};
+
+struct _wtst_shell_surface {
+ struct wl_shell_surface *shell_surface;
+ //
+ struct wl_surface *surface; /**< surface that this is wrapping. */
+ struct wl_shell_surface_listener listener;
+};
+
+struct _wtst_surface {
+ struct wl_surface *surface;
+ //
+ button_cb button;
+};
+
+pixel *wtst_shm_pool_get_membuf(wtst_shm_pool *pool)
+{
+ return (pool) ? pool->membuf : NULL;
+}
+
+struct wl_shm_pool *wtst_shm_pool_get_pool(wtst_shm_pool *pool)
+{
+ return (pool) ? pool->pool : NULL;
+}
+
+static void wtst_shm_pool_consume(wtst_shm_pool *pool, size_t mem_used)
+{
+ if (pool)
+ pool->used += mem_used;
+}
+
+wtst_shm_pool *wtst_create_mempool(struct wl_shm *shm, int fd, size_t flen)
+{
+ wtst_shm_pool *wtst_pool = malloc(sizeof(wtst_shm_pool));
+ if (wtst_pool) {
+ memset(wtst_pool, 0, sizeof(*wtst_pool));
+ wtst_pool->fd = fd;
+ wtst_pool->flen = flen;
+ wtst_pool->membuf = mmap(NULL, flen, PROT_READ | PROT_WRITE,
+ MAP_SHARED, fd, 0);
+ if (wtst_pool->membuf == MAP_FAILED) {
+ perror("ERROR: unable to memmap");
+ } else {
+ wtst_pool->pool = wl_shm_create_pool(shm, fd, flen);
+ if (!wtst_pool->pool) {
+ perror("ERROR: Unable to create pool");
+ munmap(wtst_pool->membuf, flen);
+ }
+ }
+
+ if (!wtst_pool->pool) {
+ free(wtst_pool);
+ wtst_pool = NULL;
+ }
+ }
+
+ return wtst_pool;
+}
+
+static void shell_surface_ping(void *data,
+ struct wl_shell_surface *shell_surface,
+ uint32_t serial)
+{
+ wl_shell_surface_pong(shell_surface, serial);
+}
+
+static void shell_surface_configure(void *data,
+ struct wl_shell_surface *shell_surface,
+ uint32_t edges, int32_t width, int32_t height)
+{
+}
+
+static const struct wl_shell_surface_listener
+shell_surface_listener = {
+ .ping = shell_surface_ping,
+ .configure = shell_surface_configure,
+};
+
+wtst_shell_surface *wtst_create_shell_surface(struct wl_compositor *compositor,
+ struct wl_shell *shell)
+{
+ wtst_shell_surface *wss = malloc(sizeof(wtst_shell_surface));
+ if (wss) {
+ memset(wss, 0, sizeof(*wss));
+ wss->listener.ping = shell_surface_ping;
+ wss->listener.configure = shell_surface_configure;
+
+ wss->surface = wl_compositor_create_surface(compositor);
+ }
+
+ if (wss && wss->surface) {
+ wss->shell_surface = wl_shell_get_shell_surface(shell,
+ wss->surface);
+ if (wss->shell_surface) {
+ wl_shell_surface_add_listener(wss->shell_surface,
+ &wss->listener,
+ wss);
+ wl_shell_surface_set_toplevel(wss->shell_surface);
+ wl_shell_surface_set_user_data(wss->shell_surface, wss);
+ wl_surface_set_user_data(wss->surface, NULL);
+ }
+ }
+
+ if (wss && (!wss->surface || !wss->shell_surface)) {
+ if (wss->surface)
+ wl_surface_destroy(wss->surface);
+ free(wss);
+ wss = NULL;
+ }
+
+ return wss;
+}
+
+struct wl_surface *
+wtst_shell_surface_get_surface(wtst_shell_surface *sh_surface)
+{
+ return (sh_surface) ? sh_surface->surface : NULL;
+}
+
+
+void set_button_cb(wtst_shell_surface *shell_surface, button_cb callback)
+{
+ if (shell_surface && shell_surface->surface) {
+ wtst_surface *wsurf =
+ wl_surface_get_user_data(shell_surface->surface);
+ if (!wsurf) {
+ wsurf = malloc(sizeof(wtst_surface));
+ if (wsurf) {
+ memset(wsurf, 0, sizeof(*wsurf));
+ wsurf->surface = shell_surface->surface;
+ wl_surface_set_user_data(wsurf->surface,
+ wsurf);
+ }
+ }
+
+ if (wsurf)
+ wsurf->button = callback;
+ }
+}
+
+wtst_pointer *set_pointer_with_cursor(wtst_shm_pool *pool,
+ unsigned int width, unsigned int height,
+ int32_t hit_x, int32_t hit_y,
+ struct wl_compositor *compositor,
+ struct wl_pointer *pointer)
+{
+ wtst_pointer *wtptr = malloc(sizeof(wtst_pointer));
+ if (wtptr) {
+ memset(wtptr, 0, sizeof(*wtptr));
+ wtptr->pointer = pointer;
+ wtptr->hit_x = hit_x;
+ wtptr->hit_y = hit_y;
+
+ wtptr->surface = wl_compositor_create_surface(compositor);
+ if (wtptr->surface) {
+ int32_t stride = width * sizeof(pixel);
+
+ wtptr->membuf = pool->membuf;
+ wtptr->membuf += pool->used / sizeof(*wtptr->membuf);
+ draw_crosshairs(wtptr->membuf, width, height);
+ //wtptr->membuf[0] = 0xfffc0000;
+
+ wtptr->buffer = wl_shm_pool_create_buffer(pool->pool,
+ pool->used,
+ width,
+ height,
+ stride,
+ PIXEL_FORMAT);
+ pool->used += width * height * sizeof(pixel);
+ }
+ }
+
+ if (wtptr && wtptr->buffer) {
+ draw_crosshairs(wtptr->membuf, width, height);
+ //wtptr->membuf[0] = 0xffc00000;
+ }
+
+ if (wtptr && !wtptr->buffer) {
+ if (wtptr->surface)
+ wl_surface_destroy(wtptr->surface);
+ free(wtptr);
+ wtptr = NULL;
+ }
+
+ wl_pointer_set_user_data(pointer, wtptr);
+
+ return wtptr;
+}
+
+
+static void foo_enter(void *data,
+ struct wl_pointer *wl_pointer,
+ uint32_t serial, struct wl_surface *surface,
+ wl_fixed_t surface_x, wl_fixed_t surface_y)
+{
+ wtst_pointer *pointer = (wtst_pointer *)data;
+ if (pointer) {
+ pointer->current_surface = surface;
+
+ wl_surface_attach(pointer->surface, pointer->buffer, 0, 0);
+ wl_surface_commit(pointer->surface);
+ wl_pointer_set_cursor(pointer->pointer, serial,
+ pointer->surface,
+ pointer->hit_x, pointer->hit_y);
+ }
+}
+
+static void foo_leave(void *data,
+ struct wl_pointer *wl_pointer, uint32_t serial,
+ struct wl_surface *wl_surface)
+{
+ wtst_pointer *pointer = (wtst_pointer *)data;
+ if (pointer)
+ pointer->current_surface = NULL;
+}
+
+static void foo_motion(void *data,
+ struct wl_pointer *wl_pointer, uint32_t time,
+ wl_fixed_t surface_x, wl_fixed_t surface_y)
+{
+}
+
+static void foo_button(void *data,
+ struct wl_pointer *wl_pointer, uint32_t serial,
+ uint32_t time, uint32_t button, uint32_t state)
+{
+ wtst_pointer *pointer = (wtst_pointer *)data;
+ if (pointer && pointer->current_surface) {
+ wtst_surface *wsurf =
+ wl_surface_get_user_data(pointer->current_surface);
+ if (wsurf && wsurf->button)
+ wsurf->button(serial, time, button, state);
+ }
+}
+
+static void foo_axis(void *data,
+ struct wl_pointer *wl_pointer, uint32_t time,
+ uint32_t axis, wl_fixed_t value)
+{
+}
+
+static const struct wl_pointer_listener pointer_listener = {
+ .enter = foo_enter,
+ .leave = foo_leave,
+ .motion = foo_motion,
+ .button = foo_button,
+ .axis = foo_axis
+};
diff --git a/tools/waycheck/waycheck.dox b/tools/waycheck/waycheck.dox
new file mode 100644
index 0000000..4e60604
--- /dev/null
+++ b/tools/waycheck/waycheck.dox
@@ -0,0 +1,29 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/**
+ at page waycheck
+
+A simple integration/acceptance tool to exercise Wayland compositors.
+
+Tests use @ref zunitc for their infrastructure, and most include use of a common wtst_ctx test fixture.
+*/
\ No newline at end of file
diff --git a/tools/waycheck/wtst_fixtures.c b/tools/waycheck/wtst_fixtures.c
new file mode 100644
index 0000000..437fd51
--- /dev/null
+++ b/tools/waycheck/wtst_fixtures.c
@@ -0,0 +1,289 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#include "wtst_fixtures.h"
+
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <wayland-client.h>
+
+typedef struct wtst_advertised {
+ uint32_t name;
+ char *interface;
+ uint32_t version;
+ //
+ struct wtst_advertised *next;
+} wtst_advertised;
+
+struct wtst_ctx_private {
+ int val;
+ wtst_advertised *adverts;
+};
+
+static void reg_global(void *data,
+ struct wl_registry *registry,
+ uint32_t name,
+ const char *interface,
+ uint32_t version);
+
+static void reg_global_remove(void *data,
+ struct wl_registry *registry,
+ uint32_t name);
+
+static void add_global_advert(wtst_ctx *ctx,
+ uint32_t name,
+ const char *interface,
+ uint32_t version);
+
+static wtst_ctx_private *wtst_ctx_private_create(void);
+
+static void wtst_ctx_private_destroy(wtst_ctx_private *private);
+
+static int logle = 0;
+
+
+wtst_ctx *wtst_ctx_create(void)
+{
+ wtst_ctx *ctx = malloc(sizeof(*ctx));
+ if (!ctx) {
+ perror("Unable to allocate context.");
+ } else {
+ memset(ctx, 0, sizeof(*ctx));
+ ctx->reg_listener = malloc(sizeof(*(ctx->reg_listener)));
+ memset(ctx->reg_listener, 0, sizeof(*(ctx->reg_listener)));
+
+ ctx->display = wl_display_connect(NULL);
+ if (!ctx->display) {
+ perror("Unable to connect to display");
+ free(ctx);
+ ctx = NULL;
+ } else {
+ ctx->private = wtst_ctx_private_create();
+
+ ctx->registry = wl_display_get_registry(ctx->display);
+
+ ctx->reg_listener->global = reg_global;
+ ctx->reg_listener->global_remove = reg_global_remove;
+
+ wl_registry_add_listener(ctx->registry,
+ ctx->reg_listener,
+ ctx);
+ wl_display_sync(ctx->display);
+ wl_display_roundtrip(ctx->display);
+ }
+ }
+
+ return ctx;
+}
+
+void wtst_ctx_destroy(wtst_ctx *ctx)
+{
+ if (ctx) {
+ if (ctx->registry)
+ wl_registry_destroy(ctx->registry);
+ if (ctx->reg_listener)
+ free(ctx->reg_listener);
+//
+
+ if (ctx->compositor)
+ wl_compositor_destroy(ctx->compositor);
+ if (ctx->display)
+ wl_display_disconnect(ctx->display);
+ if (ctx->shm)
+ wl_shm_destroy(ctx->shm);
+ if (ctx->shell)
+ wl_shell_destroy(ctx->shell);
+ if (ctx->seat)
+ wl_seat_destroy(ctx->seat);
+ if (ctx->pointer)
+ wl_pointer_destroy(ctx->pointer);
+
+ wtst_ctx_private_destroy(ctx->private);
+
+ free(ctx);
+ }
+}
+
+wtst_ctx_private *wtst_ctx_private_create(void)
+{
+ wtst_ctx_private *private = malloc(sizeof(wtst_ctx_private));
+ if (private) {
+ memset(private, 0, sizeof(*private));
+
+ // fill in simple marker
+ private->val = 0x59;
+ }
+
+ return private;
+}
+
+void wtst_ctx_private_destroy(wtst_ctx_private *private)
+{
+ if (private) {
+ if (private->adverts) {
+ // TODO
+ }
+ free(private);
+ }
+}
+
+
+void reg_global(void *data,
+ struct wl_registry *registry,
+ uint32_t name,
+ const char *interface,
+ uint32_t version)
+{
+ struct wtst_ctx *ctx = (struct wtst_ctx *)data;
+ if (logle > 1) {
+ printf("reg_global ++: %2d %s v%d\n",
+ name, interface, version);
+ }
+
+ add_global_advert(ctx, name, interface, version);
+
+ if (strcmp(interface, wl_seat_interface.name) == 0) {
+ if (ctx->seat)
+ wl_seat_destroy(ctx->seat);
+ ctx->seat = wl_registry_bind(registry,
+ name,
+ &wl_seat_interface,
+ version);
+ ctx->seat_name = name;
+
+ ctx->pointer = wl_seat_get_pointer(ctx->seat);
+
+ } else if (strcmp(interface, wl_compositor_interface.name) == 0) {
+ if (ctx->compositor)
+ wl_compositor_destroy(ctx->compositor);
+ ctx->compositor = wl_registry_bind(registry,
+ name,
+ &wl_compositor_interface,
+ version);
+ ctx->compositor_name = name;
+ } else if (strcmp(interface, wl_shm_interface.name) == 0) {
+ if (ctx->shm)
+ wl_shm_destroy(ctx->shm);
+ ctx->shm = wl_registry_bind(registry,
+ name,
+ &wl_shm_interface,
+ version);
+ ctx->shm_name = name;
+ } else if (strcmp(interface, wl_shell_interface.name) == 0) {
+ if (ctx->shell)
+ wl_shell_destroy(ctx->shell);
+ ctx->shell = wl_registry_bind(registry,
+ name,
+ &wl_shell_interface,
+ version);
+ ctx->shell_name = name;
+ }
+}
+
+void reg_global_remove(void *data,
+ struct wl_registry *registry,
+ uint32_t name)
+{
+ struct wtst_ctx *ctx = (struct wtst_ctx *)data;
+ if (logle > 1)
+ printf("reg_global --: %2d\n", name);
+ // TODO remove item from ctx list
+ if (name == ctx->seat_name) {
+ if (ctx->seat)
+ wl_seat_destroy(ctx->seat);
+ ctx->seat = NULL;
+ ctx->seat_name = 0;
+
+ wl_pointer_destroy(ctx->pointer);
+ ctx->pointer = 0;
+ } else if (name == ctx->compositor_name) {
+ if (ctx->compositor)
+ wl_compositor_destroy(ctx->compositor);
+ ctx->compositor = NULL;
+ ctx->compositor_name = 0;
+ } else if (name == ctx->shm_name) {
+ if (ctx->shm)
+ wl_shm_destroy(ctx->shm);
+ ctx->shm = NULL;
+ ctx->shm_name = 0;
+ } else if (name == ctx->shell_name) {
+ if (ctx->shell)
+ wl_shell_destroy(ctx->shell);
+ ctx->shell = NULL;
+ ctx->shell_name = 0;
+ }
+}
+
+// --
+
+void add_global_advert(wtst_ctx *ctx,
+ uint32_t name,
+ const char *interface,
+ uint32_t version)
+{
+ if (ctx && ctx->private) {
+ // See if we've got this interface already
+ wtst_advertised *curr;
+ for (curr = ctx->private->adverts; curr; curr = curr->next) {
+ if (strcmp(curr->interface, interface) == 0)
+ break;
+ }
+
+ if (curr) {
+ // Update these in case they have changed.
+ curr->name = name;
+ curr->version = version;
+ } else {
+ // create a new one
+ wtst_advertised *advert =
+ malloc(sizeof(wtst_advertised));
+ memset(advert, 0, sizeof(*advert));
+ advert->name = name;
+ advert->interface = strdup(interface);
+ advert->version = version;
+ curr = ctx->private->adverts;
+ while (curr && curr->next) {
+ curr = curr->next;
+ }
+ if (curr)
+ curr->next = advert;
+ else
+ ctx->private->adverts = advert;
+ }
+ }
+}
+
+int wtst_is_global_advertised(wtst_ctx *ctx, char const *interface)
+{
+ int found = 0;
+ if (ctx && ctx->private && interface) {
+ wtst_advertised *curr = ctx->private->adverts;
+ while (curr && strcmp(interface, curr->interface)) {
+ curr = curr->next;
+ }
+ found = curr != NULL;
+ }
+ return found;
+}
diff --git a/tools/waycheck/wtst_fixtures.h b/tools/waycheck/wtst_fixtures.h
new file mode 100644
index 0000000..c9c2756
--- /dev/null
+++ b/tools/waycheck/wtst_fixtures.h
@@ -0,0 +1,144 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef WTST_FIXTURES_H
+#define WTST_FIXTURES_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @file
+ * Common helpers for Wayland tests.
+ */
+
+#include <stdint.h>
+
+/**
+ * Mapping of the public fixture struct.
+ */
+typedef struct wtst_ctx wtst_ctx;
+
+/**
+ * Mapping of the private fixture struct.
+ */
+typedef struct wtst_ctx_private wtst_ctx_private;
+
+//
+
+/**
+ * Test fixture that holds the basics for simple Wayland client testing.
+ *
+ * @see wtst_ctx_create()
+ * @see wtst_ctx_destroy()
+ */
+struct wtst_ctx
+{
+ /** The display the client is connected to. */
+ struct wl_display *display;
+
+ //
+ /** The registry the client is connected to. */
+ struct wl_registry *registry;
+
+ //
+
+ /** Main compositor as advertised and updated by the registry. */
+ struct wl_compositor *compositor;
+
+ /** Current main compositor name advertised by the registry. */
+ uint32_t compositor_name;
+
+ /**
+ * Main shared memory object as advertised and updated by the
+ * registry.
+ */
+ struct wl_shm *shm;
+
+ /** Current shared memory object name advertised by the registry. */
+ uint32_t shm_name;
+
+ /** Main shell as advertised and updated by the registry. */
+ struct wl_shell *shell;
+
+ /** Current shell name advertised by the registry. */
+ uint32_t shell_name;
+
+ /** Main seat as advertised and updated by the registry. */
+ struct wl_seat *seat;
+
+ /** Current seat name advertised by the registry. */
+ uint32_t seat_name;
+
+ //
+
+ /** Pointer from the current seat. @see seat */
+ struct wl_pointer *pointer;
+
+ //
+
+ /** Listener registered with the registry. */
+ struct wl_registry_listener *reg_listener;
+
+ //
+
+ /** Context for internal implementation details. */
+ wtst_ctx_private *private;
+};
+
+//
+
+/**
+ * Creates an instance of the test fixture.
+ *
+ * @return a pointer to a test fixture upon success, NULL otherwise.
+ * @see wtst_ctx_destroy()
+ */
+wtst_ctx *wtst_ctx_create(void);
+
+/**
+ * Destroys a test fixture.
+ *
+ * @param ctx pointer to a test fixture to destroy.
+ * It should have previously been created via wtst_ctx_create().
+ * @see wtst_ctx_create()
+ */
+void wtst_ctx_destroy(wtst_ctx *ctx);
+
+/**
+ * Determines of an interface has been advertized by the Wayland registry
+ * as being present.
+ *
+ * @param ctx the test fixture in use.
+ * @param interface the name of the interface to query.
+ * @return true if the interface is supported, false otherwise.
+ */
+int wtst_is_global_advertised(wtst_ctx *ctx, char const *interface);
+
+//
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
+
+#endif // WTST_FIXTURES_H
diff --git a/tools/zunitc/doc/zunitc.dox b/tools/zunitc/doc/zunitc.dox
new file mode 100644
index 0000000..136d926
--- /dev/null
+++ b/tools/zunitc/doc/zunitc.dox
@@ -0,0 +1,67 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/**
+ at page zunitc zunitc
+
+A simple test framework in plain C suitable for basic unit and integration testing.
+
+The main rationale for creating this framework was to have a simple to use testing
+framework with tests implemented in C using common patterns and under a
+compatible license. The structure of the test code and macro use is intended to
+follow common patterns established by frameworks such as Boost Test and Google Test.
+
+
+To get started, one or more tests should be defined via ZUC_TEST(), then in
+the main() ZUC_ADD_TEST() should be called for each defined test. Finally
+ZUC_RUN_TESTS() should be called.
+
+
+Tests can use several ZUC_EXPECT_* or ZUC_ASSERT_* checks to validate
+conditions. The ZUC_EXPECT_* ones upon failure will mark the current test
+as failing, but allow execution to continue. On the other hand, the
+ZUC_ASSERT_* tests will mark the current test as failed and then immediately
+terminate the test.
+
+The set of non-fatal test checks are
+
+- ZUC_EXPECT_TRUE()
+- ZUC_EXPECT_FALSE()
+- ZUC_EXPECT_EQ()
+- ZUC_EXPECT_NE()
+- ZUC_EXPECT_LT()
+- ZUC_EXPECT_LE()
+- ZUC_EXPECT_GT()
+- ZUC_EXPECT_GE()
+
+The set of fatal test checks are
+
+- ZUC_ASSERT_TRUE()
+- ZUC_ASSERT_FALSE()
+- ZUC_ASSERT_EQ()
+- ZUC_ASSERT_NE()
+- ZUC_ASSERT_LT()
+- ZUC_ASSERT_LE()
+- ZUC_ASSERT_GT()
+- ZUC_ASSERT_GE()
+
+*/
diff --git a/tools/zunitc/inc/zunitc/zunitc.h b/tools/zunitc/inc/zunitc/zunitc.h
new file mode 100644
index 0000000..f1435da
--- /dev/null
+++ b/tools/zunitc/inc/zunitc/zunitc.h
@@ -0,0 +1,300 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef Z_UNIT_C_H_SEEN_
+#define Z_UNIT_C_H_SEEN_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @file
+ * Simple unit test framework declarations.
+ */
+
+#include "zunitc/zunitc_impl.h"
+
+/**
+ * Adds a test to the list of those to be run.
+ * @param tcase the name for the test case to group this test under.
+ * @param test the name of this specific test.
+ */
+#define ZUC_ADD_TEST(tcase, test) \
+ zucimpl_add_test(zuctest_##tcase##_##test, #tcase, #test)
+
+/**
+ * Runs all tests that have been registered.
+ */
+#define ZUC_RUN_TESTS() \
+ zucimpl_run_tests()
+
+/**
+ * Defines a test case that can be registered to run.
+ */
+#define ZUC_TEST(tcase, test) \
+ static void zuctest_##tcase##_##test(void)
+
+//#define ZUC_TEST_F(tcase, test) static void zuctest_##tcase##_##test(void)
+
+
+/**
+ * Verfies that the specified expression is true and marks the test as failed
+ * if it is not.
+ *
+ * @param condition the expression that is expected to be true.
+ * @note it is far better to use a more specific check when possible
+ * (e.g. ZUC_EXPECT_EQ(), ZUC_EXPECT_NE(), etc.)
+ */
+#define ZUC_EXPECT_TRUE(condition) \
+ zucimpl_expect_true(condition, __FILE__, __LINE__, #condition)
+
+/**
+ * Verfies that the specified expression is false and marks the test as failed
+ * if it is not.
+ *
+ * @param condition the expression that is expected to be false.
+ * @note it is far better to use a more specific check when possible
+ * (e.g. ZUC_EXPECT_EQ(), ZUC_EXPECT_NE(), etc.)
+ */
+#define ZUC_EXPECT_FALSE(condition) \
+ zucimpl_expect_false(condition, __FILE__, __LINE__, #condition)
+
+/**
+ * Verfies that the values of the specified expressions match and marks
+ * the test as failed if they do not.
+ *
+ * @param expected the value the result should hold.
+ * @param actual the actual value seen in testing.
+ */
+#define ZUC_EXPECT_EQ(expected, actual) \
+ zucimpl_expect_eq((expected), (actual), __FILE__, __LINE__, #actual)
+
+/**
+ * Verfies that the values of the specified expressions differ and marks
+ * the test as failed if they do not.
+ *
+ * @param expected the value the result should not hold.
+ * @param actual the actual value seen in testing.
+ */
+#define ZUC_EXPECT_NE(expected, actual) \
+ zucimpl_expect_ne((expected), (actual), __FILE__, __LINE__, #actual)
+
+/**
+ * Verifies that the value of the first expression is less than the value
+ * of the second expression and marks the test as failed if it is not.
+ *
+ * @param lhs the expression whose value should be lesser than the other.
+ * @param rhs the expression whose value should be greater than the other.
+ */
+#define ZUC_EXPECT_LT(lhs, rhs) \
+ zucimpl_expect_lt((lhs), (rhs), __FILE__, __LINE__, #lhs, #rhs)
+
+/**
+ * Verifies that the value of the first expression is less than or equal
+ * to the value of the second expression and marks the test as failed if
+ * it is not.
+ *
+ * @param lhs the expression whose value should be lesser than or equal to
+ * the other.
+ * @param rhs the expression whose value should be greater than or equal to
+ * the other.
+ */
+#define ZUC_EXPECT_LE(lhs, rhs) \
+ zucimpl_expect_le((lhs), (rhs), __FILE__, __LINE__, #lhs, #rhs)
+
+/**
+ * Verifies that the value of the first expression is greater than the
+ * value of the second expression and marks the test as failed if it is not.
+ *
+ * @param lhs the expression whose value should be greater than the other.
+ * @param rhs the expression whose value should be lesser than the other.
+ */
+#define ZUC_EXPECT_GT(lhs, rhs) \
+ zucimpl_expect_gt((lhs), (rhs), __FILE__, __LINE__, #lhs, #rhs)
+
+/**
+ * Verifies that the value of the first expression is greater than or equal
+ * to the value of the second expression and marks the test as failed if
+ * it is not.
+ *
+ * @param lhs the expression whose value should be greater than or equal to
+ * the other.
+ * @param rhs the expression whose value should be lesser than or equal to
+ * the other.
+ */
+#define ZUC_EXPECT_GE(lhs, rhs) \
+ zucimpl_expect_ge((lhs), (rhs), __FILE__, __LINE__, #lhs, #rhs)
+
+
+
+/**
+ * Verfies that the specified expression is true, marks the test as failed
+ * and terminates the test if it is not.
+ *
+ * @param condition the expression that is expected to be true.
+ * @note it is far better to use a more specific check when possible
+ * (e.g. ZUC_EXPECT_EQ(), ZUC_EXPECT_NE(), etc.)
+ */
+#define ZUC_ASSERT_TRUE(condition) \
+ do { \
+ if (zucimpl_expect_true(condition, \
+ __FILE__, __LINE__, \
+ #condition)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verfies that the specified expression is false, marks the test as
+ * failed and terminates the test if it is not.
+ *
+ * @param condition the expression that is expected to be false.
+ * @note it is far better to use a more specific check when possible
+ * (e.g. ZUC_EXPECT_EQ(), ZUC_EXPECT_NE(), etc.)
+ */
+#define ZUC_ASSERT_FALSE(condition) \
+ do { \
+ if (zucimpl_expect_false(condition, \
+ __FILE__, __LINE__, \
+ #condition)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verfies that the values of the specified expressions match, marks the
+ * test as failed and terminates the test if they do not.
+ *
+ * @param expected the value the result should hold.
+ * @param actual the actual value seen in testing.
+ */
+#define ZUC_ASSERT_EQ(expected, actual) \
+ do { \
+ if (zucimpl_expect_eq((expected), (actual), \
+ __FILE__, __LINE__, \
+ #actual)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verfies that the values of the specified expressions differ, marks the
+ * test as failed and terminates the test if they do not.
+ *
+ * @param expected the value the result should not hold.
+ * @param actual the actual value seen in testing.
+ */
+#define ZUC_ASSERT_NE(expected, actual) \
+ do { \
+ if (zucimpl_expect_ne((expected), (actual), \
+ __FILE__, __LINE__, \
+ #actual)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verifies that the value of the first expression is less than the value
+ * of the second expression, marks the test as failed and terminates the
+ * test if it is not.
+ *
+ * @param lhs the expression whose value should be lesser than the other.
+ * @param rhs the expression whose value should be greater than the other.
+ */
+#define ZUC_ASSERT_LT(lhs, rhs) \
+ do { \
+ if (zucimpl_expect_lt((lhs), (rhs), \
+ __FILE__, __LINE__, \
+ #lhs, #rhs)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verifies that the value of the first expression is less than or equal
+ * to the value of the second expression, marks the test as failed and
+ * terminates the test if it is not.
+ *
+ * @param lhs the expression whose value should be lesser than or equal to
+ * the other.
+ * @param rhs the expression whose value should be greater than or equal to
+ * the other.
+ */
+#define ZUC_ASSERT_LE(lhs, rhs) \
+ do { \
+ if (zucimpl_expect_le((lhs), (rhs), \
+ __FILE__, __LINE__, \
+ #lhs, #rhs)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verifies that the value of the first expression is greater than the
+ * value of the second expression, marks the test as failed and terminates
+ * the test if it is not.
+ *
+ * @param lhs the expression whose value should be greater than the other.
+ * @param rhs the expression whose value should be lesser than the other.
+ */
+#define ZUC_ASSERT_GT(lhs, rhs) \
+ do { \
+ if (zucimpl_expect_gt((lhs), (rhs), \
+ __FILE__, __LINE__, \
+ #lhs, #rhs)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+/**
+ * Verifies that the value of the first expression is greater than or equal
+ * to the value of the second expression, marks the test as failed and
+ * terminates the test if it is not.
+ *
+ * @param lhs the expression whose value should be greater than or equal to
+ * the other.
+ * @param rhs the expression whose value should be lesser than or equal to
+ * the other.
+ */
+#define ZUC_ASSERT_GE(lhs, rhs) \
+ do { \
+ if (zucimpl_expect_ge((lhs), (rhs), \
+ __FILE__, __LINE__, \
+ #lhs, #rhs)) { \
+ return; \
+ } \
+ } \
+ while (0)
+
+#ifdef __cplusplus
+} // extern "C"
+#endif
+
+#endif // Z_UNIT_C_H_SEEN_
diff --git a/tools/zunitc/inc/zunitc/zunitc_impl.h b/tools/zunitc/inc/zunitc/zunitc_impl.h
new file mode 100644
index 0000000..0b9bdd5
--- /dev/null
+++ b/tools/zunitc/inc/zunitc/zunitc_impl.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef Z_UNIT_C_IMPL_H_SEEN_
+#define Z_UNIT_C_IMPL_H_SEEN_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef void (*zucimpl_test_fn)(void);
+
+void zucimpl_add_test(zucimpl_test_fn testFn,
+ char const *caseName, char const *testName);
+
+void zucimpl_run_tests(void);
+
+int zucimpl_testFailed(void);
+
+int zucimpl_expect_true(int condition,
+ char const *file, int line,
+ const char *valueStr);
+
+int zucimpl_expect_false(int condition,
+ char const *file, int line,
+ const char *valueStr);
+
+int zucimpl_expect_eq(int expected, int actual,
+ char const *file, int line,
+ const char *valueStr);
+
+int zucimpl_expect_ne(int expected, int actual,
+ char const *file, int line,
+ const char *valueStr);
+
+int zucimpl_expect_lt(int lhs, int rhs,
+ char const *file, int line,
+ const char *lhsStr, const char* rhsStr);
+
+int zucimpl_expect_le(int lhs, int rhs,
+ char const *file, int line,
+ const char *lhsStr, const char* rhsStr);
+
+int zucimpl_expect_gt(int lhs, int rhs,
+ char const *file, int line,
+ const char *lhsStr, const char* rhsStr);
+
+int zucimpl_expect_ge(int lhs, int rhs,
+ char const *file, int line,
+ const char *lhsStr, const char* rhsStr);
+
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // Z_UNIT_C_IMPL_H_SEEN_
diff --git a/tools/zunitc/src/zunitc_impl.c b/tools/zunitc/src/zunitc_impl.c
new file mode 100644
index 0000000..2421f27
--- /dev/null
+++ b/tools/zunitc/src/zunitc_impl.c
@@ -0,0 +1,496 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+// Required #define to get clock_gettime() & strdup
+#define _POSIX_C_SOURCE 200809L
+#include <time.h>
+#include <string.h>
+
+#include <unistd.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "zunitc/zunitc_impl.h"
+#include "zunitc/zunitc.h"
+
+
+#if _POSIX_MONOTONIC_CLOCK
+static const clockid_t TARGET_TIMER = CLOCK_MONOTONIC;
+#else
+static const clockid_t TARGET_TIMER = CLOCK_REALTIME;
+#endif
+
+typedef struct ZucTest
+{
+ zucimpl_test_fn fn;
+ char *caseName;
+ char *testName;
+ int failed;
+ int disabled;
+ long elapsed;
+
+ struct ZucTest *next;
+} ZucTest;
+
+typedef struct ZucCase
+{
+ char *caseName;
+ long elapsed;
+ int testCount;
+ ZucTest *firstTest;
+
+ struct ZucCase *next;
+} ZucCase;
+
+
+static char const DISABLED_PREFIX[] = "DISABLED_";
+
+// Data structure simple, but should suffice for smaller numbers of tests.
+static int caseListCount = 0;
+static ZucCase *caseListHead = NULL;
+
+static int gBad = 0;
+
+static ZucCase *gCurrCase = NULL;
+static ZucTest *gCurrTest = NULL;
+
+
+static ZucCase *getCase(char const *caseName);
+
+static void attachTest(ZucTest *test);
+
+static void countLiveTests(int *caseCount, int *testCount, int *disabledCount);
+
+static void countLiveTestsForCase(ZucCase const *testCase,
+ int *testCount, int *disabledCount);
+
+
+ZucCase *getCase(char const *caseName)
+{
+ ZucCase *foundCase = NULL;
+ if (caseName)
+ {
+ ZucCase *currCase;
+ for (currCase = caseListHead; currCase && !foundCase;
+ currCase = currCase->next)
+ {
+ if (strcmp(currCase->caseName, caseName) == 0)
+ {
+ foundCase = currCase;
+ }
+ }
+ }
+ return foundCase;
+}
+
+void zucimpl_add_test(zucimpl_test_fn testFn,
+ char const *caseName, char const *testName)
+{
+ ZucTest *test = (ZucTest *)malloc(sizeof(ZucTest));
+ if (test) {
+ memset(test, 0, sizeof(ZucTest));
+ test->fn = testFn;
+ test->caseName = strdup(caseName);
+ test->testName = strdup(testName);
+ if (!testFn ||
+ (strncmp(DISABLED_PREFIX,
+ testName, sizeof(DISABLED_PREFIX) - 1) == 0))
+ {
+ test->disabled = 1;
+ }
+
+ attachTest(test);
+ } else {
+ fprintf(stderr, "%s:%d: error unable to allocate memory.\n",
+ __FILE__, __LINE__);
+ }
+}
+
+void attachTest(ZucTest *test)
+{
+ if (test) {
+ ZucCase *testCase = getCase(test->caseName);
+ if (!testCase)
+ {
+ // Need to add a new case to hold the test
+ testCase = (ZucCase *)malloc(sizeof(ZucCase));
+ memset(testCase, 0, sizeof(ZucCase));
+ testCase->caseName = strdup(test->caseName);
+
+ if (caseListHead) {
+ ZucCase *curr = caseListHead;
+ while (curr && curr->next) {
+ curr = curr->next;
+ }
+ curr->next = testCase;
+ } else {
+ caseListHead = testCase;
+ }
+ caseListCount++;
+ }
+
+ if (testCase->firstTest) {
+ ZucTest *curr = testCase->firstTest;
+ while (curr && curr->next) {
+ curr = curr->next;
+ }
+ curr->next = test;
+ } else {
+ testCase->firstTest = test;
+ }
+ testCase->testCount++;
+ }
+}
+
+void zucimpl_run_tests(void)
+{
+ printf("Running tests...\n");
+
+ int liveCaseCount = 0;
+ int liveTestCount = 0;
+ int disabledCount = 0;
+ countLiveTests(&liveCaseCount, &liveTestCount, &disabledCount);
+
+ printf("[==========] Running %d %s from %d test %s.\n",
+ liveTestCount,
+ (liveTestCount == 1) ? "test" : "tests",
+ liveCaseCount,
+ (liveCaseCount == 1) ? "case" : "cases");
+
+ long totalElapsed = 0;
+ int totalPassed = 0;
+ int totalFailed = 0;
+ gBad = 0;
+ ZucCase *currCase;
+ for (currCase = caseListHead; currCase; currCase = currCase->next)
+ {
+ gCurrCase = currCase;
+
+ int countXX = 0;
+ countLiveTestsForCase(currCase, &countXX, NULL);
+ if (countXX)
+ {
+ printf("[----------] %d %s from %s.\n",
+ countXX,
+ (countXX == 1) ? "test" : "tests",
+ currCase->caseName);
+
+ ZucTest *curr;
+ for (curr = currCase->firstTest; curr;
+ curr = curr->next)
+ {
+ if (!curr->disabled)
+ {
+ gCurrTest = curr;
+ printf("[ RUN ] %s:%s\n",
+ curr->caseName, curr->testName);
+ struct timespec begin;
+ memset(&begin, 0, sizeof(begin));
+ clock_gettime(TARGET_TIMER, &begin);
+
+ curr->fn();
+
+ if (curr->failed)
+ {
+ totalFailed++;
+ } else {
+ totalPassed++;
+ }
+
+ struct timespec end;
+ memset(&end, 0, sizeof(end));
+ clock_gettime(TARGET_TIMER, &end);
+ // tv_sec, tv_nsec
+
+ long elapsed =
+ (end.tv_sec - begin.tv_sec)
+ * 1000L;
+ if (end.tv_sec != begin.tv_sec) {
+ elapsed -= (begin.tv_nsec)
+ / 1000000L;
+ elapsed += (end.tv_nsec)
+ / 1000000L;
+ } else {
+ elapsed +=
+ (end.tv_nsec
+ - begin.tv_nsec)
+ / 1000000L;
+ }
+ curr->elapsed = elapsed;
+ currCase->elapsed += elapsed;
+
+ if (curr->failed)
+ {
+ printf("[ FAILED ] %s:%s (%ld ms)\n",curr->caseName, curr->testName, curr->elapsed);
+ }
+ else
+ {
+ printf("[ OK ] %s:%s (%ld ms)\n", curr->caseName, curr->testName, curr->elapsed);
+ }
+
+ gCurrTest = NULL;
+ }
+ }
+
+ totalElapsed += currCase->elapsed;
+ printf("[----------] %d %s from %s (%ld ms)\n",
+ currCase->testCount,
+ (currCase->testCount == 1) ? "test" : "tests",
+ currCase->caseName,
+ currCase->elapsed);
+ printf("\n");
+ }
+ gCurrCase = NULL;
+ }
+ printf("[==========] %d %s from %d test %s ran. (%ld ms)\n",
+ liveTestCount,
+ (liveTestCount == 1) ? "test" : "tests",
+ liveCaseCount,
+ (liveCaseCount == 1) ? "case" : "cases",
+ totalElapsed);
+ if (totalPassed) {
+ printf("[ PASSED ] %d %s.\n", totalPassed, (totalPassed == 1) ? "test" : "tests");
+ }
+
+ if (totalFailed) {
+ printf("[ FAILED ] %d %s, listed below:\n",
+ totalFailed, (totalFailed == 1) ? "test" : "tests");
+
+ for (currCase = caseListHead; currCase; currCase = currCase->next)
+ {
+ ZucTest *curr;
+ for (curr = currCase->firstTest; curr; curr = curr->next)
+ {
+ if (curr->failed) {
+ printf("[ FAILED ] %s.%s\n", currCase->caseName, curr->testName);
+ }
+ }
+ }
+ }
+
+ if (totalFailed || disabledCount)
+ {
+ printf("\n");
+ }
+
+ if (totalFailed)
+ {
+ printf(" %d FAILED %s\n",
+ totalFailed,
+ (totalFailed == 1) ? "TEST" : "TESTS");
+ }
+
+ if (disabledCount)
+ {
+ printf(" YOU HAVE %d DISABLED %s\n",
+ disabledCount,
+ (disabledCount == 1) ? "TEST" : "TESTS");
+ }
+}
+
+int zucimpl_testFailed()
+{
+ int failed = gBad;
+ if (gCurrTest) {
+ failed = gCurrTest->failed;
+ }
+ return failed;
+}
+
+static void markFailed(void)
+{
+ gBad = 1;
+ if (gCurrTest) {
+ gCurrTest->failed = 1;
+ }
+}
+
+int zucimpl_expect_true(int condition, char const *file, int line, const char *valueStr){
+ int failed = 0;
+ if (!condition)
+ {
+ printf("%s:%d: error: Value of: %s\n", file, line, valueStr);
+ printf(" Actual: %d\n", condition);
+ printf("Expected: TRUE\n");
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_false(int condition, char const *file, int line, const char *valueStr)
+{
+ int failed = 0;
+ if (condition)
+ {
+ printf("%s:%d: error: Value of: %s\n", file, line, valueStr);
+ printf(" Actual: %d\n", condition);
+ printf("Expected: FALSE\n");
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_eq(int expected, int actual, char const *file, int line, const char *valueStr)
+{
+ int failed = 0;
+ if (expected != actual)
+ {
+ printf("%s:%d: error: Value of: %s\n", file, line, valueStr);
+ printf(" Actual: %d\n", actual);
+ printf("Expected: %d\n", expected);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_ne(int expected, int actual, char const *file, int line, const char *valueStr)
+{
+ int failed = 0;
+ if (expected == actual)
+ {
+ printf("%s:%d: error: ", file, line);
+ printf("Expected: (%d) != (%s), actual %d vs %d\n", expected, valueStr, expected, actual);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_lt(int lhs, int rhs, char const *file, int line, const char *lhsStr, const char* rhsStr)
+{
+ int failed = 0;
+ if (lhs >= rhs)
+ {
+ printf("%s:%d: error: ", file, line);
+ printf("Expected: (%s) < (%s), actual %d vs %d\n", lhsStr, rhsStr, lhs, rhs);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_le(int lhs, int rhs, char const *file, int line, const char *lhsStr, const char* rhsStr)
+{
+ int failed = 0;
+ if (lhs > rhs)
+ {
+ printf("%s:%d: error: ", file, line);
+ printf("Expected: (%s) <= (%s), actual %d vs %d\n", lhsStr, rhsStr, lhs, rhs);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_gt(int lhs, int rhs, char const *file, int line, const char *lhsStr, const char* rhsStr)
+{
+ int failed = 0;
+ if (lhs <= rhs)
+ {
+ printf("%s:%d: error: ", file, line);
+ printf("Expected: (%s) > (%s), actual %d vs %d\n", lhsStr, rhsStr, lhs, rhs);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+int zucimpl_expect_ge(int lhs, int rhs, char const *file, int line, const char *lhsStr, const char* rhsStr)
+{
+ int failed = 0;
+ if (lhs < rhs)
+ {
+ printf("%s:%d: error: ", file, line);
+ printf("Expected: (%s) >= (%s), actual %d vs %d\n", lhsStr, rhsStr, lhs, rhs);
+ failed = 1;
+ markFailed();
+ }
+ return failed;
+}
+
+void countLiveTestsForCase(ZucCase const *testCase, int *testCount, int *disabledCount)
+{
+ int localTestCount = 0;
+ int localSkippedCount = 0;
+ ZucTest *curr;
+ for (curr = testCase->firstTest; curr; curr = curr->next)
+ {
+ if (curr->disabled)
+ {
+ localSkippedCount++;
+ }
+ else
+ {
+ localTestCount++;
+ }
+ }
+
+ if (testCount)
+ {
+ *testCount = localTestCount;
+ }
+
+ if (disabledCount)
+ {
+ *disabledCount = localSkippedCount;
+ }
+}
+
+void countLiveTests(int *caseCount, int *testCount, int *disabledCount)
+{
+ int localCaseCount = 0;
+ int localTestCount = 0;
+ int localSkippedCount = 0;
+
+ ZucCase *currCase;
+ for (currCase = caseListHead; currCase; currCase = currCase->next)
+ {
+ int liveInCase = 0;
+ int skippedInCase = 0;
+ countLiveTestsForCase(currCase, &liveInCase, &skippedInCase);
+ localSkippedCount += skippedInCase;
+ localTestCount += liveInCase;
+ if (liveInCase)
+ {
+ localCaseCount++;
+ }
+ }
+
+ if (caseCount)
+ {
+ *caseCount = localCaseCount;
+ }
+
+ if (testCount)
+ {
+ *testCount = localTestCount;
+ }
+
+ if (disabledCount)
+ {
+ *disabledCount = localSkippedCount;
+ }
+}
diff --git a/tools/zunitc/test/zunitc_test.c b/tools/zunitc/test/zunitc_test.c
new file mode 100644
index 0000000..9c8e3a9
--- /dev/null
+++ b/tools/zunitc/test/zunitc_test.c
@@ -0,0 +1,106 @@
+/*
+ * Copyright © 2015 Samsung Electronics
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of the copyright holders not be used in
+ * advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission. The copyright holders make
+ * no representations about the suitability of this software for any
+ * purpose. It is provided "as is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
+ * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
+ * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
+ * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/*
+ * A simple file to show tests being setup and run.
+ */
+
+#include "config.h"
+
+#include <unistd.h>
+#include <stdio.h>
+
+
+
+#include "zunitc/zunitc.h"
+
+ZUC_TEST(BaseTest, MathIsSane)
+{
+ ZUC_EXPECT_EQ(4, 2 + 2);
+}
+
+ZUC_TEST(BaseTest, MathIsHard)
+{
+#ifdef ENABLE_FAIL_TESTS
+ ZUC_EXPECT_EQ(5, 2 + 2);
+ ZUC_EXPECT_EQ(7, 9);
+#endif
+}
+
+ZUC_TEST(BaseTest, MathIsMoreHard)
+{
+#ifdef ENABLE_FAIL_TESTS
+ ZUC_ASSERT_EQ(5, 2 + 2);
+ ZUC_ASSERT_EQ(7, 9);
+#endif
+}
+
+ZUC_TEST(OtherTest, MathMonkey)
+{
+ ZUC_EXPECT_TRUE(1);
+ ZUC_EXPECT_TRUE(3);
+ ZUC_EXPECT_FALSE(0);
+
+ ZUC_ASSERT_TRUE(1);
+ ZUC_ASSERT_TRUE(3);
+ ZUC_ASSERT_FALSE(0);
+
+ ZUC_EXPECT_EQ(5, 2 + 3);
+ ZUC_ASSERT_EQ(5, 2 + 3);
+
+ int b = 9;
+ ZUC_EXPECT_NE(1, 2);
+ ZUC_EXPECT_NE(b, b + 2);
+
+ ZUC_ASSERT_NE(1, 2);
+ ZUC_ASSERT_NE(b, b + 1);
+
+ ZUC_EXPECT_LT(1, 2);
+ ZUC_ASSERT_LT(1, 3);
+
+ ZUC_EXPECT_LE(1, 2);
+ ZUC_ASSERT_LE(1, 3);
+
+ ZUC_EXPECT_LE(1, 1);
+ ZUC_ASSERT_LE(1, 1);
+
+ ZUC_EXPECT_GT(2, 1);
+ ZUC_ASSERT_GT(3, 1);
+
+ ZUC_EXPECT_GE(1, 1);
+ ZUC_ASSERT_GE(1, 1);
+
+ ZUC_EXPECT_GE(2, 1);
+ ZUC_ASSERT_GE(3, 1);
+}
+
+int main( int argc, const char* argv[] )
+{
+ ZUC_ADD_TEST(BaseTest, MathIsSane);
+ ZUC_ADD_TEST(BaseTest, MathIsHard);
+ ZUC_ADD_TEST(BaseTest, MathIsMoreHard);
+ ZUC_ADD_TEST(OtherTest, MathMonkey);
+
+ ZUC_RUN_TESTS();
+
+ return 0;
+}
--
2.1.0
More information about the wayland-devel
mailing list