ManagementException配额违规,呼叫取消,提供商负载故障

时间:2014-12-19 08:33:36

标签: c# wmi

在过去半年中,有三个用户遇到了问题,您可以在下面看到。

(Error, 27.11.2014 15:47:53+01:00) The request for Windows processes was terminated by an error.
System.Management.ManagementException: Quota violation 
   at System.Management.ManagementException.ThrowWithExtendedInfo(ManagementStatus errorCode)
   at System.Management.ManagementObjectCollection.ManagementObjectEnumerator.MoveNext()
   at System.Linq.Enumerable.<CastIterator>d__b1`1.MoveNext()
   at System.Linq.Lookup`2.CreateForJoin(IEnumerable`1 source, Func`2 keySelector, IEqualityComparer`1 comparer)
   at System.Linq.Enumerable.<JoinIterator>d__61`4.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.Any[TSource](IEnumerable`1 source)
   at XY.IsProcessFromDirectoryRunning(String directory)
(Error, 27.11.2014 15:47:53+01:00) The request for Windows processes was terminated by an error.
System.Management.ManagementException: Call cancelled 
   at System.Management.ManagementException.ThrowWithExtendedInfo(ManagementStatus errorCode)
   at System.Management.ManagementObjectCollection.ManagementObjectEnumerator.MoveNext()
   at System.Linq.Enumerable.<CastIterator>d__b1`1.MoveNext()
   at System.Linq.Lookup`2.CreateForJoin(IEnumerable`1 source, Func`2 keySelector, IEqualityComparer`1 comparer)
   at System.Linq.Enumerable.<JoinIterator>d__61`4.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.Any[TSource](IEnumerable`1 source)
   at XY.IsProcessFromDirectoryRunning(String directory)
(Error, 27.11.2014 15:47:53+01:00) The request for Windows processes was terminated by an error.
System.Management.ManagementException: Provider load failure 
   at System.Management.ManagementException.ThrowWithExtendedInfo(ManagementStatus errorCode)
   at System.Management.ManagementObjectCollection.ManagementObjectEnumerator.MoveNext()
   at System.Linq.Enumerable.<CastIterator>d__b1`1.MoveNext()
   at System.Linq.Lookup`2.CreateForJoin(IEnumerable`1 source, Func`2 keySelector, IEqualityComparer`1 comparer)
   at System.Linq.Enumerable.<JoinIterator>d__61`4.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.Any[TSource](IEnumerable`1 source, Func`2 predicate)
   at XY.IsProcessFromDirectoryRunning(String directory)
(Error, 27.11.2014 15:47:53+01:00) The request for Windows processes was terminated by an error.
System.Management.ManagementException: Provider load failure 
   at System.Management.ManagementException.ThrowWithExtendedInfo(ManagementStatus errorCode)
   at System.Management.ManagementObjectCollection.ManagementObjectEnumerator.MoveNext()
   at System.Linq.Enumerable.<CastIterator>d__b1`1.MoveNext()
   at System.Linq.Lookup`2.CreateForJoin(IEnumerable`1 source, Func`2 keySelector, IEqualityComparer`1 comparer)
   at System.Linq.Enumerable.<JoinIterator>d__61`4.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
   at System.Linq.Enumerable.Any[TSource](IEnumerable`1 source)
   at XY.IsProcessFromDirectoryRunning(String directory)

提供程序加载失败异常一直持续到应用程序关闭或由于内存泄漏(由此问题导致)导致CTD。此外,我无法重现此问题,我尝试从测试应用程序调用此方法+/- 1,5M次,但它没有问题。

方法应该没问题,但你可以在下面看到:

public static IEnumerable<Process> GetProcessesFromDirectory(string directory)
{
    if (directory.Last() != Path.DirectorySeparatorChar)
    {
        directory += Path.DirectorySeparatorChar;
    }

    var wmiQueryString = "SELECT ProcessId, ExecutablePath FROM Win32_Process";

    try
    {
        using (var searcher = new ManagementObjectSearcher(wmiQueryString))
        {
            return
                from process in Process.GetProcesses()
                join managementObject in searcher.Get().Cast<ManagementObject>()
                    on process.Id equals (int)(uint)managementObject["ProcessId"]
                let processExecutable = (string)managementObject["ExecutablePath"]
                where processExecutable != null && processExecutable.StartsWith(directory, StringComparison.OrdinalIgnoreCase)
                select process;
        }
    }
    catch (ManagementException ex)
    {
        return Enumerable.Empty<Process>();
    }
}

public bool IsProcessFromDirectoryRunning(string directory)
{
    try
    {
        return this.GetProcessesFromDirectory(directory).Any();
    }
    catch (ManagementException ex)
    {
        this.logger.Log(ex, Strings.ProcessSearchError);
        return false;
    }
}

问题是如果我得到提供商加载失败我可以以某种方式重新启动吗?我试图在谷歌找到答案,但我没有找到任何有用的东西。我将非常感谢任何帮助。

1 个答案:

答案 0 :(得分:1)

我发现使用Process.GetProcesses()并使用MainModule.FilePath比通过WMI检查进程要快得多,因此WMI问题就会消失。

return Process.GetProcesses().Where(p => p.Id > 4 && !p.HasExited && p.MainModule.FileName.StartsWith(directory));