[M3devel] checking function pointers for null?
Jay K
jay.krell at cornell.edu
Mon Jun 21 22:55:06 CEST 2010
The backend is doing what the front/middle end asks.
My original question stands: The check for NULL is worthless, right?
Either it should do more: call m3_fault
Or it should do less: don't bother checking, let the hardware do it at the call or marker check (the marker check, in reality)
?
I can understand the stance that the software does all the checking. That we don't/shouldn't depend on hardware checking.
Though that isn't true -- the rationale for "Target.first_readable_address" or such is that hardware checks for NULL deref,
and even "small deref" -- anything in the first page at least.
But this seems in between -- it avoids the null deref for the marker check but doesn't avoid it for the call.
Perhaps there is an idea that the hardware checking is somehow different for data vs. code??
MODULE Main;
TYPE Function = PROCEDURE ();
PROCEDURE C(a:Function) =
BEGIN
a();
END C;
BEGIN
END Main.
(23) begin_procedure
procedure Main__C
Main__C(24) set_source_line
source line 6
(25) set_source_line
source line 7
(26) load
type:addr
type:addr
m3cg_load (M3_CQL02D_a): offset 0x0, convert addr -> addr
(27) declare_temp
type:addr
temp var type:addr size:0x40 alignment:0x40
(28) store
type:addr
type:addr
store (noname) offset:0x0 src_t:addr dst_t:addr
(29) start_call_indirect
type:void
start call procedure indirect type:void
(30) load
type:addr
type:addr
m3cg_load (noname): offset 0x0, convert addr -> addr
(31) load_nil ***
(32) if_eq ***
type:addr
label 1
(33) load
type:addr
type:addr
m3cg_load (noname): offset 0x0, convert addr -> addr
(34) load_indirect
type:int64
type:int64
load address offset:0x0 src_t:int64 dst_t:int64
(35) load_integer
type:int64
integer i:0xfe n_bytes:0x1 0x00000000000000001 sign -1
(36) if_ne
type:int64
label 1
(37) set_label
label 2
(38) load
type:addr
type:addr
m3cg_load (noname): offset 0x0, convert addr -> addr
(39) load_indirect
type:addr
type:addr
load address offset:0x80 src_t:addr dst_t:addr
(40) pop_static_link
(41) load
type:addr
type:addr
m3cg_load (noname): offset 0x0, convert addr -> addr
(42) load_indirect
type:addr
type:addr
load address offset:0x40 src_t:addr dst_t:addr
(43) store
type:addr
type:addr
store (noname) offset:0x0 src_t:addr dst_t:addr
(44) set_label
label 1
(45) load
type:addr
type:addr
m3cg_load (noname): offset 0x0, convert addr -> addr
(46) call_indirect
type:void
call procedure indirect type:void
(47) set_source_line
source line 8
(48) exit_proc
type:void
(49) free_temp
(50) end_procedure
procedure Main__C
- Jay
________________________________
> From: jay.krell at cornell.edu
> To: hosking at cs.purdue.edu
> CC: m3devel at elegosoft.com
> Subject: RE: [M3devel] checking function pointers for null?
> Date: Mon, 21 Jun 2010 17:47:48 +0000
>
>
>
>
>
>
>
> Neither backend would add these checks themself, it is m3cg, IR later.
>
>> Subject: Re: [M3devel] checking function pointers for null?
>> From: hosking at cs.purdue.edu
>> Date: Mon, 21 Jun 2010 10:26:31 -0400
>> CC: m3devel at elegosoft.com
>> To: jay.krell at cornell.edu
>>
>> Is this code from M3CG or the Windows native backend?
>>
>> If from M3CG perhaps you can show us the M3CG IR code.
>>
>> On 21 Jun 2010, at 03:55, Jay K wrote:
>>
>>>
>>> This is code that calls a function pointer:
>>>
>>>
>>> testq %rbx, %rbx ; test function pointer for null
>>> je L6
>>> cmpq $-1, (%rbx) ; check for closure marker
>>> jne L6 ; if not a closure, goto L6
>>> movq 16(%rbx), %r13 ; r13=static chain (ought to use r10?)
>>> movq 8(%rbx), %rax ; rax=actual function pointer
>>> jmp L8
>>> L6:
>>> movq %rbx, %rax ; rax=actual function pointer
>>> L8:
>>> movq %r13, %r10 ; r10=static chain (it should have just used r10 in the first place? or is r13 otherwise the previous static chain?)
>>> call *%rax
>>>
>>>
>>> What is the point of the initial testq/je, if we are just going to jump to the address anyway?
>>> Should we do something else if in fact the function pointer is null? Or just let a jump to null fail as it will?
>>> You know -- it seems me we should do either more or less here.
>>> More: report a null deref by calling m3_fault
>>> Less: remove the null check
>>>
>>>
>>> - Jay
>>>
>>
More information about the M3devel
mailing list