10.8.1 Device-Specific Linker Script

The application source code is responsible for creating a .vector_n input section for each interrupt vector. The C/C++ compiler creates this section when either the vector(n) or at_vector(n) attribute is applied to the interrupt service routine. In assembly code, use the .section directive to create a new named section.

The device-specific linker script creates a single output section named .vectors that groups all of the individual .vector_n input sections from the project. The start of the interrupt-vector table is mapped to the address (_ebase_address + 0x200). The default value of the _ebase_address symbol is also provided in the linker script.

For each vector, the linker script also creates a symbol named __vector_offset_n whose value is the offset of the vector address from the _ebase_address address.

PROVIDE(_ebase_address = 0x9D000000);

SECTIONS
{
 /* Interrupt vector table with vector offsets */
 .vectors _ebase_address + 0x200 :
 {
  /* Symbol __vector_offset_n points to .vector_n if it exists,
   * otherwise points to the default handler. The
   * vector_offset_init.o module then provides a .data section
   * containing values used to initialize the vector-offset SFRs
   * in the crt0 startup code.
   */
__vector_offset_0 = (DEFINED(__vector_dispatch_0) ? (. - _ebase_address) : __vector_offset_default);
KEEP(*(.vector_0))
__vector_offset_1 = (DEFINED(__vector_dispatch_1) ? (. - _ebase_address) : __vector_offset_default);
KEEP(*(.vector_1))
__vector_offset_2 = (DEFINED(__vector_dispatch_2) ? (. - _ebase_address) : __vector_offset_default);
KEEP(*(.vector_2))

/* … */

__vector_offset_190 = (DEFINED(__vector_dispatch_190) ? (. - _ebase_address) : __vector_offset_default);
KEEP(*(.vector_190))
}
}