| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120 |
- From 27298389d9d09bcebf06ea47206141b22fabcaca Mon Sep 17 00:00:00 2001
- From: Ingo Molnar <[email protected]>
- Date: Sat, 23 Dec 2017 13:14:25 +0100
- Subject: [PATCH 136/242] x86/insn-eval: Add utility functions to get segment
- selector
- MIME-Version: 1.0
- Content-Type: text/plain; charset=UTF-8
- Content-Transfer-Encoding: 8bit
- CVE-2017-5754
- When computing a linear address and segmentation is used, we need to know
- the base address of the segment involved in the computation. In most of
- the cases, the segment base address will be zero as in USER_DS/USER32_DS.
- However, it may be possible that a user space program defines its own
- segments via a local descriptor table. In such a case, the segment base
- address may not be zero. Thus, the segment base address is needed to
- calculate correctly the linear address.
- If running in protected mode, the segment selector to be used when
- computing a linear address is determined by either any of segment override
- prefixes in the instruction or inferred from the registers involved in the
- computation of the effective address; in that order. Also, there are cases
- when the segment override prefixes shall be ignored (i.e., code segments
- are always selected by the CS segment register; string instructions always
- use the ES segment register when using rDI register as operand). In long
- mode, segment registers are ignored, except for FS and GS. In these two
- cases, base addresses are obtained from the respective MSRs.
- For clarity, this process can be split into four steps (and an equal
- number of functions): determine if segment prefixes overrides can be used;
- parse the segment override prefixes, and use them if found; if not found
- or cannot be used, use the default segment registers associated with the
- operand registers. Once the segment register to use has been identified,
- read its value to obtain the segment selector.
- The method to obtain the segment selector depends on several factors. In
- 32-bit builds, segment selectors are saved into a pt_regs structure
- when switching to kernel mode. The same is also true for virtual-8086
- mode. In 64-bit builds, segmentation is mostly ignored, except when
- running a program in 32-bit legacy mode. In this case, CS and SS can be
- obtained from pt_regs. DS, ES, FS and GS can be read directly from
- the respective segment registers.
- In order to identify the segment registers, a new set of #defines is
- introduced. It also includes two special identifiers. One of them
- indicates when the default segment register associated with instruction
- operands shall be used. Another one indicates that the contents of the
- segment register shall be ignored; this identifier is used when in long
- mode.
- Improvements-by: Borislav Petkov <[email protected]>
- Signed-off-by: Ricardo Neri <[email protected]>
- Signed-off-by: Thomas Gleixner <[email protected]>
- Reviewed-by: Borislav Petkov <[email protected]>
- Cc: "Michael S. Tsirkin" <[email protected]>
- Cc: Peter Zijlstra <[email protected]>
- Cc: Dave Hansen <[email protected]>
- Cc: [email protected]
- Cc: Adrian Hunter <[email protected]>
- Cc: Paul Gortmaker <[email protected]>
- Cc: Huang Rui <[email protected]>
- Cc: Qiaowei Ren <[email protected]>
- Cc: Shuah Khan <[email protected]>
- Cc: Kees Cook <[email protected]>
- Cc: Jonathan Corbet <[email protected]>
- Cc: Jiri Slaby <[email protected]>
- Cc: Dmitry Vyukov <[email protected]>
- Cc: "Ravi V. Shankar" <[email protected]>
- Cc: Chris Metcalf <[email protected]>
- Cc: Brian Gerst <[email protected]>
- Cc: Arnaldo Carvalho de Melo <[email protected]>
- Cc: Andy Lutomirski <[email protected]>
- Cc: Colin Ian King <[email protected]>
- Cc: Chen Yucong <[email protected]>
- Cc: Adam Buchbinder <[email protected]>
- Cc: Vlastimil Babka <[email protected]>
- Cc: Lorenzo Stoakes <[email protected]>
- Cc: Masami Hiramatsu <[email protected]>
- Cc: Paolo Bonzini <[email protected]>
- Cc: Andrew Morton <[email protected]>
- Cc: Thomas Garnier <[email protected]>
- Link: https://lkml.kernel.org/r/1509135945-13762-14-git-send-email-ricardo.neri-calderon@linux.intel.com
- Signed-off-by: Ingo Molnar <[email protected]>
- (Partially cherry picked from commit 32d0b95300db03c2b23b2ea2c94769a4a138e79d)
- (cherry picked from commit ca2c18cb10c8beb56dfe21321abdddc724cec4de)
- Signed-off-by: Andy Whitcroft <[email protected]>
- Signed-off-by: Kleber Sacilotto de Souza <[email protected]>
- (cherry picked from commit abd7780592a3687eacc0a295d4d2959bb11ff75f)
- Signed-off-by: Fabian Grünbichler <[email protected]>
- ---
- arch/x86/include/asm/inat.h | 10 ++++++++++
- 1 file changed, 10 insertions(+)
- diff --git a/arch/x86/include/asm/inat.h b/arch/x86/include/asm/inat.h
- index 02aff0867211..1c78580e58be 100644
- --- a/arch/x86/include/asm/inat.h
- +++ b/arch/x86/include/asm/inat.h
- @@ -97,6 +97,16 @@
- #define INAT_MAKE_GROUP(grp) ((grp << INAT_GRP_OFFS) | INAT_MODRM)
- #define INAT_MAKE_IMM(imm) (imm << INAT_IMM_OFFS)
-
- +/* Identifiers for segment registers */
- +#define INAT_SEG_REG_IGNORE 0
- +#define INAT_SEG_REG_DEFAULT 1
- +#define INAT_SEG_REG_CS 2
- +#define INAT_SEG_REG_SS 3
- +#define INAT_SEG_REG_DS 4
- +#define INAT_SEG_REG_ES 5
- +#define INAT_SEG_REG_FS 6
- +#define INAT_SEG_REG_GS 7
- +
- /* Attribute search APIs */
- extern insn_attr_t inat_get_opcode_attribute(insn_byte_t opcode);
- extern int inat_get_last_prefix_id(insn_byte_t last_pfx);
- --
- 2.14.2
|