I banged out the missing piece of the firmware, namely to send the received Pronto codes over UART, and the opposite direction as well. This part of the code is not meant to be optimal or well-structured, just something to get things working.
I first tested this still in loopback mode, and it works fine. So it was time to get dirty with some real-life infrared signals.
There's a myriad of IR receivers available, I went with Vishay's TSMP58000, which they recommend for IR learning applications - perfect for me, I thought. I removed the loopback between the STM32's I/Os, and hooked up the TSMP58000 on the breadboard without any additional components.
I have configured a known Pronto code in the IR Remote app, and pressed the new button. The IR receiver has picked up the signal, as the logic analyzer confirmed it. The STM32's firmware rejected the signal though. As I have seen on the logic analyzer's capture, the ON durations are significantly less than 50% of the period. The TSMP58000 recommends some passive components to improve the signal quality, but they aren't addressing this particular problem. I have instead increased the tolerance value in the firmware. After that, I have seen the same code on the terminal, as was entered in the app. Success! (To be fair, there are some expected differences, e.g. the once count shows the number of burst pairs instead of the repeat count, the last off duration is different.)
Now that the firmware is ready for action, I have connected it to my Galaxy S5 mini, so I can learn the IR codes of the remotes in the house, and directly save it into the IR Remote app. That's when I got really disappointed: the power LEDs are off on the STM32 kit, meaning that the phone's USB OTG host mode is broken. After some searching it seems that this is a known issue in LineageOS :(
I will have to connect it to my laptop and transfer the Pronto codes to my phone after learning the remote codes.
It would be great to share these device codes, but such projects (e.g. https://github.com/probonopd/irdb) don't take raw Pronto HEX codes, only codes with known protocols. Maybe IrScrutinizer could be used to find out the protocol? At the moment I'm not that motivated to dig deeper into this though.