使用Python的线程COM对象中的内存泄漏 [英] Memory Leak in Threaded COM Object with Python

查看:1037
本文介绍了使用Python的线程COM对象中的内存泄漏的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在一个线程中创建一个COM客户端,并使用此客户端执行几个操作。每个线程都是从使用Python的 socketserver 模块的服务器生成的,该模块具有内置的线程支持。

I am creating a COM client within a thread and performing several operations with this client. Each thread is spawned from a server that uses Python's socketserver module which has built-in threading support.

加载和使用这个COM对象有一个预期的内存使用率峰值由python.exe。有10个并发线程,内存使用量达到峰值500Mb。然而,当操作完成并且COM对象显然被释放时,该进程使用的额外内存比以前多50Mb。如果我然后产生10额外的线程使用相同的服务器,在这些COM对象被关闭后,python.exe有额外使用的13Mb。最终,每完成10个额外的并发线程,大约6Mb。当我结束整个python.exe进程,所有的内存被释放。

When I am loading and using this COM object there is an expected spike in memory usage by python.exe. With 10 concurrent threads there is a peak in memory usage of about 500Mb. However when the operations are finished and the COM object is apparently released, there are 50Mb of additional memory used by the process than before. If I then spawn 10 additional threads using the same server there are 13Mb additional used by python.exe after those COM objects are closed. Eventually every 10 additional concurrent threads adds approximately 6Mb after they are done. When I end the entire python.exe process, all the memory is released.

我简化了下面的代码来模拟socketserver如何使用 threadding ,问题是完全相同的。

I have simplified the following code to mimic how the socketserver uses threadding and the problem is the exact same.

import win32com.client
import threading
import pythoncom

def CreateTom():
    pythoncom.CoInitialize()
    tom = win32com.client.Dispatch("TOM.Document")
    tom.Dataset.Load("FileName")
    tom.Clear()
    pythoncom.CoUninitialize()

for i in range(50):
    t = threading.Thread(target = CreateTom)
    t.daemon = False
    t.start()

我知道我不太可能在这里的特定COM库(它是一个IBM产品用于市场研究称为TablesObjectModel)。但是我想知道是否有什么,任何,额外的,我可以做释放这个记忆。我已经阅读关于COM公寓,但它听起来像pythoncom.CoInitialize应该照顾这对我。任何帮助将不胜感激。

I understand that I will unlikely get any support here around the specific COM library (it is an IBM product used in Market Research known as the TablesObjectModel). However I want to know if there is anything, ANYTHING, additional that I can do to release this memory. I have read about Apartments in COM but it sounds like pythoncom.CoInitialize should take care of this for me. Any help would be appreciated.

推荐答案

事实上,这种内存增加实际上是由于写入COM对象。 NET和与线程无关。 此处是任务管理器的详细说明,给出了有关.NET应用程序的内存使用情况的误导性信息。为了解决这个问题,我添加了以下到我的代码,我都设置。希望别人在他们开始撕掉他们的头发,试图在他们的代码中找到内存泄漏之前读取这个响应。

As it turns out this increase in Memory was in fact due to the COM object written in .NET and had nothing to do with threading. Here is a detailed description of Task Manager giving misleading information about memory usage for .NET apps. To resolve this issue I added the following to my code and I am all set. Hopefully someone else reads this response before they start tearing their hair out trying to find a memory leak in their code.

from win32process import SetProcessWorkingSetSize
from win32api import GetCurrentProcessId, OpenProcess
from win32con import PROCESS_ALL_ACCESS

import win32com.client
import threading
import pythoncom

def CreateTom():
    pythoncom.CoInitialize()
    tom = win32com.client.Dispatch("TOM.Document")
    tom.Dataset.Load("FileName")
    tom.Clear()
    pythoncom.CoUninitialize()
    SetProcessWorkingSetSize(handle,-1,-1) #Releases memory after every use

pid = GetCurrentProcessId()
handle = OpenProcess(PROCESS_ALL_ACCESS, True, pid)

for i in range(50):
    t = threading.Thread(target = CreateTom)
    t.daemon = False
    t.start()

这篇关于使用Python的线程COM对象中的内存泄漏的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆