diff options
author | Russ Cox <rsc@golang.org> | 2020-01-17 13:54:30 -0500 |
---|---|---|
committer | Russ Cox <rsc@golang.org> | 2020-03-13 19:05:54 +0000 |
commit | fc8a6336d1ad29acf2c7728ce669df9059169132 (patch) | |
tree | 4121580d23be8c08aa0a7b0077254035ecb4473b /src/runtime/asm_amd64.s | |
parent | 877ef86bec593cd7e40899ac5446791e65b47839 (diff) | |
download | go-fc8a6336d1ad29acf2c7728ce669df9059169132.tar.gz go-fc8a6336d1ad29acf2c7728ce669df9059169132.zip |
cmd/asm, cmd/compile, runtime: add -spectre=ret mode
This commit extends the -spectre flag to cmd/asm and adds
a new Spectre mitigation mode "ret", which enables the use
of retpolines.
Retpolines prevent speculation about the target of an indirect
jump or call and are described in more detail here:
https://support.google.com/faqs/answer/7625886
Change-Id: I4f2cb982fa94e44d91e49bd98974fd125619c93a
Reviewed-on: https://go-review.googlesource.com/c/go/+/222661
Reviewed-by: Keith Randall <khr@golang.org>
Diffstat (limited to 'src/runtime/asm_amd64.s')
-rw-r--r-- | src/runtime/asm_amd64.s | 34 |
1 files changed, 33 insertions, 1 deletions
diff --git a/src/runtime/asm_amd64.s b/src/runtime/asm_amd64.s index c191599c28..b872b8834d 100644 --- a/src/runtime/asm_amd64.s +++ b/src/runtime/asm_amd64.s @@ -510,7 +510,8 @@ TEXT NAME(SB), WRAPPER, $MAXSIZE-32; \ /* call function */ \ MOVQ f+8(FP), DX; \ PCDATA $PCDATA_StackMapIndex, $0; \ - CALL (DX); \ + MOVQ (DX), AX; \ + CALL AX; \ /* copy return values back */ \ MOVQ argtype+0(FP), DX; \ MOVQ argptr+16(FP), DI; \ @@ -1743,3 +1744,34 @@ TEXT runtime·panicSlice3CU(SB),NOSPLIT,$0-16 DATA runtime·tls_g+0(SB)/8, $16 GLOBL runtime·tls_g+0(SB), NOPTR, $8 #endif + +// The compiler and assembler's -spectre=ret mode rewrites +// all indirect CALL AX / JMP AX instructions to be +// CALL retpolineAX / JMP retpolineAX. +// See https://support.google.com/faqs/answer/7625886. +#define RETPOLINE(reg) \ + /* CALL setup */ BYTE $0xE8; BYTE $(2+2); BYTE $0; BYTE $0; BYTE $0; \ + /* nospec: */ \ + /* PAUSE */ BYTE $0xF3; BYTE $0x90; \ + /* JMP nospec */ BYTE $0xEB; BYTE $-(2+2); \ + /* setup: */ \ + /* MOVQ AX, 0(SP) */ BYTE $0x48|((reg&8)>>1); BYTE $0x89; \ + BYTE $0x04|((reg&7)<<3); BYTE $0x24; \ + /* RET */ BYTE $0xC3 + +TEXT runtime·retpolineAX(SB),NOSPLIT,$0; RETPOLINE(0) +TEXT runtime·retpolineCX(SB),NOSPLIT,$0; RETPOLINE(1) +TEXT runtime·retpolineDX(SB),NOSPLIT,$0; RETPOLINE(2) +TEXT runtime·retpolineBX(SB),NOSPLIT,$0; RETPOLINE(3) +/* SP is 4, can't happen / magic encodings */ +TEXT runtime·retpolineBP(SB),NOSPLIT,$0; RETPOLINE(5) +TEXT runtime·retpolineSI(SB),NOSPLIT,$0; RETPOLINE(6) +TEXT runtime·retpolineDI(SB),NOSPLIT,$0; RETPOLINE(7) +TEXT runtime·retpolineR8(SB),NOSPLIT,$0; RETPOLINE(8) +TEXT runtime·retpolineR9(SB),NOSPLIT,$0; RETPOLINE(9) +TEXT runtime·retpolineR10(SB),NOSPLIT,$0; RETPOLINE(10) +TEXT runtime·retpolineR11(SB),NOSPLIT,$0; RETPOLINE(11) +TEXT runtime·retpolineR12(SB),NOSPLIT,$0; RETPOLINE(12) +TEXT runtime·retpolineR13(SB),NOSPLIT,$0; RETPOLINE(13) +TEXT runtime·retpolineR14(SB),NOSPLIT,$0; RETPOLINE(14) +TEXT runtime·retpolineR15(SB),NOSPLIT,$0; RETPOLINE(15) |