From 0d1f4ceb3904c4c82231adf98f0e84f37bc8d4ea Mon Sep 17 00:00:00 2001 From: Pedro Alves Date: Wed, 5 Apr 2017 19:21:36 +0100 Subject: -Wwrite-strings: Wrap PyGetSetDef for construction with string literals Unfortunately, PyGetSetDef's 'name' and 'doc' members are 'char *' instead of 'const char *', meaning that in order to list-initialize PyGetSetDef arrays using string literals requires writing explicit 'char *' casts. For example: static PyGetSetDef value_object_getset[] = { - { "address", valpy_get_address, NULL, "The address of the value.", + { (char *) "address", valpy_get_address, NULL, + (char *) "The address of the value.", NULL }, - { "is_optimized_out", valpy_get_is_optimized_out, NULL, - "Boolean telling whether the value is optimized " + { (char *) "is_optimized_out", valpy_get_is_optimized_out, NULL, + (char *) "Boolean telling whether the value is optimized " "out (i.e., not available).", NULL }, - { "type", valpy_get_type, NULL, "Type of the value.", NULL }, - { "dynamic_type", valpy_get_dynamic_type, NULL, - "Dynamic type of the value.", NULL }, - { "is_lazy", valpy_get_is_lazy, NULL, - "Boolean telling whether the value is lazy (not fetched yet\n\ + { (char *) "type", valpy_get_type, NULL, + (char *) "Type of the value.", NULL }, + { (char *) "dynamic_type", valpy_get_dynamic_type, NULL, + (char *) "Dynamic type of the value.", NULL }, + { (char *) "is_lazy", valpy_get_is_lazy, NULL, + (char *) "Boolean telling whether the value is lazy (not fetched yet\n\ from the inferior). A lazy value is fetched when needed, or when\n\ the \"fetch_lazy()\" method is called.", NULL }, {NULL} /* Sentinel */ We have ~20 such arrays, and I first wrote a patch that fixed all of them like that... It's not pretty... One way to make these a bit less ugly would be add a new macro that hides the casts, like: #define GDBPY_GSDEF(NAME, GET, SET, DOC, CLOSURE) \ { (char *) NAME, GET, SET, (char *) DOC, CLOSURE } and then use it like: static PyGetSetDef value_object_getset[] = { GDBPY_GSDEF ("address", valpy_get_address, NULL, "The address of the value.", NULL), GDBPY_GSDEF ("is_optimized_out", valpy_get_is_optimized_out, NULL, "Boolean telling whether the value is optimized ", NULL), {NULL} /* Sentinel */ }; But since we have C++11, which gives us constexpr and list initialization, I thought of a way that requires no changes where the arrays are initialized: We add a new type that extends PyGetSetDef (called gdb_PyGetSetDef), and add constexpr constructors that accept const 'name' and 'doc', and then list/aggregate initialization simply "calls" these matching constructors instead. I put "calls" in quotes, because given "constexpr", it's all done at compile time, and there's no overhead either in binary size or at run time. In fact, we get identical binaries, before/after this change. Unlike the fixes that fix some old Python API to match the API of more recent Python, this switches to using explicit "gdb_PyGetSetDef" everywhere, just to be clear that we are using our own version of it. gdb/ChangeLog: 2017-04-05 Pedro Alves * python/python-internal.h (gdb_PyGetSetDef): New type. * python/py-block.c (block_object_getset) (breakpoint_object_getset): Now a gdb_PyGetSetDef array. * python/py-event.c (event_object_getset) (finish_breakpoint_object_getset): Likewise. * python/py-inferior.c (inferior_object_getset): Likewise. * python/py-infthread.c (thread_object_getset): Likewise. * python/py-lazy-string.c (lazy_string_object_getset): Likewise. * python/py-linetable.c (linetable_entry_object_getset): Likewise. * python/py-objfile.c (objfile_getset): Likewise. * python/py-progspace.c (pspace_getset): Likewise. * python/py-record-btrace.c (btpy_insn_getset, btpy_call_getset): Likewise. * python/py-record.c (recpy_record_getset): Likewise. * python/py-symbol.c (symbol_object_getset): Likewise. * python/py-symtab.c (symtab_object_getset, sal_object_getset): Likewise. * python/py-type.c (type_object_getset, field_object_getset): Likewise. * python/py-value.c (value_object_getset): Likewise. --- gdb/ChangeLog | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) (limited to 'gdb/ChangeLog') diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 9430d3a..28557c2 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,5 +1,28 @@ 2017-04-05 Pedro Alves + * python/python-internal.h (gdb_PyGetSetDef): New type. + * python/py-block.c (block_object_getset) + (breakpoint_object_getset): Now a gdb_PyGetSetDef array. + * python/py-event.c (event_object_getset) + (finish_breakpoint_object_getset): Likewise. + * python/py-inferior.c (inferior_object_getset): Likewise. + * python/py-infthread.c (thread_object_getset): Likewise. + * python/py-lazy-string.c (lazy_string_object_getset): Likewise. + * python/py-linetable.c (linetable_entry_object_getset): Likewise. + * python/py-objfile.c (objfile_getset): Likewise. + * python/py-progspace.c (pspace_getset): Likewise. + * python/py-record-btrace.c (btpy_insn_getset, btpy_call_getset): + Likewise. + * python/py-record.c (recpy_record_getset): Likewise. + * python/py-symbol.c (symbol_object_getset): Likewise. + * python/py-symtab.c (symtab_object_getset, sal_object_getset): + Likewise. + * python/py-type.c (type_object_getset, field_object_getset): + Likewise. + * python/py-value.c (value_object_getset): Likewise. + +2017-04-05 Pedro Alves + * python/python-internal.h (gdb_PyObject_CallMethod) (gdb_PyErr_NewException, gdb_PySys_GetObject, gdb_PySys_SetPath): New functions. -- cgit v1.1