diff options
author | Armin Rigo <arigo@tunes.org> | 2014-01-20 15:18:55 +0100 |
---|---|---|
committer | Armin Rigo <arigo@tunes.org> | 2014-01-20 15:18:55 +0100 |
commit | ffe751a21307d6be3eaba9ed7eb2370d7a77c32c (patch) | |
tree | ad06ea3351637dec484bbf37f272cc58e50a2f02 | |
parent | 142f525c0112cc6494a4d678466436c0952e6303 (diff) | |
download | cffi-ffe751a21307d6be3eaba9ed7eb2370d7a77c32c.tar.gz |
Raise a NotImplementedError in one messy corner case
-rw-r--r-- | c/_cffi_backend.c | 8 | ||||
-rw-r--r-- | c/test_c.py | 10 |
2 files changed, 18 insertions, 0 deletions
diff --git a/c/_cffi_backend.c b/c/_cffi_backend.c index 7aefbd3..a1292c0 100644 --- a/c/_cffi_backend.c +++ b/c/_cffi_backend.c @@ -3817,6 +3817,14 @@ static PyObject *b_complete_struct_or_union(PyObject *self, PyObject *args) if (bits_already_occupied + fbitsize > 8 * ftype->ct_size) { /* it would not fit, we need to start at the next allowed position */ + if ((sflags & SF_PACKED) && + (bits_already_occupied & 7)) { + PyErr_Format(PyExc_NotImplementedError, + "with 'packed', gcc would compile field " + "'%s.%s' to reuse some bits in the previous " + "field", ct->ct_name, PyText_AS_UTF8(fname)); + goto error; + } field_offset_bytes += falign; assert(boffset < field_offset_bytes * 8); boffset = field_offset_bytes * 8; diff --git a/c/test_c.py b/c/test_c.py index 005a089..09d0a13 100644 --- a/c/test_c.py +++ b/c/test_c.py @@ -3177,6 +3177,16 @@ def test_packed(): assert sizeof(BStruct) == sizeof(BLong) + sizeof(BChar) + sizeof(BShort) assert alignof(BStruct) == 1 +def test_packed_with_bitfields(): + BLong = new_primitive_type("long") + BChar = new_primitive_type("char") + BStruct = new_struct_type("struct foo") + py.test.raises(NotImplementedError, + complete_struct_or_union, + BStruct, [('a1', BLong, 30), + ('a2', BChar, 5)], + None, -1, -1, 8) # SF_PACKED==8 + def test_version(): # this test is here mostly for PyPy assert __version__ == "0.8" |