Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement expectHold #16

Open
ducky64 opened this issue Feb 8, 2019 · 2 comments
Open

Implement expectHold #16

ducky64 opened this issue Feb 8, 2019 · 2 comments

Comments

@ducky64
Copy link
Member

ducky64 commented Feb 8, 2019

This would check some signal holds for the duration of the enclosing timescope. Checks are made between timeslots (right before the clock edge) and handled by infrastructure. Motivating case is to check certain signals are held, specifying the held time with a timescope ("while this is happening, expect these signals to hold at x").

expectDuring (or similar) might also be a useful construct, where it expect some signal value during some period in time. Or perhaps more useful would be a wait-until-with-cap, which does the same but also advances time. Use case could be where a spec calls for some maximum latency without needing to be precise.

Random thoughts:

  • Alternate semantics could have checks be made between thread switches or between regions. But between timeslots (before the clock edge) is probably sufficiently robust since it ignores the effect of combinational testdriver logic.
  • It would be nice to be able to implement this as a library instead of in infrastructure, however there would need to be some way to detect the end of a timescope (not sure what that would look like, maybe getTimescope as a function for library developers that returns the current topmost timescope, which can be queried for open / closed status?). In this case, these checks would happen in the monitor region (or in a new, dedicated region).
@ducky64
Copy link
Member Author

ducky64 commented Feb 22, 2019

Results of today's discussion:

  • Proposed syntax is an expansion of the expect syntax: wire.expect(val).hold, which performs the immediate instantaneous expect and holds until the end of the timescope. Semantics are inclusive at start and exclusive at end (so it does not perform the check on the cycle the timescope ends, this allows waiting on a precondition for the expect.
  • One consideration is that this has to work with Regions. The proposed syntax is a delayed expect: wire.expect.hold.onRegion(region).do(val).
    • Note: ideally we would have wire.expect(val).hold.onRegion(region), but the expect(val) will evaluate instantaneously and cause problems. The above is kind of a least-worst solution, but ideas are welcome.
  • Order checking is unclear, but the simplest is that the expect executes every timeslot after the thread (or where it would be scheduled to execute, if it is blocked), and cross-thread-dependency checks happen accordingly. Unless anyone has better ideas, this is what will be implemented, though as Testers2 remains in alpha we can always change it.

@ducky64
Copy link
Member Author

ducky64 commented Feb 25, 2019

Putting down some more thoughts.

One question is whether expect-hold should be only level-sensitive or also driver-sensitive (as is the case with instantaneous expect - it checks the driver must be the same thread or a parent thread before the immediate child spawned). Note that driver sensitivity only matters for combinational paths within the testdriver code.

Driver sensitive

  • Implementation would largely be as described above, the expect would evaluate immediately, and at the end of the thread's execution slot for each timeslot the timescope is active.
  • This should indirectly ensure the value holds through all threads executing. The point is moot for threads executing before, and only parent threads execute after. Parent threads can't override-poke wires that child threads are expecting after the child thread spawns.
  • Main arguments for would be this providing consistent semantics as the regular expect while maintaining the level sensitivity property through the end of the timeslot. Might also disallow potentially unsafe interactions, which can be explicitly overridden with the use of regions.
  • On the other hand, this might also disallow potentially useful interactions. While the same thread can poke a wire that is expectHeld, a child thread cannot. But given that this is a disallowed interaction with regular expect, perhaps expectHold shouldn't allow this either.

Driver insensitive

  • Implementation would be slightly different, the expect would evaluate immediately, and at the end of each timeslot (after all threads have run).
  • Aside from the initial expect (which can be skipped), this can't throw a thread order exception. Also directly ensures the value holds right before a clock edge.
  • Main argument for would be that it's currently unclear what antipatterns the driver-sensitive path would prevent. But as the driver-sensitive path is more restrictive, I'm probably going to implement that first.

Other

  • For multiclock designs, consistent use of expectHold (instead of the instantaneous expect) with a timescope lasting one clock cycle can ensure that a signal lasts to the end of the specified clock, even if another thread clobbers the signal in a timeslot before the relevant clock edge. This may be more a library style thing, to encourage the use of expectHold where an instantaneous expect might not be robust to multiclock and extra timeslots between clock edges.

@ducky64 ducky64 added this to the 0.2 Moar features milestone Sep 16, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant