Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
108 changes: 108 additions & 0 deletions docs/dev/stdlib-worksheets/08-12-02-map.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
# §8.12.2 — actor `map`

Source: ASAM OpenSCENARIO DSL 2.2.0, `domain-model` §8.12.2 (Tables 186–214).
Landed in slice 43e. Target chunk: `kDomainMap` in `frontends/dsl/src/stdlib.cpp`.

`map` is the top-level actor holding the abstract road network. §8.12.2 prints
its parameters as one table, then its 18 methods as `extend map:` **code blocks**
(unusually — most of §8 is tables only), then its 12 modifiers as tables.

Everything the actor references — `route`, `junction`, `road`, `lane`,
`lane_section`, `crossing`, the point/path/trajectory structs and the road enums —
landed in 43c. The two traffic-light fields land with §8.15 in the same PR.

## Fields (Table 187)

| Field | Type | Mandatory | ⚠ |
| --- | --- | --- | --- |
| `map_file` | `string` | no | |
| `routes` | `list of route` | yes | |
| `junctions` | `list of junction` | yes | |
| `driving_rule` | `driving_rule` | yes | field name equals its type name — allowed, cf. `hitch_receiver.hitch_type` (§8.7.13) |
| `traffic_light_groups` | `list of traffic_light_group` | no | §8.15.4.2; §8.15.7 prints this pair as a separate `extend map:` block |
| `traffic_light_control` | `list of traffic_light_cycle` | no | §8.15.6.2; same |

§8.15.7 spells the last two as an `extend map:` block rather than as rows of
Table 187. Since both chapters land in one slice they are declared inline on the
actor, which is the same program — §7.3.15 makes a type the union of its
declarations either way.

## Methods (§8.12.2.1, prototypes printed as code)

All are declared `is undefined`: they are queries a runtime answers, and the
library only has to give them a signature to check against.

| § | Method | Signature | ⚠ |
| --- | --- | --- | --- |
| .1.1 | `odr_to_route_point` | `(road_id: string, lane_id: string, s: length, t: length) -> route_point` | `lane_id` is documented optional; the language has no optional marker (§7.3.11 covers it) |
| .1.2 | `xyz_to_route_point` | `(x: length, y: length, z: length) -> route_point` | |
| .1.3 | `route_point_to_xyz` | `(route_point: route_point) -> xyz_point` | parameter name equals its type name |
| .1.4 | `outer_side` | `() -> side_left_right` | |
| .1.5 | `inner_side` | `() -> side_left_right` | |
| .1.6 | `create_route` | `(routes: list of route, connect_points_by: connect_route_points, legal_route: bool) -> compound_route` | Code 75/76 call it with one argument; defaults are `waypoint` / `true` per Table 191 but the prototype declares none, so none is declared |
| .1.7 | `create_route_point` | `(route: route, s: length, t: length) -> route_point` | |
| .1.8 | `create_xyz_point` | `(x: length, y: length, z: length) -> xyz_point` | |
| .1.9 | `create_odr_point` | `(road_id: string, lane_id: string, s: length, t: length) -> odr_point` | |
| .1.10 | `create_path` | `(points: list of pose_3d, interpolation: path_interpolation) -> path` | |
| .1.11 | `create_path_odr_points` | `(points: list of odr_point, interpolation: path_interpolation, on_road_network: bool) -> path` | |
| .1.12 | `create_path_route_points` | `(points: list of route_point, interpolation: path_interpolation, on_road_network: bool) -> path` | |
| .1.13 | `create_trajectory` | `(points: list of pose_3d, time_stamps: list of time, interpolation: path_interpolation) -> trajectory` | prototype prints `list of time,interpolation` with no space — typography, not syntax |
| .1.14 | `create_trajectory_odr_points` | `(points: list of odr_point, time_stamps: list of time, interpolation: path_interpolation, on_road_network: bool) -> trajectory` | |
| .1.15 | `create_trajectory_route_points` | `(points: list of route_point, time_stamps: list of time, interpolation: path_interpolation, on_road_network: bool) -> trajectory` | Code 82 omits `on_road_network` |
| .1.16 | `resolve_relative_path` | `(relative_path: relative_path, reference: physical_object, transform: relative_transform) -> path` | parameter name equals its type name |
| .1.17 | `resolve_relative_trajectory` | `(relative_trajectory: relative_trajectory, reference: physical_object, transform: relative_transform) -> trajectory` | same |
| .1.18 | `get_map_file` | `() -> string` | |

## Modifiers (§8.12.2.2, tables only)

Declared in the §7.2.2.2.9 prefixed form `modifier map.<name>:` — an actor's
modifier is never `modifier <name> of map`, because §7.3.12.2's `of` names a
scenario or an action (43b finding).

| § | Modifier | Fields |
| --- | --- | --- |
| .2.1 | `number_of_lanes` | `route: route`, `num_of_lanes: uint`, `lane_type: lane_type`, `lane_use: lane_use`, `directionality: directionality` |
| .2.2 | `routes_are_in_sequence` | `preceding: route`, `succeeding: route`, `road: road` |
| .2.3 | `roads_follow_in_junction` | `junction: junction`, `in_road: road`, `out_road: road`, `direction: junction_direction`, `clockwise_count: uint`, `number_of_roads: uint`, `in_lane: lane`, `out_lane: lane`, `junction_route: route`, `resulting_route: route` |
| .2.4 | `routes_overlap` | `route1: route`, `route2: route`, `overlap_kind: route_overlap_kind` |
| .2.5 | `lane_side` | `lane1: lane`, `side: side_left_right`, `lane2: lane`, `count: uint`, `lane_section: lane_section` |
| .2.6 | `compound_lane_side` | `lane1: compound_lane`, `side: side_left_right`, `lane2: compound_lane`, `count: uint`, `route: route` |
| .2.7 | `end_lane` | `lane: lane` |
| .2.8 | `start_lane` | `lane: lane` |
| .2.9 | `crossing_connects` | `crossing: crossing`, `start_lane: lane`, `end_lane: lane`, `start_s_coord: length`, `start_angle: angle` |
| .2.10 | `routes_are_opposite` | `route1: route`, `route2: route`, `containing_road: road`, `lateral_overlap: lateral_overlap_kind` |
| .2.11 | `set_map_file` | `file: string` |
| .2.12 | `set_traffic_lights_control_file` | `file: string` |

## ⚠ Notes carried into the library

1. **Three modifier field names collide with type names in the same
namespace** — `lane_type`, `lane_use`, `directionality`, `lane_section`,
`crossing`, `junction`, `route`, `road`, `lane`. A member name and a type name
live in different lookup spaces, so this checks cleanly; it is worth knowing
because it reads like a collision. Pinned by test.
2. **`map.end_lane` / `map.start_lane` each take one field named `lane` of type
`lane`** — the narrowest instance of the above.
3. **Code 78/79's `map.create_path_odr_points(..., smooth, true)` passes a bare
enum literal.** `smooth` is unique to `path_interpolation`, so no `type!literal`
prefix is needed here — unlike `driving`, which §7.3.3 requires be written
`lane_type!driving` (43c finding).
4. **Table 205's `clockwise_count` documents `1`=left … `4`=U-turn** for a
four-way junction. That is runtime semantics, not a type constraint; the field
is a plain `uint`.
5. **§8.12.2.1.6's syntax examples (Code 75/76) call `create_route` with a single
list argument.** The declared prototype has three parameters and prints no
defaults, so the library declares three. A caller supplying one argument is a
caller-side concern (§7.2.2.5.2 positional arguments), not a library one.
6. **These twelve modifiers cannot yet be applied — issue #100.** Writing
`my_map.lane_side(a, side_left_right!left, b, 1, ls)` reports "unknown
modifier 'lane_side'". The cause is in the resolver, not in the library: the
parser keeps the whole qualified behavior name, so the declaration
`modifier map.lane_side` creates a type named `map.lane_side`, while
`check_modifier_application` looks up the bare `lane_side`. Unassociated
modifiers apply fine. The defect predates this chapter — §8.7's
`stationary_object.location` and `vehicle.tow_trailer` have it too — and it is
what §8.9's movement modifiers (p8-s3, #46) will need fixed first.
`TheMapModifiersAreAssociatedWithTheMap` pins the declarations, which are
well-formed; nothing pins the broken application, because that behaviour is
not the one we want to keep.
95 changes: 95 additions & 0 deletions docs/dev/stdlib-worksheets/08-15-traffic-lights.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
# §8.15 — traffic lights

Source: ASAM OpenSCENARIO DSL 2.2.0, `domain-model` §8.15 (Tables 301–343).
Landed in slice 43h. Target chunk: `kDomainTrafficLights` in
`frontends/dsl/src/stdlib.cpp`.

§8.15 is three enums and a bulb struct (§8.15.2), a semantic-state enum
(§8.15.3), the traffic-light and group structs with their methods (§8.15.4), the
stop line (§8.15.5), phase and cycle (§8.15.6), the two `map` fields (§8.15.7),
the controller actor (§8.15.8) and seven actions (§8.15.9). Everything is
printed as tables except the four method prototypes.

## Enums

| § | Enum | Members | ⚠ |
| --- | --- | --- | --- |
| .2.1 | `bulb_icon` | 45 values, `unknown` first — see the chunk for the full list in table order | the comment column maps each to an OpenDRIVE signal type; not carried, it is documentation |
| .2.2 | `bulb_color` | `unknown, red, yellow, green, blue, white` | every member also exists in `color` (§8.7.15) → callers need `bulb_color!red` (§7.3.3) |
| .2.3 | `bulb_state` | `unknown, is_off, is_on, is_flashing` | |
| .3.1 | `semantic_traffic_light_state` | `off, stop, attention, caution, stop_attention, go, go_exclusive, non_functional` | `off` is not a reserved word (§7.2.1.5.1 makes keywords positional), so it needs no escaping |
| .5.1 | `stop_line_marking` | `none, solid, broken` | `none` also exists in `hitch_type` (§8.7.18) and `directionality` (§8.12.6) |

## Structs

| § | Struct | Members | ⚠ |
| --- | --- | --- | --- |
| .2.4 | `traffic_light_bulb` | `map_id: string`, `icon: bulb_icon`, `color: bulb_color`, `icon_positive: bool`, `state: bulb_state` | Table 308 lists the first four as parameters, Table 309 lists `state` as a state variable; both become fields (43b rule) |
| .4.1 | `traffic_light` | `map_id: string`, `bulbs: list of traffic_light_bulb`, `pose: pose_3d`, `height: length`, `width: length`, `group: traffic_light_group` | forward reference to `traffic_light_group`, declared below it |
| .4.2 | `traffic_light_group` | `map_id: string`, `bulbs: list of traffic_light_bulb`, `traffic_lights: list of traffic_light`, `cycle: traffic_light_cycle` | mutually recursive with `traffic_light`; `cycle` forward-references §8.15.6.2 |
| .5.2 | `traffic_light_stop_line` **inherits `route_element`** | `traffic_light_group: traffic_light_group`, `route: route`, `rightmost_lane: uint`, `leftmost_lane: uint`, `offset: length`, `secondary_stop_offset: length`, `primary_stop_line_marking: stop_line_marking`, `secondary_stop_line_marking: stop_line_marking` | two field names equal their type names |
| .6.1 | `traffic_light_phase` | `group: traffic_light_group`, `bulbs_state: list of traffic_light_bulb`, `duration: time` | |
| .6.2 | `traffic_light_cycle` | `phases: list of traffic_light_phase`, `synchronization_group_id: uint`, `start_offset: time` | |

## Methods (§8.15.4.1.1, §8.15.4.2.1 — prototypes printed as code)

| Owner | Method | Signature |
| --- | --- | --- |
| `traffic_light` | `state_equal` | `(bulbs: list of traffic_light_bulb) -> bool` |
| `traffic_light` | `semantic_state_to_state` | `(state: semantic_traffic_light_state) -> list of traffic_light_bulb` |
| `traffic_light` | `state_to_semantic_state` | `(bulbs: list of traffic_light_bulb) -> semantic_traffic_light_state` |
| `traffic_light_group` | `state_equal` | `(bulbs: list of traffic_light_bulb) -> bool` |

⚠ §8.15.4.2.1's prototype for the **group's** `state_equal` prints
`extend traffic_light:`, not `extend traffic_light_group:`. The surrounding prose,
the section heading and Table 319 all say the method belongs to
`traffic_light_group`, so the prototype's receiver is a copy-paste slip and the
method is declared on the group. This is the one place in the chapter where the
printed code is not followed; see note 1 below.

## Actor and actions

`actor traffic_light_controller inherits osc_actor` (§8.15.8.1, Table 329).

The seven §8.15.9 actions are declared on it. §8.8.1 defines only
`action_for_environment` and `action_for_movable_object` as intermediate bases,
so these inherit `osc_actor.osc_action` directly rather than inventing a third
intermediate. All are instantaneous except `play_cycles`; action ending is
runtime semantics and is not expressible in a declaration.

| § | Action | Fields |
| --- | --- | --- |
| .9.1.1 | `set_bulb_state` | `traffic_light: traffic_light`, `bulb_color: bulb_color`, `bulb_kind: bulb_icon`, `bulb_state: bulb_state`, `sync: bool` |
| .9.2.1 | `set_state` | `traffic_light: traffic_light`, `state: list of bulb_state`, `sync: bool` |
| .9.3.1 | `set_semantic_state` | `traffic_light: traffic_light`, `state: semantic_traffic_light_state`, `sync: bool` |
| .9.4.1 | `set_group_bulb_state` | `traffic_light: traffic_light`, `bulb_color: bulb_color`, `bulb_kind: bulb_icon`, `bulb_state: bulb_state`, `sync: bool` ⚠ |
| .9.5.1 | `set_group_state` | `group: traffic_light_group`, `state: list of bulb_state`, `sync: bool` |
| .9.6.1 | `set_group_semantic_state` | `traffic_light_group: traffic_light_group`, `state: semantic_traffic_light_state`, `sync: bool` |
| .9.7.1 | `play_cycles` | `cycles: list of traffic_light_cycle` |

## ⚠ Notes carried into the library

1. **Table 337 (`set_group_bulb_state`) names its first parameter
`traffic_light` of type `traffic_light`, while its description says "The
traffic light group affected by the action".** The parameter table is the
normative surface and it is what a conforming scenario would be written
against, so the printed name and type are carried verbatim and the
inconsistency is recorded here. This follows the same rule as the §8.14.1.3
conversion factors (ADR-0029): what the standard prints wins over what it
evidently meant. Contrast §8.15.4.2.1, where the *prose, the heading and the
table* agree against a single line of printed code — there the code loses.
The distinction is which surface the rest of the chapter corroborates.
2. **`set_group_state` names the parameter `group`, `set_group_semantic_state`
names it `traffic_light_group`.** Both carried as printed.
3. **`traffic_light` and `traffic_light_group` are mutually recursive** through
`traffic_light.group` and `traffic_light_group.traffic_lights`. The resolver's
declare pass registers every type before the link pass reads any field type,
so declaration order is free; they are declared in chapter order.
4. **Table 313's `state` for `traffic_light` does not exist.** A traffic light has
no state of its own — its state is the state of its bulbs, which is why
§8.15.4.1.1 provides `state_equal` and the two conversion methods instead. The
§8.15.10 examples read state only through those methods.
5. **§8.15.10's examples write `stop_line.road`,** but Table 323 declares the
field as `route`. The table is normative and the example is illustrative; the
field is `route`. An author following the example gets an "unknown member"
diagnostic, which is the correct outcome.
33 changes: 33 additions & 0 deletions docs/dev/stdlib-worksheets/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# Standard-library translation worksheets

Working notes for the bundled ASAM OpenSCENARIO DSL §8 standard library
(`frontends/dsl/src/stdlib.cpp`, ADR-0029).

Most of §8 is printed as *parameter tables*, not as DSL code. Turning a chapter
into library source is therefore a translation, one table row at a time, and the
expensive part is reading the chapter rather than writing the declarations. A
worksheet captures that reading once: one line per declaration, in the order the
chapter prints them, with the resulting DSL spelling and a `⚠` note wherever the
printed text needs a judgement call.

The worksheets are committed for two reasons:

- they are the auditable record of the translation — a reviewer can check a
worksheet row against the specification without re-deriving the mapping from
the library source; and
- they are the recovery path. Re-reading a chapter costs far more than reading
its worksheet.

They are developer notes, not user documentation: `docs/user-guide/` describes
what the frontend does, and `docs/roadmap/coverage/osc-dsl-coverage.md` records
what of the standard is covered. A worksheet only records how one chapter was
translated.

| Worksheet | Chapter | Landed in |
| --- | --- | --- |
| [`08-12-02-map.md`](08-12-02-map.md) | §8.12.2 actor `map` | 43e |
| [`08-15-traffic-lights.md`](08-15-traffic-lights.md) | §8.15 traffic lights | 43h |

Chapters translated before the worksheet discipline existed (§8.7, §8.10, §8.11,
§8.12.3–§8.12.41, §8.13, §8.14) have no worksheet; their findings are recorded in
the ADR and in `frontends/dsl/README.md`.
5 changes: 3 additions & 2 deletions docs/roadmap/coverage/osc-dsl-coverage.md
Original file line number Diff line number Diff line change
Expand Up @@ -110,9 +110,10 @@ included, so a conforming implementation and Scena agree.
| `stdtypes` — string methods | §8.13 | In | p7-s5 | **Landed**: declared on the `string` primitive. §8.13 heads them under the types sub-module and then names the `std` namespace; declared under the section they appear in, and nothing observable turns on it — a method on a primitive is reached through a value, never through a namespace |
| `std` — physical-object actors, structs and enums | §8.7 | In | p7-s5 | **Landed** (`dsl_stdlib_test.cpp`): the `osc_actor` → `physical_object` → `movable_object` → `traffic_participant` → `vehicle` → `trailer` chain with `stationary_object`, `person` and `animal`; `bounding_box`, `axle`, `hitch_receiver`, `hitch_coupler`; all 11 enums including the backward-compatibility spellings (`truck = heavy_truck`, `fire = fire_brigade`, …) sharing their replacement's value; the §8.7.6.1 measurement methods. §8.7.26 (traffic-participant groups) is non-normative and excluded |
| `std` — road abstraction classes | §8.12.3–§8.12.41 | In | p7-s5 | **Landed** (`dsl_stdlib_test.cpp`): the `route` → `route_element` hierarchy with `road`, `lane_section`, `lane`, `crossing`, the four point structs, `path`/`trajectory` and their relative variants, `compound_route`/`compound_lane`, `junction`, and 15 enums. The road-dependent `physical_object` and `traffic_participant` methods arrive here as `extend` blocks, which is how the standard prints their prototypes |
| `std` — the `map` actor | §8.12.2 | In | p7-s5 | Lands with the next slice of #43; §8.12.2's method and modifier surface is larger than the rest of §8.12 combined |
| `std` — the `map` actor | §8.12.2 | In | p7-s5 | **Landed** (`dsl_stdlib_test.cpp`): the top-level road-network actor with its six fields, its 18 conversion and creation methods, and its 12 search-space modifiers. *Applying* an actor-associated modifier is issue #100 — the parser keeps the actor prefix in the declared name, so the application site cannot find it; the declarations are well-formed and are pinned. Worksheet: `docs/dev/stdlib-worksheets/08-12-02-map.md` |
| `std` — action hierarchy and the environment | §8.8.1, §8.10, §8.11 | In | p7-s5 | **Landed** (`dsl_stdlib_test.cpp`): `osc_action` with `action_for_environment` and `action_for_movable_object`; the `environment` actor with `local_to_unix_time`; the `weather`/`air`/`precipitation`/`wind`/`fog`/`clouds`/`celestial_light_source` structs; the seven §8.11 environment actions. Their *execution* stays Post (see the actor table) — the DSL environment actions are checked, not run, in v0.0.1 |
| `std` — movement actions and modifiers, traffic lights, the `map` actor | §8.3, §8.5, §8.8.2–§8.9, §8.12.2, §8.15 | In | p7-s5 | Lands with the remaining slices of #43 |
| `std` — traffic lights | §8.15 | In | p7-s5 | **Landed** (`dsl_stdlib_test.cpp`): `traffic_light_bulb`, `traffic_light` and `traffic_light_group` with their state methods, `traffic_light_stop_line` (a `route_element`), `traffic_light_phase`/`traffic_light_cycle`, the `traffic_light_controller` actor and its seven §8.15.9 actions, and 5 enums. Their *execution* stays Post (see the actor table). Worksheet: `docs/dev/stdlib-worksheets/08-15-traffic-lights.md` |
| `std` — movement actions and modifiers | §8.3, §8.5, §8.8.2–§8.9 | In | p7-s5 | Lands with the remaining slices of #43 |

Coverage of the individual §8 declarations: all physical types and units
(§8.14.1), compound structs (§8.14.2), string methods (§8.13), all actors
Expand Down
Loading
Loading