PR jit/66546: Add gcc_jit_context_set_bool_allow_unreachable_blocks

gcc/jit/ChangeLog:
	PR jit/66546
	* docs/cp/topics/contexts.rst
	(gccjit::context::set_bool_allow_unreachable_blocks): New.
	* docs/topics/compatibility.rst (LIBGCCJIT_ABI_2): New.
	* docs/topics/contexts.rst (Options): Add notes discussing the
	transition from enums to entrypoints for new options.
	(gcc_jit_context_set_bool_allow_unreachable_blocks): New.
	* docs/_build/texinfo/libgccjit.texi: Regenerate.
	* jit-common.h (gcc::jit::inner_bool_option): New enum.
	* jit-recording.c: Within namespace gcc::jit...
	(recording::context::context): Handle m_inner_bool_options.
	(recording::context::set_inner_bool_option): New.
	(inner_bool_option_reproducer_strings): New.
	(recording::context::log_all_options): Log the "inner" bool
	options.
	(recording::context::log_inner_bool_option): New.
	(recording::context::dump_reproducer_to_file): Write initializers
	for "inner" bool options.
	(recording::function::validate): Don't check for block
	reachability if INNER_BOOL_OPTION_ALLOW_UNREACHABLE_BLOCKS is set.
	* jit-recording.h: Within namespace gcc::jit...
	(recording::context::set_inner_bool_option): New.
	(recording::context::get_inner_bool_option): New.
	(recording::context::log_inner_bool_option): New.
	(recording::context::m_inner_bool_options): New.
	* libgccjit++.h
	(gccjit::context::set_bool_allow_unreachable_blocks): New.
	* libgccjit.c
	(gcc_jit_context_set_bool_allow_unreachable_blocks): New.
	* libgccjit.h: Add note about options present in the
	initial release of libgccjit.
	(gcc_jit_context_set_bool_allow_unreachable_blocks): New API
	entrypoint.
	(LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks):
	New macro.
	* libgccjit.map (LIBGCCJIT_ABI_2): New, containing...
	(gcc_jit_context_set_bool_allow_unreachable_blocks): ...this new
	entrypoint.

gcc/testsuite/ChangeLog:
	PR jit/66546
	* jit.dg/all-non-failing-tests.h: Add note about
	test-validly-unreachable-block.c.
	* jit.dg/test-validly-unreachable-block.c: New file.

From-SVN: r225206
This commit is contained in:
David Malcolm 2015-06-30 19:38:12 +00:00 committed by David Malcolm
parent fa22c20d5a
commit 6a3603e356
15 changed files with 745 additions and 411 deletions

View File

@ -1,3 +1,44 @@
2015-06-30 David Malcolm <dmalcolm@redhat.com>
PR jit/66546
* docs/cp/topics/contexts.rst
(gccjit::context::set_bool_allow_unreachable_blocks): New.
* docs/topics/compatibility.rst (LIBGCCJIT_ABI_2): New.
* docs/topics/contexts.rst (Options): Add notes discussing the
transition from enums to entrypoints for new options.
(gcc_jit_context_set_bool_allow_unreachable_blocks): New.
* docs/_build/texinfo/libgccjit.texi: Regenerate.
* jit-common.h (gcc::jit::inner_bool_option): New enum.
* jit-recording.c: Within namespace gcc::jit...
(recording::context::context): Handle m_inner_bool_options.
(recording::context::set_inner_bool_option): New.
(inner_bool_option_reproducer_strings): New.
(recording::context::log_all_options): Log the "inner" bool
options.
(recording::context::log_inner_bool_option): New.
(recording::context::dump_reproducer_to_file): Write initializers
for "inner" bool options.
(recording::function::validate): Don't check for block
reachability if INNER_BOOL_OPTION_ALLOW_UNREACHABLE_BLOCKS is set.
* jit-recording.h: Within namespace gcc::jit...
(recording::context::set_inner_bool_option): New.
(recording::context::get_inner_bool_option): New.
(recording::context::log_inner_bool_option): New.
(recording::context::m_inner_bool_options): New.
* libgccjit++.h
(gccjit::context::set_bool_allow_unreachable_blocks): New.
* libgccjit.c
(gcc_jit_context_set_bool_allow_unreachable_blocks): New.
* libgccjit.h: Add note about options present in the
initial release of libgccjit.
(gcc_jit_context_set_bool_allow_unreachable_blocks): New API
entrypoint.
(LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks):
New macro.
* libgccjit.map (LIBGCCJIT_ABI_2): New, containing...
(gcc_jit_context_set_bool_allow_unreachable_blocks): ...this new
entrypoint.
2015-06-30 David Malcolm <dmalcolm@redhat.com>
PR jit/66628

File diff suppressed because it is too large Load Diff

View File

@ -184,6 +184,23 @@ Boolean options
:c:func:`gcc_jit_context_set_bool_option`; the options have the same
meaning.
.. function:: void \
gccjit::context::set_bool_allow_unreachable_blocks (int bool_value)
By default, libgccjit will issue an error about unreachable blocks
within a function.
This entrypoint can be used to disable that error; it is a thin wrapper
around the C API
:c:func:`gcc_jit_context_set_bool_allow_unreachable_blocks`.
This entrypoint was added in :ref:`LIBGCCJIT_ABI_2`; you can test for
its presence using
.. code-block:: c
#ifdef LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks
Integer options
***************

View File

@ -88,3 +88,10 @@ continue to work, with this being handled transparently by the linker
-------------------
``LIBGCCJIT_ABI_1`` covers the addition of
:func:`gcc_jit_context_add_command_line_option`
.. _LIBGCCJIT_ABI_2:
``LIBGCCJIT_ABI_2``
-------------------
``LIBGCCJIT_ABI_2`` covers the addition of
:func:`gcc_jit_context_set_bool_allow_unreachable_blocks`

View File

@ -293,6 +293,15 @@ future activies on a context to the given `FILE *`.
Options
-------
Options present in the initial release of libgccjit were handled using
enums, whereas those added subsequently have their own per-option API
entrypoints.
Adding entrypoints for each new option means that client code that use
the new options can be identified directly from binary metadata, which
would not be possible if we instead extended the various
``enum gcc_jit_*_option``.
String Options
**************
@ -304,7 +313,7 @@ String Options
.. type:: enum gcc_jit_str_option
There is currently just one string option:
There is just one string option specified this way:
.. macro:: GCC_JIT_STR_OPTION_PROGNAME
@ -441,6 +450,22 @@ Boolean options
If true, the :type:`gcc_jit_context` will not clean up intermediate files
written to the filesystem, and will display their location on stderr.
.. function:: void \
gcc_jit_context_set_bool_allow_unreachable_blocks (gcc_jit_context *ctxt, \
int bool_value)
By default, libgccjit will issue an error about unreachable blocks
within a function.
This entrypoint can be used to disable that error.
This entrypoint was added in :ref:`LIBGCCJIT_ABI_2`; you can test for
its presence using
.. code-block:: c
#ifdef LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks
Integer options
***************
@ -452,7 +477,7 @@ Integer options
.. type:: enum gcc_jit_int_option
There is currently just one integer option:
There is just one integer option specified this way:
.. macro:: GCC_JIT_INT_OPTION_OPTIMIZATION_LEVEL

View File

@ -185,6 +185,16 @@ private:
FILE *m_file;
};
/* A hidden enum of boolean options that are only exposed via API
entrypoints, rather than via gcc_jit_context_set_bool_option. */
enum inner_bool_option
{
INNER_BOOL_OPTION_ALLOW_UNREACHABLE_BLOCKS,
NUM_INNER_BOOL_OPTIONS
};
} // namespace gcc::jit
} // namespace gcc

View File

@ -489,6 +489,9 @@ recording::context::context (context *parent_ctxt)
memcpy (m_bool_options,
parent_ctxt->m_bool_options,
sizeof (m_bool_options));
memcpy (m_inner_bool_options,
parent_ctxt->m_inner_bool_options,
sizeof (m_inner_bool_options));
set_logger (parent_ctxt->get_logger ());
}
else
@ -496,6 +499,7 @@ recording::context::context (context *parent_ctxt)
memset (m_str_options, 0, sizeof (m_str_options));
memset (m_int_options, 0, sizeof (m_int_options));
memset (m_bool_options, 0, sizeof (m_bool_options));
memset (m_inner_bool_options, 0, sizeof (m_inner_bool_options));
}
memset (m_basic_types, 0, sizeof (m_basic_types));
@ -1141,6 +1145,16 @@ recording::context::set_bool_option (enum gcc_jit_bool_option opt,
log_bool_option (opt);
}
void
recording::context::set_inner_bool_option (enum inner_bool_option inner_opt,
int value)
{
gcc_assert (inner_opt >= 0 && inner_opt < NUM_INNER_BOOL_OPTIONS);
m_inner_bool_options[inner_opt] = value ? true : false;
log_inner_bool_option (inner_opt);
}
/* Add the given optname to this context's list of extra options.
Implements the post-error-checking part of
@ -1418,6 +1432,10 @@ static const char * const
"GCC_JIT_BOOL_OPTION_KEEP_INTERMEDIATES"
};
static const char * const
inner_bool_option_reproducer_strings[NUM_INNER_BOOL_OPTIONS] = {
"gcc_jit_context_set_bool_allow_unreachable_blocks"
};
/* Write the current value of all options to the log file (if any). */
@ -1437,6 +1455,8 @@ recording::context::log_all_options () const
for (opt_idx = 0; opt_idx < GCC_JIT_NUM_BOOL_OPTIONS; opt_idx++)
log_bool_option ((enum gcc_jit_bool_option)opt_idx);
for (opt_idx = 0; opt_idx < NUM_INNER_BOOL_OPTIONS; opt_idx++)
log_inner_bool_option ((enum inner_bool_option)opt_idx);
}
/* Write the current value of the given string option to the
@ -1484,6 +1504,19 @@ recording::context::log_bool_option (enum gcc_jit_bool_option opt) const
m_bool_options[opt] ? "true" : "false");
}
/* Write the current value of the given "inner" bool option to the
log file (if any). */
void
recording::context::log_inner_bool_option (enum inner_bool_option opt) const
{
gcc_assert (opt < NUM_INNER_BOOL_OPTIONS);
if (get_logger ())
log ("%s: %s",
inner_bool_option_reproducer_strings[opt],
m_inner_bool_options[opt] ? "true" : "false");
}
/* Write C source code to PATH that attempts to replay the API
calls made to this context (and its parents), for use in
minimizing test cases for libgccjit.
@ -1623,6 +1656,11 @@ recording::context::dump_reproducer_to_file (const char *path)
r.get_identifier (contexts[ctxt_idx]),
bool_option_reproducer_strings[opt_idx],
m_bool_options[opt_idx]);
for (int opt_idx = 0; opt_idx < NUM_INNER_BOOL_OPTIONS; opt_idx++)
r.write (" %s (%s, %i);\n",
inner_bool_option_reproducer_strings[opt_idx],
r.get_identifier (contexts[ctxt_idx]),
m_inner_bool_options[opt_idx]);
if (!m_command_line_options.is_empty ())
{
@ -3452,7 +3490,9 @@ recording::function::validate ()
}
/* Check that all blocks are reachable. */
if (m_blocks.length () > 0 && 0 == num_invalid_blocks)
if (!m_ctxt->get_inner_bool_option
(INNER_BOOL_OPTION_ALLOW_UNREACHABLE_BLOCKS)
&& m_blocks.length () > 0 && 0 == num_invalid_blocks)
{
/* Iteratively walk the graph of blocks, marking their "m_is_reachable"
flag, starting at the initial block. */

View File

@ -195,6 +195,10 @@ public:
set_bool_option (enum gcc_jit_bool_option opt,
int value);
void
set_inner_bool_option (enum inner_bool_option inner_opt,
int value);
void
add_command_line_option (const char *optname);
@ -223,6 +227,12 @@ public:
return m_bool_options[opt];
}
int
get_inner_bool_option (enum inner_bool_option opt) const
{
return m_inner_bool_options[opt];
}
result *
compile ();
@ -266,6 +276,7 @@ private:
void log_str_option (enum gcc_jit_str_option opt) const;
void log_int_option (enum gcc_jit_int_option opt) const;
void log_bool_option (enum gcc_jit_bool_option opt) const;
void log_inner_bool_option (enum inner_bool_option opt) const;
void validate ();
@ -287,6 +298,7 @@ private:
char *m_str_options[GCC_JIT_NUM_STR_OPTIONS];
int m_int_options[GCC_JIT_NUM_INT_OPTIONS];
bool m_bool_options[GCC_JIT_NUM_BOOL_OPTIONS];
bool m_inner_bool_options[NUM_INNER_BOOL_OPTIONS];
auto_vec <char *> m_command_line_options;
/* Dumpfiles that were requested via gcc_jit_context_enable_dump. */

View File

@ -120,6 +120,8 @@ namespace gccjit
void set_bool_option (enum gcc_jit_bool_option opt,
int value);
void set_bool_allow_unreachable_blocks (int bool_value);
void add_command_line_option (const char *optname);
location
@ -602,7 +604,13 @@ context::set_bool_option (enum gcc_jit_bool_option opt,
int value)
{
gcc_jit_context_set_bool_option (m_inner_ctxt, opt, value);
}
inline void
context::set_bool_allow_unreachable_blocks (int bool_value)
{
gcc_jit_context_set_bool_allow_unreachable_blocks (m_inner_ctxt,
bool_value);
}
inline void

View File

@ -2182,6 +2182,23 @@ gcc_jit_context_set_bool_option (gcc_jit_context *ctxt,
ctxt->set_bool_option (opt, value);
}
/* Public entrypoint. See description in libgccjit.h.
After error-checking, the real work is done by the
gcc::jit::recording::context::set_inner_bool_option method in
jit-recording.c. */
void
gcc_jit_context_set_bool_allow_unreachable_blocks (gcc_jit_context *ctxt,
int bool_value)
{
RETURN_IF_FAIL (ctxt, NULL, NULL, "NULL context");
JIT_LOG_FUNC (ctxt->get_logger ());
ctxt->set_inner_bool_option (
gcc::jit::INNER_BOOL_OPTION_ALLOW_UNREACHABLE_BLOCKS,
bool_value);
}
/* Public entrypoint. See description in libgccjit.h.
After error-checking, the real work is done by the

View File

@ -140,6 +140,9 @@ gcc_jit_context_acquire (void);
extern void
gcc_jit_context_release (gcc_jit_context *ctxt);
/* Options present in the initial release of libgccjit.
These were handled using enums. */
/* Options taking string values. */
enum gcc_jit_str_option
{
@ -243,6 +246,31 @@ gcc_jit_context_set_bool_option (gcc_jit_context *ctxt,
enum gcc_jit_bool_option opt,
int value);
/* Options added after the initial release of libgccjit.
These are handled by providing an entrypoint per option,
rather than by extending the enum gcc_jit_*_option,
so that client code that use these new options can be identified
from binary metadata. */
/* By default, libgccjit will issue an error about unreachable blocks
within a function.
This option can be used to disable that error.
This entrypoint was added in LIBGCCJIT_ABI_2; you can test for
its presence using
#ifdef LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks
*/
extern void
gcc_jit_context_set_bool_allow_unreachable_blocks (gcc_jit_context *ctxt,
int bool_value);
/* Pre-canned feature macro to indicate the presence of
gcc_jit_context_set_bool_allow_unreachable_blocks. This can be
tested for with #ifdef. */
#define LIBGCCJIT_HAVE_gcc_jit_context_set_bool_allow_unreachable_blocks
/* Add an arbitrary gcc command-line option to the context.
The context takes a copy of the string, so the
(const char *) optname is not needed anymore after the call

View File

@ -114,3 +114,9 @@ LIBGCCJIT_ABI_1 {
global:
gcc_jit_context_add_command_line_option;
} LIBGCCJIT_ABI_0;
# Add support for disabling the check for unreachable blocks (PR jit/66546).
LIBGCCJIT_ABI_2 {
global:
gcc_jit_context_set_bool_allow_unreachable_blocks;
} LIBGCCJIT_ABI_1;

View File

@ -1,3 +1,10 @@
2015-06-30 David Malcolm <dmalcolm@redhat.com>
PR jit/66546
* jit.dg/all-non-failing-tests.h: Add note about
test-validly-unreachable-block.c.
* jit.dg/test-validly-unreachable-block.c: New file.
2015-06-30 David Malcolm <dmalcolm@redhat.com>
PR jit/66628

View File

@ -189,6 +189,10 @@
#undef create_code
#undef verify_code
/* test-validly-unreachable-block.c: We don't use this one, since the use
of gcc_jit_context_set_bool_allow_unreachable_blocks affects the whole
context. */
/* test-volatile.c */
#define create_code create_code_volatile
#define verify_code verify_code_volatile

View File

@ -0,0 +1,51 @@
#include <math.h>
#include <stdlib.h>
#include <stdio.h>
#include "libgccjit.h"
#include "harness.h"
void
create_code (gcc_jit_context *ctxt, void *user_data)
{
/* Let's try to inject the equivalent of:
void
test_fn ()
{
return;
return;
}
where the second block is unreachable, but have it
survive validation (PR jit/66546).
*/
gcc_jit_context_set_bool_allow_unreachable_blocks (ctxt, 1);
gcc_jit_type *void_t =
gcc_jit_context_get_type (ctxt, GCC_JIT_TYPE_VOID);
/* Build the test_fn. */
gcc_jit_function *test_fn =
gcc_jit_context_new_function (ctxt, NULL,
GCC_JIT_FUNCTION_EXPORTED,
void_t,
"test_fn",
0, NULL,
0);
gcc_jit_block *initial =
gcc_jit_function_new_block (test_fn, "a");
gcc_jit_block *unreachable =
gcc_jit_function_new_block (test_fn, "b");
gcc_jit_block_end_with_void_return (initial, NULL);
gcc_jit_block_end_with_void_return (unreachable, NULL);
}
void
verify_code (gcc_jit_context *ctxt, gcc_jit_result *result)
{
/* Ensure that the "unreachable blocks" validator was ignored. */
CHECK_NON_NULL (result);
}