Skip to content

bpo-33738: Fix macros which contradict PEP 384#7477

Merged
ned-deily merged 2 commits intopython:masterfrom
pyside:master
Jun 9, 2018
Merged

bpo-33738: Fix macros which contradict PEP 384#7477
ned-deily merged 2 commits intopython:masterfrom
pyside:master

Conversation

@ctismer
Copy link
Copy Markdown
Contributor

@ctismer ctismer commented Jun 7, 2018

During development of the limited API support for PySide,
we saw an error in a macro that accessed a type field.

This patch fixes the 7 errors in the Python headers.
Macros which were not written as capitals were implemented
as function.

To do the necessary analysis again, a script was included that
parses all headers and looks for "->tp_" in sections which can
be reached with active limited API.

It is easily possible to call this script as a test.

Error listing:

../../Include/objimpl.h:243
#define PyObject_IS_GC(o) (PyType_IS_GC(Py_TYPE(o)) &&
(Py_TYPE(o)->tp_is_gc == NULL || Py_TYPE(o)->tp_is_gc(o)))
Action: commented only

../../Include/objimpl.h:362
#define PyType_SUPPORTS_WEAKREFS(t) ((t)->tp_weaklistoffset > 0)
Action: commented only

../../Include/objimpl.h:364
#define PyObject_GET_WEAKREFS_LISTPTR(o)
((PyObject **) (((char *) (o)) + Py_TYPE(o)->tp_weaklistoffset))
Action: commented only

../../Include/pyerrors.h:143
#define PyExceptionClass_Name(x)
((char )(((PyTypeObject)(x))->tp_name))
Action: implemented function

../../Include/abstract.h:593
#define PyIter_Check(obj)
((obj)->ob_type->tp_iternext != NULL &&
(obj)->ob_type->tp_iternext != &_PyObject_NextNotImplemented)
Action: implemented function

../../Include/abstract.h:713
#define PyIndex_Check(obj)
((obj)->ob_type->tp_as_number != NULL &&
(obj)->ob_type->tp_as_number->nb_index != NULL)
Action: implemented function

../../Include/abstract.h:924
#define PySequence_ITEM(o, i)
( Py_TYPE(o)->tp_as_sequence->sq_item(o, i) )
Action: commented only

https://bugs.python.org/issue33738

During development of the limited API support for PySide,
we saw an error in a macro that accessed a type field.

This patch fixes the 7 errors in the Python headers.
Macros which were not written as capitals were implemented
as function.

To do the necessary analysis again, a script was included that
parses all headers and looks for "->tp_" in serctions which can
be reached with active limited API.

It is easily possible to call this script as a test.

Error listing:

../../Include/objimpl.h:243
#define PyObject_IS_GC(o) (PyType_IS_GC(Py_TYPE(o)) && \
    (Py_TYPE(o)->tp_is_gc == NULL || Py_TYPE(o)->tp_is_gc(o)))
Action: commented only

../../Include/objimpl.h:362
#define PyType_SUPPORTS_WEAKREFS(t) ((t)->tp_weaklistoffset > 0)
Action: commented only

../../Include/objimpl.h:364
#define PyObject_GET_WEAKREFS_LISTPTR(o) \
    ((PyObject **) (((char *) (o)) + Py_TYPE(o)->tp_weaklistoffset))
Action: commented only

../../Include/pyerrors.h:143
#define PyExceptionClass_Name(x) \
     ((char *)(((PyTypeObject*)(x))->tp_name))
Action: implemented function

../../Include/abstract.h:593
#define PyIter_Check(obj) \
    ((obj)->ob_type->tp_iternext != NULL && \
     (obj)->ob_type->tp_iternext != &_PyObject_NextNotImplemented)
Action: implemented function

../../Include/abstract.h:713
#define PyIndex_Check(obj)                              \
    ((obj)->ob_type->tp_as_number != NULL &&            \
     (obj)->ob_type->tp_as_number->nb_index != NULL)
Action: implemented function

../../Include/abstract.h:924
#define PySequence_ITEM(o, i)\
    ( Py_TYPE(o)->tp_as_sequence->sq_item(o, i) )
Action: commented only
During development of the limited API support for PySide,
we saw an error in a macro that accessed a type field.

This patch fixes the 7 errors in the Python headers.
Macros which were not written as capitals were implemented
as function.

To do the necessary analysis again, a script was included that
parses all headers and looks for "->tp_" in sections which can
be reached with active limited API.

It is easily possible to call this script as a test.

Error listing:

../../Include/objimpl.h:243
    (Py_TYPE(o)->tp_is_gc == NULL || Py_TYPE(o)->tp_is_gc(o)))
Action: commented only

../../Include/objimpl.h:362
Action: commented only

../../Include/objimpl.h:364
    ((PyObject **) (((char *) (o)) + Py_TYPE(o)->tp_weaklistoffset))
Action: commented only

../../Include/pyerrors.h:143
     ((char *)(((PyTypeObject*)(x))->tp_name))
Action: implemented function

../../Include/abstract.h:593
    ((obj)->ob_type->tp_iternext != NULL && \
     (obj)->ob_type->tp_iternext != &_PyObject_NextNotImplemented)
Action: implemented function

../../Include/abstract.h:713
    ((obj)->ob_type->tp_as_number != NULL &&            \
     (obj)->ob_type->tp_as_number->nb_index != NULL)
Action: implemented function

../../Include/abstract.h:924
    ( Py_TYPE(o)->tp_as_sequence->sq_item(o, i) )
Action: commented only
@ctismer ctismer requested a review from a team as a code owner June 7, 2018 17:17
@ctismer
Copy link
Copy Markdown
Contributor Author

ctismer commented Jun 7, 2018

Can I squash these commits, or do I need to re-send the whole thing? (Or leave it in pieces)

@zware
Copy link
Copy Markdown
Member

zware commented Jun 7, 2018

They'll be squashed at merge time, don't worry about it until then :)

@ned-deily
Copy link
Copy Markdown
Member

LGTM, although this is not an area of my expertise. Since we are getting very close to 3.7.0rc1 and it would be good to have this resolved, I'm going to merge this to master now so it gets some buildbot exposure. If anyone has any review comments, get them in real soon! Otherwise, I will backport and merge to 3.7 within the next 24 hours.

@ned-deily ned-deily merged commit ea62ce7 into python:master Jun 9, 2018
@ned-deily
Copy link
Copy Markdown
Member

Looks like the change introduces a compile warning. Should that be addressed?:

..\Objects\exceptions.c(349): warning C4090: 'return': different 'const' qualifiers [D:\buildarea\3.x.ware-win81-release\build\PCbuild\pythoncore.vcxproj]

http://buildbot.python.org/all/#/builders/12/builds/960

@ctismer
Copy link
Copy Markdown
Contributor Author

ctismer commented Jun 9, 2018

Yes it should be fixed. I was not aware that Python has const-ness, already.
I have amended my patch with "const char *". But since it is merged, I don't see the change.

@ned-deily
Copy link
Copy Markdown
Member

@ctismer Thanks. The best thing would be to open a new PR but, if you can paste the diff here, I'll take care of it.

Comment thread Include/abstract.h
((obj)->ob_type->tp_iternext != NULL && \
(obj)->ob_type->tp_iternext != &_PyObject_NextNotImplemented)
#else
PyAPI_FUNC(int) PyIter_Check(PyObject*);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nitpick: it would look better if add a space between PyObject and *.

Comment thread Include/pyerrors.h
#define PyExceptionClass_Name(x) \
((char *)(((PyTypeObject*)(x))->tp_name))
#else
PyAPI_FUNC(char *) PyExceptionClass_Name(PyObject*);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should return const char *. And please add a space between PyObject and *.

Copy link
Copy Markdown
Contributor Author

@ctismer ctismer Jun 10, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will do.
My style is a bit spoiled by Qt's C++ style. They write "func(PyObject *self)"
but "func(PyObject*)".
I am preparing a diff as Ned said, but I can also repeat the PR.

Comment thread Include/pyerrors.h

#ifndef Py_LIMITED_API
#define PyExceptionClass_Name(x) \
((char *)(((PyTypeObject*)(x))->tp_name))
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually (char *) is not needed. But it should be documented in What's New that PyExceptionClass_Name() now returns const char * instead of char * (there were similar breaking changes in 3.7).

Comment thread Objects/exceptions.c
}

#undef PyExceptionClass_Name
char *
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Return const char *.

Comment thread Objects/abstract.c
}

#undef PyIter_Check
int PyIter_Check(PyObject *obj)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nitpick: Break a line between int and PyIter_Check.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, will do. Although all other #undef's are without newline.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Eeek, misunderstood!
Sure, you wanted a line after int!
I must have been very tired...

@serhiy-storchaka
Copy link
Copy Markdown
Member

Seems I forgot to press the "Submit review" button after adding comments.

@ctismer
Copy link
Copy Markdown
Contributor Author

ctismer commented Jun 10, 2018

Ok, I hope I got all changes right. Doing a new PR.

@serhiy-storchaka
Copy link
Copy Markdown
Member

Since this PR has been merged, my comments except the one about the result of PyExceptionClass_Name are outdated. They where just style nitpicks. And I have opened a separate issue for the latter.

@tekknolagi
Copy link
Copy Markdown
Contributor

Was this ever backported to Python 3.7?

@ned-deily
Copy link
Copy Markdown
Member

@tekknolagi No, I don't think they were ever backported to 3.7. See the discussion on the still open bug issue (https://bugs.python.org/issue33738) which is also the place for comments. In any case, with the upcoming release of 3.7.8, 3.7 has moved to security-fix mode, precluding changes like this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

7 participants