program stops execution after reception of a single character over UART
Based on @Justme comment it is also necessary to properly setup fuses informing that the interrupt vector table is located at lowest flash address. To do so the BOOTRST (Boot Reset vector Enabled) must be unprogrammed (1).
It can be achieved with AVRDUDE using following arguments:
-U lfuse:w:0xc2:m -U hfuse:w:0x99:m -U efuse:w:0xff:m

or in the source code by adding following instructions:
FUSES =
{
    .low = (FUSE_CKSEL0 &amp; FUSE_CKSEL2 &amp; FUSE_CKSEL3 &amp; FUSE_SUT0),
    .high = (FUSE_BOOTSZ0 &amp; FUSE_BOOTSZ1 &amp; FUSE_SPIEN &amp; FUSE_JTAGEN),
    .extended = EFUSE_DEFAULT,
};