【问题标题】:Runtime error R6034 in embedded Python application嵌入式 Python 应用程序中的运行时错误 R6034
【发布时间】:2013-01-11 05:16:23
【问题描述】:

我正在开发一个使用 Boost.Python 嵌入 Python 解释器的应用程序。这用于运行与主程序交互的用户生成的“脚本”。

不幸的是,一位用户在尝试运行脚本时报告了运行时错误 R6034。主程序启动正常,但我认为可能是加载python27.dll时出现问题。

我正在使用 Visual Studio 2005、Python 2.7 和 Boost.Python 1.46.1。该问题仅发生在一个用户的机器上。我以前处理过明显的问题,并设法解决了它们,但在这种情况下,我有点不知所措。

有没有其他人遇到过类似的问题?你能解决吗?怎么样?

【问题讨论】:

    标签: visual-c++ python-2.7 visual-studio-2005 manifest boost-python


    【解决方案1】:

    我找到了问题的解决方案。希望这会对其他人有所帮助 - 这些问题可能 令人沮丧,无法调试。

    问题是由第三方软件将自身添加到路径并在其程序文件夹中安装 msvcr90.dll 引起的。在这种情况下,问题是由英特尔的 iCLS 客户端引起的。

    那么……在类似情况下如何发现问题?

    1. 下载进程资源管理器here

    2. 启动您的应用程序并重现运行时错误 R6034。

    3. 启动进程浏览器。在“查看”菜单中,转到“下窗格视图”并选择“DLL”。

    4. 在顶部窗格中,找到您的应用程序并单击它。底部窗格应显示为您的应用程序加载的 DLLS 列表。

    5. 在列表中找到“msvcr??.dll”。应该有几个。查找不在“winsxs”文件夹中的那个,并记下它。

    6. 现在,在应用程序运行之前检查路径。如果它包含您在第 5 步中记下的文件夹,那么您可能已经找到了罪魁祸首。

    如何解决问题?在运行程序之前,您必须从路径中删除有问题的条目。就我而言,我不需要路径中的任何其他内容,因此我编写了一个简单的批处理文件,如下所示:

    path=
    myprogram.exe
    

    就是这样。批处理文件只是在我的程序运行之前清除路径,以便找不到冲突的运行时 DLL。

    希望这会有所帮助!

    【讨论】:

    • 您是冠军!对我来说,我试图将 YouCompleteMe 用于 gVim,而 cmake 是将其 bin 目录添加到包含 msvcr90.dll 的路径的罪犯。感谢您的出色指导
    • 真的很有帮助!在运行 Omnet++ 模拟时,我在 Windows 上使用“gdb.exe”和“mingw”时遇到问题,其中程序抛出错误 R6034。当我从 Windows 的 PATH 中排除 CMAKE 包含时,它现在就像一个魅力。谢谢!
    • 如何在Visual Studio中临时清理路径?
    • @martinako 我会小心那个。 winsxs 文件夹可以包含许多不同版本的 DLL,系统知道如何找到与您的应用程序兼容的版本。如果 DLL 在SysWOW64 文件夹中,那么我认为不会管理该版本——这可能是与您的应用程序不兼容的旧版本的 DLL。
    • 对我来说,msvcr 由两个不同的 python 解释器启动了两次导致了这个问题。使用进程监视器让我找到它并从 appdata 中删除第二个实例
    【解决方案2】:

    这篇文章详细介绍了@Micheal Cooper 和@frmdstryr,并提供了比我之前的答案更好的选择。 您可以将以下内容放在 python 脚本 前面以清除有问题的条目。

    import os, re
    path = os.environ['PATH'].split(';')
    
    def is_problem(folder):
        try:
            for item in os.listdir(folder):
                if re.match(r'msvcr\d\d\.dll', item):
                    return True
        except:
            pass
        return False
    
    path = [folder for folder in path if not is_problem(folder)]
    os.environ['PATH'] = ';'.join(path)
    

    对于 vim with YouCompleteMe 的情况,您可以将以下内容放在您的vimrc 的顶部

    python << EOF
    import os, re
    path = os.environ['PATH'].split(';')
    
    def is_problem(folder):
        try:
            for item in os.listdir(folder):
                if re.match(r'msvcr\d\d\.dll', item):
                    return True
        except:
            pass
        return False
    
    path = [folder for folder in path if not is_problem(folder)]
    os.environ['PATH'] = ';'.join(path)
    EOF
    

    【讨论】:

      【解决方案3】:

      更通用的解决方案是:

      import os
      os.environ['path'] = ";".join(
          [path for path in os.environ['path'].split(";") 
           if "msvcr90.dll" not in map((lambda x:x.lower()), os.listdir(path))])
      

      (我对 VanDyke SecureCRT 也有同样的问题)

      【讨论】:

        【解决方案4】:

        (作为评论可能比完整的答案更好,但我的尘土飞扬的 SO acct. 还没有足够的代表。)

        与 OP 一样,我也使用嵌入式 Python 2.7 和其他一些本机程序集。

        使这个问题复杂化的是,我的应用程序是一个运行在 64 位 IIS Express (VS2013) 之上的中型 .Net 解决方案。

        我尝试了 Dependency Walker(很棒的程序,但已经过时无法帮助解决此问题)和 Process Monitor(ProcMon——它可能确实找到了一些提示,但即使我使用过滤器,问题也被隐藏在数千个不相关的操作,更好的过滤器可能会有所帮助)。

        但是,非常感谢 Michael Cooper! 您的步骤和 Process Explorer (procexp) 让我很快找到了一个整天都在躲避的解决方案。

        我可以在 Michael 的出色帖子中添加一些注释。

        • 我不仅忽略了(即保持不变)\WinSxS\... 文件夹,还忽略了 \System32\... 文件夹。

        最终我发现 msvcr90.dll 是从以下位置拉进来的:

        • C:\Program Files (x86)\Intel\OpenCL SDK\2.0\bin\x64

        通过我的路径,我找到了上述和另一个类似的目录,它似乎包含 32 位版本。我删除了这两个,重新启动并... STILL 有问题。

        所以,我再次按照 Michael 的步骤进行操作,发现 另一个 msvcr90.dll 现在正在从以下位置加载:

        • C:\Program Files\Intel\iCLS 客户端\

        再次浏览我的路径,我找到了上述目录以及该目录的 (x86) 版本。所以,我删除了这两个,应用了更改,重新启动了 VS2013 并......

        不再出现 R6034 错误!

        我不禁对英特尔这样做感到沮丧。实际上,我在网上的其他地方找到了关于从路径中删除 iCLS 客户端的提示。我试过了,但症状是一样的,所以,我认为这不是问题。可悲的是,iCLS 客户端和 OpenCL SDK 正在标记我的 iisexpress。如果我有幸删除了其中任何一个,R6034 错误仍然存​​在。为了解决这个问题,我不得不切除他们两个。

        再次感谢 Michael Cooper 和其他所有人的帮助!

        【讨论】:

        • 非常感谢。这节省了我 2 天的时间。我浪费了一整天的时间来解决这个错误。终于现在我能够解决了。感谢您和@Michael Cooper
        • 另外,我在两个地方遇到了和你一样的问题,不得不找到它们并重新启动它们两次。终于摆脱了这个令人沮丧的问题。非常感谢@thomasiota
        【解决方案5】:

        使用上面迈克尔的回答,我可以通过添加以下内容来解决这个问题,而无需 bat 文件:

        import os
        
        # Remove CLS Client from system path
        if os.environ['PATH'].find("iCLS Client")>=0:
            os.environ['PATH'] = "".join([it for it in os.environ['PATH'].split(";") if not it.find("iCLS Client")>0])
        

        到应用程序的主要 python 文件。它只是确保系统路径不包括在导入加载 dll 的库之前导致问题的路径。

        谢谢!

        【讨论】:

        • 我是 python 新手,对语法不是很熟悉。如果您不介意,请向我解释一下连接括号内的内容。我是从“for”还是从“if not”开始阅读代码?
        【解决方案6】:

        这篇文章详细介绍了@Micheal Cooper 和@frmdstryr。 一旦您确定了有问题的 PATH 条目,您可以将以下内容放在前面 python 脚本,这里假设iCLS ClientCMake 有问题。

        import os
        for forbidden_substring in ['iCLS Client', 'CMake']:
            os.environ['PATH'] = ';'.join([item for item in os.environ['PATH'].split(';')
                                           if not item.lower().find(forbidden_substring.lower()) >= 0])
        

        关于 vim with YouCompleteMe 的情况,您可以将以下内容放在vimrc 的顶部

        python << EOF
        import os
        for forbidden_substring in ['iCLS Client', 'CMake']:
            os.environ['PATH'] = ';'.join([item for item in os.environ['PATH'].split(';')
                                           if not item.lower().find(forbidden_substring.lower()) >= 0])
        EOF
        

        如果这些解决方案都不适合您,您可以尝试消除导致的问题 来自您的 PATH 手动条目,但您要确保不会破坏您的其他任何内容 依赖于这些 PATH 条目的系统。因此,例如,对于 CMake,您可以尝试删除 它的 PATH 条目,并且只将指向 cmake.exe 二进制文件的符号链接(或类似的)放入一些 PATH 中的其他目录,以确保 cmake 仍然可以从任何地方运行。

        【讨论】:

        • 请参阅我的其他答案,了解什么是更好的解决方案恕我直言。我会留下这个答案作为替代。
        【解决方案7】:

        感谢您的解决方案。我只是稍微修改了这个示例代码,因为我系统中的路径变量包含字符串“ICLS CLIENT”而不是“iCLS Client”

        import os
        # print os.environ['PATH']
        # Remove CLS Client from system path
        if os.environ['PATH'].find("iCLS Client") >= 0 or os.environ['PATH'].find("ICLS CLIENT") >= 0:
            os.environ['PATH'] = "".join([it for it in os.environ['PATH'].split(";") if not (it.find("iCLS Client")>0 or it.find("ICLS CLIENT")>0)])
        

        【讨论】:

          【解决方案8】:

          在我的情况下,重建链接库和具有类似“运行时执行库”项目设置的主项目有所帮助。希望这对任何人都有用。

          【讨论】:

            【解决方案9】:

            就我而言,当我将应用程序编译为 exe 文件后,我将重命名该文件时,我意识到问题来了。所以保留exe文件的原始名称不会显示错误。

            【讨论】:

              【解决方案10】:

              此页面上的讨论涉及到比我先进得多的事情。 (我不编码。)不过,我运行 Process Explorer 作为推荐的诊断。我发现另一个程序在其程序文件夹中使用并需要 msvcr90.dll。不理解这里讨论的其他任何内容,作为一个疯狂的猜测,我暂时将 dll 移动到了相邻的程序文件夹。

              问题解决了。运行时错误消息结束。

              (当我完成生成错误消息的程序后,我将 dll 移回。)

              感谢大家的帮助和想法。

              【讨论】:

                【解决方案11】:

                我在使用 Universal-CRT 从 C 程序嵌入 Python27.dll 时也遇到了同样的问题。

                &lt;PYTHON_ROOT&gt;\msvcr90.dll 是罪犯。而&lt;PYTHON_ROOT&gt; 在我的PATH 中偏离了方向。 AFAICS msvcr90.dll 的唯一用户是 PyWin32 模块 &lt;PYTHON_ROOT&gt;\lib\site-packages\win32\win32*.pyd

                解决方法是将&lt;PYTHON_ROOT&gt;\msvcr90.dll 移动到该目录。

                PS。 7 年后,PyWin32 仍然有这个 issue

                【讨论】:

                  【解决方案12】:

                  通过 Process Explorer 检查任何具有用户指定路径的库。没必要一定是msvcr??.dll 除了运行 Python 3 之外,我解决了同样的问题。目前的解决方案没有帮助,因为它们没有指示 msvcr90.dll 的异常路径。我一步一步调试代码,直到行后出现错误对话框(当我的代码导入PyTables模块时调用):

                  import ctypes
                  ctypes.cdll.LoadLibrary('libbz2.dll')
                  

                  然后 Process Explorer 帮助找到导致问题的旧 libbz2.dll 的路径(@Micheal Cooper 算法的步骤 3、4)

                  【讨论】:

                    【解决方案13】:

                    为仍在寻找解决方案的人添加此答案。 ESRI 针对这个错误发布了一个补丁。只需从他们的网站下载补丁(无需登录),安装它即可解决问题。我下载了 10.4.1 的补丁,但可能还有其他版本的补丁。

                    【讨论】:

                    • 这个答案可能对引用信息的链接更有用。
                    猜你喜欢
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    相关资源
                    最近更新 更多