whereis asm_nodes? how to migrate it for GCC v6.x?

2017-07-05 Thread Leslie Zhai

Hi GCC developers,

There was

extern GTY(()) struct asm_node *asm_nodes;

for GCC v4.x, but how to migrate it for v6.x? there is no asm_nodes 
deprecated log in ChangeLog-201X nor git log cgraph.h... please give me 
some hint, thanks a lot!


--
Regards,
Leslie Zhai https://reviews.llvm.org/p/xiangzhai/





Re: whereis asm_nodes? how to migrate it for GCC v6.x?

2017-07-06 Thread Leslie Zhai

Hi Segher,

Thanks for your kind response!

在 2017年07月05日 18:52, Segher Boessenkool 写道:

Hi Leslie,

On Wed, Jul 05, 2017 at 05:36:15PM +0800, Leslie Zhai wrote:

There was

extern GTY(()) struct asm_node *asm_nodes;

for GCC v4.x, but how to migrate it for v6.x? there is no asm_nodes
deprecated log in ChangeLog-201X nor git log cgraph.h... please give me
some hint, thanks a lot!

symtab->first_asm_symbol ?

yes! works for me :) such as:
for (pa = symtab->first_asm_symbol (); pa; pa = pa->next)...





Segher


--
Regards,
Leslie Zhai https://reviews.llvm.org/p/xiangzhai/





How to migrate TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts for GCC v6.x?

2017-07-06 Thread Leslie Zhai

Hi GCC developers,

As ChangeLog-2014 mentioned, tree-pass.h (TODO_verify_ssa, 
TODO_verify_flow, TODO_verify_stmts...): Remove.


When I am trying to migrate:


static struct rtl_opt_pass pass_rtl_emit_function = { {
  RTL_PASS, "rtl_emit_function", /* name */
#if (GCC_MINOR >= 8)
  OPTGROUP_NONE, /* optinfo_flags */
#endif
  NULL,  /* gate */
  rtl_emit_function, /* execute */
  NULL,  /* sub */
  NULL,  /* next */
  0, /* static_pass_number */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts
} };


to GCC v6.x


const pass_data pass_data_rtl_emit_function = {
  RTL_PASS,  /* type */
  "rtl_emit_function",   /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  0, /* todo_flags_start */
  TODO_df_finish,/* todo_flags_finish */
};

class pass_rtl_emit_function : public rtl_opt_pass {
public:
  pass_rtl_emit_function(gcc::context *ctxt)
  : rtl_opt_pass(pass_data_rtl_emit_function, ctxt) {}

  virtual unsigned int execute(function *) { return rtl_emit_function(); }
};


I have no idea how to choose the todo_flags_XXX, please give me some 
hint, thanks a lot!


--
Regards,
Leslie Zhai https://reviews.llvm.org/p/xiangzhai/





Re: How to migrate TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts for GCC v6.x?

2017-07-06 Thread Leslie Zhai



在 2017年07月06日 17:02, Leslie Zhai 写道:

Hi GCC developers,

As ChangeLog-2014 mentioned, tree-pass.h (TODO_verify_ssa, 
TODO_verify_flow, TODO_verify_stmts...): Remove.


When I am trying to migrate:


static struct rtl_opt_pass pass_rtl_emit_function = { {
  RTL_PASS, "rtl_emit_function", /* name */
#if (GCC_MINOR >= 8)
  OPTGROUP_NONE, /* optinfo_flags */
#endif
  NULL,  /* gate */
  rtl_emit_function, /* execute */
  NULL,  /* sub */
  NULL,  /* next */
  0, /* static_pass_number */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts
} };


to GCC v6.x


const pass_data pass_data_rtl_emit_function = {
  RTL_PASS,  /* type */
  "rtl_emit_function",   /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  0, /* todo_flags_start */
  TODO_df_finish,/* todo_flags_finish */

Just 0

because const pass_data pass_data_dse migrate the todo_flags as 
https://github.com/gcc-mirror/gcc/blob/master/gcc/tree-ssa-dse.c#L818





};

class pass_rtl_emit_function : public rtl_opt_pass {
public:
  pass_rtl_emit_function(gcc::context *ctxt)
  : rtl_opt_pass(pass_data_rtl_emit_function, ctxt) {}

  virtual unsigned int execute(function *) { return 
rtl_emit_function(); }

};


I have no idea how to choose the todo_flags_XXX, please give me some 
hint, thanks a lot!




--
Regards,
Leslie Zhai https://reviews.llvm.org/p/xiangzhai/





whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-08 Thread Leslie Zhai

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to migrate it 
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES deprecated log in 
ChangeLog-201X nor git log plugin.h... please give me some hint, thanks 
a lot!


--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/






gengtype not support #if (GCC_MAJOR < 6)? how to support both for GCC v4.x and v6.x?

2017-07-10 Thread Leslie Zhai

Hi GCC developers,

As ChangeLog-2014 mentioned: Remove support for if_marked and param_is 
about ggc, so I migrate to GCC v6.x, for example:



#if (GCC_MAJOR < 6)
// FIXME: gengtype not support macro?
//static GTY((if_marked("tree2int_marked_p"), param_is(struct tree2int)))
//htab_t intCache;
#else
struct intCacheHasher : ggc_cache_ptr_hash {
  static inline hashval_t hash(tree2int *t2i) {
return tree_map_base_hash(t2i->base);
}

  static inline bool equal(tree2int *a, tree2int *b) {
return a->base.from == b->base.from;
}

  static int keep_cache_entry(tree2int *&t2i) {
return ggc_marked_p(t2i->base.from);
}
};
static GTY((cache))
hash_table *intCache;
#endif


$ gcc-6.3.0/build/gcc/build/gengtype -r gcc-6.3.0/build/gcc/gtype.state 
-P /tmp/gt-cache-6.3.inc Input.cpp


but it still parse the deprecated if_marked and param_is for GCC v4.x, 
please give me some hint, thanks a lot!


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-10 Thread Leslie Zhai

Hi David,

Thanks for your kind response!


在 2017年07月10日 22:16, David Malcolm 写道:

On Sat, 2017-07-08 at 15:50 +0800, Leslie Zhai wrote:

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to migrate
it
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES deprecated log
in
ChangeLog-201X nor git log plugin.h... please give me some hint,
thanks
a lot!

Trevor [CCed] removed it 2014-12-10 in r218558
(eb06b2519a361b7784b1807115fcb3dea0226035) in the commit:
"remove gengtype support for param_is use_param, if_marked and splay
tree allocators"

The patch was here:
   https://gcc.gnu.org/ml/gcc-patches/2014-11/msg02965.html

where he talks about plugin migration.

Hope this is helpful

yes, it is very helpful :) thank you very much!


Dave


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/






Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-10 Thread Leslie Zhai



在 2017年07月10日 22:16, David Malcolm 写道:

On Sat, 2017-07-08 at 15:50 +0800, Leslie Zhai wrote:

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to migrate
it
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES deprecated log
in
ChangeLog-201X nor git log plugin.h... please give me some hint,
thanks
a lot!

Trevor [CCed] removed it 2014-12-10 in r218558
(eb06b2519a361b7784b1807115fcb3dea0226035) in the commit:
"remove gengtype support for param_is use_param, if_marked and splay
tree allocators"

The patch was here:
   https://gcc.gnu.org/ml/gcc-patches/2014-11/msg02965.html

where he talks about plugin migration.
 Some plugins may need to add extra GGC root tables, e.g. to handle 
their own
 @code{GTY}-ed data. This can be done with the 
@code{PLUGIN_REGISTER_GGC_ROOTS}
 pseudo-event with a null callback and the extra root table (of type 
@code{struct

-ggc_root_tab*}) as @code{user_data}.  Plugins that want to use the
-@code{if_marked} hash table option can add the extra GGC cache tables 
generated
-by @code{gengtype} using the @code{PLUGIN_REGISTER_GGC_CACHES} 
pseudo-event with
-a null callback and the extra cache table (of type @code{struct 
ggc_cache_tab*})

-as @code{user_data}.  Running the @code{gengtype -p @var{source-dir}
-@var{file-list} @var{plugin*.c} ...} utility generates these extra root 
tables.

+ggc_root_tab*}) as @code{user_data}.  Running the
+ @code{gengtype -p @var{source-dir} @var{file-list} @var{plugin*.c} ...}
+utility generates these extra root tables.


After diff gcc-6.3.0/gcc/testsuite/gcc.dg/plugin and 
gcc-4.8.0/gcc/testsuite/gcc.dg/plugin

then migrate to GCC v6.x like this:


// Register our garbage collector roots.
#if GCC_MAJOR < 6
  register_callback(plugin_name, PLUGIN_REGISTER_GGC_CACHES, NULL,
#else
  register_callback(plugin_name, PLUGIN_REGISTER_GGC_ROOTS, NULL,
#endif
const_cast(gt_ggc_rc__gt_cache_h));


and Trevor talks more about GTY((if_marked(XXX), param_is(XXX))) htab_t 
migrate to GTY((cache)) hash_table such as:



#if (GCC_MAJOR < 6)
// FIXME: gengtype not support macro?
static GTY((if_marked("tree2int_marked_p"), param_is(struct tree2int)))
htab_t intCache;
#else
struct intCacheHasher : ggc_cache_ptr_hash {
  static inline hashval_t hash(tree2int *t2i) {
return tree_map_base_hash(&t2i->base);
}

  static inline bool equal(tree2int *a, tree2int *b) {
return a->base.from == b->base.from;
}
};
static GTY((cache))
hash_table *intCache;
#endif


But I have no idea why gengtype does not support macro? 
https://gcc.gnu.org/ml/gcc/2017-07/msg00045.html it just ignored #if 
(GCC_MAJOR < 6) still parse GTY((if_marked(XXX), param_is(XXX))) htab_t 
but not GTY((cache)) hash_table... please give me some hint, 
thanks a lot!




Hope this is helpful
Dave


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-11 Thread Leslie Zhai

Hi David,

Thanks for your kind response!


在 2017年07月11日 21:25, David Malcolm 写道:

On Tue, 2017-07-11 at 10:50 +0800, Leslie Zhai wrote:

在 2017年07月10日 22:16, David Malcolm 写道:

On Sat, 2017-07-08 at 15:50 +0800, Leslie Zhai wrote:

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to
migrate
it
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES deprecated
log
in
ChangeLog-201X nor git log plugin.h... please give me some hint,
thanks
a lot!

Trevor [CCed] removed it 2014-12-10 in r218558
(eb06b2519a361b7784b1807115fcb3dea0226035) in the commit:
"remove gengtype support for param_is use_param, if_marked and
splay
tree allocators"

The patch was here:
https://gcc.gnu.org/ml/gcc-patches/2014-11/msg02965.html

where he talks about plugin migration.

   Some plugins may need to add extra GGC root tables, e.g. to handle
their own
   @code{GTY}-ed data. This can be done with the
@code{PLUGIN_REGISTER_GGC_ROOTS}
   pseudo-event with a null callback and the extra root table (of type
@code{struct
-ggc_root_tab*}) as @code{user_data}.  Plugins that want to use the
-@code{if_marked} hash table option can add the extra GGC cache
tables
generated
-by @code{gengtype} using the @code{PLUGIN_REGISTER_GGC_CACHES}
pseudo-event with
-a null callback and the extra cache table (of type @code{struct
ggc_cache_tab*})
-as @code{user_data}.  Running the @code{gengtype -p @var{source-dir}
-@var{file-list} @var{plugin*.c} ...} utility generates these extra
root
tables.
+ggc_root_tab*}) as @code{user_data}.  Running the
+ @code{gengtype -p @var{source-dir} @var{file-list} @var{plugin*.c}
...}
+utility generates these extra root tables.


After diff gcc-6.3.0/gcc/testsuite/gcc.dg/plugin and
gcc-4.8.0/gcc/testsuite/gcc.dg/plugin
then migrate to GCC v6.x like this:


// Register our garbage collector roots.
#if GCC_MAJOR < 6
register_callback(plugin_name, PLUGIN_REGISTER_GGC_CACHES, NULL,
#else
register_callback(plugin_name, PLUGIN_REGISTER_GGC_ROOTS, NULL,
#endif
  const_cast(gt_ggc_rc__gt_cache_h));


and Trevor talks more about GTY((if_marked(XXX), param_is(XXX)))
htab_t
migrate to GTY((cache)) hash_table such as:


#if (GCC_MAJOR < 6)
// FIXME: gengtype not support macro?
static GTY((if_marked("tree2int_marked_p"), param_is(struct
tree2int)))
  htab_t intCache;
#else
struct intCacheHasher : ggc_cache_ptr_hash {
static inline hashval_t hash(tree2int *t2i) {
  return tree_map_base_hash(&t2i->base);
}

static inline bool equal(tree2int *a, tree2int *b) {
  return a->base.from == b->base.from;
}
};
static GTY((cache))
  hash_table *intCache;
#endif


But I have no idea why gengtype does not support macro?
https://gcc.gnu.org/ml/gcc/2017-07/msg00045.html it just ignored #if
(GCC_MAJOR < 6) still parse GTY((if_marked(XXX), param_is(XXX)))
htab_t
but not GTY((cache)) hash_table... please give me some
hint,
thanks a lot!

Unfortunately, gengtype is not a full parser for all of C++; IIRC it
doesn't have any real support for the preprocessor.

Maybe you can work around it in your plugin by providing two different
headers, one for GCC_MAJOR < 6, the other for >= 6, and setting up the
build so that gengtype is invoked on the correct header.  (I know this
is ugly, sorry).

Alternatively, maybe there's another way to solve this by rethinking
the data structure.  It seems like you have a hash table of some kind.
  Does the hash table "own" references to other GC-managed entities, or
is it simply referenced *by* other GC-managed entities.  Maybe there's
I am migrating dragonegg to GCC v6.3 and LLVM v3.9, at first it needs to 
be built successfully, no warning is better :) but I only migrated part 
of it, for example: Caching values in GCC trees right now 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Cache.cpp 
and the relationship might be: GTY((cache)) hash_table 
*intCache <- Cache::setCachedInteger <- TypeConversion::set_decl_index...
When I finished the migration, with the whole view, then I need to 
rethink the data structure as you suggested.


PS: Trevor's email is not available? thanks!



another way to represent this data which would sidestep the issue.  (I
don't know, I'm just speculating).

Hope this is helpful
Dave


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-18 Thread Leslie Zhai

Hi Trevor,

Thanks for your kind response!

在 2017年07月17日 19:51, Trevor Saunders 写道:

On Wed, Jul 12, 2017 at 10:12:03AM +0800, Leslie Zhai wrote:

PS: Trevor's email is not available? thanks!

Sorry about that, I've left Mozilla and been vacationing for a month, so
didn't get to updating MAINTAINERS yet.  Here's a patch doing that.
Could I use PLUGIN_REGISTER_GGC_ROOTS to take place of 
PLUGIN_REGISTER_GGC_CACHES? https://gcc.gnu.org/ml/gcc/2017-07/msg00052.html




Trev

commit ff900f40d23f765fd59047a90a7e3ff18cbcbf5a
Author: Trevor Saunders 
Date:   Mon Jul 17 07:44:50 2017 -0400

 update my entry in MAINTAINERS
 
 ChangeLog:
 
 * MAINTAINERS: Update my email address.


diff --git a/MAINTAINERS b/MAINTAINERS
index a2f24742374..6a314049c42 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -557,7 +557,7 @@ Hariharan Sandanagobalane   

  Iain Sandoe   
  Duncan Sands  
  Sujoy Saraswati   

-Trevor Saunders
+Trevor Saunders

  Aaron Sawdey  
  Roger Sayle   
  Will Schmidt  


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-18 Thread Leslie Zhai



在 2017年07月19日 04:54, Trevor Saunders 写道:

On Tue, Jul 18, 2017 at 03:52:55PM +0800, Leslie Zhai wrote:

Hi Trevor,

Thanks for your kind response!

在 2017年07月17日 19:51, Trevor Saunders 写道:

On Wed, Jul 12, 2017 at 10:12:03AM +0800, Leslie Zhai wrote:

PS: Trevor's email is not available? thanks!

Sorry about that, I've left Mozilla and been vacationing for a month, so
didn't get to updating MAINTAINERS yet.  Here's a patch doing that.

Could I use PLUGIN_REGISTER_GGC_ROOTS to take place of
PLUGIN_REGISTER_GGC_CACHES? https://gcc.gnu.org/ml/gcc/2017-07/msg00052.html

If you are ok with your plugin keeping things alive that would otherwise
be garbage collected because they are no longer needed sure I think that
will work.  Though some things are ggc_free()ed and so you might want to
be careful touching those things that should be collected but you are
keeping alive.  Does that help?

Very helpful :) thank you so much!




Trev


Trev

commit ff900f40d23f765fd59047a90a7e3ff18cbcbf5a
Author: Trevor Saunders 
Date:   Mon Jul 17 07:44:50 2017 -0400

  update my entry in MAINTAINERS
  ChangeLog:
  * MAINTAINERS: Update my email address.

diff --git a/MAINTAINERS b/MAINTAINERS
index a2f24742374..6a314049c42 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -557,7 +557,7 @@ Hariharan Sandanagobalane   

   Iain Sandoe  
   Duncan Sands 
   Sujoy Saraswati  

-Trevor Saunders
+Trevor Saunders

   Aaron Sawdey 
   Roger Sayle  
   Will Schmidt     

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-26 Thread Leslie Zhai



在 2017年07月11日 21:25, David Malcolm 写道:

On Tue, 2017-07-11 at 10:50 +0800, Leslie Zhai wrote:

在 2017年07月10日 22:16, David Malcolm 写道:

On Sat, 2017-07-08 at 15:50 +0800, Leslie Zhai wrote:

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to
migrate
it
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES deprecated
log
in
ChangeLog-201X nor git log plugin.h... please give me some hint,
thanks
a lot!

Trevor [CCed] removed it 2014-12-10 in r218558
(eb06b2519a361b7784b1807115fcb3dea0226035) in the commit:
"remove gengtype support for param_is use_param, if_marked and
splay
tree allocators"

The patch was here:
https://gcc.gnu.org/ml/gcc-patches/2014-11/msg02965.html

where he talks about plugin migration.

   Some plugins may need to add extra GGC root tables, e.g. to handle
their own
   @code{GTY}-ed data. This can be done with the
@code{PLUGIN_REGISTER_GGC_ROOTS}
   pseudo-event with a null callback and the extra root table (of type
@code{struct
-ggc_root_tab*}) as @code{user_data}.  Plugins that want to use the
-@code{if_marked} hash table option can add the extra GGC cache
tables
generated
-by @code{gengtype} using the @code{PLUGIN_REGISTER_GGC_CACHES}
pseudo-event with
-a null callback and the extra cache table (of type @code{struct
ggc_cache_tab*})
-as @code{user_data}.  Running the @code{gengtype -p @var{source-dir}
-@var{file-list} @var{plugin*.c} ...} utility generates these extra
root
tables.
+ggc_root_tab*}) as @code{user_data}.  Running the
+ @code{gengtype -p @var{source-dir} @var{file-list} @var{plugin*.c}
...}
+utility generates these extra root tables.


After diff gcc-6.3.0/gcc/testsuite/gcc.dg/plugin and
gcc-4.8.0/gcc/testsuite/gcc.dg/plugin
then migrate to GCC v6.x like this:


// Register our garbage collector roots.
#if GCC_MAJOR < 6
register_callback(plugin_name, PLUGIN_REGISTER_GGC_CACHES, NULL,
#else
register_callback(plugin_name, PLUGIN_REGISTER_GGC_ROOTS, NULL,
#endif
  const_cast(gt_ggc_rc__gt_cache_h));


and Trevor talks more about GTY((if_marked(XXX), param_is(XXX)))
htab_t
migrate to GTY((cache)) hash_table such as:


#if (GCC_MAJOR < 6)
// FIXME: gengtype not support macro?
static GTY((if_marked("tree2int_marked_p"), param_is(struct
tree2int)))
  htab_t intCache;
#else
struct intCacheHasher : ggc_cache_ptr_hash {
static inline hashval_t hash(tree2int *t2i) {
  return tree_map_base_hash(&t2i->base);
}

static inline bool equal(tree2int *a, tree2int *b) {
  return a->base.from == b->base.from;
}
};
static GTY((cache))
  hash_table *intCache;
#endif


But I have no idea why gengtype does not support macro?
https://gcc.gnu.org/ml/gcc/2017-07/msg00045.html it just ignored #if
(GCC_MAJOR < 6) still parse GTY((if_marked(XXX), param_is(XXX)))
htab_t
but not GTY((cache)) hash_table... please give me some
hint,
thanks a lot!

Unfortunately, gengtype is not a full parser for all of C++; IIRC it
doesn't have any real support for the preprocessor.

Maybe you can work around it in your plugin by providing two different
headers, one for GCC_MAJOR < 6, the other for >= 6, and setting up the
build so that gengtype is invoked on the correct header.  (I know this
is ugly, sorry).


Right now I am using two different files: such as Cache4.cpp and 
Cache6.cpp, and there is the same `struct GTY(()) tree2WeakVH` for GCC 
v4.x 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Cache4.cpp#L99 
also for GCC v6.x 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Cache6.cpp#L116


then gengtype auto-generated `struct ggc_root_tab` with Cache6.cpp for 
GCC v6.x 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/include/dragonegg/gt-cache-6.3.inc#L1257 
it is of course different with Cache4.cpp for GCC v4.x 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/include/dragonegg/gt-cache-4.6.inc#L970


$ gcc -fplugin=/usr/lib64/dragonegg.so hello.c
cc1: error: cannot load plugin /usr/lib64/dragonegg.so
   /usr/lib64/dragonegg.so: undefined symbol: _Z9gt_ggc_mxRP11tree2WeakVH

it is my fault! the symbol `_Z9gt_ggc_mxRP11tree2WeakVH` looks like for 
GCC v4.x, so I migrated the plugin to GCC v6.x wrongly? 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2662 
please give me some hint, thanks a lot!





Alternatively, maybe there's another way to solve this by rethinking
the data structure.  It seems like you have a hash table of some kind.
  Does the hash table "own" references to other GC-managed entities, or
is it simply referenced *by* other GC-managed entities.  Maybe there's
another way to represent this data which would sidestep the issue.  (I
don't know, I'm just speculating).

Hope this is helpful
Dave


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/
�




Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-26 Thread Leslie Zhai

Hi David,

Thanks for your kind response!


在 2017年07月26日 21:43, David Malcolm 写道:

On Wed, 2017-07-26 at 15:19 +0800, Leslie Zhai wrote:

在 2017年07月11日 21:25, David Malcolm 写道:

On Tue, 2017-07-11 at 10:50 +0800, Leslie Zhai wrote:

在 2017年07月10日 22:16, David Malcolm 写道:

On Sat, 2017-07-08 at 15:50 +0800, Leslie Zhai wrote:

Hi GCC developers,

There was

PLUGIN_REGISTER_GGC_CACHES

pseudo-events for register_callback in GCC v4.x, but how to
migrate
it
for GCC v6.x? there is no  PLUGIN_REGISTER_GGC_CACHES
deprecated
log
in
ChangeLog-201X nor git log plugin.h... please give me some
hint,
thanks
a lot!

Trevor [CCed] removed it 2014-12-10 in r218558
(eb06b2519a361b7784b1807115fcb3dea0226035) in the commit:
"remove gengtype support for param_is use_param, if_marked and
splay
tree allocators"

The patch was here:
 https://gcc.gnu.org/ml/gcc-patches/2014-11/msg02965.html

where he talks about plugin migration.

Some plugins may need to add extra GGC root tables, e.g. to
handle
their own
@code{GTY}-ed data. This can be done with the
@code{PLUGIN_REGISTER_GGC_ROOTS}
pseudo-event with a null callback and the extra root table (of
type
@code{struct
-ggc_root_tab*}) as @code{user_data}.  Plugins that want to use
the
-@code{if_marked} hash table option can add the extra GGC cache
tables
generated
-by @code{gengtype} using the @code{PLUGIN_REGISTER_GGC_CACHES}
pseudo-event with
-a null callback and the extra cache table (of type @code{struct
ggc_cache_tab*})
-as @code{user_data}.  Running the @code{gengtype -p @var{source
-dir}
-@var{file-list} @var{plugin*.c} ...} utility generates these
extra
root
tables.
+ggc_root_tab*}) as @code{user_data}.  Running the
+ @code{gengtype -p @var{source-dir} @var{file-list}
@var{plugin*.c}
...}
+utility generates these extra root tables.


After diff gcc-6.3.0/gcc/testsuite/gcc.dg/plugin and
gcc-4.8.0/gcc/testsuite/gcc.dg/plugin
then migrate to GCC v6.x like this:


// Register our garbage collector roots.
#if GCC_MAJOR < 6
 register_callback(plugin_name, PLUGIN_REGISTER_GGC_CACHES,
NULL,
#else
 register_callback(plugin_name, PLUGIN_REGISTER_GGC_ROOTS,
NULL,
#endif
   const_cast(gt_ggc_rc__gt_cache_h));


and Trevor talks more about GTY((if_marked(XXX), param_is(XXX)))
htab_t
migrate to GTY((cache)) hash_table such as:


#if (GCC_MAJOR < 6)
// FIXME: gengtype not support macro?
static GTY((if_marked("tree2int_marked_p"), param_is(struct
tree2int)))
   htab_t intCache;
#else
struct intCacheHasher : ggc_cache_ptr_hash {
 static inline hashval_t hash(tree2int *t2i) {
   return tree_map_base_hash(&t2i->base);
}

 static inline bool equal(tree2int *a, tree2int *b) {
   return a->base.from == b->base.from;
}
};
static GTY((cache))
   hash_table *intCache;
#endif


But I have no idea why gengtype does not support macro?
https://gcc.gnu.org/ml/gcc/2017-07/msg00045.html it just ignored
#if
(GCC_MAJOR < 6) still parse GTY((if_marked(XXX), param_is(XXX)))
htab_t
but not GTY((cache)) hash_table... please give me some
hint,
thanks a lot!

Unfortunately, gengtype is not a full parser for all of C++; IIRC
it
doesn't have any real support for the preprocessor.

Maybe you can work around it in your plugin by providing two
different
headers, one for GCC_MAJOR < 6, the other for >= 6, and setting up
the
build so that gengtype is invoked on the correct header.  (I know
this
is ugly, sorry).

Right now I am using two different files: such as Cache4.cpp and
Cache6.cpp, and there is the same `struct GTY(()) tree2WeakVH` for
GCC
v4.x
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Cache4
.cpp#L99
also for GCC v6.x
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Cache6
.cpp#L116

then gengtype auto-generated `struct ggc_root_tab` with Cache6.cpp
for
GCC v6.x
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/include/dr
agonegg/gt-cache-6.3.inc#L1257
it is of course different with Cache4.cpp for GCC v4.x
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/include/dr
agonegg/gt-cache-4.6.inc#L970

It looks strange to me that this repository contains these per-gcc
-version auto-generated .inc files; aren't these something that should
just be created at build time?

I am using Fedora, and perhaps no RPM packages provides gengtype:
$ dnf repoquery --whatprovides gengtype

compare with
$ dnf repoquery --whatprovides *libgcc-c-api*
gcc-python-plugin-c-api-0:0.15-8.1.fc25.x86_64
...

so I have no idea how to auto-generated them at build time, instead I 
built GCC v4.6 and v6.3 https://github.com/xiangzhai/dragonegg/wiki/GGC 
please give me some hint, thanks a lot!






Near the end of:
   https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/Makefile
I see that a make target that invokes gengtype.

I think the best approach is to add logic to that Makefile so that that
gengtype invocation either loads Cache4.cpp *or* Cache6.cpp, depend

Re: whereis PLUGIN_REGISTER_GGC_CACHES? how to migrate it for GCC v6.x?

2017-07-26 Thread Leslie Zhai

Hi Duncan,

Thanks for your kind response! My sincere thanks goes to you, the core 
developer of llvm-gcc and dragonegg 
http://llvm.org/devmtg/2009-10/Sands_LLVMGCCPlugin.pdf


dragonegg release_33 is still able to work happily for GCC v4.6.3 and 
LLVM v3.3 https://pbs.twimg.com/media/DFtthrTVoAEhnhA.jpg



> IIRC I did it this way because to generate these files you need to 
have theentire GCC sources, while one of the goals of dragonegg was that 
in order to beable to build dragonegg you should only need to have the 
gcc headers installed.



Yes, it is for the benefit of the dragonegg maintainers, and I built GCC 
v4.6.3 and v6.3 by myself https://github.com/xiangzhai/dragonegg/wiki/GGC


but after GCC v4.x, the API of GCC v5.x, v6.x, v7.x and v8.x (git master 
branch) had been changed a lot, so I am trying to migrate dragonegg for 
GCC v6.3 and LLVM v3.9 https://reviews.llvm.org/D35667


could you give me some hint, thanks a lot!

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





pass 'lto_gimple_out' not found, how to migrate it for GCC v6.x?

2017-07-27 Thread Leslie Zhai

Hi GCC developers,

As ChangeLog-2013 mentioned by Bernd Schmidt: ... 
pass_ipa_lto_gimple_out ... Remove. Delete.


there is no 'pass_ipa_lto_gimple_out' in lto-streamer-out.c any more.

then how to migrate it for GCC v6.x? just like this: 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2880 
to ignore it?


or do I need to find other equivalent PASS? please give me some hint, 
thanks a lot!



PS: Thanks for David's hint, I fixed 'undefined symbol 
gt_ggc_mx(tree2WeakVH*&)' issue, I forgot to add 'for_user' for 
GTY((XXX))...


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/






Re: pass 'lto_gimple_out' not found, how to migrate it for GCC v6.x?

2017-07-28 Thread Leslie Zhai

Hi Richard,

Thanks for your kind response!


在 2017年07月28日 15:54, Richard Biener 写道:

On Fri, Jul 28, 2017 at 6:12 AM, Leslie Zhai  wrote:

Hi GCC developers,

As ChangeLog-2013 mentioned by Bernd Schmidt: ... pass_ipa_lto_gimple_out
... Remove. Delete.

there is no 'pass_ipa_lto_gimple_out' in lto-streamer-out.c any more.

then how to migrate it for GCC v6.x? just like this:
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2880
to ignore it?

or do I need to find other equivalent PASS? please give me some hint, thanks
a lot!

It says

// Disable all LTO passes.

(for whatever reason).  So try just removing this part - the pass is
already removed.
Yes, I use the macro (GCC_MAJOR < 5) to disable it (just removing this 
part, to ignore it) 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2884 
sorry I am not the original developer of DragonEgg 
http://llvm.org/devmtg/2009-10/Sands_LLVMGCCPlugin.pdf and recently I am 
learning about GCC plugin and GIMPLE https://reviews.llvm.org/D35667 for 
converting GIMPLE to LLVM IR, then disable GCC PASS but use LLVM's 
instead, but I don't have the whole view of it, I need to deepin to it 
more :) please Duncan answer your question about 'for whatever reason', 
thanks!





Richard.


PS: Thanks for David's hint, I fixed 'undefined symbol
gt_ggc_mx(tree2WeakVH*&)' issue, I forgot to add 'for_user' for
GTY((XXX))...

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/






--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





How to migrate struct rtl_opt_pass to class for GCC v6.x?

2017-08-02 Thread Leslie Zhai

Hi GCC developers,

As ChangeLog-2013 mentioned:

2013-08-05  David Malcolm 

This is the automated part of the conversion of passes from C
structs to C++ classes.

...

* auto-inc-dec.c (pass_inc_dec): Convert from a global struct to a
subclass of rtl_opt_pass along with...


so I migrate struct rtl_opt_pass: 
https://github.com/llvm-mirror/dragonegg/blob/master/src/Backend.cpp#L1731



static struct rtl_opt_pass pass_rtl_emit_function = { {
  RTL_PASS, "rtl_emit_function", /* name */
#if (GCC_MINOR > 7)
  OPTGROUP_NONE, /* optinfo_flags */
#endif
  NULL,  /* gate */
  rtl_emit_function, /* execute */
  NULL,  /* sub */
  NULL,  /* next */
  0, /* static_pass_number */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts, /* 
todo_flags_start */

  TODO_ggc_collect /* todo_flags_finish */
} };


to GCC v6.x C++ classes' style: 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2072



const pass_data pass_data_rtl_emit_function = {
  RTL_PASS,  /* type */
  "rtl_emit_function",   /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  0, /* todo_flags_start */
  0, /* todo_flags_finish */
};

class pass_rtl_emit_function : public rtl_opt_pass {
public:
  pass_rtl_emit_function(gcc::context *ctxt)
  : rtl_opt_pass(pass_data_rtl_emit_function, ctxt) {}

  unsigned int execute(function *) { return rtl_emit_function(); }

  opt_pass *clone() { return this; }
};


GCC v4.6 will call the callback `rtl_emit_function`, but GCC v6.x will 
not, did I forget something? is there some options need to be set? 
please give me some hint, thanks a lot!


PS: GCC v6.x *call* the callback `rtl_emit_function` 
https://github.com/xiangzhai/dragonball/blob/master/tests/plugin.cpp#L67 
in this testcase, I will check the source code about register_callback, 
rtl_opt_pass, and opt_pass.


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/
@




Re: How to migrate struct rtl_opt_pass to class for GCC v6.x?

2017-08-03 Thread Leslie Zhai
/opt/gcc-6.3/bin/gcc -fplugin=./dragonegg.so test/hello.c -wrapper 
gdb,--args

GNU gdb (GDB) Fedora 7.12.1-48.fc25
...
Reading symbols from 
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1...done.

(gdb) b /data/project/xiangzhai/gcc-6.3.0/gcc/passes.c:2288
Breakpoint 1 at 0x91b8d4: file ../../gcc/passes.c, line 2288.
(gdb) r
Starting program: 
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1 -quiet 
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-gnu/6.3.0/plugin 
test/hello.c 
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-gnu/6.3.0/plugin 
-quiet -dumpbase hello.c -mtune=generic -march=x86-64 -auxbase hello 
-fplugin=./dragonegg.so -o /tmp/cco7mKtB.s

...

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c7b730) at 
../../gcc/passes.c:2288

warning: Source file is more recent than executable.
2288  current_pass = pass;

(gdb) p pass
$1 = (opt_pass *) 0x1c7b730
(gdb) p current_pass
$2 = (opt_pass *) 0x0
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p current_pass
$3 = (opt_pass *) 0x1c7b730
(gdb) p gate_status
$4 = false
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) p gate_status
$5 = false
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p gate_status
$6 = false
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE, &gate_status);
(gdb) p gate_status
$7 = true
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE, &gate_status);
(gdb) n
2298  if (!gate_status)
(gdb) p gate_status
$8 = true
(gdb) n
...
(gdb) n
2336  todo_after = pass->execute (cfun); <--- gcc called execute hook?
(gdb) p todo_after
$9 = 0
(gdb) n
2338  if (todo_after & TODO_discard_function)
(gdb) p todo_after
$10 = 0
(gdb)


2336  todo_after = pass->execute (cfun); <--- gcc called execute 
hook? but why not dragonegg 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2103




在 2017年08月03日 11:24, Leslie Zhai 写道:

Hi GCC developers,

As ChangeLog-2013 mentioned:

2013-08-05  David Malcolm 

This is the automated part of the conversion of passes from C
structs to C++ classes.

...

* auto-inc-dec.c (pass_inc_dec): Convert from a global struct to a
subclass of rtl_opt_pass along with...


so I migrate struct rtl_opt_pass: 
https://github.com/llvm-mirror/dragonegg/blob/master/src/Backend.cpp#L1731



static struct rtl_opt_pass pass_rtl_emit_function = { {
  RTL_PASS, "rtl_emit_function", /* name */
#if (GCC_MINOR > 7)
  OPTGROUP_NONE, /* optinfo_flags */
#endif
  NULL,  /* gate */
  rtl_emit_function, /* execute */
  NULL,  /* sub */
  NULL,  /* next */
  0, /* static_pass_number */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts, /* 
todo_flags_start */

  TODO_ggc_collect /* todo_flags_finish */
} };


to GCC v6.x C++ classes' style: 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2072



const pass_data pass_data_rtl_emit_function = {
  RTL_PASS,  /* type */
  "rtl_emit_function",   /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  0, /* todo_flags_start */
  0, /* todo_flags_finish */
};

class pass_rtl_emit_function : public rtl_opt_pass {
public:
  pass_rtl_emit_function(gcc::context *ctxt)
  : rtl_opt_pass(pass_data_rtl_emit_function, ctxt) {}

  unsigned int execute(function *) { return rtl_emit_function(); }

  opt_pass *clone() { return this; }
};


GCC v4.6 will call the callback `rtl_emit_function`, but GCC v6.x will 
not, did I forget something? is there some options need to be set? 
please give me some hint, thanks a lot!


PS: GCC v6.x *call* the callback `rtl_emit_function` 
https://github.com/xiangzhai/dragonball/blob/master/tests/plugin.cpp#L67 
in this testcase, I will check the source code about 
register_callback, rtl_opt_pass, and opt_pass.




--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: How to migrate struct rtl_opt_pass to class for GCC v6.x?

2017-08-03 Thread Leslie Zhai

Hi David,

Thanks for your kind response!


在 2017年08月03日 21:54, David Malcolm 写道:

On Thu, 2017-08-03 at 17:21 +0800, Leslie Zhai wrote:

/opt/gcc-6.3/bin/gcc -fplugin=./dragonegg.so test/hello.c -wrapper
gdb,--args
GNU gdb (GDB) Fedora 7.12.1-48.fc25
...
Reading symbols from
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1...done.
(gdb) b /data/project/xiangzhai/gcc-6.3.0/gcc/passes.c:2288
Breakpoint 1 at 0x91b8d4: file ../../gcc/passes.c, line 2288.
(gdb) r
Starting program:
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1 -quiet
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-
gnu/6.3.0/plugin
test/hello.c
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-
gnu/6.3.0/plugin
-quiet -dumpbase hello.c -mtune=generic -march=x86-64 -auxbase hello
-fplugin=./dragonegg.so -o /tmp/cco7mKtB.s
...

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c7b730) at
../../gcc/passes.c:2288
warning: Source file is more recent than executable.

This warning is somewhat unnerving; have you updated the source code
for the compiler since you last recompiled it?


The warning disappeared after recompiled GCC v6.3





2288  current_pass = pass;

(gdb) p pass
$1 = (opt_pass *) 0x1c7b730
(gdb) p current_pass
$2 = (opt_pass *) 0x0
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p current_pass
$3 = (opt_pass *) 0x1c7b730
(gdb) p gate_status
$4 = false
(gdb) n
2293  gate_status = override_gate_status (pass,
current_function_decl, gate_status);
(gdb) p gate_status
$5 = false
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p gate_status
$6 = false
(gdb) n
2293  gate_status = override_gate_status (pass,
current_function_decl, gate_status);
(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE,
&gate_status);
(gdb) p gate_status
$7 = true
(gdb) n
2293  gate_status = override_gate_status (pass,
current_function_decl, gate_status);
(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE,
&gate_status);
(gdb) n
2298  if (!gate_status)
(gdb) p gate_status
$8 = true
(gdb) n
...
(gdb) n
2336  todo_after = pass->execute (cfun); <--- gcc called execute
hook?

Try "step" here rather than "n" for "next"; that way you can see
exactly what is being called.

I had a hunch that you might be running into the default implementation
of opt_pass::execute, which is a no-op.

opt_pass::execute used to take "void", but was changed to take a
"function *" in r209482 (aka 65b0537f9e9741318f7c8e738b6dd3b8f82f58b5)
on 2014-04-17.   If you're using a >= C++11 compiler, you might want to
try adding "final override" to the execute method of your pass to
ensure that it's an override of the execute virtual function.   We have
macros "FINAL" and "OVERRIDE" for this in recent versions of gcc.


Add as your suggestion. 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2110





Is this definitely the correct pass?  What does

(gdb) p *pass

print?


Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c7b730) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
...
(gdb) p pass->name
$1 = 0x11a2369 "*warn_unused_result"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86270) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$2 = 0x1181b98 "*diagnose_omp_blocks"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c862d0) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$3 = 0x119d740 "*diagnose_tm_blocks"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86330) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$4 = 0x1181bad "omplower"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86390) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$5 = 0x11be968 "lower"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c863f0) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$6 = 0x119d738 "tmlower"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86450) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$7 = 0x11a711e "ehopt"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c864b0) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$8 = 0x119b9cf "eh"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86510) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gdb) p pass->name
$9 = 0x11972bb "cfg"
(gdb) c
Continuing.

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c86570) at 
../../gcc/passes.c:2288

2288  current_pass = pass;
(gd

How to migrate POINTER_TYPE_OVERFLOW_UNDEFINED for GCC v8.x?

2017-08-04 Thread Leslie Zhai

Hi GCC developers,

As ChangeLog mentioned:

2017-08-01  Bin Cheng 

* tree.h (POINTER_TYPE_OVERFLOW_UNDEFINED): Delete.


Then how to migrate it for GCC v8.x? for example:

Constant *Result = POINTER_TYPE_OVERFLOW_UNDEFINED ? A : B;

migrated to

Constant *Result = A;


because there was a patch 'Make pointer overflow always undefined and 
remove the macro' https://patchwork.ozlabs.org/patch/792677/


please give me some hint, thanks a lot!

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: How to migrate POINTER_TYPE_OVERFLOW_UNDEFINED for GCC v8.x?

2017-08-04 Thread Leslie Zhai

Hi Bin,

Thanks for your kind response!


在 2017年08月04日 15:45, Bin.Cheng 写道:

On Fri, Aug 4, 2017 at 8:00 AM, Leslie Zhai  wrote:

Hi GCC developers,

As ChangeLog mentioned:

2017-08-01  Bin Cheng 

 * tree.h (POINTER_TYPE_OVERFLOW_UNDEFINED): Delete.


Then how to migrate it for GCC v8.x? for example:

Constant *Result = POINTER_TYPE_OVERFLOW_UNDEFINED ? A : B;

migrated to

Constant *Result = A;

Yes, basically this is what I did in the patch: simply assuming TRUE
and simplifying the expression.


I migrated to GCC v8.x now 
https://github.com/xiangzhai/dragonegg/commit/d78389c502f5a06b21fcf1a1590e44451e59f461
thanks for your patch's hint :) it can't work for GCC v8.x, even though 
compiled without error, but able to work for GCC v4.6 and v4.8, I am 
stuck at rtl_opt_pass https://gcc.gnu.org/ml/gcc/2017-08/msg00045.html

hope I can figure it out the root cause.




Thanks,
bin


because there was a patch 'Make pointer overflow always undefined and remove
the macro' https://patchwork.ozlabs.org/patch/792677/

please give me some hint, thanks a lot!

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/



Re: How to migrate struct rtl_opt_pass to class for GCC v6.x?

2017-08-16 Thread Leslie Zhai



在 2017年08月03日 17:21, Leslie Zhai 写道:
/opt/gcc-6.3/bin/gcc -fplugin=./dragonegg.so test/hello.c -wrapper 
gdb,--args

GNU gdb (GDB) Fedora 7.12.1-48.fc25
...
Reading symbols from 
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1...done.

(gdb) b /data/project/xiangzhai/gcc-6.3.0/gcc/passes.c:2288
Breakpoint 1 at 0x91b8d4: file ../../gcc/passes.c, line 2288.
(gdb) r
Starting program: 
/opt/gcc-6.3/libexec/gcc/x86_64-redhat-linux-gnu/6.3.0/cc1 -quiet 
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-gnu/6.3.0/plugin 
test/hello.c 
-iplugindir=/opt/gcc-6.3/lib/gcc/x86_64-redhat-linux-gnu/6.3.0/plugin 
-quiet -dumpbase hello.c -mtune=generic -march=x86-64 -auxbase hello 
-fplugin=./dragonegg.so -o /tmp/cco7mKtB.s

...

Breakpoint 1, execute_one_pass (pass=pass@entry=0x1c7b730) at 
../../gcc/passes.c:2288

warning: Source file is more recent than executable.
2288  current_pass = pass;

(gdb) p pass
$1 = (opt_pass *) 0x1c7b730
(gdb) p current_pass
$2 = (opt_pass *) 0x0
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p current_pass
$3 = (opt_pass *) 0x1c7b730
(gdb) p gate_status
$4 = false
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) p gate_status
$5 = false
(gdb) n
2292  gate_status = pass->gate (cfun);
(gdb) p gate_status
$6 = false
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE, &gate_status);
(gdb) p gate_status
$7 = true
(gdb) n
2293  gate_status = override_gate_status (pass, 
current_function_decl, gate_status);

(gdb) n
2296  invoke_plugin_callbacks (PLUGIN_OVERRIDE_GATE, &gate_status);
(gdb) n
2298  if (!gate_status)
(gdb) p gate_status
$8 = true
(gdb) n
...
(gdb) n
2336  todo_after = pass->execute (cfun); <--- gcc called execute 
hook?

(gdb) p todo_after
$9 = 0
(gdb) n
2338  if (todo_after & TODO_discard_function)
(gdb) p todo_after
$10 = 0
(gdb)


2336  todo_after = pass->execute (cfun); <--- gcc called execute 
hook? but why not dragonegg 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2103




在 2017年08月03日 11:24, Leslie Zhai 写道:

Hi GCC developers,

As ChangeLog-2013 mentioned:

2013-08-05  David Malcolm 

This is the automated part of the conversion of passes from C
structs to C++ classes.

...

* auto-inc-dec.c (pass_inc_dec): Convert from a global struct to a
subclass of rtl_opt_pass along with...


so I migrate struct rtl_opt_pass: 
https://github.com/llvm-mirror/dragonegg/blob/master/src/Backend.cpp#L1731



static struct rtl_opt_pass pass_rtl_emit_function = { {
  RTL_PASS, "rtl_emit_function", /* name */
#if (GCC_MINOR > 7)
  OPTGROUP_NONE, /* optinfo_flags */
#endif
  NULL,  /* gate */
  rtl_emit_function, /* execute */
  NULL,  /* sub */
  NULL,  /* next */
  0, /* static_pass_number */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  TODO_verify_ssa | TODO_verify_flow | TODO_verify_stmts, /* 
todo_flags_start */

  TODO_ggc_collect /* todo_flags_finish */
} };


to GCC v6.x C++ classes' style: 
https://github.com/xiangzhai/dragonegg/blob/gcc-6_3-branch/src/Backend.cpp#L2072



const pass_data pass_data_rtl_emit_function = {
  RTL_PASS,  /* type */
  "rtl_emit_function",   /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_NONE,   /* tv_id */
  PROP_ssa | PROP_gimple_leh | PROP_cfg, /* properties_required */
  0, /* properties_provided */
  PROP_ssa | PROP_trees, /* properties_destroyed */
  0, /* todo_flags_start */
  0, /* todo_flags_finish */
};

class pass_rtl_emit_function : public rtl_opt_pass {
public:
  pass_rtl_emit_function(gcc::context *ctxt)
  : rtl_opt_pass(pass_data_rtl_emit_function, ctxt) {}

  unsigned int execute(function *) { return rtl_emit_function(); }

  opt_pass *clone() { return this; }
};


GCC v4.6 will call the callback `rtl_emit_function`, but GCC v6.x 
will not, did I forget something? is there some options need to be 
set? please give me some hint, thanks a lot!


PS: GCC v6.x *call* the callback `rtl_emit_function` 
https://github.com/xiangzhai/dragonball/blob/master/tests/plugin.cpp#L67 
in this testcase, I will check the source code about 
register_callback, rtl_opt_pass, and opt_pass.


I found it!

with -flto option,

How to migrate ggc_alloc_XXX for GCC v8.x (git-20170816)?

2017-08-16 Thread Leslie Zhai

Hi GCC developers,

GCC v4.6's gengtype will auto-generate Allocators for known structs and 
unions, for example: ggc_alloc_tree2WeakVH for tree2WeakVH 
https://github.com/xiangzhai/dragonegg/blob/master/include/dragonegg/gt-cache-4.6.inc#L24


but gengtype will not auto-generate ggc_alloc_XXX for GCC v6.x or v8.x 
(git-20170816), for example: struct GTY((for_user)) tree2WeakVH 
https://github.com/xiangzhai/dragonegg/blob/master/include/dragonegg/gt-cache-8.0.inc#L1284


As ChangeLog-2014 mentioned:

2014-05-17  Trevor Saunders 

...
(ggc_alloc): Install the type's destructor as the finalizer if it
might do something.

Please give me some hint about ggc_alloc migration, thanks a lot!

--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: How to migrate ggc_alloc_XXX for GCC v8.x (git-20170816)?

2017-08-16 Thread Leslie Zhai

Hi Trevor,

Thanks for your kind response!


在 2017年08月16日 20:02, Trevor Saunders 写道:

On Wed, Aug 16, 2017 at 05:32:10PM +0800, Leslie Zhai wrote:

Hi GCC developers,

GCC v4.6's gengtype will auto-generate Allocators for known structs and
unions, for example: ggc_alloc_tree2WeakVH for tree2WeakVH 
https://github.com/xiangzhai/dragonegg/blob/master/include/dragonegg/gt-cache-4.6.inc#L24

but gengtype will not auto-generate ggc_alloc_XXX for GCC v6.x or v8.x
(git-20170816), for example: struct GTY((for_user)) tree2WeakVH 
https://github.com/xiangzhai/dragonegg/blob/master/include/dragonegg/gt-cache-8.0.inc#L1284

As ChangeLog-2014 mentioned:

2014-05-17  Trevor Saunders 

 ...
 (ggc_alloc): Install the type's destructor as the finalizer if it
 might do something.

Please give me some hint about ggc_alloc migration, thanks a lot!

if you look at the patches they convert ggc_alloc_foo to ggc_alloc
and you should do the same.


Thanks for your hint! I do the same :) 
https://github.com/xiangzhai/dragonegg/blob/master/src/Cache.cpp#L255
PS: how to find the relative patch for the ChangeLog's item? I use 
Google, for example: (ggc_alloc): Install the type's destructor as the 
finalizer if it might do something.





Trev


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





Re: Locating a commit from its ChangeLog entry (was Re: How to migrate ggc_alloc_XXX for GCC v8.x (git-20170816)?)

2017-08-17 Thread Leslie Zhai



在 2017年08月17日 23:10, David Malcolm 写道:

On Thu, 2017-08-17 at 09:52 +0800, Leslie Zhai wrote:

Hi Trevor,

Thanks for your kind response!


在 2017年08月16日 20:02, Trevor Saunders 写道:

On Wed, Aug 16, 2017 at 05:32:10PM +0800, Leslie Zhai wrote:

Hi GCC developers,

GCC v4.6's gengtype will auto-generate Allocators for known
structs and
unions, for example: ggc_alloc_tree2WeakVH for tree2WeakVH https:
//github.com/xiangzhai/dragonegg/blob/master/include/dragonegg/gt
-cache-4.6.inc#L24

but gengtype will not auto-generate ggc_alloc_XXX for GCC v6.x or
v8.x
(git-20170816), for example: struct GTY((for_user)) tree2WeakVH h
ttps://github.com/xiangzhai/dragonegg/blob/master/include/dragone
gg/gt-cache-8.0.inc#L1284

As ChangeLog-2014 mentioned:

2014-05-17  Trevor Saunders 

  ...
  (ggc_alloc): Install the type's destructor as the finalizer
if it
  might do something.

Please give me some hint about ggc_alloc migration, thanks a lot!

if you look at the patches they convert ggc_alloc_foo to
ggc_alloc
and you should do the same.

Thanks for your hint! I do the same :)
https://github.com/xiangzhai/dragonegg/blob/master/src/Cache.cpp#L255
PS: how to find the relative patch for the ChangeLog's item? I use
Google, for example: (ggc_alloc): Install the type's destructor as
the
finalizer if it might do something.

Another way is to use "git blame" on the ChangeLog to find the commit
that added the ChangeLog entry.

For "archived" ChangeLog files like "ChangeLog-2014" that will just
tell you which commit moved all of the entries for that years ChangeLog
entries to "ChangeLog-2014", so you can use "git log":

   git log gcc/ChangeLog-2014

to identify the commit that archived the ChangeLog:

commit e64e0023b9a6796858262f8fd38005a08d234d82
Author: green 
Date:   Thu Jan 1 15:43:47 2015 +

 Roll ChangeLog file.  Limit offsets to 16 bits for moxie.


Once you have that commit you can use "^" to find the prior state of
the tree, and then use git blame:

   git blame e64e0023b9a6796858262f8fd38005a08d234d82^ gcc/ChangeLog


Thanks for your hint!



and then search for the text of interest:

9296020474 (tbsaunde  2014-05-17 23:15:55 + 38073) 2014-05-17  Trevor 
Saunders  
9296020474 (tbsaunde  2014-05-17 23:15:55 + 38074)
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38075)  * ggc-common.c 
(ggc_internal_cleared_alloc): Adjust.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38076)  * ggc-none.c 
(ggc_internal_alloc): Assert if a finalizer is passed.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38077)  
(ggc_internal_cleared_alloc): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38078)  * ggc-page.c 
(finalizer): New class.
b540cb16c9 (uros  2014-05-18 07:24:24 + 38079)  
(vec_finalizer): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38080)  
(globals::finalizers): New member.
b540cb16c9 (uros  2014-05-18 07:24:24 + 38081)  
(globals::vec_finalizers): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38082)  
(ggc_internal_alloc): Record the finalizer if any for the block bei
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38083)  allocated.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38084)  
(ggc_handle_finalizers): New function.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38085)  (ggc_collect): 
Call ggc_handle_finalizers.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38086)  * ggc.h 
(ggc_internal_alloc): Add arguments to allow installing a
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38087)  finalizer.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38088)  
(ggc_internal_cleared_alloc): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38089)  (finalize): New 
function.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38090)  
(need_finalization_p): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38091)  (ggc_alloc): 
Install the type's destructor as the finalizer if it
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38092)  might do 
something.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38093)  
(ggc_cleared_alloc): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38094)  
(ggc_vec_alloc): Likewise.
92f06184bb (tbsaunde  2014-05-17 23:08:00 + 38095)  
(ggc_cleared_vec_alloc): Likewise.

which identifies the commit as 92f06184bb.

"git show 92f06184bb" shows the commit you're looking for, and contains this 
line:

 git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@210568 
138bc75d-0d04-0410-961f-82ee72b054a4

from which you can see (if you need to) that the SVN commit was r210568.


Dave


--
Regards,
Leslie Zhai - a LLVM developer https://reviews.llvm.org/p/xiangzhai/





DragonEgg for GCC v8.x and LLVM v6.x is just able to work

2017-08-20 Thread Leslie Zhai

Hi LLVM and GCC developers,

My sincere thanks will goto:

* Duncan, the core developer of llvm-gcc and dragonegg 
http://llvm.org/devmtg/2009-10/Sands_LLVMGCCPlugin.pdf


* David, the innovator and developer of GCC 
https://dmalcolm.fedorapeople.org/gcc/global-state/requirements.html


and others who give me kind response for teaching me patiently and 
carefully about how to migrate GCC v4.8.x to GCC v8.x (git-20170818)


DragonEgg has been migrated to GCC v8.x and LLVM v6.x (svn-r311142), but 
also able to work for GCC v4.8.x and LLVM v3.3 
https://reviews.llvm.org/D35667 and it is just able to work now, for 
example:



CC=/opt/gcc-git/bin/gcc

LC=/opt/llvm-svn/bin/llvm-config

export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$($LC --libdir)

GCC=$CC LLVM_CONFIG=$LC ENABLE_LLVM_PLUGINS=1 DRAGONEGG_DEBUG=1 make -j4


$CC -fplugin=./dragonegg.so \
-fplugin-arg-dragonegg-debug-pass-arguments \
-ftime-report \
-fverbose-asm \
-fplugin-arg-dragonegg-enable-gcc-optzns \
-fplugin-arg-dragonegg-emit-ir \
-S \
test/hello.c \
-wrapper gdb,--args


hello.s (LLVM IR, the extension name is not important)

; ModuleID = 'test/hello.c'
source_filename = "test/hello.c"
target triple = "x86_64-redhat-linux"

module asm "\09.ident\09\22GCC: (GNU) 6.4.1 20170727 (Red Hat 6.4.1-1) 
LLVM: 3.9.1\22"


@__func__.2210 = internal local_unnamed_addr constant [4 x i8] c"foo\00"
@.cst = private local_unnamed_addr constant [24 x i8] c"DEBUG: %s, line 
%d: %s\0A\00", align 8
@.cst.1 = private local_unnamed_addr constant [13 x i8] 
c"test/hello.c\00", align 8
@.cst.2 = private local_unnamed_addr constant [12 x i8] c"Leslie 
Zhai\00", align 8
@.cst.3 = private local_unnamed_addr constant [20 x i8] c"%s: Hello 
World %d\0A\00", align 8


; Function Attrs: nounwind uwtable
define void @foo(...) unnamed_addr #0 {
entry:
  %"ssa point" = bitcast i32 0 to i32
  br label %""

"": ; preds = %entry
  %0 = call i32 (i8*, ...) @printf(i8* noalias getelementptr inbounds 
([24 x i8], [24 x i8]* @.cst, i64 0, i64 0), [13 x i8]* @.cst.1, i32 4, 
[4 x i8]* @__func__.2210) #1

  br label %return

return:   ; preds = %""
  ret void
}

declare i32 @printf(i8*, ...)

; Function Attrs: nounwind uwtable
define i32 @main(i32 %argc, i8** %argv) unnamed_addr #0 {
entry:
  %argc_addr = alloca i32, align 4
  %argv_addr = alloca i8**, align 8
  %n = alloca i32
  %s = alloca i8*
  %"" = alloca i32
  %"alloca point" = bitcast i32 0 to i32
  store i32 %argc, i32* %argc_addr, align 1
  store i8** %argv, i8*** %argv_addr, align 1
  %"ssa point" = bitcast i32 0 to i32
  br label %""

"": ; preds = %entry
  %0 = call i32 (i8*, ...) @printf(i8* noalias getelementptr inbounds 
([20 x i8], [20 x i8]* @.cst.3, i64 0, i64 0), i8* getelementptr 
inbounds ([12 x i8], [12 x i8]* @.cst.2, i64 0, i64 0), i32 1) #1

  br label %""

"":   ; preds = %""
  store i32 0, i32* %"", align 1
  br label %return

return:   ; preds = %""
  %1 = load i32, i32* %"", align 4
  ret i32 %1
}

attributes #0 = { nounwind uwtable "no-frame-pointer-elim-non-leaf"="true" }
attributes #1 = { nounwind }

!llvm.module.flags = !{!0}

!0 = !{i32 1, !"PIE Level", i32 2}


$ llc hello.s

.text
.file"hello.s"
# Start of file scope inline 
assembly

.ident"GCC: (GNU) 6.4.1 20170727 (Red Hat 6.4.1-1) LLVM: 3.9.1"

# End of file scope inline assembly
.globlfoo
.p2align4, 0x90
.typefoo,@function
foo:# @foo
.cfi_startproc
# BB#0: # %entry
pushq%rbp
.Ltmp0:
.cfi_def_cfa_offset 16
.Ltmp1:
.cfi_offset %rbp, -16
movq%rsp, %rbp
.Ltmp2:
.cfi_def_cfa_register %rbp
movl$.L.cst, %edi
movl$.L.cst.1, %esi
movl$4, %edx
movl$__func__.2210, %ecx
xorl%eax, %eax
callqprintf
popq%rbp
retq
.Lfunc_end0:
.sizefoo, .Lfunc_end0-foo
.cfi_endproc

.globlmain
.p2align4, 0x90
.typemain,@function
main:   # @main
.cfi_startproc
# BB#0: # %entry
pushq%rbp
.Ltmp3:
.cfi_def_cfa_offset 16
.Ltmp4:
.cfi_offset %rbp, -16
movq%rsp, %rbp
.Ltmp5:
.cfi_def_cfa_register %rbp
subq$32, %rsp
movl%edi, -8(%rbp)
movq%rsi, -16(%rbp)
movl$.L.cst.3, %edi
movl$.L.cst.2,

Re: DragonEgg for GCC v8.x and LLVM v6.x is just able to work

2017-09-04 Thread Leslie Zhai

Hi LLVM and GCC developers,

LLVM China  http://www.llvm.org.cn  forked DragonEgg 
https://github.com/LLVM-China/dragonegg  because:


* Some subprojects are impractical or uninteresting to relicense (e.g. 
llvm-gcc  and dragonegg). These will be split off from the LLVM project 
(e.g. to separate Github projects), allowing interested people to 
continue their development elsewhere. 
http://lists.llvm.org/pipermail/llvm-dev/2017-August/116266.html


* There are a lot of issues 
https://github.com/xiangzhai/dragonegg/issues  so I need smarter 
developers' help.



在 2017年08月21日 11:31, Leslie Zhai 写道:

Hi LLVM and GCC developers,

My sincere thanks will goto:

* Duncan, the core developer of llvm-gcc and dragonegg 
http://llvm.org/devmtg/2009-10/Sands_LLVMGCCPlugin.pdf


* David, the innovator and developer of GCC 
https://dmalcolm.fedorapeople.org/gcc/global-state/requirements.html


and others who give me kind response for teaching me patiently and 
carefully about how to migrate GCC v4.8.x to GCC v8.x (git-20170818)


DragonEgg has been migrated to GCC v8.x and LLVM v6.x (svn-r311142), 
but also able to work for GCC v4.8.x and LLVM v3.3 
https://reviews.llvm.org/D35667 and it is just able to work now, for 
example:



CC=/opt/gcc-git/bin/gcc

LC=/opt/llvm-svn/bin/llvm-config

export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$($LC --libdir)

GCC=$CC LLVM_CONFIG=$LC ENABLE_LLVM_PLUGINS=1 DRAGONEGG_DEBUG=1 make -j4


$CC -fplugin=./dragonegg.so \
-fplugin-arg-dragonegg-debug-pass-arguments \
-ftime-report \
-fverbose-asm \
-fplugin-arg-dragonegg-enable-gcc-optzns \
-fplugin-arg-dragonegg-emit-ir \
-S \
test/hello.c \
-wrapper gdb,--args


hello.s (LLVM IR, the extension name is not important)

; ModuleID = 'test/hello.c'
source_filename = "test/hello.c"
target triple = "x86_64-redhat-linux"

module asm "\09.ident\09\22GCC: (GNU) 6.4.1 20170727 (Red Hat 6.4.1-1) 
LLVM: 3.9.1\22"


@__func__.2210 = internal local_unnamed_addr constant [4 x i8] c"foo\00"
@.cst = private local_unnamed_addr constant [24 x i8] c"DEBUG: %s, 
line %d: %s\0A\00", align 8
@.cst.1 = private local_unnamed_addr constant [13 x i8] 
c"test/hello.c\00", align 8
@.cst.2 = private local_unnamed_addr constant [12 x i8] c"Leslie 
Zhai\00", align 8
@.cst.3 = private local_unnamed_addr constant [20 x i8] c"%s: Hello 
World %d\0A\00", align 8


; Function Attrs: nounwind uwtable
define void @foo(...) unnamed_addr #0 {
entry:
  %"ssa point" = bitcast i32 0 to i32
  br label %""

"": ; preds = %entry
  %0 = call i32 (i8*, ...) @printf(i8* noalias getelementptr inbounds 
([24 x i8], [24 x i8]* @.cst, i64 0, i64 0), [13 x i8]* @.cst.1, i32 
4, [4 x i8]* @__func__.2210) #1

  br label %return

return:   ; preds = %""
  ret void
}

declare i32 @printf(i8*, ...)

; Function Attrs: nounwind uwtable
define i32 @main(i32 %argc, i8** %argv) unnamed_addr #0 {
entry:
  %argc_addr = alloca i32, align 4
  %argv_addr = alloca i8**, align 8
  %n = alloca i32
  %s = alloca i8*
  %"" = alloca i32
  %"alloca point" = bitcast i32 0 to i32
  store i32 %argc, i32* %argc_addr, align 1
  store i8** %argv, i8*** %argv_addr, align 1
  %"ssa point" = bitcast i32 0 to i32
  br label %""

"": ; preds = %entry
  %0 = call i32 (i8*, ...) @printf(i8* noalias getelementptr inbounds 
([20 x i8], [20 x i8]* @.cst.3, i64 0, i64 0), i8* getelementptr 
inbounds ([12 x i8], [12 x i8]* @.cst.2, i64 0, i64 0), i32 1) #1

  br label %""

"":   ; preds = %""
  store i32 0, i32* %"", align 1
  br label %return

return:   ; preds = %""
  %1 = load i32, i32* %"", align 4
  ret i32 %1
}

attributes #0 = { nounwind uwtable 
"no-frame-pointer-elim-non-leaf"="true" }

attributes #1 = { nounwind }

!llvm.module.flags = !{!0}

!0 = !{i32 1, !"PIE Level", i32 2}


$ llc hello.s

.text
.file"hello.s"
# Start of file scope inline 
assembly

.ident"GCC: (GNU) 6.4.1 20170727 (Red Hat 6.4.1-1) LLVM: 3.9.1"

# End of file scope inline 
assembly

.globlfoo
.p2align4, 0x90
.typefoo,@function
foo:# @foo
.cfi_startproc
# BB#0: # %entry
pushq%rbp
.Ltmp0:
.cfi_def_cfa_offset 16
.Ltmp1:
.cfi_offset %rbp, -16
movq%rsp, %rbp
.Ltmp2:
.cfi_def_cfa_register %rbp
movl$.L.cst, %edi
movl$.L.cst.1, %esi
movl$4, %edx
movl$__f

Re: Assigning the result of a function call to a variable in the Gfortran frontend

2017-09-05 Thread Leslie Zhai



在 2017年09月05日 14:14, Tobias Grosser 写道:

Hi Leslie,

I copied you in this thread as you currently worked quite a bit with
dragonegg and we are currently trying to generate metadata that makes it
easier to reason about multi-dimensional fortran arrays.

Best,
Tobias

On Mon, Sep 4, 2017, at 23:06, (IIIT) Siddharth Bhat wrote:

Hello,

I've been hacking on the Gfortran frontend to change array index
expressions to function calls, so that I can inspect them later on in the
pipeline. I go from Fortran -> LLVM IR (through dragonegg) where I will
look at the function call nodes.

However, I'm not able to generate correct IR for this. I can create
function call, but I am unable to assign the return value of a function
call to a variable here.

Here's a link to my experiments here: It includes a patch, a test file
and
the GIMPLE output
<https://gist.github.com/bollu/999184bdb3d0f1569ee0fd0a351689e3#file-m-gimple-L24>


I rebase the patch for GCC v8.x at first:


diff --git a/gcc/fortran/trans-array.c b/gcc/fortran/trans-array.c
index 9efb531..73dad6e 100644
--- a/gcc/fortran/trans-array.c
+++ b/gcc/fortran/trans-array.c
@@ -3251,6 +3251,7 @@ gfc_conv_scalarized_array_ref (gfc_se * se, 
gfc_array_ref * ar)

   if (build_class_array_ref (se, tmp, index))
 return;

+  call_polly_index(&se->pre, index, ar);
   se->expr = gfc_build_array_ref (tmp, index, decl);
 }

@@ -3335,6 +3336,24 @@ build_array_ref (tree desc, tree offset, tree 
decl, tree vptr)

   return tmp;
 }

+// See: gfc_call_malloc
+static tree call_polly_index(stmtblock_t *parent_block, tree 
*original_index,

+gfc_array_ref *ar) {
+  tree fncall, var, result;
+  stmtblock_t block;
+
+  var = gfc_create_var(gfc_array_index_type, "pollyindex");
+  gfc_init_block (&block);
+
+  fncall = build_call_expr_loc(input_location, 
gfor_fndecl_polly_array_index, 0);

+  gfc_add_modify(&block, var, fold_convert(gfc_array_index_type, fncall));
+  result = gfc_finish_block (&block);
+  gfc_add_expr_to_block(parent_block, result);
+  return var;
+
+  // return var;
+}
+

 /* Build an array reference.  se->expr already holds the array descriptor.
This should be either a variable, indirect variable reference or 
component

diff --git a/gcc/fortran/trans-decl.c b/gcc/fortran/trans-decl.c
index 74d8606..28ddcfd 100644
--- a/gcc/fortran/trans-decl.c
+++ b/gcc/fortran/trans-decl.c
@@ -95,6 +95,7 @@ static int seen_ieee_symbol;

 /* Function declarations for builtin library functions.  */

+tree gfor_fndecl_polly_array_index;
 tree gfor_fndecl_pause_numeric;
 tree gfor_fndecl_pause_string;
 tree gfor_fndecl_stop_numeric;
@@ -3495,6 +3496,14 @@ gfc_build_builtin_function_decls (void)
   /* ERROR STOP doesn't return.  */
   TREE_THIS_VOLATILE (gfor_fndecl_error_stop_string) = 1;

+
+  printf("building polly_array_index function decl...\n");
+  gfor_fndecl_polly_array_index = gfc_build_library_function_decl (
+get_identifier (PREFIX("polly_array_index")),
+gfc_array_index_type, 0);
+  TREE_THIS_VOLATILE (gfor_fndecl_polly_array_index) = 1;
+  printf("built polly_array_index function decl...\n");
+
   gfor_fndecl_pause_numeric = gfc_build_library_function_decl (
 get_identifier (PREFIX("pause_numeric")),
 void_type_node, 1, gfc_int4_type_node);
diff --git a/gcc/fortran/trans.h b/gcc/fortran/trans.h
index d02f347..c8d24ec 100644
--- a/gcc/fortran/trans.h
+++ b/gcc/fortran/trans.h
@@ -781,6 +781,7 @@ struct gimplify_omp_ctx;
 void gfc_omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *, tree);

 /* Runtime library function decls.  */
+extern GTY(()) tree gfor_fndecl_polly_array_index;
 extern GTY(()) tree gfor_fndecl_pause_numeric;
 extern GTY(()) tree gfor_fndecl_pause_string;
 extern GTY(()) tree gfor_fndecl_stop_numeric;


then I will rebuild GCC for investigation.



.

Help would be very much appreciated!

Thanks,
Siddharth.
--
Sending this from my phone, please excuse any typos!


--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/





Re: Assigning the result of a function call to a variable in the Gfortran frontend

2017-09-05 Thread Leslie Zhai



在 2017年09月05日 15:25, Leslie Zhai 写道:



在 2017年09月05日 14:14, Tobias Grosser 写道:

Hi Leslie,

I copied you in this thread as you currently worked quite a bit with
dragonegg and we are currently trying to generate metadata that makes it
easier to reason about multi-dimensional fortran arrays.

Best,
Tobias

On Mon, Sep 4, 2017, at 23:06, (IIIT) Siddharth Bhat wrote:

Hello,

I've been hacking on the Gfortran frontend to change array index
expressions to function calls, so that I can inspect them later on 
in the

pipeline. I go from Fortran -> LLVM IR (through dragonegg) where I will
look at the function call nodes.

However, I'm not able to generate correct IR for this. I can create
function call, but I am unable to assign the return value of a function
call to a variable here.

Here's a link to my experiments here: It includes a patch, a test file
and
the GIMPLE output
<https://gist.github.com/bollu/999184bdb3d0f1569ee0fd0a351689e3#file-m-gimple-L24> 



I rebase the patch for GCC v8.x at first:



diff --git a/gcc/fortran/trans-array.c b/gcc/fortran/trans-array.c
index 9efb531..5cf5ba9 100644
--- a/gcc/fortran/trans-array.c
+++ b/gcc/fortran/trans-array.c
@@ -91,6 +91,8 @@ along with GCC; see the file COPYING3.  If not see
 #include "dependency.h"

 static bool gfc_get_array_constructor_size (mpz_t *, 
gfc_constructor_base);
+static tree call_polly_index(stmtblock_t *parent_block, tree 
*original_index,

+ gfc_array_ref *ar);

 /* The contents of this structure aren't actually used, just the 
address.  */

 static gfc_ss gfc_ss_terminator_var;
@@ -3251,7 +3253,13 @@ gfc_conv_scalarized_array_ref (gfc_se * se, 
gfc_array_ref * ar)

   if (build_class_array_ref (se, tmp, index))
 return;

+  printf("TIMSTAMP: %s - %s\n", __DATE__, __TIME__);
+  printf("==\n");
+
+  printf("# 1. index(new):\n");
+  call_polly_index(&se->pre, &index, ar);
   se->expr = gfc_build_array_ref (tmp, index, decl);
+  printf("==\n");
 }


@@ -3335,6 +3343,22 @@ build_array_ref (tree desc, tree offset, tree 
decl, tree vptr)

   return tmp;
 }

+// See: gfc_call_malloc
+static tree call_polly_index(stmtblock_t *parent_block, tree 
*/*original_index*/,

+gfc_array_ref */*ar*/) {
+  tree fncall, var, result;
+  stmtblock_t block;
+
+  var = gfc_create_var(gfc_array_index_type, "pollyindex");
+  gfc_init_block (&block);
+
+  fncall = build_call_expr_loc(input_location, 
gfor_fndecl_polly_array_index, 0);

+  gfc_add_modify(&block, var, fold_convert(gfc_array_index_type, fncall));
+  result = gfc_finish_block (&block);
+  gfc_add_expr_to_block(parent_block, result);
+  return var;
+}
+

 /* Build an array reference.  se->expr already holds the array descriptor.
This should be either a variable, indirect variable reference or 
component

diff --git a/gcc/fortran/trans-decl.c b/gcc/fortran/trans-decl.c
index 74d8606..28ddcfd 100644
--- a/gcc/fortran/trans-decl.c
+++ b/gcc/fortran/trans-decl.c
@@ -95,6 +95,7 @@ static int seen_ieee_symbol;

 /* Function declarations for builtin library functions.  */

+tree gfor_fndecl_polly_array_index;
 tree gfor_fndecl_pause_numeric;
 tree gfor_fndecl_pause_string;
 tree gfor_fndecl_stop_numeric;
@@ -3495,6 +3496,14 @@ gfc_build_builtin_function_decls (void)
   /* ERROR STOP doesn't return.  */
   TREE_THIS_VOLATILE (gfor_fndecl_error_stop_string) = 1;

+
+  printf("building polly_array_index function decl...\n");
+  gfor_fndecl_polly_array_index = gfc_build_library_function_decl (
+get_identifier (PREFIX("polly_array_index")),
+gfc_array_index_type, 0);
+  TREE_THIS_VOLATILE (gfor_fndecl_polly_array_index) = 1;
+  printf("built polly_array_index function decl...\n");
+
   gfor_fndecl_pause_numeric = gfc_build_library_function_decl (
 get_identifier (PREFIX("pause_numeric")),
 void_type_node, 1, gfc_int4_type_node);
diff --git a/gcc/fortran/trans.h b/gcc/fortran/trans.h
index d02f347..c8d24ec 100644
--- a/gcc/fortran/trans.h
+++ b/gcc/fortran/trans.h
@@ -781,6 +781,7 @@ struct gimplify_omp_ctx;
 void gfc_omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *, tree);

 /* Runtime library function decls.  */
+extern GTY(()) tree gfor_fndecl_polly_array_index;
 extern GTY(()) tree gfor_fndecl_pause_numeric;
 extern GTY(()) tree gfor_fndecl_pause_string;
 extern GTY(()) tree gfor_fndecl_stop_numeric;







diff --git a/gcc/fortran/trans-array.c b/gcc/fortran/trans-array.c
index 9efb531..73dad6e 100644
--- a/gcc/fortran/trans-array.c
+++ b/gcc/fortran/trans-array.c
@@ -3251,6 +3251,7 @@ gfc_conv_scalarized_array_ref (gfc_se * se, 
gfc_array_ref * ar)

   if (build_class_array_ref (se, tmp, index))
 return;

+  call_polly_index(&se->pre, index, ar);
   se->expr = gfc_build_array_ref (tmp, index, decl);
 }

@@ -3335,6 +3336,24 @@ build_array_re

Re: Assigning the result of a function call to a variable in the Gfortran frontend

2017-09-05 Thread Leslie Zhai

Hi Tobias,

You are welcome!


在 2017年09月06日 13:14, Tobias Grosser 写道:

Thank you leslie!

Best,
Tobias

On Wed, Sep 6, 2017, at 05:25, Leslie Zhai wrote:


在 2017年09月05日 15:25, Leslie Zhai 写道:


在 2017年09月05日 14:14, Tobias Grosser 写道:

Hi Leslie,

I copied you in this thread as you currently worked quite a bit with
dragonegg and we are currently trying to generate metadata that makes it
easier to reason about multi-dimensional fortran arrays.

Best,
Tobias

On Mon, Sep 4, 2017, at 23:06, (IIIT) Siddharth Bhat wrote:

Hello,

I've been hacking on the Gfortran frontend to change array index
expressions to function calls, so that I can inspect them later on
in the
pipeline. I go from Fortran -> LLVM IR (through dragonegg) where I will
look at the function call nodes.

However, I'm not able to generate correct IR for this. I can create
function call, but I am unable to assign the return value of a function
call to a variable here.

Here's a link to my experiments here: It includes a patch, a test file
and
the GIMPLE output
<https://gist.github.com/bollu/999184bdb3d0f1569ee0fd0a351689e3#file-m-gimple-L24>


I rebase the patch for GCC v8.x at first:


diff --git a/gcc/fortran/trans-array.c b/gcc/fortran/trans-array.c
index 9efb531..5cf5ba9 100644
--- a/gcc/fortran/trans-array.c
+++ b/gcc/fortran/trans-array.c
@@ -91,6 +91,8 @@ along with GCC; see the file COPYING3.  If not see
   #include "dependency.h"

   static bool gfc_get_array_constructor_size (mpz_t *,
gfc_constructor_base);
+static tree call_polly_index(stmtblock_t *parent_block, tree
*original_index,
+ gfc_array_ref *ar);

   /* The contents of this structure aren't actually used, just the
address.  */
   static gfc_ss gfc_ss_terminator_var;
@@ -3251,7 +3253,13 @@ gfc_conv_scalarized_array_ref (gfc_se * se,
gfc_array_ref * ar)
 if (build_class_array_ref (se, tmp, index))
   return;

+  printf("TIMSTAMP: %s - %s\n", __DATE__, __TIME__);
+  printf("==\n");
+
+  printf("# 1. index(new):\n");
+  call_polly_index(&se->pre, &index, ar);
 se->expr = gfc_build_array_ref (tmp, index, decl);
+  printf("==\n");
   }


@@ -3335,6 +3343,22 @@ build_array_ref (tree desc, tree offset, tree
decl, tree vptr)
 return tmp;
   }

+// See: gfc_call_malloc
+static tree call_polly_index(stmtblock_t *parent_block, tree
*/*original_index*/,
+gfc_array_ref */*ar*/) {
+  tree fncall, var, result;
+  stmtblock_t block;
+
+  var = gfc_create_var(gfc_array_index_type, "pollyindex");
+  gfc_init_block (&block);
+
+  fncall = build_call_expr_loc(input_location,
gfor_fndecl_polly_array_index, 0);
+  gfc_add_modify(&block, var, fold_convert(gfc_array_index_type,
fncall));
+  result = gfc_finish_block (&block);
+  gfc_add_expr_to_block(parent_block, result);
+  return var;
+}
+

   /* Build an array reference.  se->expr already holds the array
   descriptor.
  This should be either a variable, indirect variable reference or
component
diff --git a/gcc/fortran/trans-decl.c b/gcc/fortran/trans-decl.c
index 74d8606..28ddcfd 100644
--- a/gcc/fortran/trans-decl.c
+++ b/gcc/fortran/trans-decl.c
@@ -95,6 +95,7 @@ static int seen_ieee_symbol;

   /* Function declarations for builtin library functions.  */

+tree gfor_fndecl_polly_array_index;
   tree gfor_fndecl_pause_numeric;
   tree gfor_fndecl_pause_string;
   tree gfor_fndecl_stop_numeric;
@@ -3495,6 +3496,14 @@ gfc_build_builtin_function_decls (void)
 /* ERROR STOP doesn't return.  */
 TREE_THIS_VOLATILE (gfor_fndecl_error_stop_string) = 1;

+
+  printf("building polly_array_index function decl...\n");
+  gfor_fndecl_polly_array_index = gfc_build_library_function_decl (
+get_identifier (PREFIX("polly_array_index")),
+gfc_array_index_type, 0);
+  TREE_THIS_VOLATILE (gfor_fndecl_polly_array_index) = 1;
+  printf("built polly_array_index function decl...\n");
+
 gfor_fndecl_pause_numeric = gfc_build_library_function_decl (
   get_identifier (PREFIX("pause_numeric")),
   void_type_node, 1, gfc_int4_type_node);
diff --git a/gcc/fortran/trans.h b/gcc/fortran/trans.h
index d02f347..c8d24ec 100644
--- a/gcc/fortran/trans.h
+++ b/gcc/fortran/trans.h
@@ -781,6 +781,7 @@ struct gimplify_omp_ctx;
   void gfc_omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *,
   tree);

   /* Runtime library function decls.  */
+extern GTY(()) tree gfor_fndecl_polly_array_index;
   extern GTY(()) tree gfor_fndecl_pause_numeric;
   extern GTY(()) tree gfor_fndecl_pause_string;
   extern GTY(()) tree gfor_fndecl_stop_numeric;






diff --git a/gcc/fortran/trans-array.c b/gcc/fortran/trans-array.c
index 9efb531..73dad6e 100644
--- a/gcc/fortran/trans-array.c
+++ b/gcc/fortran/trans-array.c
@@ -3251,6 +3251,7 @@ gfc_conv_scalarized_array_ref (gfc_se * se,
gfc_array_ref * ar)
if (build_class_a

Re: [llvm-dev] DragonEgg for GCC v8.x and LLVM v6.x is just able to work

2017-09-06 Thread Leslie Zhai

Dear Chris,

Thanks for your kind response!

The motivating of this work:

1. Clang can not build Linux https://bugs.llvm.org/show_bug.cgi?id=22830 
and LLVMLinux patch was not be maintained? 
http://llvm.linuxfoundation.org/index.php/Main_Page


2. Clang analyzer Frontend can not static analysis glibc or Linux 
https://bugs.llvm.org/show_bug.cgi?id=31017 but analyzer checker is able 
to find the bugs for KDE :) 
http://www.leetcode.cn/2016/11/analyzing-code-for-kde-qt-open-source-components.html


3. For leaning GCC plugin, GIMPLE, LLVM IR, GCC PASS, LLVM PASS, 
CodeGen, etc. from llvm-gcc and dragonegg, thanks for your great job!


The usecase for dragonegg:

1. mips64-linux-gnu-gcc (WIP), arm-linux-gnu-gcc and x86 GCC Frontend -> 
GIMPLE -> LLVM IR -> Assembly or for KLEE


2. GCC Frontend -> GIMPLE -> Clang AST (WIP)

I am interested in some other frontend, such as flang-clang 
https://github.com/flang-compiler/clang/pull/28 and it is glad to learn 
from other developers :) https://gcc.gnu.org/ml/gcc/2017-09/msg00022.html



在 2017年09月07日 12:10, Chris Lattner 写道:

On Sep 4, 2017, at 8:13 PM, Leslie Zhai via llvm-dev  
wrote:

Hi LLVM and GCC developers,

LLVM China  http://www.llvm.org.cn  forked DragonEgg 
https://github.com/LLVM-China/dragonegg  because:

* Some subprojects are impractical or uninteresting to relicense (e.g. llvm-gcc 
 and dragonegg). These will be split off from the LLVM project (e.g. to 
separate Github projects), allowing interested people to continue their 
development elsewhere. 
http://lists.llvm.org/pipermail/llvm-dev/2017-August/116266.html

* There are a lot of issues https://github.com/xiangzhai/dragonegg/issues  so I 
need smarter developers' help.

Hi Leslie,

Out of curiosity, what is motivating this work?  What is the usecase for 
dragonegg these days, now that Clang has great C++ support?  Are you interested 
in Ada + LLVM or some other frontend?

-Chris




--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/





Register Allocation Graph Coloring algorithm and Others

2017-12-14 Thread Leslie Zhai

Hi GCC and LLVM developers,

I am learning Register Allocation algorithms and I am clear that:

* Unlimited VirtReg (pseudo) -> limited or fixed or alias[1] PhysReg (hard)

* Memory (20 - 100 cycles) is expensive than Register (1 cycle), but it 
has to spill code when PhysReg is unavailable


* Folding spill code into instructions, handling register coallescing, 
splitting live ranges, doing rematerialization, doing shrink wrapping 
are harder than RegAlloc


* LRA and IRA is default Passes in RA for GCC:

$ /opt/gcc-git/bin/gcc hello.c
DEBUG: ../../gcc/lra.c, lra_init_once, line 2441
DEBUG: ../../gcc/ira-build.c, ira_build, line 3409

* Greedy is default Pass for LLVM

But I have some questions, please give me some hint, thanks a lot!

* IRA is regional register allocator performing graph coloring on a 
top-down traversal of nested regions, is it Global? compares with Local LRA


* The papers by Briggs and Chaiten contradict[2] themselves when examine 
the text of the paper vs. the pseudocode provided?


* Why  interference graph is expensive to build[3]?

And I am practicing[4] to use HEA, developed by Dr. Rhydian Lewis, for 
LLVM firstly.



[1] https://reviews.llvm.org/D39712

[2] http://lists.llvm.org/pipermail/llvm-dev/2008-March/012940.html

[3] https://github.com/joaotavio/llvm-register-allocator

[4] https://github.com/xiangzhai/llvm/tree/avr/include/llvm/CodeGen/GCol

--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/





Re: Register Allocation Graph Coloring algorithm and Others

2017-12-14 Thread Leslie Zhai

Hi Vladimir,

Thanks for your kind and very detailed response!


在 2017年12月15日 12:40, Vladimir Makarov 写道:



On 12/14/2017 10:18 PM, Leslie Zhai wrote:

Hi GCC and LLVM developers,

I am learning Register Allocation algorithms and I am clear that:

* Unlimited VirtReg (pseudo) -> limited or fixed or alias[1] PhysReg 
(hard)


* Memory (20 - 100 cycles) is expensive than Register (1 cycle), but 
it has to spill code when PhysReg is unavailable



It might be much less if memory value is in L1 cache.
* Folding spill code into instructions, handling register 
coallescing, splitting live ranges, doing rematerialization, doing 
shrink wrapping are harder than RegAlloc


RegAlloc is in a wide sense includes all this tasks and more.  For 
some architectures, other tasks like a right live range splitting 
might be even more important for generated code quality than just 
better graph coloring.

* LRA and IRA is default Passes in RA for GCC:

$ /opt/gcc-git/bin/gcc hello.c
DEBUG: ../../gcc/lra.c, lra_init_once, line 2441
DEBUG: ../../gcc/ira-build.c, ira_build, line 3409

* Greedy is default Pass for LLVM

But I have some questions, please give me some hint, thanks a lot!

* IRA is regional register allocator performing graph coloring on a 
top-down traversal of nested regions, is it Global? compares with 
Local LRA

IRA is a global RA.  The description of its initial version can be found

https://vmakarov.fedorapeople.org/vmakarov-submission-cgo2008.pdf

I am reading this paper at present :)





LRA in some way is also global RA but it is a very simplified version 
of global RA (e.g. LRA does not use conflict graph and its coloring 
algoritm is closer to priority coloring).  LRA does a lot of other 
very complicated things besides RA, for example instruction selection 
which is quite specific to GCC machine description. Usually code 
selection task is a separate pass in other compilers. Generally 
speaking LRA is more complicated, machine dependent and more buggy 
than IRA.  But fortunately LRA is less complicated than its 
predecessor so called reload pass.


IRA and LRA names have a long history and they do not reflect 
correctly the current situation.


It would be possible to incorporate LRA tasks into IRA, but the final 
RA would be much slower, even more complicated and hard to maintain 
and the generated code would be not much better.  So to improve RA 
maintainability, RA is divided on two parts solving a bit different 
tasks.  This is a typical engineering approach.

I am debugging by printf to be familiar with LRA and IRA.






* The papers by Briggs and Chaiten contradict[2] themselves when 
examine the text of the paper vs. the pseudocode provided?
I don't examine Preston Briggs work so thoroughly.  So I can not say 
that is true.  Even so it is natural that there are discrepancy in 
pseudocode and its description especially for such size description.


For me Preston Briggs is famous for his introduction of optimistic 
coloring.


* Why  interference graph is expensive to build[3]?

That is because it might be N^2 algorithm.  There are a lot of 
publications investigating building conflict graphs and its cost in RAs.
And I am practicing[4] to use HEA, developed by Dr. Rhydian Lewis, 
for LLVM firstly.


When I just started to work on RAs very long ago I used about the same 
approach: a lot of tiny transformations directed by a cost function 
and using metaheuristics (I also used tabu search as HEA). Nothing 
good came out of this.
Thanks for your lesson! But are there some benchmarks when you used Tabu 
search as HEA, AntCol, etc. such as 
https://pbs.twimg.com/media/DRD-kxcUMAAxZec.jpg






If you are interesting in RA algorithms and architectures, I'd 
recommend Michael Matz article


ftp://gcc.gnu.org/pub/gcc/summit/2003/Graph%20Coloring%20Register%20Allocation.pdf 



as a start point.

Thanks! I am reading it.




[1] https://reviews.llvm.org/D39712

[2] http://lists.llvm.org/pipermail/llvm-dev/2008-March/012940.html

[3] https://github.com/joaotavio/llvm-register-allocator

[4] https://github.com/xiangzhai/llvm/tree/avr/include/llvm/CodeGen/GCol





--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/





Re: Register Allocation Graph Coloring algorithm and Others

2017-12-18 Thread Leslie Zhai

Hi David,

Thanks for your teaching!

I am a newbie in compiler area, I only learned Compiler Principle in 
2002 https://www.leetcode.cn/2017/12/ilove-compiler-principle.html


But I like to practice and learn :) 
https://github.com/xiangzhai/llvm/blob/avr/lib/CodeGen/RegAllocGraphColoring.cpp#L327 
because theory is not always correct, or misunderstood by people, so I 
want to compare solutionByHEA, IRA, Greedy, PBQP and other algorithms.


Thanks for your lessons to correct my mistakes, such as memory=bad 
register=good, and I need to find the answer *when* memory is worse than 
a register, I am maintaining AVR target, there are 32 general registers, 
32K flash, 2K sram 
http://www.atmel.com/Images/Atmel-42735-8-bit-AVR-Microcontroller-ATmega328-328P_Datasheet.pdf 
so perhaps to MCU, memory might be expensive than register? but what 
about AMDGPU or VLIW processors? I don't have experienced on them, 
please teach me.


I am reading LLVM's code SpillXXX, LiveRangeXXX, RegisterCoalescer, etc. 
to get the whole view of CodeGen.


I am reading Dr. Rhydian Lewis's book: A Guide to Graph Colouring: 
Algorithms and Applications 
http://www.springer.com/us/book/9783319257280   and other papers, even 
if HEA is not the best solution, I still want to practice and see the 
benchmark, I am not computing professionals, I am only 34 olds, perhaps 
I have enough time to waste :)



在 2017年12月19日 00:41, d...@cray.com 写道:

Leslie Zhai  writes:


* Memory (20 - 100 cycles) is expensive than Register (1 cycle), but
it has to spill code when PhysReg is unavailable

As Vladimir said, the cache makes this kind of analysis much more
tricky.  It's not necessarily the case that memory=bad and
register=good.  Since there are tradeoffs involved, one needs to
evaluate different strategies to determine *when* memory is worse than a
register.  It may very well be the case that leaving something in memory
frees up a register for something much more important to use it.  All of
the register allocation algorithms try to determine this kind of thing
through various heuristics.  Which heuristic is most effective is highly
target-dependent.

In my experience, changing heuristics can swing performance 20% or more
in some cases.  Today's processors and memory systems are so complex
that 2nd- and even 3rd-order effects become important.

It is very, very wrong on today's machines to use # of spills as a
metric to determine the "goodness" of an allocation.  Determining *what*
to spill is much more important than the raw number of spills.  Many
times I have a seen codes generated with more spills perform much better
than the code generated with fewer spills.  Almost all of the papers
around the time of Chaiten-Briggs used # of spills as the metric.  That
may have been appropriate at that time but take those results with giant
grains of salt today.  Of course they are still very good papers for
understanding algorithms and heuristics.

The best way I know to determine what's best for your target is to run a
whole bunch of *real* codes on them, trying different allocation
algorithms and heuristics.  It is a lot of work, still worthy of a
Ph.D. even today.  Register allocation is not a "solved" problem and
probably never will be as architectures continue to change and become
ever more diverse.


* Folding spill code into instructions, handling register coallescing,
splitting live ranges, doing rematerialization, doing shrink wrapping
are harder than RegAlloc

Again, as Vladimir said, they are all part of register allocation.
Sometimes they are implemented as separate passes but logically they all
contribute work to the task of assigning registers as efficiently as
possible.  And all of them use heuristics.  Choosing when and when not
to, for example, coalesce can be important.  Splitting live ranges is
logically the opposite of coalescing.  Theoretically one can "undo" a
bad coalescing decision by re-splitting the live range but it's usually
not that simple as other decisions in the interim can make that tricky
if not impossible.  It is a delicate balancing act.


* The papers by Briggs and Chaiten contradict[2] themselves when
examine the text of the paper vs. the pseudocode provided?

As others have said, I don't recall any inconsistencies but that doesn't
mean there aren't bugs and/or incomplete descriptions open to
interpretation.  One of my biggest issues with our computer academic
culture is that we do not value repeatability.  It is virtually
impossible to take a paper, implement the algorithm as described (or as
best as possible given ambiguity) and obtain the same results.  Heck,
half my Ph.D. dissertation was dissecting a published paper, examining
the sensitivity of the described algorithm to various parts of the
described heuristic that were ambiguous.  By interpreting the heuristic
description in different ways I observed very different results.  I

Re: Register Allocation Graph Coloring algorithm and Others

2017-12-18 Thread Leslie Zhai

Hi Michael,

Thanks for your sharing!

I will read the papers as you suggested, and I asked Quantum Computing 
professionals about solving the NP-complete problem 
https://github.com/epiqc/ScaffCC/issues/14 but GCC's IRA and LRA proved 
that there is a solution in SSA form for classical computer.


Sorting MachineBasicBlock by frequency firstly is a good idea, and I 
only experienced some PASS, such as LoopUnroll 
http://lists.llvm.org/pipermail/llvm-dev/2017-October/118419.html but I 
will practice your idea in my solutionByHEA 
https://github.com/xiangzhai/llvm/blob/avr/lib/CodeGen/RegAllocGraphColoring.cpp#L327


I experienced binary translation from X86 to Mips, QEMU is expensive 
https://www.leetcode.cn/2017/09/tcg-ir-to-llvm-ir.html I will bookmark 
your JIT engine to my blog :)



在 2017年12月19日 08:07, Michael Clark 写道:

Hi Leslie,

I suggest adding these 3 papers to your reading list.

Register allocation for programs in SSA-form
Sebastian Hack, Daniel Grund, and Gerhard Goos
http://www.rw.cdl.uni-saarland.de/~grund/papers/cc06-ra_ssa.pdf

Simple and Efficient Construction of Static Single Assignment Form
Matthias Braun , Sebastian Buchwald , Sebastian Hack , Roland Leißa , 
Christoph Mallon , and Andreas Zwinkau
https://www.info.uni-karlsruhe.de/uploads/publikationen/braun13cc.pdf

Optimal register allocation for SSA-form programs in polynomial time
Sebastian Hack, Gerhard Goos
http://web.cs.ucla.edu/~palsberg/course/cs232/papers/HackGoos-ipl06.pdf

A lot of the earlier literature regarding the register allocation problem 
describes the general graph colouring problem as NP-complete, however previous 
research in Register Allocation has been in the context of programs that were 
not in SSA form. i.e. the Chaitin-Briggs paper states that register allocation 
is NP-complete and proposes an iterative algorithm.

If one reads Hack Goos, there is the discovery that programs that are in SSA 
form have chordal graphs, and the colouring algorithm for chordal graphs can be 
completed in polynomial time. After the cost of building the interference 
graph, it is possible to perform register allocation in a single pass. The key 
is in not modifying the graph.

If one has frequency for each basic block, then one can sort basic blocks by 
frequency, allocating the highest frequency blocks first, and where possible 
assigning the same physcial register to all virtual registers in each phi node 
(to avoid copies). At program points where the live set is larger than k, the 
set of physical registers, one spills the the register that has the largest 
distance between its next use. At least that is how I am thinking about this 
problem. I am also a novice with regards to register allocation.

I intend to develop a register allocator for use in this JIT engine:

rv8: a high performance RISC-V to x86 binary translator
Michael Clark, Bruce Hoult
https://carrv.github.io/papers/clark-rv8-carrv2017.pdf

Our JIT already performs almost twice as fast a QEMU and we are using a static 
register allocation, and QEMU i believe has a register allocator. We are 
mapping a 31 register RISC architecture to a 16 register CISC architecture. I 
have statistics on the current slow-down, and it appears to mainly be L1 
accesses to spilled registers. I believe after we have implemented a register 
allocator in our JIT we will be able to run RISC-V binaries at near native 
performance on x86-64. In fact given we are performing runtime profile guided 
optimisation, it may even be possible for some benchmarks to run faster than 
register allocations that are based on static estimates of loop frequencies.

https://anarch128.org/~mclark/rv8-slides.pdf
https://rv8.io/bench

We’ve still got a long way to go to get to ~1:1 performance for RISC-V on 
x86-64, but I think it is possible, at least for some codes…

Regards,
Michael.


On 15/12/2017, at 4:18 PM, Leslie Zhai  wrote:

Hi GCC and LLVM developers,

I am learning Register Allocation algorithms and I am clear that:

* Unlimited VirtReg (pseudo) -> limited or fixed or alias[1] PhysReg (hard)

* Memory (20 - 100 cycles) is expensive than Register (1 cycle), but it has to 
spill code when PhysReg is unavailable

* Folding spill code into instructions, handling register coallescing, 
splitting live ranges, doing rematerialization, doing shrink wrapping are 
harder than RegAlloc

* LRA and IRA is default Passes in RA for GCC:

$ /opt/gcc-git/bin/gcc hello.c
DEBUG: ../../gcc/lra.c, lra_init_once, line 2441
DEBUG: ../../gcc/ira-build.c, ira_build, line 3409

* Greedy is default Pass for LLVM

But I have some questions, please give me some hint, thanks a lot!

* IRA is regional register allocator performing graph coloring on a top-down 
traversal of nested regions, is it Global? compares with Local LRA

* The papers by Briggs and Chaiten contradict[2] themselves when exa

Re: [llvm-dev] Register Allocation Graph Coloring algorithm and Others

2017-12-18 Thread Leslie Zhai

Hi Matthias,

Thanks for your hint!

It is just for learning and practicing for me, just like migrate 
DragonEgg 
http://lists.llvm.org/pipermail/llvm-dev/2017-September/117201.html the 
motivating is for learning from GCC and LLVM developers.



在 2017年12月19日 10:07, Matthias Braun 写道:



On Dec 18, 2017, at 9:52 AM, Leslie Zhai via llvm-dev 
mailto:llvm-...@lists.llvm.org>> wrote:


Hi David,

Thanks for your teaching!

I am a newbie in compiler area, I only learned Compiler Principle in 
2002https://www.leetcode.cn/2017/12/ilove-compiler-principle.html


But I like to practice and learn 
:)https://github.com/xiangzhai/llvm/blob/avr/lib/CodeGen/RegAllocGraphColoring.cpp#L327because 
theory is not always correct, or misunderstood by people, so I want 
to compare solutionByHEA, IRA, Greedy, PBQP and other algorithms.


Just as another tip:
- Indeed in my experience: Just implementing some algorithms yourself 
and comparing them against what existing compilers produce and then 
figuring out why is the best way to learn about allocators.
- Don't just put emphasis on all the different different coloring 
techniques. In practice it is usually the way you deal register 
constraints and other target specific coloring constraints, 
rematerialization and how you get coalescing into the picture. Most 
regalloc papers don't talk too much about that as it's highly finicky 
and often target specific. But they do have a huge impact on 
allocation quality and can make or break any of those algorithms...


- Matthias



Thanks for your lessons to correct my mistakes, such as memory=bad 
register=good, and I need to find the answer *when* memory is worse 
than a register, I am maintaining AVR target, there are 32 general 
registers, 32K flash, 2K 
sramhttp://www.atmel.com/Images/Atmel-42735-8-bit-AVR-Microcontroller-ATmega328-328P_Datasheet.pdfso 
perhaps to MCU, memory might be expensive than register? but what 
about AMDGPU or VLIW processors? I don't have experienced on them, 
please teach me.


I am reading LLVM's code SpillXXX, LiveRangeXXX, RegisterCoalescer, 
etc. to get the whole view of CodeGen.


I am reading Dr. Rhydian Lewis's book: A Guide to Graph Colouring: 
Algorithms and 
Applicationshttp://www.springer.com/us/book/9783319257280   and other 
papers, even if HEA is not the best solution, I still want to 
practice and see the benchmark, I am not computing professionals, I 
am only 34 olds, perhaps I have enough time to waste :)



在 2017年12月19日 00:41,d...@cray.com <mailto:d...@cray.com>写道:
Leslie Zhai mailto:lesliez...@llvm.org.cn>> 
writes:



* Memory (20 - 100 cycles) is expensive than Register (1 cycle), but
it has to spill code when PhysReg is unavailable

As Vladimir said, the cache makes this kind of analysis much more
tricky.  It's not necessarily the case that memory=bad and
register=good.  Since there are tradeoffs involved, one needs to
evaluate different strategies to determine *when* memory is worse than a
register.  It may very well be the case that leaving something in memory
frees up a register for something much more important to use it.  All of
the register allocation algorithms try to determine this kind of thing
through various heuristics.  Which heuristic is most effective is highly
target-dependent.

In my experience, changing heuristics can swing performance 20% or more
in some cases.  Today's processors and memory systems are so complex
that 2nd- and even 3rd-order effects become important.

It is very, very wrong on today's machines to use # of spills as a
metric to determine the "goodness" of an allocation.  Determining *what*
to spill is much more important than the raw number of spills.  Many
times I have a seen codes generated with more spills perform much better
than the code generated with fewer spills.  Almost all of the papers
around the time of Chaiten-Briggs used # of spills as the metric.  That
may have been appropriate at that time but take those results with giant
grains of salt today.  Of course they are still very good papers for
understanding algorithms and heuristics.

The best way I know to determine what's best for your target is to run a
whole bunch of *real* codes on them, trying different allocation
algorithms and heuristics.  It is a lot of work, still worthy of a
Ph.D. even today.  Register allocation is not a "solved" problem and
probably never will be as architectures continue to change and become
ever more diverse.


* Folding spill code into instructions, handling register coallescing,
splitting live ranges, doing rematerialization, doing shrink wrapping
are harder than RegAlloc

Again, as Vladimir said, they are all part of register allocation.
Sometimes they are implemented as separate passes but logically they all
contribute work to the task of assigning registers as efficiently as
possible.  And all of them use heuristics.  Choosing when and when not
to, for

Re: Register Allocation Graph Coloring algorithm and Others

2017-12-20 Thread Leslie Zhai

Hi Jakob,

Thanks for your kind response!

My usecase is for AVR and RISCV targets, and I just want to learn and 
practice HEA in RA, thanks for your sharing.



在 2017年12月21日 01:25, Jakob Stoklund Olesen 写道:


On Dec 18, 2017, at 19:03, Leslie Zhai <mailto:lesliez...@llvm.org.cn>> wrote:


Hi Leslie,

As others have pointed out, the notion that register allocation is 
isomorphic to graph coloring is poppycock. There are other important 
aspects, in particular the placement of spill/fill/copy instructions. 
The importance of graph coloring relative to spill code placement 
depends on how many registers you have available. If you are 
generating code for 32-bit x86 which has only 6-7 general purpose 
registers, you will have so much spill code and short live ranges that 
graph coloring doesn’t matter much at all. On the other hand, if you 
have 32 registers like Chaitin did, you have much less spilling in 
typical code, and the graph coloring aspect becomes important.


Early compilers would keep each local variable in a stack slot, and 
the register allocation optimization would literally allocate a whole 
local variable to a register. The C “register” keyword makes sense in 
that context. Later improvements like copy coalescing and live range 
splitting meant that multiple local variables could use the same 
register and a variable could live in different places at different 
times. It is sometimes useful to take this development to its logical 
extreme and look at register allocation as a caching problem: The 
register allocator’s job is to make sure that values are available to 
the instructions the need them, using the registers as a cache to get 
the values there in the most efficient way possible.


Guo, J., Garzarán, M. J., & Padua, D. (2004). The Power of
Belady’s Algorithm in Register Allocation for Long Basic Blocks.
In Languages and Compilers for Parallel Computing (Vol. 2958, pp.
374–389). Berlin, Heidelberg: Springer Berlin Heidelberg.
http://doi.org/10.1007/978-3-540-24644-2_24

Braun, M., & Hack, S. (2009). Register spilling and live-range
splitting for SSA-form programs. International Conference on
Compiler Construction.


When you look at register allocation that way, the graph coloring 
aspect almost disappears. The optimum approach is probably somewhere 
in the middle.


A third important aspect is register constraints on individual 
instructions. Sometimes you almost need a little constraint solver 
just to figure out a valid register assignment for a single 
instruction. Preston Briggs dealt with this in his thesis, but it 
hasn’t gotten as much attention as graph coloring since.


Pereira, F. Q., & Palsberg, J. (2008). Register allocation by
puzzle solving.


Regards,
/jakob



--
Regards,
Leslie Zhai - https://reviews.llvm.org/p/xiangzhai/






Re: [llvm-dev] Register Allocation Graph Coloring algorithm and Others

2017-12-21 Thread Leslie Zhai

Hi Bruce,

Thanks for your sharing!

I am porting GlobalISel to RISCV target[1], the highest priority in the 
TODO list[2], welcome to contribute to lowRISC, if fixed all the issues, 
then I could try to implement RegAllocGraphColoring in HEA and write 
great Machine Schedulers.


[1] https://github.com/lowRISC/riscv-llvm/issues/19
[2] https://github.com/lowRISC/riscv-llvm/issues

在 2017年12月21日 19:09, Bruce Hoult 写道:
So, both AVR and RISC-V are fairly register-rich with usually 32. 
RV32E only has 16, but that's still a lot better than i386. If you use 
a lot of 16 bit integers then AVR also only has effectively 16 
registers (or a more with a mix of 8 and 16 bit variables). 32 bit 
integers should be rare in AVR code, but soft float/double variables 
are common in Arduino code (both are implemented as 32 bits), so you 
only have room for 8 of those.


RISC-V doesn't have any hard constraints on something that *must* go 
in a certain register, except the usual argument passing/return 
convention. There is a an advantage to allocating both the data 
src/dst register and the pointer base register for a load or store 
from x8-x15 (s0-1,a0-5) as much as possible as this allows the 
assembler to use a two byte instruction instead of a four byte 
instruction.


I haven't look at AVR in detail for a while, but I seem to recall the 
top six registers make up three 16 bit pointer registers X,Y,Z. Any of 
them can be used for (C language) *p, *--p, *p++, only Y&Z can be used 
for p->foo, and only Z can be used for computed jumps (including 
function link register) or loading constants from program memory. Also 
the various multiply instructions take their 8 bit operands from any 
registers but always produce the 16 bit result in r1:r0. Annoying but 
nowhere near as bad as i386 as r0 and r1 are not used for anything 
else. The usual ABI makes r0 a clobber-at-will temp. r1 is supposed to 
be "always zero", so you need to CLR it after retrieving (or ignoring) 
the high bits of a multiply result.


On Thu, Dec 21, 2017 at 3:44 AM, Leslie Zhai via llvm-dev 
mailto:llvm-...@lists.llvm.org>> wrote:


Hi Jakob,

Thanks for your kind response!

My usecase is for AVR and RISCV targets, and I just want to learn
and practice HEA in RA, thanks for your sharing.


在 2017年12月21日 01:25, Jakob Stoklund Olesen 写道:


    On Dec 18, 2017, at 19:03, Leslie Zhai
mailto:lesliez...@llvm.org.cn>
<mailto:lesliez...@llvm.org.cn
<mailto:lesliez...@llvm.org.cn>>> wrote:


Hi Leslie,

As others have pointed out, the notion that register
allocation is isomorphic to graph coloring is poppycock. There
are other important aspects, in particular the placement of
spill/fill/copy instructions. The importance of graph coloring
relative to spill code placement depends on how many registers
you have available. If you are generating code for 32-bit x86
which has only 6-7 general purpose registers, you will have so
much spill code and short live ranges that graph coloring
doesn’t matter much at all. On the other hand, if you have 32
registers like Chaitin did, you have much less spilling in
typical code, and the graph coloring aspect becomes important.

Early compilers would keep each local variable in a stack
slot, and the register allocation optimization would literally
allocate a whole local variable to a register. The C
“register” keyword makes sense in that context. Later
improvements like copy coalescing and live range splitting
meant that multiple local variables could use the same
register and a variable could live in different places at
different times. It is sometimes useful to take this
development to its logical extreme and look at register
allocation as a caching problem: The register allocator’s job
is to make sure that values are available to the instructions
the need them, using the registers as a cache to get the
values there in the most efficient way possible.

    Guo, J., Garzarán, M. J., & Padua, D. (2004). The Power of
    Belady’s Algorithm in Register Allocation for Long Basic
Blocks.
    In Languages and Compilers for Parallel Computing (Vol.
2958, pp.
    374–389). Berlin, Heidelberg: Springer Berlin Heidelberg.
http://doi.org/10.1007/978-3-540-24644-2_24
<http://doi.org/10.1007/978-3-540-24644-2_24>

    Braun, M., & Hack, S. (2009). Register spilling and live-range
    splitting for SSA-form programs. International Conference on
    Compiler Construction.


When you look at register allocation that way, the graph
coloring aspect almost disappears. The optimum approach is
probably 

Re: [llvm-dev] GCC 5 and -Wstrict-aliasing in JSON.h

2018-08-08 Thread Leslie Zhai
json::Value::as() const [with T = llvm::json::Object]’:

/home/loongson/llvm/include/llvm/Support/JSON.h:424:62:   required from here
/home/loongson/llvm/include/llvm/Support/JSON.h:455:47: warning: 
dereferencing type-punned pointer will break strict-aliasing rules 
[-Wstrict-aliasing]
/home/loongson/llvm/include/llvm/Support/JSON.h: In instantiation of ‘T& 
llvm::json::Value::as() const [with T = llvm::json::Array]’:

/home/loongson/llvm/include/llvm/Support/JSON.h:430:60:   required from here
/home/loongson/llvm/include/llvm/Support/JSON.h:455:47: warning: 
dereferencing type-punned pointer will break strict-aliasing rules 
[-Wstrict-aliasing]



Hi GCC developers,

Thanks for your patch to gcc-7-branch!

Could you test to compile LLVM with GCC old versions 4/5/6? Does it need 
to backport your patch to GCC old version?



1.
$ cat punning.cpp
template
struct aligned_storage
{
  union type
{
  unsigned char __data[_Len];
  struct __attribute__((__aligned__((_Align { } __align;
};
};

aligned_storage::type storage;

int main()
{
  *reinterpret_cast(&storage) = 42;
}

2.
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/libexec/gcc/mips64el-redhat-linux/4.9.3/lto-wrapper
Target: mips64el-redhat-linux
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man 
--infodir=/usr/share/info 
--with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-bootstrap 
--enable-shared --enable-threads=posix --enable-checking=release 
--enable-multilib --with-system-zlib --enable-__cxa_atexit 
--disable-libunwind-exceptions --enable-gnu-unique-object 
--enable-linker-build-id --with-arch=loongson3a 
--enable-languages=c,c++,objc,obj-c++,fortran,go,lto --enable-plugin 
--disable-libgcj 
--with-isl=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/isl-install 
--with-cloog=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/cloog-install 
--enable-gnu-indirect-function --with-long-double-128 
--build=mips64el-redhat-linux

Thread model: posix
gcc version 4.9.3 20150626 (Red Hat 4.9.3-8) (GCC)


在 2018年08月09日 04:31, Kim Gräsman via llvm-dev 写道:

Hello,

For the IWYU project, we have a buildbot on Ubuntu 16.04 and its
bundled GCC (which I think is some GCC 5 variant).

We're getting a number of -Wstrict-aliasing warnings from JSON.h on this line:
https://github.com/llvm-mirror/llvm/blob/master/include/llvm/Support/JSON.h#L455

I'm not sure if GCC has a point here but GCC 7.2 does not complain, so
I'm going to guess no.

Would you consider patches to disable -Wstrict-aliasing wholesale for
GCC 5 and older?
But it is *no* warning when bootstrap with LLVM toolchain, and Sam 
should test it before code review https://reviews.llvm.org/D45753




- Kim
___
LLVM Developers mailing list
llvm-...@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev


--
Regards,
Leslie Zhai




Re: [llvm-dev] GCC 5 and -Wstrict-aliasing in JSON.h

2018-08-09 Thread Leslie Zhai

Hi Jonathan,

Thanks for your response!

So workaround for Kim's issue is bootstrap old version LLVM with GCC 4/5 
to build old clang, then bootstrap latest LLVM with old clang.



在 2018年08月09日 17:16, Jonathan Wakely 写道:

On Thu, 9 Aug 2018 at 03:09, Leslie Zhai wrote:

Could you test to compile LLVM with GCC old versions 4/5/6? Does it need
to backport your patch to GCC old version?

GCC versions before 6.4 are not supported, so no backports will happen
to 4.x or 5 releases and I doubt anybody's going to routinely test
anything with them. If there's a bug in GCC 4.9.3 that you can't work
around then you should upgrade to a supported release (or use a
distribution that provides support for older releases).


--
Regards,
Leslie Zhai




Re: [llvm-dev] GCC 5 and -Wstrict-aliasing in JSON.h

2018-08-09 Thread Leslie Zhai

Hi Sam,

Thanks for your response!

Please review it, thanks a lot!

A patch by Loongson!

diff --git a/include/llvm/Support/JSON.h b/include/llvm/Support/JSON.h
index da3c5ea..fd60b40 100644
--- a/include/llvm/Support/JSON.h
+++ b/include/llvm/Support/JSON.h
@@ -452,7 +452,10 @@ private:
 new (reinterpret_cast(Union.buffer)) T(std::forward(V)...);
   }
   template  T &as() const {
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wstrict-aliasing"
 return *reinterpret_cast(Union.buffer);
+#pragma GCC diagnostic pop
   }

   template 


在 2018年08月09日 19:25, Sam McCall 写道:
Author of the problematic code here. Thanks everyone, and sorry to 
have caused difficulty!


Obviously if there really is something illegal here we should fix it 
in LLVM, but it looks like this warning is a false positive (anyone 
disagree?)

False positive!



Still if there's a simple source-level workaround, or we can suppress 
the warning with a #pragma, I'd be happy to do that. GCC 4.9.3 is a 
supported compiler for LLVM and the more configurations we build 
cleanly in, the better.


If this is a useful direction, could someone with an affected 
environment send me a small patch? I don't have the right setup to 
verify myself.

I test it for mips64el built with gcc-4-branch:
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/libexec/gcc/mips64el-redhat-linux/4.9.3/lto-wrapper
Target: mips64el-redhat-linux
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man 
--infodir=/usr/share/info 
--with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-bootstrap 
--enable-shared --enable-threads=posix --enable-checking=release 
--enable-multilib --with-system-zlib --enable-__cxa_atexit 
--disable-libunwind-exceptions --enable-gnu-unique-object 
--enable-linker-build-id --with-arch=loongson3a 
--enable-languages=c,c++,objc,obj-c++,fortran,go,lto --enable-plugin 
--disable-libgcj 
--with-isl=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/isl-install 
--with-cloog=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/cloog-install 
--enable-gnu-indirect-function --with-long-double-128 
--build=mips64el-redhat-linux

Thread model: posix
gcc version 4.9.3 20150626 (Red Hat 4.9.3-8) (GCC)



Cheers, Sam


--
Regards,
Leslie Zhai




[MIPS] hsdis need non-executable PT_GNU_STACK support

2018-08-14 Thread Leslie Zhai

Hi all,

hsdis PrintLIRWithAssembly failed to work for mips64el after upgraded to 
jdk8u181-b13.


http://mail.openjdk.java.net/pipermail/jdk8u-dev/2018-August/007753.html

The root cause is the patch [MIPS] Enable non-executable PT_GNU_STACK 
support, contributed by Faraz in 2016 February, had not been merged by 
GCC toolchain upstream.


https://gcc.gnu.org/ml/gcc-patches/2016-02/msg00444.html

And Maciej also need to increase `MAJOR_VERSION` to check whether or not 
support IFUNC, unfortunately still not merged by upstream.


https://sourceware.org/ml/libc-alpha/2016-12/msg00856.html

But I would apply the patch and rebuild gcc-8.1, binutils-gdb-2.30, 
glibc-2.27, to support Faraz, Joseph and Maciej :)


Thanks for your great job!


在 2018年08月14日 14:15, Florian Weimer 写道:

On 08/14/2018 04:08 AM, Leslie Zhai wrote:
But workaround for mips64el's PrintLIRWithAssembly is adding 
-Wl,-z,noexecstack linking flag, strangely X86 does *not* need such 
flag, so I am investigating the root cause.


MIPS soft-float apparently needs an executable stack:

<https://sourceware.org/ml/libc-alpha/2016-01/msg00567.html>
<https://sourceware.org/ml/libc-alpha/2016-01/msg00719.html>

This could be why the toolchain does not specify a non-executable 
stack by default.


Florian


--
Regards,
Leslie Zhai




Re: [MIPS] hsdis need non-executable PT_GNU_STACK support

2018-08-14 Thread Leslie Zhai

Hi Joseph,

Thanks for your response!

hsdis is just able to workaround when linking with -Wl,-z,noexecstack 
flag, and my environment:


$ uname -a
Linux localhost.localdomain 3.10.84-19.fc21.loongson.2.mips64el #1 SMP 
PREEMPT Fri Jul 6 18:47:47 CST 2018 mips64 mips64 mips64 GNU/Linux


$ gcc -v
Using built-in specs.
COLLECT_GCC=gcc
COLLECT_LTO_WRAPPER=/usr/libexec/gcc/mips64el-redhat-linux/4.9.3/lto-wrapper
Target: mips64el-redhat-linux
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man 
--infodir=/usr/share/info 
--with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-bootstrap 
--enable-shared --enable-threads=posix --enable-checking=release 
--enable-multilib --with-system-zlib --enable-__cxa_atexit 
--disable-libunwind-exceptions --enable-gnu-unique-object 
--enable-linker-build-id --with-arch=loongson3a 
--enable-languages=c,c++,objc,obj-c++,fortran,go,lto --enable-plugin 
--disable-libgcj 
--with-isl=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/isl-install 
--with-cloog=/builddir/build/BUILD/gcc-4.9.3/obj-mips64el-redhat-linux/cloog-install 
--enable-gnu-indirect-function --with-long-double-128 
--build=mips64el-redhat-linux

Thread model: posix
gcc version 4.9.3 20150626 (Red Hat 4.9.3-8) (GCC)

$ ld -v
GNU ld version 2.24

$ rpm -q glibc
glibc-2.20-15.fc21.loongson.10.mips64el

But I want to find out the root cause, I have no idea whether or not 
kernel supported ELF MIPS_GNU_STACK:


+ /* Flag to indicate that non-executable stack supported by kernel.
+Ref: arch/mips/include/asm/elf.h in kernel sources. */
+#define AV_FLAGS_MIPS_GNU_STACK(1 << 24)

https://sourceware.org/ml/libc-alpha/2016-01/msg00568.html

But what is the status of kernel and toolchain for X86? Why it is *not* able to 
reproduce the hsdis issue for X86?

And I can prepare the test environment with the latest kernel and toolchain 
applied with your patch. Please give me some suggestion to support your job, 
thanks a lot!


在 2018年08月14日 17:43, Joseph Myers 写道:

On Tue, 14 Aug 2018, Leslie Zhai wrote:


The root cause is the patch [MIPS] Enable non-executable PT_GNU_STACK support,
contributed by Faraz in 2016 February, had not been merged by GCC toolchain
upstream.

https://gcc.gnu.org/ml/gcc-patches/2016-02/msg00444.html

Was there a non-RFC GCC patch posting?  RFC means you're looking for
comments with a view to producing later patch versions, not for an actual
review with a view to getting that version of the changes checked in.

As noted in <https://sourceware.org/ml/libc-alpha/2016-12/msg00853.html>
you'll need a non-RFC glibc patch posting, with architecture-independent
and MIPS-specific parts split out, and with comments pointing to the
upstream releases of kernel, GCC, binutils with relevant support.



--
Regards,
Leslie Zhai