VirtualBox

Changeset 97052 in vbox


Ignore:
Timestamp:
Oct 7, 2022 9:50:54 PM (2 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
154001
Message:

VMM/hmvmxinline.h: Attempt at proper vmread inline assembly for GCC.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/include/VBox/vmm/hmvmxinline.h

    r96407 r97052  
    5757#else
    5858# define VMX_USE_MSC_INTRINSICS 0
     59#endif
     60
     61/**
     62 * Whether we think the assembler supports VMX instructions.
     63 *
     64 * Guess that GCC 5 should have sufficient recent enough binutils.
     65 */
     66#if RT_INLINE_ASM_GNU_STYLE && RT_GNUC_PREREQ(5,0)
     67# define VMX_USE_GNU_STYLE_INLINE_VMX_INSTRUCTIONS 1
     68#else
     69# define VMX_USE_GNU_STYLE_INLINE_VMX_INSTRUCTIONS 0
     70#endif
     71
     72/** Whether we can use the subsection trick to put error handling code
     73 *  elsewhere. */
     74#if VMX_USE_GNU_STYLE_INLINE_VMX_INSTRUCTIONS && defined(__ELF__)
     75# define VMX_USE_GNU_STYLE_INLINE_SECTION_TRICK 1
     76#else
     77# define VMX_USE_GNU_STYLE_INLINE_SECTION_TRICK 0
    5978#endif
    6079
     
    885904#  endif
    886905
     906# elif VMX_USE_GNU_STYLE_INLINE_VMX_INSTRUCTIONS
     907    RTCCUINTREG uTmp = 0;
     908#  ifdef VBOX_WITH_VMREAD_VMWRITE_NOCHECK
     909    __asm__ __volatile__("vmread  %[uField],%[uDst]"
     910                         : [uDst] "=mr" (uTmp)
     911                         : [uField] "r" ((RTCCUINTREG)uFieldEnc));
     912    *pData = (uint32_t)uTmp;
     913    return VINF_SUCCESS;
     914#  else
     915#if 0
     916    int      rc;
     917    __asm__ __volatile__("vmread  %[uField],%[uDst]\n\t"
     918                         "movl    %[rcSuccess],%[rc]\n\t"
     919#    if VMX_USE_GNU_STYLE_INLINE_SECTION_TRICK
     920                         "jna     1f\n\t"
     921                         ".section .text.vmread_failures, \"ax?\"\n\t"
     922                         "1:\n\t"
     923                         "movl    %[rcInvalidVmcsPtr],%[rc]\n\t"
     924                         "jnz     2f\n\t"
     925                         "movl    %[rcInvalidVmcsField],%[rc]\n\t"
     926                         "2:\n\t"
     927                         "jmp     3f\n\t"
     928                         ".previous\n\t"
     929                         "3:\n\t"
     930#    else
     931                         "ja      1f\n\t"
     932                         "movl    %[rcInvalidVmcsPtr],%[rc]\n\t"
     933                         "jnz     1f\n\t"
     934                         "movl    %[rcInvalidVmcsField],%[rc]\n\t"
     935                         "1:\n\t"
     936#    endif
     937                         : [uDst] "=mr" (uTmp)
     938                         , [rc] "=r" (rc)
     939                         : [uField] "r" ((RTCCUINTREG)uFieldEnc)
     940                         , [rcSuccess] "i" (VINF_SUCCESS)
     941                         , [rcInvalidVmcsPtr] "i" (VERR_VMX_INVALID_VMCS_PTR)
     942                         , [rcInvalidVmcsField] "i" (VERR_VMX_INVALID_VMCS_FIELD));
     943    *pData = uTmp;
     944    return rc;
     945#else
     946    int fSuccess, fFieldError;
     947    __asm__ __volatile__("vmread  %[uField],%[uDst]"
     948                         : [uDst] "=mr" (uTmp)
     949                         , "=@cca" (fSuccess)
     950                         , "=@ccnc" (fFieldError)
     951                         : [uField] "r" ((RTCCUINTREG)uFieldEnc));
     952    *pData = uTmp;
     953    return RT_LIKELY(fSuccess) ? VINF_SUCCESS : fFieldError ? VERR_VMX_INVALID_VMCS_FIELD : VERR_VMX_INVALID_VMCS_PTR;
     954#endif
     955#  endif
     956
    887957# elif RT_INLINE_ASM_GNU_STYLE
    888958#  ifdef VBOX_WITH_VMREAD_VMWRITE_NOCHECK
     
    9751045#  endif
    9761046
     1047# elif VMX_USE_GNU_STYLE_INLINE_VMX_INSTRUCTIONS
     1048    uint64_t uTmp = 0;
     1049#  ifdef VBOX_WITH_VMREAD_VMWRITE_NOCHECK
     1050    __asm__ __volatile__("vmreadq %[uField],%[uDst]"
     1051                         : [uDst] "=m" (uTmp)
     1052                         : [uField] "r" ((uint64_t)uFieldEnc));
     1053    *pData = uTmp;
     1054    return VINF_SUCCESS;
     1055#  elif 0
     1056    int      rc;
     1057    __asm__ __volatile__("vmreadq %[uField],%[uDst]\n\t"
     1058                         "movl    %[rcSuccess],%[rc]\n\t"
     1059#    if VMX_USE_GNU_STYLE_INLINE_SECTION_TRICK
     1060                         "jna     1f\n\t"
     1061                         ".section .text.vmread_failures, \"ax?\"\n\t"
     1062                         "1:\n\t"
     1063                         "movl    %[rcInvalidVmcsPtr],%[rc]\n\t"
     1064                         "jnz     2f\n\t"
     1065                         "movl    %[rcInvalidVmcsField],%[rc]\n\t"
     1066                         "2:\n\t"
     1067                         "jmp     3f\n\t"
     1068                         ".previous\n\t"
     1069                         "3:\n\t"
     1070#    else
     1071                         "ja      1f\n\t"
     1072                         "movl    %[rcInvalidVmcsPtr],%[rc]\n\t"
     1073                         "jnz     1f\n\t"
     1074                         "movl    %[rcInvalidVmcsField],%[rc]\n\t"
     1075                         "1:\n\t"
     1076#    endif
     1077                         : [uDst] "=mr" (uTmp)
     1078                         , [rc] "=r" (rc)
     1079                         : [uField] "r" ((uint64_t)uFieldEnc)
     1080                         , [rcSuccess] "i" (VINF_SUCCESS)
     1081                         , [rcInvalidVmcsPtr] "i" (VERR_VMX_INVALID_VMCS_PTR)
     1082                         , [rcInvalidVmcsField] "i" (VERR_VMX_INVALID_VMCS_FIELD)
     1083                         );
     1084    *pData = uTmp;
     1085    return rc;
     1086#  else
     1087    int fSuccess, fFieldError;
     1088    __asm__ __volatile__("vmread  %[uField],%[uDst]"
     1089                         : [uDst] "=mr" (uTmp)
     1090                         , "=@cca" (fSuccess)
     1091                         , "=@ccnc" (fFieldError)
     1092                         : [uField] "r" ((RTCCUINTREG)uFieldEnc));
     1093    *pData = uTmp;
     1094    return RT_LIKELY(fSuccess) ? VINF_SUCCESS : fFieldError ? VERR_VMX_INVALID_VMCS_FIELD : VERR_VMX_INVALID_VMCS_PTR;
     1095#  endif
     1096
    9771097# elif RT_INLINE_ASM_GNU_STYLE
    9781098#  ifdef VBOX_WITH_VMREAD_VMWRITE_NOCHECK
     
    10031123    return rc;
    10041124#  endif
     1125
    10051126# else
    10061127#  error "Shouldn't be here..."
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette