Click here to Skip to main content
15,861,367 members
Articles / Desktop Programming / MFC
Article

Include File Hierarchy Viewer

Rate me:
Please Sign up or sign in to vote.
4.84/5 (108 votes)
29 Jul 2003CPOL8 min read 377.6K   4.5K   151   112
A tool to view the include file hierarchy of your source code.

Image 1

Introduction

I've seen many people ask about utilities to view the tree of #included files in their source code. I think I've seen one of these before, either here at CodeProject or maybe at CodeGuru, but I can't seem to find it. Since I really enjoy text processing, I took it upon myself to write my own. What I've come up with is a fast, multi-threaded #include tree generator.

Features

Searching multiple directories

Image 2

As you can see in the screenshot above, there are a few fields to fill in before you can generate the tree. I think it's pretty self-explanatory, but I will explain the fields here just in case some think it's not.

  • Search in

    Type in a list of directories you want to search. You can enter multiple directories at one time by separating them with semi-colons. Or, optionally, use the browse button ("...") to pick a directory from the standard Shell Browser. This combo box will store the recently searched directories, so you can also select a directory from the drop-down list if you like.

  • File mask

    Type in a list of file masks you want to search for. You can enter multiple file masks at one time by separating them with semi-colons. This combo box will store the recently used file masks, so you can also select a mask from the drop-down list if you like.

  • Includes

    Type in a list of directories where external header files reside. You can enter multiple include directories at one time by separating them with semicolons. Also, it's possible to enter an environment variable in this field, which the software will expand at runtime. To do this, simply prefix the variable with a '%' character (i.e. %INCLUDE).

  • Recurse subdirectories

    Set this check box if you want the program to recurse through subdirectories of the directories you entered.

Searching files loaded from VC6/VC7 workspaces or projects

Image 3

When searching a workspace or project, you don't have to input as much information as when searching a directory, but you still have to load a project or workspace, specify a file mask, and select a configuration. The software will read settings related to preprocessing, such as additional include directories, and preprocessor definitions. Also, the VC6 project reader will read the registry for the VC6 include directories, and the VC7 project reader will read the registry for the VC7 include directories, which means if you have VC6 or VC7 configured already, you don't have to configure this program as well.

Note: The workspace and project loading isn't perfect yet, but I have tested it in a variety of scenarios, and it works well for me. The biggest problem is accurately interpreting the project settings, which there are still issues with.

  • Workspace

    Type in the path to the workspace or project you want to load. Or, optionally, use the browse button ("...") to pick a workspace from the standard File Open dialog box. This combo box will store the recently searched workspaces, so you can also select a recent entry from the drop-down list if you like.

  • Load workspace

    Click this button to load the selected workspace or project, so you can select a configuration. If you don't load the workspace before you click Start, the Include Finder will use the first configuration found in each project.

  • File mask

    Type in a list of file masks you want to search for. You can enter multiple file masks at one time by separating them with semi-colons. This combo box will store the recently used file masks, so you can also select a mask from the drop-down list if you like.

  • Configuration

    Select a project configuration. The configuration you select will determine which preprocessor include directories are used, and also which preprocessor definitions are used.

Other options

  • Parse preprocessor macros

    There is now the capability to parse the preprocessor macros, and this flag is used to turn that feature on and off. Since the parsing may not be 100% accurate (with respect to the compiler), I leave this as a choice to you.

Once you've entered some valid data, click Start and the program will start the search. The searching is done in a separate thread, so you will see the button's text turn to "Stop" once you click Start. To stop the search, simply click Stop and the thread will quit, turning the Stop button back into the Start button.

Viewing and searching the output

The output is shown in a standard Win32 tree control, using MFC's CTreeCtrl. As each source file is completed, the program populates the tree with the source file and all the files #included by it. You will notice that there are a few icons used in the tree that denote properties of the item. Here's an explanation of them:

Image 4 This icon is used to denote a regular file.

Image 5 This icon is used to denote that the instance of the file is not the first time it was included by the current source file (either directly or indirectly).

Image 6 This icon is used to denote that the file could not be found along the specified include paths.

Image 7 This icon is used to denote that the file has been recursively included.

To search the tree for a particular file, select the Find... menu item, or click F3 to search for the next occurrence of a string.

Saving and restoring the data

If you click on the Save toolbar icon, or select the Save Results... menu item, you will be prompted to enter a file name to save to. The results are saved in XML format like the sample shown below.

Sample XML output (viewed with IE)

Image 8

Once you have saved an XML file, you can click the Open toolbar icon, or select the Open... menu item to select a file to reload. The XML tree will be reloaded into the Include Finder.

About the code

Note: At my work we have a coding standard which is a form of Hungarian notation. I've also used this standard in this project. It's what I've been using for the past few years, and I like it, but that's not the point of the article or the code, so please don't flame me for it.

I've tried to keep the core code of the program as separated from the interface as possible, so that it will be easy for someone to reuse the interesting portions. Since the code has grown substantially in size since the first version, I decided to omit descriptions of the classes. If you are interested in using the code, you can find a description of what's in each file in the headers at the top of them.

Acknowledgements

I'd like to thank the following people:

To Do

  • It would be neat to make a static library out of the core, thereby making it possible to use the core in a Developer Studio add-in, as well as the external tool that it currently is.
  • The preprocessor macro handling could be better.
  • Interpreting the project settings could also be better.
  • I've tried to write the code cleanly, but I'm sure it could still use some clean-up.
  • Documentation for those who would like to use the code?

History

  1. January 7th, 2003 - Initial release.
  2. January 27th, 2003
    • Added the capability to read .dsp/.dsw/.vcproj/.sln files.
    • Added an option to parse preprocessor macros.
    • Added the capability to search multiple directories at once.
    • Added an option to show only files which couldn't be found.
    • Added support for entering environment variables in the Includes field.
    • Added the capability to load a saved XML file from disk.
    • Added the capability to select a custom program for viewing source files.
    • Added the capability to double-click a leaf node in the tree to open the file.
    • Added the capability to search the tree for specified strings.
    • Added CMMFStream class, which improved parsing performance greatly.
  3. February 24th, 2003 (bug fixes) - Thanks to Medved, Oliver Wahl, and Andreas Saurwin for alerting me to, and/or showing patches for these bugs.
    • CMMFStream would incorrectly handle files with zero length.
    • CParser::FindFullPath had a bug which made it find the incorrect file in certain cases.
    • CLexer incorrectly handled certain characters that could be found in binary files.
    • CLexer incorrectly handled files which had a strange combination of \r\n, which caused a crash.
  4. July 30th, 2003 (bug fixes and some changes to run on NT 4 without IE shell update)
    • Fixed a bug where FindFullPath would incorrectly handle two files with the same name but in different paths. - Thanks to Oliver Wahl.
    • Fixed a bug where bracketed include directories from project settings weren't read. - Thanks to EvanKeats.
    • Removed the use of SHGetSpecialFolderPath and replaced it with SHGetSpecialFolderLocation/SHGetPathFromIDList. - Thanks to brownfox and Hemal Shah.

Disclaimer and copyright

Although great care has gone into developing this software, it is provided without any guarantee of reliability, accuracy of information, or correctness of operation. I am not responsible for any damages that may occur as a result of using this software. Use this software entirely at your own risk. Copyright 2003, Chris Richardson.

Final notes

Any feedback or bug reports will be greatly appreciated. If you do or do not like the article, the code, or the program I've provided, please tell me why.

Thanks for taking the time to read my article. I hope you enjoyed it, and I hope you find the Include Finder useful.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior)
United States United States
I like to program, I like to sail.

Comments and Discussions

 
Generalstdafx.h Pin
fioresoft15-Dec-04 9:54
fioresoft15-Dec-04 9:54 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.