O manual do usuário do AVR-Libc possui um capítulo inteiro sobre como construir uma biblioteca . Eu sugeriria começar por aí. Se você usar um IDE como o eclipse, haverá configurações de projeto aplicáveis se você deseja construir como uma biblioteca em vez de um executável.
Editar
Aqui está o que o eclipse faz quando eu o configuro para o seu exemplo:
Para que não pudesse ser facilmente compilado, alterei sua função test_ para:
#include "test.h"
void test_function()
{
volatile int i = 0;
i++;
}
Construindo a biblioteca:
avr-gcc -Wall -g2 -gstabs -Os -fpack-struct -fshort-enums -std=gnu99 -funsigned-char -funsigned-bitfields -mmcu=atmega328p -DF_CPU=16000000UL -MMD -MP -MF"test.d" -MT"test.d" -c -o"test.o" "../test.c"
avr-ar -r "libtest.a" ./test.o
avr-objdump -h -S libtest.a >"libtest.lss"
avr-size --format=avr --mcu=atmega328p libtest.a
Construindo o programa principal
avr-gcc -I"C:\path\to\my\workspace\test" -Wall -g2 -gstabs -Os -fpack-struct -fshort-enums -std=gnu99 -funsigned-char -funsigned-bitfields -mmcu=atmega328p -DF_CPU=16000000UL -MMD -MP -MF"program.d" -MT"program.d" -c -o"program.o" "../program.c"
avr-gcc -Wl,-Map,MainProgram.map -L"C:\path\to\my\workspace\test\Release" -mmcu=atmega328p -o"MainProgram.elf" ./program.o -ltest
avr-objdump -h -S MainProgram.elf >"MainProgram.lss"
avr-size --format=avr --mcu=atmega328p MainProgram.elf
... e cria sem erro. Meu palpite é que você precisa incluir os caminhos especificados nas linhas de comando. Seguir convenções de nomenclatura adequadas também é muito importante, tente seguir o padrão acima. Obviamente, os comandos avr-objdump e avr-size são apenas para obter mais informações e não são necessários se você estiver construindo.
Tenho certeza de que, se você precisar recompilar sua biblioteca para arquiteturas de destino específicas e velocidades de clock também.