]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
gdb/gdbserver: pass inferior arguments as a single string
authorAndrew Burgess <aburgess@redhat.com>
Thu, 23 Nov 2023 18:46:54 +0000 (18:46 +0000)
committerAndrew Burgess <aburgess@redhat.com>
Fri, 12 Sep 2025 10:06:00 +0000 (11:06 +0100)
GDB holds the inferior arguments as a single string.  Currently when
GDB needs to pass the inferior arguments to a remote target as part of
a vRun packet, this is done by splitting the single argument string
into its component arguments by calling gdb::remote_args::split, which
uses the gdb_argv class to split the arguments for us.

The same gdb_argv class is used when the user has asked GDB/gdbserver
to start the inferior without first invoking a shell; the gdb_argv
class is used to split the argument string into it component
arguments, and each is passed as a separate argument to the execve
call which spawns the inferior.

There is however, a problem with using gdb_argv to split the arguments
before passing them to a remote target.  To understand this problem we
must first understand how gdb_argv is used when invoking an inferior
without a shell.

And to understand how gdb_argv is used to start an inferior without a
shell, I feel we need to first look at an example of starting an
inferior with a shell.

Consider these two cases:

  (a)  (gdb) set args \$VAR
  (b)  (gdb) set args $VAR

When starting with a shell, in case (a) the user expects the inferior
to receive a literal '$VAR' string as an argument, while in case (b)
the user expects to see the shell expanded value of the variable $VAR.

If the user does 'set startup-with-shell off', then in (a) GDB will
strip the '\' while splitting the arguments, and the inferior will be
passed a literal '$VAR'.  In (b) there is no '\' to strip, so also in
this case the inferior will receive a literal '$VAR', remember
startup-with-shell is off, so there is no shell that can ever expand
$VAR.

Notice, that when startup-with-shell is off, we end up with a many to
one mapping, both (a) and (b) result in the literal string $VAR being
passed to the inferior.  I think this is the correct behaviour in this
case.

However, as we use gdb_argv to split the remote arguments we have the
same many to one mapping within the vRun packet.  But the vRun packet
will be used when startup-with-shell is both on and off.  What this
means is that when gdbserver receives a vRun packet containing '$VAR'
it doesn't know if GDB actually had '$VAR', or if GDB had '\$VAR'.
And this is a huge problem.

We can address this by making the argument splitting for remote
targets smarter, and I do have patches that try to do this in this
series:

  https://inbox.sourceware.org/gdb-patches/cover.1730731085.git.aburgess@redhat.com

That series was pretty long, and wasn't getting reviewed, so I'm
pulling the individual patches out and posting them separately.

This patch doesn't try to improve remote argument splitting.  I think
that splitting and then joining the arguments is a mistake which can
only introduce problems.  The patch in the above series which tries to
make the splitting and joining "smarter" handles unquoted, single
quoted, and double quoted strings.  But that doesn't really address
parameter substitution, command substitution, or arithmetic expansion.
And even if we did try to address these cases, what rules exactly
would we implement?  Probably POSIX shell rules, but what if the
remote target doesn't have a POSIX shell?  The only reason we're
talking about which shell rules to follow is because the splitting and
joining logic needs to mirror those rules.  If we stop splitting and
joining then we no longer need to care about the target's shell.

Clearly, for backward compatibility we need to maintain some degree of
argument splitting and joining as we currently have; and that's why I
have a later patch (see the series above) that tries to improve that
splitting and joining a little.  But I think, what we should really
do, is add a new feature flag (as used by the qSupported packet) and,
if GDB and the remote target agree, we should pass the inferior
arguments as a single string.

This solves all our problems.  In the startup with shell case, we no
longer need to worry about splitting at all.  The arguments are passed
unmodified to the remote target, that can then pass the arguments to
the shell directly.

In the 'startup-with-shell off' case it is now up to the remote target
to split the arguments, though in gdbserver we already did this, so
nothing really changes in this case.  And if the remote target doesn't
have a POSIX shell, well GDB just doesn't need to worry about it!

Something similar to this was originally suggested in this series:

  https://inbox.sourceware.org/gdb-patches/20211022071933.3478427-1-m.weghorn@posteo.de/

though this series didn't try to maintain backward compatibility,
which I think is an issue that my patch solves.  Additionally, this
series only passed the arguments as a single string in some cases,
I've simplified this so that, when GDB and the remote agree, the
arguments are always passed as a single string.  I think this is a
little cleaner.

I've also added documentation and some tests with this commit,
including ensuring that we test both the new single string approach,
and the fallback split/join approach.

I've credited the author of the referenced series as co-author as they
did come to a similar conclusion, though I think my implementation is
different enough that I'm happy to list myself as primary author.

Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=28392

Co-Authored-By: Michael Weghorn <m.weghorn@posteo.de>
Reviewed-By: Eli Zaretskii <eliz@gnu.org>
Tested-By: Guinevere Larsen <guinevere@redhat.com>
Approved-by: Kevin Buettner <kevinb@redhat.com>
gdb/NEWS
gdb/doc/gdb.texinfo
gdb/remote.c
gdb/testsuite/gdb.base/args.exp
gdb/testsuite/gdb.base/inferior-args.exp
gdb/testsuite/gdb.base/startup-with-shell.exp
gdbserver/server.cc
gdbserver/server.h

index 1daddd059eb80f37d5c159dad60f752c3fb25168..01bd1524c7ae38e9a3c75394005a6154313598ea 100644 (file)
--- a/gdb/NEWS
+++ b/gdb/NEWS
 
 GNU/Linux/MicroBlaze (gdbserver) microblazeel-*linux*
 
+* Changed remote packets
+
+single-inf-arg in qSupported
+  The new single-inf-arg feature within the qSupported packet allows
+  GDB to inform the stub that it would like to send the inferior
+  arguments as a single string within the vRun packet.  The stub can
+  reply with the single-inf-arg feature to indicate that it is able to
+  accept arguments as a single string.
+
 *** Changes in GDB 17
 
 * Debugging Linux programs that use x86-64 or x86-64 with 32-bit pointer
index f8154212fa438553ceb50f7021f3c88398cff397..676143be416684dc8ca076b7bb46be1afc0741f6 100644 (file)
@@ -43771,6 +43771,12 @@ command line.  The file and arguments are hex-encoded strings.  If
 (e.g.@: the last program run).  The program is created in the stopped
 state.
 
+If @value{GDBN} sent the @samp{single-inf-arg} feature in the
+@samp{qSupported} packet (@pxref{single-inf-arg}), and the stub replied
+with @samp{single-inf-arg+}, then there will only be a single
+@var{argument} string, which includes all inferior arguments,
+separated with whitespace.
+
 @c FIXME:  What about non-stop mode?
 
 This packet is only available in extended mode (@pxref{extended mode}).
@@ -45155,6 +45161,14 @@ didn't support @samp{E.@var{errtext}}, and older versions of
 
 New packets should be written to support @samp{E.@var{errtext}}
 regardless of this feature being true or not.
+
+@anchor{single-inf-arg}
+@item single-inf-arg
+This feature indicates that @value{GDBN} would like to send the
+inferior arguments as a single string within the @samp{vRun} packet.
+@value{GDBN} will not send the arguments as a single string unless the
+stub also reports that it supports this behaviour by including
+@samp{single-inf-arg+} in its @samp{qSupported} reply.
 @end table
 
 Stubs should ignore any unknown values for
@@ -45458,6 +45472,11 @@ These are the currently defined stub features and their properties:
 @tab @samp{-}
 @tab No
 
+@item @samp{single-inf-arg}
+@tab No
+@tab @samp{-}
+@tab No
+
 @end multitable
 
 These are the currently defined stub features, in more detail:
@@ -45707,6 +45726,12 @@ if it sent the @samp{error-message} feature.
 
 @item binary-upload
 The remote stub supports the @samp{x} packet (@pxref{x packet}).
+
+@item single-inf-arg
+The remote stub would like to receive the inferior arguments as a
+single string within the @samp{vRun} packet.  The stub should only
+send this feature if @value{GDBN} sent @samp{single-inf-arg+} in the
+@samp{qSupported} packet.
 @end table
 
 @item qSymbol::
index 1eb4f7279cfe4948ec0a8c6e1c691cb51c0cae3c..984b7166b7bec405be6c4621e13e3c5803666312 100644 (file)
@@ -401,6 +401,10 @@ enum {
      errors, and so they should not need to check for this feature.  */
   PACKET_accept_error_message,
 
+  /* Not really a packet; this indicates support for sending the vRun
+     inferior arguments as a single string.  */
+  PACKET_vRun_single_argument,
+
   PACKET_MAX
 };
 
@@ -826,6 +830,11 @@ struct remote_features
   bool remote_memory_tagging_p () const
   { return packet_support (PACKET_memory_tagging_feature) == PACKET_ENABLE; }
 
+  /* Returns true if there is support for sending vRun inferior arguments
+     as a single string.  */
+  bool remote_vrun_single_arg_p () const
+  { return packet_support (PACKET_vRun_single_argument) == PACKET_ENABLE; }
+
   /* Reset all packets back to "unknown support".  Called when opening a
      new connection to a remote target.  */
   void reset_all_packet_configs_support ();
@@ -5876,6 +5885,8 @@ static const struct protocol_feature remote_protocol_features[] = {
   { "error-message", PACKET_ENABLE, remote_supported_packet,
     PACKET_accept_error_message },
   { "binary-upload", PACKET_DISABLE, remote_supported_packet, PACKET_x },
+  { "single-inf-arg", PACKET_DISABLE, remote_supported_packet,
+    PACKET_vRun_single_argument },
 };
 
 static char *remote_support_xml;
@@ -5987,6 +5998,10 @@ remote_target::remote_query_supported ()
          != AUTO_BOOLEAN_FALSE)
        remote_query_supported_append (&q, "memory-tagging+");
 
+      if (m_features.packet_set_cmd_state (PACKET_vRun_single_argument)
+         != AUTO_BOOLEAN_FALSE)
+       remote_query_supported_append (&q, "single-inf-arg+");
+
       /* Keep this one last to work around a gdbserver <= 7.10 bug in
         the qSupported:xmlRegisters=i386 handling.  */
       if (remote_support_xml != NULL
@@ -10850,7 +10865,11 @@ remote_target::extended_remote_run (const std::string &args)
 
   if (!args.empty ())
     {
-      std::vector<std::string> split_args = gdb::remote_args::split (args);
+      std::vector<std::string> split_args;
+      if (!m_features.remote_vrun_single_arg_p ())
+       split_args = gdb::remote_args::split (args);
+      else
+       split_args.push_back (args);
 
       for (const auto &a : split_args)
        {
@@ -16553,6 +16572,10 @@ Show the maximum size of the address (in bits) in a memory packet."), NULL,
   add_packet_config_cmd (PACKET_accept_error_message,
                         "error-message", "error-message", 0);
 
+  add_packet_config_cmd (PACKET_vRun_single_argument,
+                        "single-inferior-argument-feature",
+                        "single-inferior-argument-feature", 0);
+
   /* Assert that we've registered "set remote foo-packet" commands
      for all packet configs.  */
   {
index b8596608439ff2d072f9f39707afcf4bcafe2e0d..573543cc1f8623e76607ab73ee501d6a99516896 100644 (file)
@@ -30,6 +30,37 @@ if {[build_executable $testfile.exp $testfile $srcfile] == -1} {
     return -1
 }
 
+# Assuming a running GDB.  Check the status of the single inferior
+# argument feature.  When this feature is on GDB passes inferior
+# arguments as a single combined string.  When this feature is off GDB
+# will split the inferior arguments into multiple separate strings.
+#
+# Return true when arguments are being split, or false when a single
+# combined string is being sent.
+
+proc is_argument_splitting_on {} {
+    set arg_splitting true
+
+    gdb_test_multiple "show remote single-inferior-argument-feature-packet" "" {
+       -re -wrap "Support for the 'single-inferior-argument-feature' packet on the current remote target is \"(on|off)\"\\.(.*)" {
+           set value $expect_out(1,string)
+           pass $gdb_test_name
+           if { $value eq "on" } {
+               set arg_splitting false
+           }
+       }
+       -re -wrap "Support for the 'single-inferior-argument-feature' packet on the current remote target is \"auto\", currently (enabled|disabled)\\.(.*)" {
+           set value $expect_out(1,string)
+           pass $gdb_test_name
+           if { $value eq "enabled" } {
+               set arg_splitting false
+           }
+       }
+    }
+
+    return $arg_splitting
+}
+
 # NAME is the name to use for the tests and ARGLIST is the list of
 # arguments that are passed to GDB when it is started.
 #
@@ -105,7 +136,8 @@ proc args_test { name arglist {re_esc_list {}} {re_no_esc_list {}} } {
                    if { $startup_with_shell eq "on"
                         && $arg_flag eq "no-escape-args"
                         && [gdb_protocol_is_remote]
-                        && [string first "\$" $arglist] != -1 } {
+                        && [string first "\$" $arglist] != -1
+                        && [is_argument_splitting_on] } {
                        setup_xfail "*-*-*" gdb/28392
                    }
 
@@ -119,36 +151,53 @@ proc args_test { name arglist {re_esc_list {}} {re_no_esc_list {}} } {
     }
 }
 
-# Test that the --args are processed correctly.
+# Run all the tests.
+proc run_all_tests {} {
+    # Test that the --args are processed correctly.
+
+    args_test basic {{1} {3}}
 
-args_test basic {{1} {3}}
+    # Test that the --args are processed correctly even if one of them is
+    # empty.
 
-# Test that the --args are processed correctly even if one of them is
-# empty.
+    args_test "one empty" {{1} {} {3}}
 
-args_test "one empty" {{1} {} {3}}
+    # Try with 2 empty args.
 
-# Try with 2 empty args.
+    args_test "two empty" {{1} {} {} 3}
 
-args_test "two empty" {{1} {} {} 3}
+    # Try with arguments containing literal single quotes.
 
-# Try with arguments containing literal single quotes.
+    args_test "one empty with single quotes" {{1} {''} {3}}
 
-args_test "one empty with single quotes" {{1} {''} {3}}
+    args_test "two empty with single quotes" {{1} {''} {''} {3}}
 
-args_test "two empty with single quotes" {{1} {''} {''} {3}}
+    # Try with arguments containing literal newlines.
 
-# Try with arguments containing literal newlines.
+    args_test "one newline" {{1} "\n" {3}} {1 \\\\n 3}
 
-args_test "one newline" {{1} "\n" {3}} {1 \\\\n 3}
+    args_test "two newlines" {{1} "\n" "\n" {3}} {1 \\\\n \\\\n 3}
 
-args_test "two newlines" {{1} "\n" "\n" {3}} {1 \\\\n \\\\n 3}
+    args_test "lone single quote" {{1} \' {3}}
 
-args_test "lone single quote" {{1} \' {3}}
+    args_test "lone double quote" {{1} \" {3}} {1 \\\\\" 3}
 
-args_test "lone double quote" {{1} \" {3}} {1 \\\\\" 3}
+    save_vars { ::env(TEST) } {
+       set ::env(TEST) "ABCD"
+       args_test "shell variable" {{$TEST}} {\\$TEST} {{ABCD}}
+    }
+}
 
-save_vars { ::env(TEST) } {
-    set ::env(TEST) "ABCD"
-    args_test "shell variable" {{$TEST}} {\\$TEST} {{ABCD}}
+run_all_tests
+
+# For extended-remote targets, disable the packet which passes
+# inferior arguments as a single string.  This changes how the vRun
+# (extended-remote only) packet works.
+if {[target_info gdb_protocol] == "extended-remote"} {
+    with_test_prefix "single-inferior-arg disabled" {
+       save_vars { GDBFLAGS } {
+           append GDBFLAGS " -ex \"set remote single-inferior-argument-feature-packet off\""
+           run_all_tests
+       }
+    }
 }
index 3887239ef3654e790af6406d2f2d33d64fd9d47d..b2916701ba9a93e9d6729e02464340ac964fd414 100644 (file)
@@ -213,14 +213,31 @@ lappend test_desc_list [list "test four" \
                            [list "$hex \"'\"" \
                                 "$hex \"\\\\\"\""]]
 
-foreach desc $test_desc_list {
-    lassign $desc name stub_suitable args re_list
-    with_test_prefix $name {
-       foreach_with_prefix set_method { "start" "starti" "run" "set args" } {
-           foreach_with_prefix startup_with_shell { on off } {
-               do_test $set_method $startup_with_shell $args $re_list \
-                   $stub_suitable
+# Run all tests in the global TEST_DESC_LIST.
+proc run_all_tests {} {
+    foreach desc $::test_desc_list {
+       lassign $desc name stub_suitable args re_list
+       with_test_prefix $name {
+           foreach_with_prefix set_method { "start" "starti" "run" "set args" } {
+               foreach_with_prefix startup_with_shell { on off } {
+                   do_test $set_method $startup_with_shell $args $re_list \
+                       $stub_suitable
+               }
            }
        }
     }
 }
+
+run_all_tests
+
+# For extended-remote targets, disable the packet which passes
+# inferior arguments as a single string.  This changes how the vRun
+# (extended-remote only) packet works.
+if {[target_info gdb_protocol] == "extended-remote"} {
+    with_test_prefix "single-inferior-arg disabled" {
+       save_vars { GDBFLAGS } {
+          append GDBFLAGS " -ex \"set remote single-inferior-argument-feature-packet off\""
+          run_all_tests
+       }
+    }
+}
index 25b161ad4f15f8f4fb8f3ea2857b954891ea8fef..a6ebb57c00e72996944939e82d2a26c1b368a398 100644 (file)
@@ -94,73 +94,97 @@ proc run_test_same { args re testname } {
     run_test $args $re $re $testname
 }
 
-# The regexp to match a single '\' character.
-set bs "\\\\"
-
-# Are we using 'remote' or 'extended-remote' protocol?
-set is_remote_p [gdb_protocol_is_remote]
-
-## Run the actual tests
-
-run_test "$unique_file_dir/*.unique-extension" \
-    "\"$unique_file\"" \
-    "\"$unique_file_dir/\\\*\.unique-extension\"" \
-    "arg is glob" \
-    $is_remote_p
-
-run_test_same "$unique_file_dir/\\*.unique-extension" \
-    "\"$unique_file_dir/\\\*\.unique-extension\"" \
-    "arg is escaped glob"
-
-save_vars { env(TEST) } {
-    set env(TEST) "1234"
-    run_test "\$TEST" \
-       "\"1234\"" \
-       "\"\\\$TEST\"" \
-       "arg is shell variable" \
-       $is_remote_p
-
-    run_test_same "\\\$TEST" \
-       "\"\\\$TEST\"" \
-       "arg is escaped shell variable"
-}
-
-run_test_same "\"\\a\"" \
-    "\"${bs}${bs}a\"" \
-    "retain backslash in double quote arg"
-
-run_test_same "'\\a'" \
-    "\"${bs}${bs}a\"" \
-    "retain backslash in single quote arg"
-
-run_test_same "\"\\\$\"" \
-    "\"\\\$\"" \
-    "'\$' can be escaped in double quote arg"
-
-run_test_same "'\\\$'" \
-    "\"${bs}${bs}\\\$\"" \
-    "'\$' is not escaped in single quote arg"
-
-run_test_same "\"\\`\"" \
-    "\"\\`\"" \
-    "'`' can be escaped in double quote arg"
-
-run_test_same "'\\`'" \
-    "\"${bs}${bs}`\"" \
-    "'`' is not escaped in single quote arg"
-
-run_test_same "\"\\\"\"" \
-    "\"${bs}\"\"" \
-    "'\"' can be escaped in double quote arg"
+# Run the actual tests
+proc run_all_tests { { is_remote_with_split_args false } } {
+    # The regexp to match a single '\' character.
+    set bs "\\\\"
+
+    run_test "$::unique_file_dir/*.unique-extension" \
+       "\"$::unique_file\"" \
+       "\"$::unique_file_dir/\\\*\.unique-extension\"" \
+       "arg is glob" \
+       $is_remote_with_split_args
+
+    run_test_same "$::unique_file_dir/\\*.unique-extension" \
+       "\"$::unique_file_dir/\\\*\.unique-extension\"" \
+       "arg is escaped glob"
+
+    save_vars { ::env(TEST) } {
+       set ::env(TEST) "1234"
+       run_test "\$TEST" \
+           "\"1234\"" \
+           "\"\\\$TEST\"" \
+           "arg is shell variable" \
+           $is_remote_with_split_args
+
+       run_test_same "\\\$TEST" \
+           "\"\\\$TEST\"" \
+           "arg is escaped shell variable"
+    }
 
-run_test_same "'\\\"'" \
-    "\"${bs}${bs}${bs}\"\"" \
-    "'\"' is not escaped in single quote arg"
+    run_test "\$(echo foo)" \
+       "\"foo\"" \
+       "\"\\\$\\(echo\"" \
+       "arg is parameter expansion, command execution" \
+       $is_remote_with_split_args
+
+    run_test "\$((2 + 3))" \
+       "\"5\"" \
+       "\"\\\$\\(\\(2\"" \
+       "arg is parameter expansion, expression evaluation" \
+       $is_remote_with_split_args
+
+    run_test_same "\"\\a\"" \
+       "\"${bs}${bs}a\"" \
+       "retain backslash in double quote arg"
+
+    run_test_same "'\\a'" \
+       "\"${bs}${bs}a\"" \
+       "retain backslash in single quote arg"
+
+    run_test_same "\"\\\$\"" \
+       "\"\\\$\"" \
+       "'\$' can be escaped in double quote arg"
+
+    run_test_same "'\\\$'" \
+       "\"${bs}${bs}\\\$\"" \
+       "'\$' is not escaped in single quote arg"
+
+    run_test_same "\"\\`\"" \
+       "\"\\`\"" \
+       "'`' can be escaped in double quote arg"
+
+    run_test_same "'\\`'" \
+       "\"${bs}${bs}`\"" \
+       "'`' is not escaped in single quote arg"
+
+    run_test_same "\"\\\"\"" \
+       "\"${bs}\"\"" \
+       "'\"' can be escaped in double quote arg"
+
+    run_test_same "'\\\"'" \
+       "\"${bs}${bs}${bs}\"\"" \
+       "'\"' is not escaped in single quote arg"
+
+    run_test_same "\"\\\\\"" \
+       "\"${bs}${bs}\"" \
+       "'\\' can be escaped in double quote arg"
+
+    run_test_same "'\\\\'" \
+       "\"${bs}${bs}${bs}${bs}\"" \
+       "'\\' is not escaped in single quote arg"
+}
 
-run_test_same "\"\\\\\"" \
-    "\"${bs}${bs}\"" \
-    "'\\' can be escaped in double quote arg"
+run_all_tests
 
-run_test_same "'\\\\'" \
-    "\"${bs}${bs}${bs}${bs}\"" \
-    "'\\' is not escaped in single quote arg"
+# For extended-remote targets, disable the packet which passes
+# inferior arguments as a single string.  This changes how the vRun
+# (extended-remote only) packet works.
+if {[target_info gdb_protocol] == "extended-remote"} {
+    with_test_prefix "single-inferior-arg disabled" {
+       save_vars { GDBFLAGS } {
+           append GDBFLAGS " -ex \"set remote single-inferior-argument-feature-packet off\""
+           run_all_tests true
+       }
+    }
+}
index 1f910a415b6ea5e3748bb2a05cde89f8083f6c46..5907e86847ad84762d9d56ee58ef60f75c2093a8 100644 (file)
@@ -2744,6 +2744,8 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p)
                }
              else if (feature == "error-message+")
                cs.error_message_supported = true;
+             else if (feature == "single-inf-arg+")
+               cs.single_inferior_argument = true;
              else
                {
                  /* Move the unknown features all together.  */
@@ -2871,6 +2873,9 @@ handle_query (char *own_buf, int packet_len, int *new_packet_len_p)
       if (target_supports_memory_tagging ())
        strcat (own_buf, ";memory-tagging+");
 
+      if (cs.single_inferior_argument)
+       strcat (own_buf, ";single-inf-arg+");
+
       /* Reinitialize components as needed for the new connection.  */
       hostio_handle_new_gdb_connection ();
       target_handle_new_gdb_connection ();
@@ -3463,7 +3468,20 @@ handle_v_run (char *own_buf)
   else
     program_path.set (new_program_name.get ());
 
-  program_args = gdb::remote_args::join (new_argv.get ());
+  if (cs.single_inferior_argument)
+    {
+      if (new_argv.get ().size () > 1)
+       {
+         write_enn (own_buf);
+         return;
+       }
+      else if (new_argv.get ().size () == 1)
+       program_args = std::string (new_argv.get ()[0]);
+      else
+       program_args.clear ();
+    }
+  else
+    program_args = gdb::remote_args::join (new_argv.get ());
 
   try
     {
index b9dacb823bcb217a0bcbb08ced513ffa2e41737a..1bf3e7757a65163bd0f0453fba43c4fbe21e6c94 100644 (file)
@@ -197,6 +197,11 @@ struct client_state
      are not supported with qRcmd and m packets, but are still supported
      everywhere else.  This is for backward compatibility reasons.  */
   bool error_message_supported = false;
+
+  /* If true then we've agreed that the debugger will send all inferior
+     arguments as a single string.  When false the debugger will attempt
+     to split the inferior arguments before sending them.  */
+  bool single_inferior_argument = false;
 };
 
 client_state &get_client_state ();