EventDeclaration TransformAutomaticEvents(CustomEventDeclaration ev) { if (!ev.PrivateImplementationType.IsNull) { return(null); } if (!ev.Modifiers.HasFlag(Modifiers.Abstract)) { if (!CheckAutomaticEventV4(ev) && !CheckAutomaticEventV2(ev) && !CheckAutomaticEventV4MCS(ev)) { return(null); } } RemoveCompilerGeneratedAttribute(ev.AddAccessor.Attributes, attributeTypesToRemoveFromAutoEvents); EventDeclaration ed = new EventDeclaration(); ev.Attributes.MoveTo(ed.Attributes); foreach (var attr in ev.AddAccessor.Attributes) { attr.AttributeTarget = "method"; ed.Attributes.Add(attr.Detach()); } ed.ReturnType = ev.ReturnType.Detach(); ed.Modifiers = ev.Modifiers; ed.Variables.Add(new VariableInitializer(ev.Name)); ed.CopyAnnotationsFrom(ev); IEvent eventDef = ev.GetSymbol() as IEvent; if (eventDef != null) { IField field = eventDef.DeclaringType.GetFields(f => f.Name == ev.Name, GetMemberOptions.IgnoreInheritedMembers).SingleOrDefault(); if (field != null) { ed.AddAnnotation(field); var attributes = field.GetAttributes() .Where(a => !attributeTypesToRemoveFromAutoEvents.Contains(a.AttributeType.FullName)) .Select(context.TypeSystemAstBuilder.ConvertAttribute).ToArray(); if (attributes.Length > 0) { var section = new AttributeSection { AttributeTarget = "field" }; section.Attributes.AddRange(attributes); ed.Attributes.Add(section); } } } ev.ReplaceWith(ed); return(ed); }
EventDeclaration TransformAutomaticEvents(CustomEventDeclaration ev) { Match m1 = automaticEventPatternV4.Match(ev.AddAccessor); if (!CheckAutomaticEventV4Match(m1, ev, true)) { return(null); } Match m2 = automaticEventPatternV4.Match(ev.RemoveAccessor); if (!CheckAutomaticEventV4Match(m2, ev, false)) { return(null); } EventDeclaration ed = new EventDeclaration(); ev.Attributes.MoveTo(ed.Attributes); ed.ReturnType = ev.ReturnType.Detach(); ed.Modifiers = ev.Modifiers; ed.Variables.Add(new VariableInitializer(ev.Name)); ed.CopyAnnotationsFrom(ev); EventDefinition eventDef = ev.Annotation <EventDefinition>(); if (eventDef != null) { FieldDefinition field = eventDef.DeclaringType.Fields.FirstOrDefault(f => f.Name == ev.Name); if (field != null) { ed.AddAnnotation(field); AstBuilder.ConvertAttributes(ed, field, AttributeTarget.Field); } } ev.ReplaceWith(ed); return(ed); }
public void Run(AstNode compilationUnit) { foreach (var en in compilationUnit.Descendants.OfType <EntityDeclaration>()) { var def = en.Annotation <IMemberDef>(); Debug.Assert(def != null); if (def == null) { continue; } // The decompiler doesn't remove IteratorStateMachineAttributes/AsyncStateMachineAttribute. // These attributes usually contain the name of a type with invalid characters in its name // and will prevent the user from compiling the code. if (en.SymbolKind == SymbolKind.Method) { foreach (var sect in en.Attributes) { foreach (var attr in sect.Attributes) { var ca = attr.Annotation <CustomAttribute>(); var fn = ca?.TypeFullName; if (fn == "System.Runtime.CompilerServices.IteratorStateMachineAttribute" || fn == "System.Runtime.CompilerServices.AsyncStateMachineAttribute") { attr.Remove(); } } if (!sect.Attributes.Any()) { sect.Remove(); } } } if (makeEverythingPublic) { const Modifiers accessFlags = Modifiers.Private | Modifiers.Internal | Modifiers.Protected | Modifiers.Public; en.Modifiers = (en.Modifiers & ~accessFlags) | Modifiers.Public; bool clearModifiers = false; var owner = en.Parent as TypeDeclaration; if (owner?.ClassType == ClassType.Enum || owner?.ClassType == ClassType.Interface) { clearModifiers = true; } else if (en is Accessor) { // If it's a getter/setter/adder/remover, its owner (the property/event) already is public, // so remove the modifier from the accessor clearModifiers = true; } else if (en.SymbolKind == SymbolKind.Destructor) { clearModifiers = true; } else if (en.SymbolKind == SymbolKind.Constructor && en.HasModifier(Modifiers.Static)) { clearModifiers = true; } else if (en is MethodDeclaration) { var md = (MethodDeclaration)en; if (!md.PrivateImplementationType.IsNull || (md.Parent as TypeDeclaration)?.ClassType == ClassType.Interface) { clearModifiers = true; } } else if (en is CustomEventDeclaration) { var ed = (CustomEventDeclaration)en; if (!ed.PrivateImplementationType.IsNull || (ed.Parent as TypeDeclaration)?.ClassType == ClassType.Interface) { clearModifiers = true; } } else if (en is PropertyDeclaration) { var pd = (PropertyDeclaration)en; if (!pd.PrivateImplementationType.IsNull || (pd.Parent as TypeDeclaration)?.ClassType == ClassType.Interface) { clearModifiers = true; } } if (clearModifiers) { en.Modifiers &= ~accessFlags; } } if (partialTypes.Contains(def)) { var tdecl = en as TypeDeclaration; Debug.Assert(tdecl != null); if (tdecl != null) { tdecl.Modifiers |= Modifiers.Partial; if (!showDefinitions) { tdecl.BaseTypes.Clear(); tdecl.Attributes.Clear(); } } } else { // The decompiler doesn't support Roslyn yet so remove this since // it will break compilation if (def is TypeDef && def.Name == "<>c") { en.Remove(); } if (showDefinitions) { if (!defsToShow.Contains(def)) { en.Remove(); } } else { if (defsToShow.Contains(def)) { en.Remove(); } else if (en is CustomEventDeclaration) { // Convert this hidden event to an automatic event var ev = (CustomEventDeclaration)en; var ed = new EventDeclaration(); ed.ReturnType = ev.ReturnType.Detach(); ed.Modifiers = ev.Modifiers; ed.Variables.Add(new VariableInitializer(TextColorHelper.GetColor(ev.Annotation <EventDef>()), ev.Name)); ed.CopyAnnotationsFrom(ev); ev.ReplaceWith(ed); } } } } }