[Lldb-commits] [lldb] r112502 - in /lldb/trunk: include/lldb/API/SBDebugger.h include/lldb/Core/Debugger.h include/lldb/Host/Host.h lldb.xcodeproj/project.pbxproj source/API/SBDebugger.cpp source/Commands/CommandObjectFrame.cpp source/Commands/CommandObjectThread.cpp source/Core/Debugger.cpp source/Host/macosx/Host.mm source/Host/macosx/cfcpp/CFCReleaser.h tools/driver/Driver.cpp tools/driver/Driver.h
Jim Ingham
jingham at apple.com
Mon Aug 30 12:44:40 PDT 2010
Author: jingham
Date: Mon Aug 30 14:44:40 2010
New Revision: 112502
URL: http://llvm.org/viewvc/llvm-project?rev=112502&view=rev
Log:
Added a way to open the current source file & line in an external editor, and you can turn this on with:
lldb -e
Modified:
lldb/trunk/include/lldb/API/SBDebugger.h
lldb/trunk/include/lldb/Core/Debugger.h
lldb/trunk/include/lldb/Host/Host.h
lldb/trunk/lldb.xcodeproj/project.pbxproj
lldb/trunk/source/API/SBDebugger.cpp
lldb/trunk/source/Commands/CommandObjectFrame.cpp
lldb/trunk/source/Commands/CommandObjectThread.cpp
lldb/trunk/source/Core/Debugger.cpp
lldb/trunk/source/Host/macosx/Host.mm
lldb/trunk/source/Host/macosx/cfcpp/CFCReleaser.h
lldb/trunk/tools/driver/Driver.cpp
lldb/trunk/tools/driver/Driver.h
Modified: lldb/trunk/include/lldb/API/SBDebugger.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/API/SBDebugger.h?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/include/lldb/API/SBDebugger.h (original)
+++ lldb/trunk/include/lldb/API/SBDebugger.h Mon Aug 30 14:44:40 2010
@@ -106,6 +106,14 @@
lldb::SBSourceManager &
GetSourceManager ();
+
+ // FIXME: Once we get the set show stuff in place, the driver won't need
+ // an interface to the Set/Get UseExternalEditor.
+ bool
+ SetUseExternalEditor (bool input);
+
+ bool
+ UseExternalEditor ();
bool
GetDefaultArchitecture (char *arch_name, size_t arch_name_len);
Modified: lldb/trunk/include/lldb/Core/Debugger.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/Debugger.h?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Core/Debugger.h (original)
+++ lldb/trunk/include/lldb/Core/Debugger.h Mon Aug 30 14:44:40 2010
@@ -143,6 +143,20 @@
static lldb::DebuggerSP
FindDebuggerWithID (lldb::user_id_t id);
+
+ bool
+ SetUseExternalEditor (bool value)
+ {
+ bool old_value = m_use_external_editor;
+ m_use_external_editor = value;
+ return old_value;
+ }
+
+ bool
+ UseExternalEditor ()
+ {
+ return m_use_external_editor;
+ }
protected:
@@ -170,6 +184,7 @@
std::stack<lldb::InputReaderSP> m_input_readers;
std::string m_input_reader_data;
+ bool m_use_external_editor; // FIXME: Convert this to a set/show variable on the debugger.
private:
Modified: lldb/trunk/include/lldb/Host/Host.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Host/Host.h?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Host/Host.h (original)
+++ lldb/trunk/include/lldb/Host/Host.h Mon Aug 30 14:44:40 2010
@@ -267,6 +267,9 @@
static ArchSpec
GetArchSpecForExistingProcess (const char *process_name);
+
+ static bool
+ OpenFileInExternalEditor (FileSpec &file_spec, uint32_t line_no);
};
Modified: lldb/trunk/lldb.xcodeproj/project.pbxproj
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/lldb.xcodeproj/project.pbxproj?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/lldb.xcodeproj/project.pbxproj (original)
+++ lldb/trunk/lldb.xcodeproj/project.pbxproj Mon Aug 30 14:44:40 2010
@@ -356,6 +356,7 @@
4C08CDEC11C81F1E001610A8 /* ThreadSpec.h in Headers */ = {isa = PBXBuildFile; fileRef = 4C08CDEB11C81F1E001610A8 /* ThreadSpec.h */; };
4C5DBBC811E3FEC60035160F /* CommandObjectCommands.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4C5DBBC611E3FEC60035160F /* CommandObjectCommands.cpp */; };
4C5DBBC911E3FEC60035160F /* CommandObjectCommands.h in Headers */ = {isa = PBXBuildFile; fileRef = 4C5DBBC711E3FEC60035160F /* CommandObjectCommands.h */; };
+ 4C74CB6312288704006A8171 /* Carbon.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 4C74CB6212288704006A8171 /* Carbon.framework */; };
4CA9637B11B6E99A00780E28 /* CommandObjectApropos.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4CA9637911B6E99A00780E28 /* CommandObjectApropos.cpp */; };
9A19A6AF1163BBB200E0D453 /* SBValue.h in Headers */ = {isa = PBXBuildFile; fileRef = 9A19A6A51163BB7E00E0D453 /* SBValue.h */; settings = {ATTRIBUTES = (Public, ); }; };
9A19A6B01163BBB300E0D453 /* SBValue.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9A19A6AD1163BB9800E0D453 /* SBValue.cpp */; };
@@ -960,6 +961,7 @@
4C51FF1611A4C486007C962F /* ObjCTrampolineHandler.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ObjCTrampolineHandler.cpp; sourceTree = "<group>"; };
4C5DBBC611E3FEC60035160F /* CommandObjectCommands.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = CommandObjectCommands.cpp; path = source/Commands/CommandObjectCommands.cpp; sourceTree = "<group>"; };
4C5DBBC711E3FEC60035160F /* CommandObjectCommands.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = CommandObjectCommands.h; path = source/Commands/CommandObjectCommands.h; sourceTree = "<group>"; };
+ 4C74CB6212288704006A8171 /* Carbon.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Carbon.framework; path = /System/Library/Frameworks/Carbon.framework; sourceTree = "<absolute>"; };
4C98D3DA118FB96F00E575D0 /* ClangFunction.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ClangFunction.cpp; path = source/Expression/ClangFunction.cpp; sourceTree = "<group>"; };
4C98D3DB118FB96F00E575D0 /* RecordingMemoryManager.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = RecordingMemoryManager.cpp; path = source/Expression/RecordingMemoryManager.cpp; sourceTree = "<group>"; };
4C98D3E0118FB98F00E575D0 /* ClangFunction.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ClangFunction.h; path = include/lldb/Expression/ClangFunction.h; sourceTree = "<group>"; };
@@ -1075,6 +1077,7 @@
26680231115FD1A0008E1FE4 /* Foundation.framework in Frameworks */,
26680232115FD1A4008E1FE4 /* libpython2.6.dylib in Frameworks */,
26680233115FD1A7008E1FE4 /* libobjc.dylib in Frameworks */,
+ 4C74CB6312288704006A8171 /* Carbon.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -1105,6 +1108,7 @@
08FB7795FE84155DC02AAC07 /* Source */,
26F5C22410F3D950009D5894 /* Tools */,
1AB674ADFE9D54B511CA2CBB /* Products */,
+ 4C74CB6212288704006A8171 /* Carbon.framework */,
);
name = lldb;
sourceTree = "<group>";
Modified: lldb/trunk/source/API/SBDebugger.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/API/SBDebugger.cpp?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/API/SBDebugger.cpp (original)
+++ lldb/trunk/source/API/SBDebugger.cpp Mon Aug 30 14:44:40 2010
@@ -563,3 +563,23 @@
sb_debugger.reset (debugger_sp);
return sb_debugger;
}
+
+bool
+SBDebugger::SetUseExternalEditor (bool value)
+{
+ if (m_opaque_sp)
+ return m_opaque_sp->SetUseExternalEditor (value);
+ else
+ return false;
+}
+
+bool
+SBDebugger::UseExternalEditor ()
+{
+ if (m_opaque_sp)
+ return m_opaque_sp->UseExternalEditor ();
+ else
+ return false;
+}
+
+
Modified: lldb/trunk/source/Commands/CommandObjectFrame.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Commands/CommandObjectFrame.cpp?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/Commands/CommandObjectFrame.cpp (original)
+++ lldb/trunk/source/Commands/CommandObjectFrame.cpp Mon Aug 30 14:44:40 2010
@@ -114,12 +114,19 @@
if (exe_ctx.frame)
{
+ bool already_shown = false;
+ SymbolContext frame_sc(exe_ctx.frame->GetSymbolContext(eSymbolContextLineEntry));
+ if (interpreter.GetDebugger().UseExternalEditor() && frame_sc.line_entry.file && frame_sc.line_entry.line != 0)
+ {
+ already_shown = Host::OpenFileInExternalEditor (frame_sc.line_entry.file, frame_sc.line_entry.line);
+ }
+
if (DisplayFrameForExecutionContext (exe_ctx.thread,
exe_ctx.frame,
interpreter,
result.GetOutputStream(),
true,
- true,
+ !already_shown,
3,
3))
{
Modified: lldb/trunk/source/Commands/CommandObjectThread.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Commands/CommandObjectThread.cpp?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/Commands/CommandObjectThread.cpp (original)
+++ lldb/trunk/source/Commands/CommandObjectThread.cpp Mon Aug 30 14:44:40 2010
@@ -60,13 +60,21 @@
// Show one frame with only the first showing source
if (show_source)
{
+ bool already_shown = false;
+ StackFrameSP frame_sp = thread->GetStackFrameAtIndex(0);
+ SymbolContext frame_sc(frame_sp->GetSymbolContext (eSymbolContextLineEntry));
+ if (interpreter.GetDebugger().UseExternalEditor() && frame_sc.line_entry.file && frame_sc.line_entry.line != 0)
+ {
+ already_shown = Host::OpenFileInExternalEditor (frame_sc.line_entry.file, frame_sc.line_entry.line);
+ }
+
DisplayFramesForExecutionContext (thread,
interpreter,
strm,
0, // Start at first frame
1, // Number of frames to show
false,// Don't show the frame info since we already displayed most of it above...
- 1, // Show source for the first frame
+ !already_shown, // Show source for the first frame
3, // lines of source context before
3); // lines of source context after
}
Modified: lldb/trunk/source/Core/Debugger.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/Debugger.cpp?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/Core/Debugger.cpp (original)
+++ lldb/trunk/source/Core/Debugger.cpp Mon Aug 30 14:44:40 2010
@@ -128,7 +128,8 @@
m_command_interpreter_ap (new CommandInterpreter (*this, eScriptLanguageDefault, false)),
m_exe_ctx (),
m_input_readers (),
- m_input_reader_data ()
+ m_input_reader_data (),
+ m_use_external_editor(false)
{
m_command_interpreter_ap->Initialize ();
}
Modified: lldb/trunk/source/Host/macosx/Host.mm
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Host/macosx/Host.mm?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/Host/macosx/Host.mm (original)
+++ lldb/trunk/source/Host/macosx/Host.mm Mon Aug 30 14:44:40 2010
@@ -24,6 +24,8 @@
#include <objc/objc-auto.h>
#include <Foundation/Foundation.h>
+#include <CoreServices/CoreServices.h>
+#include <Carbon/Carbon.h>
#include "cfcpp/CFCBundle.h"
#include "cfcpp/CFCReleaser.h"
@@ -779,3 +781,116 @@
}
return returnSpec;
}
+
+bool
+Host::OpenFileInExternalEditor (FileSpec &file_spec, uint32_t line_no)
+{
+ // We attach this to an 'odoc' event to specify a particular selection
+ typedef struct {
+ int16_t reserved0; // must be zero
+ int16_t fLineNumber;
+ int32_t fSelStart;
+ int32_t fSelEnd;
+ uint32_t reserved1; // must be zero
+ uint32_t reserved2; // must be zero
+ } BabelAESelInfo;
+
+ char file_path[PATH_MAX];
+ file_spec.GetPath(file_path, PATH_MAX);
+ CFCString file_cfstr (file_path, kCFStringEncodingUTF8);
+ CFCReleaser<CFURLRef> file_URL(::CFURLCreateWithFileSystemPath(NULL, file_cfstr.get(), kCFURLPOSIXPathStyle, false));
+
+ OSStatus error;
+ BabelAESelInfo file_and_line_info;
+
+ AEKeyDesc file_and_line_desc;
+
+ bzero(&file_and_line_info, sizeof (file_and_line_info));
+ file_and_line_info.fSelStart = 1;
+ file_and_line_info.fSelEnd = 1;
+ file_and_line_info.fLineNumber = line_no - 1;
+
+ error = AECreateDesc(typeChar, &file_and_line_info, sizeof (file_and_line_info), &(file_and_line_desc.descContent));
+ if (error != noErr)
+ {
+ return false;
+ }
+
+ file_and_line_desc.descKey = keyAEPosition;
+
+ LSApplicationParameters app_params;
+ bzero (&app_params, sizeof (app_params));
+ app_params.flags = kLSLaunchDefaults | kLSLaunchDontSwitch;
+
+ ProcessSerialNumber psn;
+ CFCReleaser<CFArrayRef> file_array(CFArrayCreate (NULL, (const void **) file_URL.ptr_address(false), 1, NULL));
+ error = LSOpenURLsWithRole(file_array.get(), kLSRolesAll, &file_and_line_desc, &app_params, &psn, 1);
+
+ AEDisposeDesc (&(file_and_line_desc.descContent));
+
+ if (error != noErr)
+ {
+ return false;
+ }
+
+ ProcessInfoRec which_process;
+ bzero(&which_process, sizeof(which_process));
+ unsigned char ap_name[PATH_MAX];
+ which_process.processName = ap_name;
+ error = GetProcessInformation (&psn, &which_process);
+
+ bool using_xcode = strncmp((char *) ap_name+1, "Xcode", 5) == 0;
+
+ // Xcode doesn't obey the line number in the Open Apple Event. So I have to send
+ // it an AppleScript to focus on the right line.
+
+ if (using_xcode)
+ {
+ static ComponentInstance osa_component = NULL;
+ static const char *as_template = "tell application \"Xcode\"\n"
+ "set doc to the first document whose path is \"%s\"\n"
+ "set the selection to paragraph %d of doc\n"
+ "--- set the selected paragraph range to {%d, %d} of doc\n"
+ "end tell\n";
+ const int chars_for_int = 32;
+ static int as_template_len = strlen (as_template);
+
+
+ char *as_str;
+ AEDesc as_desc;
+
+ if (osa_component == NULL)
+ {
+ osa_component = OpenDefaultComponent (kOSAComponentType,
+ kAppleScriptSubtype);
+ }
+
+ if (osa_component == NULL)
+ {
+ return false;
+ }
+
+ uint32_t as_str_size = as_template_len + strlen (file_path) + 3 * chars_for_int + 1;
+ as_str = (char *) malloc (as_str_size);
+ snprintf (as_str, as_str_size - 1, as_template, file_path, line_no, line_no, line_no);
+ error = AECreateDesc (typeChar, as_str, strlen (as_str), &as_desc);
+
+ free (as_str);
+
+ if (error != noErr)
+ return false;
+
+ OSAID ret_OSAID;
+ error = OSACompileExecute (osa_component, &as_desc, kOSANullScript,
+ kOSAModeNeverInteract, &ret_OSAID);
+
+ OSADispose (osa_component, ret_OSAID);
+
+ AEDisposeDesc (&as_desc);
+
+ if (error != noErr)
+ return false;
+ }
+
+ return true;
+}
Modified: lldb/trunk/source/Host/macosx/cfcpp/CFCReleaser.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Host/macosx/cfcpp/CFCReleaser.h?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/source/Host/macosx/cfcpp/CFCReleaser.h (original)
+++ lldb/trunk/source/Host/macosx/cfcpp/CFCReleaser.h Mon Aug 30 14:44:40 2010
@@ -96,11 +96,14 @@
// assertion fires, check the offending code, or call
// reset() prior to using the "ptr_address()" member to make
// sure any owned objects has CFRelease called on it.
+ // I had to add the "enforce_null" bool here because some
+ // API's require the pointer address even though they don't change it.
//----------------------------------------------------------
T*
- ptr_address()
+ ptr_address(bool enforce_null = true)
{
- assert (_ptr == NULL);
+ if (enforce_null)
+ assert (_ptr == NULL);
return &_ptr;
}
Modified: lldb/trunk/tools/driver/Driver.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/tools/driver/Driver.cpp?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/tools/driver/Driver.cpp (original)
+++ lldb/trunk/tools/driver/Driver.cpp Mon Aug 30 14:44:40 2010
@@ -70,6 +70,9 @@
{ LLDB_OPT_SET_3, true, "file", 'f', required_argument, NULL, NULL, "<filename>",
"Tells the debugger to use the file <filename> as the program to be debugged." },
+ { LLDB_OPT_SET_ALL, false, "editor", 'e', no_argument, NULL, NULL, "<external-editor>",
+ "Tells the debugger to open source files using the host's \"external editor\" mechanism." },
+
// { LLDB_OPT_SET_4, true, "crash-log", 'c', required_argument, NULL, NULL, "<file>",
// "Load executable images from a crash log for symbolication." },
@@ -324,7 +327,8 @@
m_debug_mode (false),
m_print_version (false),
m_print_help (false),
- m_seen_options()
+ m_seen_options(),
+ m_use_external_editor(false)
{
}
@@ -341,6 +345,7 @@
m_debug_mode = false;
m_print_help = false;
m_print_version = false;
+ m_use_external_editor = false;
}
void
@@ -508,7 +513,10 @@
case 'c':
m_option_data.m_crash_log = optarg;
break;
-
+ case 'e':
+ m_option_data.m_use_external_editor = true;
+ break;
+
case 'f':
{
SBFileSpec file(optarg);
@@ -1042,6 +1050,8 @@
m_debugger.SetErrorFileHandle (stderr, false);
m_debugger.SetOutputFileHandle (stdout, false);
m_debugger.SetInputFileHandle (stdin, true);
+
+ m_debugger.SetUseExternalEditor(m_option_data.m_use_external_editor);
// You have to drain anything that comes to the master side of the PTY. master_out_comm is
// for that purpose. The reason you need to do this is a curious reason... editline will echo
Modified: lldb/trunk/tools/driver/Driver.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/tools/driver/Driver.h?rev=112502&r1=112501&r2=112502&view=diff
==============================================================================
--- lldb/trunk/tools/driver/Driver.h (original)
+++ lldb/trunk/tools/driver/Driver.h Mon Aug 30 14:44:40 2010
@@ -103,6 +103,7 @@
bool m_debug_mode;
bool m_print_version;
bool m_print_help;
+ bool m_use_external_editor; // FIXME: When we have set/show variables we can remove this from here.
typedef std::set<char> OptionSet;
OptionSet m_seen_options;
};
More information about the lldb-commits
mailing list