As part of a game engine I am writing in cython, one of the challenges I am facing is creating a consistent interface for error handling that works at the C and python levels of my code. I am interested in maintaining two interfaces to the engine; one that operates at the C-level on structs with no involvement of the python interpreter, and one that operates on python "cdef classes" that indirectly wrap these structs.
Given that raising python Error objects would invoke the GIL, I am interested in using error codes within my C-level functions. These error codes would then be mapped to a corresponding error message string for display on the python wrapper function, which can freely use the GIL.
At the moment, I am planning to store the error codes in a single massive enum alongside a corresponding dict mapping error codes to error strings. This raises the following questions for me:
Should error codes be named per-struct? For example, I have multiple structs that represent common data structures such as
vector
andslot map
. As these are dynamically sized containers, allocations could fail on growing these structures. Would it be better to use generic error codes likeERROR_OUT_OF_MEMORY
to represent such failures, or use struct-specific codes likeERROR_ITEM_VECTOR_OUT_OF_MEMORY
,ERROR_ITEM_SLOT_MAP_OUT_OF_MEMORY
, etc? Another example would be individual graphical shader versus shader program compilation, where I could either use a singleERROR_COMPILE
code or anERROR_SHADER_COMPILE
andERROR_PROGRAM_COMPILE
codes.How should the error code <-> error message mapping be stored? On one hand, I could have a global dict in a header file that maps a unique code to a unique corresponding error message in a centralized location. Alternatively, I could write the strings directly in the python code, which might allow some added flexibility (e.g. using format strings to provide context-specific error messages).
Any help would be appreciated.