Michael Ellerman <m...@ellerman.id.au> writes:

> Oliver O'Halloran <ooh...@gmail.com> writes:
>
>> When the kernel is compiled to use 64bit ABIv2 the _GLOBAL() macro does not
>> include a global entry point. A function's global entry point is used when 
>> the
>> function is called from a different TOC context and in the kernel this
>> typically means a call from a module into the vmlinux (or vis-a-vis).
>>
>> There are a few exported ASM functions declared with _GLOBAL() and calling
>> them from a module will module will likely crash the kernel since any TOC
>> relative load will yield garbage.
>>
>> To fix this use _GLOBAL_TOC() for exported asm functions rather than 
>> _GLOBAL()
>> and some documentation about when to use each.
>
> I wonder if we should just change _GLOBAL() to include the global entry
> point. Persisting with _GLOBAL_TOC() seems like it's just going to be a
> game of whack-a-mole.

Turns out that doesn't work well at all.

We have *a lot* of places that use _GLOBAL() to make a symbol global,
but which aren't functions entry points, eg:

        .align  7
  _GLOBAL(ret_from_except)
        ld      r11,_TRAP(r1)
        andi.   r0,r11,1
        bne     ret_from_except_lite
        REST_NVGPRS(r1)
  
  _GLOBAL(ret_from_except_lite)
        ...


Because ret_from_except wants to fallthrough there, we can't have
_GLOBAL() insert instructions at ret_from_except_lite.

So for now we'll merge a version of this fix.

In the medium term we should change all our asm functions to use
FUNC_START(), so it's clear they are functions, and then FUNC_START()
should add the global entry point.

We can then have a hard rule that anything EXPORT_SYMBOL'ed should use
FUNC_START().

cheers

Reply via email to