Home | History | Annotate | Download | only in Sema
      1 // REQUIRES: x86-registered-target
      2 // RUN: %clang_cc1 %s -triple x86_64-apple-darwin10 -fms-extensions -fasm-blocks -Wno-microsoft -Wunused-label -verify -fsyntax-only
      3 
      4 void t1(void) {
      5  __asm __asm // expected-error {{__asm used with no assembly instructions}}
      6 }
      7 
      8 void f() {
      9   int foo;
     10   __asm {
     11     mov eax, eax
     12     .unknowndirective // expected-error {{unknown directive}}
     13   }
     14   f();
     15   __asm {
     16     mov eax, 1+=2 // expected-error {{unknown token in expression}}
     17   }
     18   f();
     19   __asm {
     20     mov eax, 1+++ // expected-error {{unknown token in expression}}
     21   }
     22   f();
     23   __asm {
     24     mov eax, LENGTH bar // expected-error {{unable to lookup expression}}
     25   }
     26   f();
     27   __asm {
     28     mov eax, SIZE bar // expected-error {{unable to lookup expression}}
     29   }
     30   f();
     31   __asm {
     32     mov eax, TYPE bar // expected-error {{unable to lookup expression}} expected-error {{use of undeclared label 'bar'}}
     33   }
     34 }
     35 
     36 void rdar15318432(void) {
     37   // We used to crash on this.  When LLVM called back to Clang to parse a name
     38   // and do name lookup, if parsing failed, we did not restore the lexer state
     39   // properly.
     40 
     41   __asm {
     42     and ecx, ~15
     43   }
     44 
     45   int x = 0;
     46   __asm {
     47     and ecx, x
     48     and ecx, ~15
     49   }
     50 }
     51 
     52 static int global;
     53 
     54 int t2(int *arr, int i) {
     55   __asm {
     56     mov eax, arr;
     57     mov eax, arr[0];
     58     mov eax, arr[1 + 2];
     59     mov eax, arr[1 + (2 * 5) - 3 + 1<<1];
     60   }
     61 
     62   // expected-error@+1 {{cannot use base register with variable reference}}
     63   __asm { mov eax, arr[ebp + 1 + (2 * 5) - 3 + 1<<1] }
     64   // expected-error@+1 {{cannot use index register with variable reference}}
     65   __asm { mov eax, arr[esi * 4] }
     66   // expected-error@+1 {{cannot use more than one symbol in memory operand}}
     67   __asm { mov eax, arr[i] }
     68   // expected-error@+1 {{cannot use more than one symbol in memory operand}}
     69   __asm { mov eax, global[i] }
     70 
     71   // FIXME: Why don't we diagnose this?
     72   // expected-Xerror@+1 {{cannot reference multiple local variables in assembly operand}}
     73   //__asm mov eax, [arr + i];
     74   return 0;
     75 }
     76 
     77 typedef struct {
     78   int a;
     79   int b;
     80 } A;
     81 
     82 void t3() {
     83   __asm { mov eax, [eax] UndeclaredId } // expected-error {{unknown token in expression}} expected-error {{use of undeclared label 'UndeclaredId'}}
     84 
     85   // FIXME: Only emit one diagnostic here.
     86   // expected-error@+3 {{use of undeclared label 'A'}}
     87   // expected-error@+2 {{unexpected type name 'A': expected expression}}
     88   // expected-error@+1 {{unknown token in expression}}
     89   __asm { mov eax, [eax] A }
     90 }
     91 
     92 void t4() {
     93   // The dot in the "intel dot operator" is optional in MSVC.  MSVC also does
     94   // global field lookup, but we don't.
     95   __asm { mov eax, [0] A.a }
     96   __asm { mov eax, [0].A.a }
     97   __asm { mov eax, [0].a } // expected-error {{Unable to lookup field reference!}}
     98   __asm { mov eax, fs:[0] A.a }
     99   __asm { mov eax, fs:[0].A.a }
    100   __asm { mov eax, fs:[0].a } // expected-error {{Unable to lookup field reference!}}
    101   __asm { mov eax, fs:[0]. A.a } // expected-error {{Unexpected token type!}}
    102 }
    103 
    104 void test_operand_size() {
    105   __asm { call word t4 } // expected-error {{Expected 'PTR' or 'ptr' token!}}
    106 }
    107 
    108 __declspec(naked) int t5(int x) { // expected-note {{attribute is here}}
    109   asm { movl eax, x } // expected-error {{parameter references not allowed in naked functions}} expected-error {{use of undeclared label 'x'}}
    110   asm { retl }
    111 }
    112 
    113 int y;
    114 __declspec(naked) int t6(int x) {
    115   asm { mov eax, y } // No error.
    116   asm { ret }
    117 }
    118 
    119 void t7() {
    120   __asm {
    121     foo: // expected-note {{inline assembly label 'foo' declared here}}
    122     mov eax, 0
    123   }
    124   goto foo; // expected-error {{cannot jump from this goto statement to label 'foo' inside an inline assembly block}}
    125 }
    126 
    127 void t8() {
    128   __asm foo: // expected-note {{inline assembly label 'foo' declared here}}
    129   __asm mov eax, 0
    130   goto foo; // expected-error {{cannot jump from this goto statement to label 'foo' inside an inline assembly block}}
    131 }
    132 
    133 void t9() {
    134   goto foo; // expected-error {{cannot jump from this goto statement to label 'foo' inside an inline assembly block}}
    135   __asm {
    136     foo: // expected-note {{inline assembly label 'foo' declared here}}
    137     mov eax, 0
    138   }
    139 }
    140 
    141 void t10() {
    142   goto foo; // expected-error {{cannot jump from this goto statement to label 'foo' inside an inline assembly block}}
    143   __asm foo: // expected-note {{inline assembly label 'foo' declared here}}
    144   __asm mov eax, 0
    145 }
    146 
    147 void t11() {
    148 foo:
    149   __asm mov eax, foo // expected-error {{use of undeclared label 'foo'}} expected-warning {{unused label 'foo'}}
    150 }
    151 
    152 void t12() {
    153   __asm foo:
    154   __asm bar: // expected-warning {{unused label 'bar'}}
    155   __asm jmp foo
    156 }
    157