Print this page
11787 Kernel needs to be built with retpolines
11788 Kernel needs to generally use RSB stuffing
Reviewed by: Jerry Jelinek <jerry.jelinek@joyent.com>
Reviewed by: John Levon <john.levon@joyent.com>

@@ -19,11 +19,11 @@
  * CDDL HEADER END
  */
 
 /*
  * Copyright (c) 1992, 2010, Oracle and/or its affiliates. All rights reserved.
- * Copyright (c) 2017, Joyent, Inc. All rights reserved.
+ * Copyright 2019 Joyent, Inc.
  */
 
 #include <sys/asm_linkage.h>
 
 #if defined(__lint)

@@ -89,12 +89,10 @@
 
 /*
  * This file contains the stubs routines for modules which can be autoloaded.
  */
 
-#if defined(__amd64)
-
 /*
  * See the 'struct mod_modinfo' definition to see what this declaration
  * is trying to achieve here.
  */
 #define MODULE(module,namespace)        \

@@ -128,11 +126,12 @@
         leaq    fcnname/**/_info(%rip), %rax;                           \
         cmpl    $0, MODS_FLAG(%rax);                    /* weak? */     \
         je      stubs_common_code;                      /* not weak */  \
         testb   $MODS_INSTALLED, MODS_FLAG(%rax);       /* installed? */ \
         jne     stubs_common_code;              /* yes, do the mod_hold */ \
-        jmp     *MODS_RETFCN(%rax);             /* no, jump to retfcn */ \
+        movq    MODS_RETFCN(%rax), %rax;        /* no, load retfcn */   \
+        INDIRECT_JMP_REG(rax);                  /* no, jump to retfcn */ \
         SET_SIZE(fcnname);                                              \
         .data;                                                          \
         .align   CPTRSIZE;                                              \
         .type   fcnname/**/_info, @object;                              \
 fcnname/**/_info:                                                       \

@@ -146,14 +145,16 @@
 #define STUB_NO_UNLOADABLE(module, fcnname, install_fcn, retfcn, weak)  \
         ENTRY(fcnname);                                                 \
         leaq    fcnname/**/_info(%rip), %rax;                           \
         testb   $MODS_INSTALLED, MODS_FLAG(%rax); /* installed? */      \
         je      5f;                     /* no */                        \
-        jmp     *(%rax);                /* yes, jump to install_fcn */  \
+        movq    MODS_INSTFCN(%rax), %rax; /* yes, load install_fcn */   \
+        INDIRECT_JMP_REG(rax);          /* yes, jump to install_fcn */  \
 5:      testb   $MODS_WEAK, MODS_FLAG(%rax);    /* weak? */             \
         je      stubs_common_code;      /* no, do mod load */           \
-        jmp     *MODS_RETFCN(%rax);     /* yes, jump to retfcn */       \
+        movq    MODS_RETFCN(%rax), %rax; /* yes, load retfcn */         \
+        INDIRECT_JMP_REG(rax);          /* yes, jump to retfcn */       \
         SET_SIZE(fcnname);                                              \
         .data;                                                          \
         .align  CPTRSIZE;                                               \
         .type   fcnname/**/_info, @object;                              \
 fcnname/**/_info:                                                       \

@@ -188,11 +189,11 @@
         movq    %r15, %rdi
         call    mod_hold_stub           /* mod_hold_stub(mod_stub_info *) */
         cmpl    $-1, %eax               /* error? */
         jne     .L1
         movq    0x18(%r15), %rax
-        call    *%rax
+        INDIRECT_CALL_REG(rax)
         addq    $0x30, %rsp
         jmp     .L2
 .L1:
         /*
          * copy MAXNARG == 10 incoming arguments

@@ -217,11 +218,12 @@
         movl    $MAXNARG - 6 + 3, %r11d
         pushq   (%rsp, %r11, 8)
         pushq   (%rsp, %r11, 8)
         pushq   (%rsp, %r11, 8)
         pushq   (%rsp, %r11, 8)
-        call    *(%r15)                 /* call the stub fn(arg, ..) */
+        movq    (%r15), %rax
+        INDIRECT_CALL_REG(rax)          /* call the stub fn(arg, ..) */
         addq    $0x20, %rsp             /* pop off last 4 args */
         pushq   %rax                    /* save any return values */
         pushq   %rdx
         movq    %r15, %rdi
         call    mod_release_stub        /* release hold on module */

@@ -231,138 +233,10 @@
         popq    %r15
         leave
         ret
         SET_SIZE(stubs_common_code)
 
-#elif defined(__i386)
-
-/*
- * See the 'struct mod_modinfo' definition to see what this declaration
- * is trying to achieve here.
- */
-#define MODULE(module,namespace)        \
-        .data;                          \
-module/**/_modname:                     \
-        .string "namespace/module";     \
-        SET_SIZE(module/**/_modname);   \
-        .align  CPTRSIZE;               \
-        .globl  module/**/_modinfo;     \
-        .type   module/**/_modinfo, @object;    \
-module/**/_modinfo:                     \
-        .long   module/**/_modname;     \
-        .long   0       /* storage for modctl pointer */
-
-        /* then mod_stub_info structures follow until a mods_func_adr is 0 */
-
-/* this puts a 0 where the next mods_func_adr would be */
-#define END_MODULE(module)              \
-        .data;                          \
-        .align  CPTRSIZE;               \
-        .long 0;                        \
-        SET_SIZE(module/**/_modinfo)
-
-/*
- * The data section in the stub_common macro is the
- * mod_stub_info structure for the stub function
- */
-
-/*      
- * The flag MODS_INSTALLED is stored in the stub data and is used to
- * indicate if a module is installed and initialized.  This flag is used
- * instead of the mod_stub_info->mods_modinfo->mod_installed flag
- * to minimize the number of pointer de-references for each function
- * call (and also to avoid possible TLB misses which could be induced
- * by dereferencing these pointers.)
- */     
-
-#define STUB_COMMON(module, fcnname, install_fcn, retfcn, weak)         \
-        ENTRY(fcnname);                                                 \
-        leal    fcnname/**/_info, %eax;                                 \
-        cmpl    $0, MODS_FLAG(%eax);    /* weak? */                     \
-        je      stubs_common_code;      /* not weak */                  \
-        testb   $MODS_INSTALLED, MODS_FLAG(%eax); /* installed? */      \
-        jne     stubs_common_code;      /* yes, do the mod_hold */      \
-        jmp     *MODS_RETFCN(%eax);     /* no, just jump to retfcn */   \
-        SET_SIZE(fcnname);                                              \
-        .data;                                                          \
-        .align   CPTRSIZE;                                              \
-        .type   fcnname/**/_info, @object;                              \
-fcnname/**/_info:                                                       \
-        .long   install_fcn;                                            \
-        .long   module/**/_modinfo;                                     \
-        .long   fcnname;                                                \
-        .long   retfcn;                                                 \
-        .long   weak;                                                   \
-        SET_SIZE(fcnname/**/_info)
-        
-#define STUB_NO_UNLOADABLE(module, fcnname, install_fcn, retfcn, weak)  \
-        ENTRY(fcnname);                                                 \
-        leal    fcnname/**/_info, %eax;                                 \
-        testb   $MODS_INSTALLED, MODS_FLAG(%eax); /* installed? */      \
-        je      5f;             /* no */                                \
-        jmp     *(%eax);        /* yes, just jump to install_fcn */     \
-5:      testb   $MODS_WEAK, MODS_FLAG(%eax);    /* weak? */             \
-        je      stubs_common_code;      /* no, do mod load */           \
-        jmp     *MODS_RETFCN(%eax);     /* yes, just jump to retfcn */  \
-        SET_SIZE(fcnname);                                              \
-        .data;                                                          \
-        .align  CPTRSIZE;                                               \
-        .type   fcnname/**/_info, @object;                              \
-fcnname/**/_info:                                                       \
-        .long   install_fcn;            /* 0 */                         \
-        .long   module/**/_modinfo;     /* 0x4 */                       \
-        .long   fcnname;                /* 0x8 */                       \
-        .long   retfcn;                 /* 0xc */                       \
-        .long   weak;                   /* 0x10 */                      \
-        SET_SIZE(fcnname/**/_info)
-
-/*
- * We branch here with the fcnname_info pointer in %eax
- */
-        ENTRY_NP(stubs_common_code)
-        .globl  mod_hold_stub
-        .globl  mod_release_stub
-        pushl   %esi
-        movl    %eax, %esi              / save the info pointer
-        pushl   %eax
-        call    mod_hold_stub           / mod_hold_stub(mod_stub_info *)
-        popl    %ecx
-        cmpl    $-1, %eax               / error?
-        jne     .L1
-        movl    MODS_RETFCN(%esi), %eax
-        call    *%eax   
-        popl    %esi                    / yes, return error (panic?)
-        ret
-.L1:
-        movl    $MAXNARG+1, %ecx
-        / copy incoming arguments
-        pushl   (%esp, %ecx, 4)         / push MAXNARG times
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        pushl   (%esp, %ecx, 4)
-        call    *(%esi)                 / call the stub function(arg1,arg2, ...)
-        add     $_MUL(MAXNARG, 4), %esp / pop off MAXNARG arguments
-        pushl   %eax                    / save any return values from the stub
-        pushl   %edx
-        pushl   %esi
-        call    mod_release_stub        / release hold on module
-        addl    $4, %esp
-        popl    %edx                    / restore return values
-        popl    %eax
-.L2:
-        popl    %esi
-        ret
-        SET_SIZE(stubs_common_code)
-
-#endif  /* __i386 */
-
 #define STUB(module, fcnname, retfcn)   \
     STUB_COMMON(module, fcnname, mod_hold_stub, retfcn, 0)
 
 /*
  * "weak stub", don't load on account of this call

@@ -1408,14 +1282,12 @@
  */
 #ifndef ELFEXEC_MODULE
         MODULE(elfexec,exec);
         STUB(elfexec, elfexec,          nomod_einval);
         STUB(elfexec, mapexec_brand,    nomod_einval);
-#if defined(__amd64)
         STUB(elfexec, elf32exec,        nomod_einval);
         STUB(elfexec, mapexec32_brand,  nomod_einval);
-#endif
         END_MODULE(elfexec);
 #endif
 
 /*
  * Stub(s) for APIX module.

@@ -1424,11 +1296,13 @@
         MODULE(apix,mach);
         WSTUB(apix, apix_loaded, nomod_zero);
         END_MODULE(apix);
 #endif
 
-/ this is just a marker for the area of text that contains stubs 
+/*
+ * this is just a marker for the area of text that contains stubs
+ */
 
         ENTRY_NP(stubs_end)
         nop
 
 #endif  /* lint */