Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d904e899 authored by Henri Chataing's avatar Henri Chataing Committed by Gerrit Code Review
Browse files

Merge "pdl: Use correct semantic for padding field"

parents 3017d433 8d582a2e
Loading
Loading
Loading
Loading
+5 −3
Original line number Diff line number Diff line
@@ -563,11 +563,13 @@ packet CRCedBrew {
> padding_field:\
>    `_padding_` `[` [INTEGER](#integer) `]`

A *\_padding\_* field adds a number of **octet** of padding.
A *\_padding\_* field immediately following an array field pads the array field with `0`s to the
specified number of **octets**.

```
packet Padded {
  _padding_[1] // 1 octet/8bit of padding
packet PaddedCoffee {
  additions: CoffeeAddition[],
  _padding_[100]
}
```

+19 −1
Original line number Diff line number Diff line
@@ -177,6 +177,8 @@ class FieldParser:
        """Parse the selected array field."""
        array_size = core.get_array_field_size(field)
        element_width = core.get_array_element_size(field)
        padded_size = field.padded_size

        if element_width:
            if element_width % 8 != 0:
                raise Exception('Array element size is not a multiple of 8')
@@ -202,6 +204,12 @@ class FieldParser:
        if field.size_modifier and size:
            self.append_(f"{size} = {size} - {field.size_modifier}")

        # Parse from the padded array if padding is present.
        if padded_size:
            self.check_size_(padded_size)
            self.append_(f"remaining_span = span[{padded_size}:]")
            self.append_(f"span = span[:{padded_size}]")

        # The element width is not known, but the array full octet size
        # is known by size field. Parse elements item by item as a vector.
        if element_width is None and size is not None:
@@ -263,6 +271,10 @@ class FieldParser:
            if size is not None:
                self.append_(f"span = span[{size}:]")

        # Drop the padding
        if padded_size:
            self.append_(f"span = remaining_span")

    def parse_bit_field_(self, field: ast.Field):
        """Parse the selected field as a bit field.
        The field is added to the current chunk. When a byte boundary
@@ -346,7 +358,7 @@ class FieldParser:

        if self.shift != 0:
            raise Exception('Padding field does not start on an octet boundary')
        self.offset += field.width
        self.offset += field.size

    def parse_payload_field_(self, field: Union[ast.BodyField, ast.PayloadField]):
        """Parse body and payload fields."""
@@ -535,6 +547,9 @@ class FieldSerializer:

    def serialize_array_field_(self, field: ast.ArrayField):
        """Serialize the selected array field."""
        if field.padded_size:
            self.append_(f"_{field.id}_start = len(_span)")

        if field.width == 8:
            self.append_(f"_span.extend(self.{field.id})")
        else:
@@ -543,6 +558,9 @@ class FieldSerializer:
            self.serialize_array_element_(field)
            self.unindent_()

        if field.padded_size:
            self.append_(f"_span.extend([0] * ({field.padded_size} - len(_span) + _{field.id}_start))")

    def serialize_bit_field_(self, field: ast.Field):
        """Serialize the selected field as a bit field.
        The field is added to the current chunk. When a byte boundary
+2 −1
Original line number Diff line number Diff line
@@ -59,7 +59,7 @@ class ChecksumField(Field):

@node('padding_field')
class PaddingField(Field):
    width: int
    size: int


@node('size_field')
@@ -109,6 +109,7 @@ class ArrayField(Field):
    type_id: Optional[str]
    size_modifier: Optional[str]
    size: Optional[int]
    padded_size: Optional[int] = field(init=False, default=None)

    @property
    def type(self) -> Optional['Declaration']:
+8 −3
Original line number Diff line number Diff line
@@ -2,7 +2,7 @@ from typing import Optional, List, Dict, Union, Tuple
from .ast import *


def desugar_field_(field: Field, constraints: Dict[str, Constraint]) -> List[Field]:
def desugar_field_(field: Field, previous: Field, constraints: Dict[str, Constraint]) -> List[Field]:
    """Inline group and constrained fields.
    Constrained fields are transformed into fixed fields.
    Group fields are inlined and recursively desugared."""
@@ -13,6 +13,10 @@ def desugar_field_(field: Field, constraints: Dict[str, Constraint]) -> List[Fie
        fixed.parent = field.parent
        return [fixed]

    elif isinstance(field, PaddingField):
        previous.padded_size = field.size
        return []

    elif isinstance(field, TypedefField) and field.id in constraints:
        tag_id = constraints[field.id].tag_id
        fixed = FixedField(kind='fixed_field', loc=field.loc, enum_id=field.type_id, tag_id=tag_id)
@@ -24,7 +28,8 @@ def desugar_field_(field: Field, constraints: Dict[str, Constraint]) -> List[Fie
        constraints = dict([(c.id, c) for c in field.constraints])
        fields = []
        for f in group.fields:
            fields.extend(desugar_field_(f, constraints))
            fields.extend(desugar_field_(f, previous, constraints))
            previous = f
        return fields

    else:
@@ -45,7 +50,7 @@ def desugar(file: File):
        if isinstance(d, (PacketDeclaration, StructDeclaration)):
            fields = []
            for f in d.fields:
                fields.extend(desugar_field_(f, {}))
                fields.extend(desugar_field_(f, fields[-1] if len(fields) > 0 else None, {}))
            d.fields = fields

        declarations.append(d)
+1 −1
Original line number Diff line number Diff line
@@ -73,7 +73,7 @@ pub enum Field {
    #[serde(rename = "checksum_field")]
    Checksum { loc: SourceRange, field_id: String },
    #[serde(rename = "padding_field")]
    Padding { loc: SourceRange, width: usize },
    Padding { loc: SourceRange, size: usize },
    #[serde(rename = "size_field")]
    Size { loc: SourceRange, field_id: String, width: usize },
    #[serde(rename = "count_field")]
Loading