diff --git a/include/WinStd/COM.h b/include/WinStd/COM.h index bc043557..dac444ac 100644 --- a/include/WinStd/COM.h +++ b/include/WinStd/COM.h @@ -184,7 +184,7 @@ namespace winstd /// /// \return Duplicated object handle /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { h->AddRef(); return h; @@ -271,9 +271,12 @@ namespace winstd /// /// \sa [SysAllocString function](https://msdn.microsoft.com/en-us/library/windows/desktop/ms221458.aspx) /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { - return SysAllocStringLen(h, SysStringLen(h)); + handle_type h_new = SysAllocStringLen(h, SysStringLen(h)); + if (h_new != invalid) + return h_new; + throw std::bad_alloc(); } }; diff --git a/include/WinStd/Common.h b/include/WinStd/Common.h index 06f870c6..74e89f2a 100644 --- a/include/WinStd/Common.h +++ b/include/WinStd/Common.h @@ -854,7 +854,7 @@ namespace winstd /// /// \param[inout] h A reference of another object /// - dplhandle(_In_ const dplhandle &h) noexcept : handle(duplicate_internal(h.m_h)) + dplhandle(_In_ const dplhandle &h) : handle(duplicate_internal(h.m_h)) { } @@ -888,13 +888,11 @@ namespace winstd if (this != std::addressof(h)) { if (h.m_h != invalid) { handle_type h_new = duplicate_internal(h.m_h); - if (h_new != invalid) { - if (m_h != invalid) - free_internal(); - m_h = h_new; - } else - assert(0); // Could not duplicate the handle + if (m_h != invalid) + free_internal(); + + m_h = h_new; } else { if (m_h != invalid) free_internal(); @@ -932,27 +930,24 @@ namespace winstd /// /// \param[in] h Object handle of existing object /// - /// \return - /// - true when duplication succeeds; - /// - false when duplication fails. In case of failure obtaining the extended error information is object type specific (for example: `GetLastError()`). - /// - bool attach_duplicated(_In_opt_ handle_type h) + void attach_duplicated(_In_opt_ handle_type h) { if (m_h != invalid) free_internal(); - return h != invalid ? (m_h = duplicate_internal(h)) != invalid : (m_h = invalid, true); + m_h = h != invalid ? duplicate_internal(h) : invalid; } protected: /// /// Abstract member function that must be implemented by child classes to do the actual object handle duplication. + /// On failure, it should throw appropriate exception describing the cause, rather than return an invalid handle. /// /// \param[in] h Object handle of existing object /// /// \return Duplicated object handle /// - virtual handle_type duplicate_internal(_In_ handle_type h) const noexcept = 0; + virtual handle_type duplicate_internal(_In_ handle_type h) const = 0; }; /// @} diff --git a/include/WinStd/Crypt.h b/include/WinStd/Crypt.h index 8847062c..d92d41f3 100644 --- a/include/WinStd/Crypt.h +++ b/include/WinStd/Crypt.h @@ -370,8 +370,9 @@ namespace winstd /// /// \sa [CertDuplicateCertificateContext function](https://msdn.microsoft.com/en-us/library/windows/desktop/aa376045.aspx) /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { + // As per doc, this only increases refcounter. Should never fail. return CertDuplicateCertificateContext(h); } }; @@ -415,10 +416,11 @@ namespace winstd /// /// \return Duplicated certificate chain context handle /// - /// \sa [CertDuplicateCertificateContext function](https://msdn.microsoft.com/en-us/library/windows/desktop/aa376045.aspx) + /// \sa [CertDuplicateCertificateChain function](https://learn.microsoft.com/en-us/windows/win32/api/wincrypt/nf-wincrypt-certduplicatecertificatechain) /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { + // As per doc, this only increases refcounter. Should never fail. return CertDuplicateCertificateChain(h); } }; @@ -531,10 +533,12 @@ namespace winstd /// /// \sa [CryptDuplicateHash function](https://msdn.microsoft.com/en-us/library/windows/desktop/aa379919.aspx) /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { handle_type hNew; - return CryptDuplicateHash(h, NULL, 0, &hNew) ? hNew : invalid; + if (CryptDuplicateHash(h, NULL, 0, &hNew)) + return hNew; + throw win_runtime_error("CryptDuplicateHash failed"); } }; @@ -652,10 +656,12 @@ namespace winstd /// /// \sa [CryptDuplicateKey function](https://msdn.microsoft.com/en-us/library/windows/desktop/aa379920.aspx) /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { handle_type hNew; - return CryptDuplicateKey(h, NULL, 0, &hNew) ? hNew : invalid; + if (CryptDuplicateKey(h, NULL, 0, &hNew)) + return hNew; + throw win_runtime_error("CryptDuplicateKey failed"); } }; diff --git a/include/WinStd/EAP.h b/include/WinStd/EAP.h index 91452f55..818d0ff9 100644 --- a/include/WinStd/EAP.h +++ b/include/WinStd/EAP.h @@ -271,13 +271,10 @@ namespace winstd dwLength = a.dwLength; if (a.dwLength) { BYTE *pValueNew = new BYTE[a.dwLength]; - if (pValueNew) { - if (pValue) - delete [] pValue; - memcpy(pValueNew, a.pValue, a.dwLength); - pValue = pValueNew; - } else - assert(0); // Could not allocate memory + if (pValue) + delete [] pValue; + memcpy(pValueNew, a.pValue, a.dwLength); + pValue = pValueNew; } else pValue = NULL; } @@ -472,16 +469,15 @@ namespace winstd /// /// Duplicates the EAP packet. /// - handle_type duplicate_internal(_In_ handle_type h) const noexcept override + handle_type duplicate_internal(_In_ handle_type h) const override { const WORD n = ntohs(*reinterpret_cast(h->Length)); handle_type h2 = static_cast(HeapAlloc(GetProcessHeap(), 0, n)); - if (h2 == NULL) { - SetLastError(ERROR_OUTOFMEMORY); - return NULL; + if (h2 != invalid) { + memcpy(h2, h, n); + return h2; } - memcpy(h2, h, n); - return h2; + throw std::bad_alloc(); } };