Fix handling of padding after empty sequences
This commit is contained in:
parent
8bf8994fbf
commit
ac55fd2f4a
@ -119,6 +119,7 @@ def generate_getsize_cdr(fields: list[Field]) -> tuple[CDRSerSize, int]:
|
|||||||
else:
|
else:
|
||||||
anext = align(subdesc)
|
anext = align(subdesc)
|
||||||
if aligned < anext:
|
if aligned < anext:
|
||||||
|
lines.append(f' if len(message.{fieldname}):')
|
||||||
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
||||||
aligned = anext
|
aligned = anext
|
||||||
lines.append(f' pos += len(message.{fieldname}) * {SIZEMAP[subdesc.args]}')
|
lines.append(f' pos += len(message.{fieldname}) * {SIZEMAP[subdesc.args]}')
|
||||||
@ -272,6 +273,7 @@ def generate_serialize_cdr(fields: list[Field], endianess: str) -> CDRSer:
|
|||||||
if (endianess == 'le') != (sys.byteorder == 'little'):
|
if (endianess == 'le') != (sys.byteorder == 'little'):
|
||||||
lines.append(' val = val.byteswap()')
|
lines.append(' val = val.byteswap()')
|
||||||
if aligned < (anext := align(subdesc)):
|
if aligned < (anext := align(subdesc)):
|
||||||
|
lines.append(' if size:')
|
||||||
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
||||||
lines.append(' rawdata[pos:pos + size] = val.view(numpy.uint8)')
|
lines.append(' rawdata[pos:pos + size] = val.view(numpy.uint8)')
|
||||||
lines.append(' pos += size')
|
lines.append(' pos += size')
|
||||||
@ -417,6 +419,7 @@ def generate_deserialize_cdr(fields: list[Field], endianess: str) -> CDRDeser:
|
|||||||
else:
|
else:
|
||||||
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
||||||
if aligned < (anext := align(subdesc)):
|
if aligned < (anext := align(subdesc)):
|
||||||
|
lines.append(' if size:')
|
||||||
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
lines.append(f' pos = (pos + {anext} - 1) & -{anext}')
|
||||||
lines.append(
|
lines.append(
|
||||||
f' val = numpy.frombuffer(rawdata, '
|
f' val = numpy.frombuffer(rawdata, '
|
||||||
|
|||||||
@ -151,6 +151,7 @@ def generate_ros1_to_cdr(
|
|||||||
aligned = 1
|
aligned = 1
|
||||||
else:
|
else:
|
||||||
if aligned < (anext := align(subdesc)):
|
if aligned < (anext := align(subdesc)):
|
||||||
|
lines.append(' if size:')
|
||||||
lines.append(f' opos = (opos + {anext} - 1) & -{anext}')
|
lines.append(f' opos = (opos + {anext} - 1) & -{anext}')
|
||||||
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
||||||
if copy:
|
if copy:
|
||||||
@ -304,6 +305,7 @@ def generate_cdr_to_ros1(
|
|||||||
aligned = 1
|
aligned = 1
|
||||||
else:
|
else:
|
||||||
if aligned < (anext := align(subdesc)):
|
if aligned < (anext := align(subdesc)):
|
||||||
|
lines.append(' if size:')
|
||||||
lines.append(f' ipos = (ipos + {anext} - 1) & -{anext}')
|
lines.append(f' ipos = (ipos + {anext} - 1) & -{anext}')
|
||||||
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
lines.append(f' length = size * {SIZEMAP[subdesc.args]}')
|
||||||
if copy:
|
if copy:
|
||||||
|
|||||||
@ -167,6 +167,16 @@ test_msgs/msg/dynamic_64_s[] seq_msg_d6s
|
|||||||
test_msgs/msg/dynamic_s_64[] seq_msg_ds6
|
test_msgs/msg/dynamic_s_64[] seq_msg_ds6
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
SU64_B = """
|
||||||
|
uint64[] su64
|
||||||
|
bool b
|
||||||
|
"""
|
||||||
|
|
||||||
|
SU64_U64 = """
|
||||||
|
uint64[] su64
|
||||||
|
uint64 u64
|
||||||
|
"""
|
||||||
|
|
||||||
|
|
||||||
@pytest.fixture()
|
@pytest.fixture()
|
||||||
def _comparable() -> Generator[None, None, None]:
|
def _comparable() -> Generator[None, None, None]:
|
||||||
@ -411,3 +421,43 @@ def test_cdr_to_ros1() -> None:
|
|||||||
header = std_msgs__msg__Header(stamp=builtin_interfaces__msg__Time(42, 666), frame_id='frame')
|
header = std_msgs__msg__Header(stamp=builtin_interfaces__msg__Time(42, 666), frame_id='frame')
|
||||||
msg_ros = cdr_to_ros1(serialize_cdr(header, 'std_msgs/msg/Header'), 'std_msgs/msg/Header')
|
msg_ros = cdr_to_ros1(serialize_cdr(header, 'std_msgs/msg/Header'), 'std_msgs/msg/Header')
|
||||||
assert msg_ros == b'\x00\x00\x00\x00*\x00\x00\x00\x9a\x02\x00\x00\x05\x00\x00\x00frame'
|
assert msg_ros == b'\x00\x00\x00\x00*\x00\x00\x00\x9a\x02\x00\x00\x05\x00\x00\x00frame'
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.usefixtures('_comparable')
|
||||||
|
def test_padding_empty_sequence() -> None:
|
||||||
|
"""Test empty sequences do not add item padding."""
|
||||||
|
# pylint: disable=protected-access
|
||||||
|
register_types(dict(get_types_from_msg(SU64_B, 'test_msgs/msg/su64_b')))
|
||||||
|
|
||||||
|
su64_b = get_msgdef('test_msgs/msg/su64_b').cls
|
||||||
|
msg = su64_b(numpy.array([], dtype=numpy.uint64), True)
|
||||||
|
|
||||||
|
cdr = serialize_cdr(msg, msg.__msgtype__)
|
||||||
|
assert cdr[4:] == b'\x00\x00\x00\x00\x01'
|
||||||
|
|
||||||
|
ros1 = cdr_to_ros1(cdr, msg.__msgtype__)
|
||||||
|
assert ros1 == cdr[4:]
|
||||||
|
|
||||||
|
assert ros1_to_cdr(ros1, msg.__msgtype__) == cdr
|
||||||
|
|
||||||
|
assert deserialize_cdr(cdr, msg.__msgtype__) == msg
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.mark.usefixtures('_comparable')
|
||||||
|
def test_align_after_empty_sequence() -> None:
|
||||||
|
"""Test alignment after empty sequences."""
|
||||||
|
# pylint: disable=protected-access
|
||||||
|
register_types(dict(get_types_from_msg(SU64_U64, 'test_msgs/msg/su64_u64')))
|
||||||
|
|
||||||
|
su64_b = get_msgdef('test_msgs/msg/su64_u64').cls
|
||||||
|
msg = su64_b(numpy.array([], dtype=numpy.uint64), 42)
|
||||||
|
|
||||||
|
cdr = serialize_cdr(msg, msg.__msgtype__)
|
||||||
|
assert cdr[4:] == b'\x00\x00\x00\x00\x00\x00\x00\x00\x2a\x00\x00\x00\x00\x00\x00\x00'
|
||||||
|
|
||||||
|
ros1 = cdr_to_ros1(cdr, msg.__msgtype__)
|
||||||
|
assert ros1 == b'\x00\x00\x00\x00\x2a\x00\x00\x00\x00\x00\x00\x00'
|
||||||
|
|
||||||
|
assert ros1_to_cdr(ros1, msg.__msgtype__) == cdr
|
||||||
|
|
||||||
|
assert deserialize_cdr(cdr, msg.__msgtype__) == msg
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user