Home | History | Annotate | Download | only in x86_64
      1 /*
      2  * Copyright (C) 2013 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #ifndef ART_RUNTIME_ARCH_X86_64_ASM_SUPPORT_X86_64_S_
     18 #define ART_RUNTIME_ARCH_X86_64_ASM_SUPPORT_X86_64_S_
     19 
     20 #include "asm_support_x86_64.h"
     21 
     22 // Regular gas(1) & current clang/llvm assembler support named macro parameters.
     23 #define MACRO0(macro_name) .macro macro_name
     24 #define MACRO1(macro_name, macro_arg1) .macro macro_name macro_arg1
     25 #define MACRO2(macro_name, macro_arg1, macro_arg2) .macro macro_name macro_arg1, macro_arg2
     26 #define MACRO3(macro_name, macro_arg1, macro_arg2, macro_arg3) .macro macro_name macro_arg1, macro_arg2, macro_arg3
     27 #define MACRO4(macro_name, macro_arg1, macro_arg2, macro_arg3, macro_arg4) .macro macro_name macro_arg1, macro_arg2, macro_arg3, macro_arg4
     28 #define END_MACRO .endm
     29 
     30 #if defined(__clang__)
     31     // Clang/llvm does not support .altmacro. However, the clang/llvm preprocessor doesn't
     32     // separate the backslash and parameter by a space. Everything just works.
     33     #define RAW_VAR(name) \name
     34     #define VAR(name) SYMBOL(\name)
     35     #define PLT_VAR(name) \name@PLT
     36     #define REG_VAR(name) %\name
     37     #define CALL_MACRO(name) \name
     38 #else
     39     // Regular gas(1) uses \argument_name for macro arguments.
     40     // We need to turn on alternate macro syntax so we can use & instead or the preprocessor
     41     // will screw us by inserting a space between the \ and the name. Even in this mode there's
     42     // no special meaning to $, so literals are still just $x. The use of altmacro means % is a
     43     // special character meaning care needs to be taken when passing registers as macro
     44     // arguments.
     45     .altmacro
     46     #define RAW_VAR(name) name&
     47     #define VAR(name) name&
     48     #define PLT_VAR(name) name&@PLT
     49     #define REG_VAR(name) %name
     50     #define CALL_MACRO(name) name&
     51 #endif
     52 
     53 #define LITERAL(value) $value
     54 #if defined(__APPLE__)
     55     #define MACRO_LITERAL(value) $$(value)
     56 #else
     57     #define MACRO_LITERAL(value) $value
     58 #endif
     59 
     60 #if defined(__APPLE__)
     61     #define FUNCTION_TYPE(name)
     62     #define SIZE(name)
     63 #else
     64     #define FUNCTION_TYPE(name) .type name, @function
     65     #define SIZE(name) .size name, .-name
     66 #endif
     67 
     68     // CFI support.
     69 #if !defined(__APPLE__)
     70     #define CFI_STARTPROC .cfi_startproc
     71     #define CFI_ENDPROC .cfi_endproc
     72     #define CFI_ADJUST_CFA_OFFSET(size) .cfi_adjust_cfa_offset size
     73     #define CFI_DEF_CFA(reg,size) .cfi_def_cfa reg,size
     74     #define CFI_DEF_CFA_REGISTER(reg) .cfi_def_cfa_register reg
     75     #define CFI_RESTORE(reg) .cfi_restore reg
     76     #define CFI_REL_OFFSET(reg,size) .cfi_rel_offset reg,size
     77 #else
     78     // Mac OS' doesn't like cfi_* directives.
     79     #define CFI_STARTPROC
     80     #define CFI_ENDPROC
     81     #define CFI_ADJUST_CFA_OFFSET(size)
     82     #define CFI_DEF_CFA(reg,size)
     83     #define CFI_DEF_CFA_REGISTER(reg)
     84     #define CFI_RESTORE(reg)
     85     #define CFI_REL_OFFSET(reg,size)
     86 #endif
     87 
     88     // Symbols.
     89 #if !defined(__APPLE__)
     90     #define SYMBOL(name) name
     91     #define PLT_SYMBOL(name) name ## @PLT
     92 #else
     93     #define SYMBOL(name) _ ## name
     94     #define PLT_SYMBOL(name) _ ## name
     95 #endif
     96 
     97 // Directive to hide a function symbol.
     98 #if defined(__APPLE__)
     99     #define ASM_HIDDEN .private_extern
    100 #else
    101     #define ASM_HIDDEN .hidden
    102 #endif
    103 
    104     /* Cache alignment for function entry */
    105 MACRO0(ALIGN_FUNCTION_ENTRY)
    106     .balign 16
    107 END_MACRO
    108 
    109 // TODO: we might need to use SYMBOL() here to add the underscore prefix
    110 // for mac builds.
    111 MACRO1(DEFINE_FUNCTION, c_name)
    112     FUNCTION_TYPE(SYMBOL(\c_name))
    113     ASM_HIDDEN SYMBOL(\c_name)
    114     .globl VAR(c_name)
    115     ALIGN_FUNCTION_ENTRY
    116 VAR(c_name):
    117     CFI_STARTPROC
    118     // Ensure we get a sane starting CFA.
    119     CFI_DEF_CFA(rsp, 8)
    120 END_MACRO
    121 
    122 MACRO1(END_FUNCTION, c_name)
    123     CFI_ENDPROC
    124     SIZE(SYMBOL(\c_name))
    125 END_MACRO
    126 
    127 MACRO1(PUSH, reg)
    128     pushq REG_VAR(reg)
    129     CFI_ADJUST_CFA_OFFSET(8)
    130     CFI_REL_OFFSET(REG_VAR(reg), 0)
    131 END_MACRO
    132 
    133 MACRO1(POP, reg)
    134     popq REG_VAR(reg)
    135     CFI_ADJUST_CFA_OFFSET(-8)
    136     CFI_RESTORE(REG_VAR(reg))
    137 END_MACRO
    138 
    139 MACRO1(UNIMPLEMENTED,name)
    140     FUNCTION_TYPE(SYMBOL(\name))
    141     ASM_HIDDEN VAR(name)
    142     .globl VAR(name)
    143     ALIGN_FUNCTION_ENTRY
    144 VAR(name):
    145     CFI_STARTPROC
    146     int3
    147     int3
    148     CFI_ENDPROC
    149     SIZE(SYMBOL(\name))
    150 END_MACRO
    151 
    152 MACRO0(UNREACHABLE)
    153     int3
    154 END_MACRO
    155 
    156 MACRO0(UNTESTED)
    157     int3
    158 END_MACRO
    159 
    160 // Macros to poison (negate) the reference for heap poisoning.
    161 MACRO1(POISON_HEAP_REF, rRef)
    162 #ifdef USE_HEAP_POISONING
    163     negl REG_VAR(rRef)
    164 #endif  // USE_HEAP_POISONING
    165 END_MACRO
    166 
    167 // Macros to unpoison (negate) the reference for heap poisoning.
    168 MACRO1(UNPOISON_HEAP_REF, rRef)
    169 #ifdef USE_HEAP_POISONING
    170     negl REG_VAR(rRef)
    171 #endif  // USE_HEAP_POISONING
    172 END_MACRO
    173 
    174 #endif  // ART_RUNTIME_ARCH_X86_64_ASM_SUPPORT_X86_64_S_
    175