Changes in kernel/arch/amd64/src/asm.S [f77e591d:c0e9f3f] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/arch/amd64/src/asm.S
rf77e591d rc0e9f3f 192 192 #define ERROR_WORD_INTERRUPT_LIST 0x00027D00 193 193 194 .macro handler i 195 .global int_\i 196 int_\i: 197 194 #define INTERRUPT_ALIGN 256 195 196 /** Declare interrupt handlers 197 * 198 * Declare interrupt handlers for n interrupt 199 * vectors starting at vector i. 200 * 201 * The handlers call exc_dispatch(). 202 * 203 */ 204 .macro handler i n 205 198 206 /* 199 207 * Choose between version with error code and version without error 200 * code. 208 * code. Both versions have to be of the same size. amd64 assembly is, 209 * however, a little bit tricky. For instance, subq $0x80, %rsp and 210 * subq $0x78, %rsp can result in two instructions with different 211 * op-code lengths. 212 * Therefore we align the interrupt handlers. 201 213 */ 202 214 … … 278 290 addq $(ISTATE_SOFT_SIZE + 8), %rsp 279 291 iretq 292 293 .align INTERRUPT_ALIGN 294 .if (\n - \i) - 1 295 handler "(\i + 1)", \n 296 .endif 280 297 .endm 281 298 282 #define LIST_0_63 \ 283 0, 1, 2, 3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,\ 284 28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,\ 285 53,54,55,56,57,58,59,60,61,62,63 286 299 .align INTERRUPT_ALIGN 287 300 interrupt_handlers: 288 .irp cnt, LIST_0_63 289 handler \cnt290 .endr 301 h_start: 302 handler 0 IDT_ITEMS 303 h_end: 291 304 292 305 /** Low-level syscall handler … … 321 334 movq %gs:8, %rsp /* set this thread's kernel RSP */ 322 335 323 /* 324 * Note that the space needed for the imitated istate structure has been 325 * preallocated for us in thread_create_arch() and set in 326 * before_thread_runs_arch(). 327 */ 328 329 /* 330 * Save the general purpose registers and push the 7th argument (syscall 331 * number) onto the stack. Note that the istate structure has a layout 332 * which supports this. 333 */ 334 movq %rax, ISTATE_OFFSET_RAX(%rsp) /* 7th argument, passed on stack */ 335 movq %rbx, ISTATE_OFFSET_RBX(%rsp) /* observability */ 336 movq %rcx, ISTATE_OFFSET_RCX(%rsp) /* userspace RIP */ 337 movq %rdx, ISTATE_OFFSET_RDX(%rsp) /* 3rd argument, observability */ 338 movq %rsi, ISTATE_OFFSET_RSI(%rsp) /* 2nd argument, observability */ 339 movq %rdi, ISTATE_OFFSET_RDI(%rsp) /* 1st argument, observability */ 340 movq %rbp, ISTATE_OFFSET_RBP(%rsp) /* need to preserve userspace RBP */ 341 movq %r8, ISTATE_OFFSET_R8(%rsp) /* 5th argument, observability */ 342 movq %r9, ISTATE_OFFSET_R9(%rsp) /* 6th argument, observability */ 343 movq %r10, ISTATE_OFFSET_R10(%rsp) /* 4th argument, observability */ 344 movq %r11, ISTATE_OFFSET_R11(%rsp) /* low 32 bits userspace RFLAGS */ 345 movq %r12, ISTATE_OFFSET_R12(%rsp) /* observability */ 346 movq %r13, ISTATE_OFFSET_R13(%rsp) /* observability */ 347 movq %r14, ISTATE_OFFSET_R14(%rsp) /* observability */ 348 movq %r15, ISTATE_OFFSET_R15(%rsp) /* observability */ 349 350 /* 351 * Save the return address and the userspace stack on locations that 352 * would normally be taken by them. 353 */ 354 movq %gs:0, %rax 355 movq %rax, ISTATE_OFFSET_RSP(%rsp) 356 movq %rcx, ISTATE_OFFSET_RIP(%rsp) 357 358 /* 359 * Imitate a regular stack frame linkage. 360 */ 361 movq $0, ISTATE_OFFSET_RBP_FRAME(%rsp) 362 movq %rcx, ISTATE_OFFSET_RIP_FRAME(%rsp) 363 leaq ISTATE_OFFSET_RBP_FRAME(%rsp), %rbp 364 365 /* Switch back to normal %gs */ 336 /* Switch back to remain consistent */ 366 337 swapgs 367 338 sti 368 339 340 pushq %rcx 341 pushq %r11 342 pushq %rbp 343 344 xorq %rbp, %rbp /* stop the stack traces here */ 345 369 346 /* Copy the 4th argument where it is expected */ 370 347 movq %r10, %rcx 371 372 /* 373 * Call syscall_handler() with the 7th argument passed on stack. 374 */ 348 pushq %rax 349 375 350 call syscall_handler 376 351 352 addq $8, %rsp 353 354 popq %rbp 355 popq %r11 356 popq %rcx 357 377 358 cli 378 379 /* 380 * Restore registers needed for return via the SYSRET instruction and 381 * the clobbered preserved registers (i.e. RBP). 382 */ 383 movq ISTATE_OFFSET_RBP(%rsp), %rbp 384 movq ISTATE_OFFSET_RCX(%rsp), %rcx 385 movq ISTATE_OFFSET_R11(%rsp), %r11 386 movq ISTATE_OFFSET_RSP(%rsp), %rsp 387 359 swapgs 360 361 /* Restore the user RSP */ 362 movq %gs:0, %rsp 363 swapgs 364 388 365 sysretq 389 366 … … 532 509 ret 533 510 511 .data 512 .global interrupt_handler_size 513 514 interrupt_handler_size: .quad (h_end - h_start) / IDT_ITEMS
Note:
See TracChangeset
for help on using the changeset viewer.