The rtld-debugger interface offers the ability to help skip over procedure linkage table entries (refer to "Procedure Linkage Table (Processor-Specific)"). When a controlling process, such as a debugger, is asked to step into a function for the first time, they often wish to skip the actual procedure linkage table processing, as this results in control being passed to the runtime linker to search for the function definition.
The following interface allows a controlling process to step over the runtime linker's procedure linkage table processing. It is assumed that the controlling process can determine when a procedure linkage table entry is encountered, based on external information provided in the ELF file.
Once a target process has stepped into a procedure linkage table entry, it calls the following interface:
rd_err_e rd_plt_resolution(rd_agent_t * rdap, paddr_t pc, lwpid_t lwpid, paddr_t plt_base, rd_plt_info_t * rpi); |
This function returns the resolution state of the current procedure linkage table entry and information on how to skip it.
pc represents the first instruction of the procedure linkage table entry. lwpid provides the lwp identifier and plt_base provides the base address of the procedure linkage table. These three variables provide information sufficient for various architectures to process the procedure linkage table.
rpi provides detailed information regarding the procedure linkage table entry as defined in the following data structure (defined in rtld_db.h):
typedef enum { RD_RESOLVE_NONE, RD_RESOLVE_STEP, RD_RESOLVE_TARGET, RD_RESOLVE_TARGET_STEP } rd_skip_e; typedef struct rd_plt_info { rd_skip_e pi_skip_method; long pi_nstep; psaddr_t pi_target; psaddr_t pi_baddr; unsigned int pi_flags; } rd_plt_info_t; #define RD_FLG_PI_PLTBOUND 0x0001 |
Identifies how the procedure linkage table entry can be traversed. It will be set to one of the rd_skip_e values.
Identifies how many instructions to step over when RD_RESOLVE_STEP or RD_RESOLVE_TARGET_STEP are returned.
Specifies the address at which to set a breakpoint when RD_RESOLVE_TARGET_STEP or RD_RESOLVE_TARGET are returned.
The procedure linkage table destination address, added with RD_VERSION3. When the RD_FLG_PI_PLTBOUND flag of the pi_flags field is set, this element identifies the resolved (bound) destination address.
A flags field, added with RD_VERSION3. The flag RD_FLG_PI_PLTBOUND identifies the procedure linkage entry as having been resolved (bound) to its destination address, which is available in the pi_baddr field.
The following scenarios are possible from the rd_plt_info_t return values:
This is the first call through this procedure linkage table so it must be resolved by the runtime linker. rd_plt_info_t will contain:
{RD_RESOLVE_TARGET_STEP, M, <BREAK>, 0, 0} |
The controlling process sets a break-point at BREAK and continues the target process. When the break-point is reached, the procedure linkage table entry processing has finished, and the controlling process can step M instructions to the destination function. Notice that the bound addres (pi_baddr) has not been set since this is the first call through a procedure linkage table entry.
This is the Nth time through this procedure linkage table. rd_plt_info_t will contain:
{RD_RESOLVE_STEP, M, 0, <BoundAddr>, RD_FLG_PI_PLTBOUND} |
The procedure linkage table entry has already been resolved and the controlling process can step M instructions to the destination function. The address that the procedure linkage table entry is bound to is <BoundAddr> and the RD_FLG_PI_PLTBOUND bit has been set in the flags field.
Future implementations might employ RD_RESOLVE_TARGET as a means of setting a break point directly in the target function; however, this capability is not yet available in this version of the rtld-debugger interface.