void ExecuteMacro(MacroOutput output, CodeConstruct sourceFileCode, string sourceFilePath, string defaultNamespace, int orderNo) { var types = new Type[] { typeof(sbyte), typeof(short), typeof(ushort), typeof(int), typeof(uint), typeof(long), typeof(ulong), typeof(char), typeof(float), typeof(double), typeof(decimal), typeof(bool) }; output.CodeConstruct.CompilationUnit.AddUsings(sourceFileCode.CompilationUnit.GetUsings()); var ns = sourceFileCode.Clone().CompilationUnit.Down().OfType <NamespaceDeclaration>().First(); ns.Children.Clear(); output.CodeConstruct.CompilationUnit.AddChild(ns); var partialType = GetPartialType(sourceFileCode); partialType.Children.Clear(); ns.AddChild(partialType); foreach (var type in types) { var code = sourceFileCode.Clone(); var typeReference = type.ToTypeReference(); var pointerType = type.MakePointerType().ToTypeReference(); var createMethod = GetPartialType(sourceFileCode).Down().OfType <MethodDeclaration>().First(m => m.Name == "Create" && m.Parameters.Count == 3); createMethod.Parameters.First().TypeReference = type.MakeArrayType().ToTypeReference(); createMethod.Body.Children.OfType <LocalVariableDeclaration>().First(vd => vd.Variables.First().Name == "sizeofTData").Variables.First() .Initializer.Cast <SizeOfExpression>().TypeReference = typeReference; createMethod.Body.Children.OfType <UnsafeStatement>().First().Block.Children.OfType <FixedStatement>().First().PointerDeclaration .Cast <LocalVariableDeclaration>().TypeReference = pointerType; partialType.AddChild(createMethod); createMethod = GetPartialType(sourceFileCode).Down().OfType <MethodDeclaration>().First(m => m.Name == "Create" && m.Parameters.Count == 1); createMethod.Parameters.First().TypeReference = type.MakeArrayType().ToTypeReference(); createMethod.Body.Children.OfType <LocalVariableDeclaration>().First(vd => vd.Variables.First().Name == "sizeofTData").Variables.First() .Initializer.Cast <SizeOfExpression>().TypeReference = typeReference; partialType.AddChild(createMethod); var modifiedType = code.CompilationUnit.Down().OfType <TypeDeclaration>().First(t => t.Name == "PointerArrayOfByte"); modifiedType.Name = modifiedType.Name.Replace("Byte", type.Name); modifiedType.BaseTypes.First().GenericTypes[0] = typeReference; modifiedType.Down().OfType <PropertyDeclaration>().First(p => p.IsIndexer).TypeReference = typeReference; modifiedType.Down().OfType <PropertyDeclaration>().First(p => p.IsIndexer).GetRegion.Block.Children.First().Cast <UnsafeStatement>().Block.Children .First().Cast <ReturnStatement>().Expression.Cast <IndexerExpression>().TargetObject.Cast <ParenthesizedExpression>().Expression.Cast <CastExpression>() .CastTo = pointerType; modifiedType.Down().OfType <PropertyDeclaration>().First(p => p.IsIndexer).SetRegion.Block.Children.First().Cast <UnsafeStatement>().Block.Children .First().Cast <ExpressionStatement>().Expression.Cast <AssignmentExpression>().Left.Cast <IndexerExpression>().TargetObject.Cast <ParenthesizedExpression>() .Expression.Cast <CastExpression>().CastTo = pointerType; ns.AddChild(modifiedType); } }
void ExecuteMacro(MacroOutput output, CodeConstruct sourceFileCode, string sourceFilePath, string defaultNamespace, int orderNo) { NamespaceDeclaration ns = output.CodeConstruct.CompilationUnit.PushChild( new NamespaceDeclaration(sourceFileCode.CompilationUnit.Down().OfType <NamespaceDeclaration>().First().Name)); ns.AddUsing("System"); List <string> genericTypeNameList = new List <string>(); List <string> paramNameList = new List <string>(); for (int i = 1; i <= MAX_PARAMS; i++) { genericTypeNameList.Add("T" + i); paramNameList.Add("param" + i); } for (int paramCount = 1; paramCount <= MAX_PARAMS; paramCount++) { Func <string, int, bool> where = (name, index) => index < paramCount; IEnumerable <string> genericTypeNames = genericTypeNameList.Where(where); string[] paramNames = paramNameList.Where(where).ToArray(); CodeConstruct sourceFileCodeClone = sourceFileCode.Clone(); ns.AddChild(MakeGenericCopy(sourceFileCodeClone, "WeakAction", genericTypeNames, paramNames)); ns.AddChild(MakeGenericCopy(sourceFileCodeClone, "WeakFunc", genericTypeNames, paramNames)); } }
void MakeMethodWithAdditionalGenericTypes(TypeDeclaration generatedType, CodeConstruct sourceFileCode, IEnumerable <string> genericTypeNames, string[] paramNames, string typeName, string methodName, bool staticMethod) { TypeDeclaration type = sourceFileCode.Clone().CompilationUnit.Down() .OfType <TypeDeclaration>().First(t => t.Name == typeName); MethodDeclaration method = type.Children.OfType <MethodDeclaration>().First(m => m.Name == methodName && m.Templates.Count != 0 && ((staticMethod && m.Modifier.HasFlag(Modifiers.Static)) || !(staticMethod || m.Modifier.HasFlag(Modifiers.Static)))); method.Templates[0].Name = "T1"; method.Templates.AddRange(genericTypeNames.Select(name => new TemplateDefinition(name, null))); method.Parameters[0].TypeReference.GenericTypes[0].Type = "T1"; method.Parameters[0].TypeReference.GenericTypes.AddRange(genericTypeNames.Select(name => new TypeReference(name))); method.Parameters[1].TypeReference.Type = "T1"; method.Parameters[1].ParameterName = "param1"; method.Parameters.AddRange(genericTypeNames.Select((name, index) => new ParameterDeclarationExpression(new TypeReference(name), paramNames[index++]))); InvocationExpression invocation = method.Body.Children.OfType <LocalVariableDeclaration>().First().Variables.First().Initializer .Cast <ObjectCreateExpression>().Parameters[0].Cast <AnonymousMethodExpression>().Body.Children.Cast <ExpressionStatement>().First() .Expression.Cast <InvocationExpression>(); invocation.Arguments[0].Cast <IdentifierExpression>().Identifier = "param1"; invocation.Arguments.AddRange(paramNames.Select(name => new IdentifierExpression(name))); generatedType.AddChild(method); }
void MakeGeneric(INode parent, CodeConstruct sourceFileCode, string typeName) { CodeConstruct sourceFileCodeClone; for (int paramCount = 1; paramCount <= MAX_PARAMS; paramCount++) { sourceFileCodeClone = sourceFileCode.Clone(); TypeDeclaration type = new DownwardTreeWalk <INode>(sourceFileCodeClone.CompilationUnit, n => n.Children) .OfType <TypeDeclaration>().First(t => t.Name == typeName); parent.AddChild(type); List <string> genericTypeNames = new List <string>(); List <string> paramNames = new List <string>(); for (int i = 1; i <= paramCount; i++) { string templateName = "T"; string paramName = "param"; if (paramCount > 1) { templateName += i; paramName += i; } genericTypeNames.Add(templateName); paramNames.Add(paramName); } type.Templates.AddRange(genericTypeNames.Select(name => new TemplateDefinition(name, null))); MethodDeclaration invokeMethod = type.Children.OfType <MethodDeclaration>().First(method => method.Name == "Invoke"); invokeMethod.Parameters.AddRange(genericTypeNames.Select((name, i) => new ParameterDeclarationExpression(new TypeReference(name), paramNames[i]))); ExpressionStatement statement = invokeMethod.Body.Children.OfType <ExpressionStatement>().First(); InvocationExpression invocation = (InvocationExpression)statement.Expression; invocation.Arguments.AddRange(paramNames.Select(name => new IdentifierExpression(name))); MethodDeclaration getInstanceMethod = type.Children.OfType <MethodDeclaration>().First(method => method.Name == "GetInstance"); AddGenericTypes(getInstanceMethod.TypeReference, genericTypeNames); CastExpression cast = getInstanceMethod.Body.Children.OfType <ReturnStatement>().First().Expression.Cast <CastExpression>(); AddGenericTypes(cast.CastTo, genericTypeNames); AddGenericTypes(cast.Expression.Cast <InvocationExpression>().Arguments.First().Cast <ObjectCreateExpression>().CreateType, genericTypeNames); } }
TypeDeclaration GetPartialType(CodeConstruct sourceFileCode) { return(sourceFileCode.Clone().CompilationUnit.Down().OfType <TypeDeclaration>().First(t => t.Name == "PointerArray" && t.Modifier.HasFlag(Modifiers.Partial))); }
void ExecuteMacro(MacroOutput output, CodeConstruct sourceFileCode, string sourceFilePath, string defaultNamespace, int orderNo) { string typeName = sourceFileCode.CompilationUnit.Down().OfType <TypeDeclaration>().First().Name; NamespaceDeclaration ns = (NamespaceDeclaration)output.CodeConstruct.CompilationUnit.PushChild(sourceFileCode.Clone().CompilationUnit .GetPartialClassArchitecture(typeName)); ns.AddUsings(sourceFileCode.CompilationUnit.GetUsings()); TypeDeclaration generatedType = output.CodeConstruct.CompilationUnit.Down() .OfType <TypeDeclaration>().First(t => t.Name == typeName); List <string> genericTypeNameList = new List <string>(); List <string> paramNameList = new List <string>(); for (int i = 2; i <= MAX_PARAMS; i++) { genericTypeNameList.Add("T" + i); paramNameList.Add("param" + i); } for (int paramCount = 2; paramCount <= MAX_PARAMS; paramCount++) { IEnumerable <string> genericTypeNames = genericTypeNameList.Where((name, index) => index <= paramCount - 2); string[] paramNames = paramNameList.Where((name, index) => index <= paramCount - 2).ToArray(); MakeMethodWithAdditionalGenericTypes(generatedType, sourceFileCode, genericTypeNames, paramNames, typeName, "InvokeActionInUnmonitoredWorkerThread", true); MakeMethodWithAdditionalGenericTypes(generatedType, sourceFileCode, genericTypeNames, paramNames, typeName, "InvokeActionInWorkerThread", false); } }