Re: avoiding SIGSEGV



Herbert Kleebauer wrote:
Frank Kotler wrote:
#define valid_ptr(p) ((access((char*)p, 0) == -1) ? (errno != EFAULT)
: 1)

I translated this highly-readable C into a crude test to see if it'd
work. Seems to. I don't know if this would be useful in a library or not...

No, you didn't translate the above but wrote a subroutine.

True. You don't miss much...

And
this subroutine written in C surely is easier to read than your
assembler code:

if (access(p,0) == -1) return (errno != EFAULT); else return 1;

Okay. Maybe it's my eyesight...

But the above is much more flexible, you can for example use it in

x = 4 + 3*valid_ptr(p);

which you can't do with a subroutine.

I'll leave it to a\/b to implement it as a macro so he can use it in *his* assembly source that looks like that. :)

In an xterm, the "non-robust" build segfaults as expected. With the

But which value has esi when it faults?

0804A000h, same as in a "regular" terminal. It's the behavior of the "-dROBUST" version that's puzzling! It *doesn't* fault, but exits cleanly, as expected, but later than expected...

If, for example, there is
1 Mbyte memory accessible, then you will not notice the time delay
for 1 million "lodsb" instructions.

Mmmm, on *my* machine, "hardly notice" would be closer. :)

"access" in there, it behaves as if "access" were allocating memory as
it goes - doesn't quit for a long time! Eventually, it does - told ya we
could determine if it halts if we were patient enough! :) No idea what's
going on there...

But 1 million calls to "access" will take it's time.

Hundreds of times more than in a "regular" terminal???

The "instrumented" version is slower still, of course - I really should have used a larger increment than just "lodsb"! Up to 12817??? (too fast to read) and still going. If you try the instrumented, "-dROBUST" version in an xterm, I suggest you set it going before you go to bed! :) The "non-robust" version, and the "robust" version in a "regular" terminal run in reasonable times.

Or maybe you'll tell me I'm imagining things - could happen. I suppose I *shouldn't* be surprised - things are different in X - but I am!

Best,
Frank

; nasm -f elf myprog.asm [-dROBUST]
; ld -o myprog myprog.o

global _start

section .bss
buf resb 100

section .text
_start:

mov esi, buf
..top:
mov eax, esi
call showeaxh

%ifdef ROBUST
call is_memory_valid
test eax, eax
js exit
%endif

lodsb
jmp .top

exit:
mov eax, 1
int 80h
;-----------------------------

;-----------------------------
; tests if [esi] is valid memory
; returns -1 if not
;-----------------------------
is_memory_valid:
push ebx
push ecx
mov eax, 33 ; __NR_access
mov ebx, esi
xor ecx, ecx ; F_OK
int 80h
cmp eax, -14 ; -EFAULT
jnz .good
or eax, byte -1
jmp short .done
..good:
xor eax, eax
..done:
pop ecx
pop ebx
ret
;----------------------------

;------------------------------
showeaxh:
push eax
push ebx
push ecx
push edx

sub esp, 10h

mov ecx, esp
xor edx, edx
mov ebx, eax
..top:
rol ebx, 4
mov al, bl
and al, 0Fh
cmp al, 0Ah
sbb al, 69h
das
mov [ecx + edx], al
inc edx
cmp edx, 8
jnz .top

; throw in a newline
mov byte [ecx + edx], 10
inc edx

mov ebx, 1
mov eax, 4
int 80h

add esp, 10h


pop edx
pop ecx
pop ebx
pop eax
ret
;------------------------------
.



Relevant Pages