Hum, to give more context to the discussion, the two discussed macros are documented this way:
#ifndef Py_LIMITED_API /* Safely decref `op` and set `op` to `op2`. * * As in case of Py_CLEAR "the obvious" code can be deadly: * * Py_DECREF(op); * op = op2; * * The safe way is: * * Py_SETREF(op, op2); * * That arranges to set `op` to `op2` _before_ decref'ing, so that any code * triggered as a side-effect of `op` getting torn down no longer believes * `op` points to a valid object. * * Py_XSETREF is a variant of Py_SETREF that uses Py_XDECREF instead of * Py_DECREF. */ #define Py_SETREF(op, op2) \ do { \ PyObject *_py_tmp = (PyObject *)(op); \ (op) = (op2); \ Py_DECREF(_py_tmp); \ } while (0) #define Py_XSETREF(op, op2) \ do { \ PyObject *_py_tmp = (PyObject *)(op); \ (op) = (op2); \ Py_XDECREF(_py_tmp); \ } while (0) #endif /* ifndef Py_LIMITED_API */ Victor 2017-11-09 13:22 GMT+01:00 Raymond Hettinger <raymond.hettin...@gmail.com>: > >> On Nov 9, 2017, at 2:44 AM, Serhiy Storchaka <storch...@gmail.com> wrote: >> >> If the problem is with naming, what names do you prefer? This already was >> bikeshedded (I insisted on discussing names before introducing the macros), >> but may now you have better ideas? > > It didn't really seem like a bad idea until after you swept through the code > with 200+ applications of the macro and I saw how unclear the results were. > Even code that I wrote myself is now harder for me to grok (for example, the > macro was applied 17 times to already correct code in itertools). > > We used to employ a somewhat plain coding style that was easy to walk > through, but the following examples seem opaque. I find it takes practice to > look at any one of these and say that it is unequivocally correct (were the > function error return arguments handled correctly, are the typecasts proper, > at what point can a reentrant call occur, which is the source operand and > which is the destination, is the macro using either of the operands twice, is > the destination operand an allowable lvalue, do I need to decref the source > operand afterwards, etc): > > Py_SETREF(((PyHeapTypeObject*)type)->ht_name, value) > Py_SETREF(newconst, PyFrozenSet_New(newconst)); > Py_XSETREF(c->u->u_private, s->v.ClassDef.name); > Py_SETREF(*p, t); > Py_XSETREF(self->lineno, PyTuple_GET_ITEM(info, 1)); > Py_SETREF(entry->path, PyUnicode_EncodeFSDefault(entry->path)); > Py_XSETREF(self->checker, PyObject_GetAttrString(ob, "_check_retval_")); > Py_XSETREF(fut->fut_source_tb, > _PyObject_CallNoArg(traceback_extract_stack)); > > Stylistically, all of these seem awkward and I think there is more to it than > just the name. I'm not sure it is wise to pass complex inputs into a > two-argument macro that makes an assignment and has a conditional refcount > side-effect. Even now, one of the above looks to me like it might not be > correct. > > Probably, we're the wrong people to be talking about this. The proposal is > to make these macros part of the official API so that it starts to appear in > source code everywhere. The question isn't whether the above makes sense to > you and me; instead, it is whether other people can make heads or tails out > the above examples. As a result of making the macros official, will the > Python world have a net increase in complexity or decrease in complexity? > > My personal experience with the macros hasn't been positive. Perhaps > everyone else thinks it's fine. If so, I won't stand in your way. > > > Raymond > > _______________________________________________ > Python-Dev mailing list > Python-Dev@python.org > https://mail.python.org/mailman/listinfo/python-dev > Unsubscribe: > https://mail.python.org/mailman/options/python-dev/victor.stinner%40gmail.com _______________________________________________ Python-Dev mailing list Python-Dev@python.org https://mail.python.org/mailman/listinfo/python-dev Unsubscribe: https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com