Hi,

What's the purpose of IronPython.Rumtime.WeakRefTracker?

I did run the attached program (which is similar to the example for 
http://ironpython.codeplex.com/workitem/31764).

After running a bunch of scripts, the program calls GC.Collect() and 
GC.WaitForPendingFinalizers() several times.

At that moment, the code does not hold any reference to any IronPython or 
Scripting related objects, so I'd expect everything to be cleaned up by the GC.

Despite that fact, I found out that the program spends several seconds with 
100% CPU load after returning from the Main() method. When Breaking it in the 
Debugger several times, it did always end up in the Finalizer method of the 
WeakRefTracker, so my guess is that most of those several seconds are spent 
there.

Best regards

Markus Schaber
--
___________________________
We software Automation.

3S-Smart Software Solutions GmbH
Markus Schaber | Developer
Memminger Str. 151 | 87439 Kempten | Germany | Tel. +49-831-54031-0 | Fax 
+49-831-54031-50

Email: m.scha...@3s-software.com<mailto:m.scha...@3s-software.com> | Web: 
http://www.3s-software.com <http://www.3s-software.com/>
CoDeSys internet forum: 
http://forum.3s-software.com<http://forum-en.3s-software.com/>
Download CoDeSys sample projects: 
http://www.3s-software.com/index.shtml?sample_projects

Managing Directors: Dipl.Inf. Dieter Hess, Dipl.Inf. Manfred Werner | Trade 
register: Kempten HRB 6186 | Tax ID No.: DE 167014915




namespace IronPythonLeakTest
{
        using System;
        using System.Collections.Generic;
        using System.Runtime.InteropServices;
        using System.Threading;
        using System.Windows.Forms;
        using IronPython.Hosting;
        using IronPython.Runtime;
        using IronPython.Runtime.Exceptions;
        using IronPython.Runtime.Types;
        using Microsoft.Scripting;
        using Microsoft.Scripting.Hosting;
        using System.Diagnostics;
        using System.IO;

        public static class ScriptExecutor
        {
                private static readonly TextWriter Window = Console.Out;

                private const string LIB_PATH = @"C:\Program Files 
(x86)\IronPython 2.7.1\Lib";
                
                private static void Main()
                {
                        try
                        {
                                ExecuteRuns(50);
                        }
                        finally
                        {
                                Console.ReadLine();
                        }
                }

                internal static void ExecuteRuns(int runs)
                {

                        long afterFirst = 0;
                        long beforeStart = 0;
                        try
                        {
                                beforeStart = GC.GetTotalMemory(true);

                                Execute(0);

                                afterFirst = GC.GetTotalMemory(true);

                                for (int i = 1; i < runs; i += 1)
                                {
                                        Execute(i);
                                }
                        }
                        finally
                        {
                                long afterLast = GC.GetTotalMemory(false);
                                Window.WriteLine("Script Finished");
                                Window.Write("First run: {0}Mb, {1} runs: 
{2}Mb, avg = {3}",
                                        Math.Round((afterFirst - beforeStart) / 
(1024.0 * 1024), 1),
                                        runs,
                                        Math.Round((afterLast - beforeStart) / 
(1024.0 * 1024), 1),
                                        Math.Round((afterLast - beforeStart) / 
(1024.0 * 1024 * runs), 1))
                                ;
                                for (int i = 0; i < 5; i += 1)
                                {
                                        Application.DoEvents();
                                        GC.Collect();
                                        Thread.Sleep(100);
                                        GC.WaitForPendingFinalizers();
                                }

                                long afterGC = GC.GetTotalMemory(true);
                                Window.WriteLine("After GC: {0}Mb, avg = {1}",
                                        Math.Round((afterGC - beforeStart) / 
(1024.0 * 1024), 1),
                                        Math.Round((afterGC - beforeStart) / 
(1024.0 * 1024 * runs), 1))
                                ;
                        }
                }

                private static void Execute(int i)
                {
                        DateTime start = DateTime.Now;

                        string src = String.Format("from __future__ import 
print_function \n"
                                + "import os, warnings \n"
                                + "write('hallo: %s\t ' % {0}) \n", i);

                        ScriptEngine engine = Python.CreateEngine();

                        ScriptRuntime runtime = engine.Runtime;
                        ScriptScope mainScope = engine.CreateScope();

                        
runtime.LoadAssembly(typeof(IronPython.Modules.PythonNT).Assembly);

                        ScriptSource scriptSource = 
engine.CreateScriptSourceFromString(src, "TestScript", 
SourceCodeKind.AutoDetect);

                        var compiledCode = 
scriptSource.Compile(ErrorListenerImpl.INSTANCE);

                        // Set the search pathes.
                        engine.SetSearchPaths(new[] { LIB_PATH });

                        engine.SetTrace(TRACE_FUNC);

                        //var warningModule = engine.ImportModule("warnings");

                        mainScope.SetVariable("write", new 
Action<object>(Window.Write));

                        compiledCode.Execute(mainScope);

                        Window.WriteLine("{0}s - \t {1} \t- {2}", 
                                Math.Round((DateTime.Now - start).TotalSeconds, 
1), 
                                GC.GetTotalMemory(false),
                                GC.CollectionCount(0));
                }

                private static readonly TracebackDelegate TRACE_FUNC = 
TraceFunc;

                private static TracebackDelegate TraceFunc(TraceBackFrame 
frame, string result, object payload)
                {
                        return TRACE_FUNC;
                }
        }

        public delegate void ShowWarning(
                CodeContext context, object message, PythonType category, 
string filename, int lineno,
                [DefaultParameterValue(null)] object file, 
[DefaultParameterValue(null)] string line);

        class ErrorListenerImpl : ErrorListener
        {
                public static readonly ErrorListenerImpl INSTANCE = new 
ErrorListenerImpl();

                public override void ErrorReported(ScriptSource source, string 
stMessage, Microsoft.Scripting.SourceSpan span, int errorCode, 
Microsoft.Scripting.Severity severity)
                {
                        Console.WriteLine(stMessage);
                }
        }
}


_______________________________________________
Ironpython-users mailing list
Ironpython-users@python.org
http://mail.python.org/mailman/listinfo/ironpython-users

Reply via email to