This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [RFC] Dejagnu patch to handle multi-line directives


Tom de Vries <Tom_deVries@mentor.com> writes:
> [ attached patch ]
>
> On 06/10/2017 09:57 AM, Tom de Vries wrote:
>> Hi,
>> 
>> one thing that has bothered me on a regular basis is the inability to 
>> spread long dejagnu directives over multiple lines.
>> 
>> I've written a demonstrator patch (for the dejagnu sources) and tested 
>> it by splitting this 108 chars line:
>> ...
>> /* { dg-additional-options "-DSTACK_SIZE=[dg-effective-target-value 
>> stack_size]" { target { stack_size } } } */
>> ...
>> into:
>> ...
>> /* { dg-additional-options }
>>     { dg-dc "-DSTACK_SIZE=[dg-effective-target-value stack_size]" }
>>     { dg-dc { target { stack_size } } } */
>> ...
>> 
>> Good idea to fix this?
>> 
>> Good idea to fix this like this?
>> 
>> If so, any other comments, before I suggest this at dejagnu project?
>> 
>> Thanks,
>> - Tom
>> 
>
> Add dg-dc support
>
> ---
>  lib/dg.exp | 57 +++++++++++++++++++++++++++++++++++++++++++++++++++++----
>  1 file changed, 53 insertions(+), 4 deletions(-)
>
> diff --git a/lib/dg.exp b/lib/dg.exp
> index 7a894cb..67f46ab 100644
> --- a/lib/dg.exp
> +++ b/lib/dg.exp
> @@ -181,15 +181,64 @@ proc dg-format-linenum { linenum } {
>  # we return:
>  #
>  # { dg-prms-id 1 1234 } { dg-build 2 fatal "some comment" }
> +#
> +# Directive dg-dc (short for dg-directive-continue) can be used for multi-line
> +# directives.  This:
> +#
> +# /* { dg-x a b c } */
> +#
> +# is equivalent to:
> +#
> +# /* { dg-x } */
> +# /* { dg-dc a b } */
> +# /* { dg-dc c } */
> +#
> +# and to:
> +#
> +# /* { dg-x a } */
> +# /* { dg-dc b c} */
>  
>  proc dg-get-options { prog } {
>      set result ""
> -
> -    set tmp [grep $prog "{\[ \t\]\+dg-\[-a-z\]\+\[ \t\]\+.*\[ \t\]\+}" line]
> +    set cmd_prev ""
> +
> +    set grep_pattern [join {
> +	"{"
> +	"\[ \t\]\+"
> +	"dg-\[-a-z\]\+"
> +	"\[ \t\]\+"
> +	"(.*\[ \t\]\+)?"
> +	"}"
> +    } ""]
> +    set tmp [grep $prog $grep_pattern line]
>      if {![string match "" $tmp]} {
> +	set pattern [join {
> +	    "(\[0-9\]+)"
> +	    "\[ \t\]+"
> +	    "{"
> +	    "\[ \t\]+"
> +	    "(dg-\[-a-z\]+)"
> +	    "\[ \t\]+"
> +	    "((.*)\[ \t\]+)?"
> +	    "}"
> +	    "\[^\}\]*"
> +	    "(\n|$)"
> +	} ""]
>  	foreach i $tmp {
> -	    regexp "(\[0-9\]+)\[ \t\]+{\[ \t\]+(dg-\[-a-z\]+)\[ \t\]+(.*)\[ \t\]+}\[^\}\]*(\n|$)" $i i line cmd args
> -	    append result " { $cmd $line $args }"
> +	    regexp $pattern $i dummy line cmd ws_args args
> +	    if { "$cmd" == "dg-dc" } {
> +		set args_prev "$args_prev $args"
> +	    } else {
> +		if { "$cmd_prev" != "" } {
> +		    append result " { $cmd_prev $line_prev $args_prev }"
> +		}
> +		set cmd_prev $cmd
> +		set line_prev $line
> +		set args_prev "$args"
> +	    }
> +	}
> +	if { "$cmd_prev" != "" } {
> +	    append result " { $cmd_prev $line_prev $args_prev }"
>  	}
>      }
>      return $result

I realise there's probably more that can go wrong with it, but how
about instead treating unbalanced { ... } as a sign that the directive
continues to the next line?  This would allow:

/* { dg-additional-options
      "-DSTACK_SIZE=[dg-effective-target-value stack_size]"
      { target { stack_size } } } */

To support per-line comments we probably need to drop the characters
before the start column, as in:

! { dg-additional-options
!     "-DSTACK_SIZE=[dg-effective-target-value stack_size]"
!     { target { stack_size } } }

Only lightly tested.

Thanks,
Richard


--- utils.exp.1	2017-06-12 08:07:34.004143966 +0100
+++ utils.exp	2017-06-12 08:54:13.609875614 +0100
@@ -161,6 +161,8 @@
 #            second is the pattern,
 #            third are any options.
 #     Options: line  - puts line numbers of match in list
+#              tcl   - match trailing characters until a complete Tcl
+#                      script is read
 #
 proc grep { args } {
 
@@ -178,20 +180,51 @@
     } else {
 	set options ""
     }
+    set line_p [expr { [lsearch $options line] >= 0 }]
+    set tcl_p [expr { [lsearch $options tcl] >= 0 }]
 
     set i 0
     set fd [open $file r]
-    while { [gets $fd cur_line]>=0 } {
+    while { $i >= 0 && [gets $fd cur_line] >= 0 } {
 	incr i
-	if [regexp -- "$pattern" $cur_line match] {
-	    if ![string match "" $options] {
-		foreach opt $options {
-		    case $opt in {
-			"line" {
-			    lappend grep_out [concat $i $match]
+	if [regexp -indices -- "$pattern" $cur_line indices] {
+	    set line $i
+	    set start [lindex $indices 0]
+	    set end [lindex $indices 1]
+	    set match [string range $cur_line $start $end]
+	    if { $tcl_p } {
+		incr end
+		while { ![info complete $match] } {
+		    set next [string first "\}" $cur_line $end]
+		    if { $next >= 0 } {
+			append match [string range $cur_line $end $next]
+			set end [expr $next + 1]
+		    } else {
+			append match [string trimright \
+					  [string range $cur_line $end end]]
+			# Expect the same number of characters of indentation.
+			# If we don't get a line that we expect, still treat
+			# this as a match (by breaking), so that it gets
+			# reported where appropriate.
+			if { [gets $fd cur_line] < 0 } {
+			    break
 			}
+			incr i
+			if { [string length $cur_line] < $start } {
+			    break
+			}
+			set cur_line [string trimleft \
+					  [string range $cur_line $start end]]
+			if { [string is space $cur_line] } {
+			    break
+			}
+			append match " "
+			set end 0
 		    }
 		}
+	    }
+	    if { $line_p } {
+		lappend grep_out [concat $line $match]
 	    } else {
 		lappend grep_out $match
 	    }
--- dg.exp.1	2017-06-12 08:06:55.292935737 +0100
+++ dg.exp	2017-06-12 08:32:14.309351359 +0100
@@ -186,7 +186,7 @@
 proc dg-get-options { prog } {
     set result ""
 
-    set tmp [grep $prog "{\[ \t\]\+dg-\[-a-z\]\+\[ \t\]\+.*\[ \t\]\+}" line]
+    set tmp [grep $prog "\{\[ \t\]\+dg-\[-a-z\]\+\[ \t\]" line tcl]
     if ![string match "" $tmp] {
 	foreach i $tmp {
 	    #send_user "Found: $i\n"


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]