Commit Graph

327 Commits

Author SHA1 Message Date
bors[bot]
d0703f83db
Merge #1435
1435: Added example for multi priority executors rp2040 r=Dirbaio a=fakusb

I added an example for multiple priorities of tasks on rp2040 by adjusting [examples/nrf52840/src/bin/multiprio.rs](https://github.com/embassy-rs/embassy/blob/master/examples/nrf52840/src/bin/multiprio.rs) .

This needs https://github.com/embassy-rs/rp-pac/pull/2 , and this commit also adds the 6 new interrupt handlers for software interrupts to embassy-rs.

We might need to change the git path for rp-pac in [embassy-rp/Cargo.toml](https://github.com/embassy-rs/embassy/compare/master...fakusb:rp2040-multiprio-executor?expand=1#diff-47463ea358745927ecdb686f52feab816fde5d402a9628a136c116f34a802ab0)

Closes #1413

Co-authored-by: Fabian Kunze <fkunze@fkunze.de>
2023-05-08 16:59:07 +00:00
Fabian Kunze
87795cbca8 added example multi priority executors rp2040 2023-05-07 01:00:13 +02:00
pennae
db9b8eb88f rp/pio: make sure gpio() asserts are compiled out
we'll have to touch pio one way or other if the number of gpio pins ever
increases. may as well make sure an assert never fires until that happens.
2023-05-06 21:14:00 +02:00
pennae
b38d496d51 rp/pio: allow wrap-around program loading
execution wraps around after the end of instruction memory and wrapping
works with this, so we may as well allow program loading across this
boundary. could be useful for reusing chunks of instruction memory.
2023-05-06 21:08:20 +02:00
pennae
374c7513f9 rp/pio: mark exec_instr as unsafe
because it most definitely is.
2023-05-06 17:24:06 +02:00
pennae
bdcea84ca1 rp/pio: add sm batch operations
sometimes state machines need to be started, restarted, or synchronized
at exactly the same time. the current interface does not allow this but
the hardware does, so let's expose that.
2023-05-06 17:23:41 +02:00
pennae
8e4d65e163 rp/pio: configure state machines with Config struct
the many individual sets aren't very efficient, and almost no checks
were done to ensure that the configuration written to the hardware was
actually valid. this adresses both of these.
2023-05-06 17:23:41 +02:00
pennae
2873cb93ee rp/pio: mark pio_instr_util unsafe
none of these are safe. the x/y functions mangle the fifos, the set
functions require the state machine to be stopped to be in any way safe,
the out functions do both of those things at once. only the jump
instruction is marginally safe, but running this on an active program is
bound to cause problems.
2023-05-06 11:52:25 +02:00
pennae
37b460637d rp/pio: add set-pin-{values,dirs} convenience functions
these are needed a lot during state machine setup, it makes sense to
provide convenience functions for them.
2023-05-06 11:52:25 +02:00
pennae
41ec4170a5 rp/pio: add load_program, use_program
programs contain information we could pull from them directly and use to
validate other configuration of the state machine instead of asking the
user to pull them out and hand them to us bit by bit. unfortunately
programs do not specify how many in or out bits they use, so we can only
handle side-set and wrapping jumps like this. it's still something though.
2023-05-06 11:44:04 +02:00
pennae
5f7ef8bed0 rp/pio: only clear diag bits if they're set
otherwise we may lose a bit being raised after it was read, but before
it was cleared.
2023-05-05 19:08:16 +02:00
pennae
ed843b519b rp/pio: tighten variance of particle structs
all of these exist in 1:1 correspondence to their parent hal objects, so
let's make all of their lifetimes invariant.
2023-05-05 19:08:16 +02:00
pennae
09f078a1cc rp/pio: remove critical section in IrqFuture::poll
there's nothing this critical section protects against. both read and
write-to-clear are atomic and don't interfere with other irq futures,
only potentially with setting/clearing an irq flag from an arm core.
neither have ever been synchronized, and both have the same observable
effects under atomic writes and critical sections. (for both setting and
clearing an irq flag observable differences could only happen if the
set/clear happened after the poll read, but before the write. if it's a
clear we observe the same effects as sequencing the clear entirely after
the poll, and if it's a set we observe the same effects as sequencing
the set entirely before the poll)
2023-05-05 19:08:16 +02:00
pennae
8ebe6e5f20 rp/pio: drop Pio prefix from almost all names
it's only any good for PioPin because there it follows a pattern of gpio
pin alternate functions being named like that, everything else can just
as well be referred to as `pio::Thing`
2023-05-05 19:08:16 +02:00
pennae
c44c108db5 rp/pio: wrap sm rx, tx in structs and allow splitting
this *finally* allows sound implementions of bidirectional transfers
without blocking. the futures previously allowed only a single direction
to be active at any given time, and the dma transfers didn't take a
mutable reference and were thus unsound.
2023-05-03 13:00:52 +02:00
pennae
77f7830da3 rp/pio: move irq flag handling to own struct
this way we can share irq handling between state machines and common
without having to duplicate the methods. it also lets us give irq flag
access to places without having to dedicate a state machine or the
common instance to those places, which can be very useful to eg trigger
an event and wait for a confirmation using an irq wait object.
2023-05-03 13:00:08 +02:00
pennae
909a5fe2e5 rp/pio: split irqs from state machines
we can only have one active waiter for any given irq at any given time.
allowing waits for irqs on state machines bypasses this limitation and
causes lost events for all but the latest waiter for a given irq.
splitting this out also allows us to signal from state machines to other
parts of the application without monopolizing state machine access for
the irq wait, as would be necessary to make irq waiting sound.
2023-05-03 12:57:21 +02:00
pennae
486fe9e59d rp/pio: remove PioStateMachineInstance
move all methods into PioStateMachine instead. the huge trait wasn't
object-safe and thus didn't have any benefits whatsoever except for
making it *slightly* easier to write bounds for passing around state
machines. that would be much better solved with generics-less instances.
2023-05-03 11:25:58 +02:00
pennae
906d2b2db7 rp/pio: PioStateMachine{Instance, => ,Instance}
next step: get rid of the insance trait entirely
2023-05-03 11:25:58 +02:00
pennae
79985f0036 rp/pio: hide pio/sm numbers
nothing should care which number pio it is running on, and the state
machine index could always be extracted from type information.
2023-05-03 11:25:58 +02:00
pennae
6ad58f428a rp/pio: wrap PioPins from ref, like everything else
also store peripheral refs instead of a raw pin/bank number, like
everything else.
2023-05-03 11:25:53 +02:00
pennae
4ccb2bc95a rp/pio: add PioPin trait
pio can only access pins in bank 0, so it doesn't make sense to even
allow wrapping of other banks' pins.
2023-05-03 11:25:43 +02:00
pennae
17e78175a6 rp/pio: disable state machines on drop 2023-05-03 11:25:32 +02:00
pennae
62841dd5b9 rp/pio: revert pio pin funcsel to null on pio+sms drop
once all sharing owners of pio pins have been dropped we should reset
the pin for use by other hal objects. unfortunately this needs an atomic
state per pio block because PioCommon and all of the state machines
really do share ownership of any wrapped pins. only PioCommon can create
them, but all state machines can keep them alive. since state machines
can be moved to core1 we can't do reference counting in relaxed mode,
but we *can* do relaxed pin accounting (since only common and the final
drop can modify this).
2023-05-03 11:25:28 +02:00
pennae
1e8da91def rp/pio: make free_instr unsafe
we can't prove that some instruction memory is not used as long as state
machines are alive, and we can pass instance memory handles between
instances as well. mark free_instr unsafe, with documentation for this caveat.
2023-05-03 08:53:34 +02:00
bors[bot]
2afa08c923
Merge #1425
1425: rp pio, round 2 r=Dirbaio a=pennae

another round of bugfixes for pio, and some refactoring. in the end we'd like to make pio look like all the other modules and not expose traits that provide all the methods of a type, but put them onto the type itself. traits only make much sense, even if we added an AnyPio and merged the types for the member state machines (at the cost of at least a u8 per member of Pio).

Co-authored-by: pennae <github@quasiparticle.net>
2023-05-02 18:03:00 +00:00
pennae
7a36072a15 rp/pio: drop SmInstance{,Base}
these are just overly convoluted ways of writing down numbers.
2023-05-02 18:01:18 +02:00
pennae
a167c77d39 rp/pio: make PioCommon a struct
the PioCommon trait does not serve much of a purpose; there can be only
two implementations and they only differ in a few associated constants.
2023-05-02 18:01:18 +02:00
pennae
8839f3f62a rp/pio: PioInstance::split -> Pio::new
not requiring a PioInstance for splitting lets us split from a
PeripheralRef or borrowed PIO as well, mirroring every other peripheral
in embassy_rp. pio pins still have to be constructed from owned pin
instances for now.
2023-05-02 15:52:50 +02:00
pennae
ac111f40d8 rp/pio: fix PioPin::set_pull, set_schmitt comment 2023-05-02 15:46:22 +02:00
pennae
3229b5e809 rp/pio: remove PioPeripheral
merge into PioInstance instead. PioPeripheral was mostly a wrapper
around PioInstance anyway, and the way the wrapping was done required
PioInstanceBase<N> types where PIO{N} could've been used instead.
2023-05-02 15:46:21 +02:00
bors[bot]
b2047c4351
Merge #1423
1423: rp: fix gpio InputFuture and inefficiencies r=pennae a=pennae

InputFuture could not wait for edges without breaking due to a broken From impl, but even if the impl had been correct it would not have worked correctly because raw edge interrupts are sticky and must be cleared from software. also replace critical sections with atomic accesses, and do nvic setup only once.

Co-authored-by: pennae <github@quasiparticle.net>
2023-05-02 12:56:51 +00:00
pennae
849011b826 rp/gpio: set up gpio interrupts only once
doing this setup work repeatedly, on every wait, is unnecessary. with
nothing ever disabling the interrupt it is sufficient to enable it once
during device init and never touch it again.
2023-05-02 14:28:27 +02:00
pennae
6cec6fa09b rp/pio: don't use modify on shared registers
pio control registers are notionally shared between state machines as
well. state machine operations that change these registers must use
atomic accesses (or critical sections, which would be overkill).

notably PioPin::set_input_sync_bypass was even wrong, enabling the
bypass on a pin requires the corresponding bit to be set (not cleared).
the PioCommon function got it right.
2023-05-02 13:44:24 +02:00
pennae
0d224a00e1 rp/pio: avoid sm(SM_NO) indexing
accessing the current state machine is an extremely common operation
that shouldn't have its specifics repeated myriad times.
2023-05-02 13:44:24 +02:00
pennae
47ae9b7981 rp/pio: add funcsel values to PioInstance
makes code setting funcsels easier to read and should make it easier to
hook up more pio blocks, should they ever appear
2023-05-02 13:44:24 +02:00
pennae
54e695b1b2 rp/pio: fix dma
fixing the dma word size to 32 makes it impossible to implement any
peripheral that takes its data in smaller chunks, eg uart, spi, i2c,
ws2812, the list goes on.

compiler barriers were also not set correctly; we need a SeqCst barrier
before starting a transfer as well to avoid reordering of accesses into
a buffer after dma has started.
2023-05-02 10:56:37 +02:00
pennae
8fc92fdf62 rp/gpio: drop critical_section use
we don't need critical sections if we just use atomic access aliases.
2023-05-02 08:43:04 +02:00
pennae
c6424fdc11 gp/gpio: fix InputFuture edge waits
InputFuture did not use and check edge interrupts correctly.
InterruptTrigger should've checked for not 1,2,3,4 but 1,2,4,8 since the
inte fields are bitmasks, and not clearing INTR would have repeatedly
triggered edge interrupts early.
2023-05-02 08:43:04 +02:00
pennae
3c31236c10 rp: remove leftovers from #1414
forgot to remove these when they were no longer necessary or useful. oops.
2023-05-02 07:40:12 +02:00
bors[bot]
05c36e05f9
Merge #1414
1414: rp: report errors from buffered and dma uart receives r=Dirbaio a=pennae

neither of these reported errors so far, which is not ideal. add error reporting to both of them that matches the blocking error reporting as closely as is feasible, even allowing partial receives from buffered uarts before errors are reported where they would have been by the blocking code. dma transfers don't do this, if an errors applies to any byte in a transfer the entire transfer is nuked (though we probably could report how many bytes have been transferred).

Co-authored-by: pennae <github@quasiparticle.net>
2023-05-01 15:35:39 +00:00
pennae
b58b9ff390 rp/uart: report errors from dma receive 2023-05-01 15:36:53 +02:00
pennae
1d5adb8974 rp/uart: extract fifo draining from blocking_read
this will also be needed for dma operations.
2023-05-01 15:32:58 +02:00
pennae
be66e0f7ce rp/uart: make dma multicore-safe
running rx and tx on different cores could lead to hangs if the dmacr
register modifys run concurrently. this is bad.
2023-05-01 15:32:58 +02:00
pennae
861f49cfd4 rp/uart: report errors from buffered uart
this reports errors at the same location the blocking uart would, which
works out to being mostly exact (except in the case of overruns, where
one extra character is dropped). this is actually easier than going
nuclear in the case of errors and nuking both the buffer contents and
the rx fifo, both of which are things we'd have to do in addition to
what's added here, and neither are needed for correctness.
2023-05-01 15:32:58 +02:00
pennae
7ab9fe0522 rp/uart: extract common code from async and blocking buffered reads
once we add error propagation the common code will become even larger,
so it makes sense to move it out.
2023-05-01 15:24:03 +02:00
pennae
19588a9e6f rp/uart: rename state to buffered_state
we'll add a dma state soon as well.
2023-05-01 15:22:39 +02:00
pennae
1d2f6667df rp/uart: add set-break functions
sending break conditions is necessary to implement some protocols, and
the hardware supports this natively. we do have to make sure that we
don't assert a break condition while the uart is busy though, otherwise
the break may be inserted before the last character in the tx fifo.
2023-05-01 15:16:30 +02:00
pennae
7336b8cd88 rp/uart: add UartRx::new_blocking 2023-05-01 13:00:40 +02:00
pennae
f4ade6af8b rp/pio: write instr memory only from common
instruction memory is a shared resource. writing it only from PioCommon
clarifies this, and perhaps makes it more obvious that multiple state
machines can share the same instructions.

this also allows *freeing* of instruction memory to reprogram the
system, although this interface is not entirely safe yet. it's safe in
the sense rusts understands things, but state machines may misbehave if
their instruction memory is freed and rewritten while they are running.
fixing this is out of scope for now since it requires some larger
changes to how state machines are handled. the interface provided
currently is already unsafe in that it lets people execute instruction
memory that has never been written, so this isn't much of a drawback for now.
2023-05-01 12:58:57 +02:00