qpid-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Jiri Daněk (JIRA) <j...@apache.org>
Subject [jira] [Commented] (PROTON-1556) [proton-cpp] ssl_client_options is not self-assignable
Date Tue, 10 Oct 2017 18:18:00 GMT

    [ https://issues.apache.org/jira/browse/PROTON-1556?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16199125#comment-16199125
] 

Jiri Daněk commented on PROTON-1556:
------------------------------------

btw, the Internets apparently frown upon doing the explicit check, https://stackoverflow.com/questions/12015156/what-is-wrong-with-checking-for-self-assignment-and-what-does-it-mean

> [proton-cpp] ssl_client_options is not self-assignable
> ------------------------------------------------------
>
>                 Key: PROTON-1556
>                 URL: https://issues.apache.org/jira/browse/PROTON-1556
>             Project: Qpid Proton
>          Issue Type: Bug
>          Components: cpp-binding
>    Affects Versions: proton-c-0.18.0
>            Reporter: Jiri Daněk
>            Assignee: Cliff Jansen
>            Priority: Trivial
>             Fix For: proton-c-0.18.0
>
>         Attachments: report-7646dc.html
>
>
> {{ssl_client_options}} probably cannot be self-assigned. See the attached report from
clang-analyzer, which looks very plausible.
> The problem is that assuming {{x == *this}}, the assignment operator will decref and
then incref the same value. Assuming the reference count was {{1}} to start with, there will
be use-after-free.
> This probably does not matter that much in real-world code, but I found some quotations
that making self assignment work is really important in C++...
> {noformat}
> 58	ssl_domain& internal::ssl_domain::operator=(const ssl_domain&x) {
> 59	    if (impl_) impl_->decref();
> 60	    impl_ = x.impl_;
> 61	    server_type_ = x.server_type_;
> 62	    if (impl_) impl_->incref();
> 63	    return *this;
> 64	}
> {noformat}
> I believe the static analyzer is correct, because when I do not make any changes to the
{{examples/cpp/ssl}} example, Valgrind does not report errors concerning the class, but if
I add a {{ssl_cli = ssl_cli;}}, then I get
> {noformat}
> $ valgrind ./ssl -c /home/jdanek/Work/repos/qpid-proton/examples/cpp/ssl_certs/
> ==4950== Memcheck, a memory error detector
> ==4950== Copyright (C) 2002-2015, and GNU GPL'd, by Julian Seward et al.
> ==4950== Using Valgrind-3.12.0 and LibVEX; rerun with -h for copyright info
> ==4950== Command: ./ssl -c /home/jdanek/Work/repos/qpid-proton/examples/cpp/ssl_certs/
> ==4950== 
> ==4950== Invalid read of size 4
> ==4950==    at 0x4E715CC: incref (ssl_domain.cpp:37)
> ==4950==    by 0x4E715CC: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:62)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Address 0x766a3c0 is 0 bytes inside a block of size 16 free'd
> ==4950==    at 0x4C2D2EB: operator delete(void*) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E715FA: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E715FA: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:59)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Block was alloc'd at
> ==4950==    at 0x4C2C22F: operator new(unsigned long) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E7166C: proton::internal::ssl_domain::pn_domain() (ssl_domain.cpp:72)
> ==4950==    by 0x4E7195C: proton::ssl_client_options::ssl_client_options(std::__cxx11::basic_string<char,
std::char_traits<char>, std::allocator<char> > const&, proton::ssl::verify_mode)
(ssl_domain.cpp:120)
> ==4950==    by 0x4032B9: main (ssl.cpp:175)
> ==4950== 
> ==4950== Invalid read of size 4
> ==4950==    at 0x4E71619: decref (ssl_domain.cpp:39)
> ==4950==    by 0x4E71619: proton::internal::ssl_domain::~ssl_domain() (ssl_domain.cpp:66)
> ==4950==    by 0x4032F8: ~ssl_client_options (ssl.hpp:172)
> ==4950==    by 0x4032F8: main (ssl.cpp:175)
> ==4950==  Address 0x766a3c0 is 0 bytes inside a block of size 16 free'd
> ==4950==    at 0x4C2D2EB: operator delete(void*) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E715FA: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E715FA: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:59)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Block was alloc'd at
> ==4950==    at 0x4C2C22F: operator new(unsigned long) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E7166C: proton::internal::ssl_domain::pn_domain() (ssl_domain.cpp:72)
> ==4950==    by 0x4E7195C: proton::ssl_client_options::ssl_client_options(std::__cxx11::basic_string<char,
std::char_traits<char>, std::allocator<char> > const&, proton::ssl::verify_mode)
(ssl_domain.cpp:120)
> ==4950==    by 0x4032B9: main (ssl.cpp:175)
> ==4950== 
> ==4950== Invalid read of size 8
> ==4950==    at 0x4E71620: ~ssl_domain_impl (ssl_domain.cpp:36)
> ==4950==    by 0x4E71620: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E71620: proton::internal::ssl_domain::~ssl_domain() (ssl_domain.cpp:66)
> ==4950==    by 0x4032F8: ~ssl_client_options (ssl.hpp:172)
> ==4950==    by 0x4032F8: main (ssl.cpp:175)
> ==4950==  Address 0x766a3c8 is 8 bytes inside a block of size 16 free'd
> ==4950==    at 0x4C2D2EB: operator delete(void*) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E715FA: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E715FA: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:59)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Block was alloc'd at
> ==4950==    at 0x4C2C22F: operator new(unsigned long) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E7166C: proton::internal::ssl_domain::pn_domain() (ssl_domain.cpp:72)
> ==4950==    by 0x4E7195C: proton::ssl_client_options::ssl_client_options(std::__cxx11::basic_string<char,
std::char_traits<char>, std::allocator<char> > const&, proton::ssl::verify_mode)
(ssl_domain.cpp:120)
> ==4950==    by 0x4032B9: main (ssl.cpp:175)
> ==4950== 
> ==4950== Invalid read of size 4
> ==4950==    at 0x52B8840: pn_ssl_domain_free (openssl.c:559)
> ==4950==    by 0x4E71628: ~ssl_domain_impl (ssl_domain.cpp:36)
> ==4950==    by 0x4E71628: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E71628: proton::internal::ssl_domain::~ssl_domain() (ssl_domain.cpp:66)
> ==4950==    by 0x4032F8: ~ssl_client_options (ssl.hpp:172)
> ==4950==    by 0x4032F8: main (ssl.cpp:175)
> ==4950==  Address 0x76c1c08 is 24 bytes inside a block of size 40 free'd
> ==4950==    at 0x4C2CDEB: free (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E715ED: ~ssl_domain_impl (ssl_domain.cpp:36)
> ==4950==    by 0x4E715ED: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E715ED: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:59)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Block was alloc'd at
> ==4950==    at 0x4C2DBD5: calloc (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x52B8C26: pn_ssl_domain (openssl.c:490)
> ==4950==    by 0x4E71BB9: proton::ssl_domain_impl::ssl_domain_impl(bool) (ssl_domain.cpp:33)
> ==4950==    by 0x4E7167B: proton::internal::ssl_domain::pn_domain() (ssl_domain.cpp:72)
> ==4950==    by 0x4E7195C: proton::ssl_client_options::ssl_client_options(std::__cxx11::basic_string<char,
std::char_traits<char>, std::allocator<char> > const&, proton::ssl::verify_mode)
(ssl_domain.cpp:120)
> ==4950==    by 0x4032B9: main (ssl.cpp:175)
> ==4950== 
> ==4950== Invalid free() / delete / delete[] / realloc()
> ==4950==    at 0x4C2D2EB: operator delete(void*) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4032F8: ~ssl_client_options (ssl.hpp:172)
> ==4950==    by 0x4032F8: main (ssl.cpp:175)
> ==4950==  Address 0x766a3c0 is 0 bytes inside a block of size 16 free'd
> ==4950==    at 0x4C2D2EB: operator delete(void*) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E715FA: decref (ssl_domain.cpp:40)
> ==4950==    by 0x4E715FA: proton::internal::ssl_domain::operator=(proton::internal::ssl_domain
const&) (ssl_domain.cpp:59)
> ==4950==    by 0x4032F0: operator= (ssl.hpp:172)
> ==4950==    by 0x4032F0: main (ssl.cpp:176)
> ==4950==  Block was alloc'd at
> ==4950==    at 0x4C2C22F: operator new(unsigned long) (in /nix/store/gv9x2j31hvn0wf37h4jmb9xz6vgc3vvv-valgrind-3.12.0/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
> ==4950==    by 0x4E7166C: proton::internal::ssl_domain::pn_domain() (ssl_domain.cpp:72)
> ==4950==    by 0x4E7195C: proton::ssl_client_options::ssl_client_options(std::__cxx11::basic_string<char,
std::char_traits<char>, std::allocator<char> > const&, proton::ssl::verify_mode)
(ssl_domain.cpp:120)
> ==4950==    by 0x4032B9: main (ssl.cpp:175)
> ==4950== 
> ==4950== 
> ==4950== HEAP SUMMARY:
> ==4950==     in use at exit: 98,536 bytes in 3,275 blocks
> ==4950==   total heap usage: 3,651 allocs, 377 frees, 237,715 bytes allocated
> ==4950== 
> ==4950== LEAK SUMMARY:
> ==4950==    definitely lost: 0 bytes in 0 blocks
> ==4950==    indirectly lost: 0 bytes in 0 blocks
> ==4950==      possibly lost: 0 bytes in 0 blocks
> ==4950==    still reachable: 98,536 bytes in 3,275 blocks
> ==4950==         suppressed: 0 bytes in 0 blocks
> ==4950== Rerun with --leak-check=full to see details of leaked memory
> ==4950== 
> ==4950== For counts of detected and suppressed errors, rerun with: -v
> ==4950== ERROR SUMMARY: 8 errors from 5 contexts (suppressed: 0 from 0)
> {noformat}
> Hat tip to [~rkubis] for help with C++.



--
This message was sent by Atlassian JIRA
(v6.4.14#64029)

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@qpid.apache.org
For additional commands, e-mail: dev-help@qpid.apache.org


Mime
View raw message