Mercurial > projects > ldc
annotate gen/asmstmt.cpp @ 227:3092a38dddab trunk
[svn r243] fixed inline asm arg_pointer args hopefully.
author | lindquist |
---|---|
date | Sat, 07 Jun 2008 19:19:30 +0200 |
parents | 4145266ff4bd |
children | cac3d27ae481 |
rev | line source |
---|---|
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
1 // Taken from GDC source tree, licence unclear? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
2 // |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
3 // Taken from an earlier version of DMD -- why is it missing from 0.79? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
4 |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
5 #include "gen/llvm.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
6 #include "llvm/InlineAsm.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
7 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
8 //#include "d-gcc-includes.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
9 //#include "total.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
10 #include "dmd/statement.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
11 #include "dmd/scope.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
12 #include "dmd/declaration.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
13 #include "dmd/dsymbol.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
14 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
15 #include <cassert> |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
16 #include <deque> |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
17 #include <iostream> |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
18 #include <sstream> |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
19 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
20 //#include "d-lang.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
21 //#include "d-codegen.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
22 |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
23 #include "gen/irstate.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
24 #include "gen/dvalue.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
25 #include "gen/tollvm.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
26 #include "gen/logger.h" |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
27 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
28 typedef enum { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
29 Arg_Integer, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
30 Arg_Pointer, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
31 Arg_Memory, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
32 Arg_FrameRelative, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
33 Arg_LocalSize, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
34 Arg_Dollar |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
35 } AsmArgType; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
36 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
37 typedef enum { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
38 Mode_Input, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
39 Mode_Output, |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
40 Mode_Update |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
41 } AsmArgMode; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
42 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
43 struct AsmArg { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
44 AsmArgType type; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
45 Expression * expr; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
46 AsmArgMode mode; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
47 AsmArg(AsmArgType type, Expression * expr, AsmArgMode mode) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
48 this->type = type; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
49 this->expr = expr; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
50 this->mode = mode; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
51 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
52 }; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
53 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
54 struct AsmCode { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
55 char * insnTemplate; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
56 unsigned insnTemplateLen; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
57 Array args; // of AsmArg |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
58 unsigned moreRegs; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
59 unsigned dollarLabel; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
60 int clobbersMemory; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
61 AsmCode() { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
62 insnTemplate = NULL; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
63 insnTemplateLen = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
64 moreRegs = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
65 dollarLabel = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
66 clobbersMemory = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
67 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
68 }; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
69 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
70 llvm::InlineAsm* |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
71 d_build_asm_stmt(std::string code, std::deque<DValue*> const& output_values, std::deque<DValue*> const& input_values, std::string constraints) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
72 { |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
73 std::vector<const LLType*> params; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
74 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
75 // outputs |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
76 const LLType* ret = LLType::VoidTy; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
77 if (!output_values.empty()) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
78 { |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
79 assert(output_values.size() == 1); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
80 const LLType* llty = DtoType(output_values[0]->getType()); |
225
74701ba40398
[svn r241] Fixed missing terminator for void main() with inline asm block.
lindquist
parents:
224
diff
changeset
|
81 std::cout << "out: " << *llty << '\n'; |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
82 params.push_back(llty); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
83 } |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
84 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
85 // inputs |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
86 if (!input_values.empty()) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
87 { |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
88 assert(input_values.size() == 1); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
89 const LLType* llty = DtoType(input_values[0]->getType()); |
225
74701ba40398
[svn r241] Fixed missing terminator for void main() with inline asm block.
lindquist
parents:
224
diff
changeset
|
90 std::cout << "in: " << *llty << '\n'; |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
91 params.push_back(llty); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
92 } |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
93 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
94 llvm::FunctionType* asmfnty = llvm::FunctionType::get(ret, params, false); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
95 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
96 std::cout << "function type: " << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
97 std::cout << *asmfnty << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
98 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
99 return llvm::InlineAsm::get(asmfnty, code, constraints, true); |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
100 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
101 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
102 AsmStatement::AsmStatement(Loc loc, Token *tokens) : |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
103 Statement(loc) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
104 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
105 this->tokens = tokens; // Do I need to copy these? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
106 asmcode = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
107 asmalign = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
108 refparam = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
109 naked = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
110 regs = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
111 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
112 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
113 Statement *AsmStatement::syntaxCopy() |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
114 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
115 // copy tokens? copy 'code'? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
116 AsmStatement * a_s = new AsmStatement(loc,tokens); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
117 a_s->asmcode = asmcode; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
118 a_s->refparam = refparam; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
119 a_s->naked = naked; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
120 a_s->regs = a_s->regs; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
121 return a_s; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
122 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
123 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
124 void AsmStatement::toCBuffer(OutBuffer *buf, HdrGenState *hgs) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
125 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
126 bool sep = 0, nsep = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
127 buf->writestring("asm { "); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
128 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
129 for (Token * t = tokens; t; t = t->next) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
130 switch (t->value) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
131 case TOKlparen: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
132 case TOKrparen: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
133 case TOKlbracket: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
134 case TOKrbracket: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
135 case TOKcolon: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
136 case TOKsemicolon: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
137 case TOKcomma: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
138 case TOKstring: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
139 case TOKcharv: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
140 case TOKwcharv: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
141 case TOKdcharv: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
142 nsep = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
143 break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
144 default: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
145 nsep = 1; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
146 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
147 if (sep + nsep == 2) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
148 buf->writeByte(' '); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
149 sep = nsep; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
150 buf->writestring(t->toChars()); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
151 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
152 buf->writestring("; }"); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
153 buf->writenl(); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
154 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
155 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
156 int AsmStatement::comeFrom() |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
157 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
158 return FALSE; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
159 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
160 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
161 /* GCC does not support jumps from asm statements. When optimization |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
162 is turned on, labels referenced only from asm statements will not |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
163 be output at the correct location. There are ways around this: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
164 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
165 1) Reference the label with a reachable goto statement |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
166 2) Have reachable computed goto in the function |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
167 3) Hack cfgbuild.c to act as though there is a computed goto. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
168 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
169 These are all pretty bad, but if would be nice to be able to tell |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
170 GCC not to optimize in this case (even on per label/block basis). |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
171 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
172 The current solution is output our own private labels (as asm |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
173 statements) along with the "real" label. If the label happens to |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
174 be referred to by a goto statement, the "real" label will also be |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
175 output in the correct location. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
176 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
177 Also had to add 'asmLabelNum' to LabelDsymbol to indicate it needs |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
178 special processing. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
179 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
180 (junk) d-lang.cc:916:case LABEL_DECL: // C doesn't do this. D needs this for referencing labels in inline assembler since there may be not goto referencing it. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
181 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
182 */ |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
183 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
184 static unsigned d_priv_asm_label_serial = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
185 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
186 // may need to make this target-specific |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
187 static void d_format_priv_asm_label(char * buf, unsigned n) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
188 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
189 //ASM_GENERATE_INTERNAL_LABEL(buf, "LDASM", n);//inserts a '*' for use with assemble_name |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
190 sprintf(buf, ".LDASM%u", n); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
191 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
192 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
193 void |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
194 d_expand_priv_asm_label(IRState * irs, unsigned n) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
195 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
196 /* char buf[64]; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
197 d_format_priv_asm_label(buf, n); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
198 strcat(buf, ":"); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
199 tree insnt = build_string(strlen(buf), buf); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
200 #if D_GCC_VER < 40 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
201 expand_asm(insnt, 1); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
202 #else |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
203 tree t = d_build_asm_stmt(insnt, NULL_TREE, NULL_TREE, NULL_TREE); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
204 ASM_VOLATILE_P( t ) = 1; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
205 ASM_INPUT_P( t) = 1; // what is this doing? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
206 irs->addExp(t); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
207 #endif*/ |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
208 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
209 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
210 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
211 // StringExp::toIR usually adds a NULL. We don't want that... |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
212 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
213 /*static tree |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
214 naturalString(Expression * e) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
215 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
216 // don't fail, just an error? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
217 assert(e->op == TOKstring); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
218 StringExp * s = (StringExp *) e; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
219 assert(s->sz == 1); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
220 return build_string(s->len, (char *) s->string); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
221 }*/ |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
222 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
223 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
224 #include "d-asm-i386.h" |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
225 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
226 bool d_have_inline_asm() { return true; } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
227 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
228 Statement *AsmStatement::semantic(Scope *sc) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
229 { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
230 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
231 sc->func->inlineAsm = 1; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
232 sc->func->inlineStatus = ILSno; // %% not sure |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
233 // %% need to set DECL_UNINLINABLE too? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
234 sc->func->hasReturnExp = 1; // %% DMD does this, apparently... |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
235 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
236 // empty statement -- still do the above things because they might be expected? |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
237 if (! tokens) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
238 return this; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
239 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
240 AsmProcessor ap(sc, this); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
241 ap.run(); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
242 return this; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
243 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
244 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
245 void |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
246 AsmStatement::toIR(IRState * irs) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
247 { |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
248 Logger::println("AsmStatement::toIR(): %s", loc.toChars()); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
249 LOG_SCOPE; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
250 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
251 // FIXME |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
252 // gen.doLineNote( loc ); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
253 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
254 if (! asmcode) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
255 return; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
256 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
257 static std::string i_cns = "i"; |
227
3092a38dddab
[svn r243] fixed inline asm arg_pointer args hopefully.
lindquist
parents:
226
diff
changeset
|
258 static std::string p_cns = "m"; |
222
251548c1035d
[svn r238] use *m for memory input constraints and pass in their address
ChristianK
parents:
221
diff
changeset
|
259 static std::string m_cns = "*m"; |
221
68687d8c3e9a
[svn r237] some inline asm output now seems to work, see tangotests/asm2.d
lindquist
parents:
220
diff
changeset
|
260 static std::string mw_cns = "=*m"; |
223
5ffca623b5df
[svn r239] also use indirect modifier for update constraints
ChristianK
parents:
222
diff
changeset
|
261 static std::string mrw_cns = "+*m"; |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
262 static std::string memory_name = "memory"; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
263 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
264 AsmCode * code = (AsmCode *) asmcode; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
265 std::deque<DValue*> input_values; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
266 std::deque<std::string> input_constraints; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
267 std::deque<DValue*> output_values; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
268 std::deque<std::string> output_constraints; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
269 std::deque<std::string> clobbers; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
270 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
271 // FIXME |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
272 #define HOST_WIDE_INT long |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
273 HOST_WIDE_INT var_frame_offset; // "frame_offset" is a macro |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
274 bool clobbers_mem = code->clobbersMemory; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
275 int input_idx = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
276 int n_outputs = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
277 int arg_map[10]; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
278 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
279 assert(code->args.dim <= 10); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
280 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
281 for (unsigned i = 0; i < code->args.dim; i++) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
282 AsmArg * arg = (AsmArg *) code->args.data[i]; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
283 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
284 bool is_input = true; |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
285 DValue* arg_val = 0; |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
286 std::string cns; |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
287 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
288 std::cout << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
289 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
290 switch (arg->type) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
291 case Arg_Integer: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
292 arg_val = arg->expr->toElem(irs); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
293 do_integer: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
294 cns = i_cns; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
295 break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
296 case Arg_Pointer: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
297 // FIXME |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
298 std::cout << "asm fixme Arg_Pointer" << std::endl; |
226
4145266ff4bd
[svn r242] fixed (I think) arg_pointer inline asm args
lindquist
parents:
225
diff
changeset
|
299 arg_val = arg->expr->toElem(irs); |
4145266ff4bd
[svn r242] fixed (I think) arg_pointer inline asm args
lindquist
parents:
225
diff
changeset
|
300 arg_val = new DVarValue(arg_val->getType()->pointerTo(), arg_val->getRVal(), true); |
4145266ff4bd
[svn r242] fixed (I think) arg_pointer inline asm args
lindquist
parents:
225
diff
changeset
|
301 /*if (arg->expr->op == TOKvar) |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
302 arg_val = arg->expr->toElem(irs); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
303 else if (arg->expr->op == TOKdsymbol) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
304 arg_val = arg->expr->toElem(irs); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
305 else |
226
4145266ff4bd
[svn r242] fixed (I think) arg_pointer inline asm args
lindquist
parents:
225
diff
changeset
|
306 assert(0);*/ |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
307 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
308 cns = p_cns; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
309 break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
310 case Arg_Memory: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
311 // FIXME |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
312 std::cout << "asm fixme Arg_Memory" << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
313 if (arg->expr->op == TOKvar) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
314 arg_val = arg->expr->toElem(irs); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
315 else |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
316 arg_val = arg->expr->toElem(irs); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
317 |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
318 switch (arg->mode) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
319 case Mode_Input: cns = m_cns; break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
320 case Mode_Output: cns = mw_cns; is_input = false; break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
321 case Mode_Update: cns = mrw_cns; is_input = false; break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
322 default: assert(0); break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
323 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
324 break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
325 case Arg_FrameRelative: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
326 // FIXME |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
327 std::cout << "asm fixme Arg_FrameRelative" << std::endl; |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
328 /* if (arg->expr->op == TOKvar) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
329 arg_val = ((VarExp *) arg->expr)->var->toSymbol()->Stree; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
330 else |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
331 assert(0);*/ |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
332 if ( getFrameRelativeValue(arg_val, & var_frame_offset) ) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
333 // arg_val = irs->integerConstant(var_frame_offset); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
334 cns = i_cns; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
335 } else { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
336 this->error("%s", "argument not frame relative"); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
337 return; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
338 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
339 if (arg->mode != Mode_Input) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
340 clobbers_mem = true; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
341 break; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
342 case Arg_LocalSize: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
343 // FIXME |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
344 std::cout << "asm fixme Arg_LocalSize" << std::endl; |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
345 /* var_frame_offset = cfun->x_frame_offset; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
346 if (var_frame_offset < 0) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
347 var_frame_offset = - var_frame_offset; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
348 arg_val = irs->integerConstant( var_frame_offset );*/ |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
349 goto do_integer; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
350 default: |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
351 assert(0); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
352 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
353 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
354 if (is_input) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
355 arg_map[i] = --input_idx; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
356 //inputs.cons(tree_cons(NULL_TREE, cns, NULL_TREE), arg_val); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
357 input_values.push_back(arg_val); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
358 input_constraints.push_back(cns); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
359 } else { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
360 arg_map[i] = n_outputs++; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
361 //outputs.cons(tree_cons(NULL_TREE, cns, NULL_TREE), arg_val); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
362 output_values.push_back(arg_val); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
363 output_constraints.push_back(cns); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
364 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
365 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
366 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
367 // Telling GCC that callee-saved registers are clobbered makes it preserve |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
368 // those registers. This changes the stack from what a naked function |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
369 // expects. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
370 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
371 // FIXME |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
372 // if (! irs->func->naked) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
373 for (int i = 0; i < 32; i++) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
374 if (regs & (1 << i)) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
375 //clobbers.cons(NULL_TREE, regInfo[i].gccName); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
376 clobbers.push_back(regInfo[i].gccName); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
377 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
378 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
379 for (int i = 0; i < 32; i++) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
380 if (code->moreRegs & (1 << (i-32))) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
381 //clobbers.cons(NULL_TREE, regInfo[i].gccName); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
382 clobbers.push_back(regInfo[i].gccName); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
383 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
384 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
385 if (clobbers_mem) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
386 clobbers.push_back(memory_name); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
387 //clobbers.cons(NULL_TREE, memory_name); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
388 // } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
389 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
390 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
391 // Remap argument numbers |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
392 for (unsigned i = 0; i < code->args.dim; i++) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
393 if (arg_map[i] < 0) |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
394 arg_map[i] = -arg_map[i] - 1 + n_outputs; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
395 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
396 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
397 bool pct = false; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
398 char * p = code->insnTemplate; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
399 char * q = p + code->insnTemplateLen; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
400 //printf("start: %.*s\n", code->insnTemplateLen, code->insnTemplate); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
401 while (p < q) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
402 if (pct) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
403 if (*p >= '0' && *p <= '9') { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
404 // %% doesn't check against nargs |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
405 *p = '0' + arg_map[*p - '0']; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
406 pct = false; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
407 } else if (*p == '$') { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
408 pct = false; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
409 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
410 //assert(*p == '%');// could be 'a', etc. so forget it.. |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
411 } else if (*p == '$') |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
412 pct = true; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
413 ++p; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
414 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
415 |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
416 printf("final: %.*s\n", code->insnTemplateLen, code->insnTemplate); |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
417 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
418 std::string insnt(code->insnTemplate, code->insnTemplateLen); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
419 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
420 // rewrite GCC-style constraints to LLVM-style constraints |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
421 std::string llvmConstraints; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
422 int n = 0; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
423 typedef std::deque<std::string>::iterator it; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
424 for(it i = output_constraints.begin(), e = output_constraints.end(); i != e; ++i, ++n) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
425 // rewrite update constraint to in and out constraints |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
426 if((*i)[0] == '+') { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
427 (*i)[0] = '='; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
428 std::string input_constraint; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
429 std::stringstream ss; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
430 ss << n; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
431 ss >> input_constraint; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
432 //FIXME: I think multiple inout constraints will mess up the order! |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
433 input_constraints.push_front(input_constraint); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
434 input_values.push_front(output_values[n]); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
435 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
436 llvmConstraints += *i; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
437 llvmConstraints += ","; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
438 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
439 for(it i = input_constraints.begin(), e = input_constraints.end(); i != e; ++i) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
440 llvmConstraints += *i; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
441 llvmConstraints += ","; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
442 } |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
443 for(it i = clobbers.begin(), e = clobbers.end(); i != e; ++i) { |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
444 llvmConstraints += "~{" + *i + "},"; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
445 } |
224
116cc012409b
[svn r240] do not crash on zero length constraints string
ChristianK
parents:
223
diff
changeset
|
446 if(llvmConstraints.size() > 0) |
116cc012409b
[svn r240] do not crash on zero length constraints string
ChristianK
parents:
223
diff
changeset
|
447 llvmConstraints.resize(llvmConstraints.size()-1); |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
448 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
449 std::cout << "Inline Asm code: " << std::endl; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
450 std::cout << insnt << std::endl; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
451 std::cout << "LLVM constraints: " << llvmConstraints << std::endl; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
452 |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
453 llvm::InlineAsm* t = d_build_asm_stmt(insnt, output_values, input_values, llvmConstraints); |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
454 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
455 std::cout << "llvm::InlineAsm: " << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
456 std::cout << *t << std::endl; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
457 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
458 LLSmallVector<LLValue*, 2> callargs; |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
459 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
460 size_t cn = output_values.size(); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
461 for (size_t i=0; i<cn; ++i) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
462 { |
221
68687d8c3e9a
[svn r237] some inline asm output now seems to work, see tangotests/asm2.d
lindquist
parents:
220
diff
changeset
|
463 LLValue* val = output_values[i]->getRVal(); |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
464 callargs.push_back(val); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
465 } |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
466 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
467 cn = input_values.size(); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
468 for (size_t i=0; i<cn; ++i) |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
469 { |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
470 // FIXME: these should not be allowed to intermix with asm calls. they should somehow |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
471 // be outputted before any asm from a block, or the asm's should be moved after ... |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
472 LLValue* val = input_values[i]->getRVal(); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
473 callargs.push_back(val); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
474 } |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
475 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
476 llvm::CallInst* call = irs->ir->CreateCall(t, callargs.begin(), callargs.end(), ""); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
477 |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
478 /* |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
479 // FIXME |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
480 //ASM_VOLATILE_P( t ) = 1; |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
481 //irs->addExp( t ); |
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
482 if (code->dollarLabel) |
220
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
483 d_expand_priv_asm_label(irs, code->dollarLabel); |
ccc2e6898a78
[svn r236] added initial codegen of inline asm, pretty buggy and incomplete still. see the tangotests/asm1.d test for a sample of what does
lindquist
parents:
219
diff
changeset
|
484 */ |
219
761c8352f494
[svn r235] rough port of GDC's inline assembler code, unfinished
ChristianK
parents:
diff
changeset
|
485 } |