Skip to content

Commit

Permalink
gh-93442: Make C++ version of _Py_CAST work with 0/NULL. (#93500)
Browse files Browse the repository at this point in the history
Add C++ overloads for _Py_CAST_impl() to handle 0/NULL.  This will allow
C++ extensions that pass 0 or NULL to macros using _Py_CAST() to
continue to compile.  Without this, you get an error like:

    invalid ‘static_cast’ from type ‘int’ to type ‘_object*’

The modern way to use a NULL value in C++ is to use nullptr.  However,
we want to not break extensions that do things the old way.

Co-authored-by: serge-sans-paille
  • Loading branch information
nascheme committed Jun 5, 2022
1 parent 3d647e7 commit 8bcc3fa
Show file tree
Hide file tree
Showing 3 changed files with 21 additions and 0 deletions.
14 changes: 14 additions & 0 deletions Include/pyport.h
Expand Up @@ -24,9 +24,23 @@
//
// The type argument must not be a constant type.
#ifdef __cplusplus
#include <cstddef>
# define _Py_STATIC_CAST(type, expr) static_cast<type>(expr)
extern "C++" {
namespace {
template <typename type>
inline type _Py_CAST_impl(long int ptr) {
return reinterpret_cast<type>(ptr);
}
template <typename type>
inline type _Py_CAST_impl(int ptr) {
return reinterpret_cast<type>(ptr);
}
template <typename type>
inline type _Py_CAST_impl(std::nullptr_t) {
return static_cast<type>(nullptr);
}

template <typename type, typename expr_type>
inline type _Py_CAST_impl(expr_type *expr) {
return reinterpret_cast<type>(expr);
Expand Down
4 changes: 4 additions & 0 deletions Lib/test/_testcppext.cpp
Expand Up @@ -74,6 +74,10 @@ test_api_casts(PyObject *Py_UNUSED(module), PyObject *Py_UNUSED(args))
Py_INCREF(strong_ref);
Py_DECREF(strong_ref);

// gh-93442: Pass 0 as NULL for PyObject*
Py_XINCREF(0);
Py_XDECREF(0);

Py_DECREF(obj);
Py_RETURN_NONE;
}
Expand Down
@@ -0,0 +1,3 @@
Add C++ overloads for _Py_CAST_impl() to handle 0/NULL. This will allow C++
extensions that pass 0 or NULL to macros using _Py_CAST() to continue to
compile.

0 comments on commit 8bcc3fa

Please sign in to comment.