jingham created this revision.
jingham added a reviewer: aprantl.
Herald added a subscriber: lldb-commits.

Sometimes you want to make sure that the target doesn't run at all when running 
an expression, and you'd rather the expression fail if it would have run the 
target.  You can do this with the "expression" command by passing "--allow-jit 
0" but there's no way to do that with SBExpressionOptions.  This patch adds 
that setting.


Repository:
  rLLDB LLDB

https://reviews.llvm.org/D54056

Files:
  include/lldb/API/SBExpressionOptions.h
  packages/Python/lldbsuite/test/expression_command/dont_allow_jit/Makefile
  
packages/Python/lldbsuite/test/expression_command/dont_allow_jit/TestSampleTest.py
  packages/Python/lldbsuite/test/expression_command/dont_allow_jit/main.c
  scripts/interface/SBExpressionOptions.i
  source/API/SBExpressionOptions.cpp

Index: source/API/SBExpressionOptions.cpp
===================================================================
--- source/API/SBExpressionOptions.cpp
+++ source/API/SBExpressionOptions.cpp
@@ -159,6 +159,15 @@
                                     : m_opaque_ap->default_execution_policy);
 }
 
+bool SBExpressionOptions::GetAllowJIT() {
+  return m_opaque_ap->GetExecutionPolicy() != eExecutionPolicyNever;
+}
+
+void SBExpressionOptions::SetAllowJIT(bool allow) {
+  m_opaque_ap->SetExecutionPolicy(allow ? m_opaque_ap->default_execution_policy
+                                    : eExecutionPolicyNever);
+}
+
 EvaluateExpressionOptions *SBExpressionOptions::get() const {
   return m_opaque_ap.get();
 }
Index: scripts/interface/SBExpressionOptions.i
===================================================================
--- scripts/interface/SBExpressionOptions.i
+++ scripts/interface/SBExpressionOptions.i
@@ -132,6 +132,14 @@
 
     void
     SetTopLevel(bool b = true);
+  
+    %feature("docstring", "Gets whether to JIT an expression if it cannot be interpreted.") GetAllowJIT;
+    bool
+    GetAllowJIT();
+  
+    %feature("docstring", "Sets whether to JIT an expression if it cannot be interpreted.") SetAllowJIT;
+    void
+    SetAllowJIT(bool allow);
 
 protected:
 
Index: packages/Python/lldbsuite/test/expression_command/dont_allow_jit/main.c
===================================================================
--- packages/Python/lldbsuite/test/expression_command/dont_allow_jit/main.c
+++ packages/Python/lldbsuite/test/expression_command/dont_allow_jit/main.c
@@ -0,0 +1,15 @@
+#include <stdio.h>
+
+int
+call_me(int input)
+{
+  return printf("I was called: %d.\n", input);
+}
+
+int
+main()
+{
+  int test_var = 10;
+  printf ("Set a breakpoint here: %d.\n", test_var);
+  return call_me(100);
+}
Index: packages/Python/lldbsuite/test/expression_command/dont_allow_jit/TestSampleTest.py
===================================================================
--- packages/Python/lldbsuite/test/expression_command/dont_allow_jit/TestSampleTest.py
+++ packages/Python/lldbsuite/test/expression_command/dont_allow_jit/TestSampleTest.py
@@ -0,0 +1,94 @@
+"""
+Test that --allow-jit=false does disallow JITting:
+"""
+
+from __future__ import print_function
+
+
+import os
+import time
+import re
+import lldb
+import lldbsuite.test.lldbutil as lldbutil
+from lldbsuite.test.lldbtest import *
+from lldbsuite.test.decorators import *
+
+class TestAllowJIT(TestBase):
+
+    mydir = TestBase.compute_mydir(__file__)
+
+    # If your test case doesn't stress debug info, the
+    # set this to true.  That way it won't be run once for
+    # each debug info format.
+    NO_DEBUG_INFO_TESTCASE = True
+
+    @expectedFailureAll(oslist=["windows"], bugnumber="llvm.org/pr21765")
+    def test_allow_jit_expr_command(self):
+        """Test the --allow-jit command line flag"""
+        self.build()
+        self.main_source_file = lldb.SBFileSpec("main.c")
+        self.expr_cmd_test()
+
+    @expectedFailureAll(oslist=["windows"], bugnumber="llvm.org/pr21765")
+    def test_allow_jit_options(self):
+        """Test the SetAllowJIT SBExpressionOption setting"""
+        self.build()
+        self.main_source_file = lldb.SBFileSpec("main.c")
+        self.expr_options_test()
+
+        
+
+    def setUp(self):
+        # Call super's setUp().
+        TestBase.setUp(self)
+
+    def expr_cmd_test(self):
+        (target, process, thread, bkpt) = lldbutil.run_to_source_breakpoint(self,
+                                   "Set a breakpoint here", self.main_source_file)
+
+        frame = thread.GetFrameAtIndex(0)
+        
+        # First make sure we can call the function with 
+        interp = self.dbg.GetCommandInterpreter()
+        self.expect("expr --allow-jit 1 -- call_me(10)",
+                    substrs = ["(int) $", "= 18"])
+        # Now make sure it fails with the "can't IR interpret message" if allow-jit is false:
+        self.expect("expr --allow-jit 0 -- call_me(10)",
+                    error=True,
+                    substrs = ["Can't run the expression locally"])
+        
+    def expr_options_test(self):
+        (target, process, thread, bkpt) = lldbutil.run_to_source_breakpoint(self,
+                                   "Set a breakpoint here", self.main_source_file)
+
+        frame = thread.GetFrameAtIndex(0)
+        
+        # First make sure we can call the function with the default option set. 
+        options = lldb.SBExpressionOptions()
+        # Check that the default is to allow JIT:
+        self.assertEqual(options.GetAllowJIT(), True, "Default is true")
+
+        # Now use the options:
+        result = frame.EvaluateExpression("call_me(10)", options)
+        self.assertTrue(result.GetError().Success(), "expression succeeded")
+        self.assertEqual(result.GetValueAsSigned(), 18, "got the right value.")
+
+        # Now disallow JIT and make sure it fails:
+        options.SetAllowJIT(False)
+        # Check that we got the right value:
+        self.assertEqual(options.GetAllowJIT(), False, "Got False after setting to False")
+
+        # Again use it and ensure we fail:
+        result = frame.EvaluateExpression("call_me(10)", options)
+        self.assertTrue(result.GetError().Fail(), "expression failed with no JIT")
+        self.assertTrue("Can't run the expression locally" in result.GetError().GetCString(), "Got right error")
+
+        # Finally set the allow JIT value back to true and make sure that works:
+        options.SetAllowJIT(True)
+        self.assertEqual(options.GetAllowJIT(), True, "Set back to True correctly")
+
+        # And again, make sure this works:
+        result = frame.EvaluateExpression("call_me(10)", options)
+        self.assertTrue(result.GetError().Success(), "expression succeeded")
+        self.assertEqual(result.GetValueAsSigned(), 18, "got the right value.")
+
Index: packages/Python/lldbsuite/test/expression_command/dont_allow_jit/Makefile
===================================================================
--- packages/Python/lldbsuite/test/expression_command/dont_allow_jit/Makefile
+++ packages/Python/lldbsuite/test/expression_command/dont_allow_jit/Makefile
@@ -0,0 +1,6 @@
+LEVEL = ../../make
+
+C_SOURCES := main.c
+CFLAGS_EXTRAS += -std=c99
+
+include $(LEVEL)/Makefile.rules
Index: include/lldb/API/SBExpressionOptions.h
===================================================================
--- include/lldb/API/SBExpressionOptions.h
+++ include/lldb/API/SBExpressionOptions.h
@@ -90,6 +90,12 @@
   bool GetTopLevel();
 
   void SetTopLevel(bool b = true);
+  
+  // Gets whether we will JIT an expression if it cannot be interpreted
+  bool GetAllowJIT();
+  
+  // Sets whether we will JIT an expression if it cannot be interpreted
+  void SetAllowJIT(bool allow);
 
 protected:
   SBExpressionOptions(
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to