Return Value from Syscall

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
amirsadig

Re:Return Value from Syscall

Post by amirsadig »

I have put at the beginning and end of syscall kprintf to see the system call number and return value which I have stored in regs->eax. And it display at the beginning the correct number for system call function and at the end it print the correct retun value.
here is the code :

Code: Select all

void syscall(regs_t *regs)
{
  kprintf("system call function number %d ", regs->eax);
  disable();
  __asm__ __volatile__(
   "mov %1, %%ebx;"
        "mov %2, %%ecx;"
        "pushl %%ecx ;"
        "pushl %%ebx ;"
        "call *sys_call_table(,%3, 4) ;"
        "popl %%ebx;"
        "popl %%ecx; "
   :"=a" (regs->eax):"r"(regs->ebx), "r"(regs->ecx), "r" (regs->eax)
);
kprintf(" return value = %d", regs->eax);
  enable();
}
but return value to task I receive always the system call number ( like at the beginning of isr syscall).

regs should normaly store registers value as I call the int 0x80, but as I modify regs in the syscall (exaclty EAX), why I receive the same value?
BI lazy

Re:Return Value from Syscall

Post by BI lazy »

Hm ...

Have you tried to print a register dump of your task before and after execution of syscall?

debugging such a thing a bit awful ...

can you get hands on bochs and make a debug run with hlt instruction before and after call to syscall? I'd like to see/read, what the bochs debugger says after issueing a dump-cpu command?
amirsadig

Re:Return Value from Syscall

Post by amirsadig »

note that syscall will be called from an isr as I mention earlier.
that mean when we return from syscall we still in isr.
here is before the syscall call the sys_read function

Code: Select all

eax            0x3              3
ecx            0x1              1
edx            0x1              1
ebx            0x10009fc7       268476359
esp            0x10009f28       0x10009f28
ebp            0x10009f44       0x10009f44
esi            0x108646         1082950
edi            0x108660         1082976
eip            0x104979         0x104979
eflags         0x6              6
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
this when return from sys_read ( we still in syscall handler)

Code: Select all

eax            0xffffffff       -1
ecx            0x10000ec0       268439232
edx            0xffffffff       -1
ebx            0x10009fc7       268476359
esp            0x10009f24       0x10009f24
ebp            0x10009f44       0x10009f44
esi            0x108646         1082950
edi            0x108660         1082976
eip            0x104981         0x104981
eflags         0x46             70
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
here is direct after return from syscall to ISR

Code: Select all

eax            0xffffffff       -1
ecx            0x10000ec0       268439232
edx            0xffffffff       -1
ebx            0x10009fc7       268476359
esp            0x10009f24       0x10009f24
ebp            0x10009f44       0x10009f44
esi            0x108646         1082950
edi            0x108660         1082976
eip            0x104981         0x104981
eflags         0x46             70
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
now come the error which i don't now why( EAX is still 3 as before entering syscall, but I have change the value of regs->eax!!!). if someone can exract it from such regist value, I will be glad.

Code: Select all

eax            0x3              3
ecx            0x1              1
edx            0x10009000       268472320
ebx            0x10009fc7       268476359
esp            0x10009f70       0x10009f70
ebp            0x10009f98       0x10009f98
esi            0x108646         1082950
edi            0x108660         1082976
eip            0x10009e         0x10009e
eflags         0x246            582
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
virusx

Re:Return Value from Syscall

Post by virusx »

wait a sec,
"call *sys_call_table(,%3, 4) ;"
does this handler has return statement.

int sys_write()
{
......
return state;
}

The return statements usually puts the value in eax.
Try that.

regards
distantvoices
Member
Member
Posts: 1600
Joined: Wed Oct 18, 2006 11:59 am
Location: Vienna/Austria
Contact:

Re:Return Value from Syscall

Post by distantvoices »

now, pls dump the values of esp before and after call to syscall. Not what happens inside syscall. this seems to be plain correct for you get your return code as you wish.

what I mean is: the position of esp before these instructions:
mov eax,esp
push eax.

and then the position of esp *after* the call to syscall and after this instruction:
pop eax - in your isr epilogue - all_ints.

And inside syscall, pls dump the value of regs. Maybe comparison of these three values reveals something?
... the osdever formerly known as beyond infinity ...
BlueillusionOS iso image
amirsadig

Re:Return Value from Syscall

Post by amirsadig »

what I mean is: the position of esp before these instructions:
mov eax,esp
push eax.
here is the dump for register and the value at which stack pointed before "mov eax, esp"

Code: Select all

eax            0x10             16
ecx            0x1              1
edx            0x108c91         1084561
ebx            0x10009fd7       268476375
esp            0x10009f60       0x10009f60
ebp            0x10009fa8       0x10009fa8
esi            0x108c91         1084561
edi            0x0              0
eip            0x101439         0x101439
eflags         0x7              7
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
<bochs:17> x /9dw 0x10009f60
[bochs]:
0x10009f60 <bogus+       0>:    0       1084561 268476328       268476288
0x10009f70 <bogus+      16>:    268476375       1084561 1       3
0x10009f80 <bogus+      32>:    16
the value at stack is regs struct which syscall uses it later and you see the 8 value (eax is 3 - sys_read number) is correct.
the dumb for registers at all_int you find in my last reply third code. but I put also here again.

Code: Select all

(0) [0x0010009c] 0018:0010009c (unk. ctxt): pop eax                   ; 5
<bochs:20> info registers
eax            0xffffffff       -1
ecx            0x1              1
edx            0xffffffff       -1
ebx            0x10009fd7       268476375
esp            0x10009f5c       0x10009f5c
ebp            0x10009fa8       0x10009fa8
esi            0x108c91         1084561
edi            0x0              0
eip            0x10009c         0x10009c
eflags         0x242            578
cs             0x18             24
ss             0x10             16
ds             0x10             16
es             0x10             16
fs             0x10             16
gs             0x10             16
<bochs:21> x /9dw 0x10009f5c
[bochs]:
0x10009f5c <bogus+       0>:    268476256       0       1084561 268476328
0x10009f6c <bogus+      16>:    268476288       268476375       1084561 1
0x10009f7c <bogus+      32>:    3
note that is before push eax and pusha instructions.

hi all this not a private talk beween me and "beyond infinity" :P.

I thank all for their answer. I improve always my Assembly knowledge with debugging my kernel and your question and answer.
amirsadig

Re:Return Value from Syscall

Post by amirsadig »

as I have take a look at the assemly code to syscall. I have notice some mistake (my be in my code or compiler-asm code). tell me if I WRONG.

Code: Select all

0010495c <syscall>:
  10495c:   55                      push   %ebp
  10495d:   89 e5                   mov    %esp,%ebp
  10495f:   83 ec 14                sub    $0x14,%esp
  104962:   53                      push   %ebx
  104963:   8b 5d 08                mov    0x8(%ebp),%ebx
  104966:   e8 85 39 00 00          call   1082f0 <disable>
  10496b:   8b 4b 10                mov    0x10(%ebx),%ecx
  10496e:   8b 53 18                mov    0x18(%ebx),%edx
  104971:   8b 43 1c                mov    0x1c(%ebx),%eax
  104974:   89 cb                   mov    %ecx,%ebx
  104976:   89 d1                   mov    %edx,%ecx
  104978:   51                      push   %ecx
  104979:   53                      push   %ebx
  10497a:   ff 14 85 40 b8 10 00    call   *0x10b840(,%eax,4)
  104981:   5b                      pop    %ebx
  104982:   59                      pop    %ecx
  104983:   89 43 1c                mov    %eax,0x1c(%ebx)
  104986:   e8 75 39 00 00          call   108300 <enable>
  10498b:   5b                      pop    %ebx
  10498c:   c9                      leave  
  10498d:   c3                      ret    
* gcc use EBX to as placehalter for regs and mov value to ecx and eax and ebx in instructions "10496b -> 104971"
* then it change the value of ebx ( !!) at 104974. that mean the ebx not point now to regs.
* when return from sys_read it save the return in 0x1c(%ebx), which not point regs now.

there for the eax value in regs struct have not been change. thus i receive the old value eax before call syscall.
the c-code for syscall you can find it here in this thread.

please correct me if I am wrong in my analysis !
amirsadig

Re:Return Value from Syscall

Post by amirsadig »

now I have fix the problem.

in syscall i have clobbered ebx register like ,

Code: Select all

:"=a" (regs->eax):"r"(regs->ebx), "r"(regs->ecx), "r" (regs->eax):"ebx"
that mean gcc will not use this register to store any value, because it asm inline use it.

without you help and the debugger, it could take along time to solve.
thanks everyone ;)
distantvoices
Member
Member
Posts: 1600
Joined: Wed Oct 18, 2006 11:59 am
Location: Vienna/Austria
Contact:

Re:Return Value from Syscall

Post by distantvoices »

Well done, gosh.

See: the smallest bugs have always the biggest effects.

Have a nice elongated weekend :-)

btw, I didn't do so much as asking questions and peeking around.

stay safe
... the osdever formerly known as beyond infinity ...
BlueillusionOS iso image
Post Reply