Skip to end of metadata
Go to start of metadata


Debugging on Windows is straightforward. Open the browser and Visual Studio. To debug your plugin simply go to "Debug->Attach to Process", and from the process list select the executable you want to debug (e.g. "firefox.exe"). In Firefox4 the plugins are running in a separated process called "plugin-container.exe".

Visual Studio debugger will now halt at the breakpoints you select.

Some browsers may work an multiple processes (e. g. Chrome) that do not always have a title. To identify the process that runs your plugin either

  • set a breakpoint somewhere in the code and check if it stays enabled when you attach the debugger to a browser process. If the code is not loaded in the attached process, Visual Studio disables the breakpoints and you have to select another process. Or
  • log GetCurrentProcessId() from your plugin to find out which process your plugin is in

For debugging weird crashes, it may be helpful to configure symbol servers:

Internet Explorer 8 and later

Some people have a hard time getting Visual Studio to attach to the correct IE8 process. That's because IE opens new processes for different security zones, and notably for files on the local disk. If you notice, you probably see a yellow bar confirming that you want to load the ActiveX control?

When you see that bar, attach to all iexplore.exe processes, and then activate the control. Your breakpoints should be hit.

Configuring Internet Explorer 8 and later to use a single process

It is actually possible to tell IE8 to only use a single process, thus making it much easier to debug FireBreath plugins in IE8.  You do this by creating the following registry key:

Configuring Firefox 6 and newer to use a single process

type "about:config" in the url bar.

type "plugins" in filter and select and set dom.ipc.plugins.enabled to false

Disable Firefox Crash Reporter in windows

This can be annoying and interfere with debugging. It can be disabled by setting an environment variable.

Setting the environment variable in Windows



Debugging on Chrome/windows is not too difficult, the trick is to use the --plugin-startup-dialog command line flag when starting Chrome. When you use that flag a dialog box will pop up before loading any plugin with the pid of the process the plugin will load in. Attach to the process with that pid and you should be able to debug.

Note that Chrome on windows is sometimes in a mode where it doesn't actually quit (this is to make it start up faster). If the flag doesn't seem to be helping, check your task manager to make sure all instances of chrome.exe are closed!


With Safari 5.1 (maybe other version) on windows, you must attach your debugger to the process named: WebKit2ebProcess.exe


In Xcode 3 you should turn off lazy loading of symbols in the preferences. To do this:

  1. Open Xcode
  2. Go to Xcode : Preferences
  3. Select Debugging in the scrolling list of icons on the top
  4. Uncheck "Load symbols lazily" in the top right corner of the dialog

If you don't do this, chances are you'll never get any breakpoints to hit.

Also you may need to set your target architecture to i386 (Project -> Set Active Architecture) for breakpoints to work.


In Xcode 4 this setting does not exist. Just make sure the "Breakpoints" button in the toolbar is depressed.

Finally, attach to the plugin using the menu entry Product : Attach to Process (Xcode 4) or Run : Attach to Process (Xcode3). See below for details.

Firefox 3

Firefox 3 is probably the easiest to debug in on Mac.

  1. Open <build dir>/FireBreath.xcodeproj in Xcode
  2. Add the Firefox executable by selecting Project : Add/New Custom Executable
  3. Name it Firefox and set the application to /Applications/
  4. Start Firefox (note that on many systems running Firefox from Xcode does not work, so start it normally)
  5. In Xcode attach to the process firefox-bin.
  6. In the debug console (Run : Debugger if you can't find it) click "continue"

After following these steps, set whatever breakpoints you want to and then go to a page that embeds your plugin.

Old Firefox versions can be downloaded here:

Disabling the Mozilla Crash handler

If you want to get a Mac crash dump when your plugin crashes firefox, you may want to disable the Mozilla Crash handler. To do this, edit /Applications/ and change Enabled=1 to Enabled=0 under the Crash Reporter section.

Firefox 4+

Firefox is more difficult to debug because it runs plugins in a separate process, named plugin-container. To debug early in your plugin's execution, you can add a sleep or similar in the constructor of your PluginCore class, then attach Xcode.

Alternately, if your testing doesn't require out-of-process mode, you can disable it:

  1. In your Firefox 4 location bar, type "about:config" and press enter. Agree to whatever it asks so it lets you in.
  2. in "Filter" add "ipc"
  3. If you want 32 bit plugins to not be out-of-process, set "dom.ipc.plugins.enabled.i386" to false (false by default, as of this writing)
  4. If you want 64 bit plugins to not be out of process, set "dom.ipc.plugins.enabled.x86_64 to false (true by default, as of this writing)

Setting dom.ipc.plugins.enabled can also be set to false if you do not have any of the other applicable flags. This disables the plugin-container and allows debugging the plugins for Firefox.

Firefox 4/5 also has a feature where by it will terminate plugins that do not respond after some period of time. This can become a nuisance if one is stepping through plugin code with a debugger. To prolong this hang timeout, go to the address about:config in firefox, and lengthen the setting dom.ipc.plugins.timeoutSecs


The best way to debug a plugin in the Mac version of Chrome is to start Chrome with the --plugin-startup-dialog flag. That will cause the plugin process to pause and wait for a debugger to attach as soon as it is launched (no sleep() call needed), and print the PID of the plugin process to the console. So the flow would be:

  1. Launch Chrome with --plugin-startup-dialog (if that doesn't work, try: --wait-for-debugger-children=plugin --wait-for-debugger)
    1. You can do this by calling "open /Applications/Google\ --args --plugin-startup-dialog"
  2. Go to test page that loads your plugin
  3. Look for the log message in your terminal with the PID of the plugin process
    1. In some cases the log message never appears; if this happens you can search for it with "ps -aux | grep -i MyPluginBundleName"
  4. Attach to that process from Xcode (or command-line gdb). For instance, with gdb: $ attach PID
    1. Note that the actual process will probably be called something along the lines of "Google Chrome Helper EH"

See Also: Debugging Plugins on Mac with Google Chrome


Your plugin process is called PluginProcess in Xcode. If there are several, you have to find the correct one e.g. in Activity Monitor. If you don't need to debug the plugin start-up, you can just attach and that's it. However, if you do need to debug start-up:

  1. Start Safari normally (not from Xcode)
  2. Add sleep(10000); or so in a point early in the initialization of your plugin (NP_Initialize, NPP_New, or the constructor of your PluginCore would all be good candidates)
  3. Load the plugin page in the browser, and then immediately (don't wait for the page to display) attach to the process PluginProcess in Xcode.
  4. Your breakpoint should be hit if you do it fast enough. Increase the sleep if you need more time.

NOTE: In 5.1 and later Safari seems to have a short timeout for plugin response; if your plugin doesn't respond during that time (say because a debugger has blocked the process) it just kills it.  This makes it nearly impossible to debug in these versions, so watch out for it.


Its possible to attach gdb to any running process with gdb --pid=PID. This command will require root privileges. The trick is to find out which process is running your plugin; Firefox and Chrome both have flags that indicate they should run as a single process, although Chrome may ignore this flag. Running ps aux | grep "chrome" | grep "-plugin-launcher" may be helpful in determining which process is running the plugin.



Google-chrome (chromium should as well) comes with several handy command line flags that make debugging easy on linux.

  1. Launch google-chrome with --plugin-launcher='xterm -e gdb --args'
  2. Go to test page that loads your plugin.
  3. An xterm window will popup with gdb attached to your plugin.

heh.  I should get another clock to put on the wall and I'll have two of them.  "GradeCam Standard" and "Local Time"


  1. Test like you are in the zone, internet zone.

    I was having difficulty using the standard test procedure of dragging a test page to IE8. Using the IECTT tool ( It was determined to be "Local Machine Zone Lockdown" which detects the test page was from my hard drive and locks me down. Looking on line I found this article :;

    It shows a simple workaround that lets the test page run in the internet zone again. Just add the following line to the top of the test page.<!-- saved from url=(0013)about:internet -->

    This eliminated the yellow info bar asking me if it is ok to run activeX content every single time.

  2. I've been debugging with Chrome and Visual Studio 2010 Express and noticed that you have to attach to all chrome processes otherwise Visual Studio Express will not load debug symbols of the DLL and you won't be able to break. Also, in Visual Studio Express 2010, the 'Attach Process' option is not visible by default. You have to check Tools->Settings->Expert Settings in order to make it appear.

    1. This is not actually true; you only need to attach to a single process, but it can be tricky to figure out which process that is.

      1. Okay in that case please delete the comment.

      2. A Tip for those trying to "figure out which process that is": add a function to your plugin which returns the current proces ID (tested in windows, but whould work in linux too), open your browser's console and callit to get the proccess ID, then you'll know to which proccess to attach. 

        DWORD myAwsomePluginAPI::GetCurrentProcessId(){

             return GetCurrentProcessId();


        In Firefox that ID is probably of an instance of "plugin-container.exe" rather than firefox itself.