Wednesday, October 12, 2011

Debug Top-level Toolbar

Recently the platform debug team has been working on a new idea for debug-view-less debugging. We have come up with the idea of a top-level toolbar for the common debug commands; so (in theory) you can debug with needing the debug view front and center of your current perspective. The new toolbar can be activated from within the debug view using the View Menu > Debug Toolbar menu item.

The root Eclipse bug for the enhancement is bug 258767

We have already found lots of room for improvement:
bug 359151, bug 264485, bug 360172, bug 360636 and bug 360637

So for all those interested in the debug-view-less debugging idea, please spend some time and try out the new toolbar, just remember to file bugs!

The toolbar look and feel:

The debug top-level toolbar

Friday, January 14, 2011

Debugging Ant Tasks with Self Hosting

Do you know that Eclipse Ant support has debugging capabilities?

If not, check out this tutorial to get started.

Do you know how to self-host with Eclipse to test plug-ins?

If not here is a quick overview.

To debug ant tasks in a self hosted environment, the tasks must be included in a plug-in project.  If you are working with tasks outside of a plug-in development scenario, you can use remote debugging instead.  Here is a blog post to get you started.

Scenario:


You are developing an ant task to be included in an Eclipse plug-in.  You have the java code to execute the task in a plug-in that defines the task as an ant task extension in the plug-in xml.  The task runs, but the output is a bit off.  Time to start debugging.


1) Start a runtime workbench

Same as you would when debugging any other plug-in.

2) Create a new ant script

It doesn't matter what kind of project you put the script in.

Fill in the script with the proper targets and properties.  When calling your tasks, you will have to put in their full name as defined in the org.eclipse.ant.core.antTasks extension.  When running from a built jar, just the name of the class is satisfactory, but when self hosting we need the full name.

3) Create a new ant launch configuration

Right click on the script and hold down Ctrl while clicking "Debug > Ant Script".  You can also open the launch config dialog from the main menu, "Run > External Tools > External Tools Configurations".

4) Set up configuration options

Give the configuration a name.  On the JRE tab, select "Run in the same JRE as the workspace".  If you don't change this option, debugging won't work correctly.

5) Run the configuration

If there is a problem running the task, check that you have the full name of the task written in.  You can also check that Ant knows about your task by looking on the Ant > Runtime preference page (the Tasks tab will list all known tasks).

6) Start debugging

Set some breakpoints in the host workspace.  Make sure you debug your ant script (not just run it).

Note: Hot Code Replace does not work when debugging this way as the jar containing the tasks must be rebuilt.

Wednesday, October 20, 2010

Weird SVN State

Today when I got to work and tried to sync a pile of my projects, I was met with the following exception (and a cute dialog telling me the same thing, but without as many red X's):

org.eclipse.team.svn.core.connector.SVNConnectorException: svn: '/home/mrennie/workspaces/workspace/CommandLineDebugger' is not a working copy
svn: Cannot read from '/home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format': /home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format (No such file or directory)
at org.polarion.team.svn.connector.svnkit.SVNKitConnector.handleClientException(SVNKitConnector.java:1400)
at org.polarion.team.svn.connector.svnkit.SVNKitConnector.status(SVNKitConnector.java:337)
at org.eclipse.team.svn.core.extension.factory.ThreadNameModifier.status(ThreadNameModifier.java:608)
at org.eclipse.team.svn.core.operation.local.RemoteStatusOperation$2.run(RemoteStatusOperation.java:147)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doSubTask(ProgressMonitorUtility.java:118)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.protectStep(AbstractActionOperation.java:154)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.protectStep(AbstractActionOperation.java:149)
at org.eclipse.team.svn.core.operation.local.RemoteStatusOperation.runImpl(RemoteStatusOperation.java:145)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.run(AbstractActionOperation.java:81)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTask(ProgressMonitorUtility.java:104)
at org.eclipse.team.svn.core.operation.CompositeOperation.runImpl(CompositeOperation.java:95)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.run(AbstractActionOperation.java:81)
at org.eclipse.team.svn.core.operation.LoggedOperation.run(LoggedOperation.java:39)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTask(ProgressMonitorUtility.java:104)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTaskExternal(ProgressMonitorUtility.java:90)
at org.eclipse.team.svn.core.synchronize.AbstractSVNSubscriber.findChanges(AbstractSVNSubscriber.java:314)
at org.eclipse.team.svn.core.synchronize.AbstractSVNSubscriber$UpdateStatusOperation$2.run(AbstractSVNSubscriber.java:349)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doSubTask(ProgressMonitorUtility.java:118)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.protectStep(AbstractActionOperation.java:154)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.protectStep(AbstractActionOperation.java:149)
at org.eclipse.team.svn.core.synchronize.AbstractSVNSubscriber$UpdateStatusOperation.runImpl(AbstractSVNSubscriber.java:347)
at org.eclipse.team.svn.core.operation.AbstractActionOperation.run(AbstractActionOperation.java:81)
at org.eclipse.team.svn.core.operation.LoggedOperation.run(LoggedOperation.java:39)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTask(ProgressMonitorUtility.java:104)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTaskExternal(ProgressMonitorUtility.java:90)
at org.eclipse.team.svn.core.utility.ProgressMonitorUtility.doTaskExternal(ProgressMonitorUtility.java:81)
at org.eclipse.team.svn.core.synchronize.AbstractSVNSubscriber.refresh(AbstractSVNSubscriber.java:186)
at org.eclipse.team.svn.core.synchronize.UpdateSubscriber.refresh(UpdateSubscriber.java:73)
at org.eclipse.team.core.subscribers.Subscriber.refresh(Subscriber.java:466)
at org.eclipse.team.core.subscribers.SubscriberMergeContext.refresh(SubscriberMergeContext.java:85)
at org.eclipse.team.core.mapping.provider.SynchronizationContext.refresh(SynchronizationContext.java:109)
at org.eclipse.team.internal.ui.synchronize.RefreshModelParticipantJob.doRefresh(RefreshModelParticipantJob.java:69)
at org.eclipse.team.internal.ui.synchronize.RefreshParticipantJob.run(RefreshParticipantJob.java:309)
at org.eclipse.team.internal.ui.synchronize.RefreshModelParticipantJob.run(RefreshModelParticipantJob.java:117)
at org.eclipse.core.internal.jobs.Worker.run(Worker.java:54)
Caused by: org.tigris.subversion.javahl.ClientException: svn: '/home/mrennie/workspaces/workspace/CommandLineDebugger' is not a working copy
svn: Cannot read from '/home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format': /home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format (No such file or directory)
at org.tigris.subversion.javahl.JavaHLObjectFactory.throwException(JavaHLObjectFactory.java:724)
at org.tmatesoft.svn.core.javahl.SVNClientImpl.throwException(SVNClientImpl.java:1929)
at org.tmatesoft.svn.core.javahl.SVNClientImpl.status(SVNClientImpl.java:304)
at org.tmatesoft.svn.core.javahl.SVNClientImpl.status(SVNClientImpl.java:282)
at org.polarion.team.svn.connector.svnkit.SVNKitConnector.status(SVNKitConnector.java:334)
... 33 more
Caused by: org.tmatesoft.svn.core.SVNException: svn: '/home/mrennie/workspaces/workspace/CommandLineDebugger' is not a working copy
svn: Cannot read from '/home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format': /home/mrennie/workspaces/workspace/CommandLineDebugger/.svn/format (No such file or directory)
at org.tmatesoft.svn.core.internal.wc.SVNErrorManager.error(SVNErrorManager.java:64)
at org.tmatesoft.svn.core.internal.wc.admin.SVNAdminAreaFactory.open(SVNAdminAreaFactory.java:149)
at org.tmatesoft.svn.core.internal.wc.admin.SVNWCAccess.doOpen(SVNWCAccess.java:355)
at org.tmatesoft.svn.core.internal.wc.admin.SVNWCAccess.open(SVNWCAccess.java:263)
at org.tmatesoft.svn.core.internal.wc.admin.SVNWCAccess.open(SVNWCAccess.java:256)
at org.tmatesoft.svn.core.internal.wc.admin.SVNWCAccess.openAnchor(SVNWCAccess.java:151)
at org.tmatesoft.svn.core.wc.SVNStatusClient.doStatus(SVNStatusClient.java:320)
at org.tmatesoft.svn.core.javahl.SVNClientImpl.status(SVNClientImpl.java:300)
... 35 more

After swearing for a bit and asking Google what I should do (and having no luck) I tried deleting suspicious looking files from the /.svn folder located in each affected project. The winner - at least for me - was to delete the /.svn/tmp folder and all of its contents and then restart Eclipse. After that all is well and I can sync to my hearts content.

I filed a bug for this state problem here:
https://bugs.eclipse.org/bugs/show_bug.cgi?id=328258

Wednesday, September 15, 2010

How p2 based targets work

Software Site locations in Target Definitions, typically described as "p2 based targets" are targets that get their bundles from an update site or p2 repository. This article will go over some of the implementation details of these targets. Knowing how the bundles are downloaded and added to the target can help to reproduce bugs and find workarounds.

For more general information on Target Platforms, see my previous article. The Eclipse help doc also explains a lot about how to create p2 based targets and add content to them.

The Basics:

Target definitions are created using the preference page or the editor. To create a p2 based target, at least one 'software site' location must be added to the target. The actual site location is abstracted from PDE. A local zipped repo, a remote site or a local profile will all be treated the same. A software site location specifies a site (or a category such as "all available sites") as well as one or more Root IUs. The root IUs describe what is being downloaded from the site, they are often high level features that effectively group a collection of bundles.

Target definitions must be resolved to modify the bundle list on the content tab or to set one as the active target platform. The resolve operation runs for each location independently. For most locations the resolve simply scans the location to get a list of file locations for bundles. In the case of a software site location, a more complex operation must be run.

Resolving Software Sites:

For each software site location, the following steps are taken:

  1. Load the repositories. This will create a queryable repository object. p2 will often request a repo's contents.xml file.
  2. Get the root IUs. If the location didn't already have actual installable units for the root units, the root IUs will be obtained from the site.
  3. Setup the planner or slicer. More on this later.
  4. Create a profile.
  5. Run the operation. Downloads and installs the units into the profile.
  6. Collect bundle locations for the target platform.
Note: In 3.7 a new performance enhancement was added that will skip the above steps and instead attempt to get a list of bundles from the stored profile. If the profile doesn't contain all the expected bundles or a problem occurs, the operation reverts to following the above steps.

Important Locations:

The following directories describe where PDE/p2 stores information related to the target resolution. Those familiar with p2 can modify the contents of the directories to force things to be recreated or to use the contents for a special purpose.

Target Definition Files:
/.metadata/.plugins/org.eclipse.pde.core/.local_targets
Where PDE stores the targets it creates from the preference page.

Profile Location:
/p2/org.eclipse.equinox.p2.engine/profileRegistry
Where profiles are created and persisted

Bundle Pool:
/.metadata/.plugins/org.eclipse.pde.core/.bundle_pool
Where p2 will download the bundles to during the operation

Planning vs Slicing

Once we have one or more sites and root IUs, we run a provisioning operation to download the required bundles and install them into a profile. The operation can be done using a slicer, which is typically used for mirroring a site or a planner, which is used by Eclipse to safely install and update itself.

Which one to use is determined by the options at the bottom of the wizard when editing a software site location. If "Include required software" is checked the planner is used. If unchecked the slicer is used. The include all environments setting determines if environment properties are set on the slicer.

The planner behaves the same as though we were installing the root IUs into an application. Therefore it checks that the complete set of required IUs are available to be downloaded and installed. If any IU is missing, the planner will report an error saying that a requirement is missing. This can be convenient as you may not realize some important piece is missing from your target. However, the target does not need to be a complete, runnable install, so forcibly requiring everything may be optimal.

The slicer uses an operation that copies IUs from a remote site to a local location. The slicer does create a list of required IUs, however it does not fail if the requirements are missing. Instead it will download all requirements it can from the site or sites that have been provided. This is a lot more flexible than the planner as all available IUs (even IUs that don't apply to the current environment settings) will be downloaded.

Conclusion:

After the resolve operation is complete, a list of bundles will be returned (pointing to the local copies in the bundle pool). PDE will use the local bundles as the target.