This is done using the standard relocation methods which have been in ELF since long before the invention of the plt (procedure linking table).
Long ago (for some definition of long), external functions were called directly from within code. Which means, if your program called
printf from 1000 different places, each of these 1000 places had to be adjusted to the new dynamic location of
printf everytime the program was started. Each of these 1000 places was added to the relocation table, and starting a program included walking the relocation table and adjusting every position referenced in it. Needless to say, this made starting programs take much more time, especially when the number of dynamic libraries used in programs increased.
The plt was invented to improve this - instead of producing a call to
printf directly, the program got a new
plt section. Each call to
printf would be converted to a call to
printf@plt - which could be done at link time, so it wouldn't affect program loading - and
printf@plt did nothing but jump to
printf. This still needs a relocation entry for
printf@plt, but it's much faster to do this single relocation at load time than many of them. And it doesn't affect execution much, because unconditional jumps can be handled by the processor pipeline quite efficiently.
So what happens in your case is: the
printf@plt does not make a call to the dynamic linker. The
printf@plt makes a jump to a static address, and the dynamic linker adjusts the target of this static address when it loads the program. It uses the relocation table to find out where to adjust things, and which target address to adjust them to.
In your case, the jump is implemented by taking the original pc, adding 12, adding 8000, then doing an indirect jump (
ldr pc, ... instead of
b). I'd assume that the 12 and the 8000 get adjusted to the load address of the .so that's loaded (libc.so), and libc.so contains a jump at offset
0x344 to the real printf function. (However, i might be wrong here, i'd have to test on a real system, which i can't do conveniently right now)