On 2/18/21 10:31 AM, Richard Biener wrote:
On Wed, Feb 17, 2021 at 2:16 PM Martin Liška <mli...@suse.cz> wrote:

On 2/17/21 9:36 AM, Martin Liška wrote:
I'll write it even more robust...

This is more elegant approach I've just tested on the instrumented clang.

Patch can bootstrap on x86_64-linux-gnu and survives regression tests.

Ready to be installed?

Isn't it still too complicated?  We're asked to write N counters so why
don't we just write N counters?

Well, we are asked to stream N counters. But each has a variable length,
which makes it funny :)

  Thus, you already do

        for (struct gcov_kvp *node = (struct gcov_kvp *)(intptr_t)start;
-          node != NULL; node = node->next)
+          node != NULL; node = node->next, j++)
         {
           gcov_write_counter (node->value);
           gcov_write_counter (node->count);
+
+         /* Stop when we reach expected number of items.  */
+         if (j + 1 == list_sizes[i])
+           break;
         }

why isn't this then only thing you need (just using pair_count as gathered
previously)?  And just count pair_count to zero as IV?  No need to
do the node != NULL check?

We can't do that, because that will lead in a corrupted profile.
We can have 2 problematic situations:

1) linked list is shorter, e.g.

10 2 10000 10

Here 2 represents 2 tuples, but we stream only one {10000: 10}. That happens in 
the instrumented clang.

2) linked list is longer, e.g.
10 1 10000 5 222222 5

Here 1 represents 1 tuple, be we stream 2 tuples {10000: 10} and {222222: 5}.


Note architectures with less nice memory ordering guarantees might
eventually see partially updated pointers and counters so I think
we at least want atomic_read ()s of the values with the weakest
consistency possible.  (but that can be done as followup if we agree on that)

Can we really see a partially updated pointer?

Thanks,
Martin


Richard.

Thanks,
Martin

Reply via email to