* Re: [tree-ssa] Simplifying TARGET_EXPR @ 2002-07-20 18:54 Jason Merrill 2002-07-21 0:41 ` Richard Henderson 2002-07-21 17:32 ` [tree-ssa] " Mark Mitchell 0 siblings, 2 replies; 15+ messages in thread From: Jason Merrill @ 2002-07-20 18:54 UTC (permalink / raw) To: Mark Mitchell; +Cc: Richard Henderson, gcc, Jason Merrill [-- Attachment #1: Type: text/plain, Size: 594 bytes --] I'm interested in what y'all think about the second issue; it's something I've run into previously when thinking about expanding NEW_EXPR. One problem with (b) is that using it requires the frontend to know about passing by invisible reference. However, in the cases where we pass by invisible reference because TREE_ADDRESSABLE is set on the type, it's already controlled by the frontend, so that doesn't seem like a big issue. For cases where we would pass by invisiref for other reasons, doing a bitwise copy is just inefficient, and we could leave it up to the optimizer to fix that up. [-- Attachment #2: Type: message/rfc822, Size: 793 bytes --] From: Jason Merrill <jason@redhat.com> To: gcc@gcc.gnu.org Subject: [tree-ssa] Simplifying TARGET_EXPR Date: Tue, 16 Jul 2002 11:02:01 +0100 [snip] 2) Passing a TARGET_EXPR to a call means initializing the temporary on the stack and passing its address to the call. There's no way to express this in a simplified form; if we replace the TARGET_EXPR with the variable it initializes, expand_call will make a bitwise copy, which is wrong. I can think of two solutions to this: a) Change expand_call to not copy variables with DECL_ARTIFICIAL set. b) Pass an ADDR_EXPR of the variable instead, and change expand_call to handle that case. My preference is for (b), as (a) might have unintended consequences. Thoughts? Jason ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-20 18:54 [tree-ssa] Simplifying TARGET_EXPR Jason Merrill @ 2002-07-21 0:41 ` Richard Henderson 2002-07-26 14:51 ` PATCH " Jason Merrill 2002-07-21 17:32 ` [tree-ssa] " Mark Mitchell 1 sibling, 1 reply; 15+ messages in thread From: Richard Henderson @ 2002-07-21 0:41 UTC (permalink / raw) To: Jason Merrill; +Cc: Mark Mitchell, gcc On Sat, Jul 20, 2002 at 05:09:42PM +0100, Jason Merrill wrote: > 2) Passing a TARGET_EXPR to a call means initializing the temporary on the > stack and passing its address to the call. There's no way to express > this in a simplified form; if we replace the TARGET_EXPR with the > variable it initializes, expand_call will make a bitwise copy, which is > wrong. I can think of two solutions to this: > > a) Change expand_call to not copy variables with DECL_ARTIFICIAL set. > b) Pass an ADDR_EXPR of the variable instead, and change expand_call > to handle that case. > > My preference is for (b), as (a) might have unintended consequences. [...] > One problem with (b) is that using it requires the frontend to know about > passing by invisible reference. However, in the cases where we pass by > invisible reference because TREE_ADDRESSABLE is set on the type, it's > already controlled by the frontend, so that doesn't seem like a big issue. > For cases where we would pass by invisiref for other reasons, doing a > bitwise copy is just inefficient, and we could leave it up to the optimizer > to fix that up. (a) is definitely scary. (b) doesn't seem quite right since the type of the argument doesn't match up with the type actually passed. Seems like we'd get into trouble with the backends wrt FUNCTION_ARG et al. Given that the front end has to know about the semantics of copying objects and how that affects parameter passing anyway, perhaps the front end should modify the type of the parameter at the same time. Perhaps a REFERENCE_TYPE with DECL_ARTIFICIAL set? Then an ADDR_EXPR would match up nicely. r~ ^ permalink raw reply [flat|nested] 15+ messages in thread
* PATCH Re: Simplifying TARGET_EXPR 2002-07-21 0:41 ` Richard Henderson @ 2002-07-26 14:51 ` Jason Merrill 0 siblings, 0 replies; 15+ messages in thread From: Jason Merrill @ 2002-07-26 14:51 UTC (permalink / raw) To: Richard Henderson; +Cc: Mark Mitchell, gcc, gcc-patches [-- Attachment #1: Type: text/plain, Size: 1558 bytes --] >>>>> "Richard" == Richard Henderson <rth@redhat.com> writes: > Given that the front end has to know about the semantics of copying > objects and how that affects parameter passing anyway, perhaps the > front end should modify the type of the parameter at the same time. > Perhaps a REFERENCE_TYPE with DECL_ARTIFICIAL set? Then an ADDR_EXPR > would match up nicely. It occurred to me that we already have DECL_ARG_TYPE for handling this sort of thing. This patch sets DECL_ARG_TYPE to a REFERENCE_TYPE if we want to pass by invisible reference for frontend-specific reasons. These semantics are handled by three new functions in cp/call.c; the rest of the patch is telling other bits of code to use them. Tested i686-pc-linux-gnu. I'll check this in soon if nobody complains. 2002-07-25 Jason Merrill <jason@redhat.com> * function.c (assign_parms): Handle frontend-directed pass by invisible reference. cp/ * call.c (build_over_call): Likewise. (cp_convert_parm_for_inlining): New fn. (convert_for_arg_passing): New fn. (convert_default_arg, build_over_call): Use it. (type_passed_as): New fn. * pt.c (tsubst_decl): Use it. * decl2.c (cp_build_parm_decl): New fn. (build_artificial_parm): Use it. (start_static_storage_duration_function): Likewise. * decl.c (start_cleanup_fn, grokdeclarater): Likewise. (grokparms): Don't mess with DECL_ARG_TYPE. * typeck.c (convert_arguments): Use convert_for_arg_passing. * cp-lang.c (LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING): Define. * cp-tree.h: Declare new fns. [-- Warning: decoded text below may be mangled, UTF-8 assumed --] [-- Attachment #2: Type: text/x-patch, Size: 12744 bytes --] *** ./cp/pt.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/pt.c Wed Jul 24 12:35:50 2002 *************** tsubst_decl (t, args, type, complain) *** 6023,6032 **** complain, in_decl); DECL_CONTEXT (r) = NULL_TREE; ! if (!DECL_TEMPLATE_PARM_P (r) && PROMOTE_PROTOTYPES ! && INTEGRAL_TYPE_P (type) ! && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)) ! DECL_ARG_TYPE (r) = integer_type_node; if (TREE_CHAIN (t)) TREE_CHAIN (r) = tsubst (TREE_CHAIN (t), args, complain, TREE_CHAIN (t)); --- 6023,6031 ---- complain, in_decl); DECL_CONTEXT (r) = NULL_TREE; ! ! if (!DECL_TEMPLATE_PARM_P (r)) ! DECL_ARG_TYPE (r) = type_passed_as (type); if (TREE_CHAIN (t)) TREE_CHAIN (r) = tsubst (TREE_CHAIN (t), args, complain, TREE_CHAIN (t)); *** ./cp/call.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/call.c Wed Jul 24 17:10:12 2002 *************** convert_default_arg (type, arg, fn, parm *** 4128,4142 **** arg = convert_for_initialization (0, type, arg, LOOKUP_NORMAL, "default argument", fn, parmnum); ! if (PROMOTE_PROTOTYPES ! && INTEGRAL_TYPE_P (type) ! && (TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node))) ! arg = default_conversion (arg); } return arg; } /* Subroutine of the various build_*_call functions. Overload resolution has chosen a winning candidate CAND; build up a CALL_EXPR accordingly. ARGS is a TREE_LIST of the unconverted arguments to the call. FLAGS is a --- 4128,4191 ---- arg = convert_for_initialization (0, type, arg, LOOKUP_NORMAL, "default argument", fn, parmnum); ! arg = convert_for_arg_passing (type, arg); } return arg; } + /* Returns the type which will really be used for passing an argument of + type TYPE. */ + + tree + type_passed_as (type) + tree type; + { + /* Pass classes with copy ctors by invisible reference. */ + if (TREE_ADDRESSABLE (type)) + type = build_reference_type (type); + else if (PROMOTE_PROTOTYPES + && INTEGRAL_TYPE_P (type) + && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)) + type = integer_type_node; + + return type; + } + + /* Actually perform the appropriate conversion. */ + + tree + convert_for_arg_passing (type, val) + tree type, val; + { + /* Pass classes with copy ctors by invisible reference. */ + if (TREE_ADDRESSABLE (type)) + val = build1 (ADDR_EXPR, build_reference_type (type), val); + else if (PROMOTE_PROTOTYPES + && INTEGRAL_TYPE_P (type) + && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)) + val = default_conversion (val); + return val; + } + + /* Convert VALUE for assignment into inlined parameter PARM. */ + + tree + cp_convert_parm_for_inlining (parm, value, fn) + tree parm, value; + tree fn ATTRIBUTE_UNUSED; + { + /* When inlining, we don't need to mess with invisible references, so + undo the ADDR_EXPR. */ + if (TREE_ADDRESSABLE (TREE_TYPE (parm))) + { + if (TREE_TYPE (value) != build_reference_type (TREE_TYPE (parm))) + abort (); + value = build_indirect_ref (value, NULL); + } + return value; + } + /* Subroutine of the various build_*_call functions. Overload resolution has chosen a winning candidate CAND; build up a CALL_EXPR accordingly. ARGS is a TREE_LIST of the unconverted arguments to the call. FLAGS is a *************** build_over_call (cand, args, flags) *** 4222,4231 **** val = convert_like_with_context (conv, TREE_VALUE (arg), fn, i - is_method); ! if (PROMOTE_PROTOTYPES ! && INTEGRAL_TYPE_P (type) ! && (TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node))) ! val = default_conversion (val); converted_args = tree_cons (NULL_TREE, val, converted_args); } --- 4271,4277 ---- val = convert_like_with_context (conv, TREE_VALUE (arg), fn, i - is_method); ! val = convert_for_arg_passing (type, val); converted_args = tree_cons (NULL_TREE, val, converted_args); } *** ./cp/decl.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/decl.c Wed Jul 24 12:35:46 2002 *************** start_cleanup_fn () *** 8518,8526 **** { tree parmdecl; ! parmdecl = build_decl (PARM_DECL, NULL_TREE, ptr_type_node); DECL_CONTEXT (parmdecl) = fndecl; - DECL_ARG_TYPE (parmdecl) = ptr_type_node; TREE_USED (parmdecl) = 1; DECL_ARGUMENTS (fndecl) = parmdecl; } --- 8518,8525 ---- { tree parmdecl; ! parmdecl = cp_build_parm_decl (NULL_TREE, ptr_type_node); DECL_CONTEXT (parmdecl) = fndecl; TREE_USED (parmdecl) = 1; DECL_ARGUMENTS (fndecl) = parmdecl; } *************** grokdeclarator (declarator, declspecs, d *** 11366,11372 **** for (args = TYPE_ARG_TYPES (type); args; args = TREE_CHAIN (args)) { ! tree decl = build_decl (PARM_DECL, NULL_TREE, TREE_VALUE (args)); TREE_CHAIN (decl) = decls; decls = decl; --- 11365,11371 ---- for (args = TYPE_ARG_TYPES (type); args; args = TREE_CHAIN (args)) { ! tree decl = cp_build_parm_decl (NULL_TREE, TREE_VALUE (args)); TREE_CHAIN (decl) = decls; decls = decl; *************** friend declaration requires class-key, i *** 11510,11526 **** if (decl_context == PARM) { ! decl = build_decl (PARM_DECL, declarator, type); bad_specifiers (decl, "parameter", virtualp, quals != NULL_TREE, inlinep, friendp, raises != NULL_TREE); - - /* Compute the type actually passed in the parmlist, - for the case where there is no prototype. - (For example, shorts and chars are passed as ints.) - When there is a prototype, this is overridden later. */ - - DECL_ARG_TYPE (decl) = type_promotes_to (type); } else if (decl_context == FIELD) { --- 11509,11518 ---- if (decl_context == PARM) { ! decl = cp_build_parm_decl (declarator, type); bad_specifiers (decl, "parameter", virtualp, quals != NULL_TREE, inlinep, friendp, raises != NULL_TREE); } else if (decl_context == FIELD) { *************** grokparms (first_parm) *** 12206,12216 **** decl, ptr ? "pointer" : "reference", t); } - DECL_ARG_TYPE (decl) = TREE_TYPE (decl); - if (PROMOTE_PROTOTYPES - && INTEGRAL_TYPE_P (type) - && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)) - DECL_ARG_TYPE (decl) = integer_type_node; if (!any_error && init) init = check_default_argument (decl, init); else --- 12198,12203 ---- *** ./cp/cp-lang.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/cp-lang.c Tue Jul 23 17:53:41 2002 *************** static bool cxx_warn_unused_global_decl *** 120,125 **** --- 120,128 ---- #undef LANG_HOOKS_TREE_INLINING_COPY_RES_DECL_FOR_INLINING #define LANG_HOOKS_TREE_INLINING_COPY_RES_DECL_FOR_INLINING \ cp_copy_res_decl_for_inlining + #undef LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING + #define LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING \ + cp_convert_parm_for_inlining #undef LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P #define LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P anon_aggr_type_p #undef LANG_HOOKS_TREE_INLINING_START_INLINING *** ./cp/cp-tree.h.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/cp-tree.h Wed Jul 24 17:09:43 2002 *************** extern tree convert_default_arg *** 3683,3688 **** --- 3683,3691 ---- extern tree convert_arg_to_ellipsis PARAMS ((tree)); extern tree build_x_va_arg PARAMS ((tree, tree)); extern tree cxx_type_promotes_to PARAMS ((tree)); + extern tree type_passed_as PARAMS ((tree)); + extern tree convert_for_arg_passing PARAMS ((tree, tree)); + extern tree cp_convert_parm_for_inlining PARAMS ((tree, tree, tree)); extern int is_properly_derived_from PARAMS ((tree, tree)); extern tree initialize_reference PARAMS ((tree, tree)); extern tree strip_top_quals PARAMS ((tree)); *************** extern void mark_used PARAMS ((tree)) *** 3962,3967 **** --- 3965,3971 ---- extern tree handle_class_head (enum tag_types, tree, tree, tree, int, int *); extern tree lookup_arg_dependent PARAMS ((tree, tree, tree)); extern void finish_static_data_member_decl PARAMS ((tree, tree, tree, int)); + extern tree cp_build_parm_decl PARAMS ((tree, tree)); extern tree build_artificial_parm PARAMS ((tree, tree)); extern tree get_guard PARAMS ((tree)); extern tree get_guard_cond PARAMS ((tree)); *** ./cp/decl2.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/decl2.c Wed Jul 24 12:35:47 2002 *************** grok_x_components (specs) *** 808,813 **** --- 808,826 ---- finish_member_declaration (build_decl (FIELD_DECL, NULL_TREE, t)); } + /* Build a PARM_DECL with NAME and TYPE, and set DECL_ARG_TYPE + appropriately. */ + + tree + cp_build_parm_decl (name, type) + tree name; + tree type; + { + tree parm = build_decl (PARM_DECL, name, type); + DECL_ARG_TYPE (parm) = type_passed_as (type); + return parm; + } + /* Returns a PARM_DECL for a parameter of the indicated TYPE, with the indicated NAME. */ *************** build_artificial_parm (name, type) *** 816,829 **** tree name; tree type; { ! tree parm; ! ! parm = build_decl (PARM_DECL, name, type); DECL_ARTIFICIAL (parm) = 1; /* All our artificial parms are implicitly `const'; they cannot be assigned to. */ TREE_READONLY (parm) = 1; - DECL_ARG_TYPE (parm) = type; return parm; } --- 829,839 ---- tree name; tree type; { ! tree parm = cp_build_parm_decl (name, type); DECL_ARTIFICIAL (parm) = 1; /* All our artificial parms are implicitly `const'; they cannot be assigned to. */ TREE_READONLY (parm) = 1; return parm; } *************** start_static_storage_duration_function ( *** 2866,2881 **** VARRAY_PUSH_TREE (ssdf_decls, ssdf_decl); /* Create the argument list. */ ! initialize_p_decl = build_decl (PARM_DECL, ! get_identifier (INITIALIZE_P_IDENTIFIER), ! integer_type_node); DECL_CONTEXT (initialize_p_decl) = ssdf_decl; - DECL_ARG_TYPE (initialize_p_decl) = integer_type_node; TREE_USED (initialize_p_decl) = 1; ! priority_decl = build_decl (PARM_DECL, get_identifier (PRIORITY_IDENTIFIER), ! integer_type_node); DECL_CONTEXT (priority_decl) = ssdf_decl; - DECL_ARG_TYPE (priority_decl) = integer_type_node; TREE_USED (priority_decl) = 1; TREE_CHAIN (initialize_p_decl) = priority_decl; --- 2876,2888 ---- VARRAY_PUSH_TREE (ssdf_decls, ssdf_decl); /* Create the argument list. */ ! initialize_p_decl = cp_build_parm_decl ! (get_identifier (INITIALIZE_P_IDENTIFIER), integer_type_node); DECL_CONTEXT (initialize_p_decl) = ssdf_decl; TREE_USED (initialize_p_decl) = 1; ! priority_decl = cp_build_parm_decl ! (get_identifier (PRIORITY_IDENTIFIER), integer_type_node); DECL_CONTEXT (priority_decl) = ssdf_decl; TREE_USED (priority_decl) = 1; TREE_CHAIN (initialize_p_decl) = priority_decl; *** ./cp/typeck.c.~1~ Wed Jul 24 12:40:22 2002 --- ./cp/typeck.c Wed Jul 24 17:04:54 2002 *************** convert_arguments (typelist, values, fnd *** 3145,3155 **** parmval = convert_for_initialization (NULL_TREE, type, val, flags, "argument passing", fndecl, i); ! if (PROMOTE_PROTOTYPES ! && INTEGRAL_TYPE_P (type) ! && (TYPE_PRECISION (type) ! < TYPE_PRECISION (integer_type_node))) ! parmval = default_conversion (parmval); } if (parmval == error_mark_node) --- 3145,3151 ---- parmval = convert_for_initialization (NULL_TREE, type, val, flags, "argument passing", fndecl, i); ! parmval = convert_for_arg_passing (type, parmval); } if (parmval == error_mark_node) *** ./function.c.~1~ Wed Jul 24 12:40:22 2002 --- ./function.c Wed Jul 24 12:35:18 2002 *************** assign_parms (fndecl) *** 4425,4430 **** --- 4425,4439 ---- passed_pointer = 1; passed_mode = nominal_mode = Pmode; } + /* See if the frontend wants to pass this by invisible reference. */ + else if (passed_type != nominal_type + && POINTER_TYPE_P (passed_type) + && TREE_TYPE (passed_type) == nominal_type) + { + nominal_type = passed_type; + passed_pointer = 1; + passed_mode = nominal_mode = Pmode; + } promoted_mode = passed_mode; ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-20 18:54 [tree-ssa] Simplifying TARGET_EXPR Jason Merrill 2002-07-21 0:41 ` Richard Henderson @ 2002-07-21 17:32 ` Mark Mitchell 2002-07-21 18:04 ` Gabriel Dos Reis 2002-07-21 22:35 ` Jason Merrill 1 sibling, 2 replies; 15+ messages in thread From: Mark Mitchell @ 2002-07-21 17:32 UTC (permalink / raw) To: Jason Merrill; +Cc: Richard Henderson, gcc --On Saturday, July 20, 2002 05:09:42 PM +0100 Jason Merrill <jason@redhat.com> wrote: > I'm interested in what y'all think about the second issue; it's something > I've run into previously when thinking about expanding NEW_EXPR. > > One problem with (b) is that using it requires the frontend to know about > passing by invisible reference. I think (b) is by far better than (a). (What I'd really like to see is the elimination of TARGET_EXPR in the front end before we reach the optimizers and code generators. This might miss some opportunities for elimination of copy constructors, but, in practice, very few. And, to be honest, I'm nervous about the compiler changing the number of objects constructed and destructed when optimization is enabled; that makes debugging optimized code that much harder.) -- Mark Mitchell mark@codesourcery.com CodeSourcery, LLC http://www.codesourcery.com ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 17:32 ` [tree-ssa] " Mark Mitchell @ 2002-07-21 18:04 ` Gabriel Dos Reis 2002-07-21 18:14 ` Mark Mitchell 2002-07-21 22:35 ` Jason Merrill 1 sibling, 1 reply; 15+ messages in thread From: Gabriel Dos Reis @ 2002-07-21 18:04 UTC (permalink / raw) To: Mark Mitchell; +Cc: Jason Merrill, Richard Henderson, gcc Mark Mitchell <mark@codesourcery.com> writes: | --On Saturday, July 20, 2002 05:09:42 PM +0100 Jason Merrill | <jason@redhat.com> wrote: | | > I'm interested in what y'all think about the second issue; it's something | > I've run into previously when thinking about expanding NEW_EXPR. | > | > One problem with (b) is that using it requires the frontend to know about | > passing by invisible reference. | | I think (b) is by far better than (a). | | (What I'd really like to see is the elimination of TARGET_EXPR in the | front end before we reach the optimizers and code generators. This | might miss some opportunities for elimination of copy constructors, | but, in practice, very few. And, to be honest, I'm nervous about the | compiler changing the number of objects constructed and destructed | when optimization is enabled; that makes debugging optimized code | that much harder.) Do you think we should always elide copy-constructors by default, unless explicitly told the contrary? -- Gaby ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 18:04 ` Gabriel Dos Reis @ 2002-07-21 18:14 ` Mark Mitchell 2002-07-21 20:39 ` Gabriel Dos Reis 2002-07-22 12:33 ` Nathan Sidwell 0 siblings, 2 replies; 15+ messages in thread From: Mark Mitchell @ 2002-07-21 18:14 UTC (permalink / raw) To: Gabriel Dos Reis; +Cc: Jason Merrill, Richard Henderson, gcc > Do you think we should always elide copy-constructors by default, > unless explicitly told the contrary? Yes. I think the front end shoul consistently try hard to elide copy-constructors, then give up and hand off the result to the optimizers without hoping for any more elision. Maybe I'm developing an unhealthy paranoia. On the one hand, optimizing away more copy constructors is like optimizinga away more copies between scalars, and I'm all for having -O2 do more of that! On the other, copy constructor elision is observable behavior in the program, and it's going to make it hard to do debug, profile, and otherwise analyze your program if the number of copy constructor calls changes when you optimize. My two cents, -- Mark Mitchell mark@codesourcery.com CodeSourcery, LLC http://www.codesourcery.com ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 18:14 ` Mark Mitchell @ 2002-07-21 20:39 ` Gabriel Dos Reis 2002-07-22 8:32 ` Michael Matz 2002-07-22 12:33 ` Nathan Sidwell 1 sibling, 1 reply; 15+ messages in thread From: Gabriel Dos Reis @ 2002-07-21 20:39 UTC (permalink / raw) To: Mark Mitchell; +Cc: Jason Merrill, Richard Henderson, gcc Mark Mitchell <mark@codesourcery.com> writes: | > Do you think we should always elide copy-constructors by default, | > unless explicitly told the contrary? | | Yes. OK, I got it -- I think we're on the same page. [...] | On the other, copy constructor elision is observable | behavior in the program, and it's going to make it hard to do | debug, profile, and otherwise analyze your program if the number | of copy constructor calls changes when you optimize. Since the standard explicitly allows a compiler to elide copy-constructors even though they have side-effects, C++ proggrammers have come up (at least there are guidelines to that effect) not to write programs whose semantics criticall depends on the number of times copy-constructor/destructor are called. I'm sympathetic to your take that we should try hard to preserve the number of copy-constructor calls. -- Gaby ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 20:39 ` Gabriel Dos Reis @ 2002-07-22 8:32 ` Michael Matz 2002-07-22 12:02 ` Gabriel Dos Reis 2002-07-24 3:22 ` Mark Mitchell 0 siblings, 2 replies; 15+ messages in thread From: Michael Matz @ 2002-07-22 8:32 UTC (permalink / raw) To: Mark Mitchell, Gabriel Dos Reis; +Cc: gcc Hi, On Sun, 21 Jul 2002, Mark Mitchell wrote: > > Do you think we should always elide copy-constructors by default, > > unless explicitly told the contrary? > > Yes. > > Maybe I'm developing an unhealthy paranoia. And your coworkers too it seems ;-) First, I think you meant debugging in general, not specifically with gdb, didn't you? Because with -O2 programs are not debuggable easily with gdb, even right now, so gdb-debugging should not be the reason to not elide copy ctors (or more generally debugging with programs interpreting the debug info). Then it can only be a form of printf debugging, or asserts. But e.g. strict aliasing makes such debugging also harder in a similar way, because valid, but possibly surprising, transformations are made. We do them anyway, so that also can't be the reason to not elide copy ctors by default. So not eliding them should be done only when a switch is given. Maybe -fno-surprising (which also would switch off other optimizations), or -fdebug. Ciao, Michael. ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-22 8:32 ` Michael Matz @ 2002-07-22 12:02 ` Gabriel Dos Reis 2002-07-24 3:22 ` Mark Mitchell 1 sibling, 0 replies; 15+ messages in thread From: Gabriel Dos Reis @ 2002-07-22 12:02 UTC (permalink / raw) To: Michael Matz; +Cc: Mark Mitchell, aj, gcc Michael Matz <matz@suse.de> writes: | Hi, | | On Sun, 21 Jul 2002, Mark Mitchell wrote: | | > > Do you think we should always elide copy-constructors by default, | > > unless explicitly told the contrary? | > | > Yes. | > | > Maybe I'm developing an unhealthy paranoia. | | And your coworkers too it seems ;-) If you have something particular with me, let's take it to private mails. | First, I think you meant debugging in general, not specifically with gdb, | didn't you? Because with -O2 programs are not debuggable easily with gdb, | even right now, Not just because it is already uneasy means we should make it more difficult. | so gdb-debugging should not be the reason to not elide | copy ctors (or more generally debugging with programs interpreting the | debug info). Then it can only be a form of printf debugging, or asserts. Nobody (neither Mark nor me) is proposing not to elide copy constructors. On the contrary, we're proposing to always elide them unless explicitly told otherwise. -- Gaby ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-22 8:32 ` Michael Matz 2002-07-22 12:02 ` Gabriel Dos Reis @ 2002-07-24 3:22 ` Mark Mitchell 1 sibling, 0 replies; 15+ messages in thread From: Mark Mitchell @ 2002-07-24 3:22 UTC (permalink / raw) To: Michael Matz, Gabriel Dos Reis; +Cc: gcc > But e.g. strict aliasing makes such debugging also harder in a similar > way, because valid, but possibly surprising, transformations are made. We > do them anyway, so that also can't be the reason to not elide copy ctors > by default. I agree with the antecedent, but not the conclusion. :-) These are definitly analgous situations, but to me it is a matter of degree. In other words, the same considerations apply, but in different proportions, and therefore I reach a different conclusion. Inserting and removing function calls is -- in my opinion -- a more significant change in program semantics. I dn't feel too strongly about this. Maybe I am scarred by having worked on too many compilers that did this transformation strictly in the front end. -- Mark Mitchell mark@codesourcery.com CodeSourcery, LLC http://www.codesourcery.com ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 18:14 ` Mark Mitchell 2002-07-21 20:39 ` Gabriel Dos Reis @ 2002-07-22 12:33 ` Nathan Sidwell 2002-07-22 12:53 ` Gabriel Dos Reis 2002-07-22 13:10 ` Jason Merrill 1 sibling, 2 replies; 15+ messages in thread From: Nathan Sidwell @ 2002-07-22 12:33 UTC (permalink / raw) To: Mark Mitchell; +Cc: Gabriel Dos Reis, Jason Merrill, Richard Henderson, gcc Mark Mitchell wrote: > Maybe I'm developing an unhealthy paranoia. On the one hand, > optimizing away more copy constructors is like optimizinga away > more copies between scalars, and I'm all for having -O2 do more > of that! On the other, copy constructor elision is observable > behavior in the program, and it's going to make it hard to do > debug, profile, and otherwise analyze your program if the number > of copy constructor calls changes when you optimize. I disagree. Alias analysis makes optimized broken programs hard to debug, I\x13 don't see why temporary elision is any different.. Maybe have the elision separately disablable at -O2, but I think it should be permissable. nathan -- Dr Nathan Sidwell :: http://www.codesourcery.com :: CodeSourcery LLC 'But that's a lie.' - 'Yes it is. What's your point?' nathan@codesourcery.com : http://www.cs.bris.ac.uk/~nathan/ : nathan@acm.org ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-22 12:33 ` Nathan Sidwell @ 2002-07-22 12:53 ` Gabriel Dos Reis 2002-07-22 13:10 ` Jason Merrill 1 sibling, 0 replies; 15+ messages in thread From: Gabriel Dos Reis @ 2002-07-22 12:53 UTC (permalink / raw) To: Nathan Sidwell; +Cc: Mark Mitchell, Jason Merrill, Richard Henderson, gcc Nathan Sidwell <nathan@codesourcery.com> writes: | Maybe have the elision separately disablable at -O2, but I think | it should be permissable. I think copy-elision is already controlled by a separate flag. -- Gaby ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-22 12:33 ` Nathan Sidwell 2002-07-22 12:53 ` Gabriel Dos Reis @ 2002-07-22 13:10 ` Jason Merrill 1 sibling, 0 replies; 15+ messages in thread From: Jason Merrill @ 2002-07-22 13:10 UTC (permalink / raw) To: Nathan Sidwell; +Cc: Mark Mitchell, Gabriel Dos Reis, Richard Henderson, gcc >>>>> "Nathan" == Nathan Sidwell <nathan@codesourcery.com> writes: > Mark Mitchell wrote: >> Maybe I'm developing an unhealthy paranoia. On the one hand, >> optimizing away more copy constructors is like optimizing away >> more copies between scalars, and I'm all for having -O2 do more >> of that! On the other, copy constructor elision is observable >> behavior in the program, and it's going to make it hard to do >> debug, profile, and otherwise analyze your program if the number >> of copy constructor calls changes when you optimize. > I disagree. Alias analysis makes optimized broken programs hard > to debug, I don't see why temporary elision is any different.. > Maybe have the elision separately disablable at -O2, but I think > it should be permissable. I agree. Copy constructor calls are small change in debuggability of optimized code. Of course, we've never tried to optimize away more copy constructors after inlining, so this is all theoretical... Jason ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [tree-ssa] Simplifying TARGET_EXPR 2002-07-21 17:32 ` [tree-ssa] " Mark Mitchell 2002-07-21 18:04 ` Gabriel Dos Reis @ 2002-07-21 22:35 ` Jason Merrill 1 sibling, 0 replies; 15+ messages in thread From: Jason Merrill @ 2002-07-21 22:35 UTC (permalink / raw) To: Mark Mitchell; +Cc: Richard Henderson, gcc >>>>> "Mark" == Mark Mitchell <mark@codesourcery.com> writes: > (What I'd really like to see is the elimination of TARGET_EXPR in the > front end before we reach the optimizers and code generators. Yep, that's what I have in mind. Jason ^ permalink raw reply [flat|nested] 15+ messages in thread
* [tree-ssa] Simplifying TARGET_EXPR @ 2002-07-16 9:52 Jason Merrill 0 siblings, 0 replies; 15+ messages in thread From: Jason Merrill @ 2002-07-16 9:52 UTC (permalink / raw) To: gcc Thinking about simplifying TARGET_EXPR, I see two issues to be dealt with: 1) expand_expr's treatment of TARGET_EXPR depends on whether or not it is being expanded with a target: if so, it initializes the target object; if not, it initializes a new object. There's no way to model that behavior with the current simplification code, as there's no concept of 'target'. However, I think that the copy-elision should only occur under an INIT_EXPR, so we can check for TARGET_EXPR in simplify_modify_expr. This should work fine. 2) Passing a TARGET_EXPR to a call means initializing the temporary on the stack and passing its address to the call. There's no way to express this in a simplified form; if we replace the TARGET_EXPR with the variable it initializes, expand_call will make a bitwise copy, which is wrong. I can think of two solutions to this: a) Change expand_call to not copy variables with DECL_ARTIFICIAL set. b) Pass an ADDR_EXPR of the variable instead, and change expand_call to handle that case. My preference is for (b), as (a) might have unintended consequences. Thoughts? Jason ^ permalink raw reply [flat|nested] 15+ messages in thread
end of thread, other threads:[~2002-07-26 10:04 UTC | newest] Thread overview: 15+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2002-07-20 18:54 [tree-ssa] Simplifying TARGET_EXPR Jason Merrill 2002-07-21 0:41 ` Richard Henderson 2002-07-26 14:51 ` PATCH " Jason Merrill 2002-07-21 17:32 ` [tree-ssa] " Mark Mitchell 2002-07-21 18:04 ` Gabriel Dos Reis 2002-07-21 18:14 ` Mark Mitchell 2002-07-21 20:39 ` Gabriel Dos Reis 2002-07-22 8:32 ` Michael Matz 2002-07-22 12:02 ` Gabriel Dos Reis 2002-07-24 3:22 ` Mark Mitchell 2002-07-22 12:33 ` Nathan Sidwell 2002-07-22 12:53 ` Gabriel Dos Reis 2002-07-22 13:10 ` Jason Merrill 2002-07-21 22:35 ` Jason Merrill -- strict thread matches above, loose matches on Subject: below -- 2002-07-16 9:52 Jason Merrill
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).