Most implementations of the RIPEMD-160 hash function out there are optimised for speed, and are typically written with (manually) unrolled loops and aggressive inlining, at the cost of code size. Even an implementation that claims to be "optimized for MCU" yields over 25kB of code when compiled for an 8-bit Atmel microcontroller (e.g. an Arduino), which is awfully large when you only have 32kB of program memory available.
The fundamental algorithm is pretty uniform, so if you don't need the raw speed but do want to generate less code then it pays to make use of all the uniformity instead. That's what this implementation does:
$ avr-gcc -Os -mmcu=atmega328p -o ripemd160.o -c ripemd160.c
$ readelf -s ripemd160.o | grep GLOBAL
11: 00000000 772 FUNC GLOBAL DEFAULT 1 ripemd160_compute_line
12: 00000082 16 OBJECT GLOBAL DEFAULT 3 ripemd160_rho
13: 00000304 494 FUNC GLOBAL DEFAULT 1 ripemd160_update_digest
14: 00000005 5 OBJECT GLOBAL DEFAULT 3 ripemd160_fns_left
15: 0000001e 20 OBJECT GLOBAL DEFAULT 3 ripemd160_constants_left
16: 00000032 80 OBJECT GLOBAL DEFAULT 3 ripemd160_shifts
17: 00000000 5 OBJECT GLOBAL DEFAULT 3 ripemd160_fns_right
18: 0000000a 20 OBJECT GLOBAL DEFAULT 3 ripemd160_constants_right
19: 000004f2 314 FUNC GLOBAL DEFAULT 1 ripemd160
20: 00000092 20 OBJECT GLOBAL DEFAULT 3 ripemd160_initial_digest
21: 00000000 0 NOTYPE GLOBAL DEFAULT UND __do_copy_data
$ readelf -s ripemd160.o | grep GLOBAL | awk '{SUM+=$3}END{print SUM}'
1746
This isn't the smallest possible code, and it's certainly not the fastest, but it's less than 2kB which is enough for me. Enjoy!