led1! ( ? -- ) set LED1 (blue)
led2! ( ? -- ) set LED2 (green)
led3! ( ? -- ) set LED3 (red)
led1@ ( -- ? ) get LED1 (blue)
led2@ ( -- ? ) get LED2 (green)
led3@ ( -- ? ) get LED3 (red)
switch1? ( -- ? ) get switch1, closed=TRUE
switch2? ( -- ? ) get switch2, closed=TRUE
switch3? ( -- ? ) get switch3, closed=TRUE
dport! ( n -- ) set the digital output port (D0=bit0 .. D15=bit15).
dport@ ( -- n ) get the digital input/output port (D0=bit0 .. D15=bit15).
dpin! ( n a -- ) set the digital output port pin (D0=0 .. D15=15)
dpin@ ( a -- n ) get the digital input/output port pin
dmod ( u a -- ) set the pin mode: 0 in, 1 in pull-up, 2 in pull-down, 3 out push pull, 4 out open drain,
5 out push pull PWM, 6 input capture, 7 output compare, 8 I2C
EXTImod ( u a -- ) set for pin a (D2, D4, D7, D10) the EXTI mode u: 0 rising, 1 falling, 2 both edges, 3 none
EXTIwait ( u a -- ) wait for EXTI interrupt on pin a (D2, D4, D7, D10), timeout u in [ms]
pwmpin! ( u a -- ) set the digital output port pin a (D3=3, D6=6, D9=9) to a PWM value u (0..1000). Default frequency is 1 kHz, TIMER1
pwmprescale ( u -- ) Set the PWM prescale for TIMER1. 32 kHz / prescale, default 32 -> PWM frequency 1 kHz
ICOCprescale ( u -- ) set the input capture / output compare prescale for TIMER2. default 32 -> 32 MHz / 32 = 1 MHz, timer resolution 1 us
ICOCperiod! ( u -- ) set the input capture / output compare (TIMER2) period. default $FFFFFFFF (4'294'967'295).
When the up counter reaches the period, the counter is set to 0.
For prescale 32 the maximum time is about 1 h 11 m
ICOCcount! ( -- u ) set the input capture / output compare counter for TIMER2
ICOCcount@ ( u -- ) get the input capture / output compare counter for TIMER2
ICOCstart ( -- ) start the ICOC period
ICOCstop ( -- ) stop the ICOC period
OCmod ( u a -- ) set for pin a (D0, D1, D5) the Output Compare mode u: 0 frozen, 1 active level on match, 2 inactive level on match,
3 toggle on match, 4 forced active, 5 forced inactive
OCstart ( u a -- ) start the output compare mode for pin a with pulse u
OCstop ( a -- ) stop output compare for pin a
ICstart ( u -- ) start input capture u: 0 rising edge, 1 falling edge, 2 both edges
ICstop ( -- ) stop input capture
waitperiod ( -- ) wait for the end of the TIMER2 period
OCwait ( a -- ) wait for the end of output capture on pin a
ICwait ( u -- u ) wait for the end of input capture with timeout u, returns counter u
apin@ ( a -- u ) get the analog input port pin (A0 .. A5). Returns a 12 bit value (0..4095)
vref@ ( -- u ) get the Vref voltage in mV (rather the VDDA)
vbat@ ( -- u ) get the Vbat voltage in mV
CPUtemp@ ( -- u ) get CPU temperature in degree Celsius
I2Cput ( a # u -- ) put a message with length u (count in bytes) from buffer at a to the I2C slave device u
I2Cget ( a # u -- ) get a message with length u from I2C slave device to buffer at a
I2Cputget ( a #1 #2 u -- ) put a message with length #1 from buffer at a to the I2C slave device u
and get a message with length #2 from device to buffer at a
SPIget ( a # -- ) get a message with length # from SPI slave device to buffer at a
SPIput ( a # -- ) put a message with length # from buffer at a to the SPI slave device
SPIputget ( a #1 #2 -- ) put a message with length #1 from buffer at a to the SPI slave device
and get a message with length #2 from device to buffer at a
SPImutex ( -- a ) get the SPI mutex address
dport! and dport@ set and get all 16 digital pins (D0 to D15) at once. You have to press the SW1 push button til D0 is set to cancel the operation.
3 0 dmod \ set D0 to Output 3 1 dmod \ set D1 to Output 3 2 dmod \ set D2 to Output 3 3 dmod \ set D3 to Output 3 4 dmod \ set D4 to Output 3 5 dmod \ set D5 to Output 3 6 dmod \ set D6 to Output 3 7 dmod \ set D7 to Output
: left ( -- )
7 0 do
dport@ shl dport!
100 osDelay drop
loop
;
|
: right ( -- )
7 0 do
dport@ shr dport!
100 osDelay drop
loop
;
|
: knightrider ( -- )
1 dport!
begin
left right
switch1? \ or key?
until
0 dport!
;
|
: left ( -- )
7 0 do
1 i dpin!
100 osDelay drop
0 i dpin!
loop
;
|
: right ( -- )
8 1 do
1 8 i - dpin!
100 osDelay drop
0 8 i - dpin!
loop
;
|
: knigthrider ( -- )
begin
left right
switch1?
until
0 0 dpin!
;
|
apin@ ( a -- u ) returns the ADC value (12 bit, 0 .. 4095) from one of the analog pins A0 to A5 (0 .. 5). Here I use the A0 to control the delay.
: left ( -- )
7 0 do
1 i dpin!
0 apin@ 10 / osDelay drop \ delay depends on A0
0 i dpin!
loop
;
|
: right ( -- )
8 1 do
1 8 i - dpin!
0 apin@ 10 / osDelay drop \ delay depends on A0
0 8 i - dpin!
loop
;
|
left or right word takes about 125 us, the knightrider loop about 50 us (no osDelay). Pretty fast for my opinion.
CH1 yellow: D0 pin
pwmprescale from 32 kHz (value 1) down to 0.5 Hz (64000).
5 3 dmod \ set D3 to PWM
: pwm ( -- )
begin
0 apin@ 4 / 3 pwmpin!
10 osDelay drop
switch1?
until
;
: period ( -- )
5000000 ICOCperiod! \ 5 s period
ICOCstart
begin
waitperiod
cr .time
key? until
key drop
;
: oc-toggle ( -- )
5000000 ICOCperiod! \ 5 s period
ICOCstart
3 0 OCmod 1000000 0 OCstart \ toggle D0 after 1 s
3 1 OCmod 2000000 1 OCstart \ toggle D1 after 2 s
3 5 OCmod 3000000 5 OCstart \ toggle D5 after 3 s
begin
waitperiod
cr .time
key? until
key drop
;
When you abort (hit any key) the program, the timer still runs and controls the port pins. To stop the port pins:
0 OCstop 1 OCstop 5 OCstopOr change the prescale to make it faster or slower:
1 ICOCprescale
: ic-test ( -- )
6 2 dmod \ input capture on A2
ICOCstart
2 ICstart \ both edges
ICOCcount@ ( -- count )
begin
2000 \ 2 s timeout
ICwait ( -- old-capture capture )
cr
dup 0= if
." timeout" drop
else
dup rot ( -- capture capture old-capture )
- 1000 / . ." ms"
then
key? until
key drop
drop
ICstop
;
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| SWITCH1 | PC4 (PC13) | (WKUP2) |
| SWITCH2 | PD0 | |
| SWITCH3 | PD1 |
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| LD1 | PB5 | |
| LD2 | PB0 | |
| LD3 | PB1 | |
| Neopixel | PC12 | D8 |
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| UART_TX | PB6 | USART1_TX |
| UART_RX | PB7 | USART1_RX |
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| FLASH_NCS | PD3 | QUADSPI_BK1_NCS |
| FLASH_IO0 | PB9 | QUADSPI_BK1_IO0 |
| FLASH_IO1 | PD5 | QUADSPI_BK1_IO1 |
| FLASH_IO2 | PD6 | QUADSPI_BK1_IO2 |
| FLASH_IO3 | PD7 | QUADSPI_BK1_IO3 |
| FLASH_SCLK | PA3 | QUADSPI_BK1_SCLK |
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| SWITCH1 | PC12 | WKUP3 |
| Signal name | STM32WB55 pin | Comment |
|---|---|---|
| LD1 | PB5 | |
| LD2 | PB0 | |
| LD3 | PA4 | |
| Neopixel | PC12 | D6 |
| Description | Dongle | Function | Feather | Micro-SD | JTAG 14pin |
|---|---|---|---|---|---|
| GND | CN1.1 | GND | JP1.13 GND | GND | 5, 7, 11 |
| NRST | CN1.2 | RES | JP1.16 RST | 12 | |
| PA13 | CN1.3 | SWDIO | - | 4 | |
| PA14 | CN1.4 | SWDCLK | - | 6 | |
| PB3 | CN1.5 | SWO | A4? | 8 | |
| 3V3 | CN1.6 | 3V3 | JP1.14/15 3V3 | 3V 5V | 3 |
| PB2 | CN1.7 | SPI_CS | - | CS | |
| PA5 | CN1.8 | D13 SCK | JP1.6 SCK | CLK | |
| PA6 | CN1.9 | D12 MISO | JP1.4 MISO | DO | |
| PA7 | CN1.10 | D11 MOSI | JP1.5 MOSI | DI | |
| PB8 | CN2.1 | D15 SCL | JP3.11 SCL | ||
| PB9 | CN2.2 | D14 SDA | JP3.12 SDA | ||
| PA0 | CN2.3 | A3 | JP1.9 A3 | ||
| PA2 | CN2.4 | D1 | JP1.2 D1 | ||
| PA3 | CN2.5 | D0 | JP1.3 D0 | ||
| PB6 | CN2.6 | UARTRX | 13 | ||
| PA9 | CN2.7 | D9 | JP3.8 D9 | ||
| PB7 | CN2.7 | UARTTX | 14 | ||
| PA8 | CN2.8 | D6 Neopixel | JP3.9 D6 | ||
| GND | CN2.9 | GND | GND | ||
| PA1 | CN2.10 | A2 | JP1.10 A2 | ||
| USB5V | 5V | JP3.3 USB | |||
| BOOT0 | BOOT0 | JP1.1 B0 | |||
| PB0 AT2 ? | JP1.12 A0 | ||||
| PB1 AT2 ? | JP1.11 A1 | ||||
| PB3 ? | CN1.5 | SWO | JP1.8 A4? | 8 | |
| JP1.7 A5 | |||||
| JP3.1 VBAT | |||||
| JP3.2 EN |

| I | Attachment | History | Action | Size | Date | Who | Comment |
|---|---|---|---|---|---|---|---|
| |
TEK0012.png | r1 | manage | 3.6 K | 2020-04-16 - 14:22 | PeterSchmid |