using System;
using System.Collections;
using System.Collections.Generic;
+using System.Collections.ObjectModel;
using System.Diagnostics;
using System.Globalization;
using System.IO;
MyXmlNodeList extensionMethods = new MyXmlNodeList ();
+ HashSet<string> forwardedTypes = new HashSet<string> ();
+
public override void Run (IEnumerable<string> args)
{
show_exceptions = DebugOutput;
this.assemblies = assemblies.Select (a => LoadAssembly (a)).ToList ();
+ // Store types that have been forwarded to avoid duplicate generation
+ GatherForwardedTypes ();
+
docEnum = docEnum ?? new DocumentationEnumerator ();
// PERFORM THE UPDATES
}
}
+ void GatherForwardedTypes ()
+ {
+ foreach (var asm in assemblies)
+ foreach (var type in asm.MainModule.ExportedTypes.Where (t => t.IsForwarder).Select (t => t.FullName))
+ forwardedTypes.Add (type);
+ }
+
static ExceptionLocations ParseExceptionLocations (string s)
{
ExceptionLocations loc = ExceptionLocations.Member;
index_assemblies.RemoveAll ();
- HashSet<string> goodfiles = new HashSet<string> ();
+ HashSet<string> goodfiles = new HashSet<string> (StringComparer.OrdinalIgnoreCase);
foreach (AssemblyDefinition assm in assemblies) {
AddIndexAssembly (assm, index_assemblies);
{
foreach (TypeDefinition type in docEnum.GetDocumentationTypes (assembly, null)) {
string typename = GetTypeFileName(type);
- if (!IsPublic (type) || typename.IndexOfAny (InvalidFilenameChars) >= 0)
+ if (!IsPublic (type) || typename.IndexOfAny (InvalidFilenameChars) >= 0 || forwardedTypes.Contains (type.FullName))
continue;
string reltypepath = DoUpdateType (type, source, dest);
{
TypeDefinition decl = type;
while (decl != null) {
- if (!(decl.IsPublic || decl.IsNestedPublic)) {
+ if (!(decl.IsPublic || decl.IsNestedPublic ||
+ decl.IsNestedFamily || decl.IsNestedFamily || decl.IsNestedFamilyOrAssembly)) {
return false;
}
decl = (TypeDefinition) decl.DeclaringType;
XmlDocument doc = new XmlDocument ();
doc.Load (typefile.FullName);
XmlElement e = doc.SelectSingleNode("/Type") as XmlElement;
- if (UpdateAssemblyVersions(e, GetAssemblyVersions(), false)) {
+ if (!no_assembly_versions && UpdateAssemblyVersions(e, GetAssemblyVersions(), false)) {
using (TextWriter writer = OpenWrite (typefile.FullName, FileMode.Truncate))
WriteXml(doc.DocumentElement, writer);
goodfiles.Add (relTypeFile);
// Deleted (or signature changed)
if (oldmember2 == null) {
- if (UpdateAssemblyVersions (oldmember, new string[]{ GetAssemblyVersion (type.Module.Assembly) }, false))
+ if (!no_assembly_versions && UpdateAssemblyVersions (oldmember, new string[]{ GetAssemblyVersion (type.Module.Assembly) }, false))
continue;
DeleteMember ("Member Removed", output, oldmember, todelete);
continue;
NormalizeWhitespace(e);
}
- private static string MakeAttributesValueString (object v, TypeReference valueType)
+ public static string MakeAttributesValueString (object v, TypeReference valueType)
{
if (v == null)
return "null";
return "typeof(" + v.ToString () + ")";
if (valueType.FullName == "System.String")
return "\"" + v.ToString () + "\"";
+ if (valueType.FullName == "System.Char")
+ return "'" + v.ToString () + "'";
if (v is Boolean)
return (bool)v ? "true" : "false";
TypeDefinition valueDef = valueType.Resolve ();
(from i in values.Keys
where (c & i) != 0
select typename + "." + values [i])
- .ToArray ());
+ .DefaultIfEmpty (v.ToString ()).ToArray ());
}
return "(" + GetDocTypeFullName (valueType) + ") " + v.ToString ();
}
}
}
+public class DynamicParserContext {
+ public ReadOnlyCollection<bool> TransformFlags;
+ public int TransformIndex;
+
+ public DynamicParserContext (ICustomAttributeProvider provider)
+ {
+ CustomAttribute da;
+ if (provider.HasCustomAttributes &&
+ (da = (provider.CustomAttributes.Cast<CustomAttribute>()
+ .SingleOrDefault (ca => ca.GetDeclaringType() == "System.Runtime.CompilerServices.DynamicAttribute"))) != null) {
+ CustomAttributeArgument[] values = da.ConstructorArguments.Count == 0
+ ? new CustomAttributeArgument [0]
+ : (CustomAttributeArgument[]) da.ConstructorArguments [0].Value;
+
+ TransformFlags = new ReadOnlyCollection<bool> (values.Select (t => (bool) t.Value).ToArray());
+ }
+ }
+}
+
public enum MemberFormatterState {
None,
WithinGenericTypeParameters,
get {return "";}
}
- public virtual string GetName (MemberReference member)
+ public string GetName (MemberReference member)
+ {
+ return GetName (member, null);
+ }
+
+ public virtual string GetName (MemberReference member, DynamicParserContext context)
{
TypeReference type = member as TypeReference;
if (type != null)
- return GetTypeName (type);
+ return GetTypeName (type, context);
MethodReference method = member as MethodReference;
if (method != null && method.Name == ".ctor") // method.IsConstructor
return GetConstructorName (method);
}
protected virtual string GetTypeName (TypeReference type)
+ {
+ return GetTypeName (type, null);
+ }
+
+ protected virtual string GetTypeName (TypeReference type, DynamicParserContext context)
{
if (type == null)
throw new ArgumentNullException ("type");
- return _AppendTypeName (new StringBuilder (type.Name.Length), type).ToString ();
+ return _AppendTypeName (new StringBuilder (type.Name.Length), type, context).ToString ();
}
protected virtual char[] ArrayDelimeters {
protected virtual MemberFormatterState MemberFormatterState { get; set; }
- protected StringBuilder _AppendTypeName (StringBuilder buf, TypeReference type)
+ protected StringBuilder _AppendTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
if (type is ArrayType) {
TypeSpecification spec = type as TypeSpecification;
- _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType ());
+ _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType (), context);
return AppendArrayModifiers (buf, (ArrayType) type);
}
if (type is ByReferenceType) {
- return AppendRefTypeName (buf, type);
+ return AppendRefTypeName (buf, type, context);
}
if (type is PointerType) {
- return AppendPointerTypeName (buf, type);
+ return AppendPointerTypeName (buf, type, context);
}
AppendNamespace (buf, type);
if (type is GenericParameter) {
- return AppendTypeName (buf, type);
+ return AppendTypeName (buf, type, context);
}
GenericInstanceType genInst = type as GenericInstanceType;
if (type.GenericParameters.Count == 0 &&
(genInst == null ? true : genInst.GenericArguments.Count == 0)) {
- return AppendFullTypeName (buf, type);
+ return AppendFullTypeName (buf, type, context);
}
- return AppendGenericType (buf, type);
+ return AppendGenericType (buf, type, context);
}
protected virtual StringBuilder AppendNamespace (StringBuilder buf, TypeReference type)
return buf;
}
- protected virtual StringBuilder AppendFullTypeName (StringBuilder buf, TypeReference type)
+ protected virtual StringBuilder AppendFullTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
if (type.DeclaringType != null)
- AppendFullTypeName (buf, type.DeclaringType).Append (NestedTypeSeparator);
- return AppendTypeName (buf, type);
+ AppendFullTypeName (buf, type.DeclaringType, context).Append (NestedTypeSeparator);
+ return AppendTypeName (buf, type, context);
}
- protected virtual StringBuilder AppendTypeName (StringBuilder buf, TypeReference type)
+ protected virtual StringBuilder AppendTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
+ if (context != null)
+ context.TransformIndex++;
return AppendTypeName (buf, type.Name);
}
get {return "@";}
}
- protected virtual StringBuilder AppendRefTypeName (StringBuilder buf, TypeReference type)
+ protected virtual StringBuilder AppendRefTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
TypeSpecification spec = type as TypeSpecification;
- return _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType ())
+ return _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType (), context)
.Append (RefTypeModifier);
}
get {return "*";}
}
- protected virtual StringBuilder AppendPointerTypeName (StringBuilder buf, TypeReference type)
+ protected virtual StringBuilder AppendPointerTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
TypeSpecification spec = type as TypeSpecification;
- return _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType ())
+ return _AppendTypeName (buf, spec != null ? spec.ElementType : type.GetElementType (), context)
.Append (PointerModifier);
}
get {return '.';}
}
- protected virtual StringBuilder AppendGenericType (StringBuilder buf, TypeReference type)
+ protected virtual StringBuilder AppendGenericType (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
List<TypeReference> decls = DocUtils.GetDeclaringTypes (
type is GenericInstanceType ? type.GetElementType () : type);
buf.Append (NestedTypeSeparator);
}
insertNested = true;
- AppendTypeName (buf, declDef);
+ AppendTypeName (buf, declDef, context);
int ac = DocUtils.GetGenericArgumentCount (declDef);
int c = ac - prev;
prev = ac;
buf.Append (GenericTypeContainer [0]);
var origState = MemberFormatterState;
MemberFormatterState = MemberFormatterState.WithinGenericTypeParameters;
- _AppendTypeName (buf, genArgs [argIdx++]);
- for (int i = 1; i < c; ++i)
- _AppendTypeName (buf.Append (","), genArgs [argIdx++]);
+ _AppendTypeName (buf, genArgs [argIdx++], context);
+ for (int i = 1; i < c; ++i) {
+ _AppendTypeName (buf.Append (","), genArgs [argIdx++], context);
+ }
MemberFormatterState = origState;
buf.Append (GenericTypeContainer [1]);
}
if (type == null)
throw new ArgumentNullException ("type");
StringBuilder buf = new StringBuilder (type.Name.Length);
- _AppendTypeName (buf, type);
+ _AppendTypeName (buf, type, null);
AppendGenericTypeConstraints (buf, type);
return buf.ToString ();
}
if (buf.Length != 0)
buf.Append (" ");
- buf.Append (GetTypeName (method.MethodReturnType)).Append (" ");
+ buf.Append (GetTypeName (method.ReturnType, new DynamicParserContext (method.MethodReturnType))).Append (" ");
AppendMethodName (buf, method);
AppendGenericMethod (buf, method).Append (" ");
return buf.ToString ();
}
- protected virtual string GetTypeName (MethodReturnType returnType)
- {
- return GetName (returnType.ReturnType);
- }
-
protected virtual StringBuilder AppendMethodName (StringBuilder buf, MethodDefinition method)
{
return buf.Append (method.Name);
return buf.Append (typename);
}
- protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type)
+ protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
- if (type is GenericParameter)
- return AppendGenericParameterConstraints (buf, (GenericParameter) type).Append (type.Name);
+ if (type is GenericParameter) {
+ AppendGenericParameterConstraints (buf, (GenericParameter) type).Append (type.Name);
+ return buf;
+ }
string s = GetBuiltinType (type.FullName);
- if (s != null)
+ if (s != null) {
return buf.Append (s);
- return base.AppendTypeName (buf, type);
+ }
+ return base.AppendTypeName (buf, type, context);
}
private StringBuilder AppendGenericParameterConstraints (StringBuilder buf, GenericParameter type)
return buf.ToString ();
}
- protected override StringBuilder AppendGenericType (StringBuilder buf, TypeReference type)
+ protected override StringBuilder AppendGenericType (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
List<TypeReference> decls = DocUtils.GetDeclaringTypes (
type is GenericInstanceType ? type.GetElementType () : type);
buf.Append (NestedTypeSeparator);
}
first = false;
- AppendTypeName (buf, declDef);
+ AppendTypeName (buf, declDef, context);
}
buf.Append ('<');
first = true;
if (!first)
buf.Append (", ");
first = false;
- _AppendTypeName (buf, arg);
+ _AppendTypeName (buf, arg, context);
}
buf.Append ('>');
return buf;
buf.Append ("virtual ");
if (!method.IsStatic)
buf.Append ("instance ");
- _AppendTypeName (buf, method.ReturnType);
+ _AppendTypeName (buf, method.ReturnType, new DynamicParserContext (method.MethodReturnType));
buf.Append (' ')
.Append (method.Name);
if (method.IsGenericMethod ()) {
IList<GenericParameter> args = method.GenericParameters;
if (args.Count > 0) {
buf.Append ("<");
- _AppendTypeName (buf, args [0]);
+ _AppendTypeName (buf, args [0], null);
for (int i = 1; i < args.Count; ++i)
- _AppendTypeName (buf.Append (", "), args [i]);
+ _AppendTypeName (buf.Append (", "), args [i], null);
buf.Append (">");
}
MemberFormatterState = state;
if (!first)
buf.Append (", ");
first = false;
- _AppendTypeName (buf, method.Parameters [i].ParameterType);
+ _AppendTypeName (buf, method.Parameters [i].ParameterType, new DynamicParserContext (method.Parameters [i]));
buf.Append (' ');
buf.Append (method.Parameters [i].Name);
}
.Append (".property ");
if (!(gm ?? sm).IsStatic)
buf.Append ("instance ");
- _AppendTypeName (buf, property.PropertyType);
+ _AppendTypeName (buf, property.PropertyType, new DynamicParserContext (property));
buf.Append (' ').Append (property.Name);
if (!property.HasParameters || property.Parameters.Count == 0)
return buf.ToString ();
if (!first)
buf.Append (", ");
first = false;
- _AppendTypeName (buf, p.ParameterType);
+ _AppendTypeName (buf, p.ParameterType, new DynamicParserContext (p));
}
buf.Append (')');
buf.Append ("initonly ");
if (field.IsLiteral)
buf.Append ("literal ");
- _AppendTypeName (buf, field.FieldType);
+ _AppendTypeName (buf, field.FieldType, new DynamicParserContext (field));
buf.Append (' ').Append (field.Name);
AppendFieldValue (buf, field);
return null;
}
- protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type)
+ protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
+ if (context != null && context.TransformFlags != null &&
+ (context.TransformFlags.Count == 0 || context.TransformFlags [context.TransformIndex])) {
+ context.TransformIndex++;
+ return buf.Append ("dynamic");
+ }
+
if (type is GenericParameter)
- return AppendGenericParameterConstraints (buf, (GenericParameter) type).Append (type.Name);
+ return AppendGenericParameterConstraints (buf, (GenericParameter) type, context).Append (type.Name);
string t = type.FullName;
if (!t.StartsWith ("System.")) {
- return base.AppendTypeName (buf, type);
+ return base.AppendTypeName (buf, type, context);
}
string s = GetCSharpType (t);
- if (s != null)
+ if (s != null) {
+ if (context != null)
+ context.TransformIndex++;
return buf.Append (s);
+ }
- return base.AppendTypeName (buf, type);
+ return base.AppendTypeName (buf, type, context);
}
- private StringBuilder AppendGenericParameterConstraints (StringBuilder buf, GenericParameter type)
+ private StringBuilder AppendGenericParameterConstraints (StringBuilder buf, GenericParameter type, DynamicParserContext context)
{
if (MemberFormatterState != MemberFormatterState.WithinGenericTypeParameters)
return buf;
if (DocUtils.IsDelegate (type)) {
buf.Append("delegate ");
MethodDefinition invoke = type.GetMethod ("Invoke");
- buf.Append (full.GetName (invoke.ReturnType)).Append (" ");
+ buf.Append (full.GetName (invoke.ReturnType, new DynamicParserContext (invoke.MethodReturnType))).Append (" ");
buf.Append (GetName (type));
AppendParameters (buf, invoke, invoke.Parameters);
AppendGenericTypeConstraints (buf, type);
return null;
}
- protected override string GetTypeName (MethodReturnType returnType)
- {
- return GetTypeName (returnType, () => returnType.ReturnType);
- }
-
- string GetTypeName (ICustomAttributeProvider provider, Func<TypeReference> selector)
- {
- string type = GetName (selector ());
- if (type == "object" && provider.HasCustomAttributes &&
- provider.CustomAttributes.Cast<CustomAttribute>()
- .Any (ca => ca.GetDeclaringType() == "System.Runtime.CompilerServices.DynamicAttribute"))
- return "dynamic";
- return type;
- }
-
protected override StringBuilder AppendMethodName (StringBuilder buf, MethodDefinition method)
{
if (DocUtils.IsExplicitlyImplemented (method)) {
else
buf.Append ("ref ");
}
- buf.Append (GetTypeName (parameter, () => parameter.ParameterType)).Append (" ");
- return buf.Append (parameter.Name);
+ buf.Append (GetTypeName (parameter.ParameterType, new DynamicParserContext (parameter))).Append (" ");
+ buf.Append (parameter.Name);
+ if (parameter.HasDefault && parameter.IsOptional && parameter.HasConstant) {
+ buf.AppendFormat (" = {0}", MDocUpdater.MakeAttributesValueString (parameter.Constant, parameter.ParameterType));
+ }
+ return buf;
}
protected override string GetPropertyDeclaration (PropertyDefinition property)
modifiers = "";
buf.Append (modifiers).Append (' ');
- buf.Append (GetName (property.PropertyType)).Append (' ');
+ buf.Append (GetTypeName (property.PropertyType, new DynamicParserContext (property))).Append (' ');
IEnumerable<MemberReference> defs = property.DeclaringType.GetDefaultMembers ();
string name = property.Name;
if (field.IsLiteral)
buf.Append (" const");
- buf.Append (' ').Append (GetName (field.FieldType)).Append (' ');
+ buf.Append (' ').Append (GetTypeName (field.FieldType, new DynamicParserContext (field))).Append (' ');
buf.Append (field.Name);
AppendFieldValue (buf, field);
buf.Append (';');
AppendModifiers (buf, e.AddMethod);
buf.Append (" event ");
- buf.Append (GetName (e.EventType)).Append (' ');
+ buf.Append (GetTypeName (e.EventType, new DynamicParserContext (e.AddMethod.Parameters [0]))).Append (' ');
buf.Append (e.Name).Append (';');
return buf.ToString ();
private TypeReference genDeclType;
private MethodReference genDeclMethod;
- protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type)
+ protected override StringBuilder AppendTypeName (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
if (type is GenericParameter) {
int l = buf.Length;
}
}
else {
- base.AppendTypeName (buf, type);
+ base.AppendTypeName (buf, type, context);
if (AddTypeCount) {
int numArgs = type.GenericParameters.Count;
if (type.DeclaringType != null)
return buf.Append (ArrayDelimeters [1]);
}
- protected override StringBuilder AppendGenericType (StringBuilder buf, TypeReference type)
+ protected override StringBuilder AppendGenericType (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
if (!AddTypeCount)
- base.AppendGenericType (buf, type);
+ base.AppendGenericType (buf, type, context);
else
- AppendType (buf, type);
+ AppendType (buf, type, context);
return buf;
}
- private StringBuilder AppendType (StringBuilder buf, TypeReference type)
+ private StringBuilder AppendType (StringBuilder buf, TypeReference type, DynamicParserContext context)
{
List<TypeReference> decls = DocUtils.GetDeclaringTypes (type);
bool insertNested = false;
if (insertNested)
buf.Append (NestedTypeSeparator);
insertNested = true;
- base.AppendTypeName (buf, decl);
+ base.AppendTypeName (buf, decl, context);
int argCount = DocUtils.GetGenericArgumentCount (decl);
int numArgs = argCount - prevParamCount;
prevParamCount = argCount;