About implementation of the Negative property of options.
gengqi-linux
gengqi@linux.alibaba.com
Wed Apr 28 12:36:11 GMT 2021
I have been fixing a bug. It involved the Negative property of options, and I have some confusion about it.
gcc/optc-gen.awk: 383
neg = opt_args("Negative", flags[i]);
if (neg != "")
idx = indices[neg]
else {
if (flag_set_p("RejectNegative", flags[i]))
idx = -1;
else {
if (opts[i] ~ "^[Wfgm]")
idx = indices[opts[i]];
else
idx = -1;
}
}
Above is the code that handles the ‘Nagetive’ property. I don't see why the 'idx' should be set -1 when 'RejectNegative'.
As I understand it, ‘Negative’ and ‘RejectNegative’ are similar name, but not related in implementation.
The following is my implementation about it:
--- a/gcc/doc/options.texi
+++ b/gcc/doc/options.texi
@@ -220,11 +220,7 @@ property is used.
The option will turn off another option @var{othername}, which is
the option name with the leading ``-'' removed. This chain action will
propagate through the @code{Negative} property of the option to be
-turned off. The driver will prune options, removing those that are
-turned off by some later option. This pruning is not done for options
-with @code{Joined} or @code{JoinedOrMissing} properties, unless the
-options have either @code{RejectNegative} property or the @code{Negative}
-property mentions an option other than itself.
+turned off.
As a consequence, if you have a group of mutually-exclusive
options, their @code{Negative} properties should form a circular chain.
diff --git a/gcc/optc-gen.awk b/gcc/optc-gen.awk
index 880ac77..d32354c 100644
--- a/gcc/optc-gen.awk
+++ b/gcc/optc-gen.awk
@@ -383,7 +383,9 @@ for (i = 0; i < n_opts; i++) {
if (neg != "")
idx = indices[neg]
else {
- if (flag_set_p("RejectNegative", flags[i]))
+ if (flag_set_p("Joined", flags[i]) \
+ || flag_set_p("JoinedOrMissing", flags[i]) \
+ || flag_set_p("Separate", flags[i]))
idx = -1;
else {
if (opts[i] ~ "^[Wfgm]")
diff --git a/gcc/opts-common.c b/gcc/opts-common.c
index 5e10ede..898e8d8 100644
--- a/gcc/opts-common.c
+++ b/gcc/opts-common.c
@@ -1039,11 +1039,12 @@ cancel_option (int opt_idx, int next_opt_idx, int orig_next_opt_idx)
if (cl_options [next_opt_idx].neg_index == opt_idx)
return true;
- if (cl_options [next_opt_idx].neg_index != orig_next_opt_idx)
- return cancel_option (opt_idx, cl_options [next_opt_idx].neg_index,
- orig_next_opt_idx);
+ if (cl_options [next_opt_idx].neg_index == orig_next_opt_idx
+ || cl_options [next_opt_idx].neg_index < 0)
+ return false;
- return false;
+ return cancel_option (opt_idx, cl_options [next_opt_idx].neg_index,
+ orig_next_opt_idx);
}
/* Filter out options canceled by the ones after them. */
@@ -1088,14 +1089,6 @@ prune_options (struct cl_decoded_option **decoded_options,
default:
gcc_assert (opt_idx < cl_options_count);
option = &cl_options[opt_idx];
- if (option->neg_index < 0)
- goto keep;
-
- /* Skip joined switches. */
- if ((option->flags & CL_JOINED)
- && (!option->cl_reject_negative
- || (unsigned int) option->neg_index != opt_idx))
- goto keep;
for (j = i + 1; j < old_decoded_options_count; j++)
{
@@ -1104,13 +1097,6 @@ prune_options (struct cl_decoded_option **decoded_options,
next_opt_idx = old_decoded_options[j].opt_index;
if (next_opt_idx >= cl_options_count)
continue;
- if (cl_options[next_opt_idx].neg_index < 0)
- continue;
- if ((cl_options[next_opt_idx].flags & CL_JOINED)
- && (!cl_options[next_opt_idx].cl_reject_negative
- || ((unsigned int) cl_options[next_opt_idx].neg_index
- != next_opt_idx)))
- continue;
if (cancel_option (opt_idx, next_opt_idx, next_opt_idx))
break;
}
--
2.7.4
More information about the Gcc-patches
mailing list