示例#1
0
        public static void Dump()
        {
            TypeData.Start();
            List <KeyValuePair <Type, Exception> > parseErrors = new List <KeyValuePair <Type, Exception> >();

            string time       = DateTime.Now.ToString().Replace('/', '_').Replace(':', '_');
            string outPutFile = "E://LT_SnapShot/MonoHeap/" + time + ".txt";

            using (var sw = new StreamWriter(outPutFile, false))
            {
                sw.WriteLine("====================Mono Info=====================");
                long monoReserved = UnityEngine.Profiling.Profiler.GetMonoHeapSizeLong();
                long monoUsed     = UnityEngine.Profiling.Profiler.GetMonoUsedSizeLong();
                sw.WriteLine($"monoReserved: {monoReserved / (1024*1024)}MB");
                sw.WriteLine($"monoUsed: {monoUsed / (1024*1024)}MB");

                sw.WriteLine("====================Heap Details=====================");
                foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
                {
                    foreach (var type in assembly.GetTypes())
                    {
                        try
                        {
                            new StructOrClass(type, sw);
                        }
                        catch (Exception e)
                        {
                            parseErrors.Add(new KeyValuePair <Type, Exception>(type, e));
                        }
                    }
                }
            }

            TypeData.Clear();
        }
示例#2
0
    public static void Create()
    {
        TypeData.Start();
        ThreadJobsPrinting = 0;
        ThreadJobsDone     = 0;

        if (Directory.Exists("dump"))
        {
            Directory.Delete("dump", true);
        }
        Directory.CreateDirectory("dump");
        Directory.CreateDirectory("dump/sobjects");
        Directory.CreateDirectory("dump/uobjects");
        Directory.CreateDirectory("dump/statics");

        using (var logger = new StreamWriter("dump/memory.csv"))
        {
            Dictionary <Assembly, List <StructOrClass> > assemblyResults = new Dictionary <Assembly, List <StructOrClass> >();
            Dictionary <Assembly, int>             assemblySizes         = new Dictionary <Assembly, int>();
            List <KeyValuePair <Type, Exception> > parseErrors           = new List <KeyValuePair <Type, Exception> >();
            foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
            {
                string assemblyFolder;
                if (assembly.FullName.Contains("Assembly-CSharp"))
                {
                    assemblyFolder = string.Format("dump/statics/{0}/", assembly.FullName.Replace("<", "(").Replace(">", ")").Replace(".", "_"));
                }
                else
                {
                    assemblyFolder = "dump/statics/misc/";
                }
                Directory.CreateDirectory(assemblyFolder);
                List <StructOrClass> types = new List <StructOrClass>();
                foreach (var type in assembly.GetTypes())
                {
                    if (type.IsEnum || type.IsGenericType)
                    {
                        continue;
                    }
                    try
                    {
                        types.Add(new StructOrClass(type, assemblyFolder));
                    }
                    catch (Exception e)
                    {
                        parseErrors.Add(new KeyValuePair <Type, Exception>(type, e));
                    }
                }
                assemblyResults[assembly] = types;
            }

            List <StructOrClass> unityComponents = new List <StructOrClass>();

            foreach (var go in Resources.FindObjectsOfTypeAll <GameObject>())
            {
                foreach (var component in go.GetComponents <Component>())
                {
                    if (component == null)
                    {
                        continue;
                    }
                    try
                    {
                        unityComponents.Add(new StructOrClass(component));
                    }
                    catch (Exception e)
                    {
                        parseErrors.Add(new KeyValuePair <Type, Exception>(component.GetType(), e));
                    }
                }
            }

            List <StructOrClass> unityScriptableObjects = new List <StructOrClass>();

            foreach (ScriptableObject scriptableObject in Resources.FindObjectsOfTypeAll <ScriptableObject>())
            {
                if (scriptableObject == null)
                {
                    continue;
                }
                try
                {
                    unityScriptableObjects.Add(new StructOrClass(scriptableObject));
                }
                catch (Exception e)
                {
                    parseErrors.Add(new KeyValuePair <Type, Exception>(scriptableObject.GetType(), e));
                }
            }

            foreach (var genericType in genericTypes.ToList())
            {
                try
                {
                    assemblyResults[genericType.Assembly].Add(new StructOrClass(genericType, "dump/statics/misc/"));
                }
                catch (Exception e)
                {
                    parseErrors.Add(new KeyValuePair <Type, Exception>(genericType, e));
                }
            }

            foreach (var pair in assemblyResults)
            {
                assemblySizes[pair.Key] = pair.Value.Sum(a => a.Size);
                pair.Value.Sort((a, b) => b.Size - a.Size);
            }

            TypeData.Clear();

            var assemblySizesList = assemblySizes.ToList();
            assemblySizesList.Sort((a, b) => (b.Value - a.Value));

            unityComponents.Sort((a, b) => (b.Size - a.Size));
            int  unityComponentsSize    = unityComponents.Sum(a => a.Size);
            bool printedUnityComponents = false;

            unityScriptableObjects.Sort((a, b) => (b.Size - a.Size));
            int  unityScriptableObjectsSize    = unityScriptableObjects.Sum(a => a.Size);
            bool printedUnityScriptableObjects = false;

            //logger.WriteLine("Total tracked memory (including duplicates, so too high) = {0}", assemblySizesList.Sum(a => a.Value) + unityComponentsSize + unityScriptableObjectsSize);


            foreach (var pair in assemblySizesList)
            {
                var assembly = pair.Key;
                var size     = pair.Value;

                if (!printedUnityComponents && size < unityComponentsSize)
                {
                    printedUnityComponents = true;
                    //logger.WriteLine("Unity components of total size: {0}", unityComponentsSize);
                    foreach (var instance in unityComponents)
                    {
                        if (instance.Size >= TYPE_MIN_SIZE_TO_PRINT)
                        {
                            logger.WriteLine("\"{0}\",\"{1}\",{2},{3}", "Unity Components", instance.ParsedType.FullName, instance.InstanceID, instance.Size);
                        }
                    }
                }

                if (!printedUnityScriptableObjects && size < unityScriptableObjectsSize)
                {
                    printedUnityScriptableObjects = true;
                    //logger.WriteLine("Unity scriptableobjects of total size: {0}", unityScriptableObjectsSize);
                    foreach (var instance in unityScriptableObjects)
                    {
                        if (instance.Size >= TYPE_MIN_SIZE_TO_PRINT)
                        {
                            logger.WriteLine("\"{0}\",\"{1}\",{2},{3}", "Unity ScriptableObjects", instance.ParsedType.FullName, instance.InstanceID, instance.Size);
                        }
                    }
                }

                //logger.WriteLine("Assembly: {0} of total size: {1}", assembly, size);
                foreach (var type in assemblyResults[assembly])
                {
                    if (type.Size >= TYPE_MIN_SIZE_TO_PRINT)
                    {
                        logger.WriteLine("\"{0}\",\"{1}\",,{2}", assembly, type.ParsedType.FullName, type.Size);
                    }
                }
            }
            foreach (var error in parseErrors)
            {
                //logger.WriteLine(error);
            }
        }

        while (ThreadJobsDone < ThreadJobsPrinting)
        {
            System.Threading.Thread.Sleep(1);
        }
    }