This is the mail archive of the
gdb-patches@sourceware.org
mailing list for the GDB project.
Re: [RFA 6/8] Use value_freer in dwarf2_evaluate_loc_desc_full
- From: Pedro Alves <palves at redhat dot com>
- To: Tom Tromey <tom at tromey dot com>
- Cc: gdb-patches at sourceware dot org
- Date: Tue, 20 Dec 2016 14:49:07 +0000
- Subject: Re: [RFA 6/8] Use value_freer in dwarf2_evaluate_loc_desc_full
- Authentication-results: sourceware.org; auth=none
- References: <1480395946-10924-1-git-send-email-tom@tromey.com> <1480395946-10924-7-git-send-email-tom@tromey.com> <06e2b7b1-feca-29f7-7e49-e05f01d05485@redhat.com> <87bmwgez57.fsf@tromey.com>
On 12/13/2016 01:28 PM, Tom Tromey wrote:
>>>>>> "Pedro" == Pedro Alves <palves@redhat.com> writes:
>
> Pedro> Or "reset ()", following the naming used in the standard smart pointers?
>
> I went with reset since I think "free" can be a macro sometimes.
> Or at least it could in C... not actually sure if C++ removed this
> possibility.
I always assumed it has, but had never went looking for the specific
wording. Looking at the C++14 draft N4140, I see:
17.6.1.2 - Headers:
5 - Names which are defined as macros in C shall be defined as macros in
the C ++ standard library, even if C grants license for implementation
as functions. [ Note: The names defined as macros in C include the
following: assert, offsetof, setjmp, va_arg, va_end, and va_start. - end note ]
6 - Names that are defined as functions in C shall be defined as functions in
the C ++ standard library." (175)
And then footnote 175 clarifies:
"175) This disallows the practice, allowed in C, of providing a masking
macro in addition to the function prototype. The only way to achieve equivalent
inline behavior in C ++ is to provide a definition as an extern inline function."
So I think the answer is yes, C++ removes that possibility.
BTW, I meanwhile realized that "release" would also be a
naming/concept conflict with release_value / value_release_to_mark
too. Really best to avoid it here.
In pondering a bit more over this, I wonder whether
adding a "scoped_" to go with scoped_restore etc., would make
it a bit clearer to readers that this is a RAII type. Then
also considering value_release_to_mark, I wonder would an
API/naming like this:
struct scoped_value_mark
{
scoped_value_mark () : m_value (value_mark ()) {}
~scoped_value_mark () { free_to_mark ()}
void free_to_mark () { if (m_value) value_free_to_mark (m_value); }
void release_to_mark () { if (m_value) value_release_to_mark (m_value); }
/* Get the mark value. */
struct value *get () { return m_value; }
};
Uses would look like:
scoped_value_mark value_mark;
...
value_mark.free_to_mark (); // some path than wants an explicit "free_to_mark".
In eval.c:fetch_subexp_value we'd use it like:
/* Evaluate the expression. */
scoped_value_mark mark;
[...]
result = evaluate_subexp (NULL_TYPE, exp, pc, EVAL_NORMAL);
[...]
new_mark = value_mark ();
if (mark.get () == new_mark)
return;
/* Make sure it's not lazy, so that after the target stops again we
have a non-lazy previous value to compare with. */
[...]
if (val_chain)
{
/* Return the chain of intermediate values. We use this to
decide which addresses to watch. */
*val_chain = new_mark;
mark.release_to_mark ();
}
}
Would this result in clearer client code? IMHO, yes, but WDYT?
Thanks,
Pedro Alves