public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* [PATCH, MELT] add dominance functions
@ 2011-05-18 20:12 Pierre Vittet
  2011-05-19 10:28 ` Basile Starynkevitch
  0 siblings, 1 reply; 6+ messages in thread
From: Pierre Vittet @ 2011-05-18 20:12 UTC (permalink / raw)
  To: gcc-patches

[-- Attachment #1: Type: text/plain, Size: 1845 bytes --]

Hello,

I have written a patch to allow the use of the GCC dominance functions 
into MELT.

This is made in order to abstract the use of calculate_dominance_info 
and free_dominance_info:
     If the user use one of the MELT dominance related functions, it 
will only call calculate_dominance_info and register a call to 
free_dominance_info (at the end of the MELT pass) if the dominance info 
were not previously calculated.

The idea is :
     - dominance info were already calculated (in a previous pass):
         -we can use dominance info and at the end of pass, no call is 
made to free_dominance_info (as we expect a next pass to use dominance 
info and to free only when necessary).

     -dominance info were not already calculated:
         -We first compute dominance info, use them during the pass and 
free them at the end of the plugin pass (as we don't expect a next pass 
to use it).

Unsafe functions are only for internal use and so are not exported.

I have compiled GCC MELT with the patch and successfully test the functions.


Changelog:
2011-05-17  Pierre Vittet <piervit@pvittet.com>

     * melt/xtramelt-ana-base.melt
     (is_dominance_info_available, is_post_dominance_info_available,
     calculate_dominance_info_unsafe,
     calculate_post_dominance_info_unsafe,
     free_dominance_info, free_post_dominance_info,
     calculate_dominance_info,
     calculate_post_dominance_info, debug_dominance_info,
     debug_post_dominance_info, get_immediate_dominator_unsafe,
     get_immediate_dominator, get_immediate_post_dominator_unsafe,
     get_immediate_post_dominator, dominated_by_other_unsafe,
     dominated_by_other, post_dominated_by_other_unsafe,
     post_dominated_by_other, foreach_dominated_unsafe,
     dominated_by_bb_iterator): Add primitives, functions, iterators for
     using dominance info.



[-- Attachment #2: add_dominance_function.diff --]
[-- Type: text/plain, Size: 8956 bytes --]

Index: gcc/melt/xtramelt-ana-base.melt
===================================================================
--- gcc/melt/xtramelt-ana-base.melt	(revision 173832)
+++ gcc/melt/xtramelt-ana-base.melt	(working copy)
@@ -1910,6 +1910,242 @@
 (defprimitive basicblock_nth_succ_edge  (:basic_block bb :long ix) :edge
   #{(($bb && $ix>=0 && $ix<EDGE_COUNT($bb->succs))?EDGE_SUCC($bb,$ix):NULL)}#)
 
+;Primitives concerning dominance in basic_blocks
+;those functions mainly come from gcc/dominance.c
+
+(defprimitive is_dominance_info_available () :long
+  :doc #{Check if dominance info are already calculated.
+        User normally doesn't have to call this primitive, as MELT functions
+        check if there is a need to use this.
+        }#
+  #{dom_info_available_p(CDI_DOMINATORS)}#
+)
+
+(defprimitive is_post_dominance_info_available () :long
+  :doc #{Check if post dominance info are already calculated.
+        User normally doesn't have to call this primitive, as MELT functions
+        check if there is a need to use this.
+       }#
+  #{dom_info_available_p(CDI_POST_DOMINATORS)}#
+)
+
+(defprimitive calculate_dominance_info_unsafe() :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+    Build the struct containing dominance info.
+    This struct is necessary to use others dominance related function.
+    This function is unsafe because it does not register any future call to
+    free_dominance_info. 
+    }#
+  #{calculate_dominance_info(CDI_DOMINATORS)}#
+)
+
+(defprimitive calculate_post_dominance_info_unsafe () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+    Build the struct containing post dominance info.
+    This struct is necessary to use other dominance related function.
+    This function is unsafe because it does not register any future call to
+    free_dominance_info. 
+    }#
+  #{calculate_dominance_info(CDI_POST_DOMINATORS)}#
+)
+
+(defprimitive free_dominance_info () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+  Clear dominance info if they have been allocated.
+  }#
+  #{free_dominance_info(CDI_DOMINATORS)}#
+)
+
+(defprimitive free_post_dominance_info () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+  Clear post dominance info if they have been allocated.
+  }#
+  #{free_dominance_info(CDI_POST_DOMINATORS)}#
+)
+
+(defun calculate_dominance_info()
+  :doc #{This primitive is internaly called, user doesn't need it.
+  Build the struct containing dominance info.
+  This struct is necessary to use other dominance related info.
+  It place a call to free dominance info when pass is finished if it is
+  necessary.
+  }#
+  (if (is_dominance_info_available)
+    () ;; do nothing
+    (progn ;; else calculate dom and ask to free them at end of pass
+      (calculate_dominance_info_unsafe)
+      (at_end_melt_pass_first free_dominance_info)
+    ))
+)
+
+(defun calculate_post_dominance_info () 
+  :doc #{This primitive is internaly called, user doesn't need it
+  Build the struct containing post dominance info.
+  This struct is necessary to use other post dominance related info.
+  It place a call to free dominance info when pass is finished if it is
+  necessary.
+  }#
+  (if (is_post_dominance_info_available)
+    ()  ;; do nothing
+    (progn ;; else calculate dom and ask to free them at end of pass
+      (calculate_post_dominance_info)
+      (at_end_melt_pass_first free_post_dominance_info)
+    ))
+)
+
+(defun debug_dominance_info () 
+  :doc#{Print to stderr all dominance relation, in the format "bb1->bb2".}#
+  (calculate_dominance_info)
+  (each_bb_current_fun () (:basic_block curbb)
+    (let ( (:basic_block dombb (basicblock_content (get_immediate_dominator
+                                  (make_basicblock discr_basic_block curbb)))))
+      (if dombb 
+        (code_chunk debugpostdomchunk 
+        #{/*$DEBUGPOSTDOMCHUNK*/
+        fprintf (stderr, "%i dominated by %i\n", $CURBB->index, $DOMBB->index);
+        }#
+      ))
+    )
+  )
+)
+
+(defun debug_post_dominance_info ()
+  :doc#{Print to stderr all post dominance relation, in the format
+  "bb1->bb2".}#
+  (calculate_post_dominance_info) 
+  (each_bb_current_fun () (:basic_block curbb)
+    (let ( (:basic_block dombb (basicblock_content 
+              (get_immediate_post_dominator (make_basicblock discr_basic_block
+                                                                    curbb)))))
+      (if dombb 
+        (code_chunk debugpostdomchunk 
+        #{/*$DEBUGPOSTDOMCHUNK*/
+        fprintf (stderr, "%i dominated by %i\n", $CURBB->index, $DOMBB->index);
+        }#
+      ))
+    )
+  )
+)
+
+(defprimitive get_immediate_dominator_unsafe(:basic_block bb) :basic_block
+  :doc#{It doesn't check that dominance info are build, use
+    get_immediate_dominator instead.}#
+  #{($bb) ? get_immediate_dominator (CDI_DOMINATORS, $bb) : NULL}#
+)
+
+(defun get_immediate_dominator(bb) 
+ :doc#{Return the next immediate dominator of the basic_block $BB as a MELT
+value.}#
+  (if (is_basicblock bb)
+  (progn
+    (calculate_dominance_info) 
+    (return (make_basicblock discr_basic_block 
+      (get_immediate_dominator_unsafe (basicblock_content bb))))))
+)
+
+(defprimitive get_immediate_post_dominator_unsafe(:basic_block bb) :basic_block
+  :doc#{It doesn't check that post_dominance info are build, use
+    get_immediate_post_dominator instead.}#
+  #{($bb) ? get_immediate_dominator (CDI_POST_DOMINATORS, $bb) : NULL}#
+)
+
+(defun get_immediate_post_dominator(bb) 
+ :doc#{Return the next immediate post dominator of the basic_block $BB as a
+MELT value.}#
+ (if (is_basicblock bb)
+ (progn
+ (calculate_post_dominance_info) 
+  (return (make_basicblock discr_basic_block 
+    (get_immediate_post_dominator_unsafe (basicblock_content bb))))))
+)
+
+(defprimitive 
+  dominated_by_other_unsafe(:basic_block bbA :basic_block bbB) :long
+  :doc#{It doesn't check that dominance info are build, use
+    dominated_by_other instead.}#
+  #{ (($bbA) && ($bbB)) ?
+      dominated_by_p (CDI_DOMINATORS, $bbA, $bbB) 
+      : 0 
+  }#
+)
+
+(defun dominated_by_other(bbA bbB)
+  :doc#{true if basic_block $BBA is dominated by basic_block $BBB.}#
+  (if (and (is_basicblock bbA) (is_basicblock bbB))
+  (progn
+    (calculate_dominance_info) 
+    (if (dominated_by_other_unsafe (basicblock_content bbA) 
+                                   (basicblock_content bbB))
+      (return :true)
+    )))
+)
+
+(defprimitive 
+  post_dominated_by_other_unsafe(:basic_block bbA :basic_block bbB) :long
+  :doc#{It doesn't check that post_dominance info are build, use
+    post_dominated_by_other instead.}#
+  #{ (($bbA) && ($bbB)) ?
+      dominated_by_p (CDI_POST_DOMINATORS, $bbA, $bbB) 
+      : 0 
+  }#
+)
+
+(defun post_dominated_by_other(bbA bbB)
+  :doc#{true if basic_block $BBA is post dominated by basic_block BBB.}#
+  (if (and (is_basicblock bbA) (is_basicblock bbB))
+  (progn
+    (calculate_post_dominance_info) 
+    (if (post_dominated_by_other_unsafe (basicblock_content bbA) 
+                                   (basicblock_content bbB))
+      (return :true)
+    )))
+)
+
+(defciterator foreach_dominated_unsafe
+  (:basic_block dominator_bb)
+  ebbdomd
+  (:basic_block dominated_bb)
+  #{
+    /* $EBBDOMD before+ */
+
+    VEC (basic_block, heap)*  $EBBDOMD#_bbvec = 0;
+    unsigned int $EBBDOMD#_ix = 0;
+    basic_block $EBBDOMD#_bb = 0;
+
+    if($DOMINATOR_BB){
+      $EBBDOMD#_bbvec = get_dominated_by(CDI_DOMINATORS, $DOMINATOR_BB);
+      if($EBBDOMD#_bbvec){
+        FOR_EACH_VEC_ELT (basic_block, $EBBDOMD#_bbvec, 
+          $EBBDOMD#_ix, $EBBDOMD#_bb){
+          if (!$EBBDOMD#_ix)
+            continue;
+          $DOMINATED_BB = $EBBDOMD#_bb;
+     /*$EBBDOMD before- */}#
+      ;;after expansion
+  #{/*$EBBDOMD after+ */
+          }
+      }}
+    VEC_free (basic_block, heap, $EBBDOMD#_bbvec);
+    $EBBDOMD#_bbvec = 0;
+    $EBBDOMD#_bb = 0;
+    /* $EBBDOMD after- */}#
+)
+
+;;; 
+(defun dominated_by_bb_iterator (f data bb)
+  :doc #{run function $F on every basicblocks dominated by $BB with $DATA as
+  first parameters and ending with the dominated basicblock as last
+  parameters.
+  }#
+  (calculate_dominance_info)
+  (foreach_dominated_unsafe
+    ((basicblock_content bb))
+    (:basic_block dominated_bb)
+    (f data dominated_bb)
+  )
+)
+
+
 ;;;;
 (defprimitive null_gimpleseq () :gimple_seq #{((gimple_seq)0)}#)
 ;;;;;;;;;;;;;;;;
@@ -2931,6 +3167,17 @@ and discriminant $DIS, usually $DISCR_MIXED_LOCATI
  basicblock_nb_succ
  basicblock_phinodes
  basicblock_single_succ 
+ debug_dominance_info
+ debug_post_dominance_info
+ get_immediate_dominator
+ get_immediate_post_dominator
+ dominated_by_other
+ post_dominated_by_other
+ dominated_by_bb_iterator
+ get_immediate_dominator
+ get_immediate_post_dominator
+ dominated_by_other
+ post_dominated_by_other
  cfun_decl
  cfun_gimple_body
  cfun_has_cfg

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH, MELT] add dominance functions
  2011-05-18 20:12 [PATCH, MELT] add dominance functions Pierre Vittet
@ 2011-05-19 10:28 ` Basile Starynkevitch
  2011-05-20 11:47   ` Pierre Vittet
  0 siblings, 1 reply; 6+ messages in thread
From: Basile Starynkevitch @ 2011-05-19 10:28 UTC (permalink / raw)
  To: Pierre Vittet; +Cc: gcc-patches

On Wed, 18 May 2011 21:04:39 +0200
Pierre Vittet <piervit@pvittet.com> wrote:

> Hello,
> 
> I have written a patch to allow the use of the GCC dominance functions 
> into MELT.
[...]

> Changelog:
> 2011-05-17  Pierre Vittet <piervit@pvittet.com>
> 
>      * melt/xtramelt-ana-base.melt
>      (is_dominance_info_available, is_post_dominance_info_available,
>      calculate_dominance_info_unsafe,
>      calculate_post_dominance_info_unsafe,
>      free_dominance_info, free_post_dominance_info,
>      calculate_dominance_info,
>      calculate_post_dominance_info, debug_dominance_info,
>      debug_post_dominance_info, get_immediate_dominator_unsafe,
>      get_immediate_dominator, get_immediate_post_dominator_unsafe,
>      get_immediate_post_dominator, dominated_by_other_unsafe,
>      dominated_by_other, post_dominated_by_other_unsafe,
>      post_dominated_by_other, foreach_dominated_unsafe,
>      dominated_by_bb_iterator): Add primitives, functions, iterators for
>      using dominance info.
> 
> 

Thanks for the patch. Some minor tweaks:

First, put a space between formal arguments list & function name. 
So 

+(defprimitive calculate_dominance_info_unsafe() :void
should be
+(defprimitive calculate_dominance_info_unsafe () :void

Then, please put the defined name on the same line that defprimitive or
defun or def... When consecutive MELT formals have the same ctype, you
don't need to repeat it 

So

+(defprimitive 
+  dominated_by_other_unsafe(:basic_block bbA :basic_block bbB) :long

should be

+(defprimitive dominated_by_other_unsafe (:basic_block bbA bbB) :long

In :doc strings, document when something is a boxed value 
(distinction between values & stuffs is crucial), so write instead 
[I added the boxed word, it is important]

+(defun get_immediate_dominator (bb) 
+ :doc#{Return the next immediate dominator of the boxed basic_block
$BB as a MELT +value.}#

At last, all debug* operations should only output debug to stderr only
when flag_melt_debug is set and give the MELT source position (because
we don't want any debug printing in the usual case when -fmelt-debug is
not given to our cc1) Look at debugloop in xtramelt-ana-base.melt for
an example (notice that debugeprintfnonl is a C macro printing the MELT
source position.


So please resubmit a slightly improved patch.

Regards.
-- 
Basile STARYNKEVITCH         http://starynkevitch.net/Basile/
email: basile<at>starynkevitch<dot>net mobile: +33 6 8501 2359
8, rue de la Faiencerie, 92340 Bourg La Reine, France
*** opinions {are only mine, sont seulement les miennes} ***

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH, MELT] add dominance functions
  2011-05-19 10:28 ` Basile Starynkevitch
@ 2011-05-20 11:47   ` Pierre Vittet
  2011-05-20 14:09     ` Basile Starynkevitch
  0 siblings, 1 reply; 6+ messages in thread
From: Pierre Vittet @ 2011-05-20 11:47 UTC (permalink / raw)
  To: gcc-patches; +Cc: Basile Starynkevitch

[-- Attachment #1: Type: text/plain, Size: 4030 bytes --]

I have corrected my patch with your remarks.

Especially about the debug functions, it takes the debug melt flag into 
account. Moreover, I have allowed the user to give a message when 
calling this function, as usual in MELT debug functions. Giving this 
message was a bit difficult (This is the only argument of the function, 
so this must be a MELT value, and that uneasy to convert the value into 
:cstring).

I have used debugeprintf macro into a code_chunk to give the MELT file + 
line numbers, followed by a outstr_err, which displays the user message. 
I think the only disavantage is that it puts an end of lines between the 
two informations. If you think there is a best way to do this, I am ok 
to try it.

The new changelog:

2011-05-20  Pierre Vittet <piervit@pvittet.com>

     * melt/xtramelt-ana-base.melt
     (is_dominance_info_available, is_post_dominance_info_available,
     calculate_dominance_info_unsafe, calculate_post_dominance_info_unsafe,
     free_dominance_info, free_post_dominance_info, 
calculate_dominance_info,
     calculate_post_dominance_info, debug_dominance_info,
     debug_post_dominance_info, get_immediate_dominator_unsafe,
     get_immediate_dominator, get_immediate_post_dominator_unsafe,
     get_immediate_post_dominator, dominated_by_other_unsafe,
     dominated_by_other, post_dominated_by_other_unsafe,
     post_dominated_by_other, foreach_dominated_unsafe,
     dominated_by_bb_iterator): Add primitives, functions, iterators for 
using
     dominance info.


On 19/05/2011 07:32, Basile Starynkevitch wrote:
> On Wed, 18 May 2011 21:04:39 +0200
> Pierre Vittet<piervit@pvittet.com>  wrote:
>
>    
>> Hello,
>>
>> I have written a patch to allow the use of the GCC dominance functions
>> into MELT.
>>      
> [...]
>
>    
>> Changelog:
>> 2011-05-17  Pierre Vittet<piervit@pvittet.com>
>>
>>       * melt/xtramelt-ana-base.melt
>>       (is_dominance_info_available, is_post_dominance_info_available,
>>       calculate_dominance_info_unsafe,
>>       calculate_post_dominance_info_unsafe,
>>       free_dominance_info, free_post_dominance_info,
>>       calculate_dominance_info,
>>       calculate_post_dominance_info, debug_dominance_info,
>>       debug_post_dominance_info, get_immediate_dominator_unsafe,
>>       get_immediate_dominator, get_immediate_post_dominator_unsafe,
>>       get_immediate_post_dominator, dominated_by_other_unsafe,
>>       dominated_by_other, post_dominated_by_other_unsafe,
>>       post_dominated_by_other, foreach_dominated_unsafe,
>>       dominated_by_bb_iterator): Add primitives, functions, iterators for
>>       using dominance info.
>>
>>
>>      
> Thanks for the patch. Some minor tweaks:
>
> First, put a space between formal arguments list&  function name.
> So
>
> +(defprimitive calculate_dominance_info_unsafe() :void
> should be
> +(defprimitive calculate_dominance_info_unsafe () :void
>
> Then, please put the defined name on the same line that defprimitive or
> defun or def... When consecutive MELT formals have the same ctype, you
> don't need to repeat it
>
> So
>
> +(defprimitive
> +  dominated_by_other_unsafe(:basic_block bbA :basic_block bbB) :long
>
> should be
>
> +(defprimitive dominated_by_other_unsafe (:basic_block bbA bbB) :long
>
> In :doc strings, document when something is a boxed value
> (distinction between values&  stuffs is crucial), so write instead
> [I added the boxed word, it is important]
>
> +(defun get_immediate_dominator (bb)
> + :doc#{Return the next immediate dominator of the boxed basic_block
> $BB as a MELT +value.}#
>
> At last, all debug* operations should only output debug to stderr only
> when flag_melt_debug is set and give the MELT source position (because
> we don't want any debug printing in the usual case when -fmelt-debug is
> not given to our cc1) Look at debugloop in xtramelt-ana-base.melt for
> an example (notice that debugeprintfnonl is a C macro printing the MELT
> source position.
>
>
> So please resubmit a slightly improved patch.
>
> Regards.
>    


[-- Attachment #2: add_dominance_functions-173936.diff --]
[-- Type: text/plain, Size: 9775 bytes --]

Index: gcc/melt/xtramelt-ana-base.melt
===================================================================
--- gcc/melt/xtramelt-ana-base.melt	(revision 173936)
+++ gcc/melt/xtramelt-ana-base.melt	(working copy)
@@ -1871,7 +1871,6 @@
 (defprimitive make_basicblock (discr :basic_block bb) :value
  #{/*make_basicblock*/(meltgc_new_basicblock((meltobject_ptr_t)($discr),($bb)))}# )
 
-
 (defprimitive basicblock_content (v) :basic_block
  #{(melt_basicblock_content((melt_ptr_t)($v)))}# )
 
@@ -1910,6 +1909,243 @@
 (defprimitive basicblock_nth_succ_edge  (:basic_block bb :long ix) :edge
   #{(($bb && $ix>=0 && $ix<EDGE_COUNT($bb->succs))?EDGE_SUCC($bb,$ix):NULL)}#)
 
+;; Primitives concerning dominance in basic_blocks
+;; those functions mainly come from gcc/dominance.c
+
+(defprimitive is_dominance_info_available () :long
+  :doc #{Check if dominance info are already calculated.
+        User normally doesn't have to call this primitive, as MELT functions
+        check if there is a need to use this.}#
+  #{dom_info_available_p(CDI_DOMINATORS)}#
+)
+
+(defprimitive is_post_dominance_info_available () :long
+  :doc #{Check if post dominance info are already calculated.
+        User normally doesn't have to call this primitive, as MELT functions
+        check if there is a need to use this.}#
+  #{dom_info_available_p(CDI_POST_DOMINATORS)}#
+)
+
+(defprimitive calculate_dominance_info_unsafe () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+        Build the struct containing dominance info.
+        This struct is necessary to use others dominance related function.
+        This function is unsafe because it does not register any future call to
+        free_dominance_info.}#
+  #{calculate_dominance_info(CDI_DOMINATORS)}#
+)
+
+(defprimitive calculate_post_dominance_info_unsafe () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+        Build the struct containing post dominance info.
+        This struct is necessary to use other dominance related function.
+        This function is unsafe because it does not register any future call to
+        free_dominance_info.}#
+  #{calculate_dominance_info(CDI_POST_DOMINATORS)}#
+)
+
+(defprimitive free_dominance_info () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+        Clear dominance info if they have been allocated.}#
+  #{free_dominance_info(CDI_DOMINATORS)}#
+)
+
+(defprimitive free_post_dominance_info () :void
+  :doc #{This primitive is internaly called, user doesn't need it.
+    Clear post dominance info if they have been allocated.}#
+  #{free_dominance_info(CDI_POST_DOMINATORS)}#
+)
+
+(defun calculate_dominance_info ()
+  :doc #{This primitive is internaly called, user doesn't need it.
+      Build the struct containing dominance info.
+      This struct is necessary to use other dominance related info.
+      It place a call to free dominance info when pass is finished if it is
+      necessary.}#
+  (if (is_dominance_info_available)
+    () ;; do nothing
+    (progn ;; else calculate dom and ask to free them at end of pass
+      (calculate_dominance_info_unsafe)
+      (at_end_melt_pass_first free_dominance_info)
+    ))
+)
+
+(defun calculate_post_dominance_info () 
+  :doc #{This primitive is internaly called, user doesn't need it
+      Build the struct containing post dominance info.
+      This struct is necessary to use other post dominance related info.
+      It place a call to free dominance info when pass is finished if it is
+      necessary.}#
+  (if (is_post_dominance_info_available)
+    ()  ;; do nothing
+    (progn ;; else calculate dom and ask to free them at end of pass
+      (calculate_post_dominance_info_unsafe)
+      (at_end_melt_pass_first free_post_dominance_info)
+    ))
+)
+
+(defun debug_dominance_info (msg) 
+  :doc#{Print to stderr all dominance relation, in the format "bb1->bb2".}#
+  (calculate_dominance_info)
+    (code_chunk debugdomchunk #{
+      /*$DEBUGDOMCHUNK*/
+      debugeprintf("debugdominanceinfo: ");}#)
+      (outstr_err msg)
+  (each_bb_current_fun () (:basic_block curbb)
+    (let ((:basic_block dombb (basicblock_content (get_immediate_dominator
+                                  (make_basicblock discr_basic_block curbb)))))
+      (if dombb 
+        (code_chunk debugbbdomchunk 
+        #{
+        if (flag_melt_debug)
+          fprintf (stderr, "%i dominated by %i\n", $CURBB->index, 
+                                                   $DOMBB->index);
+        }#
+      ))
+    )
+  )
+)
+
+(defun debug_post_dominance_info (msg)
+  :doc#{Print to stderr all post dominance relation, in the format
+      "bb1 dominated_by bb2".}#
+  (calculate_post_dominance_info) 
+    (outstr_dbg msg)
+    (code_chunk debugpostdomchunk #{
+      /*$DEBUGPOSTDOMCHUNK*/
+      debugeprintf("debugpostdominanceinfo: ");}#)
+      (outstr_err msg)
+  (each_bb_current_fun () (:basic_block curbb)
+    (let ( (:basic_block dombb (basicblock_content 
+              (get_immediate_post_dominator (make_basicblock discr_basic_block
+                                                                    curbb)))))
+      (if dombb 
+        (code_chunk debugbbpostdomchunk 
+        #{
+        if(flag_melt_debug)
+          fprintf (stderr, "%i post-dominated by %i\n", $CURBB->index,
+                                                        $DOMBB->index);
+        }#
+      ))
+    )
+  )
+)
+
+(defprimitive get_immediate_dominator_unsafe (:basic_block bb) :basic_block
+  :doc#{It doesn't check that dominance info are build, use
+      get_immediate_dominator instead.}#
+  #{($bb) ? get_immediate_dominator (CDI_DOMINATORS, $bb) : NULL}#
+)
+
+(defun get_immediate_dominator (bb) 
+ :doc#{Return the next immediate dominator of the boxed basic_block $BB as a
+      MELT value.}#
+  (if (is_basicblock bb)
+  (progn
+    (calculate_dominance_info) 
+    (return (make_basicblock discr_basic_block 
+      (get_immediate_dominator_unsafe (basicblock_content bb))))))
+)
+
+(defprimitive get_immediate_post_dominator_unsafe (:basic_block bb) :basic_block
+  :doc#{It doesn't check that post_dominance info are build, use
+      get_immediate_post_dominator instead.}#
+  #{($bb) ? get_immediate_dominator (CDI_POST_DOMINATORS, $bb) : NULL}#
+)
+
+(defun get_immediate_post_dominator (bb)
+ :doc#{Return the next immediate post dominator of the boxed basic_block $BB as
+      a MELT value.}#
+ (if (is_basicblock bb)
+ (progn
+ (calculate_post_dominance_info) 
+  (return (make_basicblock discr_basic_block 
+    (get_immediate_post_dominator_unsafe (basicblock_content bb))))))
+)
+
+(defprimitive dominated_by_other_unsafe (:basic_block bbA bbB) :long
+  :doc#{It doesn't check that dominance info are build, use
+      dominated_by_other instead.}#
+  #{ (($bbA) && ($bbB)) ?
+      dominated_by_p (CDI_DOMINATORS, $bbA, $bbB) 
+      : 0 
+  }#
+)
+
+(defun dominated_by_other (bbA bbB)
+  :doc#{true if boxed basic_block $BBA is dominated by boxed basic_block $BBB.}#
+  (if (and (is_basicblock bbA) (is_basicblock bbB))
+  (progn
+    (calculate_dominance_info) 
+    (if (dominated_by_other_unsafe (basicblock_content bbA) 
+                                   (basicblock_content bbB))
+      (return :true)
+    )))
+)
+
+(defprimitive post_dominated_by_other_unsafe (:basic_block bbA bbB) :long
+  :doc#{It doesn't check that post_dominance info are build, use
+      post_dominated_by_other instead.}#
+  #{ (($bbA) && ($bbB)) ?
+      dominated_by_p (CDI_POST_DOMINATORS, $bbA, $bbB) 
+      : 0 
+  }#
+)
+
+(defun post_dominated_by_other (bbA bbB)
+  :doc#{true if boxed basic_block $BBA is post dominated by boxed basic_block
+      $BBB.}#
+  (if (and (is_basicblock bbA) (is_basicblock bbB))
+  (progn
+    (calculate_post_dominance_info) 
+    (if (post_dominated_by_other_unsafe (basicblock_content bbA) 
+                                   (basicblock_content bbB))
+      (return :true)
+    )))
+)
+
+(defciterator foreach_dominated_unsafe
+  (:basic_block dominator_bb)
+  ebbdomd
+  (:basic_block dominated_bb)
+  #{
+    /* $EBBDOMD before+ */
+
+    VEC (basic_block, heap)*  $EBBDOMD#_bbvec = 0;
+    unsigned int $EBBDOMD#_ix = 0;
+    basic_block $EBBDOMD#_bb = 0;
+
+    if($DOMINATOR_BB){
+      $EBBDOMD#_bbvec = get_dominated_by(CDI_DOMINATORS, $DOMINATOR_BB);
+      if($EBBDOMD#_bbvec){
+        FOR_EACH_VEC_ELT (basic_block, $EBBDOMD#_bbvec, 
+          $EBBDOMD#_ix, $EBBDOMD#_bb){
+          if (!$EBBDOMD#_ix)
+            continue;
+          $DOMINATED_BB = $EBBDOMD#_bb;
+     /*$EBBDOMD before- */}#
+      ;; after expansion
+  #{/*$EBBDOMD after+ */
+          }
+      }}
+    VEC_free (basic_block, heap, $EBBDOMD#_bbvec);
+    $EBBDOMD#_bbvec = 0;
+    $EBBDOMD#_bb = 0;
+    /* $EBBDOMD after- */}#
+)
+
+(defun dominated_by_bb_iterator (f data bb)
+  :doc #{run function $F on every basicblocks dominated by boxed basic_block
+      $BB with $DATA as first parameters and ending with the dominated
+      basicblock as last parameters.}#
+  (calculate_dominance_info)
+  (foreach_dominated_unsafe
+    ((basicblock_content bb))
+    (:basic_block dominated_bb)
+    (f data dominated_bb)
+  )
+)
+
 ;;;;
 (defprimitive null_gimpleseq () :gimple_seq #{((gimple_seq)0)}#)
 ;;;;;;;;;;;;;;;;
@@ -2931,6 +3167,17 @@ and discriminant $DIS, usually $DISCR_MIXED_LOCATI
  basicblock_nb_succ
  basicblock_phinodes
  basicblock_single_succ 
+ debug_dominance_info
+ debug_post_dominance_info
+ get_immediate_dominator
+ get_immediate_post_dominator
+ dominated_by_other
+ post_dominated_by_other
+ dominated_by_bb_iterator
+ get_immediate_dominator
+ get_immediate_post_dominator
+ dominated_by_other
+ post_dominated_by_other
  cfun_decl
  cfun_gimple_body
  cfun_has_cfg

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH, MELT] add dominance functions
  2011-05-20 11:47   ` Pierre Vittet
@ 2011-05-20 14:09     ` Basile Starynkevitch
  2011-05-22 18:01       ` Gerald Pfeifer
  0 siblings, 1 reply; 6+ messages in thread
From: Basile Starynkevitch @ 2011-05-20 14:09 UTC (permalink / raw)
  To: Pierre Vittet; +Cc: gcc-patches

On Fri, 20 May 2011 11:47:57 +0200
Pierre Vittet <piervit@pvittet.com> wrote:

> I have corrected my patch with your remarks.
> 
> Especially about the debug functions, it takes the debug melt flag into 
> account. Moreover, I have allowed the user to give a message when 
> calling this function, as usual in MELT debug functions. Giving this 
> message was a bit difficult (This is the only argument of the function, 
> so this must be a MELT value, and that uneasy to convert the value into 
> :cstring).
> 
> I have used debugeprintf macro into a code_chunk to give the MELT file + 
> line numbers, followed by a outstr_err, which displays the user message. 
> I think the only disavantage is that it puts an end of lines between the 
> two informations. If you think there is a best way to do this, I am ok 
> to try it.


Thanks. I've committed Pierre's patch with minor improvements
(simplification of debug_dominance_info) discussed by phone.
I also changed the spelling of internaly to internally! 
And I added Pierre's name as a contributor in the copyright notice of
xtramelt-ana-base.melt

Committed revision 173945.


By the way, I am quite happy of Pierre patches to the MELT branch. Is
this enough to get him a write access to GCC SVN (all legalese is
done)? I fear that to really get that write access, Pierre would also
need to have accepted patches to the trunk (i.e. that writing good
patches to a branch is not enough)... I still don't understand the
criteria to admit Pierre to the Write After Approval list of
maintainers with a write access to GCC SVN...

Regards
-- 
Basile STARYNKEVITCH         http://starynkevitch.net/Basile/
email: basile<at>starynkevitch<dot>net mobile: +33 6 8501 2359
8, rue de la Faiencerie, 92340 Bourg La Reine, France
*** opinions {are only mine, sont seulement les miennes} ***

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH, MELT] add dominance functions
  2011-05-20 14:09     ` Basile Starynkevitch
@ 2011-05-22 18:01       ` Gerald Pfeifer
  2011-05-22 18:49         ` Basile Starynkevitch
  0 siblings, 1 reply; 6+ messages in thread
From: Gerald Pfeifer @ 2011-05-22 18:01 UTC (permalink / raw)
  To: Basile Starynkevitch; +Cc: Pierre Vittet, gcc-patches

On Fri, 20 May 2011, Basile Starynkevitch wrote:
> By the way, I am quite happy of Pierre patches to the MELT branch. Is 
> this enough to get him a write access to GCC SVN (all legalese is done)? 
> I fear that to really get that write access, Pierre would also need to 
> have accepted patches to the trunk (i.e. that writing good patches to a 
> branch is not enough)... I still don't understand the criteria to admit 
> Pierre to the Write After Approval list of maintainers with a write 
> access to GCC SVN...

This indeed is a bit of an unusual situation.  Are you planning to,
realistically, merge the MELT branch into mainline at one point?

In any case, let's do this:  once ten, twelve patches by Pierre have
been applied (regardless where) request an account and put me in as 
approved.

Gerald

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH, MELT] add dominance functions
  2011-05-22 18:01       ` Gerald Pfeifer
@ 2011-05-22 18:49         ` Basile Starynkevitch
  0 siblings, 0 replies; 6+ messages in thread
From: Basile Starynkevitch @ 2011-05-22 18:49 UTC (permalink / raw)
  To: Gerald Pfeifer; +Cc: Pierre Vittet, gcc-patches

On Sun, 22 May 2011 15:24:30 +0200 (CEST)
Gerald Pfeifer <gerald@pfeifer.com> wrote:

> On Fri, 20 May 2011, Basile Starynkevitch wrote:
> > By the way, I am quite happy of Pierre patches to the MELT branch. Is 
> > this enough to get him a write access to GCC SVN (all legalese is done)? 
> > I fear that to really get that write access, Pierre would also need to 
> > have accepted patches to the trunk (i.e. that writing good patches to a 
> > branch is not enough)... I still don't understand the criteria to admit 
> > Pierre to the Write After Approval list of maintainers with a write 
> > access to GCC SVN...
> 
> This indeed is a bit of an unusual situation.  Are you planning to,
> realistically, merge the MELT branch into mainline at one point?

I am dreaming of either merging MELT into mainline, or at least having
it be an essential GCC plugin distributed with GCC.... (ideally, I
would prefer MELT to be merged, because that would give it more
visibility). 

But I don't know how realistic is that dream. And I even don't know how
to make it happen. (The main issue being: who will review a 60KLOC
patch, most of it being in a "bizarre" language, MELT itself??)

As I told in informal discussions at some GCC Summits, I feel that MELT
is or may become a bit like the tree-browser.c : something useful
enough to some people to be integrated into mainline, even if most GCC
users don't even know about that functionality, and don't care or use
it when compiling their software. I am quite sure that 99% of GCC users
don't need or know about tree-browser.c and could use GCC with the
tree-browser disabled! I believe it could be the same for MELT: it
would be useful to a small fraction of users, but to them it would
bring enough value.

I am believing that Pierre's work can indeed attract much more attention
to MELT, because it shows very well MELT's interest: providing a
higher-level formalism which makes possible extra features (e.g.
specific warnings, in Pierre's GSOC work case) which would not be
realistically or economically possible without MELT.


The point is that MELT is usually quite near to the mainline: we
carefully avoid adding things into MELT which make MELT incompatible
with the mainline (unless we believe it shows a feature which should be
accepted), because we strongly want MELT to be either compilable as a
branch or as a plugin (to the next GCC release).

To be more specific, the difference between MELT (as a branch) and the
trunk are two lines in gengtype.c, a few lines in toplevel.c, some
additional options & parameters (common.opt, params.def), and the whole
MELT infrastructure (melt-runtime.[ch], melt/generated/*, melt/*) which
is by default disabled. So the behavior of the MELT branch when no MELT
specific program options are given is exactly the behavior of the trunk
(which was last merged into MELT). This is done on purpose, because
MELT can also be built and used as a GCC plugin, so its behavior is
"plugin-like": unless enabled (by options -fmelt*), MELT branch does
exactly what the trunk do. And even when required by -fmelt* arguments
to cc1, MELT branch behavior is exactly that of the melt.so plugin
(except that arguments which are -fmelt* to the MELT branch becomes
-fplugin-arg-melt-* arguments for -fplugin=melt). Internally, the MELT
branch registers a pseudo builtin/MELT plugin and uses the plugin hooks
(only when enabled).

The distributed MELT plugin is made of files extracted from the MELT
branch: the melt.so plugin is obtained by compiling melt-runtime.c as a
plugin...

Regards.

PS. I surely don't want to start a useless flamewar...
-- 
Basile STARYNKEVITCH         http://starynkevitch.net/Basile/
email: basile<at>starynkevitch<dot>net mobile: +33 6 8501 2359
8, rue de la Faiencerie, 92340 Bourg La Reine, France
*** opinions {are only mine, sont seulement les miennes} ***

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2011-05-22 15:27 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-05-18 20:12 [PATCH, MELT] add dominance functions Pierre Vittet
2011-05-19 10:28 ` Basile Starynkevitch
2011-05-20 11:47   ` Pierre Vittet
2011-05-20 14:09     ` Basile Starynkevitch
2011-05-22 18:01       ` Gerald Pfeifer
2011-05-22 18:49         ` Basile Starynkevitch

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).