~ubuntu-branches/ubuntu/trusty/monodevelop/trusty-proposed

« back to all changes in this revision

Viewing changes to contrib/ICSharpCode.NRefactory.CSharp/OutputVisitor/CodeDomConvertVisitor.cs

  • Committer: Package Import Robot
  • Author(s): Jo Shields
  • Date: 2013-05-12 09:46:03 UTC
  • mto: This revision was merged to the branch mainline in revision 29.
  • Revision ID: package-import@ubuntu.com-20130512094603-mad323bzcxvmcam0
Tags: upstream-4.0.5+dfsg
ImportĀ upstreamĀ versionĀ 4.0.5+dfsg

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team
2
 
// 
3
 
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
4
 
// software and associated documentation files (the "Software"), to deal in the Software
5
 
// without restriction, including without limitation the rights to use, copy, modify, merge,
6
 
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
7
 
// to whom the Software is furnished to do so, subject to the following conditions:
8
 
// 
9
 
// The above copyright notice and this permission notice shall be included in all copies or
10
 
// substantial portions of the Software.
11
 
// 
12
 
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
13
 
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
14
 
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
15
 
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
16
 
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
17
 
// DEALINGS IN THE SOFTWARE.
18
 
 
19
 
using System;
20
 
using System.CodeDom;
21
 
using System.Collections.Generic;
22
 
using System.IO;
23
 
using System.Linq;
24
 
using ICSharpCode.NRefactory.CSharp.Resolver;
25
 
using ICSharpCode.NRefactory.CSharp.TypeSystem;
26
 
using ICSharpCode.NRefactory.PatternMatching;
27
 
using ICSharpCode.NRefactory.Semantics;
28
 
using ICSharpCode.NRefactory.TypeSystem;
29
 
using ICSharpCode.NRefactory.TypeSystem.Implementation;
30
 
 
31
 
namespace ICSharpCode.NRefactory.CSharp
32
 
{
33
 
        /// <summary>
34
 
        /// Converts from C# AST to CodeDom.
35
 
        /// </summary>
36
 
        /// <remarks>
37
 
        /// The conversion is intended for use in the SharpDevelop forms designer.
38
 
        /// </remarks>
39
 
        public class CodeDomConvertVisitor : IAstVisitor<CodeObject>
40
 
        {
41
 
                //ICompilation compilation = MinimalResolveContext.Instance;
42
 
                CSharpAstResolver resolver;
43
 
                bool useFullyQualifiedTypeNames;
44
 
                
45
 
                /// <summary>
46
 
                /// Gets/Sets whether the visitor should use fully-qualified type references.
47
 
                /// </summary>
48
 
                public bool UseFullyQualifiedTypeNames {
49
 
                        get { return useFullyQualifiedTypeNames; }
50
 
                        set { useFullyQualifiedTypeNames = value; }
51
 
                }
52
 
                
53
 
                /// <summary>
54
 
                /// Converts a compilation unit to CodeDom.
55
 
                /// </summary>
56
 
                /// <param name="compilationUnit">The input compilation unit.</param>
57
 
                /// <param name="compilation">The current compilation.</param>
58
 
                /// <param name="parsedFile">CSharpParsedFile, used for resolving.</param>
59
 
                /// <returns>Converted CodeCompileUnit</returns>
60
 
                /// <remarks>
61
 
                /// This conversion process requires a resolver because it needs to distinguish field/property/event references etc.
62
 
                /// </remarks>
63
 
                public CodeCompileUnit Convert(ICompilation compilation, CompilationUnit compilationUnit, CSharpParsedFile parsedFile)
64
 
                {
65
 
                        if (compilationUnit == null)
66
 
                                throw new ArgumentNullException("compilationUnit");
67
 
                        if (compilation == null)
68
 
                                throw new ArgumentNullException("compilation");
69
 
                        
70
 
                        CSharpAstResolver resolver = new CSharpAstResolver(compilation, compilationUnit, parsedFile);
71
 
                        return (CodeCompileUnit)Convert(compilationUnit, resolver);
72
 
                }
73
 
                
74
 
                /// <summary>
75
 
                /// Converts a C# AST node to CodeDom.
76
 
                /// </summary>
77
 
                /// <param name="node">The input node.</param>
78
 
                /// <param name="resolver">The AST resolver.</param>
79
 
                /// <returns>The node converted into CodeDom</returns>
80
 
                /// <remarks>
81
 
                /// This conversion process requires a resolver because it needs to distinguish field/property/event references etc.
82
 
                /// </remarks>
83
 
                public CodeObject Convert(AstNode node, CSharpAstResolver resolver)
84
 
                {
85
 
                        if (node == null)
86
 
                                throw new ArgumentNullException("node");
87
 
                        if (resolver == null)
88
 
                                throw new ArgumentNullException("resolver");
89
 
                        try {
90
 
                                this.resolver = resolver;
91
 
                                return node.AcceptVisitor(this);
92
 
                        } finally {
93
 
                                this.resolver = null;
94
 
                        }
95
 
                }
96
 
                
97
 
                ResolveResult Resolve(AstNode node)
98
 
                {
99
 
                        if (resolver == null)
100
 
                                return ErrorResolveResult.UnknownError;
101
 
                        else
102
 
                                return resolver.Resolve(node);
103
 
                }
104
 
                
105
 
                CodeExpression Convert(Expression expr)
106
 
                {
107
 
                        return (CodeExpression)expr.AcceptVisitor(this);
108
 
                }
109
 
                
110
 
                CodeExpression[] Convert(IEnumerable<Expression> expressions)
111
 
                {
112
 
                        List<CodeExpression> result = new List<CodeExpression>();
113
 
                        foreach (Expression expr in expressions) {
114
 
                                CodeExpression e = Convert(expr);
115
 
                                if (e != null)
116
 
                                        result.Add(e);
117
 
                        }
118
 
                        return result.ToArray();
119
 
                }
120
 
                
121
 
                CodeTypeReference Convert(AstType type)
122
 
                {
123
 
                        return (CodeTypeReference)type.AcceptVisitor(this);
124
 
                }
125
 
                
126
 
                CodeTypeReference[] Convert(IEnumerable<AstType> types)
127
 
                {
128
 
                        List<CodeTypeReference> result = new List<CodeTypeReference>();
129
 
                        foreach (AstType type in types) {
130
 
                                CodeTypeReference e = Convert(type);
131
 
                                if (e != null)
132
 
                                        result.Add(e);
133
 
                        }
134
 
                        return result.ToArray();
135
 
                }
136
 
                
137
 
                CodeTypeReference Convert(IType type)
138
 
                {
139
 
                        return new CodeTypeReference(type.ReflectionName);
140
 
                }
141
 
                
142
 
                CodeStatement Convert(Statement stmt)
143
 
                {
144
 
                        return (CodeStatement)stmt.AcceptVisitor(this);
145
 
                }
146
 
                
147
 
                CodeStatement[] ConvertBlock(BlockStatement block)
148
 
                {
149
 
                        List<CodeStatement> result = new List<CodeStatement>();
150
 
                        foreach (Statement stmt in block.Statements) {
151
 
                                CodeStatement s = Convert(stmt);
152
 
                                if (s != null)
153
 
                                        result.Add(s);
154
 
                        }
155
 
                        return result.ToArray();
156
 
                }
157
 
                
158
 
                CodeStatement[] ConvertEmbeddedStatement(Statement embeddedStatement)
159
 
                {
160
 
                        BlockStatement block = embeddedStatement as BlockStatement;
161
 
                        if (block != null) {
162
 
                                return ConvertBlock(block);
163
 
                        }
164
 
                        CodeStatement s = Convert(embeddedStatement);
165
 
                        if (s != null)
166
 
                                return new CodeStatement[] { s };
167
 
                        else
168
 
                                return new CodeStatement[0];
169
 
                }
170
 
                
171
 
                string MakeSnippet(AstNode node)
172
 
                {
173
 
                        StringWriter w = new StringWriter();
174
 
                        CSharpOutputVisitor v = new CSharpOutputVisitor(w, FormattingOptionsFactory.CreateMono ());
175
 
                        node.AcceptVisitor(v);
176
 
                        return w.ToString();
177
 
                }
178
 
                
179
 
                /// <summary>
180
 
                /// Converts an expression by storing it as C# snippet.
181
 
                /// This is used for expressions that cannot be represented in CodeDom.
182
 
                /// </summary>
183
 
                CodeSnippetExpression MakeSnippetExpression(Expression expr)
184
 
                {
185
 
                        return new CodeSnippetExpression(MakeSnippet(expr));
186
 
                }
187
 
                
188
 
                CodeSnippetStatement MakeSnippetStatement(Statement stmt)
189
 
                {
190
 
                        return new CodeSnippetStatement(MakeSnippet(stmt));
191
 
                }
192
 
                
193
 
                CodeObject IAstVisitor<CodeObject>.VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression)
194
 
                {
195
 
                        return MakeSnippetExpression(anonymousMethodExpression);
196
 
                }
197
 
                
198
 
                CodeObject IAstVisitor<CodeObject>.VisitUndocumentedExpression(UndocumentedExpression undocumentedExpression)
199
 
                {
200
 
                        return MakeSnippetExpression(undocumentedExpression);
201
 
                }
202
 
                
203
 
                CodeObject IAstVisitor<CodeObject>.VisitArrayCreateExpression(ArrayCreateExpression arrayCreateExpression)
204
 
                {
205
 
                        CodeArrayCreateExpression ace = new CodeArrayCreateExpression();
206
 
                        int dimensions = arrayCreateExpression.Arguments.Count;
207
 
                        int nestingDepth = arrayCreateExpression.AdditionalArraySpecifiers.Count;
208
 
                        if (dimensions > 0)
209
 
                                nestingDepth++;
210
 
                        if (nestingDepth > 1 || dimensions > 1) {
211
 
                                // CodeDom does not support jagged or multi-dimensional arrays
212
 
                                return MakeSnippetExpression(arrayCreateExpression);
213
 
                        }
214
 
                        if (arrayCreateExpression.Type.IsNull) {
215
 
                                ace.CreateType = Convert(Resolve(arrayCreateExpression).Type);
216
 
                        } else {
217
 
                                ace.CreateType = Convert(arrayCreateExpression.Type);
218
 
                        }
219
 
                        if (arrayCreateExpression.Arguments.Count == 1) {
220
 
                                ace.SizeExpression = Convert(arrayCreateExpression.Arguments.Single());
221
 
                        }
222
 
                        ace.Initializers.AddRange(Convert(arrayCreateExpression.Initializer.Elements));
223
 
                        return ace;
224
 
                }
225
 
                
226
 
                CodeObject IAstVisitor<CodeObject>.VisitArrayInitializerExpression(ArrayInitializerExpression arrayInitializerExpression)
227
 
                {
228
 
                        // Array initializers should be handled by the parent node
229
 
                        return MakeSnippetExpression(arrayInitializerExpression);
230
 
                }
231
 
                
232
 
                CodeObject IAstVisitor<CodeObject>.VisitAsExpression(AsExpression asExpression)
233
 
                {
234
 
                        return MakeSnippetExpression(asExpression);
235
 
                }
236
 
                
237
 
                CodeObject IAstVisitor<CodeObject>.VisitAssignmentExpression(AssignmentExpression assignmentExpression)
238
 
                {
239
 
                        // assignments are only supported as statements, not as expressions
240
 
                        return MakeSnippetExpression(assignmentExpression);
241
 
                }
242
 
                
243
 
                CodeObject IAstVisitor<CodeObject>.VisitBaseReferenceExpression(BaseReferenceExpression baseReferenceExpression)
244
 
                {
245
 
                        return new CodeBaseReferenceExpression();
246
 
                }
247
 
                
248
 
                CodeObject IAstVisitor<CodeObject>.VisitBinaryOperatorExpression(BinaryOperatorExpression binaryOperatorExpression)
249
 
                {
250
 
                        CodeBinaryOperatorType op;
251
 
                        switch (binaryOperatorExpression.Operator) {
252
 
                                case BinaryOperatorType.BitwiseAnd:
253
 
                                        op = CodeBinaryOperatorType.BitwiseAnd;
254
 
                                        break;
255
 
                                case BinaryOperatorType.BitwiseOr:
256
 
                                        op = CodeBinaryOperatorType.BitwiseOr;
257
 
                                        break;
258
 
                                case BinaryOperatorType.ConditionalAnd:
259
 
                                        op = CodeBinaryOperatorType.BooleanAnd;
260
 
                                        break;
261
 
                                case BinaryOperatorType.ConditionalOr:
262
 
                                        op = CodeBinaryOperatorType.BooleanOr;
263
 
                                        break;
264
 
                                case BinaryOperatorType.GreaterThan:
265
 
                                        op = CodeBinaryOperatorType.GreaterThan;
266
 
                                        break;
267
 
                                case BinaryOperatorType.GreaterThanOrEqual:
268
 
                                        op = CodeBinaryOperatorType.GreaterThanOrEqual;
269
 
                                        break;
270
 
                                case BinaryOperatorType.LessThan:
271
 
                                        op = CodeBinaryOperatorType.LessThan;
272
 
                                        break;
273
 
                                case BinaryOperatorType.LessThanOrEqual:
274
 
                                        op = CodeBinaryOperatorType.LessThanOrEqual;
275
 
                                        break;
276
 
                                case BinaryOperatorType.Add:
277
 
                                        op = CodeBinaryOperatorType.Add;
278
 
                                        break;
279
 
                                case BinaryOperatorType.Subtract:
280
 
                                        op = CodeBinaryOperatorType.Subtract;
281
 
                                        break;
282
 
                                case BinaryOperatorType.Multiply:
283
 
                                        op = CodeBinaryOperatorType.Multiply;
284
 
                                        break;
285
 
                                case BinaryOperatorType.Divide:
286
 
                                        op = CodeBinaryOperatorType.Divide;
287
 
                                        break;
288
 
                                case BinaryOperatorType.Modulus:
289
 
                                        op = CodeBinaryOperatorType.Modulus;
290
 
                                        break;
291
 
                                case BinaryOperatorType.Equality:
292
 
                                case BinaryOperatorType.InEquality:
293
 
                                        OperatorResolveResult rr = Resolve(binaryOperatorExpression) as OperatorResolveResult;
294
 
                                        if (rr != null && rr.GetChildResults().Any(cr => cr.Type.IsReferenceType == true)) {
295
 
                                                if (binaryOperatorExpression.Operator == BinaryOperatorType.Equality)
296
 
                                                        op = CodeBinaryOperatorType.IdentityEquality;
297
 
                                                else
298
 
                                                        op = CodeBinaryOperatorType.IdentityInequality;
299
 
                                        } else {
300
 
                                                if (binaryOperatorExpression.Operator == BinaryOperatorType.Equality) {
301
 
                                                        op = CodeBinaryOperatorType.ValueEquality;
302
 
                                                } else {
303
 
                                                        // CodeDom is retarded and does not support ValueInequality, so we'll simulate it using
304
 
                                                        // ValueEquality and Not... but CodeDom doesn't have Not either, so we use
305
 
                                                        // '(a == b) == false'
306
 
                                                        return new CodeBinaryOperatorExpression(
307
 
                                                                new CodeBinaryOperatorExpression(
308
 
                                                                        Convert(binaryOperatorExpression.Left),
309
 
                                                                        CodeBinaryOperatorType.ValueEquality,
310
 
                                                                        Convert(binaryOperatorExpression.Right)
311
 
                                                                ),
312
 
                                                                CodeBinaryOperatorType.ValueEquality,
313
 
                                                                new CodePrimitiveExpression(false)
314
 
                                                        );
315
 
                                                }
316
 
                                        }
317
 
                                        break;
318
 
                                default:
319
 
                                        // not supported: xor, shift, null coalescing
320
 
                                        return MakeSnippetExpression(binaryOperatorExpression);
321
 
                        }
322
 
                        return new CodeBinaryOperatorExpression(Convert(binaryOperatorExpression.Left), op, Convert(binaryOperatorExpression.Right));
323
 
                }
324
 
                
325
 
                CodeObject IAstVisitor<CodeObject>.VisitCastExpression(CastExpression castExpression)
326
 
                {
327
 
                        return new CodeCastExpression(Convert(castExpression.Type), Convert(castExpression.Expression));
328
 
                }
329
 
                
330
 
                CodeObject IAstVisitor<CodeObject>.VisitCheckedExpression(CheckedExpression checkedExpression)
331
 
                {
332
 
                        return MakeSnippetExpression(checkedExpression);
333
 
                }
334
 
                
335
 
                CodeObject IAstVisitor<CodeObject>.VisitConditionalExpression(ConditionalExpression conditionalExpression)
336
 
                {
337
 
                        return MakeSnippetExpression(conditionalExpression);
338
 
                }
339
 
                
340
 
                CodeObject IAstVisitor<CodeObject>.VisitDefaultValueExpression(DefaultValueExpression defaultValueExpression)
341
 
                {
342
 
                        return new CodeDefaultValueExpression(Convert(defaultValueExpression.Type));
343
 
                }
344
 
                
345
 
                CodeObject IAstVisitor<CodeObject>.VisitDirectionExpression(DirectionExpression directionExpression)
346
 
                {
347
 
                        System.CodeDom.FieldDirection direction;
348
 
                        if (directionExpression.FieldDirection == FieldDirection.Out) {
349
 
                                direction = System.CodeDom.FieldDirection.Out;
350
 
                        } else {
351
 
                                direction = System.CodeDom.FieldDirection.Ref;
352
 
                        }
353
 
                        return new CodeDirectionExpression(direction, Convert(directionExpression.Expression));
354
 
                }
355
 
                
356
 
                CodeObject IAstVisitor<CodeObject>.VisitIdentifierExpression(IdentifierExpression identifierExpression)
357
 
                {
358
 
                        ResolveResult rr = Resolve(identifierExpression);
359
 
                        LocalResolveResult lrr = rr as LocalResolveResult;
360
 
                        if (lrr != null && lrr.IsParameter) {
361
 
                                if (lrr.Variable.Name == "value" && identifierExpression.Ancestors.Any(a => a is Accessor)) {
362
 
                                        return new CodePropertySetValueReferenceExpression();
363
 
                                } else {
364
 
                                        return new CodeArgumentReferenceExpression(lrr.Variable.Name);
365
 
                                }
366
 
                        }
367
 
                        MemberResolveResult mrr = rr as MemberResolveResult;
368
 
                        if (mrr != null) {
369
 
                                return HandleMemberReference(null, identifierExpression.Identifier, identifierExpression.TypeArguments, mrr);
370
 
                        }
371
 
                        TypeResolveResult trr = rr as TypeResolveResult;
372
 
                        if (trr != null) {
373
 
                                CodeTypeReference typeRef;
374
 
                                if (useFullyQualifiedTypeNames) {
375
 
                                        typeRef = Convert(trr.Type);
376
 
                                } else {
377
 
                                        typeRef = new CodeTypeReference(identifierExpression.Identifier);
378
 
                                        typeRef.TypeArguments.AddRange(Convert(identifierExpression.TypeArguments));
379
 
                                }
380
 
                                return new CodeTypeReferenceExpression(typeRef);
381
 
                        }
382
 
                        MethodGroupResolveResult mgrr = rr as MethodGroupResolveResult;
383
 
                        if (mgrr != null) {
384
 
                                return new CodeMethodReferenceExpression(new CodeThisReferenceExpression(), identifierExpression.Identifier, Convert(identifierExpression.TypeArguments));
385
 
                        }
386
 
                        return new CodeVariableReferenceExpression(identifierExpression.Identifier);
387
 
                }
388
 
                
389
 
                CodeObject IAstVisitor<CodeObject>.VisitIndexerExpression(IndexerExpression indexerExpression)
390
 
                {
391
 
                        if (Resolve(indexerExpression) is ArrayAccessResolveResult)
392
 
                                return new CodeArrayIndexerExpression(Convert(indexerExpression.Target), Convert(indexerExpression.Arguments));
393
 
                        else
394
 
                                return new CodeIndexerExpression(Convert(indexerExpression.Target), Convert(indexerExpression.Arguments));
395
 
                }
396
 
                
397
 
                CodeObject IAstVisitor<CodeObject>.VisitInvocationExpression(InvocationExpression invocationExpression)
398
 
                {
399
 
                        MemberResolveResult rr = Resolve(invocationExpression) as MemberResolveResult;
400
 
                        CSharpInvocationResolveResult csRR = rr as CSharpInvocationResolveResult;
401
 
                        if (csRR != null && csRR.IsDelegateInvocation) {
402
 
                                return new CodeDelegateInvokeExpression(Convert(invocationExpression.Target), Convert(invocationExpression.Arguments));
403
 
                        }
404
 
                        
405
 
                        Expression methodExpr = invocationExpression.Target;
406
 
                        while (methodExpr is ParenthesizedExpression)
407
 
                                methodExpr = ((ParenthesizedExpression)methodExpr).Expression;
408
 
                        CodeMethodReferenceExpression mr = null;
409
 
                        MemberReferenceExpression mre = methodExpr as MemberReferenceExpression;
410
 
                        if (mre != null) {
411
 
                                mr = new CodeMethodReferenceExpression(Convert(mre.Target), mre.MemberName, Convert(mre.TypeArguments));
412
 
                        }
413
 
                        IdentifierExpression id = methodExpr as IdentifierExpression;
414
 
                        if (id != null) {
415
 
                                CodeExpression target;
416
 
                                if (rr != null && rr.Member.IsStatic)
417
 
                                        target = new CodeTypeReferenceExpression(Convert(rr.Member.DeclaringType));
418
 
                                else
419
 
                                        target = new CodeThisReferenceExpression();
420
 
                                
421
 
                                mr = new CodeMethodReferenceExpression(target, id.Identifier, Convert(id.TypeArguments));
422
 
                        }
423
 
                        if (mr != null)
424
 
                                return new CodeMethodInvokeExpression(mr, Convert(invocationExpression.Arguments));
425
 
                        else
426
 
                                return MakeSnippetExpression(invocationExpression);
427
 
                }
428
 
                
429
 
                CodeObject IAstVisitor<CodeObject>.VisitIsExpression(IsExpression isExpression)
430
 
                {
431
 
                        return MakeSnippetExpression(isExpression);
432
 
                }
433
 
                
434
 
                CodeObject IAstVisitor<CodeObject>.VisitLambdaExpression(LambdaExpression lambdaExpression)
435
 
                {
436
 
                        return MakeSnippetExpression(lambdaExpression);
437
 
                }
438
 
                
439
 
                CodeObject IAstVisitor<CodeObject>.VisitMemberReferenceExpression(MemberReferenceExpression memberReferenceExpression)
440
 
                {
441
 
                        CodeExpression target = Convert(memberReferenceExpression.Target);
442
 
                        ResolveResult rr = Resolve(memberReferenceExpression);
443
 
                        MemberResolveResult mrr = rr as MemberResolveResult;
444
 
                        if (mrr != null) {
445
 
                                return HandleMemberReference(target, memberReferenceExpression.MemberName, memberReferenceExpression.TypeArguments, mrr);
446
 
                        } else {
447
 
                                if (memberReferenceExpression.TypeArguments.Any() || rr is MethodGroupResolveResult) {
448
 
                                        return new CodeMethodReferenceExpression(target, memberReferenceExpression.MemberName, Convert(memberReferenceExpression.TypeArguments));
449
 
                                } else {
450
 
                                        return new CodePropertyReferenceExpression(target, memberReferenceExpression.MemberName);
451
 
                                }
452
 
                        }
453
 
                }
454
 
                
455
 
                CodeExpression HandleMemberReference(CodeExpression target, string identifier, AstNodeCollection<AstType> typeArguments, MemberResolveResult mrr)
456
 
                {
457
 
                        if (target == null) {
458
 
                                if (mrr.Member.IsStatic)
459
 
                                        target = new CodeTypeReferenceExpression(Convert(mrr.Member.DeclaringType));
460
 
                                else
461
 
                                        target = new CodeThisReferenceExpression();
462
 
                        }
463
 
                        if (mrr.Member is IField) {
464
 
                                return new CodeFieldReferenceExpression(target, identifier);
465
 
                        } else if (mrr.Member is IMethod) {
466
 
                                return new CodeMethodReferenceExpression(target, identifier, Convert(typeArguments));
467
 
                        } else if (mrr.Member is IEvent) {
468
 
                                return new CodeEventReferenceExpression(target, identifier);
469
 
                        } else {
470
 
                                return new CodePropertyReferenceExpression(target, identifier);
471
 
                        }
472
 
                }
473
 
                
474
 
                CodeObject IAstVisitor<CodeObject>.VisitNamedArgumentExpression(NamedArgumentExpression namedArgumentExpression)
475
 
                {
476
 
                        return MakeSnippetExpression(namedArgumentExpression);
477
 
                }
478
 
                
479
 
                CodeObject IAstVisitor<CodeObject>.VisitNamedExpression(NamedExpression namedExpression)
480
 
                {
481
 
                        return MakeSnippetExpression(namedExpression);
482
 
                }
483
 
                
484
 
                CodeObject IAstVisitor<CodeObject>.VisitNullReferenceExpression(NullReferenceExpression nullReferenceExpression)
485
 
                {
486
 
                        return new CodePrimitiveExpression(null);
487
 
                }
488
 
                
489
 
                CodeObject IAstVisitor<CodeObject>.VisitObjectCreateExpression(ObjectCreateExpression objectCreateExpression)
490
 
                {
491
 
                        if (!objectCreateExpression.Initializer.IsNull)
492
 
                                return MakeSnippetExpression(objectCreateExpression);
493
 
                        return new CodeObjectCreateExpression(Convert(objectCreateExpression.Type), Convert(objectCreateExpression.Arguments));
494
 
                }
495
 
                
496
 
                CodeObject IAstVisitor<CodeObject>.VisitAnonymousTypeCreateExpression(AnonymousTypeCreateExpression anonymousTypeCreateExpression)
497
 
                {
498
 
                        return MakeSnippetExpression(anonymousTypeCreateExpression);
499
 
                }
500
 
                
501
 
                CodeObject IAstVisitor<CodeObject>.VisitParenthesizedExpression(ParenthesizedExpression parenthesizedExpression)
502
 
                {
503
 
                        // CodeDom generators will insert parentheses where necessary
504
 
                        return Convert(parenthesizedExpression.Expression);
505
 
                }
506
 
                
507
 
                CodeObject IAstVisitor<CodeObject>.VisitPointerReferenceExpression(PointerReferenceExpression pointerReferenceExpression)
508
 
                {
509
 
                        return MakeSnippetExpression(pointerReferenceExpression);
510
 
                }
511
 
                
512
 
                CodeObject IAstVisitor<CodeObject>.VisitPrimitiveExpression(PrimitiveExpression primitiveExpression)
513
 
                {
514
 
                        return new CodePrimitiveExpression(primitiveExpression.Value);
515
 
                }
516
 
                
517
 
                CodeObject IAstVisitor<CodeObject>.VisitSizeOfExpression(SizeOfExpression sizeOfExpression)
518
 
                {
519
 
                        return MakeSnippetExpression(sizeOfExpression);
520
 
                }
521
 
                
522
 
                CodeObject IAstVisitor<CodeObject>.VisitStackAllocExpression(StackAllocExpression stackAllocExpression)
523
 
                {
524
 
                        return MakeSnippetExpression(stackAllocExpression);
525
 
                }
526
 
                
527
 
                CodeObject IAstVisitor<CodeObject>.VisitThisReferenceExpression(ThisReferenceExpression thisReferenceExpression)
528
 
                {
529
 
                        return new CodeThisReferenceExpression();
530
 
                }
531
 
                
532
 
                CodeObject IAstVisitor<CodeObject>.VisitTypeOfExpression(TypeOfExpression typeOfExpression)
533
 
                {
534
 
                        return new CodeTypeOfExpression(Convert(typeOfExpression.Type));
535
 
                }
536
 
                
537
 
                CodeObject IAstVisitor<CodeObject>.VisitTypeReferenceExpression(TypeReferenceExpression typeReferenceExpression)
538
 
                {
539
 
                        return new CodeTypeReferenceExpression(Convert(typeReferenceExpression.Type));
540
 
                }
541
 
                
542
 
                CodeObject IAstVisitor<CodeObject>.VisitUnaryOperatorExpression(UnaryOperatorExpression unaryOperatorExpression)
543
 
                {
544
 
                        switch (unaryOperatorExpression.Operator) {
545
 
                                case UnaryOperatorType.Not:
546
 
                                        return new CodeBinaryOperatorExpression(
547
 
                                                Convert(unaryOperatorExpression.Expression),
548
 
                                                CodeBinaryOperatorType.ValueEquality,
549
 
                                                new CodePrimitiveExpression(false));
550
 
                                case UnaryOperatorType.Minus:
551
 
                                        return new CodeBinaryOperatorExpression(
552
 
                                                new CodePrimitiveExpression(0),
553
 
                                                CodeBinaryOperatorType.Subtract,
554
 
                                                Convert(unaryOperatorExpression.Expression));
555
 
                                case UnaryOperatorType.Plus:
556
 
                                        return Convert(unaryOperatorExpression.Expression);
557
 
                                default:
558
 
                                        return MakeSnippetExpression(unaryOperatorExpression);
559
 
                        }
560
 
                }
561
 
                
562
 
                CodeObject IAstVisitor<CodeObject>.VisitUncheckedExpression(UncheckedExpression uncheckedExpression)
563
 
                {
564
 
                        return MakeSnippetExpression(uncheckedExpression);
565
 
                }
566
 
                
567
 
                CodeObject IAstVisitor<CodeObject>.VisitEmptyExpression(EmptyExpression emptyExpression)
568
 
                {
569
 
                        return null;
570
 
                }
571
 
                
572
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryExpression(QueryExpression queryExpression)
573
 
                {
574
 
                        return MakeSnippetExpression(queryExpression);
575
 
                }
576
 
                
577
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryContinuationClause(QueryContinuationClause queryContinuationClause)
578
 
                {
579
 
                        throw new NotSupportedException();
580
 
                }
581
 
                
582
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryFromClause(QueryFromClause queryFromClause)
583
 
                {
584
 
                        throw new NotSupportedException();
585
 
                }
586
 
                
587
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryLetClause(QueryLetClause queryLetClause)
588
 
                {
589
 
                        throw new NotSupportedException();
590
 
                }
591
 
                
592
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryWhereClause(QueryWhereClause queryWhereClause)
593
 
                {
594
 
                        throw new NotSupportedException();
595
 
                }
596
 
                
597
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryJoinClause(QueryJoinClause queryJoinClause)
598
 
                {
599
 
                        throw new NotSupportedException();
600
 
                }
601
 
                
602
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryOrderClause(QueryOrderClause queryOrderClause)
603
 
                {
604
 
                        throw new NotSupportedException();
605
 
                }
606
 
                
607
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryOrdering(QueryOrdering queryOrdering)
608
 
                {
609
 
                        throw new NotSupportedException();
610
 
                }
611
 
                
612
 
                CodeObject IAstVisitor<CodeObject>.VisitQuerySelectClause(QuerySelectClause querySelectClause)
613
 
                {
614
 
                        throw new NotSupportedException();
615
 
                }
616
 
                
617
 
                CodeObject IAstVisitor<CodeObject>.VisitQueryGroupClause(QueryGroupClause queryGroupClause)
618
 
                {
619
 
                        throw new NotSupportedException();
620
 
                }
621
 
                
622
 
                CodeObject IAstVisitor<CodeObject>.VisitAttribute(Attribute attribute)
623
 
                {
624
 
                        throw new NotSupportedException();
625
 
                }
626
 
                
627
 
                CodeObject IAstVisitor<CodeObject>.VisitAttributeSection(AttributeSection attributeSection)
628
 
                {
629
 
                        throw new NotSupportedException();
630
 
                }
631
 
                
632
 
                CodeAttributeDeclaration Convert(Attribute attribute)
633
 
                {
634
 
                        var attr = new CodeAttributeDeclaration(Convert(attribute.Type));
635
 
                        foreach (Expression expr in attribute.Arguments) {
636
 
                                NamedExpression ne = expr as NamedExpression;
637
 
                                if (ne != null)
638
 
                                        attr.Arguments.Add(new CodeAttributeArgument(ne.Name, Convert(ne.Expression)));
639
 
                                else
640
 
                                        attr.Arguments.Add(new CodeAttributeArgument(Convert(expr)));
641
 
                        }
642
 
                        return attr;
643
 
                }
644
 
                
645
 
                CodeAttributeDeclaration[] Convert(IEnumerable<AttributeSection> attributeSections)
646
 
                {
647
 
                        List<CodeAttributeDeclaration> result = new List<CodeAttributeDeclaration>();
648
 
                        foreach (AttributeSection section in attributeSections) {
649
 
                                foreach (Attribute attr in section.Attributes) {
650
 
                                        CodeAttributeDeclaration attrDecl = Convert(attr);
651
 
                                        if (attrDecl != null)
652
 
                                                result.Add(attrDecl);
653
 
                                }
654
 
                        }
655
 
                        return result.ToArray();
656
 
                }
657
 
                
658
 
                CodeObject IAstVisitor<CodeObject>.VisitDelegateDeclaration(DelegateDeclaration delegateDeclaration)
659
 
                {
660
 
                        CodeTypeDelegate d = new CodeTypeDelegate(delegateDeclaration.Name);
661
 
                        d.Attributes = ConvertMemberAttributes(delegateDeclaration.Modifiers);
662
 
                        d.CustomAttributes.AddRange(Convert(delegateDeclaration.Attributes));
663
 
                        d.ReturnType = Convert(delegateDeclaration.ReturnType);
664
 
                        d.Parameters.AddRange(Convert(delegateDeclaration.Parameters));
665
 
                        d.TypeParameters.AddRange(ConvertTypeParameters(delegateDeclaration.TypeParameters, delegateDeclaration.Constraints));
666
 
                        return d;
667
 
                }
668
 
                
669
 
                static MemberAttributes ConvertMemberAttributes(Modifiers modifiers)
670
 
                {
671
 
                        MemberAttributes a = 0;
672
 
                        if ((modifiers & Modifiers.Abstract) != 0)
673
 
                                a |= MemberAttributes.Abstract;
674
 
                        if ((modifiers & Modifiers.Sealed) != 0)
675
 
                                a |= MemberAttributes.Final;
676
 
                        if ((modifiers & Modifiers.Static) != 0)
677
 
                                a |= MemberAttributes.Static;
678
 
                        if ((modifiers & Modifiers.Override) != 0)
679
 
                                a |= MemberAttributes.Override;
680
 
                        if ((modifiers & Modifiers.Const) != 0)
681
 
                                a |= MemberAttributes.Const;
682
 
                        if ((modifiers & Modifiers.New) != 0)
683
 
                                a |= MemberAttributes.New;
684
 
                        
685
 
                        if ((modifiers & Modifiers.Public) != 0)
686
 
                                a |= MemberAttributes.Public;
687
 
                        else if ((modifiers & (Modifiers.Protected | Modifiers.Internal)) == (Modifiers.Protected | Modifiers.Internal))
688
 
                                a |= MemberAttributes.FamilyOrAssembly;
689
 
                        else if ((modifiers & Modifiers.Protected) != 0)
690
 
                                a |= MemberAttributes.Family;
691
 
                        else if ((modifiers & Modifiers.Internal) != 0)
692
 
                                a |= MemberAttributes.Assembly;
693
 
                        else if ((modifiers & Modifiers.Private) != 0)
694
 
                                a |= MemberAttributes.Private;
695
 
                        
696
 
                        return a;
697
 
                }
698
 
                
699
 
                CodeObject IAstVisitor<CodeObject>.VisitNamespaceDeclaration(NamespaceDeclaration namespaceDeclaration)
700
 
                {
701
 
                        CodeNamespace ns = new CodeNamespace(namespaceDeclaration.Name);
702
 
                        foreach (AstNode node in namespaceDeclaration.Members) {
703
 
                                CodeObject r = node.AcceptVisitor(this);
704
 
                                
705
 
                                CodeNamespaceImport import = r as CodeNamespaceImport;
706
 
                                if (import != null)
707
 
                                        ns.Imports.Add(import);
708
 
                                
709
 
                                CodeTypeDeclaration typeDecl = r as CodeTypeDeclaration;
710
 
                                if (typeDecl != null)
711
 
                                        ns.Types.Add(typeDecl);
712
 
                        }
713
 
                        return ns;
714
 
                }
715
 
                
716
 
                Stack<CodeTypeDeclaration> typeStack = new Stack<CodeTypeDeclaration>();
717
 
                
718
 
                CodeObject IAstVisitor<CodeObject>.VisitTypeDeclaration(TypeDeclaration typeDeclaration)
719
 
                {
720
 
                        //bool isNestedType = typeStack.Count > 0;
721
 
                        CodeTypeDeclaration typeDecl = new CodeTypeDeclaration(typeDeclaration.Name);
722
 
                        typeDecl.Attributes = ConvertMemberAttributes(typeDeclaration.Modifiers);
723
 
                        typeDecl.CustomAttributes.AddRange(Convert(typeDeclaration.Attributes));
724
 
                        
725
 
                        switch (typeDeclaration.ClassType) {
726
 
                                case ClassType.Struct:
727
 
                                        typeDecl.IsStruct = true;
728
 
                                        break;
729
 
                                case ClassType.Interface:
730
 
                                        typeDecl.IsInterface = true;
731
 
                                        break;
732
 
                                case ClassType.Enum:
733
 
                                        typeDecl.IsEnum = true;
734
 
                                        break;
735
 
                                default:
736
 
                                        typeDecl.IsClass = true;
737
 
                                        break;
738
 
                        }
739
 
                        typeDecl.IsPartial = (typeDeclaration.Modifiers & Modifiers.Partial) == Modifiers.Partial;
740
 
                        
741
 
                        typeDecl.BaseTypes.AddRange(Convert(typeDeclaration.BaseTypes));
742
 
                        typeDecl.TypeParameters.AddRange(ConvertTypeParameters(typeDeclaration.TypeParameters, typeDeclaration.Constraints));
743
 
                        
744
 
                        typeStack.Push(typeDecl);
745
 
                        foreach (var member in typeDeclaration.Members) {
746
 
                                CodeTypeMember m = member.AcceptVisitor(this) as CodeTypeMember;
747
 
                                if (m != null)
748
 
                                        typeDecl.Members.Add(m);
749
 
                        }
750
 
                        typeStack.Pop();
751
 
                        return typeDecl;
752
 
                }
753
 
                
754
 
                void AddTypeMember(CodeTypeMember member)
755
 
                {
756
 
                        if (typeStack.Count != 0)
757
 
                                typeStack.Peek().Members.Add(member);
758
 
                }
759
 
                
760
 
                CodeObject IAstVisitor<CodeObject>.VisitUsingAliasDeclaration(UsingAliasDeclaration usingAliasDeclaration)
761
 
                {
762
 
                        return new CodeSnippetTypeMember(MakeSnippet(usingAliasDeclaration));
763
 
                }
764
 
                
765
 
                CodeObject IAstVisitor<CodeObject>.VisitUsingDeclaration(UsingDeclaration usingDeclaration)
766
 
                {
767
 
                        return new CodeNamespaceImport(usingDeclaration.Namespace);
768
 
                }
769
 
                
770
 
                CodeObject IAstVisitor<CodeObject>.VisitExternAliasDeclaration(ExternAliasDeclaration externAliasDeclaration)
771
 
                {
772
 
                        return new CodeSnippetTypeMember(MakeSnippet(externAliasDeclaration));
773
 
                }
774
 
                
775
 
                CodeObject IAstVisitor<CodeObject>.VisitBlockStatement(BlockStatement blockStatement)
776
 
                {
777
 
                        return new CodeConditionStatement(new CodePrimitiveExpression(true), ConvertBlock(blockStatement));
778
 
                }
779
 
                
780
 
                CodeObject IAstVisitor<CodeObject>.VisitBreakStatement(BreakStatement breakStatement)
781
 
                {
782
 
                        return MakeSnippetStatement(breakStatement);
783
 
                }
784
 
                
785
 
                CodeObject IAstVisitor<CodeObject>.VisitCheckedStatement(CheckedStatement checkedStatement)
786
 
                {
787
 
                        return MakeSnippetStatement(checkedStatement);
788
 
                }
789
 
                
790
 
                CodeObject IAstVisitor<CodeObject>.VisitContinueStatement(ContinueStatement continueStatement)
791
 
                {
792
 
                        return MakeSnippetStatement(continueStatement);
793
 
                }
794
 
                
795
 
                CodeObject IAstVisitor<CodeObject>.VisitDoWhileStatement(DoWhileStatement doWhileStatement)
796
 
                {
797
 
                        // do { } while (expr);
798
 
                        //
799
 
                        // emulate with:
800
 
                        //  for (bool _do = true; _do; _do = expr) {}
801
 
                        string varName = "_do" + doWhileStatement.Ancestors.OfType<DoWhileStatement>().Count();
802
 
                        return new CodeIterationStatement(
803
 
                                new CodeVariableDeclarationStatement(typeof(bool), varName, new CodePrimitiveExpression(true)),
804
 
                                new CodeVariableReferenceExpression(varName),
805
 
                                new CodeAssignStatement(new CodeVariableReferenceExpression(varName), Convert(doWhileStatement.Condition)),
806
 
                                ConvertEmbeddedStatement(doWhileStatement.EmbeddedStatement)
807
 
                        );
808
 
                }
809
 
                
810
 
                CodeObject IAstVisitor<CodeObject>.VisitEmptyStatement(EmptyStatement emptyStatement)
811
 
                {
812
 
                        return null;
813
 
                }
814
 
                
815
 
                CodeObject IAstVisitor<CodeObject>.VisitExpressionStatement(ExpressionStatement expressionStatement)
816
 
                {
817
 
                        AssignmentExpression assignment = expressionStatement.Expression as AssignmentExpression;
818
 
                        if (assignment != null && assignment.Operator == AssignmentOperatorType.Assign) {
819
 
                                return new CodeAssignStatement(Convert(assignment.Left), Convert(assignment.Right));
820
 
                        }
821
 
                        return new CodeExpressionStatement(Convert(expressionStatement.Expression));
822
 
                }
823
 
                
824
 
                CodeObject IAstVisitor<CodeObject>.VisitFixedStatement(FixedStatement fixedStatement)
825
 
                {
826
 
                        return MakeSnippetStatement(fixedStatement);
827
 
                }
828
 
                
829
 
                CodeObject IAstVisitor<CodeObject>.VisitForeachStatement(ForeachStatement foreachStatement)
830
 
                {
831
 
                        return MakeSnippetStatement(foreachStatement);
832
 
                }
833
 
                
834
 
                CodeObject IAstVisitor<CodeObject>.VisitForStatement(ForStatement forStatement)
835
 
                {
836
 
                        if (forStatement.Initializers.Count != 1 || forStatement.Iterators.Count != 1)
837
 
                                return MakeSnippetStatement(forStatement);
838
 
                        return new CodeIterationStatement(
839
 
                                Convert(forStatement.Initializers.Single()),
840
 
                                Convert(forStatement.Condition),
841
 
                                Convert(forStatement.Iterators.Single()),
842
 
                                ConvertEmbeddedStatement(forStatement.EmbeddedStatement)
843
 
                        );
844
 
                }
845
 
                
846
 
                CodeObject IAstVisitor<CodeObject>.VisitGotoCaseStatement(GotoCaseStatement gotoCaseStatement)
847
 
                {
848
 
                        return MakeSnippetStatement(gotoCaseStatement);
849
 
                }
850
 
                
851
 
                CodeObject IAstVisitor<CodeObject>.VisitGotoDefaultStatement(GotoDefaultStatement gotoDefaultStatement)
852
 
                {
853
 
                        return MakeSnippetStatement(gotoDefaultStatement);
854
 
                }
855
 
                
856
 
                CodeObject IAstVisitor<CodeObject>.VisitGotoStatement(GotoStatement gotoStatement)
857
 
                {
858
 
                        return new CodeGotoStatement(gotoStatement.Label);
859
 
                }
860
 
                
861
 
                CodeObject IAstVisitor<CodeObject>.VisitIfElseStatement(IfElseStatement ifElseStatement)
862
 
                {
863
 
                        return new CodeConditionStatement(
864
 
                                Convert(ifElseStatement.Condition),
865
 
                                ConvertEmbeddedStatement(ifElseStatement.TrueStatement),
866
 
                                ConvertEmbeddedStatement(ifElseStatement.FalseStatement));
867
 
                }
868
 
                
869
 
                CodeObject IAstVisitor<CodeObject>.VisitLabelStatement(LabelStatement labelStatement)
870
 
                {
871
 
                        return new CodeLabeledStatement(labelStatement.Label);
872
 
                }
873
 
                
874
 
                CodeObject IAstVisitor<CodeObject>.VisitLockStatement(LockStatement lockStatement)
875
 
                {
876
 
                        return MakeSnippetStatement(lockStatement);
877
 
                }
878
 
                
879
 
                CodeObject IAstVisitor<CodeObject>.VisitReturnStatement(ReturnStatement returnStatement)
880
 
                {
881
 
                        return new CodeMethodReturnStatement(Convert(returnStatement.Expression));
882
 
                }
883
 
                
884
 
                CodeObject IAstVisitor<CodeObject>.VisitSwitchStatement(SwitchStatement switchStatement)
885
 
                {
886
 
                        return MakeSnippetStatement(switchStatement);
887
 
                }
888
 
                
889
 
                CodeObject IAstVisitor<CodeObject>.VisitSwitchSection(SwitchSection switchSection)
890
 
                {
891
 
                        throw new NotSupportedException();
892
 
                }
893
 
                
894
 
                CodeObject IAstVisitor<CodeObject>.VisitCaseLabel(CaseLabel caseLabel)
895
 
                {
896
 
                        throw new NotSupportedException();
897
 
                }
898
 
                
899
 
                CodeObject IAstVisitor<CodeObject>.VisitThrowStatement(ThrowStatement throwStatement)
900
 
                {
901
 
                        return new CodeThrowExceptionStatement(Convert(throwStatement.Expression));
902
 
                }
903
 
                
904
 
                CodeObject IAstVisitor<CodeObject>.VisitTryCatchStatement(TryCatchStatement tryCatchStatement)
905
 
                {
906
 
                        List<CodeCatchClause> catchClauses = new List<CodeCatchClause>();
907
 
                        foreach (var catchClause in tryCatchStatement.CatchClauses) {
908
 
                                catchClauses.Add(new CodeCatchClause(catchClause.VariableName, Convert(catchClause.Type), ConvertBlock(catchClause.Body)));
909
 
                        }
910
 
                        return new CodeTryCatchFinallyStatement(
911
 
                                ConvertBlock(tryCatchStatement.TryBlock),
912
 
                                catchClauses.ToArray(),
913
 
                                ConvertBlock(tryCatchStatement.FinallyBlock));
914
 
                }
915
 
                
916
 
                CodeObject IAstVisitor<CodeObject>.VisitCatchClause(CatchClause catchClause)
917
 
                {
918
 
                        throw new NotSupportedException();
919
 
                }
920
 
                
921
 
                CodeObject IAstVisitor<CodeObject>.VisitUncheckedStatement(UncheckedStatement uncheckedStatement)
922
 
                {
923
 
                        return MakeSnippetStatement(uncheckedStatement);
924
 
                }
925
 
                
926
 
                CodeObject IAstVisitor<CodeObject>.VisitUnsafeStatement(UnsafeStatement unsafeStatement)
927
 
                {
928
 
                        return MakeSnippetStatement(unsafeStatement);
929
 
                }
930
 
                
931
 
                CodeObject IAstVisitor<CodeObject>.VisitUsingStatement(UsingStatement usingStatement)
932
 
                {
933
 
                        return MakeSnippetStatement(usingStatement);
934
 
                }
935
 
                
936
 
                CodeObject IAstVisitor<CodeObject>.VisitVariableDeclarationStatement(VariableDeclarationStatement variableDeclarationStatement)
937
 
                {
938
 
                        if (variableDeclarationStatement.Variables.Count != 1)
939
 
                                return MakeSnippetStatement(variableDeclarationStatement);
940
 
                        VariableInitializer vi = variableDeclarationStatement.Variables.Single();
941
 
                        return new CodeVariableDeclarationStatement(
942
 
                                Convert(variableDeclarationStatement.Type),
943
 
                                vi.Name,
944
 
                                ConvertVariableInitializer(vi.Initializer, variableDeclarationStatement.Type));
945
 
                }
946
 
                
947
 
                CodeExpression ConvertVariableInitializer(Expression expr, AstType type)
948
 
                {
949
 
                        ArrayInitializerExpression aie = expr as ArrayInitializerExpression;
950
 
                        if (aie != null) {
951
 
                                return new CodeArrayCreateExpression(Convert(type), Convert(aie.Elements));
952
 
                        } else {
953
 
                                return Convert(expr);
954
 
                        }
955
 
                }
956
 
                
957
 
                CodeObject IAstVisitor<CodeObject>.VisitWhileStatement(WhileStatement whileStatement)
958
 
                {
959
 
                        return new CodeIterationStatement(null, Convert(whileStatement.Condition), null, ConvertEmbeddedStatement(whileStatement.EmbeddedStatement));
960
 
                }
961
 
                
962
 
                CodeObject IAstVisitor<CodeObject>.VisitYieldBreakStatement(YieldBreakStatement yieldBreakStatement)
963
 
                {
964
 
                        return MakeSnippetStatement(yieldBreakStatement);
965
 
                }
966
 
                
967
 
                CodeObject IAstVisitor<CodeObject>.VisitYieldReturnStatement(YieldReturnStatement yieldStatement)
968
 
                {
969
 
                        return MakeSnippetStatement(yieldStatement);
970
 
                }
971
 
                
972
 
                CodeObject IAstVisitor<CodeObject>.VisitAccessor(Accessor accessor)
973
 
                {
974
 
                        throw new NotSupportedException();
975
 
                }
976
 
                
977
 
                CodeObject IAstVisitor<CodeObject>.VisitConstructorDeclaration(ConstructorDeclaration constructorDeclaration)
978
 
                {
979
 
                        CodeConstructor ctor = new CodeConstructor();
980
 
                        ctor.Attributes = ConvertMemberAttributes(constructorDeclaration.Modifiers);
981
 
                        ctor.CustomAttributes.AddRange(Convert(constructorDeclaration.Attributes));
982
 
                        if (constructorDeclaration.Initializer.ConstructorInitializerType == ConstructorInitializerType.This) {
983
 
                                ctor.ChainedConstructorArgs.AddRange(Convert(constructorDeclaration.Initializer.Arguments));
984
 
                        } else {
985
 
                                ctor.BaseConstructorArgs.AddRange(Convert(constructorDeclaration.Initializer.Arguments));
986
 
                        }
987
 
                        ctor.Parameters.AddRange(Convert(constructorDeclaration.Parameters));
988
 
                        
989
 
                        ctor.Statements.AddRange(ConvertBlock(constructorDeclaration.Body));
990
 
                        return ctor;
991
 
                }
992
 
                
993
 
                CodeObject IAstVisitor<CodeObject>.VisitConstructorInitializer(ConstructorInitializer constructorInitializer)
994
 
                {
995
 
                        throw new NotSupportedException();
996
 
                }
997
 
                
998
 
                CodeObject IAstVisitor<CodeObject>.VisitDestructorDeclaration(DestructorDeclaration destructorDeclaration)
999
 
                {
1000
 
                        return new CodeSnippetTypeMember(MakeSnippet(destructorDeclaration));
1001
 
                }
1002
 
                
1003
 
                CodeObject IAstVisitor<CodeObject>.VisitEnumMemberDeclaration(EnumMemberDeclaration enumMemberDeclaration)
1004
 
                {
1005
 
                        TypeDeclaration td = enumMemberDeclaration.Parent as TypeDeclaration;
1006
 
                        CodeMemberField f = new CodeMemberField(td != null ? td.Name : "Enum", enumMemberDeclaration.Name);
1007
 
                        f.Attributes = MemberAttributes.Public | MemberAttributes.Static;
1008
 
                        f.CustomAttributes.AddRange(Convert(enumMemberDeclaration.Attributes));
1009
 
                        f.InitExpression = Convert(enumMemberDeclaration.Initializer);
1010
 
                        return f;
1011
 
                }
1012
 
                
1013
 
                CodeObject IAstVisitor<CodeObject>.VisitEventDeclaration(EventDeclaration eventDeclaration)
1014
 
                {
1015
 
                        foreach (VariableInitializer vi in eventDeclaration.Variables) {
1016
 
                                if (!vi.Initializer.IsNull) {
1017
 
                                        AddTypeMember(new CodeSnippetTypeMember(MakeSnippet(eventDeclaration)));
1018
 
                                        continue;
1019
 
                                }
1020
 
                                
1021
 
                                CodeMemberEvent e = new CodeMemberEvent();
1022
 
                                e.Attributes = ConvertMemberAttributes(eventDeclaration.Modifiers);
1023
 
                                e.CustomAttributes.AddRange(Convert(eventDeclaration.Attributes));
1024
 
                                e.Name = vi.Name;
1025
 
                                e.Type = Convert(eventDeclaration.ReturnType);
1026
 
                                AddTypeMember(e);
1027
 
                        }
1028
 
                        return null;
1029
 
                }
1030
 
                
1031
 
                CodeObject IAstVisitor<CodeObject>.VisitCustomEventDeclaration(CustomEventDeclaration customEventDeclaration)
1032
 
                {
1033
 
                        return new CodeSnippetTypeMember(MakeSnippet(customEventDeclaration));
1034
 
                }
1035
 
                
1036
 
                CodeObject IAstVisitor<CodeObject>.VisitFieldDeclaration(FieldDeclaration fieldDeclaration)
1037
 
                {
1038
 
                        foreach (VariableInitializer vi in fieldDeclaration.Variables) {
1039
 
                                CodeMemberField f = new CodeMemberField(Convert(fieldDeclaration.ReturnType), vi.Name);
1040
 
                                f.Attributes = ConvertMemberAttributes(fieldDeclaration.Modifiers);
1041
 
                                f.CustomAttributes.AddRange(Convert(fieldDeclaration.Attributes));
1042
 
                                f.InitExpression = ConvertVariableInitializer(vi.Initializer, fieldDeclaration.ReturnType);
1043
 
                                AddTypeMember(f);
1044
 
                        }
1045
 
                        return null;
1046
 
                }
1047
 
                
1048
 
                CodeObject IAstVisitor<CodeObject>.VisitIndexerDeclaration(IndexerDeclaration indexerDeclaration)
1049
 
                {
1050
 
                        CodeMemberProperty p = new CodeMemberProperty();
1051
 
                        p.Attributes = ConvertMemberAttributes(indexerDeclaration.Modifiers);
1052
 
                        p.CustomAttributes.AddRange(Convert(indexerDeclaration.Attributes));
1053
 
                        p.Name = "Items";
1054
 
                        p.PrivateImplementationType = Convert(indexerDeclaration.PrivateImplementationType);
1055
 
                        p.Parameters.AddRange(Convert(indexerDeclaration.Parameters));
1056
 
                        p.Type = Convert(indexerDeclaration.ReturnType);
1057
 
                        
1058
 
                        if (!indexerDeclaration.Getter.IsNull) {
1059
 
                                p.HasGet = true;
1060
 
                                p.GetStatements.AddRange(ConvertBlock(indexerDeclaration.Getter.Body));
1061
 
                        }
1062
 
                        if (!indexerDeclaration.Setter.IsNull) {
1063
 
                                p.HasSet = true;
1064
 
                                p.SetStatements.AddRange(ConvertBlock(indexerDeclaration.Setter.Body));
1065
 
                        }
1066
 
                        return p;
1067
 
                }
1068
 
                
1069
 
                CodeObject IAstVisitor<CodeObject>.VisitMethodDeclaration(MethodDeclaration methodDeclaration)
1070
 
                {
1071
 
                        CodeMemberMethod m = new CodeMemberMethod();
1072
 
                        m.Attributes = ConvertMemberAttributes(methodDeclaration.Modifiers);
1073
 
                        
1074
 
                        m.CustomAttributes.AddRange(Convert(methodDeclaration.Attributes.Where(a => a.AttributeTarget != "return")));
1075
 
                        m.ReturnTypeCustomAttributes.AddRange(Convert(methodDeclaration.Attributes.Where(a => a.AttributeTarget == "return")));
1076
 
                        
1077
 
                        m.ReturnType = Convert(methodDeclaration.ReturnType);
1078
 
                        m.PrivateImplementationType = Convert(methodDeclaration.PrivateImplementationType);
1079
 
                        m.Name = methodDeclaration.Name;
1080
 
                        m.TypeParameters.AddRange(ConvertTypeParameters(methodDeclaration.TypeParameters, methodDeclaration.Constraints));
1081
 
                        m.Parameters.AddRange(Convert(methodDeclaration.Parameters));
1082
 
                        
1083
 
                        m.Statements.AddRange(ConvertBlock(methodDeclaration.Body));
1084
 
                        return m;
1085
 
                }
1086
 
                
1087
 
                CodeObject IAstVisitor<CodeObject>.VisitOperatorDeclaration(OperatorDeclaration operatorDeclaration)
1088
 
                {
1089
 
                        CodeMemberMethod m = new CodeMemberMethod();
1090
 
                        m.Attributes = ConvertMemberAttributes(operatorDeclaration.Modifiers);
1091
 
                        
1092
 
                        m.CustomAttributes.AddRange(Convert(operatorDeclaration.Attributes.Where(a => a.AttributeTarget != "return")));
1093
 
                        m.ReturnTypeCustomAttributes.AddRange(Convert(operatorDeclaration.Attributes.Where(a => a.AttributeTarget == "return")));
1094
 
                        
1095
 
                        m.ReturnType = Convert(operatorDeclaration.ReturnType);
1096
 
                        m.Name = operatorDeclaration.Name;
1097
 
                        m.Parameters.AddRange(Convert(operatorDeclaration.Parameters));
1098
 
                        
1099
 
                        m.Statements.AddRange(ConvertBlock(operatorDeclaration.Body));
1100
 
                        return m;
1101
 
                }
1102
 
                
1103
 
                CodeObject IAstVisitor<CodeObject>.VisitParameterDeclaration(ParameterDeclaration parameterDeclaration)
1104
 
                {
1105
 
                        var p = new CodeParameterDeclarationExpression(Convert(parameterDeclaration.Type), parameterDeclaration.Name);
1106
 
                        p.CustomAttributes.AddRange(Convert(parameterDeclaration.Attributes));
1107
 
                        switch (parameterDeclaration.ParameterModifier) {
1108
 
                                case ParameterModifier.Ref:
1109
 
                                        p.Direction = System.CodeDom.FieldDirection.Ref;
1110
 
                                        break;
1111
 
                                case ParameterModifier.Out:
1112
 
                                        p.Direction = System.CodeDom.FieldDirection.Out;
1113
 
                                        break;
1114
 
                        }
1115
 
                        return p;
1116
 
                }
1117
 
                
1118
 
                CodeParameterDeclarationExpression[] Convert(IEnumerable<ParameterDeclaration> parameters)
1119
 
                {
1120
 
                        List<CodeParameterDeclarationExpression> result = new List<CodeParameterDeclarationExpression>();
1121
 
                        foreach (ParameterDeclaration pd in parameters) {
1122
 
                                CodeParameterDeclarationExpression pde = pd.AcceptVisitor(this) as CodeParameterDeclarationExpression;
1123
 
                                if (pde != null)
1124
 
                                        result.Add(pde);
1125
 
                        }
1126
 
                        return result.ToArray();
1127
 
                }
1128
 
                
1129
 
                CodeObject IAstVisitor<CodeObject>.VisitPropertyDeclaration(PropertyDeclaration propertyDeclaration)
1130
 
                {
1131
 
                        CodeMemberProperty p = new CodeMemberProperty();
1132
 
                        p.Attributes = ConvertMemberAttributes(propertyDeclaration.Modifiers);
1133
 
                        p.CustomAttributes.AddRange(Convert(propertyDeclaration.Attributes));
1134
 
                        p.Name = propertyDeclaration.Name;
1135
 
                        p.PrivateImplementationType = Convert(propertyDeclaration.PrivateImplementationType);
1136
 
                        p.Type = Convert(propertyDeclaration.ReturnType);
1137
 
                        
1138
 
                        if (!propertyDeclaration.Getter.IsNull) {
1139
 
                                p.HasGet = true;
1140
 
                                p.GetStatements.AddRange(ConvertBlock(propertyDeclaration.Getter.Body));
1141
 
                        }
1142
 
                        if (!propertyDeclaration.Setter.IsNull) {
1143
 
                                p.HasSet = true;
1144
 
                                p.SetStatements.AddRange(ConvertBlock(propertyDeclaration.Setter.Body));
1145
 
                        }
1146
 
                        return p;
1147
 
                }
1148
 
                
1149
 
                CodeObject IAstVisitor<CodeObject>.VisitVariableInitializer(VariableInitializer variableInitializer)
1150
 
                {
1151
 
                        throw new NotSupportedException(); // should be handled by the parent node
1152
 
                }
1153
 
                
1154
 
                CodeObject IAstVisitor<CodeObject>.VisitFixedFieldDeclaration(FixedFieldDeclaration fixedFieldDeclaration)
1155
 
                {
1156
 
                        return new CodeSnippetTypeMember(MakeSnippet(fixedFieldDeclaration));
1157
 
                }
1158
 
                
1159
 
                CodeObject IAstVisitor<CodeObject>.VisitFixedVariableInitializer(FixedVariableInitializer fixedVariableInitializer)
1160
 
                {
1161
 
                        throw new NotSupportedException(); // should be handled by the parent node
1162
 
                }
1163
 
                
1164
 
                CodeObject IAstVisitor<CodeObject>.VisitCompilationUnit(CompilationUnit compilationUnit)
1165
 
                {
1166
 
                        CodeCompileUnit cu = new CodeCompileUnit();
1167
 
                        foreach (AstNode node in compilationUnit.Children) {
1168
 
                                CodeObject o = node.AcceptVisitor(this);
1169
 
                                
1170
 
                                CodeNamespace ns = o as CodeNamespace;
1171
 
                                if (ns != null) {
1172
 
                                        cu.Namespaces.Add(ns);
1173
 
                                }
1174
 
                                CodeTypeDeclaration td = o as CodeTypeDeclaration;
1175
 
                                if (td != null) {
1176
 
                                        cu.Namespaces.Add(new CodeNamespace() { Types = { td } });
1177
 
                                }
1178
 
                        }
1179
 
                        return cu;
1180
 
                }
1181
 
                
1182
 
                CodeObject IAstVisitor<CodeObject>.VisitSimpleType(SimpleType simpleType)
1183
 
                {
1184
 
                        if (useFullyQualifiedTypeNames) {
1185
 
                                IType type = Resolve(simpleType).Type;
1186
 
                                if (type.Kind != TypeKind.Unknown)
1187
 
                                        return Convert(type);
1188
 
                        }
1189
 
                        var tr = new CodeTypeReference(simpleType.Identifier);
1190
 
                        tr.TypeArguments.AddRange(Convert(simpleType.TypeArguments));
1191
 
                        return tr;
1192
 
                }
1193
 
                
1194
 
                CodeObject IAstVisitor<CodeObject>.VisitMemberType(MemberType memberType)
1195
 
                {
1196
 
                        if (memberType.IsDoubleColon && new SimpleType("global").IsMatch(memberType.Target)) {
1197
 
                                var tr = new CodeTypeReference(memberType.MemberName, CodeTypeReferenceOptions.GlobalReference);
1198
 
                                tr.TypeArguments.AddRange(Convert(memberType.TypeArguments));
1199
 
                                return tr;
1200
 
                        }
1201
 
                        if (useFullyQualifiedTypeNames || memberType.IsDoubleColon) {
1202
 
                                IType type = Resolve(memberType).Type;
1203
 
                                if (type.Kind != TypeKind.Unknown)
1204
 
                                        return Convert(type);
1205
 
                        }
1206
 
                        CodeTypeReference target = Convert(memberType.Target);
1207
 
                        if (target == null)
1208
 
                                return null;
1209
 
                        target.BaseType = target.BaseType + "." + memberType.MemberName;
1210
 
                        target.TypeArguments.AddRange(Convert(memberType.TypeArguments));
1211
 
                        return target;
1212
 
                }
1213
 
                
1214
 
                CodeObject IAstVisitor<CodeObject>.VisitComposedType(ComposedType composedType)
1215
 
                {
1216
 
                        CodeTypeReference typeRef = Convert(composedType.BaseType);
1217
 
                        if (typeRef == null)
1218
 
                                return null;
1219
 
                        if (composedType.HasNullableSpecifier) {
1220
 
                                typeRef = new CodeTypeReference("System.Nullable") { TypeArguments = { typeRef } };
1221
 
                        }
1222
 
                        foreach (ArraySpecifier s in composedType.ArraySpecifiers.Reverse()) {
1223
 
                                typeRef = new CodeTypeReference(typeRef, s.Dimensions);
1224
 
                        }
1225
 
                        return typeRef;
1226
 
                }
1227
 
                
1228
 
                CodeObject IAstVisitor<CodeObject>.VisitArraySpecifier(ArraySpecifier arraySpecifier)
1229
 
                {
1230
 
                        throw new NotSupportedException(); // handled by parent node
1231
 
                }
1232
 
                
1233
 
                CodeObject IAstVisitor<CodeObject>.VisitPrimitiveType(PrimitiveType primitiveType)
1234
 
                {
1235
 
                        KnownTypeCode typeCode = primitiveType.KnownTypeCode;
1236
 
                        if (typeCode != KnownTypeCode.None) {
1237
 
                                KnownTypeReference ktr = KnownTypeReference.Get(typeCode);
1238
 
                                return new CodeTypeReference(ktr.Namespace + "." + ktr.Name);
1239
 
                        }
1240
 
                        return new CodeTypeReference(primitiveType.Keyword);
1241
 
                }
1242
 
                
1243
 
                CodeObject IAstVisitor<CodeObject>.VisitComment (Comment comment)
1244
 
                {
1245
 
                        return new CodeComment (comment.Content, comment.CommentType == CommentType.Documentation);
1246
 
                }
1247
 
 
1248
 
                CodeObject IAstVisitor<CodeObject>.VisitNewLine(NewLineNode newLineNode)
1249
 
                {
1250
 
                        throw new NotSupportedException();
1251
 
                }
1252
 
 
1253
 
                CodeObject IAstVisitor<CodeObject>.VisitWhitespace(WhitespaceNode whitespaceNode)
1254
 
                {
1255
 
                        throw new NotSupportedException();
1256
 
                }
1257
 
 
1258
 
                CodeObject IAstVisitor<CodeObject>.VisitText(TextNode textNode)
1259
 
                {
1260
 
                        throw new NotSupportedException();
1261
 
                }
1262
 
 
1263
 
                CodeObject IAstVisitor<CodeObject>.VisitPreProcessorDirective (PreProcessorDirective preProcessorDirective)
1264
 
                {
1265
 
                        return new CodeComment ("#" + preProcessorDirective.Type.ToString ().ToLower ());
1266
 
                }
1267
 
                
1268
 
                CodeObject IAstVisitor<CodeObject>.VisitTypeParameterDeclaration(TypeParameterDeclaration typeParameterDeclaration)
1269
 
                {
1270
 
                        throw new NotSupportedException(); // type parameters and constraints are handled together
1271
 
                }
1272
 
                
1273
 
                CodeObject IAstVisitor<CodeObject>.VisitConstraint(Constraint constraint)
1274
 
                {
1275
 
                        throw new NotSupportedException();
1276
 
                }
1277
 
                
1278
 
                CodeTypeParameter[] ConvertTypeParameters(IEnumerable<TypeParameterDeclaration> typeParameters, IEnumerable<Constraint> constraints)
1279
 
                {
1280
 
                        List<CodeTypeParameter> result = new List<CodeTypeParameter>();
1281
 
                        foreach (TypeParameterDeclaration tpDecl in typeParameters) {
1282
 
                                CodeTypeParameter tp = new CodeTypeParameter(tpDecl.Name);
1283
 
                                tp.CustomAttributes.AddRange(Convert(tpDecl.Attributes));
1284
 
                                foreach (Constraint constraint in constraints) {
1285
 
                                        if (constraint.TypeParameter.Identifier == tp.Name) {
1286
 
                                                foreach (AstType baseType in constraint.BaseTypes) {
1287
 
                                                        if (baseType is PrimitiveType && ((PrimitiveType)baseType).Keyword == "new") {
1288
 
                                                                tp.HasConstructorConstraint = true;
1289
 
                                                        } else {
1290
 
                                                                CodeTypeReference tr = Convert(baseType);
1291
 
                                                                if (tr != null)
1292
 
                                                                        tp.Constraints.Add(tr);
1293
 
                                                        }
1294
 
                                                }
1295
 
                                        }
1296
 
                                }
1297
 
                                result.Add(tp);
1298
 
                        }
1299
 
                        return result.ToArray();
1300
 
                }
1301
 
                
1302
 
                CodeObject IAstVisitor<CodeObject>.VisitCSharpTokenNode(CSharpTokenNode cSharpTokenNode)
1303
 
                {
1304
 
                        return null;
1305
 
                }
1306
 
                
1307
 
                CodeObject IAstVisitor<CodeObject>.VisitIdentifier(Identifier identifier)
1308
 
                {
1309
 
                        return null;
1310
 
                }
1311
 
                
1312
 
                CodeObject IAstVisitor<CodeObject>.VisitPatternPlaceholder(AstNode placeholder, ICSharpCode.NRefactory.PatternMatching.Pattern pattern)
1313
 
                {
1314
 
                        return null;
1315
 
                }
1316
 
                
1317
 
                CodeObject IAstVisitor<CodeObject>.VisitDocumentationReference(DocumentationReference documentationReference)
1318
 
                {
1319
 
                        return null;
1320
 
                }
1321
 
        }
1322
 
}