From 5988a4413964bcb376651e7322894c0050ebd238 Mon Sep 17 00:00:00 2001 From: Mark Wooding Date: Sun, 24 Nov 2019 15:11:46 +0000 Subject: [PATCH] catacomb.c, util.c: Publish `KERR_...' symbols as negative numbers. They're supposed to be, but the existing `setconstants' machinery isn't clever enough to do this properly. Fixing this involves adding a flags word to `struct nameval' to identify which constants should really be signed, and some fancy footwork to convert unsigned integers back to negative values without upsetting C. --- catacomb-python.h | 3 ++- catacomb.c | 6 ++++-- util.c | 12 ++++++------ 3 files changed, 12 insertions(+), 9 deletions(-) diff --git a/catacomb-python.h b/catacomb-python.h index c272b53..b1120fa 100644 --- a/catacomb-python.h +++ b/catacomb-python.h @@ -233,7 +233,8 @@ MODULES(DO) return (d); \ } -struct nameval { const char *name; unsigned long value; }; +struct nameval { const char *name; unsigned f; unsigned long value; }; +#define CF_SIGNED 1u extern void setconstants(PyObject *, const struct nameval *); extern PyObject *mexp_common(PyObject *, PyObject *, size_t, diff --git a/catacomb.c b/catacomb.c index d7b3dc7..edb0c4a 100644 --- a/catacomb.c +++ b/catacomb.c @@ -31,7 +31,8 @@ /*----- Main code ---------------------------------------------------------*/ static const struct nameval consts[] = { -#define C(x) { #x, x } +#define CF(f, x) { #x, f, x } +#define C(x) { #x, 0, x } C(FTY_PRIME), C(FTY_BINARY), C(PGEN_PASS), C(PGEN_FAIL), C(PGEN_BEGIN), C(PGEN_TRY), C(PGEN_DONE), C(PGEN_ABORT), @@ -51,10 +52,11 @@ static const struct nameval consts[] = { C(ED25519_KEYSZ), C(ED25519_PUBSZ), C(ED25519_SIGSZ), C(ED25519_MAXPERSOSZ), C(ED448_KEYSZ), C(ED448_PUBSZ), C(ED448_SIGSZ), C(ED448_MAXPERSOSZ), -#define ENTRY(tag, val, str) C(KERR_##tag), +#define ENTRY(tag, val, str) CF(CF_SIGNED, KERR_##tag), KEY_ERRORS(ENTRY) #undef ENTRY #undef C +#undef CF { 0 } }; diff --git a/util.c b/util.c index d613a7a..9332c8b 100644 --- a/util.c +++ b/util.c @@ -280,14 +280,14 @@ PyTypeObject *inittype(PyTypeObject *tyskel, PyTypeObject *meta) void setconstants(PyObject *mod, const struct nameval *c) { PyObject *x; + unsigned long u; while (c->name) { - if (c->value > LONG_MAX) - x = PyLong_FromUnsignedLong(c->value); - else - x = PyInt_FromLong(c->value); - PyModule_AddObject(mod, (/*unconst*/ char *)c->name, x); - c++; + u = c->value; + if (u <= LONG_MAX) x = PyInt_FromLong(u); + else if (c->f&CF_SIGNED) x = PyInt_FromLong(-1 - (long)(ULONG_MAX - u)); + else x = PyLong_FromUnsignedLong(u); + PyModule_AddObject(mod, (/*unconst*/ char *)c->name, x); c++; } } -- 2.11.0