Переместите ПК в другой регистр с ядрами xtensa (lx6)

Я пытаюсь получить текущее значение ПК в процедуре сборки, написанной для ядер xtensa (lx6). Покопавшись в документации по набору инструкций, я не могу понять, как этого добиться. Похоже, что ПК не отображается в 16 AR, и я не вижу его в списке регистров, к которым я могу получить доступ с помощью инструкции RSR или даже инструкции RER.

Любой совет ?

2 ответа

Следующий макрос является переносимым (между конфигурациями ядра xtensa) способом загрузки полного 32-битного адреса времени выполнения метки.labelв реестр:

      .macro  get_runtime_addr label, ar, at
        .ifgt 0x\ar - 0xa0
        mov     \at, a0
        .endif
        .begin  no-transform
        _call0  1f
\label:
        .end    no-transform
        .align  4
1:
        .ifgt 0x\ar - 0xa0
        mov     \ar, a0
        mov     a0, \at
        .endif
.endm

The no-transformблок вокруг вызова, а следующая метка гарантирует, что между ними не будет вставлен буквальный пул или батут для прыжков.

Когда макрос используется с другими параметрами, он сохраняет текущее значение во временном регистре. Когдаarявляетсяa0Аргументatне используется и может быть опущен.

Вот как это сделать:

          .file   "getpc.S"
    .text
.Ltext0:
    .section    .text.get_pc,"ax",@progbits
    .align  4
    .global called_routine
    .type   called_routine, @function

// All this mess to get the PC (roughly) !

// This routine is called just to get the caller return address
// it is stored into the a0 register
called_routine:    
    entry   a1, 32
    mov     a2,a0
    retw.n


// This routine obtains something which contains 30 bits of the PC
// Please refer the xtensa instruction set manual (CALL8) for more information
// on how to rebuild the topmost 2 bits of it
    .align  4
    .global get_pc
    .global get_pc_return_address
    .type   get_pc, @function
get_pc:
    entry   a1, 32

    call8   called_routine
get_pc_return_address:
    mov.n   a2, a10
    retw.n
Другие вопросы по тегам