Text about Jobs and launch support of Eclipse in general
Eclipse supports asynchronous execution via so called Jobs, implemented in org.eclipse.core.runtime.jobs.Job. These Jobs can be scheduled with Job.schedule(), which will execute the run() method of a Job, which returns an IStatus.
JobChangeListeners can be added to a Job and react to the IStatus returned by the run() method of a Job.
All Java related tasks are handled by the eu.hatsproject.absplugin.actions.JavaJob. There are three different classes starting an Java Job.
You can start a simple JavaJob with "new JavaJob(name,action,project,file).schedule()", where
|ACTION_START_SDE||starts debugging and SDEdit|
|else||only compiling (.abs files to .java and .class files)|
You can overwrite the default arguments before scheduling the JavaJob. There are several set methods like for example "setDebuggerArgsSystemObserver(String debuggerArgsSystemObserver)". The default arguments are set in "setDebuggerArgumentsIfNull".
If you want to see more output / informations while a JavaJob is working, just set the boolean debugMode to true. For further information see the Javadoc and the code itself.
The eu.hatsproject.absplugin.actions.MaudeJob extends the default Job and overrides the run method offering compiling to .maude files and execution of such. To do so, one has to create a new MaudeJob, add a new MaudeJobChangeListener to it and schedule the Job.
The probably most interesting part is the returned status of the jobs run method. The MaudeJob will always return an IStatus with severity IStatus.INFO, the actual state is encoded within the code of the IStatus. The following outcomes are possible:
|Code||What happened||Reaction of the listener|
|MAUDE_OK||files have been generated, but not executed||none|
|MAUDE_INFO||files have been generated, execution was successful||the message of the status (console output of Maude) will be printed on the Eclipse console as Info (black)|
|MAUDE_WARNING||this code is not used by the MaudeJob||the message of the status will be printed on the Eclipse console as warning (yellow)|
|MAUDE_ERROR_MAUDE||Maude encountered an error during execution of the generated .maude file||the message of the status will be printed on the Eclipse console as error (red)|
|MAUDE_ERROR||Other errors have been encountered during compiling or starting the Maude process||An error message containing the message of the status will pop up|
|MAUDE_ERROR_MAUDE_PATH||No file has been found at the Maude location specified in the preferences||An error message will pop up. If this is dismissed, the Maude Preference Page will open and allow the user to specify a valid Maude path.|
|MAUDE_USER_ABORT||The user aborted the Maude Job||An abort message is printed on the Eclipse console as error (red)|
You may extend these by implementing new codes, but then have to adapt both the Job returning the new code as well as the listener which has to react on the new code appropriately.
Like Java Jobs, there are three points at which a Maude Job is created and scheduled:
At all these three points, the explained process of creating a job, adding a MaudeJobChangeListener and scheduling the job is followed.
For further reference see the Javadoc and the code itself.
Each run configuration consist of one ore more tabs (eu.hatsproject.absplugin.actions.runconfig.JavaTab or eu.hatsproject.absplugin.actions.runconfig.MaudeTab). Run configuration attributes are set in these classes.
Tabs are composed into TabGroups (eu.hatsproject.absplugin.actions.runconfig.JavaTabGroup or eu.hatsproject.absplugin.actions.runconfig.MaudeTabGroup).
The launch of a run configuration is in eu.hatsproject.absplugin.actions.runconfig.JavaRunConfiguration or eu.hatsproject.absplugin.actions.runconfig.MaudeRunConfiguration.
If you want to add a new Scheduler or SystemObserver in the Java run configuration, just modify eu.hatsproject.absplugin.actions.runconfig.RunConfigEnums.
Generally, debugging is done in cooperation with the ABSFrontend. The Eclipse plug-in creates and starts an abs.backend.java.lib.runtime.ABSRuntime and adds an internal scheduler and listeners to it.
Schedulers have to implement abs.backend.java.scheduling.TotalSchedulingStrategy and therefor contain a choose and a schedule method.
Listeners implement methods, which are called on specific events occurring during debugging, e.g. creation of a new COG or termination of a task.
The debug package is split into four parts or sub-packages
For more details about these packages see below.
Note, that this debugger is NOT related to the Eclipse Debug API but implements everything manually.
A short overview of the classes augmenting abs.backend.java.debugging.DebugModel
|eu.hatsproject.absplugin.debug.model.Debugger||abs.backend.java.observing.SystemObserver||manage model, start and terminate debug process, react on newCOGCreated|
|eu.hatsproject.absplugin.debug.model.DebugModelListener||abs.backend.java.debugging.DebugModelListener||react on COG and Task creations and changes|
|eu.hatsproject.absplugin.debug.model.ObjectCreationObserver||abs.backend.java.observing.ObjectCreationObserver||react on object creation and initialization|
|eu.hatsproject.absplugin.debug.model.Objects eu.hatsproject.absplugin.debug.model.Tasks||necessary to group objects and tasks in the debug viewer tree.|
|eu.hatsproject.absplugin.debug.model.VariableValuePair||necessary for variable view to link field names with their values|
For more details about the model see documentation of abs.backend.java.debugging.DebugModel and related classes.
Extension points and classes for the debugging interface:
|Debug View Variable View||org.eclipse.ui.views||eu.hatsproject.absplugin.debug.views.debugview.DebugView eu.hatsproject.absplugin.debug.views.variablesview.VariablView|
Debugging of ABS files is done in a new ABSDebugPerspective. The ABSDebugPerspectiveFactory sets up the initial design of the perspective, containing the DebugView and the VariableView.
The DebugView is the most important view for debugging. Here, a TreeViewer shows the current state of the debugged program. The DebugTreeContentProvider and DebugTreeStyledLabelProvider (found in eu.hatsproject.absplugin.debug.views.debugview) construct this tree out of a given DebugModel (which is found in the ABSFrontend at abs.backend.java.debugging), similar to the TreeViewer found in the Outline
The VariableView again is similar to the OutlinePage, classes are found at eu.hatsproject.absplugin.debug.views.VariableView. The only difference worth mentioning is the LabeProvider being an org.eclipse.jface.viewers.ITableLabelProvider, which results in the contents of the tree being shown in multiple columns. Classes implementing ITableLabelProvider need to implement the methods getColumnImage and getColumnText which are similar to the equivalently named methods in the conventional LabelProvider, but also take a column index as parameter and return only the value for a specific element in a specific column. So the elements returned by the ContentProvider need to contain data for each column of the table.
Buttons are added to the DebugView with another extension point. Enablement of this buttons is set by the method eu.hatsproject.absplugin.debug.DebugUtils.refreshButtonEnablement, which is called whenever task is stepped, another task (or different element) is selected in the debug tree or the scheduler is changed. The enablement is set according to the currently selected scheduler, the selection of the debug tree and the steps that are currently possible.
Scheduling is done in two layers. The eu.hatsproject.absplugin.debug.scheduling.SchedulingStrategy is directly connected the debugger implemented in the ABSFrontend. Calls to the choose(..) and schedule(..) methods are delegated to the internal schedulers. These schedulers are an extension of the abs.backend.java.scheduling.TotalSchedulingStrategy with an additional state. The interface is eu.hatsproject.absplugin.debug.scheduling.TotalScheduler. It supports a reset() method to invalidate the internal state of the scheduler.
The SchedulingStrategy delegates all calls first to the curScheduler. This is mostly a scheduler dedicated to the action the user whats to perform. The current implementations are:
It is connected to the SchedulingStrategy.doSingleStep() method. It waits for user input and when triggered performs a single step.
It is connected to the SchedulingStrategy.doMultipleSteps(..) method. It performs the number of steps the user entered.
It is connected to the SchedulingStrategy.doRunToLine(..) method. It performs steps till the debugger reaches the given line in the given file. If the line is not reached, it performs all possible steps.
It is connected to the SchedulingStrategy.doStepOver() method. It takes the stack frame of the task, that was selected last time, and performs steps till the same stack frame is reached again. If the stack frame is never reached again, all possible steps are performed.
All these action schedulers ask a base scheduler for the next action that can be performed. The task of a base scheduler is to run through the program in a given order/sequence without interruption. If the sequence is finished, the scheduler switches the curScheduler to the GUIScheduler and lets the user decide on the next steps to take. It is controlled by an action scheduler (see above). There are currently two implementations:
It is an extension of the abs.backend.java.scheduling.RandomSchedulingStrategy. It decides on the next step randomly. If there are no deadlocks, this scheduler can decide on all steps till the program is finished.
This scheduler decides on all steps of the given task. After a reset, it may schedule the given task. Afterwards it will try to decide on the step actions. If there are no more step actions possible, the scheduler switches the curScheduler to the GUIScheduler and lets the user decide. That means, if the task is blocked or there are no steps left, the scheduler will ask the user to decide on the next actions (for example to continue by resetting the scheduler -single step ore resume- or by choosing another task).