public static void Refresh(Module module)
{
if (module == null)
{
Debug.Fail("COMPAT: Returning, but you should not pass null here");
return;
}
// Build up a list of type description providers for
// each type that is a derived type of the given
// object. We will invalidate the metadata at
// each of these levels.
Hashtable refreshedTypes = null;
lock (s_providerTable)
{
// Manual use of IDictionaryEnumerator instead of foreach to avoid DictionaryEntry box allocations.
IDictionaryEnumerator e = s_providerTable.GetEnumerator();
while (e.MoveNext())
{
DictionaryEntry de = e.Entry;
Type nodeType = de.Key as Type;
if (nodeType != null && nodeType.GetTypeInfo().Module.Equals(module) || nodeType == typeof(object))
{
TypeDescriptionNode node = (TypeDescriptionNode)de.Value;
while (node != null && !(node.Provider is ReflectTypeDescriptionProvider))
{
if (refreshedTypes == null)
{
refreshedTypes = new Hashtable();
}
refreshedTypes[nodeType] = nodeType;
node = node.Next;
}
if (node != null)
{
ReflectTypeDescriptionProvider provider = (ReflectTypeDescriptionProvider)node.Provider;
Type[] populatedTypes = provider.GetPopulatedTypes(module);
foreach (Type populatedType in populatedTypes)
{
provider.Refresh(populatedType);
if (refreshedTypes == null)
{
refreshedTypes = new Hashtable();
}
refreshedTypes[populatedType] = populatedType;
}
}
}
}
}
// And raise the event if types were refresh and handlers are attached.
//
if (refreshedTypes != null && Refreshed != null)
{
foreach (Type t in refreshedTypes.Keys)
{
RaiseRefresh(t);
}
}
}