aboutsummaryrefslogtreecommitdiff
path: root/gcc/analyzer/program-state.cc
diff options
context:
space:
mode:
authorDavid Malcolm <dmalcolm@redhat.com>2020-09-18 13:59:21 -0400
committerDavid Malcolm <dmalcolm@redhat.com>2020-09-22 14:47:03 -0400
commit809192e77e6e112a0fe32dee7fada7a49fbf25cd (patch)
treed6a2be6a09802aad22e6eb2a779f6baefacf700c /gcc/analyzer/program-state.cc
parent7c8ba5da80d5d95a8521010d6731d0d83036145d (diff)
downloadgcc-809192e77e6e112a0fe32dee7fada7a49fbf25cd.zip
gcc-809192e77e6e112a0fe32dee7fada7a49fbf25cd.tar.gz
gcc-809192e77e6e112a0fe32dee7fada7a49fbf25cd.tar.bz2
analyzer: add -fdump-analyzer-json
I've found this useful for debugging state explosions in the analyzer. gcc/analyzer/ChangeLog: * analysis-plan.cc: Include "json.h". * analyzer.opt (fdump-analyzer-json): New. * call-string.cc: Include "json.h". (call_string::to_json): New. * call-string.h (call_string::to_json): New decl. * checker-path.cc: Include "json.h". * constraint-manager.cc: Include "json.h". (equiv_class::to_json): New. (constraint::to_json): New. (constraint_manager::to_json): New. * constraint-manager.h (equiv_class::to_json): New decl. (constraint::to_json): New decl. (constraint_manager::to_json): New decl. * diagnostic-manager.cc: Include "json.h". (saved_diagnostic::to_json): New. (diagnostic_manager::to_json): New. * diagnostic-manager.h (saved_diagnostic::to_json): New decl. (diagnostic_manager::to_json): New decl. * engine.cc: Include "json.h", <zlib.h>. (exploded_node::status_to_str): New. (exploded_node::to_json): New. (exploded_edge::to_json): New. (exploded_graph::to_json): New. (dump_analyzer_json): New. (impl_run_checkers): Call it. * exploded-graph.h (exploded_node::status_to_str): New decl. (exploded_node::to_json): New. (exploded_edge::to_json): New. (exploded_graph::to_json): New. * pending-diagnostic.cc: Include "json.h". * program-point.cc: Include "json.h". (program_point::to_json): New. * program-point.h (program_point::to_json): New decl. * program-state.cc: Include "json.h". (extrinsic_state::to_json): New. (sm_state_map::to_json): New. (program_state::to_json): New. * program-state.h (extrinsic_state::to_json): New decl. (sm_state_map::to_json): New decl. (program_state::to_json): New decl. * region-model-impl-calls.cc: Include "json.h". * region-model-manager.cc: Include "json.h". * region-model-reachability.cc: Include "json.h". * region-model.cc: Include "json.h". * region-model.h (svalue::to_json): New decl. (region::to_json): New decl. * region.cc: Include "json.h". (region::to_json: New. * sm-file.cc: Include "json.h". * sm-malloc.cc: Include "json.h". * sm-pattern-test.cc: Include "json.h". * sm-sensitive.cc: Include "json.h". * sm-signal.cc: Include "json.h". (signal_delivery_edge_info_t::to_json): New. * sm-taint.cc: Include "json.h". * sm.cc: Include "diagnostic.h", "tree-diagnostic.h", and "json.h". (state_machine::state::to_json): New. (state_machine::to_json): New. * sm.h (state_machine::state::to_json): New. (state_machine::to_json): New. * state-purge.cc: Include "json.h". * store.cc: Include "json.h". (binding_key::get_desc): New. (binding_map::to_json): New. (binding_cluster::to_json): New. (store::to_json): New. * store.h (binding_key::get_desc): New decl. (binding_map::to_json): New decl. (binding_cluster::to_json): New decl. (store::to_json): New decl. * supergraph.cc: Include "json.h". (supergraph::to_json): New. (supernode::to_json): New. (superedge::to_json): New. * supergraph.h (supergraph::to_json): New decl. (supernode::to_json): New decl. (superedge::to_json): New decl. * svalue.cc: Include "json.h". (svalue::to_json): New. gcc/ChangeLog: * doc/analyzer.texi (Other Debugging Techniques): Mention -fdump-analyzer-json. * doc/invoke.texi (Static Analyzer Options): Add -fdump-analyzer-json.
Diffstat (limited to 'gcc/analyzer/program-state.cc')
-rw-r--r--gcc/analyzer/program-state.cc85
1 files changed, 85 insertions, 0 deletions
diff --git a/gcc/analyzer/program-state.cc b/gcc/analyzer/program-state.cc
index 71bb286..83a6e5b 100644
--- a/gcc/analyzer/program-state.cc
+++ b/gcc/analyzer/program-state.cc
@@ -25,6 +25,7 @@ along with GCC; see the file COPYING3. If not see
#include "diagnostic-core.h"
#include "diagnostic.h"
#include "function.h"
+#include "json.h"
#include "analyzer/analyzer.h"
#include "analyzer/analyzer-logging.h"
#include "analyzer/sm.h"
@@ -99,6 +100,26 @@ extrinsic_state::dump () const
dump_to_file (stderr);
}
+/* Return a new json::object of the form
+ {"checkers" : array of objects, one for each state_machine}. */
+
+json::object *
+extrinsic_state::to_json () const
+{
+ json::object *ext_state_obj = new json::object ();
+
+ {
+ json::array *checkers_arr = new json::array ();
+ unsigned i;
+ state_machine *sm;
+ FOR_EACH_VEC_ELT (m_checkers, i, sm)
+ checkers_arr->append (sm->to_json ());
+ ext_state_obj->set ("checkers", checkers_arr);
+ }
+
+ return ext_state_obj;
+}
+
/* Get the region_model_manager for this extrinsic_state. */
region_model_manager *
@@ -208,6 +229,33 @@ sm_state_map::dump (bool simple) const
pp_flush (&pp);
}
+/* Return a new json::object of the form
+ {"global" : (optional) value for global state,
+ SVAL_DESC : value for state}. */
+
+json::object *
+sm_state_map::to_json () const
+{
+ json::object *map_obj = new json::object ();
+
+ if (m_global_state != m_sm.get_start_state ())
+ map_obj->set ("global", m_global_state->to_json ());
+ for (map_t::iterator iter = m_map.begin ();
+ iter != m_map.end ();
+ ++iter)
+ {
+ const svalue *sval = (*iter).first;
+ entry_t e = (*iter).second;
+
+ label_text sval_desc = sval->get_desc ();
+ map_obj->set (sval_desc.m_buffer, e.m_state->to_json ());
+ sval_desc.maybe_free ();
+
+ /* This doesn't yet JSONify e.m_origin. */
+ }
+ return map_obj;
+}
+
/* Return true if no states have been set within this map
(all expressions are for the start state). */
@@ -733,6 +781,43 @@ program_state::dump (const extrinsic_state &ext_state,
dump_to_file (ext_state, summarize, true, stderr);
}
+/* Return a new json::object of the form
+ {"store" : object for store,
+ "constraints" : object for constraint_manager,
+ "curr_frame" : (optional) str for current frame,
+ "checkers" : { STATE_NAME : object per sm_state_map },
+ "valid" : true/false}. */
+
+json::object *
+program_state::to_json (const extrinsic_state &ext_state) const
+{
+ json::object *state_obj = new json::object ();
+
+ state_obj->set ("store", m_region_model->get_store ()->to_json ());
+ state_obj->set ("constraints",
+ m_region_model->get_constraints ()->to_json ());
+ if (m_region_model->get_current_frame ())
+ state_obj->set ("curr_frame",
+ m_region_model->get_current_frame ()->to_json ());
+
+ /* Provide m_checker_states as an object, using names as keys. */
+ {
+ json::object *checkers_obj = new json::object ();
+
+ int i;
+ sm_state_map *smap;
+ FOR_EACH_VEC_ELT (m_checker_states, i, smap)
+ if (!smap->is_empty_p ())
+ checkers_obj->set (ext_state.get_name (i), smap->to_json ());
+
+ state_obj->set ("checkers", checkers_obj);
+ }
+
+ state_obj->set ("valid", new json::literal (m_valid));
+
+ return state_obj;
+}
+
/* Update this program_state to reflect a top-level call to FUN.
The params will have initial_svalues. */