Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Debug Launch Configuration - Allow use of ${project_name} in Project: field on Main tab #342

Open
smagee-as opened this issue Apr 4, 2019 · 30 comments
Assignees

Comments

@smagee-as
Copy link

In Eclipse debug launch configurations, I'd like to use a variable like ${project_name} in the Project: field on the Main tab so I can reuse .launch files across projects without modification. Currently, this doesn't seem to be supported. I'm able to use ${project_name} in other fields of the debug configuration. But, if I replace the actual project name with ${project_name} in the Project: field, then I get the error:
Error while launching command: ${cross_prefix}gdb${cross_suffix} --version

I'm using the following versions:
Eclipse IDE Neon.3 Release (4.6.3) Build id: 20170314-1500
GNU MCU Eclipse plug-ins v4.3.1-201801092051
GNU MCU Eclipse Windows Build Tools v2.10-20180103
GCC Arm Embedded Tool Chain - GCC 7.0-2017-q4-major
Java Developer Kit - JDK 8u161
Segger J-Link Tools - JLINK V631b
Windows 10 Pro v1809 build 17763.379

@ilg-ul ilg-ul self-assigned this Apr 4, 2019
@ilg-ul ilg-ul added this to the Time permitting milestone Apr 4, 2019
@AntonKrug
Copy link
Contributor

AntonKrug commented Apr 25, 2019

At first it was not making any sense, the value ${project_name} is feed from the Project Name field, so you can't be populating variable from itself. But then I realize the mechanics and meaning of the variables change. In the debug launcher it's feed from the variable Project Name, BUT in the external launchers the meaning change a bit, and the ${project_name} is different: "The name of the currently selected resource's project or of the project being built if the external tool is run as part of a build."

https://help.eclipse.org/kepler/index.jsp?topic=%2Forg.eclipse.platform.doc.user%2Fconcepts%2Fconcepts-exttools.htm

If we would be able to have a option to switch between the 2 different logic (or being able to populate the Project name field with ${project_name}). Then using this would allow more dynamic launchers and therefore you might end up needing less launchers satisfying more projects, have less mess and not have to worry as much about so many launchers.

If this is achievable on GME level (and not on the CDT) then I would like look at it (time permitting) as it sounds as a good feature.

@AntonKrug
Copy link
Contributor

So it might be inherited in the TabMain.java and extending the CMainTab2 class, would it be ok to re-implement the CMainTab2 just with that different feature, or to add another ILaunchConfigurationTab tab to be able to affect it separately?

@ilg-ul
Copy link
Contributor

ilg-ul commented Apr 25, 2019

next week I plan to make a new GME plug-ins release, and I'll take a look at this issue too.

@AntonKrug
Copy link
Contributor

I was trying quickly slam the CMainTab2 functionality into your TabMain with small changes and now I can't even get it compiling. And even after I would change that tab, it would need to change the macro resolution functionality, so the feature might be more involved than it looks like on the surface, but it would be great addition, the Eclipse is clunky and sometimes bloated. This would reduce the bloat a bit. I will park it for time being, but do not hesitate to contact if you will figure out how it could be implemented and would need help writing it.

@smagee-as
Copy link
Author

Thank you for considering this enhancement!

Taking a step back and looking at the top level, my coworker was mentioning that other IDEs let you choose the debugger for the project first, let's say J-Link, CMSIS-DAP, or ST-Link, etc. Then, you configure that debugger to allow debugging, download, erase functions.

For my projects, I create launch files for various debuggers so my customers have a choice. I currently have 3 launch files (debug, download, erase) for 3 debuggers for a total of 9 launch files. I configure download and erase under the run menu only. Ideally, once the debugger is chosen in the project, then you could just click the debug icon to debug, or click on a menu to select download or erase.

For now, I'm thinking about creating an external tool batch file that will let the user select a debugger, which will copy the chosen debugger launch files to the 3 commonly named launch files used by the project. For example if J-Link is chosen in the .bat it would copy jlink_debug.launch to debug.launch. And, jlink_download.launch copied to download.launch.

@AntonKrug
Copy link
Contributor

You think within scope of single project. But for example if you have dozen projects with dozen launchers and only thing is changing the name of the project, then you could have one generic launchers which could cater all of them. And of course, like in your case this multiplies even more if you have more than 1 launcher per project.

@ilg-ul
Copy link
Contributor

ilg-ul commented Apr 25, 2019

I'm trying to understand exactly what you mean, but I need more details.

First, external launchers are different from debug launchers, and the initial request was for an enhancement to the debug launchers.

Second, although project-less debug lanchers are possible, I remember there were some limitations, including avoiding the macros defined in the project configuration (like ${cross_prefix} that you mention); thus I generally would not recommend project-less debug launchers.

if I replace the actual project name with ${project_name} in the Project: field

I'm afraid this is not possible, that field is the link between the debug launcher and the project, where do you suggest to get the value of the macro if the project is not known?

@AntonKrug
Copy link
Contributor

Yes it's for debug launchers, but what he is asking sounded to me that he wanted the behavior of the external launchers to be applied on the debug launcher. So the external launcher stay as they are, I just mentioned them because their logic is similar to what was asked originally.

The beauty of this approach would be that the original behavior would stay same, existing per project launchers would stay working. And who wants to take the risc (no pun intended :) ) could use it the new way.

It would figure out what project it is by checking what is the parent project of the currently selected resource in the project explorer. Then the user would have to be careful to have something selected for this approach to work. But it would allow users to do more verb/noun approach "I want to DEBUG this PROJECT" with just one debug launchers. When you do lot of projects and you port lot of stuff, the launchers get messy, hard to maintain, hard to transfer, it's finicky. While with this there is one rule to remember "have the project selected and be careful it will not get deselected or losing focus".

I think it's very possible, just I'm not sure about the feasibility, it offers something very interesting, but it's not that easy.

@smagee-as
Copy link
Author

Yes, actually, all of my launchers are debug launchers. On the Common tab, you can select whether they are under Debug or Run. I put download and erase under Run. For download and erase, I have the launcher execute with command line arguments for OpenOCD so it does the operation and exits debug. For J-Link, it executes some commands in "Startup->Run/Restart Commands", one of those being to "quit" debug.

I didn't mention ${cross_prefix}, but I'm using that in my launchers successfully right now. I assume because the project name is hard coded.

Ideally, if I only have 1 project open, then it would recognize that and just debug that project, even without having to select it. But, if multiple projects are open, then like AntonKrug suggested, you would have to select one of the open projects in Project Explorer before clicking debug.

@AntonKrug
Copy link
Contributor

With the ${cross_prefix} now it does that it goes to Project Name to figure out to which project it belongs, then it goes to that project to figure out what are the cross settings.

With the new approach the old approach would still work, but if the Project Name would contain macro, it would resolve the macro first depending on what is the currently selected resource into a project and then continue as the original approach.

The idea is not end up with one launcher to rule them all, but to significantly reduce them, so in the end you might end up with DEBUG_ARM and DEBUG_RISCV but you will not have dozens of RISC_Vs even when they are the same.

It would make the DEBUG/RUN approach much more feasible as well. Where there would be 2 launchers with only difference that the RUN wouldn't break in the main and ignore other breakpoints, which is similar to disabling breakpoints, disabling in the break in main in the launcher and debugging it. When you have to switch back and forth often it's annoying, creating so many launchers will make it very confusing when you will have few projects.

@ilg-ul
Copy link
Contributor

ilg-ul commented Apr 25, 2019

let me see if I got it right: if the project name is not set, you suggest to use the parent project of the selected resource.

I don't know if this is realistic, the Project Explorer might not even be present in the perspective where you want to start the launcher, or it might be present, but not visible, with nothing selected, or with a wrong selection.

as far as I know, Eclipse generally does not favour linking functionality to the selected resource in this indirect way, you generally have to right click on the resource to access the available actions.

personally I'm not very confident that this is a good idea, apart from the weird situations when you push a button and it displays a message telling you to make the Project Explorer visible and select a project, you can easily mess one target by clicking the button while the wrong resource remained selected. not to mention that if targets require separate configurations, like device names, or different speed settings, the risk of messing things is even greater and debugging these cases is even more difficult.

but what puzzles me a bit is the use case, the need to create and maintain huge numbers of debug configurations, due to huge numbers of projects in the same workspace of the same Eclipse instance.

first, debug configurations should be created only once, when the project is created, preferably automatically by the project template, and stored as .launch xml files in the project; that's the reason of using macros in it, to avoid full paths and other non portable definitions; storing them in the project allows sharing them with other developers via the repository, without having to recreate them on each workspace.

second, only tightly related projects should be in the same workspace. for experimental/research environments probably people tend to put more projects in the same workspace, but for production environments ideally one project per workspace should be seriously considered.

even more, for really serious projects, a project not only should have its own workspace, but also its own Eclipse instance, to avoid messing projects when one project needs one version of Eclipse and another one does not (yes, upgrading Eclipse has the risk of making changes in the workspace, making it crash in an older version).

people tend to forget that Eclipse is actually a folder that can be placed anywhere in the filesystem, and there is nothing wrong with having as many Eclipses as necessary. (I probably have several tens, I lost count of them).

I know that some vendors do not agree with this (sorry Anton), and insist on providing multi-GB super tools with everything but the kitchen sink packed inside, tools that it is not reasonably (sometimes not even possible) to install in multple versions/instances, but GNU MCU Eclipse does not recommend this approach and is specially designed to favour multi Eclipses, multi toolchains, and generally modular approaches (for example via xPacks).

so: modularize your environment, use multiple workpaces, possibly multiple Eclipses (which will also allow you to start many in parallel), save debug launch configurations in your projects and probably things will not be as complicated as you present.

@AntonKrug
Copy link
Contributor

If you do not have project view at all then you can still use the original way, this is option extra, not override of existing behavior. But if you would have only 1 project in the workspace like you propose then it should be possible to "guess" what project you have fairly accurately.

Multiple target boards would have own debug launchers but you would be able to switch between them faster than creating them for each project. In your ideal case when your template will create project to target board A and now you have to target board B and C, what will you do? Create new projects from templates for board B and C? And how easy it will be switch between them when your code is maybe developed and debugged on board A, but then tested and deployed on board B (when A might be more debug friendly variant of board B, but different enough that you need separate launcher).

"some vendors" actually have the Eclipse portable and you can have dozens of them installed, move them and run multiple instances of them. For example we wanted allow people to use one specific plugin and it was not portable, so we up-streamed a change to make it portable so others can benefit it from it as well. But that doesn't mean we force you to use it that way.

With this change there is the beauty to use as you using it now, no change and use your flow as you want (including having 1 project per eclipse), while allowing you to have multiple projects in same instance, in the same workspace if you prefer so. If Eclipse was not intending to be used that way, then they wouldn't never make the workspace mechanic in the first and would be more in style of VisualStudioCode. Having completely different instances for each project could make sharing of the projects bit more tricky, if each instance is meant to have different version of plugins and settings. Could xPacks orchestrate the eclipse installation, plugins installation and settings for all plugins you need for that project?

@ilg-ul
Copy link
Contributor

ilg-ul commented Apr 26, 2019

Multiple target boards would have own debug launchers but you would be able to switch between them faster than creating them for each project. In your ideal case when your template will create project to target board A and now you have to target board B and C, what will you do?

the xPack builder (a command line equivalent of the Eclipse builder) favours adding new build configurations for each board. if the project is portable, I think this is the reasonable way to do it.

Could xPacks orchestrate the eclipse installation, plugins installation and settings for all plugins you need for that project?

The xPacks design is completely unrelated to Eclipse and its plug-ins and does not depend on Eclipse specifics at all.

xPacks are specialised npm modules, that can be automatically pulled in a project to contribute versioned source files (like C/C++ files), and binary tools (like toolchains, builders, etc).

after the xPack command line tools will be ready, probably the first graphical tool to integrate them will be Visual Studio Code. Eclipse was also considered initially, but given the direction where Oracle is heading Java (did Microchip pay for your license?), and Eclipse slowly loosing traction, it is not guaranteed to happen.

@AntonKrug
Copy link
Contributor

The xPacks design is completely unrelated to Eclipse and its plug-ins and does not depend on Eclipse specifics at all.

I know, but when you share a project and it's dependent on specific feature of a specific plugin, or settings in your instance, because you propose many different instances which can be very different from each other then the receiving end now has to match your current instance. When you are going to transfer the project, now you have to transfer the whole eclipse instance.

Or you have to reconstruct the instance on other side in a deterministic way or the project will behave differently on the other side.

Yes it is out of scope of xPack, but then the "1 project per instance" can't be solved with xPack approach.

https://blog.joda.org/2018/09/do-not-fall-into-oracles-java-11-trap.html

@ilg-ul
Copy link
Contributor

ilg-ul commented Apr 26, 2019

you have to reconstruct the instance on other side in a deterministic way or the project will behave differently on the other side.

Yes it is out of scope of xPack, but then the "1 project per instance" can't be solved with xPack approach.

well, we probably have different understanding on some details, but I think you more or less got the general idea.

yes, anything related to GUI interactions is out of the scope of xPacks, but reconstructing a build environment in a deterministic way is exactly the purpose of xPacks and "1 environment per project" (which is a more accurate way of saying "1 project per instance") is the mantra.

the nice thing is that, if you want to use Eclipse for headless operations, you can easily pack Java as an xPack, Eclipse as another xPack, refer them as dependencies, and, together with one or more toolchains, builders, emulators, etc, all packed as xPacks, always create exactly the same development environment, and run tests in a deterministic way, locally, in a portable way on most modern platforms, and, even more interestingly, remotely on a CI server, like Travis.

similarly to npm, running xpm install inside an xPack folder will download all dependencies, add links to executables in a local .bin folder (or .cmd scripts on windows), and then add .bin in front of the PATH when running any of the tools. each project has its own .bin folder, so isolation is trivial.

you can easily see that the platform where this environment runs can be absolutely bare, only node.js/npm and xpm installed via npm. everything else is handled by xpm install as dependency. as for npm, dependencies do not even have to be xPacks, install can also handle custom scripts, so any scriptable tools can be used (although binary xPacks, like the existing toolchain xPacks, greately simplify this).

@AntonKrug
Copy link
Contributor

Fair point. So there is a way with xpacks too.

But my point is with giving users option would enable other workflows as well.

@XaviLC
Copy link

XaviLC commented Sep 1, 2022

Hello, I am also interested on @ilg-ul use case, I would like to forward project environmental variables to the Debugger launch. Is there any update or workaround that I can use for the time being ?

@ilg-ul
Copy link
Contributor

ilg-ul commented Sep 1, 2022

I am also interested on @ilg-ul use case

This thread went into multiple directions, could you be more specific of which use case?

@XaviLC
Copy link

XaviLC commented Sep 1, 2022

Sure, I would like to have the capability to use project defined environmental variables into the Debug launcher, something like this
image
Where all ${} variables are defined in the environment/build variables on the project build

@jonahgraham
Copy link
Contributor

@ilg-ul FWIW what @XaviLC is describing is something that Doug had started working on. But as his focus was "core build" it may not have made it everywhere, and has now been left to languish.

I assume that the processing of C/C++ Application field in embed-cdt is either just CDT or copied from CDT? If so, this bug probably needs to start life in Eclipse CDT or be contributed back there if possible?

@ilg-ul
Copy link
Contributor

ilg-ul commented Sep 1, 2022

@jonah, the implementations of the Main tab in the Embed CDT debug plug-ins look like this:

import org.eclipse.cdt.launch.ui.CMainTab2;
import org.eclipse.embedcdt.internal.debug.gdbjtag.jlink.ui.Activator;

public class TabMain extends CMainTab2 {

	/**
	 * If the preference is set to true, check program and disable Debug button
	 * if not found. The default GDB Hardware Debug plug-in behaviour is to do
	 * not check program, to allow project-less debug sessions.
	 */
	public TabMain() {
		super((Activator.getInstance().getDefaultPreferences().getTabMainCheckProgram() ? 0
				: CMainTab2.DONT_CHECK_PROGRAM) | CMainTab2.INCLUDE_BUILD_SETTINGS);
	}
}

How do you suggest to proceed?

@XaviLC
Copy link

XaviLC commented Sep 1, 2022

@jonah, the implementations of the Main tab in the Embed CDT debug plug-ins look like this:

import org.eclipse.cdt.launch.ui.CMainTab2;
import org.eclipse.embedcdt.internal.debug.gdbjtag.jlink.ui.Activator;

public class TabMain extends CMainTab2 {

	/**
	 * If the preference is set to true, check program and disable Debug button
	 * if not found. The default GDB Hardware Debug plug-in behaviour is to do
	 * not check program, to allow project-less debug sessions.
	 */
	public TabMain() {
		super((Activator.getInstance().getDefaultPreferences().getTabMainCheckProgram() ? 0
				: CMainTab2.DONT_CHECK_PROGRAM) | CMainTab2.INCLUDE_BUILD_SETTINGS);
	}
}

How do you suggest to proceed?

Is this something adding my desired functionality that I can use in my Eclipse Embed CDT? If so how can I add it?

@jonahgraham
Copy link
Contributor

Every time ICDTLaunchConfigurationConstants.ATTR_PROGRAM_NAME is read in the code it uses VariablesPlugin to resolve the variables. What needs to happen in everyone of those cases is it has to use the CDT variable resolvers that use the C Project's info too.

I am not exactly sure what needs to happen, but this code is what makes the environment variables from the project available to the target program, so adapting that should work.

I think that VariablesPlugin (which provides access to global variables, not project ones) needs to be replaced with (or enhanced with?) ICdtVariableManager usage, sort of like this untested code:

ILaunchConfiguration launchConfig = // launch configuration
IProject project = // project from Launch config, may be null/blank
ICProjectDescription projDesc = CoreModel.getDefault().getProjectDescription(project, false);
// check projDesc for null (if null, use existing VariablesPlugin method to resolve vars)
String buildConfigID = launchConfig.getAttribute(ICDTLaunchConfigurationConstants.ATTR_PROJECT_BUILD_CONFIG_ID, ""); 
ICConfigurationDescription cfg = null;
if (buildConfigID.length() != 0) {
    cfg = projDesc.getConfigurationById(buildConfigID);
}

// if configuration is null fall-back to active
if (cfg == null) {
    cfg = projDesc.getActiveConfiguration();
}

String programPath = launchConfig.getAttribute(ICDTLaunchConfigurationConstants.ATTR_PROGRAM_NAME, ""); 
programPath = CCorePlugin.getDefault().getCdtVariableManager().resolveValue(programPath, "", "", cfg);

The person I know who has the most experience on this area is @jantje - but I haven't seem him around much recently.

Ps I am @jonahgraham on GitHub (sorry @jonah - you seem to be getting more of my notifications recently!)

@jonahgraham
Copy link
Contributor

Is this something adding my desired functionality that I can use in my Eclipse Embed CDT? If so how can I add it?

If you can provide patches to CDT related to my above comment that would be great!

@XaviLC
Copy link

XaviLC commented Sep 1, 2022

Is this something adding my desired functionality that I can use in my Eclipse Embed CDT? If so how can I add it?

If you can provide patches to CDT related to my above comment that would be great!

I can try to do it but I don't know exactly where to add your code @jonahgraham

@ilg-ul
Copy link
Contributor

ilg-ul commented Sep 1, 2022

@jonahgraham, If I understand your message right, with the current implementation in Embed CDT, there is nothing that can be done to add this extra functionality. Right?

@jonahgraham
Copy link
Contributor

@jonahgraham, If I understand your message right, with the current implementation in Embed CDT, there is nothing that can be done to add this extra functionality. Right?

Yes. I think this should be in Eclipse CDT.

@jonahgraham
Copy link
Contributor

I can try to do it but I don't know exactly where to add your code @jonahgraham

You need to review/update all the uses of ATTR_PROGRAM_NAME in the CDT code base.

@XaviLC
Copy link

XaviLC commented Sep 1, 2022

I can try to do it but I don't know exactly where to add your code @jonahgraham

You need to review/update all the uses of ATTR_PROGRAM_NAME in the CDT code base.

What would this mean to have a plugin for it? Sorry I am really newbie with Eclipse implementation...

@jonahgraham
Copy link
Contributor

I can try to do it but I don't know exactly where to add your code @jonahgraham

You need to review/update all the uses of ATTR_PROGRAM_NAME in the CDT code base.

What would this mean to have a plugin for it? Sorry I am really newbie with Eclipse implementation...

The link in my comment points to all the java files that need to be updated, unfortunately - explaining Eclipse Plug-in development is out of scope of what I can teach. However there are some great resources out there. Please start with the excellent tutorials on https://www.vogella.com/tutorials/ and once you are familiar with Eclipse plug-ins/Java development I would be happy to guide you further. See also the Contributing section of the Eclipse CDT readme for how to start editing CDT.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants