[Lldb-commits] [lldb] r131042 - in /lldb/trunk: include/lldb/Expression/ source/Expression/ source/Target/

Sean Callanan scallanan at apple.com
Fri May 6 18:06:41 PDT 2011


Author: spyffe
Date: Fri May  6 20:06:41 2011
New Revision: 131042

URL: http://llvm.org/viewvc/llvm-project?rev=131042&view=rev
Log:
Made expressions that are just casts of pointer 
variables be evaluated statically.

Also fixed a bug that caused the results of
statically-evaluated expressions to be materialized
improperly.

This bug also removes some duplicate code.

Modified:
    lldb/trunk/include/lldb/Expression/ClangExpressionDeclMap.h
    lldb/trunk/include/lldb/Expression/ClangExpressionParser.h
    lldb/trunk/include/lldb/Expression/ClangExpressionVariable.h
    lldb/trunk/include/lldb/Expression/ClangUserExpression.h
    lldb/trunk/include/lldb/Expression/IRForTarget.h
    lldb/trunk/source/Expression/ClangExpressionDeclMap.cpp
    lldb/trunk/source/Expression/ClangExpressionParser.cpp
    lldb/trunk/source/Expression/ClangFunction.cpp
    lldb/trunk/source/Expression/ClangUserExpression.cpp
    lldb/trunk/source/Expression/ClangUtilityFunction.cpp
    lldb/trunk/source/Expression/IRForTarget.cpp
    lldb/trunk/source/Target/Process.cpp
    lldb/trunk/source/Target/Target.cpp

Modified: lldb/trunk/include/lldb/Expression/ClangExpressionDeclMap.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/ClangExpressionDeclMap.h?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/ClangExpressionDeclMap.h (original)
+++ lldb/trunk/include/lldb/Expression/ClangExpressionDeclMap.h Fri May  6 20:06:41 2011
@@ -127,6 +127,28 @@
                           const llvm::APInt& value);
     
     //------------------------------------------------------------------
+    /// [Used by IRForTarget] Cast an existing variable given a Decl and
+    ///     a type.
+    ///
+    /// @param[in] name
+    ///     The name of the new variable
+    ///
+    /// @param[in] decl
+    ///     The Clang variable declaration for the original variable,
+    ///     which must be looked up in the map
+    ///
+    /// @param[in] type
+    ///     The desired type of the variable after casting
+    ///
+    /// @return
+    ///     The created variable
+    //------------------------------------------------------------------
+    lldb::ClangExpressionVariableSP
+    BuildCastVariable (const ConstString &name,
+                       clang::VarDecl *decl,
+                       lldb_private::TypeFromParser type);
+    
+    //------------------------------------------------------------------
     /// [Used by IRForTarget] Add a variable to the list of persistent
     ///     variables for the process.
     ///
@@ -620,7 +642,7 @@
     /// @return
     ///     The LLDB Variable found, or NULL if none was found.
     //------------------------------------------------------------------
-    Variable *
+    lldb::VariableSP
     FindVariableInScope (StackFrame &frame,
                          const ConstString &name,
                          TypeFromUser *type = NULL);
@@ -656,7 +678,7 @@
     //------------------------------------------------------------------
     Value *
     GetVariableValue (ExecutionContext &exe_ctx,
-                      Variable *var,
+                      lldb::VariableSP var,
                       clang::ASTContext *parser_ast_context,
                       TypeFromUser *found_type = NULL,
                       TypeFromParser *parser_type = NULL);
@@ -673,7 +695,7 @@
     //------------------------------------------------------------------
     void 
     AddOneVariable (NameSearchContext &context, 
-                    Variable *var);
+                    lldb::VariableSP var);
     
     //------------------------------------------------------------------
     /// Use the NameSearchContext to generate a Decl for the given

Modified: lldb/trunk/include/lldb/Expression/ClangExpressionParser.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/ClangExpressionParser.h?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/ClangExpressionParser.h (original)
+++ lldb/trunk/include/lldb/Expression/ClangExpressionParser.h Fri May  6 20:06:41 2011
@@ -103,9 +103,13 @@
     ///     The execution context to write the function into.
     ///
     /// @param[out] const_result
-    ///     If non-NULL, the result of the expression is constant, and the
+    ///     If the result of the expression is constant, and the
     ///     expression has no side effects, this is set to the result of the 
-    ///     expression.  
+    ///     expression.
+    ///
+    /// @param[in] jit_only_if_needed
+    ///     True if the expression must be compiled, regardless of whether a
+    ///     constant result could be extracted from the IR or no.
     ///
     /// @return
     ///     An error code indicating the success or failure of the operation.
@@ -116,7 +120,8 @@
              lldb::addr_t &func_addr,
              lldb::addr_t &func_end,
              ExecutionContext &exe_ctx,
-             lldb::ClangExpressionVariableSP *const_result = NULL);
+             lldb::ClangExpressionVariableSP &const_result,
+             bool jit_only_if_needed = false);
     
     //------------------------------------------------------------------
     /// Disassemble the machine code for a JITted function from the target 

Modified: lldb/trunk/include/lldb/Expression/ClangExpressionVariable.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/ClangExpressionVariable.h?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/ClangExpressionVariable.h (original)
+++ lldb/trunk/include/lldb/Expression/ClangExpressionVariable.h Fri May  6 20:06:41 2011
@@ -97,7 +97,8 @@
             m_parser_type(),
             m_named_decl (NULL),
             m_llvm_value (NULL),
-            m_lldb_value (NULL)
+            m_lldb_value (NULL),
+            m_lldb_var   ()
         {
         }
 
@@ -105,6 +106,7 @@
         const clang::NamedDecl *m_named_decl;   ///< The Decl corresponding to this variable
         llvm::Value            *m_llvm_value;   ///< The IR value corresponding to this variable; usually a GlobalValue
         lldb_private::Value    *m_lldb_value;   ///< The value found in LLDB for this variable
+        lldb::VariableSP        m_lldb_var;     ///< The original variable for this variable
 
     private:
         DISALLOW_COPY_AND_ASSIGN (ParserVars);

Modified: lldb/trunk/include/lldb/Expression/ClangUserExpression.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/ClangUserExpression.h?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/ClangUserExpression.h (original)
+++ lldb/trunk/include/lldb/Expression/ClangUserExpression.h Fri May  6 20:06:41 2011
@@ -85,11 +85,6 @@
     ///     True if the resulting persistent variable should reside in 
     ///     target memory, if applicable.
     ///
-    /// @param[out] const_result
-    ///     If this is non-NULL, the expression has no side effects, and 
-    ///     the expression returns a constant result, then that result 
-    ///     is put into this variable.
-    ///
     /// @return
     ///     True on success (no errors); false otherwise.
     //------------------------------------------------------------------
@@ -97,8 +92,7 @@
     Parse (Stream &error_stream, 
            ExecutionContext &exe_ctx,
            TypeFromUser desired_type,
-           bool keep_result_in_memory,
-           lldb::ClangExpressionVariableSP *const_result = NULL);
+           bool keep_result_in_memory);
     
     //------------------------------------------------------------------
     /// Execute the parsed expression
@@ -133,7 +127,6 @@
     Execute (Stream &error_stream,
              ExecutionContext &exe_ctx,
              bool discard_on_error,
-             bool keep_in_memory,
              ClangUserExpressionSP &shared_ptr_to_me,
              lldb::ClangExpressionVariableSP &result);
              
@@ -244,10 +237,6 @@
     ///     True if the thread's state should be restored in the case 
     ///     of an error.
     ///
-    /// @param[in] keep_in_memory
-    ///     True if the resulting persistent variable should reside in 
-    ///     target memory, if applicable.
-    ///
     /// @param[in] expr_cstr
     ///     A C string containing the expression to be evaluated.
     ///
@@ -264,7 +253,6 @@
     static ExecutionResults
     Evaluate (ExecutionContext &exe_ctx, 
               bool discard_on_error,
-              bool keep_in_memory,
               const char *expr_cstr,
               const char *expr_prefix,
               lldb::ValueObjectSP &result_valobj_sp);
@@ -289,13 +277,15 @@
     TypeFromUser                                m_desired_type;         ///< The type to coerce the expression's result to.  If NULL, inferred from the expression.
     
     std::auto_ptr<ClangExpressionDeclMap>       m_expr_decl_map;        ///< The map to use when parsing and materializing the expression.
-    std::auto_ptr<ClangExpressionVariableList> m_local_variables;      ///< The local expression variables, if the expression is DWARF.
+    std::auto_ptr<ClangExpressionVariableList>  m_local_variables;      ///< The local expression variables, if the expression is DWARF.
     std::auto_ptr<StreamString>                 m_dwarf_opcodes;        ///< The DWARF opcodes for the expression.  May be NULL.
     
     bool                                        m_cplusplus;            ///< True if the expression is compiled as a C++ member function (true if it was parsed when exe_ctx was in a C++ method).
     bool                                        m_objectivec;           ///< True if the expression is compiled as an Objective-C method (true if it was parsed when exe_ctx was in an Objective-C method).
     bool                                        m_needs_object_ptr;     ///< True if "this" or "self" must be looked up and passed in.  False if the expression doesn't really use them and they can be NULL.
     bool                                        m_const_object;         ///< True if "this" is const.
+    
+    lldb::ClangExpressionVariableSP             m_const_result;         ///< The statically-computed result of the expression.  NULL if it could not be computed statically or the expression has side effects.
 };
     
 } // namespace lldb_private

Modified: lldb/trunk/include/lldb/Expression/IRForTarget.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Expression/IRForTarget.h?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Expression/IRForTarget.h (original)
+++ lldb/trunk/include/lldb/Expression/IRForTarget.h Fri May  6 20:06:41 2011
@@ -21,9 +21,11 @@
     class CallInst;
     class Constant;
     class Function;
+    class GlobalValue;
     class GlobalVariable;
     class Instruction;
     class Module;
+    class StoreInst;
     class Value;
 }
 
@@ -62,10 +64,9 @@
     ///     are resolved.
     ///
     /// @param[in] const_result
-    ///     If non-NULL, a shared pointer to a ClangExpressionVariable that
-    ///     is populated with the statically-computed result of the function,
-    ///     if it has no side-effects and the result can be computed
-    ///     statically.
+    ///     This variable is populated with the statically-computed result
+    ///     of the function, if it has no side-effects and the result can
+    ///     be computed statically.
     ///
     /// @param[in] error_stream
     ///     If non-NULL, a stream on which errors can be printed.
@@ -75,7 +76,7 @@
     //------------------------------------------------------------------
     IRForTarget(lldb_private::ClangExpressionDeclMap *decl_map,
                 bool resolve_vars,
-                lldb::ClangExpressionVariableSP *const_result,
+                lldb::ClangExpressionVariableSP &const_result,
                 lldb_private::Stream *error_stream,
                 const char* func_name = "$__lldb_expr");
     
@@ -153,6 +154,24 @@
     /// constant, assuming it can be evaluated.  The result variable
     /// will be reset to NULL later if the expression has side effects.
     ///
+    /// @param[in] llvm_module
+    ///     The module currently being processed.
+    ///
+    /// @param[in] global
+    ///     The global entity to search for
+    ///
+    /// @return
+    ///     The corresponding variable declaration
+    //------------------------------------------------------------------   
+    clang::NamedDecl *
+    DeclForGlobal (llvm::Module &llvm_module,
+                   llvm::GlobalValue *global);
+    
+    //------------------------------------------------------------------
+    /// Set the constant result variable m_const_result to the provided
+    /// constant, assuming it can be evaluated.  The result variable
+    /// will be reset to NULL later if the expression has side effects.
+    ///
     /// @param[in] initializer
     ///     The constant initializer for the variable.
     ///
@@ -161,9 +180,6 @@
     ///
     /// @param[in] type
     ///     The Clang type of the result variable.
-    ///
-    /// @return
-    ///     True on success; false otherwise
     //------------------------------------------------------------------    
     void 
     MaybeSetConstantResult (llvm::Constant *initializer,
@@ -171,6 +187,21 @@
                             lldb_private::TypeFromParser type);
     
     //------------------------------------------------------------------
+    /// If the IR represents a cast of a variable, set m_const_result
+    /// to the result of the cast.  The result variable will be reset to
+    /// NULL latger if the expression has side effects.
+    ///
+    /// @param[in] llvm_module
+    ///     The module currently being processed.
+    ///
+    /// @param[in] type
+    ///     The Clang type of the result variable.
+    //------------------------------------------------------------------  
+    void
+    MaybeSetCastResult (llvm::Module &llvm_module,
+                        lldb_private::TypeFromParser type);
+    
+    //------------------------------------------------------------------
     /// The top-level pass implementation
     ///
     /// @param[in] llvm_module
@@ -476,10 +507,11 @@
     lldb_private::ClangExpressionDeclMap   *m_decl_map;                 ///< The DeclMap containing the Decls 
     llvm::Constant                         *m_CFStringCreateWithBytes;  ///< The address of the function CFStringCreateWithBytes, cast to the appropriate function pointer type
     llvm::Constant                         *m_sel_registerName;         ///< The address of the function sel_registerName, cast to the appropriate function pointer type
-    lldb::ClangExpressionVariableSP        *m_const_result;             ///< If non-NULL, this value should be set to the return value of the expression if it is constant and the expression has no side effects
+    lldb::ClangExpressionVariableSP        &m_const_result;             ///< This value should be set to the return value of the expression if it is constant and the expression has no side effects
     lldb_private::Stream                   *m_error_stream;             ///< If non-NULL, the stream on which errors should be printed
     
     bool                                    m_has_side_effects;         ///< True if the function's result cannot be simply determined statically
+    llvm::StoreInst                        *m_result_store;             ///< If non-NULL, the store instruction that writes to the result variable.  If m_has_side_effects is true, this is NULL.
     bool                                    m_result_is_pointer;        ///< True if the function's result in the AST is a pointer (see comments in ASTResultSynthesizer::SynthesizeBodyResult)
     
 private:

Modified: lldb/trunk/source/Expression/ClangExpressionDeclMap.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangExpressionDeclMap.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangExpressionDeclMap.cpp (original)
+++ lldb/trunk/source/Expression/ClangExpressionDeclMap.cpp Fri May  6 20:06:41 2011
@@ -139,7 +139,7 @@
                                                      type.GetASTContext(),
                                                      type.GetOpaqueQualType()),
                            context);
-    
+        
     if (!m_parser_vars->m_persistent_vars->CreatePersistentVariable (exe_ctx->GetBestExecutionContextScope (),
                                                                      name, 
                                                                      user_type, 
@@ -194,7 +194,78 @@
     }
     
     pvar_sp->m_flags |= ClangExpressionVariable::EVIsFreezeDried;
+    pvar_sp->m_flags |= ClangExpressionVariable::EVIsLLDBAllocated;
+    pvar_sp->m_flags |= ClangExpressionVariable::EVNeedsAllocation;
+
+    return pvar_sp;
+}
+
+lldb::ClangExpressionVariableSP
+ClangExpressionDeclMap::BuildCastVariable (const ConstString &name,
+                                           clang::VarDecl *decl,
+                                           lldb_private::TypeFromParser type)
+{
+    assert (m_parser_vars.get());
+    
+    lldb::LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
+    
+    ExecutionContext *exe_ctx = m_parser_vars->m_exe_ctx;
+    clang::ASTContext *context(exe_ctx->target->GetScratchClangASTContext()->getASTContext());
+    
+    ClangExpressionVariableSP var_sp (m_found_entities.GetVariable(decl));
+    
+    if (!var_sp)
+        var_sp = m_parser_vars->m_persistent_vars->GetVariable(decl);
+    
+    if (!var_sp)
+        return ClangExpressionVariableSP();
+    
+    TypeFromUser user_type(ClangASTContext::CopyType(context, 
+                                                     type.GetASTContext(),
+                                                     type.GetOpaqueQualType()),
+                           context);
+    
+    TypeFromUser var_type = var_sp->GetTypeFromUser();
+    
+    VariableSP var = FindVariableInScope (*exe_ctx->frame, var_sp->GetName(), &var_type);
+    
+    if (!var)
+        return lldb::ClangExpressionVariableSP(); // but we should handle this; it may be a persistent variable
+    
+    ValueObjectSP var_valobj = exe_ctx->frame->GetValueObjectForFrameVariable(var, lldb::eNoDynamicValues);
 
+    if (!var_valobj)
+        return lldb::ClangExpressionVariableSP();
+    
+    ValueObjectSP var_casted_valobj = var_valobj->CastPointerType(name.GetCString(), user_type);
+    
+    if (!var_casted_valobj)
+        return lldb::ClangExpressionVariableSP();
+    
+    if (log)
+    {
+        StreamString my_stream_string;
+        
+        ClangASTType::DumpTypeDescription (var_type.GetASTContext(),
+                                           var_type.GetOpaqueQualType(),
+                                           &my_stream_string);
+        
+        
+        log->Printf("Building cast variable to type: %s", my_stream_string.GetString().c_str());
+    }
+    
+    ClangExpressionVariableSP pvar_sp = m_parser_vars->m_persistent_vars->CreatePersistentVariable (var_casted_valobj);
+    
+    if (!pvar_sp)
+        return lldb::ClangExpressionVariableSP();
+    
+    if (pvar_sp != m_parser_vars->m_persistent_vars->GetVariable(name))
+        return lldb::ClangExpressionVariableSP();
+    
+    pvar_sp->m_flags |= ClangExpressionVariable::EVIsFreezeDried;
+    pvar_sp->m_flags |= ClangExpressionVariable::EVIsLLDBAllocated;
+    pvar_sp->m_flags |= ClangExpressionVariable::EVNeedsAllocation;
+            
     return pvar_sp;
 }
 
@@ -535,9 +606,9 @@
         return false;
     }
     
-    Variable *object_ptr_var = FindVariableInScope (*exe_ctx.frame,
-                                                    object_name, 
-                                                    (suppress_type_check ? NULL : &m_struct_vars->m_object_pointer_type));
+    VariableSP object_ptr_var = FindVariableInScope (*exe_ctx.frame,
+                                                     object_name, 
+                                                     (suppress_type_check ? NULL : &m_struct_vars->m_object_pointer_type));
     
     if (!object_ptr_var)
     {
@@ -1122,7 +1193,7 @@
             if (log)
                 log->Printf("Materialized %s into 0x%llx", var_sp->GetName().GetCString(), (uint64_t)mem);
         }
-        else if (!var_sp->m_flags & ClangExpressionVariable::EVIsProgramReference)
+        else if (!(var_sp->m_flags & ClangExpressionVariable::EVIsProgramReference))
         {
             err.SetErrorStringWithFormat("Persistent variables without separate allocations are not currently supported.");
             return false;
@@ -1153,7 +1224,7 @@
     const ConstString &name(expr_var->GetName());
     TypeFromUser type(expr_var->GetTypeFromUser());
     
-    Variable *var = FindVariableInScope (*exe_ctx.frame, name, &type);
+    VariableSP var = FindVariableInScope (*exe_ctx.frame, name, &type);
     
     if (!var)
     {
@@ -1495,7 +1566,7 @@
     return true;
 }
 
-Variable *
+lldb::VariableSP
 ClangExpressionDeclMap::FindVariableInScope
 (
     StackFrame &frame,
@@ -1508,7 +1579,7 @@
     VariableList *var_list = frame.GetVariableList(true);
     
     if (!var_list)
-        return NULL;
+        return lldb::VariableSP();
     
     lldb::VariableSP var_sp (var_list->FindVariable(name));
         
@@ -1543,17 +1614,17 @@
         if (type->GetASTContext() == var_sp->GetType()->GetClangAST())
         {
             if (!ClangASTContext::AreTypesSame(type->GetASTContext(), type->GetOpaqueQualType(), var_sp->GetType()->GetClangFullType()))
-                return NULL;
+                return lldb::VariableSP();
         }
         else
         {
             if (log)
                 log->PutCString("Skipping a candidate variable because of different AST contexts");
-            return NULL;
+            return lldb::VariableSP();
         }
     }
 
-    return var_sp.get();
+    return var_sp;
 }
 
 // Interface for ClangASTSource
@@ -1590,7 +1661,7 @@
     // doesn't start with our phony prefix of '$'
     if (name_unique_cstr[0] != '$')
     {
-        Variable *var = FindVariableInScope(*m_parser_vars->m_exe_ctx->frame, name);
+        VariableSP var = FindVariableInScope(*m_parser_vars->m_exe_ctx->frame, name);
         
         // If we found a variable in scope, no need to pull up function names
         if (var != NULL)
@@ -1797,7 +1868,7 @@
 ClangExpressionDeclMap::GetVariableValue
 (
     ExecutionContext &exe_ctx,
-    Variable *var,
+    VariableSP var,
     clang::ASTContext *parser_ast_context,
     TypeFromUser *user_type,
     TypeFromParser *parser_type
@@ -1904,7 +1975,7 @@
 }
 
 void
-ClangExpressionDeclMap::AddOneVariable (NameSearchContext &context, Variable* var)
+ClangExpressionDeclMap::AddOneVariable (NameSearchContext &context, VariableSP var)
 {
     assert (m_parser_vars.get());
     
@@ -1936,6 +2007,7 @@
     entity->m_parser_vars->m_named_decl  = var_decl;
     entity->m_parser_vars->m_llvm_value  = NULL;
     entity->m_parser_vars->m_lldb_value  = var_location;
+    entity->m_parser_vars->m_lldb_var    = var;
     
     if (log)
     {

Modified: lldb/trunk/source/Expression/ClangExpressionParser.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangExpressionParser.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangExpressionParser.cpp (original)
+++ lldb/trunk/source/Expression/ClangExpressionParser.cpp Fri May  6 20:06:41 2011
@@ -456,7 +456,8 @@
                                 lldb::addr_t &func_addr, 
                                 lldb::addr_t &func_end, 
                                 ExecutionContext &exe_ctx,
-                                lldb::ClangExpressionVariableSP *const_result)
+                                lldb::ClangExpressionVariableSP &const_result,
+                                bool jit_only_if_needed)
 {
     func_allocation_addr = LLDB_INVALID_ADDRESS;
 	func_addr = LLDB_INVALID_ADDRESS;
@@ -512,6 +513,12 @@
             return err;
         }
         
+        if (jit_only_if_needed && const_result.get())
+        {
+            err.Clear();
+            return err;
+        }
+        
         if (m_expr.NeedsValidation() && exe_ctx.process->GetDynamicCheckers())
         {
             IRDynamicChecks ir_dynamic_checks(*exe_ctx.process->GetDynamicCheckers(), function_name.c_str());

Modified: lldb/trunk/source/Expression/ClangFunction.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangFunction.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangFunction.cpp (original)
+++ lldb/trunk/source/Expression/ClangFunction.cpp Fri May  6 20:06:41 2011
@@ -251,7 +251,9 @@
     if (m_JITted)
         return true;
     
-    Error jit_error (m_parser->MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx));
+    lldb::ClangExpressionVariableSP const_result;
+    
+    Error jit_error (m_parser->MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx, const_result));
     
     if (!jit_error.Success())
         return false;

Modified: lldb/trunk/source/Expression/ClangUserExpression.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangUserExpression.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangUserExpression.cpp (original)
+++ lldb/trunk/source/Expression/ClangUserExpression.cpp Fri May  6 20:06:41 2011
@@ -49,7 +49,8 @@
     m_cplusplus (false),
     m_objectivec (false),
     m_needs_object_ptr (false),
-    m_const_object (false)
+    m_const_object (false),
+    m_const_result ()
 {
 }
 
@@ -147,8 +148,7 @@
 ClangUserExpression::Parse (Stream &error_stream, 
                             ExecutionContext &exe_ctx,
                             TypeFromUser desired_type,
-                            bool keep_result_in_memory,
-                            lldb::ClangExpressionVariableSP *const_result)
+                            bool keep_result_in_memory)
 {
     lldb::LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
     
@@ -284,7 +284,7 @@
     
     m_dwarf_opcodes.reset();
     
-    Error jit_error = parser.MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx, const_result);
+    Error jit_error = parser.MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx, m_const_result, true);
     
     m_expr_decl_map->DidParse();
     
@@ -457,7 +457,6 @@
 ClangUserExpression::Execute (Stream &error_stream,
                               ExecutionContext &exe_ctx,
                               bool discard_on_error,
-                              bool keep_in_memory,
                               ClangUserExpression::ClangUserExpressionSP &shared_ptr_to_me,
                               lldb::ClangExpressionVariableSP &result)
 {
@@ -556,7 +555,6 @@
 ExecutionResults
 ClangUserExpression::Evaluate (ExecutionContext &exe_ctx, 
                                bool discard_on_error,
-                               bool keep_in_memory,
                                const char *expr_cstr,
                                const char *expr_prefix,
                                lldb::ValueObjectSP &result_valobj_sp)
@@ -603,13 +601,11 @@
     ClangUserExpressionSP user_expression_sp (new ClangUserExpression (expr_cstr, expr_prefix));
 
     StreamString error_stream;
-    
-    lldb::ClangExpressionVariableSP const_result;
-    
+        
     if (log)
         log->Printf("== [ClangUserExpression::Evaluate] Parsing expression %s ==", expr_cstr);
     
-    if (!user_expression_sp->Parse (error_stream, exe_ctx, TypeFromUser(NULL, NULL), &const_result))
+    if (!user_expression_sp->Parse (error_stream, exe_ctx, TypeFromUser(NULL, NULL), true))
     {
         if (error_stream.GetString().empty())
             error.SetErrorString ("expression failed to parse, unknown error");
@@ -620,12 +616,12 @@
     {
         lldb::ClangExpressionVariableSP expr_result;
 
-        if (const_result.get() && !keep_in_memory)
+        if (user_expression_sp->m_const_result.get())
         {
             if (log)
                 log->Printf("== [ClangUserExpression::Evaluate] Expression evaluated as a constant ==");
             
-            result_valobj_sp = const_result->GetValueObject();
+            result_valobj_sp = user_expression_sp->m_const_result->GetValueObject();
         }
         else
         {    
@@ -637,7 +633,6 @@
             execution_results = user_expression_sp->Execute (error_stream, 
                                                              exe_ctx, 
                                                              discard_on_error,
-                                                             keep_in_memory,
                                                              user_expression_sp, 
                                                              expr_result);
             

Modified: lldb/trunk/source/Expression/ClangUtilityFunction.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/ClangUtilityFunction.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/ClangUtilityFunction.cpp (original)
+++ lldb/trunk/source/Expression/ClangUtilityFunction.cpp Fri May  6 20:06:41 2011
@@ -108,8 +108,10 @@
     //////////////////////////////////
     // JIT the output of the parser
     //
+    
+    lldb::ClangExpressionVariableSP const_result;
         
-    Error jit_error = parser.MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx);
+    Error jit_error = parser.MakeJIT (m_jit_alloc, m_jit_start_addr, m_jit_end_addr, exe_ctx, const_result);
     
     if (exe_ctx.process && m_jit_start_addr != LLDB_INVALID_ADDRESS)
         m_jit_process_sp = exe_ctx.process->GetSP();

Modified: lldb/trunk/source/Expression/IRForTarget.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/IRForTarget.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Expression/IRForTarget.cpp (original)
+++ lldb/trunk/source/Expression/IRForTarget.cpp Fri May  6 20:06:41 2011
@@ -26,6 +26,7 @@
 #include "lldb/Core/Scalar.h"
 #include "lldb/Core/StreamString.h"
 #include "lldb/Expression/ClangExpressionDeclMap.h"
+#include "lldb/Symbol/ClangASTContext.h"
 
 #include <map>
 
@@ -35,7 +36,7 @@
 
 IRForTarget::IRForTarget (lldb_private::ClangExpressionDeclMap *decl_map,
                           bool resolve_vars,
-                          lldb::ClangExpressionVariableSP *const_result,
+                          lldb::ClangExpressionVariableSP &const_result,
                           lldb_private::Stream *error_stream,
                           const char *func_name) :
     ModulePass(ID),
@@ -44,10 +45,11 @@
     m_decl_map(decl_map),
     m_CFStringCreateWithBytes(NULL),
     m_sel_registerName(NULL),
-    m_const_result(const_result),
     m_error_stream(error_stream),
     m_has_side_effects(false),
-    m_result_is_pointer(false)
+    m_result_store(NULL),
+    m_result_is_pointer(false),
+    m_const_result(const_result)
 {
 }
 
@@ -87,7 +89,7 @@
 {
     llvm::Function::iterator bbi;
     BasicBlock::iterator ii;
-    
+        
     for (bbi = llvm_function.begin();
          bbi != llvm_function.end();
          ++bbi)
@@ -108,15 +110,33 @@
                     
                     Value *store_ptr = store_inst->getPointerOperand();
                     
-                    if (!isa <AllocaInst> (store_ptr))
-                        return true;
-                    else
+                    std::string ptr_name;
+                    
+                    if (store_ptr->hasName())
+                        ptr_name = store_ptr->getNameStr();
+                    
+                    if (isa <AllocaInst> (store_ptr))
                         break;
+
+                    if (ptr_name.find("$__lldb_expr_result") != std::string::npos)
+                    {
+                        if (ptr_name.find("GV") == std::string::npos)
+                            m_result_store = store_inst;
+                    }
+                    else
+                    {
+                        return true;
+                    }
+                        
+                    break;
                 }
             case Instruction::Load:
             case Instruction::Alloca:
             case Instruction::GetElementPtr:
+            case Instruction::BitCast:
             case Instruction::Ret:
+            case Instruction::ICmp:
+            case Instruction::Br:
                 break;
             }
         }
@@ -125,18 +145,133 @@
     return false;
 }
 
+clang::NamedDecl *
+IRForTarget::DeclForGlobal (llvm::Module &module, GlobalValue *global_val)
+{
+    lldb::LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
+    
+    NamedMDNode *named_metadata = module.getNamedMetadata("clang.global.decl.ptrs");
+    
+    if (!named_metadata)
+        return NULL;
+    
+    unsigned num_nodes = named_metadata->getNumOperands();
+    unsigned node_index;
+    
+    for (node_index = 0;
+         node_index < num_nodes;
+         ++node_index)
+    {
+        MDNode *metadata_node = named_metadata->getOperand(node_index);
+        
+        if (!metadata_node)
+            return NULL;
+        
+        if (metadata_node->getNumOperands() != 2)
+            continue;
+        
+        if (metadata_node->getOperand(0) != global_val)
+            continue;
+        
+        ConstantInt *constant_int = dyn_cast<ConstantInt>(metadata_node->getOperand(1));
+        
+        if (!constant_int)
+            return NULL;
+        
+        uintptr_t ptr = constant_int->getZExtValue();
+        
+        return reinterpret_cast<clang::NamedDecl *>(ptr);
+    }
+    
+    return NULL;
+}
+
 void 
 IRForTarget::MaybeSetConstantResult (llvm::Constant *initializer,
                                      const lldb_private::ConstString &name,
                                      lldb_private::TypeFromParser type)
 {
-    if (!m_const_result)
+    if (llvm::ConstantExpr *init_expr = dyn_cast<llvm::ConstantExpr>(initializer))
+    {
+        switch (init_expr->getOpcode())
+        {
+        default:
+            return;
+        case Instruction::IntToPtr:
+            MaybeSetConstantResult (init_expr->getOperand(0), name, type);
+            return;
+        }
+    }
+    else if (llvm::ConstantInt *init_int = dyn_cast<llvm::ConstantInt>(initializer))
+    {
+        m_const_result = m_decl_map->BuildIntegerVariable(name, type, init_int->getValue());
+    }
+}
+
+void
+IRForTarget::MaybeSetCastResult (llvm::Module &llvm_module, lldb_private::TypeFromParser type)
+{
+    lldb::LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS));
+    
+    if (!m_result_store)
         return;
     
-    if (llvm::ConstantInt *init_int = dyn_cast<llvm::ConstantInt>(initializer))
+    LoadInst *original_load = NULL;
+        
+    for (llvm::Value *current_value = m_result_store->getValueOperand(), *next_value;
+         current_value != NULL;
+         current_value = next_value)
     {
-        *m_const_result = m_decl_map->BuildIntegerVariable(name, type, init_int->getValue());
+        CastInst *cast_inst = dyn_cast<CastInst>(current_value);
+        LoadInst *load_inst = dyn_cast<LoadInst>(current_value);
+        
+        if (cast_inst)
+        {
+            next_value = cast_inst->getOperand(0);
+        }
+        else if(load_inst)
+        {
+            if (isa<LoadInst>(load_inst->getPointerOperand()))
+            {
+                next_value = load_inst->getPointerOperand();
+            }
+            else
+            {
+                original_load = load_inst;
+                break;
+            }
+        }
+        else
+        {
+            return;
+        }
     }
+    
+    Value *loaded_value = original_load->getPointerOperand();
+    GlobalVariable *loaded_global = dyn_cast<GlobalVariable>(loaded_value);
+    
+    if (!loaded_global)
+        return;
+    
+    clang::NamedDecl *loaded_decl = DeclForGlobal(llvm_module, loaded_global);
+    
+    if (!loaded_decl)
+        return;
+    
+    clang::VarDecl *loaded_var = dyn_cast<clang::VarDecl>(loaded_decl);
+    
+    if (!loaded_var)
+        return;
+    
+    if (log)
+    {
+        lldb_private::StreamString type_desc_stream;
+        type.DumpTypeDescription(&type_desc_stream);
+        
+        log->Printf("Type to cast variable to: \"%s\"", type_desc_stream.GetString().c_str());
+    }
+    
+    m_const_result = m_decl_map->BuildCastVariable(m_result_name, loaded_var, type);
 }
 
 bool 
@@ -214,64 +349,50 @@
         return false;
     }
     
-    // Find the metadata and follow it to the VarDecl
-    
-    NamedMDNode *named_metadata = llvm_module.getNamedMetadata("clang.global.decl.ptrs");
-    
-    if (!named_metadata)
+    clang::NamedDecl *result_decl = DeclForGlobal (llvm_module, result_global);
+    if (!result_decl)
     {
         if (log)
-            log->PutCString("No global metadata");
+            log->PutCString("Result variable doesn't have a corresponding Decl");
         
         if (m_error_stream)
-            m_error_stream->Printf("Internal error [IRForTarget]: No metadata\n");
+            m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s) does not have a corresponding Clang entity\n", result_name);
         
         return false;
     }
-        
-    unsigned num_nodes = named_metadata->getNumOperands();
-    unsigned node_index;
     
-    MDNode *metadata_node = NULL;
-    
-    for (node_index = 0;
-         node_index < num_nodes;
-         ++node_index)
+    if (log)
     {
-        metadata_node = named_metadata->getOperand(node_index);
-        
-        if (metadata_node->getNumOperands() != 2)
-            continue;
+        std::string decl_desc_str;
+        raw_string_ostream decl_desc_stream(decl_desc_str);
+        result_decl->print(decl_desc_stream);
+        decl_desc_stream.flush();
         
-        if (metadata_node->getOperand(0) == result_global)
-            break;
+        log->Printf("Found result decl: \"%s\"", decl_desc_str.c_str());
     }
     
-    if (!metadata_node)
+    clang::VarDecl *result_var = dyn_cast<clang::VarDecl>(result_decl);
+    if (!result_var)
     {
         if (log)
-            log->PutCString("Couldn't find result metadata");
+            log->PutCString("Result variable Decl isn't a VarDecl");
         
         if (m_error_stream)
-            m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s) is a global variable, but has no metadata\n", result_name);
+            m_error_stream->Printf("Internal error [IRForTarget]: Result variable (%s)'s corresponding Clang entity isn't a variable\n", result_name);
         
         return false;
     }
-        
-    ConstantInt *constant_int = dyn_cast<ConstantInt>(metadata_node->getOperand(1));
-        
-    lldb::addr_t result_decl_intptr = constant_int->getZExtValue();
     
-    clang::VarDecl *result_decl = reinterpret_cast<clang::VarDecl *>(result_decl_intptr);
-        
     // Get the next available result name from m_decl_map and create the persistent
     // variable for it
     
     lldb_private::TypeFromParser result_decl_type;
     
+    // If the result is an Lvalue, it is emitted as a pointer; see
+    // ASTResultSynthesizer::SynthesizeBodyResult.
     if (m_result_is_pointer)
     {
-        clang::QualType pointer_qual_type = result_decl->getType();
+        clang::QualType pointer_qual_type = result_var->getType();
         const clang::Type *pointer_type = pointer_qual_type.getTypePtr();
         const clang::PointerType *pointer_pointertype = dyn_cast<clang::PointerType>(pointer_type);
         
@@ -293,18 +414,19 @@
     }
     else
     {
-        result_decl_type = lldb_private::TypeFromParser(result_decl->getType().getAsOpaquePtr(),
+        result_decl_type = lldb_private::TypeFromParser(result_var->getType().getAsOpaquePtr(),
                                                         &result_decl->getASTContext());
     }
     
+    if (log)
+    {
+        lldb_private::StreamString type_desc_stream;
+        result_decl_type.DumpTypeDescription(&type_desc_stream);
+        
+        log->Printf("Result decl type: \"%s\"", type_desc_stream.GetString().c_str());
+    }
+    
     m_result_name = m_decl_map->GetPersistentResultName();
-    // If the result is an Lvalue, it is emitted as a pointer; see
-    // ASTResultSynthesizer::SynthesizeBodyResult.
-    m_decl_map->AddPersistentVariable(result_decl, 
-                                      m_result_name, 
-                                      result_decl_type,
-                                      true,
-                                      m_result_is_pointer);
     
     if (log)
         log->Printf("Creating a new result global: \"%s\"", m_result_name.GetCString());
@@ -325,8 +447,8 @@
     // ClangExpressionDeclMap::DoMaterialize, and the name of the variable is
     // fixed up.
     
-    ConstantInt *new_constant_int = ConstantInt::get(constant_int->getType(), 
-                                                     result_decl_intptr,
+    ConstantInt *new_constant_int = ConstantInt::get(llvm::Type::getInt64Ty(llvm_module.getContext()),
+                                                     reinterpret_cast<uint64_t>(result_decl),
                                                      false);
     
     llvm::Value* values[2];
@@ -334,6 +456,7 @@
     values[1] = new_constant_int;
     
     MDNode *persistent_global_md = MDNode::get(llvm_module.getContext(), values, 2);
+    NamedMDNode *named_metadata = llvm_module.getNamedMetadata("clang.global.decl.ptrs");
     named_metadata->addOperand(persistent_global_md);
     
     if (log)
@@ -384,8 +507,20 @@
     }
     else
     {
+        if (!m_has_side_effects && lldb_private::ClangASTContext::IsPointerType (result_decl_type.GetOpaqueQualType()))
+        {
+            MaybeSetCastResult (llvm_module, result_decl_type);
+        }
+        
         result_global->replaceAllUsesWith(new_result_global);
     }
+    
+    if (!m_const_result)
+        m_decl_map->AddPersistentVariable(result_decl, 
+                                          m_result_name, 
+                                          result_decl_type,
+                                          true,
+                                          m_result_is_pointer);
         
     result_global->eraseFromParent();
     
@@ -1047,45 +1182,6 @@
     return true;
 }
 
-static clang::NamedDecl *
-DeclForGlobalValue(Module &module, GlobalValue *global_value)
-{
-    NamedMDNode *named_metadata = module.getNamedMetadata("clang.global.decl.ptrs");
-    
-    if (!named_metadata)
-        return NULL;
-    
-    unsigned num_nodes = named_metadata->getNumOperands();
-    unsigned node_index;
-    
-    for (node_index = 0;
-         node_index < num_nodes;
-         ++node_index)
-    {
-        MDNode *metadata_node = named_metadata->getOperand(node_index);
-        
-        if (!metadata_node)
-            return NULL;
-        
-        if (metadata_node->getNumOperands() != 2)
-            continue;
-        
-        if (metadata_node->getOperand(0) != global_value)
-            continue;
-        
-        ConstantInt *constant_int = dyn_cast<ConstantInt>(metadata_node->getOperand(1));
-        
-        if (!constant_int)
-            return NULL;
-        
-        uintptr_t ptr = constant_int->getZExtValue();
-        
-        return reinterpret_cast<clang::NamedDecl *>(ptr);
-    }
-    
-    return NULL;
-}
-
 // This function does not report errors; its callers are responsible.
 bool 
 IRForTarget::MaybeHandleVariable (Module &llvm_module, Value *llvm_value_ptr)
@@ -1110,7 +1206,7 @@
     }
     else if (GlobalVariable *global_variable = dyn_cast<GlobalVariable>(llvm_value_ptr))
     {
-        clang::NamedDecl *named_decl = DeclForGlobalValue(llvm_module, global_variable);
+        clang::NamedDecl *named_decl = DeclForGlobal(llvm_module, global_variable);
         
         if (!named_decl)
         {
@@ -1331,7 +1427,7 @@
         str.SetCStringWithLength (fun->getName().data(), fun->getName().size());
     }
     
-    clang::NamedDecl *fun_decl = DeclForGlobalValue (llvm_module, fun);
+    clang::NamedDecl *fun_decl = DeclForGlobal (llvm_module, fun);
     lldb::addr_t fun_addr = LLDB_INVALID_ADDRESS;
     Value **fun_value_ptr = NULL;
     
@@ -1445,7 +1541,7 @@
         if (log)
             log->Printf("Examining %s, DeclForGlobalValue returns %p", 
                         (*global).getName().str().c_str(),
-                        DeclForGlobalValue(llvm_module, global));
+                        DeclForGlobal(llvm_module, global));
     
         if ((*global).getName().str().find("OBJC_IVAR") == 0)
         {
@@ -1457,7 +1553,7 @@
                 return false;
             }
         }
-        else if (DeclForGlobalValue(llvm_module, global))
+        else if (DeclForGlobal(llvm_module, global))
         {
             if (!MaybeHandleVariable (llvm_module, global))
             {
@@ -1882,6 +1978,9 @@
         return false;
     }
     
+    if (m_const_result)
+        return true;
+    
     ///////////////////////////////////////////////////////////////////////////////
     // Fix all Objective-C constant strings to use NSStringWithCString:encoding:
     //

Modified: lldb/trunk/source/Target/Process.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/Process.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Target/Process.cpp (original)
+++ lldb/trunk/source/Target/Process.cpp Fri May  6 20:06:41 2011
@@ -1246,14 +1246,13 @@
                 ExecutionContext exe_ctx;
                 frame_sp->CalculateExecutionContext (exe_ctx);
                 bool unwind_on_error = true;
-                bool keep_in_memory = false;
                 StreamString expr;
                 char path[PATH_MAX];
                 image_spec.GetPath(path, sizeof(path));
                 expr.Printf("dlopen (\"%s\", 2)", path);
                 const char *prefix = "extern \"C\" void* dlopen (const char *path, int mode);\n";
                 lldb::ValueObjectSP result_valobj_sp;
-                ClangUserExpression::Evaluate (exe_ctx, keep_in_memory, unwind_on_error, expr.GetData(), prefix, result_valobj_sp);
+                ClangUserExpression::Evaluate (exe_ctx, unwind_on_error, expr.GetData(), prefix, result_valobj_sp);
                 if (result_valobj_sp->GetError().Success())
                 {
                     Scalar scalar;
@@ -1314,12 +1313,11 @@
                         ExecutionContext exe_ctx;
                         frame_sp->CalculateExecutionContext (exe_ctx);
                         bool unwind_on_error = true;
-                        bool keep_in_memory = false;
                         StreamString expr;
                         expr.Printf("dlclose ((void *)0x%llx)", image_addr);
                         const char *prefix = "extern \"C\" int dlclose(void* handle);\n";
                         lldb::ValueObjectSP result_valobj_sp;
-                        ClangUserExpression::Evaluate (exe_ctx, unwind_on_error, keep_in_memory, expr.GetData(), prefix, result_valobj_sp);
+                        ClangUserExpression::Evaluate (exe_ctx, unwind_on_error, expr.GetData(), prefix, result_valobj_sp);
                         if (result_valobj_sp->GetError().Success())
                         {
                             Scalar scalar;

Modified: lldb/trunk/source/Target/Target.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/Target.cpp?rev=131042&r1=131041&r2=131042&view=diff
==============================================================================
--- lldb/trunk/source/Target/Target.cpp (original)
+++ lldb/trunk/source/Target/Target.cpp Fri May  6 20:06:41 2011
@@ -994,7 +994,6 @@
         
             execution_results = ClangUserExpression::Evaluate (exe_ctx, 
                                                                unwind_on_error,
-                                                               keep_in_memory,
                                                                expr_cstr, 
                                                                prefix, 
                                                                result_valobj_sp);





More information about the lldb-commits mailing list