| Summary: | Wrong arguments are passed to a program in debug mode | ||
|---|---|---|---|
| Product: | [Tools] CDT | Reporter: | Sergey Prigogin <eclipse.sprigogin> |
| Component: | cdt-debug-dsf-gdb | Assignee: | Sergey Grant <sergey.grant> |
| Status: | RESOLVED FIXED | QA Contact: | Marc Khouzam <marc.khouzam> |
| Severity: | major | ||
| Priority: | P3 | CC: | ccaughie, cdtdoug, g.janak, kagangm, marc.khouzam, sergey.grant |
| Version: | 8.7.0 | ||
| Target Milestone: | 9.0.0 | ||
| Hardware: | PC | ||
| OS: | Linux | ||
| See Also: |
https://git.eclipse.org/r/61924 https://git.eclipse.org/c/cdt/org.eclipse.cdt.git/commit/?id=8360f715ebbdb5fccc2dfa0e262766b70dfffb88 |
||
| Whiteboard: | |||
|
Description
Sergey Prigogin
New Gerrit change created: https://git.eclipse.org/r/61924 Gerrit change https://git.eclipse.org/r/61924 was merged to [master]. Commit: http://git.eclipse.org/c/cdt/org.eclipse.cdt.git/commit/?id=8360f715ebbdb5fccc2dfa0e262766b70dfffb88 In order to fix the bug, the way arguments are treated was changed, as behaviour previously was pretty much undefined. The following guidelines were used:
- The program must get the same parameters whether Run or Debug are used.
- User must be able to specify arbitrary contents for an arbitrary number of arguments.
- Aside from the constraint above, the argument window should resemble what the program receives as much as possible as opposed to providing full shell capabilities. It is impossible to do so in a consistent manner given platform differences and cross-platform configurations. The only exception to this is the substitution of variables inside ${variable_name}.
The arguments work in the following way:
- Any character following a backslash is treated literally and loses special meaning.
- Any character after a quote and before the next matching quote (or EOF) is treated literally and loses special meaning (both single and double).
- White space (unless escaped or within quotes) is used as the argument delimiter.
(Special characters, unless when they lose their special meaning, do not make it to the argument strings)
All of this was essentially already in place except broken because of two further stages every parameter went through. Firstly, all occurrences of backslash and double quote were escaped and then, if any white space is present, an argument was surrounded by double quotes. This would have been fine if each string did not undergo substitutions by BASH. This means that `date` or $PS1 or $[2+2] would be substituted and any quoting or escaping would undergo changes sometimes but would be left literally other times. The user had no power to prevent this in some cases, namely, when both space and substitutable content was present. For example, when the desired argument is
`date` hello
It would inevitably be surrounded by double quotes, and any attempts to escape or quote backticking would be cancelled by the double quotes. On the other hand, applying my solution for arguments to the rest of GDB messages broke those messages, as quotes were mistreated in those contexts.
Using same processing for arguments and other strings passed to the GDB was problematic as evidently no preprocessing could be done with arguments, neither by the user nor in the code.
The following solution is used for arguments only (in place of the general processing used for the rest of the options), after initial escaping, quoting and argument separation rules have been applied:
- Surround each argument with single quotes
- For any single quotes, use double quotes (escaping could be used too)
- Replace any newline occurrences with '$'\n''
The last step is necessary as feeding newline characters in directly ends the command and with all other approaches \n is treated literally as "backslash-lowercase-n".
The main consequences are that now it is very easy to predict what arguments will be received by the program based on the arguments window alone, that strings are treated literally and are not replaced by bash, that random processes cannot run based on the arguments, and that this behaviour is consistent with the Run configuration treatment.
This behaviour should be adopted by the JDT if it is not already.
I'm testing a new nightly CDT build. After last update, i noticed a change in handling Command line Arguments. I don't know if this , what this bug was for. I Configute something like A B ThirdParameter In My Programm (Mingw32 gcc 5.3.0 - GDB) i notices argv[1]="'A'" argv[2]="'B'" argv[3]="'ThirdParameter'" This will break Commandline Parsers... If starting with GDB , without Eclipse, i work like before... argv[1]="A" argv[2]="B" argv[3]="ThirdParameter" Is there anything I'am doing wrong ? Or is this the new prefered behavior in CDT ? Hi Gabor, Behaviour changed in that before there was no strictly defined behaviour. Wrapping arguments in quotes allows to make sure they are treated strictly as strings of characters and the program receives the arguments exactly as the users expects. It was not apparent that this led to any problems elsewhere, could you please describe exactly what breaks down as an effect and exactly which arguments you are using. Can you also confirm that the arguments you have mentioned are received with quotes by the program itself? Sergey I will try it: ;)
Simple Code:
---
#include "windows.h"
#include <iostream>
using namespace std;
int WINAPI WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
cout << "lpCmdLine:" << lpCmdLine << endl;
return 0;
}
---
Building and Executing on Windows Commandline:
>testappp.exe A B C Four
lpCmdLine:A B C Four
---
DebugSession in Eclipse.
Debug Configurations/Arguments/Program arguments:
A B C Four
---
Using a Breakpoint and using variable inspector i see the following:
Name : lpCmdLine
Details:0xb3d0f "'A' 'B' 'C' 'Four'"
Default:0xb3d0f "'A' 'B' 'C' 'Four'"
Decimal:736527
Hex:0xb3d0f
Binary:10110011110100001111
The same if i use a classic int main(int argc,char** argv)
or the GetCommandLineArgument windows API Call.
GDB trace Console interesting lines:
145,505 (gdb)
145,506 18-file-exec-and-symbols --thread-group i1 out/testappp.exe
145,552 18^done
145,552 (gdb)
145,553 19-gdb-set --thread-group i1 args 'A' 'B' 'C' 'Four'
145,563 19^done
---
Eclipse Platform
Version: Neon (4.6)
Build id: I20160128-2000
GNU gdb (GDB) 7.10.1
Using a Pure GDB Session without Eclipse (to exclude a GDB problem)
gdb --args testappp.exe A B C
(gdb) r
Starting program: d:\Workspace.eclipse\test11\out\testappp.exe A B C
lpCmdLine:A B C
What Information do you need ?
---
Additional:
If i setting in eclipse "A B C four" <-- with double Quotes.
I Am Getting this:
argc:5
argv[0]=....testappp.exe
argv[1]='A
argv[2]=B
argv[3]=C
argv[4]=Four'
without quotes:
argc:5
argv[0]=....testappp.exe
argv[1]='A'
argv[2]='B'
argv[3]='C'
argv[4]='Four'
testcode:
int main(int argc,char** argv)
{
cout << "argc:" << argc << endl;
for (int i=0;i<argc;++i)
cout << "argv["<< i << "]="<< argv[i] << endl;
I notices new interesting behavior. If i make RUN instead of DEBUG : argc:5 argv[0]=D:\Workspace.eclipse\test11\out\testappp.exe argv[1]=A argv[2]=B argv[3]=C argv[4]=Four this is what I'm expect. And I checked the Current version: I20160317-0200 - unchanged. The problem was always only with debug and not run. Perhaps this is a platform related problem. Before the change, on Windows, what was the behaviour of the examples from the original post? If they worked fine, then we must have migrated the problem and the patch should only apply to Linux, I guess. Testing it again: Tested with Eclipse Version: eclipse.buildId=4.6.0.I20160317-0200 jre1.8.0_77 (64bit) CDT Version: 9.0.0.201604161004 Build id: @build@ GNU gdb (GDB) 7.10.1 "x86_64-w64-mingw32" Platform : Windows 10 64bit GDB Trace looks the same 575,428 18-file-exec-and-symbols --thread-group i1 out/testappp.exe 575,472 18^done 575,472 (gdb) 575,473 19-gdb-set --thread-group i1 args 'A' 'B' 'C' 'Four' 575,482 19^done resulting arguments during Debug Session (Output should be without any ''): argc=5 argv[0]=D:\Workspace.eclipse est11\out estappp.exe argv[1]='A' argv[2]='B' argv[3]='C' argv[4]='Four' (output \t in console seems a other problem) resulting arguments during RUN Session: argc:5 argv[0]=D:\Workspace.eclipse\test11\out\testappp.exe argv[1]=A argv[2]=B argv[3]=C argv[4]=Four Should I open a new Ticket ? Can someone reproduce this? Perhaps its a local private problem. Hello, I am seeing exactly the same behavior with official Neon CDT distribution on Windows. Command line parser which is working with Windows CMD or Eclipse RUN launches does not work with DEBUG launches. During DEBUG Eclipse passes all command line arguments surrounded by single quotes. E.g. my.exe myarg will see "'myarg'" while debugging but will see "myarg" when running. It is not clear from the discussion if this issue being addressed. Eugene Also seeing this problem; as far as I can tell it prevents all debugging of Windows C/C++ programs that take command line arguments without modifying the code to strip out the quotes. Note that a new bug has been raised to track this since this one was closed: https://bugs.eclipse.org/bugs/show_bug.cgi?id=494246 (thanks Eugene!). |