Introducing LLBrowse: A graphical browser for LLVM modules

I’ve written a little GUI application that displays an LLVM module as an expandable tree, which can be useful for examining the module’s contents. Some features:

  • Based on wxWidgets, so it’s completely cross-platform.
  • CMake build script can locate both LLVM and wxWidgets installations automatically.
  • Loads either .ll or .bc files.
  • Supports browsing of LLVM types, variables, functions, aliases, and metadata. I’m working on supporting a more structured view of DWARF DIEs, but that is not complete.
  • Tree nodes are created lazily as needed.
  • The tree node system is highly extensible, each different LLVM object type is represented by a tree node class, adding new node classes is extremely easy.
  • The code is very straightforward and easy to read.
  • All image resources are embedded in the final executable, so the compiles program is just a single binary file, very easily installed.

This is still a work in progress, but I think it’s ready for people to start hacking on.

If there is interest, I can check the code into the llvm.org svn somewhere - I just need to know where to put it. Otherwise, I’m happy to email a zip archive to folks who are interested. I’m willing to release the code under whatever license is most convenient.

Here’s a screenshot of what it looks like:

And here’s what the node class for displaying variables looks like, as an example:

Nice! I’m interested… would also be nice to cross this with llvm diff, eh? :slight_smile:

Cheers,
Renato

Hi Talin,

This looks interesting..! Can you email me your tool?
Cheers,
Raghu.

Looks cool Talin.

Personally it would be nice if it was checked into llvm.org, but is wxWidgets LGPL like license
an issue for llvm’s repository?

Anyway I would be interested in a copy otherwise under a BSD like license.

Thanks in advance

Garrison

A lot of people have requested a source archive, so I’m making available here:

http://code.google.com/p/tart/downloads/detail?name=llbrowse.tgz

Have fun!

Looks cool Talin.

Personally it would be nice if it was checked into llvm.org, but is wxWidgets LGPL like license
an issue for llvm’s repository?

There should be no problem with the license. wxWidgets is indeed distributed under a modified version of the LGPL (with a special exception to allow people to distribute binaries of their app without requiring the source). The LGPL allows derived works to be distributed under a more permissive license (such as BSD-like licenses) as long as all of the license terms are less restrictive than the LGPL. Also, since we’re talking LGPL, not GPL, the “derived work” does not include applications based on the library, it only includes modifications to the library itself.

Since LLBrowse does not include any wxWidgets source code, the source archive can be distributed under a BSD license. Binaries of LLBrowse can be distributed freely, without source, due to the special exception in the wxWidgets license.

Thus, even though the University of Illinois license is not GPL-compatible (because of the copyright and endorsement clauses), this should not matter.

Here’s a page which lists which open source licenses are GPL-compatible:

http://www.gnu.org/licenses/license-list.html

Having GPL and other licenses in llvm’s repositories is fine, dragonegg, llvm-gcc and the llvm-testsuite each have GPL code in them. Just keep repositories like LLVM, Clang, LLDB, etc pure UIUC license.

Before checking this in to a new module, please whip up some web pages that document it. Thanks Talin!

-Chris

Do you have any suggestions as to where in the hierarchy this should go?

What kind of docs are you looking for, user docs or developer docs? The program only has one command (“load module”), the rest is just displaying read-only data in tree form.

BTW, I’ve added more support for displaying DWARF DIEs - here’s a screenshot:

Having GPL and other licenses in llvm’s repositories is fine, dragonegg, llvm-gcc and the llvm-testsuite each have GPL code in them. Just keep repositories like LLVM, Clang, LLDB, etc pure UIUC license.

Before checking this in to a new module, please whip up some web pages that document it. Thanks Talin!

Do you have any suggestions as to where in the hierarchy this should go?

I’d suggest a new top-level svn module.

What kind of docs are you looking for, user docs or developer docs? The program only has one command (“load module”), the rest is just displaying read-only data in tree form.

User docs: what it is, what it depends on, how to build it, where to email questions/discussion about it etc.

-Chris

I am interested, too.

Thank you

Chuck

LLBrowse has now been checked in to the llvm.org subversion repository:

http://llvm.org/svn/llvm-project/llbrowse/trunk/

There are instructions for building and running in the doc/ directory.

First task if someone wants to take it on - update all of the source files to have the UIUC license info at the top, and add a LICENSE.txt file :slight_smile:

Other TODO items, many of which are fairly trivial:

  • Update the status bar when a module is loaded (currently says “no module loaded”)
  • Add support for command-line parameters - you should be able to specify a module file on the command line and have it load it on startup.
  • Change the subversion property for the HTML files in the doc directory to have the proper mime type.
  • Add new icons for different DIE types (currently all DWARF nodes use the same icon.) Note that you need to re-run CMake after adding a new icon so it can create the dependency rules for converting the icon data to a C header file. Icons are always 20x20 and can easily be created in GIMP.
  • Add a “search” function that allows searching for a symbol by name. (This one’s not trivial due to the lazy construction of tree nodes. Basically what it needs to do is walk the tree (avoiding cycles), and call treeCtrl->SelectItem and treeCtrl->EnsureVisible on the node whose caption contains the search string. I have some notes on how to do this.)
  • Make sure the app isn’t leaking memory when loading a new module over an old one.
    In the mean time, I’ll be working on getting DWARF derived type DIEs to display as much information as possible… :slight_smile:

One more screen shot: The version I just checked now allows you to see all of the children of a given compile unit:

I’ve already found at least one bug in my compiler’s frontend using this tool :slight_smile:

Oh, and before I forget, I need three small changes to DebugInfo.h:

  • DebugInfoFinder’s ‘module’ parameter should be const.
  • isArtificial should return a bool, not an unsigned.
  • DIDerivedType should have an method that allows access to the ‘name’ attribute of the DIE.

I think this deserves a blog post…

–renato

Talin,

I think this deserves a blog post…

I’d like to wait until I get some feedback - I don’t know yet if anyone is having trouble building or running the thing…

Hi Talin,

What version of wxwidgets does llbrowse require, tried 2.8.10, and 2.9.1
and none worked:
/home/edwin/llbrowse/include/llbrowse/Resources.h:46: error: ISO C++
forbids declaration of ‘wxImageList’ with no type
/home/edwin/llbrowse/include/llbrowse/Resources.h:46: error: expected
‘;’ before ‘*’ token
/home/edwin/llbrowse/include/llbrowse/Resources.h:47: error: ISO C++
forbids declaration of ‘wxImageList’ with no type
/home/edwin/llbrowse/include/llbrowse/Resources.h:47: error: expected
‘;’ before ‘*’ token

Some other minor issues:
1. If llvm-config is not in the path, 'cmake .' succeeds, and 'make fails'.
cmake-gui shows that the problem is LLVM_CONFIG_EXECUTABLE-NOTFOUND.

2. It doesn't seem to build with LLVM 2.8, maybe you should check the
LLVM version in CMake:
/home/edwin/llbrowse/lib/BrowserApp.cpp:9:34: error: llvm/Support
/Signals.h: No such file or directory

Best regards,
--Edwin

    I think this deserves a blog post...

I'd like to wait until I get some feedback - I don't know yet if anyone
is having trouble building or running the thing...

Hi Talin,

What version of wxwidgets does llbrowse require, tried 2.8.10, and 2.9.1
and none worked:
/home/edwin/llbrowse/include/llbrowse/Resources.h:46: error: ISO C++
forbids declaration of ‘wxImageList’ with no type
/home/edwin/llbrowse/include/llbrowse/Resources.h:46: error: expected
‘;’ before ‘*’ token
/home/edwin/llbrowse/include/llbrowse/Resources.h:47: error: ISO C++
forbids declaration of ‘wxImageList’ with no type
/home/edwin/llbrowse/include/llbrowse/Resources.h:47: error: expected
‘;’ before ‘*’ token

Correction, 2.8.10 gets past these errors, and shows these errors instead:
CMakeFiles/llbrowse.dir/lib/BrowserApp.cpp.o:(.rodata._ZTV10BrowserApp[vtable
for BrowserApp]+0x120): undefined reference to
`wxApp::OnAssertFailure(wchar_t const*, int, wchar_t const*, wchar_t
const*, wchar_t const*)'
CMakeFiles/llbrowse.dir/lib/BrowserApp.cpp.o:(.rodata._ZTV10BrowserApp[vtable
for BrowserApp]+0x128): undefined reference to
`wxAppConsole::OnAssert(wchar_t const*, int, wchar_t const*, wchar_t
const*)'
CMakeFiles/llbrowse.dir/lib/TreeView.cpp.o: In function
`wxStringBase::wxStringBase(wxStringBase const&)':
TreeView.cpp:(.text._ZN12wxStringBaseC2ERKS_[wxStringBase::wxStringBase(wxStringBase
const&)]+0x43): undefined reference to `wxOnAssert(wchar_t const*, int,
char const*, wchar_t const*, wchar_t const*)'
CMakeFiles/llbrowse.dir/lib/TreeView.cpp.o: In function
`wxArrayString::Item(unsigned long) const':
TreeView.cpp:(.text._ZNK13wxArrayString4ItemEm[wxArrayString::Item(unsigned
long) const]+0x39): undefined reference to `wxOnAssert(wchar_t const*,
int, char const*, wchar_t const*, wchar_t const*)'

Thanks for letting me know. I’ll look into it right now.

2011/2/14 Török Edwin <edwintorok@gmail.com>

Hi Talin,

This is the build error I get on my ubuntu 64 bit system…

john@ubuntu:~/src/build-llbrowse$ make
[ 5%] Building CXX object CMakeFiles/llbrowse.dir/lib/Formatting.cpp.o
/home/john/src/llbrowse/lib/Formatting.cpp: In function ‘void printTypeExpansion(wxTextOutputStream&, const llvm::Module*, const llvm::Type*, uint32_t)’:
/home/john/src/llbrowse/lib/Formatting.cpp:33: error: ‘X86_MMXTyID’ is not a member of ‘llvm::Type’
make[2]: *** [CMakeFiles/llbrowse.dir/lib/Formatting.cpp.o] Error 1
make[1]: *** [CMakeFiles/llbrowse.dir/all] Error 2
make: *** [all] Error 2
john@ubuntu:~/src/build-llbrowse$ llvm-config --version
2.9svn

OK I figured out what the problem was - I assume you are trying to compile under Snow Leopard? There is a problem with linking against wxWidgets because the prebuilt binaries for wxWidgets are compiled in 32-bit mode, and the default compilation mode in Snow Leopard is 64 bits. See this article for an explanation:

http://wiki.wxwidgets.org/Development:_wxMac#Building_under_10.6_Snow_Leopard

Unfortunately, I am not certain what the right solution is yet. Maybe I’ll have to add a check for Snow Leopard and add a flag to compile in 32-bit mode. Apparently this problem is solved in the upcoming 2.9 release of wxWidgets, but that is still an experimental version.

In the mean time, I discovered a bunch of other build problems on OS X, which I have gone ahead and checked in fixes for (Things like vs. <auto_ptr>. I’ve also updated the docs to explain how to tell CMake where to find llvm-config.

2011/2/14 Török Edwin <edwintorok@gmail.com>