Topic: get count of std::weak_ptr objects tracking a


Author: Thiago Macieira <thiago@macieira.org>
Date: Thu, 25 Dec 2014 13:43:54 -0200
Raw View
On Thursday 25 December 2014 00:16:32 write2ramkumar@gmail.com wrote:
> It is useful to get the count of std::weak_ptr that are tracking a
> resource just as we have a reference count of std::shared_ptr that tracks a
> resource.

I dispute that. Besides for debugging, I don't see why an application would
need to know the count. Not to mention that any value you get is stale the
moment you got it, since weak_ptr is thread-safe and the atomic counter may
have changed values already.

The only thread-safe information is whether a given weak_ptr is the last
reference (i.e., count == 1).

> I have built a custom caching mechanism that does caching based on user
> request. The cached objects are disposed when the memory consumed by
> caching exceeds a pre-defined memory size set by the user. The cached
> objects are returned to the user  through  std::weak_ptr. The utility of
> the weak_ptr is primarily to avoid dangling pointers once the cache is
> cleared. However, the logic of which cache object has to be disposed is not
> a trivial decision and having a reference count of the number of weak_ptr
> is of immense value.

I think you're confounding your use-case with that of the weak_ptr. Your use-
case is valid, but your usage counts and even the age, "last use", etc., don't
belong in weak_ptr. For example, your cache could want to keep an item that
has been often requested, even though no one else is currently using it.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Thu, 25 Dec 2014 18:38:08 +0200
Raw View
On 25 December 2014 at 17:43, Thiago Macieira <thiago@macieira.org> wrote:
> On Thursday 25 December 2014 00:16:32 write2ramkumar@gmail.com wrote:
>> It is useful to get the count of std::weak_ptr that are tracking a
>> resource just as we have a reference count of std::shared_ptr that tracks a
>> resource.
>
> I dispute that. Besides for debugging, I don't see why an application would
> need to know the count. Not to mention that any value you get is stale the
> moment you got it, since weak_ptr is thread-safe and the atomic counter may
> have changed values already.

Well, the use_count of a weak_ptr or a shared_ptr is across-thread
stale the moment it's returned, but that doesn't mean it's useless.
The use_count of a weak_ptr gives you the use_count of the underlying
shared state, not the shared_weak_count *that an implementation already
has*. I can easily imagine uses for exposing both of the counts, as can
apparently the original poster.


> The only thread-safe information is whether a given weak_ptr is the last
> reference (i.e., count == 1).

Sure, but the use cases for such things are far wider than across-thread
ones.

>> I have built a custom caching mechanism that does caching based on user
>> request. The cached objects are disposed when the memory consumed by
>> caching exceeds a pre-defined memory size set by the user. The cached
>> objects are returned to the user  through  std::weak_ptr. The utility of
>> the weak_ptr is primarily to avoid dangling pointers once the cache is
>> cleared. However, the logic of which cache object has to be disposed is not
>> a trivial decision and having a reference count of the number of weak_ptr
>> is of immense value.
> I think you're confounding your use-case with that of the weak_ptr. Your use-
> case is valid, but your usage counts and even the age, "last use", etc., don't
> belong in weak_ptr. For example, your cache could want to keep an item that
> has been often requested, even though no one else is currently using it.


Fair enough, but if they "don't belong in weak_ptr", how else would you
suggest such information to be exposed?

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Miro Knejp <miro.knejp@gmail.com>
Date: Thu, 25 Dec 2014 19:00:33 +0100
Raw View
On 25 December 2014 at 17:43, Thiago Macieira <thiago@macieira.org> wrote:
> The only thread-safe information is whether a given weak_ptr is the last
> reference (i.e., count == 1).
And not even that is reliable as new independent weak_ptr instances can
be created as long as a shared_ptr exists.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Thu, 25 Dec 2014 20:20:18 -0200
Raw View
On Thursday 25 December 2014 18:38:08 Ville Voutilainen wrote:
> > I think you're confounding your use-case with that of the weak_ptr. Your
> > use- case is valid, but your usage counts and even the age, "last use",
> > etc., don't belong in weak_ptr. For example, your cache could want to
> > keep an item that has been often requested, even though no one else is
> > currently using it.
> Fair enough, but if they "don't belong in weak_ptr", how else would you
> suggest such information to be exposed?

Via composition. The cache is built around a structure that contains such
information and the object itself is one of the entries. The point being that
weak_ptr doesn't store a timestamp and I believe everyone would agree that it
never should, so I don't see why it should provide other information for
building a cache.

I wouldn't even use weak_ptr here, to be honest. It's not a cache if the
lifetime of the objects is not handled by the cache.
--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Thu, 25 Dec 2014 20:21:29 -0200
Raw View
On Thursday 25 December 2014 19:00:33 Miro Knejp wrote:
> On 25 December 2014 at 17:43, Thiago Macieira <thiago@macieira.org> wrote:
> > The only thread-safe information is whether a given weak_ptr is the last
> > reference (i.e., count == 1).
>
> And not even that is reliable as new independent weak_ptr instances can
> be created as long as a shared_ptr exists.

The "count == 1" part implies this is the last weak_ptr reference and there
are no shared_ptr references left.
--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Sat, 27 Dec 2014 20:46:29 -0800 (PST)
Raw View
------=_Part_4716_1347802864.1419741989996
Content-Type: multipart/alternative;
 boundary="----=_Part_4717_865226692.1419741989996"

------=_Part_4717_865226692.1419741989996
Content-Type: text/plain; charset=UTF-8


>
> "Not to mention that any value you get is stale the
> moment you got it, since weak_ptr is thread-safe and the atomic counter
> may
> have changed values already."
>

The use_count on a shared_ptr will be as stale as the "weak_count" if that
was available. Does not mean it is not useful!



--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_4717_865226692.1419741989996
Content-Type: text/html; charset=UTF-8

<div dir="ltr"><blockquote class="gmail_quote" style="margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;">"Not to mention that any value you get is stale the
<br>moment you got it, since weak_ptr is thread-safe and the atomic counter may
<br>have changed values already."<br></blockquote><div><br></div><div>The use_count on a shared_ptr will be as stale as the "weak_count" if that was available. Does not mean it is not useful!</div><div><br></div><div>&nbsp;</div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an email to <a href="mailto:std-proposals+unsubscribe@isocpp.org">std-proposals+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href="mailto:std-proposals@isocpp.org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href="http://groups.google.com/a/isocpp.org/group/std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/</a>.<br />

------=_Part_4717_865226692.1419741989996--
------=_Part_4716_1347802864.1419741989996--

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Sat, 27 Dec 2014 21:05:42 -0800 (PST)
Raw View
------=_Part_2465_947676650.1419743142486
Content-Type: multipart/alternative;
 boundary="----=_Part_2466_1862730398.1419743142487"

------=_Part_2466_1862730398.1419743142487
Content-Type: text/plain; charset=UTF-8



> "Fair enough, but if they "don't belong in weak_ptr", how else would you
> suggest such information to be exposed? "
>


A function to return weak_count on shared_ptr is one approach.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_2466_1862730398.1419743142487
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><br><blockquote class=3D"gmail_quote" style=3D"margin: 0;m=
argin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"><div dir=
=3D"ltr">"Fair enough, but if they "don't belong in weak_ptr", how else wou=
ld you&nbsp;<br>suggest such information to be exposed?&nbsp;"</div></block=
quote><div><br></div><div><br></div><div>A function to return weak_count on=
 shared_ptr is one approach.</div><div><br></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_2466_1862730398.1419743142487--
------=_Part_2465_947676650.1419743142486--

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Sat, 27 Dec 2014 21:07:47 -0800 (PST)
Raw View
------=_Part_5260_1886655065.1419743267485
Content-Type: multipart/alternative;
 boundary="----=_Part_5261_1415629500.1419743267485"

------=_Part_5261_1415629500.1419743267485
Content-Type: text/plain; charset=UTF-8

Just as new shared_ptr can be created to the same resource from existing
shared_ptr. The reliability of the "weak_count" is same as the reliability
of use_count on a shared_ptr.



On Thursday, December 25, 2014 11:29:48 PM UTC+5:30, Miro Knejp wrote:
>
> On 25 December 2014 at 17:43, Thiago Macieira <thi...@macieira.org
> <javascript:>> wrote:
> > The only thread-safe information is whether a given weak_ptr is the last
> > reference (i.e., count == 1).
> And not even that is reliable as new independent weak_ptr instances can
> be created as long as a shared_ptr exists.
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_5261_1415629500.1419743267485
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">Just as new shared_ptr can be created to the same resource=
 from existing shared_ptr. The reliability of the "weak_count" is same as t=
he reliability of use_count on a shared_ptr.<div><br></div><div><br><br>On =
Thursday, December 25, 2014 11:29:48 PM UTC+5:30, Miro Knejp wrote:<blockqu=
ote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left=
: 1px #ccc solid;padding-left: 1ex;">On 25 December 2014 at 17:43, Thiago M=
acieira &lt;<a href=3D"javascript:" target=3D"_blank" gdf-obfuscated-mailto=
=3D"9OdhpExsiRcJ" onmousedown=3D"this.href=3D'javascript:';return true;" on=
click=3D"this.href=3D'javascript:';return true;">thi...@macieira.org</a>&gt=
; wrote:
<br>&gt; The only thread-safe information is whether a given weak_ptr is th=
e last
<br>&gt; reference (i.e., count =3D=3D 1).
<br>And not even that is reliable as new independent weak_ptr instances can=
=20
<br>be created as long as a shared_ptr exists.
<br>
<br></blockquote></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_5261_1415629500.1419743267485--
------=_Part_5260_1886655065.1419743267485--

.


Author: David Krauss <potswa@gmail.com>
Date: Sun, 28 Dec 2014 14:29:48 +0800
Raw View
> On 2014=E2=80=9312=E2=80=9328, at 1:07 PM, Ramkumar Revanur <write2ramkum=
ar@gmail.com> wrote:
>=20
> Just as new shared_ptr can be created to the same resource from existing =
shared_ptr. The reliability of the "weak_count" is same as the reliability =
of use_count on a shared_ptr.

A combination of use_count and weak_count is safer, though, because a poten=
tially-last owner can check that there are no other potential owners on oth=
er threads. The weak count would need to be checked (evaluated) first thoug=
h, which is a bit tricky with unordered expression evaluation semantics.

For that matter, a total reference_count which is the sum of strong and wea=
k references would accomplish this more elegantly. It would be a drop-in re=
placement for use_count.

Applications that want to safely invalidate unsynchronized weak references =
need another new primitive, perhaps call it expire(), which atomically rese=
ts if unique. Then the caller can check whether the reset actually occurred=
.. This is needed to make the design in the OP safe against a race between a=
 cache eviction (or clearing) and a cache access.

Whether cache control is a valid use-case of weak_ptr, I=E2=80=99m not real=
ly sure. Why not? It=E2=80=99s unusual but clever. Control blocks introduce=
 some inefficiency, but it sounds like a big shortcut and efficiency gain v=
s. shared_ptr alone.

Anyway, the proposed extensions won=E2=80=99t add any overhead, and there a=
re surely other multithreaded applications out there with unsafe weak refer=
ences.

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

.


Author: David Krauss <potswa@gmail.com>
Date: Sun, 28 Dec 2014 15:13:04 +0800
Raw View
> On 2014=E2=80=9312=E2=80=9328, at 2:29 PM, David Krauss <potswa@gmail.com=
> wrote:
>=20
> Applications that want to safely invalidate unsynchronized weak reference=
s need another new primitive, perhaps call it expire(), which atomically re=
sets if unique. Then the caller can check whether the reset actually occurr=
ed. This is needed to make the design in the OP safe against a race between=
 a cache eviction (or clearing) and a cache access.

Eh, it=E2=80=99s not primitive. You can make a weak_pointer, reset the shar=
ed_ptr, and then reinitialize the shared_ptr from the weak_ptr.

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

.


Author: ramkumar.revanur@gmail.com
Date: Sun, 28 Dec 2014 00:09:39 -0800 (PST)
Raw View
------=_Part_1911_1647346677.1419754179526
Content-Type: multipart/alternative;
 boundary="----=_Part_1912_424288887.1419754179530"

------=_Part_1912_424288887.1419754179530
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

I like the idea of sum of shared and weak count. Not sure if it can be a=20
drop in replacement. Can be dangerous to existing code but did I=20
misunderstand what you are suggesting ?

From what I have seen, it is easy to implement this in existing=20
implementation on windows. I have to check if this is easy to implement in=
=20
other std libraries.


On Sunday, 28 December 2014 12:00:02 UTC+5:30, David Krauss wrote:
>
>
> > On 2014=E2=80=9312=E2=80=9328, at 1:07 PM, Ramkumar Revanur <write2r...=
@gmail.com=20
> <javascript:>> wrote:=20
> >=20
> > Just as new shared_ptr can be created to the same resource from existin=
g=20
> shared_ptr. The reliability of the "weak_count" is same as the reliabilit=
y=20
> of use_count on a shared_ptr.=20
>
> A combination of use_count and weak_count is safer, though, because a=20
> potentially-last owner can check that there are no other potential owners=
=20
> on other threads. The weak count would need to be checked (evaluated) fir=
st=20
> though, which is a bit tricky with unordered expression evaluation=20
> semantics.=20
>
> For that matter, a total reference_count which is the sum of strong and=
=20
> weak references would accomplish this more elegantly. It would be a drop-=
in=20
> replacement for use_count.=20
>
> Applications that want to safely invalidate unsynchronized weak reference=
s=20
> need another new primitive, perhaps call it expire(), which atomically=20
> resets if unique. Then the caller can check whether the reset actually=20
> occurred. This is needed to make the design in the OP safe against a race=
=20
> between a cache eviction (or clearing) and a cache access.=20
>
> Whether cache control is a valid use-case of weak_ptr, I=E2=80=99m not re=
ally=20
> sure. Why not? It=E2=80=99s unusual but clever. Control blocks introduce =
some=20
> inefficiency, but it sounds like a big shortcut and efficiency gain vs.=
=20
> shared_ptr alone.=20
>
> Anyway, the proposed extensions won=E2=80=99t add any overhead, and there=
 are=20
> surely other multithreaded applications out there with unsafe weak=20
> references.

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

------=_Part_1912_424288887.1419754179530
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">I like the idea of sum of shared and weak count. Not sure =
if it can be a drop in replacement. Can be dangerous to existing code but d=
id I misunderstand what you are suggesting ?<div><br></div><div>From what I=
 have seen, it is easy to implement this in existing implementation on wind=
ows. I have to check if this is easy to implement in other std libraries.<b=
r><br><br>On Sunday, 28 December 2014 12:00:02 UTC+5:30, David Krauss  wrot=
e:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;b=
order-left: 1px #ccc solid;padding-left: 1ex;">
<br>&gt; On 2014=E2=80=9312=E2=80=9328, at 1:07 PM, Ramkumar Revanur &lt;<a=
 href=3D"javascript:" target=3D"_blank" gdf-obfuscated-mailto=3D"4-boiSCh6R=
sJ" onmousedown=3D"this.href=3D'javascript:';return true;" onclick=3D"this.=
href=3D'javascript:';return true;">write2r...@gmail.com</a>&gt; wrote:
<br>&gt;=20
<br>&gt; Just as new shared_ptr can be created to the same resource from ex=
isting shared_ptr. The reliability of the "weak_count" is same as the relia=
bility of use_count on a shared_ptr.
<br>
<br>A combination of use_count and weak_count is safer, though, because a p=
otentially-last owner can check that there are no other potential owners on=
 other threads. The weak count would need to be checked (evaluated) first t=
hough, which is a bit tricky with unordered expression evaluation semantics=
..
<br>
<br>For that matter, a total reference_count which is the sum of strong and=
 weak references would accomplish this more elegantly. It would be a drop-i=
n replacement for use_count.
<br>
<br>Applications that want to safely invalidate unsynchronized weak referen=
ces need another new primitive, perhaps call it expire(), which atomically =
resets if unique. Then the caller can check whether the reset actually occu=
rred. This is needed to make the design in the OP safe against a race betwe=
en a cache eviction (or clearing) and a cache access.
<br>
<br>Whether cache control is a valid use-case of weak_ptr, I=E2=80=99m not =
really sure. Why not? It=E2=80=99s unusual but clever. Control blocks intro=
duce some inefficiency, but it sounds like a big shortcut and efficiency ga=
in vs. shared_ptr alone.
<br>
<br>Anyway, the proposed extensions won=E2=80=99t add any overhead, and the=
re are surely other multithreaded applications out there with unsafe weak r=
eferences.</blockquote></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_1912_424288887.1419754179530--
------=_Part_1911_1647346677.1419754179526--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Sun, 28 Dec 2014 12:01:23 -0200
Raw View
On Sunday 28 December 2014 00:09:39 ramkumar.revanur@gmail.com wrote:
> I like the idea of sum of shared and weak count. Not sure if it can be a
> drop in replacement. Can be dangerous to existing code but did I
> misunderstand what you are suggesting ?
>
> From what I have seen, it is easy to implement this in existing
> implementation on windows. I have to check if this is easy to implement in
> other std libraries.

A weak count or a total reference count are dangerous because one of the two
is not atomic. So not only would the value be stale by the time you got it, it
may also be fatally incorrect.

Imagine an implementation that keeps a separate strong count and a weak count.
When you ask for the total count, it needs to get both numbers and add them.
That's two operations and therefore not atomic. So it's possible that both
counts were 1 (two references) when the strong count was read, then the weak
reference was upgraded to a strong one, resulting in the weak count now being
zero and the function returning 1. That would imply the callee concludes it
has the only reference, which is incorrect.

It would be a similar situation if the implementation keeps a strong count and
a total count (such as the one I wrote for QSharedPointer). If you ask for the
weak count only, it needs to get the total count and subtract the number of
strong references. This is even worse, since the number of strong references
may have increased a lot between the two operations, so the weak count
function may return 1, zero or even negative numbers.

And I haven't heard a valid use-case for this yet. Though to be honest, I
don't know of a valid use-case for use_count() either, outside of debugging
and outside of a boolean "is it the only reference" condition.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Sun, 28 Dec 2014 12:02:55 -0200
Raw View
On Saturday 27 December 2014 20:46:29 Ramkumar Revanur wrote:
> > "Not to mention that any value you get is stale the
> > moment you got it, since weak_ptr is thread-safe and the atomic counter
> > may
> > have changed values already."
>
> The use_count on a shared_ptr will be as stale as the "weak_count" if that
> was available. Does not mean it is not useful!

Please see my other email about this.

This function is not only returning stale info, it may return *incorrect*
information. The only condition under which it would return correct info is
when you already know the information that it would return (that this is the
only reference).

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Sun, 28 Dec 2014 07:12:07 -0800 (PST)
Raw View
------=_Part_2039_404000390.1419779527827
Content-Type: multipart/alternative;
 boundary="----=_Part_2040_1838746563.1419779527827"

------=_Part_2040_1838746563.1419779527827
Content-Type: text/plain; charset=UTF-8

Let us assume that it is not straight forward to implement total_count
because the operation is not atomic. The total_count will require 2
operations as you have described. One operation to fetch the weak_count and
another to add this count to strong_count. Irrespective of how you hold the
information, there are 2 distinct operations that are to be performed.
Therefore can't be easily implemented. ( Maybe with a critical section /
volatile variables of some sort)

I am trying to understand the difficulties in implementation of weak_count
instead (on say std::shared_ptr). I don't see why the implementation detail
should not be similar to use_count on shared_ptr.

Further, I am not sure why you think the use case I have presented on
caching not valid. You can choose to implement in your own way but I am not
sure why if weak_count was available, this was not a valid use of it.


On Sunday, December 28, 2014 7:31:36 PM UTC+5:30, Thiago Macieira wrote:
>
> On Sunday 28 December 2014 00:09:39 ramkumar...@gmail.com <javascript:>
> wrote:
> > I like the idea of sum of shared and weak count. Not sure if it can be a
> > drop in replacement. Can be dangerous to existing code but did I
> > misunderstand what you are suggesting ?
> >
> > From what I have seen, it is easy to implement this in existing
> > implementation on windows. I have to check if this is easy to implement
> in
> > other std libraries.
>
> A weak count or a total reference count are dangerous because one of the
> two
> is not atomic. So not only would the value be stale by the time you got
> it, it
> may also be fatally incorrect.
>
> Imagine an implementation that keeps a separate strong count and a weak
> count.
> When you ask for the total count, it needs to get both numbers and add
> them.
> That's two operations and therefore not atomic. So it's possible that both
> counts were 1 (two references) when the strong count was read, then the
> weak
> reference was upgraded to a strong one, resulting in the weak count now
> being
> zero and the function returning 1. That would imply the callee concludes
> it
> has the only reference, which is incorrect.
>
> It would be a similar situation if the implementation keeps a strong count
> and
> a total count (such as the one I wrote for QSharedPointer). If you ask for
> the
> weak count only, it needs to get the total count and subtract the number
> of
> strong references. This is even worse, since the number of strong
> references
> may have increased a lot between the two operations, so the weak count
> function may return 1, zero or even negative numbers.
>
> And I haven't heard a valid use-case for this yet. Though to be honest, I
> don't know of a valid use-case for use_count() either, outside of
> debugging
> and outside of a boolean "is it the only reference" condition.
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_2040_1838746563.1419779527827
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div>Let us assume that it is not straight forward to impl=
ement total_count because the operation is not atomic. The total_count will=
 require 2 operations as you have described. One operation to fetch the wea=
k_count and another to add this count to strong_count. Irrespective of how =
you hold the information, there are 2 distinct operations that are to be pe=
rformed. Therefore can't be easily implemented. ( Maybe with a critical sec=
tion / volatile variables of some sort)</div><div><br></div><div>I am tryin=
g to understand the difficulties in implementation of weak_count instead (o=
n say std::shared_ptr). I don't see why the implementation detail should no=
t be similar to use_count on shared_ptr.</div><div><br></div><div>Further, =
I am not sure why you think the use case I have presented on caching not va=
lid. You can choose to implement in your own way but I am not sure why if w=
eak_count was available, this was not a valid use of it.</div><div><br></di=
v><div><br>On Sunday, December 28, 2014 7:31:36 PM UTC+5:30, Thiago Macieir=
a wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0=
..8ex;border-left: 1px #ccc solid;padding-left: 1ex;">On Sunday 28 December =
2014 00:09:39 <a href=3D"javascript:" target=3D"_blank" gdf-obfuscated-mail=
to=3D"meNxBqG1dMgJ" onmousedown=3D"this.href=3D'javascript:';return true;" =
onclick=3D"this.href=3D'javascript:';return true;">ramkumar...@gmail.com</a=
> wrote:
<br>&gt; I like the idea of sum of shared and weak count. Not sure if it ca=
n be a
<br>&gt; drop in replacement. Can be dangerous to existing code but did I
<br>&gt; misunderstand what you are suggesting ?
<br>&gt;=20
<br>&gt; From what I have seen, it is easy to implement this in existing
<br>&gt; implementation on windows. I have to check if this is easy to impl=
ement in
<br>&gt; other std libraries.
<br>
<br>A weak count or a total reference count are dangerous because one of th=
e two=20
<br>is not atomic. So not only would the value be stale by the time you got=
 it, it=20
<br>may also be fatally incorrect.
<br>
<br>Imagine an implementation that keeps a separate strong count and a weak=
 count.=20
<br>When you ask for the total count, it needs to get both numbers and add =
them.=20
<br>That's two operations and therefore not atomic. So it's possible that b=
oth=20
<br>counts were 1 (two references) when the strong count was read, then the=
 weak=20
<br>reference was upgraded to a strong one, resulting in the weak count now=
 being=20
<br>zero and the function returning 1. That would imply the callee conclude=
s it=20
<br>has the only reference, which is incorrect.
<br>
<br>It would be a similar situation if the implementation keeps a strong co=
unt and=20
<br>a total count (such as the one I wrote for QSharedPointer). If you ask =
for the=20
<br>weak count only, it needs to get the total count and subtract the numbe=
r of=20
<br>strong references. This is even worse, since the number of strong refer=
ences=20
<br>may have increased a lot between the two operations, so the weak count=
=20
<br>function may return 1, zero or even negative numbers.
<br>
<br>And I haven't heard a valid use-case for this yet. Though to be honest,=
 I=20
<br>don't know of a valid use-case for use_count() either, outside of debug=
ging=20
<br>and outside of a boolean "is it the only reference" condition.
<br>
<br>--=20
<br>Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" target=
=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75http%=
3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7euhq=
Ln_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/url=
?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNC=
Nanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a href=
=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http://ww=
w.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75AFQj=
CNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'http:=
//www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75=
AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&nbsp; &nbsp;Software Architect - Intel Open Source Technology Center
<br>&nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005 6EF4=
 5358
<br>
<br></blockquote></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_2040_1838746563.1419779527827--
------=_Part_2039_404000390.1419779527827--

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Sun, 28 Dec 2014 08:01:41 -0800 (PST)
Raw View
------=_Part_48_2133082613.1419782501073
Content-Type: multipart/alternative;
 boundary="----=_Part_49_627473673.1419782501073"

------=_Part_49_627473673.1419782501073
Content-Type: text/plain; charset=UTF-8

Look at the implementation of boost.

http://www.boost.org/doc/libs/1_57_0/boost/interprocess/smart_ptr/detail/shared_count.hpp

Boost has an implementation for weak_count!

template<class T, class VoidAllocator, class Deleter>
class weak_count { ... };




On Sunday, December 28, 2014 7:33:06 PM UTC+5:30, Thiago Macieira wrote:
>
> On Saturday 27 December 2014 20:46:29 Ramkumar Revanur wrote:
> > > "Not to mention that any value you get is stale the
> > > moment you got it, since weak_ptr is thread-safe and the atomic
> counter
> > > may
> > > have changed values already."
> >
> > The use_count on a shared_ptr will be as stale as the "weak_count" if
> that
> > was available. Does not mean it is not useful!
>
> Please see my other email about this.
>
> This function is not only returning stale info, it may return *incorrect*
> information. The only condition under which it would return correct info
> is
> when you already know the information that it would return (that this is
> the
> only reference).
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_49_627473673.1419782501073
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">Look at the implementation of boost.<div><br></div><div>ht=
tp://www.boost.org/doc/libs/1_57_0/boost/interprocess/smart_ptr/detail/shar=
ed_count.hpp</div><div><br></div><div>Boost has an implementation for weak_=
count!</div><div><br></div><div><pre style=3D"margin: 1.5em; padding: 0.5em=
; font-size: 11px; border: 1px solid rgb(204, 204, 204); overflow: auto; cl=
ear: left; color: rgb(0, 0, 0);">template&lt;class T, class VoidAllocator, =
class Deleter&gt;
class weak_count { ... };</pre><div><br></div><div><br></div><br>On Sunday,=
 December 28, 2014 7:33:06 PM UTC+5:30, Thiago Macieira wrote:<blockquote c=
lass=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px=
 #ccc solid;padding-left: 1ex;">On Saturday 27 December 2014 20:46:29 Ramku=
mar Revanur wrote:
<br>&gt; &gt; "Not to mention that any value you get is stale the
<br>&gt; &gt; moment you got it, since weak_ptr is thread-safe and the atom=
ic counter
<br>&gt; &gt; may
<br>&gt; &gt; have changed values already."
<br>&gt;=20
<br>&gt; The use_count on a shared_ptr will be as stale as the "weak_count"=
 if that
<br>&gt; was available. Does not mean it is not useful!
<br>
<br>Please see my other email about this.
<br>
<br>This function is not only returning stale info, it may return *incorrec=
t*=20
<br>information. The only condition under which it would return correct inf=
o is=20
<br>when you already know the information that it would return (that this i=
s the=20
<br>only reference).
<br>
<br>--=20
<br>Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" target=
=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75http%=
3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7euhq=
Ln_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/url=
?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNC=
Nanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a href=
=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http://ww=
w.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75AFQj=
CNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'http:=
//www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75=
AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&nbsp; &nbsp;Software Architect - Intel Open Source Technology Center
<br>&nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005 6EF4=
 5358
<br>
<br></blockquote></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_49_627473673.1419782501073--
------=_Part_48_2133082613.1419782501073--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Sun, 28 Dec 2014 16:06:28 -0200
Raw View
On Sunday 28 December 2014 07:12:07 Ramkumar Revanur wrote:
> Let us assume that it is not straight forward to implement total_count
> because the operation is not atomic. The total_count will require 2
> operations as you have described. One operation to fetch the weak_count and
> another to add this count to strong_count. Irrespective of how you hold the
> information, there are 2 distinct operations that are to be performed.
> Therefore can't be easily implemented. ( Maybe with a critical section /
> volatile variables of some sort)
>
> I am trying to understand the difficulties in implementation of weak_count
> instead (on say std::shared_ptr). I don't see why the implementation detail
> should not be similar to use_count on shared_ptr.

Like I said, it's one of the two. If the implementation holds a separate
strong and weak count, then implementing the weak count is trivial, but
implementing the total count is non-atomic. Alternatively, if the
implementation holds a strong count and a total count (like QSharedPointer
does), then implementing the weak count is non-atomic and, since it involves a
subtraction, it's even worse. However, it's easier to implement the pointers.

> Further, I am not sure why you think the use case I have presented on
> caching not valid. You can choose to implement in your own way but I am not
> sure why if weak_count was available, this was not a valid use of it.

Because either it doesn't work or I didn't understand it.

Your code held a weak_ptr to some object. That means it caches nothing, as the
data can be deleted outside of the cache's control. Any data that is still
accessible is being held alive by something else and therefore the cache,
again, does not control its lifetime.

Besides, what would you do with the number of weak references? You may have a
thousand users of the same weak_ptr object, but that's not relevant
information if the number of shared_ptr users is zero.

Maybe you wanted to get the weak count from a shared_ptr? That might make more
sense, but I still question it. So what if there are a thousand users? They
may simply want to be notified when the object gets deleted and they don't want
to influence its deletion -- that's why they're weak_ptr references instead of
shared_ptr ones.

If we go through with this, then I'd advise to go for the total count and
leave a big warning in the standard saying "in multithreaded applications, the
value returned by this function may be unreliable (more unreliable than
use_count); applications should not use this for anything except debugging".

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Sun, 28 Dec 2014 16:12:27 -0200
Raw View
On Sunday 28 December 2014 08:01:41 Ramkumar Revanur wrote:
> Look at the implementation of boost.
>
> http://www.boost.org/doc/libs/1_57_0/boost/interprocess/smart_ptr/detail/sha
> red_count.hpp
>
> Boost has an implementation for weak_count!
>
> template<class T, class VoidAllocator, class Deleter>
> class weak_count { ... };

I don't see it.

template<class T, class VoidAllocator, class Deleter>
class shared_count
{
    [...]
   long use_count() const // nothrow
   {  return m_pi != 0? m_pi->use_count(): 0;  }
    [...]
};

template<class T, class VoidAllocator, class Deleter>
class weak_count
{
    [...]
   long use_count() const // nothrow
   {  return m_pi != 0? m_pi->use_count() : 0;   }
    [...]
};

The two classes have the same implementation of use_count(). That means either
one of the two is broken or this weak_count class does not do what this mail
thread is asking for.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Howard Hinnant <howard.hinnant@gmail.com>
Date: Sun, 28 Dec 2014 14:38:01 -0500
Raw View
Informational:

The libc++ implementation would implement weak_count like so:

    long
    weak_count() const noexcept
    {
        return __shared_weak_owners_ + 1 - (use_count() > 0);
    }

I.e. the =E2=80=9Ccount of weak owners=E2=80=9D is not strictly a count of =
weak_ptrs, nor is it a total count.  All shared (strong) owners collectivel=
y count as a single weak owner.

Therefore, on this platform, neither weak_count() nor total_count() would b=
e atomic if called via a weak_ptr.  However if weak_count() is called via a=
 shared_ptr, one could assume a preori (if the shared_ptr is not empty) tha=
t use_count() > 0, and therefore the result would be atomic.  total_count()=
 would still be non-atomic if called via a shared_ptr.

shared_ptr::use_count();  atomic
shared_ptr::weak_count();  atomic
shared_ptr::total_count();  not atomic

weak_ptr::use_count();  atomic
weak_ptr::weak_count();  not atomic
weak_ptr::total_count();  not atomic

Howard

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Sun, 28 Dec 2014 20:39:58 -0200
Raw View
On Sunday 28 December 2014 14:38:01 Howard Hinnant wrote:
> shared_ptr::use_count();  atomic
> shared_ptr::weak_count();  atomic
> shared_ptr::total_count();  not atomic
>
> weak_ptr::use_count();  atomic
> weak_ptr::weak_count();  not atomic
> weak_ptr::total_count();  not atomic

libstdc++'s implementation appears to be the same as libc++'s

For QSharedPointer's implementation:

use_count(): atomic
weak_count(): not atomic
total_count(): atomic

For all users.

It stands to reason someone may have implemented a std::shared_ptr/weak_ptr
similar to what I did for QSharedPointer. Therefore, it's not possible to
guarantee in the standard which of the operations would be atomic. In turn, if
we add the function, it needs to come with a big warning saying the result may
be incorrect if the application is multithreaded.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Mon, 29 Dec 2014 02:18:37 -0800 (PST)
Raw View
------=_Part_196_2022955632.1419848317607
Content-Type: multipart/alternative;
 boundary="----=_Part_197_854207720.1419848317607"

------=_Part_197_854207720.1419848317607
Content-Type: text/plain; charset=UTF-8

Let me explain the use case again but in more detail.

I have a caching library that is responsible for the lifetime of the cached
objects. The cached objects may get populated from a database or a file.
Sqlite, Mangodb, boost memory mapped file, use your imagination.

The lifetime of the cached object is influenced by one or more of the
following

1. time when the cached object was created
2. the frequency of accessing it
3. the time it was last accessed
4. the maximum cache size the user wants the library to create before some
objects can be disposed
5 ...
(I think you get the picture)

The strategy for disposing a cached object could be a pattern decided by
rules that best suits the user. Best to simplify by saying, the library
should be smart to decide which cached objects should be disposed.
Because the library is expected to manage the lifetime of the cached
objects, the user of the library in not in control of the lifetime of the
cached object.

When the user wants to access the cached object, he fetches the cache
object wrapped in a weak_ptr. He can lock this object within a scope to get
hold of the shared_ptr. Within this scope, he will be guaranteed the
validity of the cache object. The worst the library can do is to release
the copy of shared_ptr it has but the reference count is not 0 as within
the current scope, there is a strong owner that feeds the cache object to
the user.

Now, there could be another process that could be writing to the cache
source (database / file., etc). The caching library can either update those
cached objects that are updated or decide to dispose them based on strategy
that best suits the user. If the user decided to no longer user the cached
object, he can inform the library that he is no longer using it or can
simply drop the weak_ptr and the library will know that there is no active
tracking pointer to the cached object and drop the object. Hope this
explains the motivation to use weak_ptr and weak_count.

I am sure there are other ways of implementing it and so is the case for
most problems.



> "Because either it doesn't work or I didn't understand it.
>
> Your code held a weak_ptr to some object. That means it caches nothing, as
> the
> data can be deleted outside of the cache's control. Any data that is still
> accessible is being held alive by something else and therefore the cache,
> again, does not control its lifetime.
>
> Besides, what would you do with the number of weak references? You may
> have a
> thousand users of the same weak_ptr object, but that's not relevant
> information if the number of shared_ptr users is zero.
>
> Maybe you wanted to get the weak count from a shared_ptr? That might make
> more
> sense, but I still question it. So what if there are a thousand users?
> They
> may simply want to be notified when the object gets deleted and they don't
> want
> to influence its deletion -- that's why they're weak_ptr references
> instead of
> shared_ptr ones.
>
> If we go through with this, then I'd advise to go for the total count and
> leave a big warning in the standard saying "in multithreaded applications,
> the
> value returned by this function may be unreliable (more unreliable than
> use_count); applications should not use this for anything except
> debugging".
>
>


--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_197_854207720.1419848317607
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div>Let me explain the use case again but in more detail.=
</div><div><br></div><div>I have a caching library that is responsible for =
the lifetime of the cached objects. The cached objects may get populated fr=
om a database or a file. Sqlite, Mangodb, boost memory mapped file, use you=
r imagination.</div><div><br></div><div>The lifetime of the cached object i=
s influenced by one or more of the following&nbsp;</div><div><br></div><div=
>1. time when the cached object was created</div><div>2. the frequency of a=
ccessing it</div><div>3. the time it was last accessed</div><div>4. the max=
imum cache size the user wants the library to create before some objects ca=
n be disposed</div><div>5 ...</div><div>(I think you get the picture)</div>=
<div><br></div><div>The strategy for disposing a cached object could be a p=
attern decided by rules that best suits the user. Best to simplify by sayin=
g, the library should be smart to decide which cached objects should be dis=
posed.</div><div>Because the library is expected to manage the lifetime of =
the cached objects, the user of the library in not in control of the lifeti=
me of the cached object.</div><div><br></div><div>When the user wants to ac=
cess the cached object, he fetches the cache object wrapped in a weak_ptr. =
He can lock this object within a scope to get hold of the shared_ptr. Withi=
n this scope, he will be guaranteed the validity of the cache object. The w=
orst the library can do is to release the copy of shared_ptr it has but the=
 reference count is not 0 as within the current scope, there is a strong ow=
ner that feeds the cache object to the user.</div><div><br></div><div>Now, =
there could be another process that could be writing to the cache source (d=
atabase / file., etc). The caching library can either update those cached o=
bjects that are updated or decide to dispose them based on strategy that be=
st suits the user. If the user decided to no longer user the cached object,=
 he can inform the library that he is no longer using it or can simply drop=
 the weak_ptr and the library will know that there is no active tracking po=
inter to the cached object and drop the object. Hope this explains the moti=
vation to use weak_ptr and weak_count.</div><div><br></div><div>I am sure t=
here are other ways of implementing it and so is the case for most problems=
..</div><div><br></div><div>&nbsp;</div><blockquote class=3D"gmail_quote" st=
yle=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-lef=
t: 1ex;">"Because either it doesn't work or I didn't understand it.
<br>
<br>Your code held a weak_ptr to some object. That means it caches nothing,=
 as the=20
<br>data can be deleted outside of the cache's control. Any data that is st=
ill=20
<br>accessible is being held alive by something else and therefore the cach=
e,=20
<br>again, does not control its lifetime.
<br>
<br>Besides, what would you do with the number of weak references? You may =
have a=20
<br>thousand users of the same weak_ptr object, but that's not relevant=20
<br>information if the number of shared_ptr users is zero.=20
<br>
<br>Maybe you wanted to get the weak count from a shared_ptr? That might ma=
ke more=20
<br>sense, but I still question it. So what if there are a thousand users? =
They=20
<br>may simply want to be notified when the object gets deleted and they do=
n't want=20
<br>to influence its deletion -- that's why they're weak_ptr references ins=
tead of=20
<br>shared_ptr ones.
<br>
<br>If we go through with this, then I'd advise to go for the total count a=
nd=20
<br>leave a big warning in the standard saying "in multithreaded applicatio=
ns, the=20
<br>value returned by this function may be unreliable (more unreliable than=
=20
<br>use_count); applications should not use this for anything except debugg=
ing".
<br><br></blockquote><div><br></div><div>&nbsp;</div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_197_854207720.1419848317607--
------=_Part_196_2022955632.1419848317607--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Mon, 29 Dec 2014 11:09:25 -0200
Raw View
On Monday 29 December 2014 02:18:37 Ramkumar Revanur wrote:
> When the user wants to access the cached object, he fetches the cache
> object wrapped in a weak_ptr. He can lock this object within a scope to get
> hold of the shared_ptr. Within this scope, he will be guaranteed the
> validity of the cache object. The worst the library can do is to release
> the copy of shared_ptr it has but the reference count is not 0 as within
> the current scope, there is a strong owner that feeds the cache object to
> the user.
>
> Now, there could be another process that could be writing to the cache
> source (database / file., etc). The caching library can either update those
> cached objects that are updated or decide to dispose them based on strategy
> that best suits the user. If the user decided to no longer user the cached
> object, he can inform the library that he is no longer using it or can
> simply drop the weak_ptr and the library will know that there is no active
> tracking pointer to the cached object and drop the object. Hope this
> explains the motivation to use weak_ptr and weak_count.

I find two problems with that API (this is IMO):

First, the cache manager should return a shared_ptr, not a weak_ptr, so the
user knows that the object she asked for didn't become invalid in the
microseconds between the asking and the converting to shared_ptr. If you have
an API that returns an explanation for the cache miss, then the cache hit
should be a shared_ptr. If, however, it indicates a cache miss by returning a
null pointer anyway, then this problem is minimised.

Second, since you can't forbid the upgrade to shared_ptr, the user can store
shared_ptr of your cached objects and negate your tracking of memory
consumption anyway. Moreover, the user should store weak_ptr when she wants to
declare "I don't care if this gets deleted". Your design calls for weak_ptr to
be used in the same role as shared_ptr, since it influences whether the object
gets deleted or not.

It sounds like you want an intermediate solution:
 a) like shared_ptr, is used to make the decision to delete
 b) like weak_ptr, cannot *stop* the deletion

Still IMO, you're abusing weak_ptr by using it in the way you described. The
Standard Library cannot be asked to do your job for you. Instead, you should
wrap the object and the pointer in your own class that accesses the internal
data where required. Your own class can then update an internal count of
active references. It can also update an internal age of how recently the
object has been used (the coarse monotonic timer on Linux costs little more
than one function call to obtain).

Therefore, since I find that a solution there is another solution that is a)
superior to the weak_ptr solution, b) doesn't abuse weak_ptr for what it
wasn't intended, and c) works even in multithreaded programs[*], I am still
discounting your scenario as valid.

[*] see Message-ID: <9595545.eDdFo9NLoN@tjmaciei-mobl4> for the conclusion
that weak_count would be not atomic in two of three scenarios and total_count
would also be not atomic in two of three scenarios.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Mon, 29 Dec 2014 08:31:09 -0800 (PST)
Raw View
------=_Part_846_273368555.1419870669493
Content-Type: multipart/alternative;
 boundary="----=_Part_847_1037782952.1419870669493"

------=_Part_847_1037782952.1419870669493
Content-Type: text/plain; charset=UTF-8

IMO, you have not understood my use case on caching. But that is not the
point of the discussion anyway. Difficulty to support function in a
specific implementation is also not the discussion point.

The objective of this discussion is to get views of this *forum* on
weak_count. If there is consensus, I can submit a patch to boost as a first
step.


On Monday, December 29, 2014 6:39:33 PM UTC+5:30, Thiago Macieira wrote:
>
> On Monday 29 December 2014 02:18:37 Ramkumar Revanur wrote:
> > When the user wants to access the cached object, he fetches the cache
> > object wrapped in a weak_ptr. He can lock this object within a scope to
> get
> > hold of the shared_ptr. Within this scope, he will be guaranteed the
> > validity of the cache object. The worst the library can do is to release
> > the copy of shared_ptr it has but the reference count is not 0 as within
> > the current scope, there is a strong owner that feeds the cache object
> to
> > the user.
> >
> > Now, there could be another process that could be writing to the cache
> > source (database / file., etc). The caching library can either update
> those
> > cached objects that are updated or decide to dispose them based on
> strategy
> > that best suits the user. If the user decided to no longer user the
> cached
> > object, he can inform the library that he is no longer using it or can
> > simply drop the weak_ptr and the library will know that there is no
> active
> > tracking pointer to the cached object and drop the object. Hope this
> > explains the motivation to use weak_ptr and weak_count.
>
> I find two problems with that API (this is IMO):
>
> First, the cache manager should return a shared_ptr, not a weak_ptr, so
> the
> user knows that the object she asked for didn't become invalid in the
> microseconds between the asking and the converting to shared_ptr. If you
> have
> an API that returns an explanation for the cache miss, then the cache hit
> should be a shared_ptr. If, however, it indicates a cache miss by
> returning a
> null pointer anyway, then this problem is minimised.
>
> Second, since you can't forbid the upgrade to shared_ptr, the user can
> store
> shared_ptr of your cached objects and negate your tracking of memory
> consumption anyway. Moreover, the user should store weak_ptr when she
> wants to
> declare "I don't care if this gets deleted". Your design calls for
> weak_ptr to
> be used in the same role as shared_ptr, since it influences whether the
> object
> gets deleted or not.
>
> It sounds like you want an intermediate solution:
>  a) like shared_ptr, is used to make the decision to delete
>  b) like weak_ptr, cannot *stop* the deletion
>
> Still IMO, you're abusing weak_ptr by using it in the way you described.
> The
> Standard Library cannot be asked to do your job for you. Instead, you
> should
> wrap the object and the pointer in your own class that accesses the
> internal
> data where required. Your own class can then update an internal count of
> active references. It can also update an internal age of how recently the
> object has been used (the coarse monotonic timer on Linux costs little
> more
> than one function call to obtain).
>
> Therefore, since I find that a solution there is another solution that is
> a)
> superior to the weak_ptr solution, b) doesn't abuse weak_ptr for what it
> wasn't intended, and c) works even in multithreaded programs[*], I am
> still
> discounting your scenario as valid.
>
> [*] see Message-ID: <9595545.eDdFo9NLoN@tjmaciei-mobl4> for the conclusion
> that weak_count would be not atomic in two of three scenarios and
> total_count
> would also be not atomic in two of three scenarios.
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_847_1037782952.1419870669493
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">IMO, you have not understood my use case on caching. But t=
hat is not the point of the discussion anyway. Difficulty to support functi=
on in a specific implementation is also not the discussion point.<div><br><=
div>The objective of this discussion is to get views of this *forum* on wea=
k_count. If there is consensus, I can submit a patch to boost as a first st=
ep.<div><br></div><div><div><br>On Monday, December 29, 2014 6:39:33 PM UTC=
+5:30, Thiago Macieira wrote:<blockquote class=3D"gmail_quote" style=3D"mar=
gin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;">O=
n Monday 29 December 2014 02:18:37 Ramkumar Revanur wrote:
<br>&gt; When the user wants to access the cached object, he fetches the ca=
che=20
<br>&gt; object wrapped in a weak_ptr. He can lock this object within a sco=
pe to get=20
<br>&gt; hold of the shared_ptr. Within this scope, he will be guaranteed t=
he
<br>&gt; validity of the cache object. The worst the library can do is to r=
elease
<br>&gt; the copy of shared_ptr it has but the reference count is not 0 as =
within
<br>&gt; the current scope, there is a strong owner that feeds the cache ob=
ject to
<br>&gt; the user.
<br>&gt;=20
<br>&gt; Now, there could be another process that could be writing to the c=
ache=20
<br>&gt; source (database / file., etc). The caching library can either upd=
ate those=20
<br>&gt; cached objects that are updated or decide to dispose them based on=
 strategy
<br>&gt; that best suits the user. If the user decided to no longer user th=
e cached
<br>&gt; object, he can inform the library that he is no longer using it or=
 can
<br>&gt; simply drop the weak_ptr and the library will know that there is n=
o active
<br>&gt; tracking pointer to the cached object and drop the object. Hope th=
is
<br>&gt; explains the motivation to use weak_ptr and weak_count.
<br>
<br>I find two problems with that API (this is IMO):
<br>
<br>First, the cache manager should return a shared_ptr, not a weak_ptr, so=
 the=20
<br>user knows that the object she asked for didn't become invalid in the=
=20
<br>microseconds between the asking and the converting to shared_ptr. If yo=
u have=20
<br>an API that returns an explanation for the cache miss, then the cache h=
it=20
<br>should be a shared_ptr. If, however, it indicates a cache miss by retur=
ning a=20
<br>null pointer anyway, then this problem is minimised.
<br>
<br>Second, since you can't forbid the upgrade to shared_ptr, the user can =
store=20
<br>shared_ptr of your cached objects and negate your tracking of memory=20
<br>consumption anyway. Moreover, the user should store weak_ptr when she w=
ants to=20
<br>declare "I don't care if this gets deleted". Your design calls for weak=
_ptr to=20
<br>be used in the same role as shared_ptr, since it influences whether the=
 object=20
<br>gets deleted or not.
<br>
<br>It sounds like you want an intermediate solution:
<br>&nbsp;a) like shared_ptr, is used to make the decision to delete
<br>&nbsp;b) like weak_ptr, cannot *stop* the deletion
<br>
<br>Still IMO, you're abusing weak_ptr by using it in the way you described=
.. The=20
<br>Standard Library cannot be asked to do your job for you. Instead, you s=
hould=20
<br>wrap the object and the pointer in your own class that accesses the int=
ernal=20
<br>data where required. Your own class can then update an internal count o=
f=20
<br>active references. It can also update an internal age of how recently t=
he=20
<br>object has been used (the coarse monotonic timer on Linux costs little =
more=20
<br>than one function call to obtain).
<br>
<br>Therefore, since I find that a solution there is another solution that =
is a)=20
<br>superior to the weak_ptr solution, b) doesn't abuse weak_ptr for what i=
t=20
<br>wasn't intended, and c) works even in multithreaded programs[*], I am s=
till=20
<br>discounting your scenario as valid.
<br>
<br>[*] see Message-ID: &lt;9595545.eDdFo9NLoN@tjmaciei-<wbr>mobl4&gt; for =
the conclusion=20
<br>that weak_count would be not atomic in two of three scenarios and total=
_count=20
<br>would also be not atomic in two of three scenarios.
<br>
<br>--=20
<br>Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" target=
=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75http%=
3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7euhq=
Ln_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/url=
?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNC=
Nanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a href=
=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http://ww=
w.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75AFQj=
CNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'http:=
//www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75=
AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&nbsp; &nbsp;Software Architect - Intel Open Source Technology Center
<br>&nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005 6EF4=
 5358
<br>
<br></blockquote></div></div></div></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_847_1037782952.1419870669493--
------=_Part_846_273368555.1419870669493--

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Mon, 29 Dec 2014 08:37:18 -0800 (PST)
Raw View
------=_Part_5170_1033569781.1419871038331
Content-Type: multipart/alternative;
 boundary="----=_Part_5171_212088684.1419871038332"

------=_Part_5171_212088684.1419871038332
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: quoted-printable


Thank you for this post. It does clear the air in terms of plausible atomic=
=20
implementation on shared_ptr.


On Monday, December 29, 2014 1:08:03 AM UTC+5:30, Howard Hinnant wrote:
>
> Informational:=20
>
> The libc++ implementation would implement weak_count like so:=20
>
>     long=20
>     weak_count() const noexcept=20
>     {=20
>         return __shared_weak_owners_ + 1 - (use_count() > 0);=20
>     }=20
>
> I.e. the =E2=80=9Ccount of weak owners=E2=80=9D is not strictly a count o=
f weak_ptrs, nor=20
> is it a total count.  All shared (strong) owners collectively count as a=
=20
> single weak owner.=20
>
> Therefore, on this platform, neither weak_count() nor total_count() would=
=20
> be atomic if called via a weak_ptr.  However if weak_count() is called vi=
a=20
> a shared_ptr, one could assume a preori (if the shared_ptr is not empty)=
=20
> that use_count() > 0, and therefore the result would be atomic.=20
>  total_count() would still be non-atomic if called via a shared_ptr.=20
>
> shared_ptr::use_count();  atomic=20
> shared_ptr::weak_count();  atomic=20
> shared_ptr::total_count();  not atomic=20
>
> weak_ptr::use_count();  atomic=20
> weak_ptr::weak_count();  not atomic=20
> weak_ptr::total_count();  not atomic=20
>
> Howard=20
>
>

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

------=_Part_5171_212088684.1419871038332
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div><br></div>Thank you for this post. It does clear the =
air in terms of plausible atomic implementation on shared_ptr.<div><br></di=
v><div><div><br>On Monday, December 29, 2014 1:08:03 AM UTC+5:30, Howard Hi=
nnant wrote:<blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-lef=
t: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;">Informational:
<br>
<br>The libc++ implementation would implement weak_count like so:
<br>
<br>&nbsp; &nbsp; long
<br>&nbsp; &nbsp; weak_count() const noexcept
<br>&nbsp; &nbsp; {
<br>&nbsp; &nbsp; &nbsp; &nbsp; return __shared_weak_owners_ + 1 - (use_cou=
nt() &gt; 0);
<br>&nbsp; &nbsp; }
<br>
<br>I.e. the =E2=80=9Ccount of weak owners=E2=80=9D is not strictly a count=
 of weak_ptrs, nor is it a total count. &nbsp;All shared (strong) owners co=
llectively count as a single weak owner.
<br>
<br>Therefore, on this platform, neither weak_count() nor total_count() wou=
ld be atomic if called via a weak_ptr. &nbsp;However if weak_count() is cal=
led via a shared_ptr, one could assume a preori (if the shared_ptr is not e=
mpty) that use_count() &gt; 0, and therefore the result would be atomic. &n=
bsp;total_count() would still be non-atomic if called via a shared_ptr.
<br>
<br>shared_ptr::use_count(); &nbsp;atomic
<br>shared_ptr::weak_count(); &nbsp;atomic
<br>shared_ptr::total_count(); &nbsp;not atomic
<br>
<br>weak_ptr::use_count(); &nbsp;atomic
<br>weak_ptr::weak_count(); &nbsp;not atomic
<br>weak_ptr::total_count(); &nbsp;not atomic
<br>
<br>Howard
<br>
<br></blockquote></div></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_5171_212088684.1419871038332--
------=_Part_5170_1033569781.1419871038331--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Mon, 29 Dec 2014 15:38:32 -0200
Raw View
On Monday 29 December 2014 08:31:09 Ramkumar Revanur wrote:
> IMO, you have not understood my use case on caching. But that is not the
> point of the discussion anyway. Difficulty to support function in a
> specific implementation is also not the discussion point.
>
> The objective of this discussion is to get views of this *forum* on
> weak_count. If there is consensus, I can submit a patch to boost as a first
> step.

I disagree that the difficulty of implementing is not part of the discussion. I
think it's core to the discussion. If the function cannot return a reliable
and correct value, then it should not exist.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Douglas Boffey <douglas.boffey@gmail.com>
Date: Mon, 29 Dec 2014 20:21:31 +0000
Raw View
If there's a problem with atomicity, why not a function returning both
counts simultaneously?

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 02:14:36 -0200
Raw View
On Monday 29 December 2014 20:21:31 Douglas Boffey wrote:
> If there's a problem with atomicity, why not a function returning both
> counts simultaneously?

Because that's still not atomic. It suffers from the exact same problem as I
described before. That still requires two load operations, which means the one
value loaded before might have changed by the time it got returned.

In other words having one function that returns a pair is no different than two
functions returning each an individual value.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Mon, 29 Dec 2014 21:45:04 -0800 (PST)
Raw View
------=_Part_8258_1447259267.1419918304915
Content-Type: multipart/alternative;
 boundary="----=_Part_8259_1686714547.1419918304915"

------=_Part_8259_1686714547.1419918304915
Content-Type: text/plain; charset=UTF-8

The difficulty in a *specific* implementation. The operative word here is
specific.

On Monday, December 29, 2014 11:08:37 PM UTC+5:30, Thiago Macieira wrote:
>
> On Monday 29 December 2014 08:31:09 Ramkumar Revanur wrote:
> > IMO, you have not understood my use case on caching. But that is not the
> > point of the discussion anyway. Difficulty to support function in a
> > specific implementation is also not the discussion point.
> >
> > The objective of this discussion is to get views of this *forum* on
> > weak_count. If there is consensus, I can submit a patch to boost as a
> first
> > step.
>
> I disagree that the difficulty of implementing is not part of the
> discussion. I
> think it's core to the discussion. If the function cannot return a
> reliable
> and correct value, then it should not exist.
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_8259_1686714547.1419918304915
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">The difficulty in a *specific* implementation. The operati=
ve word here is specific.<br><br>On Monday, December 29, 2014 11:08:37 PM U=
TC+5:30, Thiago Macieira wrote:<blockquote class=3D"gmail_quote" style=3D"m=
argin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding-left: 1ex;"=
>On Monday 29 December 2014 08:31:09 Ramkumar Revanur wrote:
<br>&gt; IMO, you have not understood my use case on caching. But that is n=
ot the
<br>&gt; point of the discussion anyway. Difficulty to support function in =
a
<br>&gt; specific implementation is also not the discussion point.
<br>&gt;=20
<br>&gt; The objective of this discussion is to get views of this *forum* o=
n
<br>&gt; weak_count. If there is consensus, I can submit a patch to boost a=
s a first
<br>&gt; step.
<br>
<br>I disagree that the difficulty of implementing is not part of the discu=
ssion. I=20
<br>think it's core to the discussion. If the function cannot return a reli=
able=20
<br>and correct value, then it should not exist.
<br>
<br>--=20
<br>Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" target=
=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75http%=
3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7euhq=
Ln_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/url=
?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNC=
Nanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a href=
=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http://ww=
w.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75AFQj=
CNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'http:=
//www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75=
AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&nbsp; &nbsp;Software Architect - Intel Open Source Technology Center
<br>&nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005 6EF4=
 5358
<br>
<br></blockquote></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_8259_1686714547.1419918304915--
------=_Part_8258_1447259267.1419918304915--

.


Author: Douglas Boffey <douglas.boffey@gmail.com>
Date: Tue, 30 Dec 2014 09:35:48 +0000
Raw View
And I suppose wrapping it in a mutex is no go?

On 12/30/14, Thiago Macieira <thiago@macieira.org> wrote:
> On Monday 29 December 2014 20:21:31 Douglas Boffey wrote:
>> If there's a problem with atomicity, why not a function returning both
>> counts simultaneously?
>
> Because that's still not atomic. It suffers from the exact same problem as I
>
> described before. That still requires two load operations, which means the
> one
> value loaded before might have changed by the time it got returned.
>
> In other words having one function that returns a pair is no different than
> two
> functions returning each an individual value.
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
> --
>
> ---
> You received this message because you are subscribed to the Google Groups
> "ISO C++ Standard - Future Proposals" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to std-proposals+unsubscribe@isocpp.org.
> To post to this group, send email to std-proposals@isocpp.org.
> Visit this group at
> http://groups.google.com/a/isocpp.org/group/std-proposals/.
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Tue, 30 Dec 2014 04:09:03 -0800 (PST)
Raw View
------=_Part_2822_1298197023.1419941343143
Content-Type: multipart/alternative;
 boundary="----=_Part_2823_363512041.1419941343143"

------=_Part_2823_363512041.1419941343143
Content-Type: text/plain; charset=UTF-8

There is no need for a mutex if the implementation can be atomic.

From the information presented in the thread

For QSharedPointer's implementation:

use_count(): atomic
weak_count(): not atomic
total_count(): atomic

For LibstdC++ / libC++

shared_ptr::use_count();  atomic
shared_ptr::weak_count();  atomic
shared_ptr::total_count();  not atomic

Now, for making a proposal we have to choose one of the approach for
getting the weak_count and I am OK with weak_count or total_count




On Tuesday, December 30, 2014 3:05:49 PM UTC+5:30, Douglas Boffey wrote:
>
> And I suppose wrapping it in a mutex is no go?
>
> On 12/30/14, Thiago Macieira <thi...@macieira.org <javascript:>> wrote:
> > On Monday 29 December 2014 20:21:31 Douglas Boffey wrote:
> >> If there's a problem with atomicity, why not a function returning both
> >> counts simultaneously?
> >
> > Because that's still not atomic. It suffers from the exact same problem
> as I
> >
> > described before. That still requires two load operations, which means
> the
> > one
> > value loaded before might have changed by the time it got returned.
> >
> > In other words having one function that returns a pair is no different
> than
> > two
> > functions returning each an individual value.
> >
> > --
> > Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
> >    Software Architect - Intel Open Source Technology Center
> >       PGP/GPG: 0x6EF45358; fingerprint:
> >       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
> >
> > --
> >
> > ---
> > You received this message because you are subscribed to the Google
> Groups
> > "ISO C++ Standard - Future Proposals" group.
> > To unsubscribe from this group and stop receiving emails from it, send
> an
> > email to std-proposal...@isocpp.org <javascript:>.
> > To post to this group, send email to std-pr...@isocpp.org <javascript:>.
>
> > Visit this group at
> > http://groups.google.com/a/isocpp.org/group/std-proposals/.
> >
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_2823_363512041.1419941343143
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">There is no need for a mutex if the implementation can be =
atomic.<div><br></div><div>From the information presented in the thread</di=
v><div><br></div><div>For QSharedPointer's implementation:&nbsp;<br><br>use=
_count(): atomic&nbsp;<br>weak_count(): not atomic&nbsp;<br>total_count(): =
atomic</div><div><br></div><div>For LibstdC++ / libC++</div><div><br></div>=
<div>shared_ptr::use_count(); &nbsp;atomic&nbsp;<br>shared_ptr::weak_count(=
); &nbsp;atomic&nbsp;<br>shared_ptr::total_count(); &nbsp;not atomic&nbsp;<=
br></div><div><br>Now, for making a proposal we have to choose one of the a=
pproach for getting the weak_count and I am OK with weak_count or total_cou=
nt</div><div><br></div><div><br></div><div><br></div><div><br>On Tuesday, D=
ecember 30, 2014 3:05:49 PM UTC+5:30, Douglas Boffey wrote:<blockquote clas=
s=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #c=
cc solid;padding-left: 1ex;">And I suppose wrapping it in a mutex is no go?
<br>
<br>On 12/30/14, Thiago Macieira &lt;<a href=3D"javascript:" target=3D"_bla=
nk" gdf-obfuscated-mailto=3D"geToFcT4iGAJ" onmousedown=3D"this.href=3D'java=
script:';return true;" onclick=3D"this.href=3D'javascript:';return true;">t=
hi...@macieira.org</a>&gt; wrote:
<br>&gt; On Monday 29 December 2014 20:21:31 Douglas Boffey wrote:
<br>&gt;&gt; If there's a problem with atomicity, why not a function return=
ing both
<br>&gt;&gt; counts simultaneously?
<br>&gt;
<br>&gt; Because that's still not atomic. It suffers from the exact same pr=
oblem as I
<br>&gt;
<br>&gt; described before. That still requires two load operations, which m=
eans the
<br>&gt; one
<br>&gt; value loaded before might have changed by the time it got returned=
..
<br>&gt;
<br>&gt; In other words having one function that returns a pair is no diffe=
rent than
<br>&gt; two
<br>&gt; functions returning each an individual value.
<br>&gt;
<br>&gt; --
<br>&gt; Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" tar=
get=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75ht=
tp%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7e=
uhqLn_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/=
url?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDU=
BNCNanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a h=
ref=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http:/=
/www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75A=
FQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'ht=
tp://www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg=
\75AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&gt; &nbsp; &nbsp;Software Architect - Intel Open Source Technology Cen=
ter
<br>&gt; &nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&gt; &nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005=
 6EF4 5358
<br>&gt;
<br>&gt; --
<br>&gt;
<br>&gt; ---
<br>&gt; You received this message because you are subscribed to the Google=
 Groups
<br>&gt; "ISO C++ Standard - Future Proposals" group.
<br>&gt; To unsubscribe from this group and stop receiving emails from it, =
send an
<br>&gt; email to <a href=3D"javascript:" target=3D"_blank" gdf-obfuscated-=
mailto=3D"geToFcT4iGAJ" onmousedown=3D"this.href=3D'javascript:';return tru=
e;" onclick=3D"this.href=3D'javascript:';return true;">std-proposal...@<wbr=
>isocpp.org</a>.
<br>&gt; To post to this group, send email to <a href=3D"javascript:" targe=
t=3D"_blank" gdf-obfuscated-mailto=3D"geToFcT4iGAJ" onmousedown=3D"this.hre=
f=3D'javascript:';return true;" onclick=3D"this.href=3D'javascript:';return=
 true;">std-pr...@isocpp.org</a>.
<br>&gt; Visit this group at
<br>&gt; <a href=3D"http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/" target=3D"_blank" onmousedown=3D"this.href=3D'http://groups.google.com=
/a/isocpp.org/group/std-proposals/';return true;" onclick=3D"this.href=3D'h=
ttp://groups.google.com/a/isocpp.org/group/std-proposals/';return true;">ht=
tp://groups.google.com/a/<wbr>isocpp.org/group/std-<wbr>proposals/</a>.
<br>&gt;
<br></blockquote></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_2823_363512041.1419941343143--
------=_Part_2822_1298197023.1419941343143--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 10:47:05 -0200
Raw View
On Tuesday 30 December 2014 09:35:48 Douglas Boffey wrote:
> And I suppose wrapping it in a mutex is no go?

That would imply that all the operations that change those values need to be
wrapped in a mutex. So you're introducing a performance bottleneck for every
operation just for the ability to get the count.

Is it worth it?
--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 10:48:41 -0200
Raw View
On Tuesday 30 December 2014 04:09:03 Ramkumar Revanur wrote:
> There is no need for a mutex if the implementation can be atomic.
>
> From the information presented in the thread
>
> For QSharedPointer's implementation:
>
> use_count(): atomic
> weak_count(): not atomic
> total_count(): atomic
>
> For LibstdC++ / libC++
>
> shared_ptr::use_count();  atomic
> shared_ptr::weak_count();  atomic
> shared_ptr::total_count();  not atomic
>
> Now, for making a proposal we have to choose one of the approach for
> getting the weak_count and I am OK with weak_count or total_count

Whichever way you choose, there's a good chance that you're going to find an
existing implementation of shared_ptr that is not atomic and therefore the
resulting function is, at the very least, unreliable.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 10:51:33 -0200
Raw View
On Monday 29 December 2014 21:45:04 Ramkumar Revanur wrote:
> The difficulty in a *specific* implementation. The operative word here is
> specific.
>
> > I disagree that the difficulty of implementing is not part of the
> > discussion. I
> > think it's core to the discussion. If the function cannot return a
> > reliable
> > and correct value, then it should not exist.

I'm not sure what you're getting at.

Yes, a specific implementation makes it difficult to implement it. That means
there is at least one case out there under which the function would be
labelled "dangerous", which in turn means the standard should advise that it's
dangerous in all implementations so that few (if any) people ever use the
function.

What's the point of having a function in the standard that is "dangerous, may
return incorrect results"?

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: ramkumar.revanur@gmail.com
Date: Tue, 30 Dec 2014 08:02:55 -0800 (PST)
Raw View
------=_Part_6617_306919224.1419955375247
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

So you agree it is plausible to have an atomic implementation in stl. Right=
..

I understand it is *easy* to implement weak_count in few libraries but not =
straight forward in few others. That should not be a reason to prempt a pro=
posal. Code can change and library implementation can be made coherent. We =
can patch the implementation that is incoherent to what approach we choose.=
 I can volunteer if it helps. Afterall code is expected to change.

--=20

---=20
You received this message because you are subscribed to the Google Groups "=
ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposa=
ls/.

------=_Part_6617_306919224.1419955375247--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 14:33:12 -0200
Raw View
On Tuesday 30 December 2014 08:02:55 ramkumar.revanur@gmail.com wrote:
> So you agree it is plausible to have an atomic implementation in stl. Right.

I agree it's plausible that some STL have implemented it in a way we could add
the function and it be atomic. But I am also saying that it's plausible that
there are two STL implementations that have incompatible requirements. That
means there's a very good chance that some implementations cannot do it
atomically.

> I understand it is *easy* to implement weak_count in few libraries but not
> straight forward in few others. That should not be a reason to prempt a
> proposal.

Yes, it should. It's not "uneasy" to implement a proper version in the others:
it's impossible. The value returned is unreliable in multithreaded
applications, period.

> Code can change and library implementation can be made coherent.
> We can patch the implementation that is incoherent to what approach we
> choose. I can volunteer if it helps. Afterall code is expected to change.

Only if the library breaks binary compatibility and that's a non-starter.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Tue, 30 Dec 2014 18:45:43 +0200
Raw View
On 30 December 2014 at 18:33, Thiago Macieira <thiago@macieira.org> wrote:
>> I understand it is *easy* to implement weak_count in few libraries but not
>> straight forward in few others. That should not be a reason to prempt a
>> proposal.
> Yes, it should. It's not "uneasy" to implement a proper version in the others:
> it's impossible. The value returned is unreliable in multithreaded
> applications, period.

That is, assuming that such applications don't employ external synchronization
on it, which they can choose to do.

>> Code can change and library implementation can be made coherent.
>> We can patch the implementation that is incoherent to what approach we
>> choose. I can volunteer if it helps. Afterall code is expected to change.
> Only if the library breaks binary compatibility and that's a non-starter.

A library implementation doesn't need to break binary compatibility to
make such changes. libstdc++ didn't when it made function signature changes
between c++03 and c++11.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 15:07:01 -0200
Raw View
On Tuesday 30 December 2014 18:45:43 Ville Voutilainen wrote:
> >> Code can change and library implementation can be made coherent.
> >> We can patch the implementation that is incoherent to what approach we
> >> choose. I can volunteer if it helps. Afterall code is expected to change.
> >
> > Only if the library breaks binary compatibility and that's a non-starter.
>
> A library implementation doesn't need to break binary compatibility to
> make such changes. libstdc++ didn't when it made function signature changes
> between c++03 and c++11.

I still don't know how that works. For all I know, it doesn't work.

In this case, just think of the following scenario:

- library A is built now and uses method 1 of reference-counting
- library B is built tomorrow and uses method 2 of reference-counting
- library A passes a shared_ptr object to library B, which holds a copy
- library B passes its own shared_ptr object to library A, which holds a copy

How will that work? How will library B know that it should use method 2
because the pointer came from library A? And moreover, how will library A,
which has no clue that method 2 even exists, use that method?

Remember, all of this is inlined. There are hardly any virtuals to be
overridden.

And finally, image that library B calls weak_count or total_count on all of its
pointers. How does it know which pointers are unreliable? How does the *user*
get told that the pointers are unreliable?

No, short of breaking the ABI and forcing the *whole* *world* to recompile,
this can't be done.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Tue, 30 Dec 2014 19:19:10 +0200
Raw View
On 30 December 2014 at 19:07, Thiago Macieira <thiago@macieira.org> wrote:
>> >> Code can change and library implementation can be made coherent.
>> >> We can patch the implementation that is incoherent to what approach we
>> >> choose. I can volunteer if it helps. Afterall code is expected to change.
>> > Only if the library breaks binary compatibility and that's a non-starter.
>> A library implementation doesn't need to break binary compatibility to
>> make such changes. libstdc++ didn't when it made function signature changes
>> between c++03 and c++11.
> I still don't know how that works. For all I know, it doesn't work.

For all I know, it does. I've tried it out with mixing the pre-C++11 cow
strings and C++11 non-cow strings with libstdc++.

> In this case, just think of the following scenario:
> - library A is built now and uses method 1 of reference-counting
> - library B is built tomorrow and uses method 2 of reference-counting
> - library A passes a shared_ptr object to library B, which holds a copy
> - library B passes its own shared_ptr object to library A, which holds a copy
> How will that work? How will library B know that it should use method 2
> because the pointer came from library A? And moreover, how will library A,
> which has no clue that method 2 even exists, use that method?

Library B knows which 'method' to use because the shared_ptr types are
not the same.
Library A cannot use the shared_ptr in Library B nor its 'method' because it's
not magically forward-compatible with future changes.

> And finally, image that library B calls weak_count or total_count on all of its
> pointers. How does it know which pointers are unreliable? How does the *user*
> get told that the pointers are unreliable?

Via a linker error, if the new function is attempted to be used on an
old type that
does not support it.

> No, short of breaking the ABI and forcing the *whole* *world* to recompile,
> this can't be done.

I doubt the correctness of that claim. There is practical evidence to
the contrary.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: ramkumar.revanur@gmail.com
Date: Tue, 30 Dec 2014 09:34:53 -0800 (PST)
Raw View
------=_Part_6336_955831682.1419960893549
Content-Type: multipart/alternative;
 boundary="----=_Part_6337_1485399814.1419960893550"

------=_Part_6337_1485399814.1419960893550
Content-Type: text/plain; charset=UTF-8


Some libraries take a lot of effort to make STL objects compatible. There
is no agreed rules to maintain ABI across major releases of STL library
that I know of. Please let us know what is that you follow. Some libraries
(read MS VS) take major versions as an opportunity (and rightly so) to
introduce changes that can break ABI.

For example:

*x86 Container Sizes (Bytes)**VC9 SP1*
*VC9 SP1 SCL=0**VC10**VC11*vector<int>24161612array<int, 5>20202020
deque<int>32322420forward_list<int>N/AN/A84list<int>2812128
priority_queue<int>28202016queue<int>32322420stack<int>32322420pair<int,
int>8888tuple<int, int, int>16161612map<int, int>3212168multimap<int, int>32
12168set<int>3212168multiset<int>3212168hash_map<int, int>72444432hash_multimap<int,
int>72444432hash_set<int>72444432hash_multiset<int>72444432unordered_map<int,
int>72444432unordered_multimap<int, int>72444432unordered_set<int>72444432
unordered_multiset<int>72444432string28282824wstring28282824
I am sure there are few more breaking changes in Visual Studio 2013 and
more so in Visual Studio 2015.

A nice* article
<http://www.reddit.com/r/cpp/comments/13zex3/can_vs2010_c_libsdlls_be_linked_into_a_vs2012_c/c78ott7>*comes
to my mind on rules of using STL (in MSVC?) written by Stephan T. Lavavej.




On Tuesday, 30 December 2014 22:37:08 UTC+5:30, Thiago Macieira wrote:
>
> On Tuesday 30 December 2014 18:45:43 Ville Voutilainen wrote:
> > >> Code can change and library implementation can be made coherent.
> > >> We can patch the implementation that is incoherent to what approach
> we
> > >> choose. I can volunteer if it helps. Afterall code is expected to
> change.
> > >
> > > Only if the library breaks binary compatibility and that's a
> non-starter.
> >
> > A library implementation doesn't need to break binary compatibility to
> > make such changes. libstdc++ didn't when it made function signature
> changes
> > between c++03 and c++11.
>
> I still don't know how that works. For all I know, it doesn't work.
>
> In this case, just think of the following scenario:
>
> - library A is built now and uses method 1 of reference-counting
> - library B is built tomorrow and uses method 2 of reference-counting
> - library A passes a shared_ptr object to library B, which holds a copy
> - library B passes its own shared_ptr object to library A, which holds a
> copy
>
> How will that work? How will library B know that it should use method 2
> because the pointer came from library A? And moreover, how will library A,
> which has no clue that method 2 even exists, use that method?
>
> Remember, all of this is inlined. There are hardly any virtuals to be
> overridden.
>
> And finally, image that library B calls weak_count or total_count on all
> of its
> pointers. How does it know which pointers are unreliable? How does the
> *user*
> get told that the pointers are unreliable?
>
> No, short of breaking the ABI and forcing the *whole* *world* to
> recompile,
> this can't be done.
>
> --
> Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
>    Software Architect - Intel Open Source Technology Center
>       PGP/GPG: 0x6EF45358; fingerprint:
>       E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358
>
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_6337_1485399814.1419960893550
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div><br></div>Some libraries take a lot of effort to make=
 STL objects compatible. There is no agreed rules to maintain ABI across ma=
jor releases of STL library that I know of. Please let us know what is that=
 you follow. Some libraries (read MS VS) take major versions as an opportun=
ity (and rightly so) to introduce changes that can break ABI.<div><div><br>=
</div><div>For example:</div><div><br></div><div><table border=3D"0" cellsp=
acing=3D"0" cellpadding=3D"0" style=3D"max-width: 100%; color: rgb(66, 66, =
66); font-family: 'Segoe UI', 'Lucida Grande', Verdana, Arial, Helvetica, s=
ans-serif; line-height: 19.5px; width: 545px; list-style-type: disc; border=
-collapse: collapse;"><tbody><tr height=3D"32" style=3D"height: 24pt;"><td =
width=3D"282" height=3D"32" align=3D"center" class=3D"xl67" style=3D"border=
-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; =
border-style: solid none solid solid; border-left-color: rgb(196, 215, 155)=
; padding-left: 1px; padding-right: 1px; vertical-align: middle; border-top=
-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(155, 187, 89)=
;"><span color=3D"#ffffff" style=3D"color: rgb(255, 255, 255); font-size: 9=
pt;"><strong>x86 Container Sizes (Bytes)</strong></span></td><td width=3D"7=
0" align=3D"center" class=3D"xl67" style=3D"border-bottom-color: rgb(196, 2=
15, 155); border-width: 0.5pt medium; border-style: solid none; padding-lef=
t: 1px; padding-right: 1px; vertical-align: middle; border-top-color: rgb(1=
96, 215, 155); padding-top: 1px; background: rgb(155, 187, 89);"><span colo=
r=3D"#ffffff" style=3D"color: rgb(255, 255, 255); font-size: 9pt;"><strong>=
VC9 SP1</strong></span></td><td width=3D"64" align=3D"center" class=3D"xl68=
" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt med=
ium; border-style: solid none; padding-left: 1px; padding-right: 1px; verti=
cal-align: middle; border-top-color: rgb(196, 215, 155); padding-top: 1px; =
background: rgb(155, 187, 89);"><span color=3D"#ffffff" style=3D"color: rgb=
(255, 255, 255); font-size: 9pt;"><strong>VC9 SP1&nbsp;<br>SCL=3D0</strong>=
</span></td><td width=3D"64" align=3D"center" class=3D"xl67" style=3D"borde=
r-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-styl=
e: solid none; padding-left: 1px; padding-right: 1px; vertical-align: middl=
e; border-top-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(=
155, 187, 89);"><span color=3D"#ffffff" style=3D"color: rgb(255, 255, 255);=
 font-size: 9pt;"><strong>VC10</strong></span></td><td width=3D"64" align=
=3D"center" class=3D"xl67" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid n=
one; padding-left: 1px; padding-right: 1px; vertical-align: middle; border-=
top-color: rgb(196, 215, 155); border-right-color: rgb(196, 215, 155); padd=
ing-top: 1px; background: rgb(155, 187, 89);"><span color=3D"#ffffff" style=
=3D"color: rgb(255, 255, 255); font-size: 9pt;"><strong>VC11</strong></span=
></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" alig=
n=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid so=
lid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding-righ=
t: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); paddi=
ng-top: 1px; background: rgb(235, 241, 222);"><span face=3D"Courier New" st=
yle=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"color:=
 rgb(0, 0, 0); font-size: 11pt;">vector&lt;int&gt;</span></span></td><td al=
ign=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 1=
55); border-width: 0.5pt medium; border-style: solid none; padding-left: 1p=
x; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 2=
15, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D=
"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">24</span></td><td =
align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215,=
 155); border-width: 0.5pt medium; border-style: solid none; padding-left: =
1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196,=
 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=
=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">16</span></td><=
td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 2=
15, 155); border-width: 0.5pt medium; border-style: solid none; padding-lef=
t: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(1=
96, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span col=
or=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">16</span></td=
><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196,=
 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid sol=
id solid none; padding-left: 1px; padding-right: 1px; vertical-align: botto=
m; border-top-color: rgb(196, 215, 155); border-right-color: rgb(196, 215, =
155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#00=
0000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">12</span></td></tr><tr=
 height=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" cl=
ass=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid solid; border-le=
ft-color: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px; vertic=
al-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;">=
<span face=3D"Courier New" style=3D"font-family: 'Courier New';"><span colo=
r=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">array&lt;int,=
 5&gt;</span></span></td><td align=3D"center" class=3D"xl65" style=3D"borde=
r-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-styl=
e: solid none; padding-left: 1px; padding-right: 1px; vertical-align: botto=
m; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"=
#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">20</span></td><td a=
lign=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, =
155); border-width: 0.5pt medium; border-style: solid none; padding-left: 1=
px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, =
215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0=
, 0, 0); font-size: 9pt;">20</span></td><td align=3D"center" class=3D"xl65"=
 style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medi=
um; border-style: solid none; padding-left: 1px; padding-right: 1px; vertic=
al-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;">=
<span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">20</=
span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color:=
 rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: =
solid solid solid none; padding-left: 1px; padding-right: 1px; vertical-ali=
gn: bottom; border-top-color: rgb(196, 215, 155); border-right-color: rgb(1=
96, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: r=
gb(0, 0, 0); font-size: 9pt;">20</span></td></tr><tr height=3D"20" style=3D=
"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"b=
order-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.=
5pt; border-style: solid none solid solid; border-left-color: rgb(196, 215,=
 155); padding-left: 1px; padding-right: 1px; vertical-align: bottom; borde=
r-top-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241=
, 222);"><span face=3D"Courier New" style=3D"font-family: 'Courier New';"><=
span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">dequ=
e&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65" style=3D=
"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; borde=
r-style: solid none; padding-left: 1px; padding-right: 1px; vertical-align:=
 bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; background=
: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0)=
; font-size: 9pt;">32</span></td><td align=3D"center" class=3D"xl65" style=
=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; bo=
rder-style: solid none; padding-left: 1px; padding-right: 1px; vertical-ali=
gn: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backgro=
und: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0,=
 0); font-size: 9pt;">32</span></td><td align=3D"center" class=3D"xl65" sty=
le=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; =
border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-a=
lign: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backg=
round: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, =
0, 0); font-size: 9pt;">24</span></td><td align=3D"center" class=3D"xl65" s=
tyle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt =
0.5pt medium; border-style: solid solid solid none; padding-left: 1px; padd=
ing-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155=
); border-right-color: rgb(196, 215, 155); padding-top: 1px; background: rg=
b(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); fo=
nt-size: 9pt;">20</span></td></tr><tr height=3D"20" style=3D"height: 15pt;"=
><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"border-bottom-co=
lor: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-sty=
le: solid none solid solid; border-left-color: rgb(196, 215, 155); padding-=
left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rg=
b(196, 215, 155); padding-top: 1px;"><span face=3D"Courier New" style=3D"fo=
nt-family: 'Courier New';"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 11pt;">forward_list&lt;int&gt;</span></span></td><td align=
=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt medium; border-style: solid none; padding-left: 1px; =
padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215,=
 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0,=
 0); font-size: 9pt;">N/A</span></td><td align=3D"center" class=3D"xl65" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium;=
 border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-=
align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><sp=
an color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">N/A</sp=
an></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: r=
gb(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; pa=
dding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-col=
or: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D=
"color: rgb(0, 0, 0); font-size: 9pt;">8</span></td><td align=3D"center" cl=
ass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid none; padding-l=
eft: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb=
(196, 215, 155); border-right-color: rgb(196, 215, 155); padding-top: 1px;"=
><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">4</=
span></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" =
align=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, =
155); border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none soli=
d solid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding-=
right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); p=
adding-top: 1px; background: rgb(235, 241, 222);"><span face=3D"Courier New=
" style=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"co=
lor: rgb(0, 0, 0); font-size: 11pt;">list&lt;int&gt;</span></span></td><td =
align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215,=
 155); border-width: 0.5pt medium; border-style: solid none; padding-left: =
1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196,=
 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=
=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">28</span></td><=
td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 2=
15, 155); border-width: 0.5pt medium; border-style: solid none; padding-lef=
t: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(1=
96, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span col=
or=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">12</span></td=
><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196,=
 215, 155); border-width: 0.5pt medium; border-style: solid none; padding-l=
eft: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb=
(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span c=
olor=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">12</span></=
td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(19=
6, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid s=
olid solid none; padding-left: 1px; padding-right: 1px; vertical-align: bot=
tom; border-top-color: rgb(196, 215, 155); border-right-color: rgb(196, 215=
, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#=
000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span></td></tr><t=
r height=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" c=
lass=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155); border-widt=
h: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid solid; border-l=
eft-color: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px; verti=
cal-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"=
><span face=3D"Courier New" style=3D"font-family: 'Courier New';"><span col=
or=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">priority_que=
ue&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65" style=
=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; bo=
rder-style: solid none; padding-left: 1px; padding-right: 1px; vertical-ali=
gn: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span =
color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">28</span><=
/td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(1=
96, 215, 155); border-width: 0.5pt medium; border-style: solid none; paddin=
g-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: =
rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"col=
or: rgb(0, 0, 0); font-size: 9pt;">20</span></td><td align=3D"center" class=
=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0=
..5pt medium; border-style: solid none; padding-left: 1px; padding-right: 1p=
x; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-to=
p: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9=
pt;">20</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bott=
om-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; borde=
r-style: solid solid solid none; padding-left: 1px; padding-right: 1px; ver=
tical-align: bottom; border-top-color: rgb(196, 215, 155); border-right-col=
or: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D=
"color: rgb(0, 0, 0); font-size: 9pt;">16</span></td></tr><tr height=3D"20"=
 style=3D"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" s=
tyle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium=
 0.5pt 0.5pt; border-style: solid none solid solid; border-left-color: rgb(=
196, 215, 155); padding-left: 1px; padding-right: 1px; vertical-align: bott=
om; border-top-color: rgb(196, 215, 155); padding-top: 1px; background: rgb=
(235, 241, 222);"><span face=3D"Courier New" style=3D"font-family: 'Courier=
 New';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11=
pt;">queue&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65"=
 style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medi=
um; border-style: solid none; padding-left: 1px; padding-right: 1px; vertic=
al-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; b=
ackground: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb=
(0, 0, 0); font-size: 9pt;">32</span></td><td align=3D"center" class=3D"xl6=
5" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt me=
dium; border-style: solid none; padding-left: 1px; padding-right: 1px; vert=
ical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;=
 background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: r=
gb(0, 0, 0); font-size: 9pt;">32</span></td><td align=3D"center" class=3D"x=
l65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt =
medium; border-style: solid none; padding-left: 1px; padding-right: 1px; ve=
rtical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1p=
x; background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color:=
 rgb(0, 0, 0); font-size: 9pt;">24</span></td><td align=3D"center" class=3D=
"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5p=
t 0.5pt 0.5pt medium; border-style: solid solid solid none; padding-left: 1=
px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, =
215, 155); border-right-color: rgb(196, 215, 155); padding-top: 1px; backgr=
ound: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 9pt;">20</span></td></tr><tr height=3D"20" style=3D"height=
: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"border-b=
ottom-color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; bo=
rder-style: solid none solid solid; border-left-color: rgb(196, 215, 155); =
padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-c=
olor: rgb(196, 215, 155); padding-top: 1px;"><span face=3D"Courier New" sty=
le=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"color: =
rgb(0, 0, 0); font-size: 11pt;">stack&lt;int&gt;</span></span></td><td alig=
n=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155=
); border-width: 0.5pt medium; border-style: solid none; padding-left: 1px;=
 padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215=
, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 9pt;">32</span></td><td align=3D"center" class=3D"xl65" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium;=
 border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-=
align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><sp=
an color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</spa=
n></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rg=
b(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; pad=
ding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-colo=
r: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"=
color: rgb(0, 0, 0); font-size: 9pt;">24</span></td><td align=3D"center" cl=
ass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid none; padding-l=
eft: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb=
(196, 215, 155); border-right-color: rgb(196, 215, 155); padding-top: 1px;"=
><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">20<=
/span></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20"=
 align=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215,=
 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none sol=
id solid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding=
-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); =
padding-top: 1px; background: rgb(235, 241, 222);"><span face=3D"Courier Ne=
w" style=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"c=
olor: rgb(0, 0, 0); font-size: 11pt;">pair&lt;int, int&gt;</span></span></t=
d><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196=
, 215, 155); border-width: 0.5pt medium; border-style: solid none; padding-=
left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rg=
b(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span =
color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span></=
td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(19=
6, 215, 155); border-width: 0.5pt medium; border-style: solid none; padding=
-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: r=
gb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span=
 color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span><=
/td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(1=
96, 215, 155); border-width: 0.5pt medium; border-style: solid none; paddin=
g-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: =
rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><spa=
n color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span>=
</td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(=
196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid=
 solid solid none; padding-left: 1px; padding-right: 1px; vertical-align: b=
ottom; border-top-color: rgb(196, 215, 155); border-right-color: rgb(196, 2=
15, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D=
"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span></td></tr>=
<tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right"=
 class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155); border-wi=
dth: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid solid; border=
-left-color: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px; ver=
tical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px=
;"><span face=3D"Courier New" style=3D"font-family: 'Courier New';"><span c=
olor=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">tuple&lt;i=
nt, int, int&gt;</span></span></td><td align=3D"center" class=3D"xl65" styl=
e=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; b=
order-style: solid none; padding-left: 1px; padding-right: 1px; vertical-al=
ign: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span=
 color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">16</span>=
</td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(=
196, 215, 155); border-width: 0.5pt medium; border-style: solid none; paddi=
ng-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color:=
 rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"co=
lor: rgb(0, 0, 0); font-size: 9pt;">16</span></td><td align=3D"center" clas=
s=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: =
0.5pt medium; border-style: solid none; padding-left: 1px; padding-right: 1=
px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-t=
op: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: =
9pt;">16</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bot=
tom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; bord=
er-style: solid solid solid none; padding-left: 1px; padding-right: 1px; ve=
rtical-align: bottom; border-top-color: rgb(196, 215, 155); border-right-co=
lor: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=
=3D"color: rgb(0, 0, 0); font-size: 9pt;">12</span></td></tr><tr height=3D"=
20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66=
" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt med=
ium 0.5pt 0.5pt; border-style: solid none solid solid; border-left-color: r=
gb(196, 215, 155); padding-left: 1px; padding-right: 1px; vertical-align: b=
ottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; background: =
rgb(235, 241, 222);"><span face=3D"Courier New" style=3D"font-family: 'Cour=
ier New';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size:=
 11pt;">map&lt;int, int&gt;</span></span></td><td align=3D"center" class=3D=
"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5p=
t medium; border-style: solid none; padding-left: 1px; padding-right: 1px; =
vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: =
1px; background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"colo=
r: rgb(0, 0, 0); font-size: 9pt;">32</span></td><td align=3D"center" class=
=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0=
..5pt medium; border-style: solid none; padding-left: 1px; padding-right: 1p=
x; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-to=
p: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"c=
olor: rgb(0, 0, 0); font-size: 9pt;">12</span></td><td align=3D"center" cla=
ss=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width:=
 0.5pt medium; border-style: solid none; padding-left: 1px; padding-right: =
1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-=
top: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D=
"color: rgb(0, 0, 0); font-size: 9pt;">16</span></td><td align=3D"center" c=
lass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-widt=
h: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid none; padding-=
left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rg=
b(196, 215, 155); border-right-color: rgb(196, 215, 155); padding-top: 1px;=
 background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: r=
gb(0, 0, 0); font-size: 9pt;">8</span></td></tr><tr height=3D"20" style=3D"=
height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"bo=
rder-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5=
pt; border-style: solid none solid solid; border-left-color: rgb(196, 215, =
155); padding-left: 1px; padding-right: 1px; vertical-align: bottom; border=
-top-color: rgb(196, 215, 155); padding-top: 1px;"><span face=3D"Courier Ne=
w" style=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"c=
olor: rgb(0, 0, 0); font-size: 11pt;">multimap&lt;int, int&gt;</span></span=
></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb=
(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; padd=
ing-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color=
: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"c=
olor: rgb(0, 0, 0); font-size: 9pt;">32</span></td><td align=3D"center" cla=
ss=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width:=
 0.5pt medium; border-style: solid none; padding-left: 1px; padding-right: =
1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-=
top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size:=
 9pt;">12</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bo=
ttom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: s=
olid none; padding-left: 1px; padding-right: 1px; vertical-align: bottom; b=
order-top-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000=
000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">16</span></td><td align=
=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid n=
one; padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-=
top-color: rgb(196, 215, 155); border-right-color: rgb(196, 215, 155); padd=
ing-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-s=
ize: 9pt;">8</span></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td =
height=3D"20" align=3D"right" class=3D"xl66" style=3D"border-bottom-color: =
rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-style: s=
olid none solid solid; border-left-color: rgb(196, 215, 155); padding-left:=
 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196=
, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span face=
=3D"Courier New" style=3D"font-family: 'Courier New';"><span color=3D"#0000=
00" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">set&lt;int&gt;</span></=
span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color:=
 rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; =
padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-c=
olor: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);=
"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32=
</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-colo=
r: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid none=
; padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top=
-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222=
);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">=
12</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-co=
lor: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid no=
ne; padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-t=
op-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 2=
22);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;=
">16</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-=
color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-s=
tyle: solid solid solid none; padding-left: 1px; padding-right: 1px; vertic=
al-align: bottom; border-top-color: rgb(196, 215, 155); border-right-color:=
 rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><sp=
an color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span=
></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" alig=
n=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid so=
lid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding-righ=
t: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); paddi=
ng-top: 1px;"><span face=3D"Courier New" style=3D"font-family: 'Courier New=
';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;"=
>multiset&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65" =
style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt mediu=
m; border-style: solid none; padding-left: 1px; padding-right: 1px; vertica=
l-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><=
span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</s=
pan></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: =
rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; p=
adding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-co=
lor: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=
=3D"color: rgb(0, 0, 0); font-size: 9pt;">12</span></td><td align=3D"center=
" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-w=
idth: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-ri=
ght: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); pad=
ding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-=
size: 9pt;">16</span></td><td align=3D"center" class=3D"xl65" style=3D"bord=
er-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium=
; border-style: solid solid solid none; padding-left: 1px; padding-right: 1=
px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); border-ri=
ght-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" s=
tyle=3D"color: rgb(0, 0, 0); font-size: 9pt;">8</span></td></tr><tr height=
=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"=
xl66" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt=
 medium 0.5pt 0.5pt; border-style: solid none solid solid; border-left-colo=
r: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px; vertical-alig=
n: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backgrou=
nd: rgb(235, 241, 222);"><span face=3D"Courier New" style=3D"font-family: '=
Courier New';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-s=
ize: 11pt;">hash_map&lt;int, int&gt;</span></span></td><td align=3D"center"=
 class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-wi=
dth: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-rig=
ht: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padd=
ing-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" styl=
e=3D"color: rgb(0, 0, 0); font-size: 9pt;">72</span></td><td align=3D"cente=
r" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-=
width: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-r=
ight: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); pa=
dding-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" st=
yle=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span></td><td align=3D"cen=
ter" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); borde=
r-width: 0.5pt medium; border-style: solid none; padding-left: 1px; padding=
-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); =
padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" =
style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span></td><td align=3D"c=
enter" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); bor=
der-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid none; =
padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-c=
olor: rgb(196, 215, 155); border-right-color: rgb(196, 215, 155); padding-t=
op: 1px; background: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"=
color: rgb(0, 0, 0); font-size: 9pt;">32</span></td></tr><tr height=3D"20" =
style=3D"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium =
0.5pt 0.5pt; border-style: solid none solid solid; border-left-color: rgb(1=
96, 215, 155); padding-left: 1px; padding-right: 1px; vertical-align: botto=
m; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span face=3D"C=
ourier New" style=3D"font-family: 'Courier New';"><span color=3D"#000000" s=
tyle=3D"color: rgb(0, 0, 0); font-size: 11pt;">hash_multimap&lt;int, int&gt=
;</span></span></td><td align=3D"center" class=3D"xl65" style=3D"border-bot=
tom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: so=
lid none; padding-left: 1px; padding-right: 1px; vertical-align: bottom; bo=
rder-top-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#0000=
00" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">72</span></td><td align=
=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155)=
; border-width: 0.5pt medium; border-style: solid none; padding-left: 1px; =
padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215,=
 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0,=
 0); font-size: 9pt;">44</span></td><td align=3D"center" class=3D"xl65" sty=
le=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; =
border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-a=
lign: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><spa=
n color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span=
></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb=
(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: soli=
d solid solid none; padding-left: 1px; padding-right: 1px; vertical-align: =
bottom; border-top-color: rgb(196, 215, 155); border-right-color: rgb(196, =
215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0=
, 0, 0); font-size: 9pt;">32</span></td></tr><tr height=3D"20" style=3D"hei=
ght: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"borde=
r-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt;=
 border-style: solid none solid solid; border-left-color: rgb(196, 215, 155=
); padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-to=
p-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 22=
2);"><span face=3D"Courier New" style=3D"font-family: 'Courier New';"><span=
 color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">hash_set=
&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65" style=3D"=
border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border=
-style: solid none; padding-left: 1px; padding-right: 1px; vertical-align: =
bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; background:=
 rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0);=
 font-size: 9pt;">72</span></td><td align=3D"center" class=3D"xl65" style=
=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; bo=
rder-style: solid none; padding-left: 1px; padding-right: 1px; vertical-ali=
gn: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backgro=
und: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0,=
 0); font-size: 9pt;">44</span></td><td align=3D"center" class=3D"xl65" sty=
le=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; =
border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-a=
lign: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backg=
round: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, =
0, 0); font-size: 9pt;">44</span></td><td align=3D"center" class=3D"xl65" s=
tyle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt =
0.5pt medium; border-style: solid solid solid none; padding-left: 1px; padd=
ing-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155=
); border-right-color: rgb(196, 215, 155); padding-top: 1px; background: rg=
b(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); fo=
nt-size: 9pt;">32</span></td></tr><tr height=3D"20" style=3D"height: 15pt;"=
><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"border-bottom-co=
lor: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-sty=
le: solid none solid solid; border-left-color: rgb(196, 215, 155); padding-=
left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rg=
b(196, 215, 155); padding-top: 1px;"><span face=3D"Courier New" style=3D"fo=
nt-family: 'Courier New';"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 11pt;">hash_multiset&lt;int&gt;</span></span></td><td alig=
n=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155=
); border-width: 0.5pt medium; border-style: solid none; padding-left: 1px;=
 padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215=
, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 9pt;">72</span></td><td align=3D"center" class=3D"xl65" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium;=
 border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-=
align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><sp=
an color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</spa=
n></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rg=
b(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; pad=
ding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-colo=
r: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"=
color: rgb(0, 0, 0); font-size: 9pt;">44</span></td><td align=3D"center" cl=
ass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt 0.5pt 0.5pt medium; border-style: solid solid solid none; padding-l=
eft: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb=
(196, 215, 155); border-right-color: rgb(196, 215, 155); padding-top: 1px;"=
><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32<=
/span></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20"=
 align=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215,=
 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none sol=
id solid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding=
-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); =
padding-top: 1px; background: rgb(235, 241, 222);"><span face=3D"Courier Ne=
w" style=3D"font-family: 'Courier New';"><span color=3D"#000000" style=3D"c=
olor: rgb(0, 0, 0); font-size: 11pt;">unordered_map&lt;int, int&gt;</span><=
/span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color=
: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid none;=
 padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-=
color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222)=
;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">7=
2</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-col=
or: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid non=
e; padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-to=
p-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 22=
2);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;"=
>44</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-c=
olor: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: solid n=
one; padding-left: 1px; padding-right: 1px; vertical-align: bottom; border-=
top-color: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, =
222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt=
;">44</span></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom=
-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-=
style: solid solid solid none; padding-left: 1px; padding-right: 1px; verti=
cal-align: bottom; border-top-color: rgb(196, 215, 155); border-right-color=
: rgb(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><s=
pan color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</sp=
an></td></tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" al=
ign=3D"right" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 15=
5); border-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid =
solid; border-left-color: rgb(196, 215, 155); padding-left: 1px; padding-ri=
ght: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); pad=
ding-top: 1px;"><span face=3D"Courier New" style=3D"font-family: 'Courier N=
ew';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt=
;">unordered_multimap&lt;int, int&gt;</span></span></td><td align=3D"center=
" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-w=
idth: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-ri=
ght: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); pad=
ding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-=
size: 9pt;">72</span></td><td align=3D"center" class=3D"xl65" style=3D"bord=
er-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-sty=
le: solid none; padding-left: 1px; padding-right: 1px; vertical-align: bott=
om; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D=
"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span></td><td =
align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215,=
 155); border-width: 0.5pt medium; border-style: solid none; padding-left: =
1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196,=
 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(=
0, 0, 0); font-size: 9pt;">44</span></td><td align=3D"center" class=3D"xl65=
" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5=
pt 0.5pt medium; border-style: solid solid solid none; padding-left: 1px; p=
adding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, =
155); border-right-color: rgb(196, 215, 155); padding-top: 1px;"><span colo=
r=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</span></td>=
</tr><tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"r=
ight" class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155); bord=
er-width: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid solid; b=
order-left-color: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px=
; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top=
: 1px; background: rgb(235, 241, 222);"><span face=3D"Courier New" style=3D=
"font-family: 'Courier New';"><span color=3D"#000000" style=3D"color: rgb(0=
, 0, 0); font-size: 11pt;">unordered_set&lt;int&gt;</span></span></td><td a=
lign=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, =
155); border-width: 0.5pt medium; border-style: solid none; padding-left: 1=
px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, =
215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=
=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">72</span></td><=
td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 2=
15, 155); border-width: 0.5pt medium; border-style: solid none; padding-lef=
t: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb(1=
96, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span col=
or=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span></td=
><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196,=
 215, 155); border-width: 0.5pt medium; border-style: solid none; padding-l=
eft: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: rgb=
(196, 215, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span c=
olor=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">44</span></=
td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(19=
6, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; border-style: solid s=
olid solid none; padding-left: 1px; padding-right: 1px; vertical-align: bot=
tom; border-top-color: rgb(196, 215, 155); border-right-color: rgb(196, 215=
, 155); padding-top: 1px; background: rgb(235, 241, 222);"><span color=3D"#=
000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</span></td></tr><=
tr height=3D"20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" =
class=3D"xl66" style=3D"border-bottom-color: rgb(196, 215, 155); border-wid=
th: 0.5pt medium 0.5pt 0.5pt; border-style: solid none solid solid; border-=
left-color: rgb(196, 215, 155); padding-left: 1px; padding-right: 1px; vert=
ical-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;=
"><span face=3D"Courier New" style=3D"font-family: 'Courier New';"><span co=
lor=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 11pt;">unordered_m=
ultiset&lt;int&gt;</span></span></td><td align=3D"center" class=3D"xl65" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium;=
 border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-=
align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px;"><sp=
an color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">72</spa=
n></td><td align=3D"center" class=3D"xl65" style=3D"border-bottom-color: rg=
b(196, 215, 155); border-width: 0.5pt medium; border-style: solid none; pad=
ding-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-colo=
r: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"=
color: rgb(0, 0, 0); font-size: 9pt;">44</span></td><td align=3D"center" cl=
ass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-right:=
 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding=
-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size=
: 9pt;">44</span></td><td align=3D"center" class=3D"xl65" style=3D"border-b=
ottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0.5pt medium; bo=
rder-style: solid solid solid none; padding-left: 1px; padding-right: 1px; =
vertical-align: bottom; border-top-color: rgb(196, 215, 155); border-right-=
color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#000000" style=
=3D"color: rgb(0, 0, 0); font-size: 9pt;">32</span></td></tr><tr height=3D"=
20" style=3D"height: 15pt;"><td height=3D"20" align=3D"right" class=3D"xl66=
" style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt med=
ium 0.5pt 0.5pt; border-style: solid none solid solid; border-left-color: r=
gb(196, 215, 155); padding-left: 1px; padding-right: 1px; vertical-align: b=
ottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; background: =
rgb(235, 241, 222);"><span face=3D"Courier New" style=3D"font-family: 'Cour=
ier New';"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size:=
 11pt;">string</span></span></td><td align=3D"center" class=3D"xl65" style=
=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; bo=
rder-style: solid none; padding-left: 1px; padding-right: 1px; vertical-ali=
gn: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backgro=
und: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0,=
 0); font-size: 9pt;">28</span></td><td align=3D"center" class=3D"xl65" sty=
le=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; =
border-style: solid none; padding-left: 1px; padding-right: 1px; vertical-a=
lign: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; backg=
round: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, =
0, 0); font-size: 9pt;">28</span></td><td align=3D"center" class=3D"xl65" s=
tyle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt medium=
; border-style: solid none; padding-left: 1px; padding-right: 1px; vertical=
-align: bottom; border-top-color: rgb(196, 215, 155); padding-top: 1px; bac=
kground: rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0=
, 0, 0); font-size: 9pt;">28</span></td><td align=3D"center" class=3D"xl65"=
 style=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5p=
t 0.5pt medium; border-style: solid solid solid none; padding-left: 1px; pa=
dding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 1=
55); border-right-color: rgb(196, 215, 155); padding-top: 1px; background: =
rgb(235, 241, 222);"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); =
font-size: 9pt;">24</span></td></tr><tr height=3D"20" style=3D"height: 15pt=
;"><td height=3D"20" align=3D"right" class=3D"xl66" style=3D"border-bottom-=
color: rgb(196, 215, 155); border-width: 0.5pt medium 0.5pt 0.5pt; border-s=
tyle: solid none solid solid; border-left-color: rgb(196, 215, 155); paddin=
g-left: 1px; padding-right: 1px; vertical-align: bottom; border-top-color: =
rgb(196, 215, 155); padding-top: 1px;"><span face=3D"Courier New" style=3D"=
font-family: 'Courier New';"><span color=3D"#000000" style=3D"color: rgb(0,=
 0, 0); font-size: 11pt;">wstring</span></span></td><td align=3D"center" cl=
ass=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155); border-width=
: 0.5pt medium; border-style: solid none; padding-left: 1px; padding-right:=
 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155); padding=
-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0, 0); font-size=
: 9pt;">28</span></td><td align=3D"center" class=3D"xl65" style=3D"border-b=
ottom-color: rgb(196, 215, 155); border-width: 0.5pt medium; border-style: =
solid none; padding-left: 1px; padding-right: 1px; vertical-align: bottom; =
border-top-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D"#00=
0000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">28</span></td><td alig=
n=3D"center" class=3D"xl65" style=3D"border-bottom-color: rgb(196, 215, 155=
); border-width: 0.5pt medium; border-style: solid none; padding-left: 1px;=
 padding-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215=
, 155); padding-top: 1px;"><span color=3D"#000000" style=3D"color: rgb(0, 0=
, 0); font-size: 9pt;">28</span></td><td align=3D"center" class=3D"xl65" st=
yle=3D"border-bottom-color: rgb(196, 215, 155); border-width: 0.5pt 0.5pt 0=
..5pt medium; border-style: solid solid solid none; padding-left: 1px; paddi=
ng-right: 1px; vertical-align: bottom; border-top-color: rgb(196, 215, 155)=
; border-right-color: rgb(196, 215, 155); padding-top: 1px;"><span color=3D=
"#000000" style=3D"color: rgb(0, 0, 0); font-size: 9pt;">24</span></td></tr=
></tbody></table><br>I am sure there are few more breaking changes in Visua=
l Studio 2013 and more so in Visual Studio 2015.<br><br>A nice<u> <a href=
=3D"http://www.reddit.com/r/cpp/comments/13zex3/can_vs2010_c_libsdlls_be_li=
nked_into_a_vs2012_c/c78ott7"><b>article</b> </a></u>comes to my mind on ru=
les of using STL (in MSVC?) written by&nbsp;<span style=3D"color: rgb(0, 0,=
 0); font-family: Arial, 'Liberation Sans', 'DejaVu Sans', sans-serif; font=
-size: 14px; line-height: 17.8048000335693px;">Stephan T. Lavavej.</span></=
div><div><br></div><div><br></div><div><br><br>On Tuesday, 30 December 2014=
 22:37:08 UTC+5:30, Thiago Macieira  wrote:<blockquote class=3D"gmail_quote=
" style=3D"margin: 0;margin-left: 0.8ex;border-left: 1px #ccc solid;padding=
-left: 1ex;">On Tuesday 30 December 2014 18:45:43 Ville Voutilainen wrote:
<br>&gt; &gt;&gt; Code can change and library implementation can be made co=
herent.
<br>&gt; &gt;&gt; We can patch the implementation that is incoherent to wha=
t approach we
<br>&gt; &gt;&gt; choose. I can volunteer if it helps. Afterall code is exp=
ected to change.
<br>&gt; &gt;=20
<br>&gt; &gt; Only if the library breaks binary compatibility and that's a =
non-starter.
<br>&gt;=20
<br>&gt; A library implementation doesn't need to break binary compatibilit=
y to
<br>&gt; make such changes. libstdc++ didn't when it made function signatur=
e changes
<br>&gt; between c++03 and c++11.
<br>
<br>I still don't know how that works. For all I know, it doesn't work.
<br>
<br>In this case, just think of the following scenario:
<br>
<br>- library A is built now and uses method 1 of reference-counting
<br>- library B is built tomorrow and uses method 2 of reference-counting
<br>- library A passes a shared_ptr object to library B, which holds a copy
<br>- library B passes its own shared_ptr object to library A, which holds =
a copy
<br>
<br>How will that work? How will library B know that it should use method 2=
=20
<br>because the pointer came from library A? And moreover, how will library=
 A,=20
<br>which has no clue that method 2 even exists, use that method?
<br>
<br>Remember, all of this is inlined. There are hardly any virtuals to be=
=20
<br>overridden.
<br>
<br>And finally, image that library B calls weak_count or total_count on al=
l of its=20
<br>pointers. How does it know which pointers are unreliable? How does the =
*user*=20
<br>get told that the pointers are unreliable?
<br>
<br>No, short of breaking the ABI and forcing the *whole* *world* to recomp=
ile,=20
<br>this can't be done.
<br>
<br>--=20
<br>Thiago Macieira - thiago (AT) <a href=3D"http://macieira.info" target=
=3D"_blank" onmousedown=3D"this.href=3D'http://www.google.com/url?q\75http%=
3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNCNanbu7euhq=
Ln_62FW8ag';return true;" onclick=3D"this.href=3D'http://www.google.com/url=
?q\75http%3A%2F%2Fmacieira.info\46sa\75D\46sntz\0751\46usg\75AFQjCNEswDUBNC=
Nanbu7euhqLn_62FW8ag';return true;">macieira.info</a> - thiago (AT) <a href=
=3D"http://kde.org" target=3D"_blank" onmousedown=3D"this.href=3D'http://ww=
w.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75AFQj=
CNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;" onclick=3D"this.href=3D'http:=
//www.google.com/url?q\75http%3A%2F%2Fkde.org\46sa\75D\46sntz\0751\46usg\75=
AFQjCNHGRJdo5_JYG1DowztwAHAKs80XSA';return true;">kde.org</a>
<br>&nbsp; &nbsp;Software Architect - Intel Open Source Technology Center
<br>&nbsp; &nbsp; &nbsp; PGP/GPG: 0x6EF45358; fingerprint:
<br>&nbsp; &nbsp; &nbsp; E067 918B B660 DBD1 105C &nbsp;966C 33F5 F005 6EF4=
 5358
<br>
<br></blockquote></div></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_6337_1485399814.1419960893550--
------=_Part_6336_955831682.1419960893549--

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 16:15:13 -0200
Raw View
On Tuesday 30 December 2014 19:19:10 Ville Voutilainen wrote:
> > In this case, just think of the following scenario:
> > - library A is built now and uses method 1 of reference-counting
> > - library B is built tomorrow and uses method 2 of reference-counting
> > - library A passes a shared_ptr object to library B, which holds a copy
> > - library B passes its own shared_ptr object to library A, which holds a
> > copy How will that work? How will library B know that it should use
> > method 2 because the pointer came from library A? And moreover, how will
> > library A, which has no clue that method 2 even exists, use that method?
>
> Library B knows which 'method' to use because the shared_ptr types are
> not the same.

The types being different is a binary-incompatibility change of itself.
Moreover, keeping the name the same by way of an inline namespace introduces
linker or runtime errors instead of a source-incompatible error.

> Library A cannot use the shared_ptr in Library B nor its 'method' because
> it's not magically forward-compatible with future changes.

Exactly.

So imagine:

$ cat libA.h
#include <shared_ptr>

void method_in_lib_A(const std::shared_ptr<int> &);

Now imagine that lib B calls that method. Previously, it really was
"std::shared_ptr<int>". Now, after the standard-required changes, the Standard
Library implementation decides to use an inline namespace, so the type becomes
"std::__cxx17::shared_ptr<int>". Since the header didn't specify (and can't
specify!) the base version, this implies that the new build sees as the new
type.

As libA wasn't recompiled, this can result in a linker error (unresolved
symbol: method_in_lib_A(const std::shared_ptr<int> &)). Or, worse, a runtime
error, since we're talking about building another library and the default ELF
behaviour is to not resolve at link-time.

If we're talking about system libraries, libB getting updated implies updating
libA too, which implies updating everything that uses libA. As a cascade
effect, since now everything uses the new std::shared_ptr, now everything has
to be updated too.

> > No, short of breaking the ABI and forcing the *whole* *world* to
> > recompile,
> > this can't be done.
>
> I doubt the correctness of that claim. There is practical evidence to
> the contrary.

See above.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 16:23:24 -0200
Raw View
On Tuesday 30 December 2014 09:34:53 ramkumar.revanur@gmail.com wrote:
> Some libraries take a lot of effort to make STL objects compatible. There
> is no agreed rules to maintain ABI across major releases of STL library
> that I know of. Please let us know what is that you follow. Some libraries
> (read MS VS) take major versions as an opportunity (and rightly so) to
> introduce changes that can break ABI.

Indeed, they do, which is a royal PITA for those of us trying to provide
binaries for MS compilers. Just see how many builds there are for Windows at
http://qt.io/download/ (click the option to show more). And that's not
including the different update versions -- just yesterday I was helping someone
who had downloaded the binary for MSVC 2013, but was using the wrong update
version (he had Update 3, the Qt binary was built with Update 4).

What's more, Microsoft recognised this as a problem and decided to change it
for 2015.

> I am sure there are few more breaking changes in Visual Studio 2013 and
> more so in Visual Studio 2015.
>
> A nice* article
> <http://www.reddit.com/r/cpp/comments/13zex3/can_vs2010_c_libsdlls_be_linked
> _into_a_vs2012_c/c78ott7>*comes to my mind on rules of using STL (in MSVC?)

See also:

http://blogs.msdn.com/b/vcblog/archive/2014/06/10/the-great-crt-refactoring.aspx
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4028.pdf

Anyway, Standard Libraries aren't required to keep compatibility.. But it
suffices that some want to, so any changes in the Standard that would require a
BC break need to be taken with great care. That's why I am saying that details
specific to an implementation are front and centre in this thread.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Tue, 30 Dec 2014 20:48:44 +0200
Raw View
On 30 December 2014 at 20:15, Thiago Macieira <thiago@macieira.org> wrote:
>> Library B knows which 'method' to use because the shared_ptr types are
>> not the same.
> The types being different is a binary-incompatibility change of itself.

Yes, but it's not an ABI break.

> Moreover, keeping the name the same by way of an inline namespace introduces
> linker or runtime errors instead of a source-incompatible error.

If it's done via inline namespaces, yes. If it's done with non-inline
namespaces,
then it's a source-incompatible error.

>> Library A cannot use the shared_ptr in Library B nor its 'method' because
>> it's not magically forward-compatible with future changes.
> Exactly.

And nobody imposed the type in B on A, so it's not going to break due
to B having
such a type. Such an incompatible type is not without a cost, but it
doesn't necessarily
lead to ABI breaks or recompiling the world.


> So imagine:
> $ cat libA.h
> #include <shared_ptr>
> void method_in_lib_A(const std::shared_ptr<int> &);
> Now imagine that lib B calls that method. Previously, it really was
> "std::shared_ptr<int>". Now, after the standard-required changes, the Standard
> Library implementation decides to use an inline namespace, so the type becomes
> "std::__cxx17::shared_ptr<int>". Since the header didn't specify (and can't
> specify!) the base version, this implies that the new build sees as the new
> type.

I fail to see the reason for the "can't specify"-part. The header can condition
the type it provides by default based on the C++ standard version used.

> As libA wasn't recompiled, this can result in a linker error (unresolved
> symbol: method_in_lib_A(const std::shared_ptr<int> &)). Or, worse, a runtime
> error, since we're talking about building another library and the default ELF
> behaviour is to not resolve at link-time.

Yeah, and there are ways to make it so it will just work.

> If we're talking about system libraries, libB getting updated implies updating
> libA too, which implies updating everything that uses libA. As a cascade
> effect, since now everything uses the new std::shared_ptr, now everything has
> to be updated too.

Old users of the old shared_ptr don't need to be updated, and don't need to
be recompiled.

Now, getting back to the original proposal:
1) I don't think its motivation is very strong
2) I don't think the atomicity argument is a deal-breaker
3) I'm not overly concerned about compatibility breaks
4) HOWEVER, concerning (3): I would certainly like to know whether
libc++, libstdc++ and Dinkumware/Microsoft already have a suitable shared_weak
count and whether the implementation of the proposal is just a matter
of exposing
what Howard outlined.

Without the survey in (4), I don't think the proposal should go
forward. The other
concerns become much more surmountable of (4) doesn't present problems.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Tue, 30 Dec 2014 11:16:33 -0800 (PST)
Raw View
------=_Part_6456_1303267363.1419966994013
Content-Type: multipart/alternative;
 boundary="----=_Part_6457_1828854188.1419966994013"

------=_Part_6457_1828854188.1419966994013
Content-Type: text/plain; charset=UTF-8

On #1, Does it help if more scenarios where this can be used is presented.

On #4, I am happy to look in to MS implementation and get back.



> Now, getting back to the original proposal:
> 1) I don't think its motivation is very strong
> 2) I don't think the atomicity argument is a deal-breaker
> 3) I'm not overly concerned about compatibility breaks
> 4) HOWEVER, concerning (3): I would certainly like to know whether
> libc++, libstdc++ and Dinkumware/Microsoft already have a suitable
> shared_weak
> count and whether the implementation of the proposal is just a matter
> of exposing what Howard outlined.
>
> Without the survey in (4), I don't think the proposal should go
> forward. The other
> concerns become much more surmountable of (4) doesn't present problems.
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_6457_1828854188.1419966994013
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><div>On #1, Does it help if more scenarios where this can =
be used is presented.</div><div><br></div><div>On #4, I am happy to look in=
 to MS implementation and get back.<br></div><div><br></div><div>&nbsp;</di=
v><blockquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;b=
order-left: 1px #ccc solid;padding-left: 1ex;">Now, getting back to the ori=
ginal proposal:
<br>1) I don't think its motivation is very strong
<br>2) I don't think the atomicity argument is a deal-breaker
<br>3) I'm not overly concerned about compatibility breaks
<br>4) HOWEVER, concerning (3): I would certainly like to know whether
<br>libc++, libstdc++ and Dinkumware/Microsoft already have a suitable shar=
ed_weak
<br>count and whether the implementation of the proposal is just a matter
<br>of exposing
what Howard outlined.
<br>
<br>Without the survey in (4), I don't think the proposal should go
<br>forward. The other
<br>concerns become much more surmountable of (4) doesn't present problems.
<br></blockquote></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_6457_1828854188.1419966994013--
------=_Part_6456_1303267363.1419966994013--

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Tue, 30 Dec 2014 21:23:23 +0200
Raw View
On 30 December 2014 at 21:16, Ramkumar Revanur <write2ramkumar@gmail.com> wrote:
> On #1, Does it help if more scenarios where this can be used is presented.

Certainly. Good use cases always help illustrate the motivation of proposals.

> On #4, I am happy to look in to MS implementation and get back.

Cool.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Thiago Macieira <thiago@macieira.org>
Date: Tue, 30 Dec 2014 22:12:15 -0200
Raw View
On Tuesday 30 December 2014 20:48:44 Ville Voutilainen wrote:
> On 30 December 2014 at 20:15, Thiago Macieira <thiago@macieira.org> wrote:
> >> Library B knows which 'method' to use because the shared_ptr types are
> >> not the same.
> >
> > The types being different is a binary-incompatibility change of itself.
>
> Yes, but it's not an ABI break.

Not by itself. The ABI break happens when someone uses that type in their
function parameters. Now, the change of the type causes the functions to
change mangling, which is a BC break.

> > Moreover, keeping the name the same by way of an inline namespace
> > introduces linker or runtime errors instead of a source-incompatible
> > error.
>
> If it's done via inline namespaces, yes. If it's done with non-inline
> namespaces,
> then it's a source-incompatible error.

Indeed, and in my opinion it's better to trigger a source-incompatible error
than to hide a binary- or runtime-incompatible change behind a source-
compatible change.

> >> Library A cannot use the shared_ptr in Library B nor its 'method' because
> >> it's not magically forward-compatible with future changes.
> >
> > Exactly.
>
> And nobody imposed the type in B on A, so it's not going to break due
> to B having
> such a type. Such an incompatible type is not without a cost, but it
> doesn't necessarily
> lead to ABI breaks or recompiling the world.

I'm not sure what you mean.

> > So imagine:
> > $ cat libA.h
> > #include <shared_ptr>
> > void method_in_lib_A(const std::shared_ptr<int> &);
> > Now imagine that lib B calls that method. Previously, it really was
> > "std::shared_ptr<int>". Now, after the standard-required changes, the
> > Standard Library implementation decides to use an inline namespace, so
> > the type becomes "std::__cxx17::shared_ptr<int>". Since the header didn't
> > specify (and can't specify!) the base version, this implies that the new
> > build sees as the new type.
>
> I fail to see the reason for the "can't specify"-part. The header can
> condition the type it provides by default based on the C++ standard version
> used.

The point is that libA can't specify that it *wants* the C++11 version,
regardless of whether there's a future version available.

> > As libA wasn't recompiled, this can result in a linker error (unresolved
> > symbol: method_in_lib_A(const std::shared_ptr<int> &)). Or, worse, a
> > runtime error, since we're talking about building another library and the
> > default ELF behaviour is to not resolve at link-time.
>
> Yeah, and there are ways to make it so it will just work.

And for std::string in libc++, it looks like it's possible to make it work.
However, I don't see how the counters could change in shared_ptr without
triggering a full rebuild.

> > If we're talking about system libraries, libB getting updated implies
> > updating libA too, which implies updating everything that uses libA. As a
> > cascade effect, since now everything uses the new std::shared_ptr, now
> > everything has to be updated too.
>
> Old users of the old shared_ptr don't need to be updated, and don't need to
> be recompiled.

They do if they exchange shared_ptr with any library that has been updated.
That's the cascade effect.

> Now, getting back to the original proposal:
> 1) I don't think its motivation is very strong
> 2) I don't think the atomicity argument is a deal-breaker
> 3) I'm not overly concerned about compatibility breaks
> 4) HOWEVER, concerning (3): I would certainly like to know whether
> libc++, libstdc++ and Dinkumware/Microsoft already have a suitable
> shared_weak count and whether the implementation of the proposal is just a
> matter of exposing
> what Howard outlined.
>
> Without the survey in (4), I don't think the proposal should go
> forward. The other
> concerns become much more surmountable of (4) doesn't present problems.

That's fine by me. #3 is your opinion and we agree to disagree there.

--
Thiago Macieira - thiago (AT) macieira.info - thiago (AT) kde.org
   Software Architect - Intel Open Source Technology Center
      PGP/GPG: 0x6EF45358; fingerprint:
      E067 918B B660 DBD1 105C  966C 33F5 F005 6EF4 5358

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Wed, 31 Dec 2014 02:36:00 +0200
Raw View
On 31 December 2014 at 02:12, Thiago Macieira <thiago@macieira.org> wrote:
>> > The types being different is a binary-incompatibility change of itself.
>> Yes, but it's not an ABI break.
> Not by itself. The ABI break happens when someone uses that type in their
> function parameters. Now, the change of the type causes the functions to
> change mangling, which is a BC break.

I can imagine ways to avoid changing such a parameter type change happening
without asking for it. See below.

>> > Moreover, keeping the name the same by way of an inline namespace
>> > introduces linker or runtime errors instead of a source-incompatible
>> > error.
>> If it's done via inline namespaces, yes. If it's done with non-inline
>> namespaces,
>> then it's a source-incompatible error.
> Indeed, and in my opinion it's better to trigger a source-incompatible error
> than to hide a binary- or runtime-incompatible change behind a source-
> compatible change.

No disagreement on that part.

>> >> Library A cannot use the shared_ptr in Library B nor its 'method' because
>> >> it's not magically forward-compatible with future changes.
>> > Exactly.
>> And nobody imposed the type in B on A, so it's not going to break due
>> to B having
>> such a type. Such an incompatible type is not without a cost, but it
>> doesn't necessarily
>> lead to ABI breaks or recompiling the world.
> I'm not sure what you mean.

I mean that using old-shared_ptr in A doesn't break just because B
decides to start
using a new-shared_ptr, IF the c++ library used continues to provide
both old and new.

>> > So imagine:
>> > $ cat libA.h
>> > #include <shared_ptr>
>> > void method_in_lib_A(const std::shared_ptr<int> &);
>> > Now imagine that lib B calls that method. Previously, it really was
>> > "std::shared_ptr<int>". Now, after the standard-required changes, the
>> > Standard Library implementation decides to use an inline namespace, so
>> > the type becomes "std::__cxx17::shared_ptr<int>". Since the header didn't
>> > specify (and can't specify!) the base version, this implies that the new
>> > build sees as the new type.
>> I fail to see the reason for the "can't specify"-part. The header can
>> condition the type it provides by default based on the C++ standard version
>> used.
> The point is that libA can't specify that it *wants* the C++11 version,
> regardless of whether there's a future version available.

I'm assuming it can, because I think there are ways to allow it to do so.

>> > As libA wasn't recompiled, this can result in a linker error (unresolved
>> > symbol: method_in_lib_A(const std::shared_ptr<int> &)). Or, worse, a
>> > runtime error, since we're talking about building another library and the
>> > default ELF behaviour is to not resolve at link-time.
>> Yeah, and there are ways to make it so it will just work.
> And for std::string in libc++, it looks like it's possible to make it work.
> However, I don't see how the counters could change in shared_ptr without
> triggering a full rebuild.

Well, for quite some time now I've been talking about solutions that add a new
shared_ptr rather than changing the counters in it.

>> > If we're talking about system libraries, libB getting updated implies
>> > updating libA too, which implies updating everything that uses libA. As a
>> > cascade effect, since now everything uses the new std::shared_ptr, now
>> > everything has to be updated too.
>> Old users of the old shared_ptr don't need to be updated, and don't need to
>> be recompiled.
> They do if they exchange shared_ptr with any library that has been updated.
> That's the cascade effect.

They do if they exchange a shared_ptr with any updated library and the multiple
shared_ptrs aren't versioned.

>> Now, getting back to the original proposal:
>> 1) I don't think its motivation is very strong
>> 2) I don't think the atomicity argument is a deal-breaker
>> 3) I'm not overly concerned about compatibility breaks
>> 4) HOWEVER, concerning (3): I would certainly like to know whether
>> libc++, libstdc++ and Dinkumware/Microsoft already have a suitable
>> shared_weak count and whether the implementation of the proposal is just a
>> matter of exposing
>> what Howard outlined.
>> Without the survey in (4), I don't think the proposal should go
>> forward. The other
>> concerns become much more surmountable of (4) doesn't present problems.
> That's fine by me. #3 is your opinion and we agree to disagree there.

Yeah, and I think our different day jobs cause certain differences in
our views on how important
(3) is or is not. :)

I should point out though that (1) plays a part in this. If this
proposal is likely to cause a true
ABI break, we must consider whether it's worth it. There are some
talks about an incompatible
new conceptified library, so perhaps the arrival of such a thing would
provide a more reasonable
time to make such changes than just adding small more-or-less breaking
changes here-and-there.
If this proposal were the only thing causing compatibility breaks, I
think I would seriously question
its motivation. Then again, I question its motivation even now - the
reason I'd be mildly for it is if
implementations can already easily expose this information, I don't
see the harm and can imagine
reasonable uses for it. That may end up being a very big if.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ramkumar Revanur <write2ramkumar@gmail.com>
Date: Tue, 30 Dec 2014 19:46:17 -0800 (PST)
Raw View
------=_Part_9335_1601243857.1419997577918
Content-Type: multipart/alternative;
 boundary="----=_Part_9336_1987924042.1419997577918"

------=_Part_9336_1987924042.1419997577918
Content-Type: text/plain; charset=UTF-8


On #4,

In Microsoft STL, the changes are styled in bold. I don't see it as a
breaking change either.

In file: memory

 // CLASS _Ref_count_base
class _Ref_count_base
 { // common code for reference counting
 //....
 private:
 _Atomic_counter_t _Uses;
 _Atomic_counter_t _Weaks;

 //....
public:
 unsigned int _Get_uses() const
 { // return use count
 return (_Get_atomic_count(_Uses));
 }





*unsigned int _Get_weak_count() const { // return weak_count return
(_Get_atomic_count(_Weaks)); }*


 //....

 //....



 void _Incref()
 { // increment use count
 _MT_INCR(_Ignored, _Uses);
 }


 void _Incwref()
 { // increment weak reference count
 _MT_INCR(_Ignored, _Weaks);
 }


 void _Decref()
 { // decrement use count
 if (_MT_DECR(_Ignored, _Uses) == 0)
 { // destroy managed resource, decrement weak reference count
 _Destroy();
 _Decwref();
 }
 }


 void _Decwref()
 { // decrement weak reference count
 if (_MT_DECR(_Ignored, _Weaks) == 0)
 _Delete_this();
 }


 long _Use_count() const
 { // return use count
 return (_Get_uses());
 }





*long _Weak_count() const { // return weak count return
(_Get_weak_count()); }*


 bool _Expired() const
 { // return true if _Uses == 0
 return (_Get_uses() == 0);
 }
 //....

};



//...

//...

 // TEMPLATE CLASS _Ptr_base
template<class _Ty>
 class _Ptr_base
 {
//...

//...

//...

 long use_count() const _NOEXCEPT
 { // return use count
 return (_Rep ? _Rep->_Use_count() : 0);
 }





*long weak_count() const _NOEXCEPT { // return weak count return (_Rep ?
_Rep->_Weak_count() : 0); }*
//...

 };

I am in the process and building a few unit tests and stress testing it in
concurrent usage scenarios.






On Wednesday, December 31, 2014 12:53:25 AM UTC+5:30, Ville Voutilainen
wrote:
>
> On 30 December 2014 at 21:16, Ramkumar Revanur <write2r...@gmail.com
> <javascript:>> wrote:
> > On #1, Does it help if more scenarios where this can be used is
> presented.
>
> Certainly. Good use cases always help illustrate the motivation of
> proposals.
>
> > On #4, I am happy to look in to MS implementation and get back.
>
> Cool.
>

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

------=_Part_9336_1987924042.1419997577918
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr"><br>On #4,<div><br></div><div>In Microsoft STL, the change=
s are styled in bold. I don't see it as a breaking change either.</div><div=
><br></div><div>In file: memory</div><div><br></div><div><div class=3D"pret=
typrint" style=3D"border: 1px solid rgb(187, 187, 187); word-wrap: break-wo=
rd; background-color: rgb(250, 250, 250);"><code class=3D"prettyprint"><div=
 class=3D"subprettyprint"><span style=3D"color: #000;" class=3D"styled-by-p=
rettify">&nbsp;</span><span style=3D"color: #800;" class=3D"styled-by-prett=
ify">// CLASS _Ref_count_base</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify"><br></span><span style=3D"color: #008;" class=3D"styled-=
by-prettify">class</span><span style=3D"color: #000;" class=3D"styled-by-pr=
ettify"> _Ref_count_base<br>&nbsp;</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">{</span><span style=3D"color: #000;" class=3D"style=
d-by-prettify"> </span><span style=3D"color: #800;" class=3D"styled-by-pret=
tify">// common code for reference counting</span><span style=3D"color: #00=
0;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #80=
0;" class=3D"styled-by-prettify">//....</span><span style=3D"color: #000;" =
class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #008;" =
class=3D"styled-by-prettify">private</span><span style=3D"color: #660;" cla=
ss=3D"styled-by-prettify">:</span><span style=3D"color: #000;" class=3D"sty=
led-by-prettify"><br>&nbsp;_Atomic_counter_t _Uses</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">;</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"><br>&nbsp;_Atomic_counter_t _Weaks</span><sp=
an style=3D"color: #660;" class=3D"styled-by-prettify">;</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"> &nbsp; &nbsp; &nbsp; &nbsp;=
 <br><br>&nbsp;</span><span style=3D"color: #800;" class=3D"styled-by-prett=
ify">//....</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
><br></span><span style=3D"color: #008;" class=3D"styled-by-prettify">publi=
c</span><span style=3D"color: #660;" class=3D"styled-by-prettify">:</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><=
span style=3D"color: #008;" class=3D"styled-by-prettify">unsigned</span><sp=
an style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">int</span><span style=3D"col=
or: #000;" class=3D"styled-by-prettify"> _Get_uses</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">()</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"> </span><span style=3D"color: #008;" class=
=3D"styled-by-prettify">const</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"> </span><span style=3D"color: #800;" class=3D"styled-by-prettify"=
>// return use count</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"><br>&nbsp;</span><span style=3D"color: #008;" class=3D"styled-by-=
prettify">return</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify">_Get_atomic_=
count</span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</sp=
an><span style=3D"color: #000;" class=3D"styled-by-prettify">_Uses</span><s=
pan style=3D"color: #660;" class=3D"styled-by-prettify">));</span><span sty=
le=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span sty=
le=3D"color: #660;" class=3D"styled-by-prettify">}</span><span style=3D"col=
or: #000;" class=3D"styled-by-prettify"><br><br><br></span><b><span style=
=3D"color: #000;" class=3D"styled-by-prettify">&nbsp;</span></b><b><span st=
yle=3D"color: #008;" class=3D"styled-by-prettify">unsigned</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"colo=
r: #008;" class=3D"styled-by-prettify">int</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"> _Get_weak_count</span><span style=3D"color=
: #660;" class=3D"styled-by-prettify">()</span><span style=3D"color: #000;"=
 class=3D"styled-by-prettify"> </span><span style=3D"color: #008;" class=3D=
"styled-by-prettify">const</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"> </span><span style=3D"color: #800;" class=3D"styled-by-prettify">//=
 return weak_count</span><span style=3D"color: #000;" class=3D"styled-by-pr=
ettify"><br>&nbsp;</span><span style=3D"color: #008;" class=3D"styled-by-pr=
ettify">return</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</sp=
an><span style=3D"color: #000;" class=3D"styled-by-prettify">_Get_atomic_co=
unt</span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</span=
><span style=3D"color: #000;" class=3D"styled-by-prettify">_Weaks</span><sp=
an style=3D"color: #660;" class=3D"styled-by-prettify">));</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span styl=
e=3D"color: #660;" class=3D"styled-by-prettify">}</span></b><b><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br></span></b><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br><br>&nbsp;</span><span s=
tyle=3D"color: #800;" class=3D"styled-by-prettify">//....</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br><br>&nbsp;</span><span s=
tyle=3D"color: #800;" class=3D"styled-by-prettify">//....</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br><br><br><br>&nbsp;</span=
><span style=3D"color: #008;" class=3D"styled-by-prettify">void</span><span=
 style=3D"color: #000;" class=3D"styled-by-prettify"> _Incref</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">()</span><span style=3D"=
color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"=
color: #660;" class=3D"styled-by-prettify">{</span><span style=3D"color: #0=
00;" class=3D"styled-by-prettify"> </span><span style=3D"color: #800;" clas=
s=3D"styled-by-prettify">// increment use count</span><span style=3D"color:=
 #000;" class=3D"styled-by-prettify"><br>&nbsp;_MT_INCR</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">(</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify">_Ignored</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">,</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"> _Uses</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">);</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styl=
ed-by-prettify">}</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"><br><br><br>&nbsp;</span><span style=3D"color: #008;" class=3D"style=
d-by-prettify">void</span><span style=3D"color: #000;" class=3D"styled-by-p=
rettify"> _Incwref</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">()</span><span style=3D"color: #000;" class=3D"styled-by-prettify">=
<br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-prettify">=
{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><=
span style=3D"color: #800;" class=3D"styled-by-prettify">// increment weak =
reference count</span><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"><br>&nbsp;_MT_INCR</span><span style=3D"color: #660;" class=3D"styled-=
by-prettify">(</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy">_Ignored</span><span style=3D"color: #660;" class=3D"styled-by-prettify=
">,</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _Weaks=
</span><span style=3D"color: #660;" class=3D"styled-by-prettify">);</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><=
span style=3D"color: #660;" class=3D"styled-by-prettify">}</span><span styl=
e=3D"color: #000;" class=3D"styled-by-prettify"><br><br><br>&nbsp;</span><s=
pan style=3D"color: #008;" class=3D"styled-by-prettify">void</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify"> _Decref</span><span styl=
e=3D"color: #660;" class=3D"styled-by-prettify">()</span><span style=3D"col=
or: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">{</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify"> </span><span style=3D"color: #800;" class=
=3D"styled-by-prettify">// decrement use count</span><span style=3D"color: =
#000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: =
#008;" class=3D"styled-by-prettify">if</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">(</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify">_MT_DECR</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">(</span><span style=3D"color: #000;" class=3D"styled-by-prettify">_=
Ignored</span><span style=3D"color: #660;" class=3D"styled-by-prettify">,</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _Uses</span=
><span style=3D"color: #660;" class=3D"styled-by-prettify">)</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">=3D=3D</span><span style=3D"color:=
 #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #066;" c=
lass=3D"styled-by-prettify">0</span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">)</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-=
prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"=
> </span><span style=3D"color: #800;" class=3D"styled-by-prettify">// destr=
oy managed resource, decrement weak reference count</span><span style=3D"co=
lor: #000;" class=3D"styled-by-prettify"><br>&nbsp;_Destroy</span><span sty=
le=3D"color: #660;" class=3D"styled-by-prettify">();</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"><br>&nbsp;_Decwref</span><span st=
yle=3D"color: #660;" class=3D"styled-by-prettify">();</span><span style=3D"=
color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"=
color: #660;" class=3D"styled-by-prettify">}</span><span style=3D"color: #0=
00;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #6=
60;" class=3D"styled-by-prettify">}</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"><br><br><br>&nbsp;</span><span style=3D"color: #00=
8;" class=3D"styled-by-prettify">void</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"> _Decwref</span><span style=3D"color: #660;" cla=
ss=3D"styled-by-prettify">()</span><span style=3D"color: #000;" class=3D"st=
yled-by-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"st=
yled-by-prettify">{</span><span style=3D"color: #000;" class=3D"styled-by-p=
rettify"> </span><span style=3D"color: #800;" class=3D"styled-by-prettify">=
// decrement weak reference count</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #008;" class=
=3D"styled-by-prettify">if</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by-pre=
ttify">(</span><span style=3D"color: #000;" class=3D"styled-by-prettify">_M=
T_DECR</span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</s=
pan><span style=3D"color: #000;" class=3D"styled-by-prettify">_Ignored</spa=
n><span style=3D"color: #660;" class=3D"styled-by-prettify">,</span><span s=
tyle=3D"color: #000;" class=3D"styled-by-prettify"> _Weaks</span><span styl=
e=3D"color: #660;" class=3D"styled-by-prettify">)</span><span style=3D"colo=
r: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #660;"=
 class=3D"styled-by-prettify">=3D=3D</span><span style=3D"color: #000;" cla=
ss=3D"styled-by-prettify"> </span><span style=3D"color: #066;" class=3D"sty=
led-by-prettify">0</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">)</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><=
br>&nbsp;_Delete_this</span><span style=3D"color: #660;" class=3D"styled-by=
-prettify">();</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-pretti=
fy">}</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><=
br><br>&nbsp;</span><span style=3D"color: #008;" class=3D"styled-by-prettif=
y">long</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _U=
se_count</span><span style=3D"color: #660;" class=3D"styled-by-prettify">()=
</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span><s=
pan style=3D"color: #008;" class=3D"styled-by-prettify">const</span><span s=
tyle=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">{</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #80=
0;" class=3D"styled-by-prettify">// return use count</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"c=
olor: #008;" class=3D"styled-by-prettify">return</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #660;" =
class=3D"styled-by-prettify">(</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify">_Get_uses</span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">());</span><span style=3D"color: #000;" class=3D"styled-=
by-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-=
by-prettify">}</span><span style=3D"color: #000;" class=3D"styled-by-pretti=
fy"><br><br></span><b><span style=3D"color: #000;" class=3D"styled-by-prett=
ify"><br>&nbsp;</span></b><b><span style=3D"color: #008;" class=3D"styled-b=
y-prettify">long</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"> _Weak_count</span><span style=3D"color: #660;" class=3D"styled-by-pr=
ettify">()</span><span style=3D"color: #000;" class=3D"styled-by-prettify">=
 </span><span style=3D"color: #008;" class=3D"styled-by-prettify">const</sp=
an><span style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</sp=
an><span style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span =
style=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"=
color: #800;" class=3D"styled-by-prettify">// return weak count</span><span=
 style=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span=
 style=3D"color: #008;" class=3D"styled-by-prettify">return</span><span sty=
le=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"col=
or: #660;" class=3D"styled-by-prettify">(</span><span style=3D"color: #000;=
" class=3D"styled-by-prettify">_Get_weak_count</span><span style=3D"color: =
#660;" class=3D"styled-by-prettify">());</span><span style=3D"color: #000;"=
 class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #660;"=
 class=3D"styled-by-prettify">}</span></b><b><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify"><br><br></span></b><span style=3D"color: #000;"=
 class=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #008;"=
 class=3D"styled-by-prettify">bool</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"> _Expired</span><span style=3D"color: #660;" class=
=3D"styled-by-prettify">()</span><span style=3D"color: #000;" class=3D"styl=
ed-by-prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-pre=
ttify">const</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-prettify=
">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span=
><span style=3D"color: #800;" class=3D"styled-by-prettify">// return true i=
f _Uses =3D=3D 0</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify"><br>&nbsp;</span><span style=3D"color: #008;" class=3D"styled-by-pret=
tify">return</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"> </span><span style=3D"color: #660;" class=3D"styled-by-prettify">(</span=
><span style=3D"color: #000;" class=3D"styled-by-prettify">_Get_uses</span>=
<span style=3D"color: #660;" class=3D"styled-by-prettify">()</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">=3D=3D</span><span style=3D"color:=
 #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #066;" c=
lass=3D"styled-by-prettify">0</span><span style=3D"color: #660;" class=3D"s=
tyled-by-prettify">);</span><span style=3D"color: #000;" class=3D"styled-by=
-prettify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by=
-prettify">}</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"><br>&nbsp;</span><span style=3D"color: #800;" class=3D"styled-by-prettify=
">//....</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><b=
r><br></span><span style=3D"color: #660;" class=3D"styled-by-prettify">};</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br><br>=
<br></span><span style=3D"color: #800;" class=3D"styled-by-prettify">//...<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br></s=
pan><span style=3D"color: #800;" class=3D"styled-by-prettify">//...</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br>&nbsp;</sp=
an><span style=3D"color: #800;" class=3D"styled-by-prettify">// TEMPLATE CL=
ASS _Ptr_base</span><span style=3D"color: #000;" class=3D"styled-by-prettif=
y"><br></span><span style=3D"color: #008;" class=3D"styled-by-prettify">tem=
plate</span><span style=3D"color: #660;" class=3D"styled-by-prettify">&lt;<=
/span><span style=3D"color: #008;" class=3D"styled-by-prettify">class</span=
><span style=3D"color: #000;" class=3D"styled-by-prettify"> _Ty</span><span=
 style=3D"color: #660;" class=3D"styled-by-prettify">&gt;</span><span style=
=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span style=
=3D"color: #008;" class=3D"styled-by-prettify">class</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"> _Ptr_base<br>&nbsp;</span><span =
style=3D"color: #660;" class=3D"styled-by-prettify">{</span><span style=3D"=
color: #000;" class=3D"styled-by-prettify"><br></span><span style=3D"color:=
 #800;" class=3D"styled-by-prettify">//...</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"><br><br></span><span style=3D"color: #800;"=
 class=3D"styled-by-prettify">//...</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"><br><br></span><span style=3D"color: #800;" class=
=3D"styled-by-prettify">//...</span><span style=3D"color: #000;" class=3D"s=
tyled-by-prettify"><br><br>&nbsp;</span><span style=3D"color: #008;" class=
=3D"styled-by-prettify">long</span><span style=3D"color: #000;" class=3D"st=
yled-by-prettify"> use_count</span><span style=3D"color: #660;" class=3D"st=
yled-by-prettify">()</span><span style=3D"color: #000;" class=3D"styled-by-=
prettify"> </span><span style=3D"color: #008;" class=3D"styled-by-prettify"=
>const</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _NO=
EXCEPT<br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-pret=
tify">{</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </=
span><span style=3D"color: #800;" class=3D"styled-by-prettify">// return us=
e count</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br=
>&nbsp;</span><span style=3D"color: #008;" class=3D"styled-by-prettify">ret=
urn</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> </span=
><span style=3D"color: #660;" class=3D"styled-by-prettify">(</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify">_Rep </span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">?</span><span style=3D"color=
: #000;" class=3D"styled-by-prettify"> _Rep</span><span style=3D"color: #66=
0;" class=3D"styled-by-prettify">-&gt;</span><span style=3D"color: #000;" c=
lass=3D"styled-by-prettify">_Use_count</span><span style=3D"color: #660;" c=
lass=3D"styled-by-prettify">()</span><span style=3D"color: #000;" class=3D"=
styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"styled-by=
-prettify">:</span><span style=3D"color: #000;" class=3D"styled-by-prettify=
"> </span><span style=3D"color: #066;" class=3D"styled-by-prettify">0</span=
><span style=3D"color: #660;" class=3D"styled-by-prettify">);</span><span s=
tyle=3D"color: #000;" class=3D"styled-by-prettify"><br>&nbsp;</span><span s=
tyle=3D"color: #660;" class=3D"styled-by-prettify">}</span><span style=3D"c=
olor: #000;" class=3D"styled-by-prettify"><br><br><br></span><b><span style=
=3D"color: #000;" class=3D"styled-by-prettify">&nbsp;</span></b><b><span st=
yle=3D"color: #008;" class=3D"styled-by-prettify">long</span><span style=3D=
"color: #000;" class=3D"styled-by-prettify"> weak_count</span><span style=
=3D"color: #660;" class=3D"styled-by-prettify">()</span><span style=3D"colo=
r: #000;" class=3D"styled-by-prettify"> </span><span style=3D"color: #008;"=
 class=3D"styled-by-prettify">const</span><span style=3D"color: #000;" clas=
s=3D"styled-by-prettify"> _NOEXCEPT<br>&nbsp;</span><span style=3D"color: #=
660;" class=3D"styled-by-prettify">{</span><span style=3D"color: #000;" cla=
ss=3D"styled-by-prettify"> </span><span style=3D"color: #800;" class=3D"sty=
led-by-prettify">// return weak count</span><span style=3D"color: #000;" cl=
ass=3D"styled-by-prettify"><br>&nbsp;</span><span style=3D"color: #008;" cl=
ass=3D"styled-by-prettify">return</span><span style=3D"color: #000;" class=
=3D"styled-by-prettify"> </span><span style=3D"color: #660;" class=3D"style=
d-by-prettify">(</span><span style=3D"color: #000;" class=3D"styled-by-pret=
tify">_Rep </span><span style=3D"color: #660;" class=3D"styled-by-prettify"=
>?</span><span style=3D"color: #000;" class=3D"styled-by-prettify"> _Rep</s=
pan><span style=3D"color: #660;" class=3D"styled-by-prettify">-&gt;</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify">_Weak_count</span>=
<span style=3D"color: #660;" class=3D"styled-by-prettify">()</span><span st=
yle=3D"color: #000;" class=3D"styled-by-prettify"> </span><span style=3D"co=
lor: #660;" class=3D"styled-by-prettify">:</span><span style=3D"color: #000=
;" class=3D"styled-by-prettify"> </span><span style=3D"color: #066;" class=
=3D"styled-by-prettify">0</span><span style=3D"color: #660;" class=3D"style=
d-by-prettify">);</span><span style=3D"color: #000;" class=3D"styled-by-pre=
ttify"><br>&nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-pre=
ttify">}</span></b><span style=3D"color: #000;" class=3D"styled-by-prettify=
"><br></span><span style=3D"color: #800;" class=3D"styled-by-prettify">//..=
..</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br>&=
nbsp;</span><span style=3D"color: #660;" class=3D"styled-by-prettify">};</s=
pan><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><br>I am =
</span><span style=3D"color: #008;" class=3D"styled-by-prettify">in</span><=
span style=3D"color: #000;" class=3D"styled-by-prettify"> the process </spa=
n><span style=3D"color: #008;" class=3D"styled-by-prettify">and</span><span=
 style=3D"color: #000;" class=3D"styled-by-prettify"> building a few unit t=
ests </span><span style=3D"color: #008;" class=3D"styled-by-prettify">and</=
span><span style=3D"color: #000;" class=3D"styled-by-prettify"> stress test=
ing it </span><span style=3D"color: #008;" class=3D"styled-by-prettify">in<=
/span><span style=3D"color: #000;" class=3D"styled-by-prettify"> concurrent=
 usage scenarios</span><span style=3D"color: #660;" class=3D"styled-by-pret=
tify">.</span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br=
><br></span><span style=3D"color: #000;" class=3D"styled-by-prettify"><br><=
br></span></div></code></div><div><div><br><br></div><div><br></div>On Wedn=
esday, December 31, 2014 12:53:25 AM UTC+5:30, Ville Voutilainen wrote:<blo=
ckquote class=3D"gmail_quote" style=3D"margin: 0;margin-left: 0.8ex;border-=
left: 1px #ccc solid;padding-left: 1ex;">On 30 December 2014 at 21:16, Ramk=
umar Revanur &lt;<a href=3D"javascript:" target=3D"_blank" gdf-obfuscated-m=
ailto=3D"r-OkRlP5uVYJ" onmousedown=3D"this.href=3D'javascript:';return true=
;" onclick=3D"this.href=3D'javascript:';return true;">write2r...@gmail.com<=
/a>&gt; wrote:
<br>&gt; On #1, Does it help if more scenarios where this can be used is pr=
esented.
<br>
<br>Certainly. Good use cases always help illustrate the motivation of prop=
osals.
<br>
<br>&gt; On #4, I am happy to look in to MS implementation and get back.
<br>
<br>Cool.
<br></blockquote></div></div></div>

<p></p>

-- <br />
<br />
--- <br />
You received this message because you are subscribed to the Google Groups &=
quot;ISO C++ Standard - Future Proposals&quot; group.<br />
To unsubscribe from this group and stop receiving emails from it, send an e=
mail to <a href=3D"mailto:std-proposals+unsubscribe@isocpp.org">std-proposa=
ls+unsubscribe@isocpp.org</a>.<br />
To post to this group, send email to <a href=3D"mailto:std-proposals@isocpp=
..org">std-proposals@isocpp.org</a>.<br />
Visit this group at <a href=3D"http://groups.google.com/a/isocpp.org/group/=
std-proposals/">http://groups.google.com/a/isocpp.org/group/std-proposals/<=
/a>.<br />

------=_Part_9336_1987924042.1419997577918--
------=_Part_9335_1601243857.1419997577918--

.


Author: Matthew Woehlke <mw_triad@users.sourceforge.net>
Date: Wed, 31 Dec 2014 11:27:05 -0500
Raw View
On 2014-12-30 19:36, Ville Voutilainen wrote:
> On 31 December 2014 at 02:12, Thiago Macieira wrote:
>> However, I don't see how the counters could change in shared_ptr without
>> triggering a full rebuild.
>
> Well, for quite some time now I've been talking about solutions that add a new
> shared_ptr rather than changing the counters in it.

FWIW, I don't see how this would help with the OP's use case. The point
would seem to be to continue to use std::shared_ptr / std::weak_ptr for
the benefit of external users that expect those. If the feature is added
to some new type, the OP might as well write their own pointer class
that has the necessary features, which can be done without a change to C++.

--
Matthew

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.


Author: Ville Voutilainen <ville.voutilainen@gmail.com>
Date: Wed, 31 Dec 2014 18:29:47 +0200
Raw View
On 31 December 2014 at 18:27, Matthew Woehlke
<mw_triad@users.sourceforge.net> wrote:
> On 2014-12-30 19:36, Ville Voutilainen wrote:
>> On 31 December 2014 at 02:12, Thiago Macieira wrote:
>>> However, I don't see how the counters could change in shared_ptr without
>>> triggering a full rebuild.
>>
>> Well, for quite some time now I've been talking about solutions that add a new
>> shared_ptr rather than changing the counters in it.
>
> FWIW, I don't see how this would help with the OP's use case. The point
> would seem to be to continue to use std::shared_ptr / std::weak_ptr for
> the benefit of external users that expect those. If the feature is added
> to some new type, the OP might as well write their own pointer class
> that has the necessary features, which can be done without a change to C++.


The reason for adding a new shared_ptr would be to avoid ABI breaks.
If you don't
make such a change with a different type, you may end up having ABI breakage.
That's why I asked whether the existing implementations already have a suitable
count that they could return without incurring such breakage. The rest
of the sidetrack
was mostly a discussion about how to avoid ABI breaks, if any. If none, we have
much less of a problem.

--

---
You received this message because you are subscribed to the Google Groups "ISO C++ Standard - Future Proposals" group.
To unsubscribe from this group and stop receiving emails from it, send an email to std-proposals+unsubscribe@isocpp.org.
To post to this group, send email to std-proposals@isocpp.org.
Visit this group at http://groups.google.com/a/isocpp.org/group/std-proposals/.

.