Changeset 296426ad in mainline


Ignore:
Timestamp:
2007-11-16T16:17:18Z (16 years ago)
Author:
Jakub Jermar <jakub@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
9c2fb97
Parents:
e686744c
Message:

Support for 6 syscalls arguments on amd64.

Files:
7 edited

Legend:

Unmodified
Added
Removed
  • kernel/arch/amd64/include/proc/thread.h

    re686744c r296426ad  
    3636#define KERN_amd64_THREAD_H_
    3737
     38/* CAUTION: keep these in sync with low level assembly code in syscall_entry */
     39#define SYSCALL_USTACK_RSP      0
     40#define SYSCALL_KSTACK_RSP      1
     41
    3842typedef struct {
    3943        unative_t tls;
     44        /** User and kernel RSP for syscalls. */
     45        uint64_t syscall_rsp[2];       
    4046} thread_arch_t;
    4147
  • kernel/arch/amd64/src/asm_utils.S

    re686744c r296426ad  
    221221
    222222        /*
    223          * Choose between version with error code and version without error code.
    224          * Both versions have to be of the same size. amd64 assembly is, however,
    225          * a little bit tricky. For instance, subq $0x80, %rsp and subq $0x78, %rsp
    226          * can result in two instructions with different op-code lengths.
     223         * Choose between version with error code and version without error
     224         * code. Both versions have to be of the same size. amd64 assembly is,
     225         * however, a little bit tricky. For instance, subq $0x80, %rsp and
     226         * subq $0x78, %rsp can result in two instructions with different
     227         * op-code lengths.
    227228         * Therefore we align the interrupt handlers.
    228229         */
     
    270271h_end:
    271272
    272        
     273## Low-level syscall handler
     274#
     275# Registers on entry:
     276#
     277# @param rcx            Userspace return address.
     278# @param r11            Userspace RLFAGS.
     279#
     280# @param rax            Syscall number.
     281# @param rdi            1st syscall argument.
     282# @param rsi            2nd syscall argument.
     283# @param rdx            3rd syscall argument.
     284# @param r10            4th syscall argument. Used instead of RCX because the
     285#                       SYSCALL instruction clobbers it.
     286# @param r8             5th syscall argument.
     287# @param r9             6th syscall argument.
     288#
     289# @return               Return value is in rax.
     290#
    273291syscall_entry:
    274         # Switch to hidden gs   
    275         swapgs
    276         # %gs:0 now points to pointer to stack page
    277         mov %gs:0, %r10     # We have a ptr to stack page in r10
    278         addq $PAGE_SIZE-16, %r10 # We need some space to store old %sp
    279        
    280         movq %rsp, 0(%r10)  # Save old stack pointer to stack
    281         movq %r10, %rsp     # Change to new stack
    282         pushq %rcx          # Return address
    283         pushq %r11          # Save flags
    284 
    285         # Switch back to remain consistent
    286         swapgs
    287 
     292        swapgs                  # Switch to hidden gs   
     293        #
     294        # %gs:0                 Scratch space for this thread's user RSP
     295        # %gs:8                 Address to be used as this thread's kernel RSP
     296        #
     297        movq %rsp, %gs:0        # Save this thread's user RSP
     298        movq %gs:8, %rsp        # Set this thread's kernel RSP
     299        swapgs                  # Switch back to remain consistent
    288300        sti
    289         movq %r9, %rcx      # Exchange last parameter as a third
    290        
     301       
     302        pushq %rcx
     303        pushq %r11
     304
     305        movq %r10, %rcx         # Copy the 4th argument where it is expected
     306        pushq %rax
    291307        call syscall_handler
    292         cli                 # We will be touching stack pointer
     308        addq $8, %rsp
    293309               
    294310        popq %r11
    295311        popq %rcx
    296         movq 0(%rsp), %rsp
     312
     313        cli
     314        swapgs
     315        movq %gs:0, %rsp        # Restore the user RSP
     316        swapgs
     317
    297318        sysretq
    298                
    299                
     319
    300320.data
    301321.global interrupt_handler_size
  • kernel/arch/amd64/src/proc/scheduler.c

    re686744c r296426ad  
    5757void before_thread_runs_arch(void)
    5858{
    59         CPU->arch.tss->rsp0 = (uintptr_t) &THREAD->kstack[THREAD_STACK_SIZE-SP_DELTA];
     59        CPU->arch.tss->rsp0 =
     60            (uintptr_t) &THREAD->kstack[THREAD_STACK_SIZE - SP_DELTA];
    6061
    61         /* Syscall support - write address of thread stack pointer to
    62          * hidden part of gs */
     62        /*
     63         * Syscall support.
     64         */
    6365        swapgs();
    64         write_msr(AMD_MSR_GS, (uint64_t)&THREAD->kstack);
     66        write_msr(AMD_MSR_GS, (uintptr_t)THREAD->arch.syscall_rsp);
    6567        swapgs();
    6668
     
    7274        if (CPU->id < BKPOINTS_MAX)
    7375                breakpoint_add(&((the_t *) THREAD->kstack)->as,
    74                                BKPOINT_WRITE | BKPOINT_CHECK_ZERO,
    75                                CPU->id);
     76                    BKPOINT_WRITE | BKPOINT_CHECK_ZERO, CPU->id);
    7677#endif
    7778}
  • kernel/arch/amd64/src/proc/thread.c

    re686744c r296426ad  
    4242{
    4343        t->arch.tls = 0;
     44        t->arch.syscall_rsp[SYSCALL_USTACK_RSP] = 0;
     45        /*
     46         * Kernel RSP can be precalculated at thread creation time.
     47         */
     48        t->arch.syscall_rsp[SYSCALL_KSTACK_RSP] =
     49            (uintptr_t)&t->kstack[PAGE_SIZE - sizeof(uint64_t)];
    4450}
    4551
  • kernel/arch/amd64/src/syscall.c

    re686744c r296426ad  
    5353        /* Setup syscall entry address */
    5454       
    55         /* This is _mess_ - the 64-bit CS is argument+16,
    56          * the SS is argument+8. The order is:
     55        /* This is _mess_ - the 64-bit CS is argument + 16,
     56         * the SS is argument + 8. The order is:
    5757         * +0(KDATA_DES), +8(UDATA_DES), +16(UTEXT_DES)
    5858         */
    5959        write_msr(AMD_MSR_STAR,
    60                   ((uint64_t)(gdtselector(KDATA_DES) | PL_USER)<<48) \
    61                   | ((uint64_t)(gdtselector(KTEXT_DES) | PL_KERNEL)<<32));
     60            ((uint64_t)(gdtselector(KDATA_DES) | PL_USER) << 48) |
     61            ((uint64_t)(gdtselector(KTEXT_DES) | PL_KERNEL) << 32));
    6262        write_msr(AMD_MSR_LSTAR, (uint64_t)syscall_entry);
    6363        /* Mask RFLAGS on syscall
  • uspace/lib/libc/arch/amd64/src/fibril.S

    re686744c r296426ad  
    8181        # Set thread local storage
    8282        movq OFFSET_TLS(%rdi), %rdi   # Set arg1 to TLS addr
    83         movq $1, %r8
     83        movq $1, %rax           # SYS_TLS_SET
    8484        syscall
    8585
  • uspace/lib/libc/arch/amd64/src/syscall.S

    re686744c r296426ad  
    2929.text
    3030       
    31 .globl __syscall
     31.global __syscall
     32       
     33## Make a system call.
     34#
     35# @param rdi            First argument.
     36# @param rsi            Second argument.
     37# @param rdx            Third argument.
     38# @param rcx            Fourth argument.
     39# @param r8             Fifth argument.
     40# @param r9             Sixth argument.
     41# @param 8(%rsp)        Syscall number.
     42#
     43# @return               The return value will be stored in RAX.
     44#
     45__syscall:
     46        #
     47        # Move the syscall number into RAX.
     48        movslq 8(%rsp), %rax
    3249
    33        
    34 __syscall:
    35         # rcx gets rewritten on syscall
    36         movq %rcx, %r9
     50        #
     51        # Save RCX, the 4th argument, aside because RCX gets rewritten by the
     52        # SYSCALL instruction.
     53        #
     54        movq %rcx, %r10
    3755        syscall
    3856        ret
    39        
    40 .end __syscall
     57
Note: See TracChangeset for help on using the changeset viewer.