3
3
using System . Collections . Generic ;
4
4
using System . Diagnostics ;
5
5
using System . Diagnostics . Contracts ;
6
- using System . Linq ;
7
6
using System . Management . Automation ;
8
7
using System . Management . Automation . Runspaces ;
9
8
using System . Threading ;
10
9
10
+
11
11
namespace PSParallel
12
12
{
13
13
sealed class PowershellPool : IDisposable
14
14
{
15
+ private readonly object _countLock = new object ( ) ;
15
16
private int _busyCount ;
16
- private int _processedCount ;
17
17
private readonly CancellationToken _cancellationToken ;
18
18
private readonly RunspacePool _runspacePool ;
19
19
private readonly List < PowerShellPoolMember > _poolMembers ;
20
20
private readonly BlockingCollection < PowerShellPoolMember > _availablePoolMembers = new BlockingCollection < PowerShellPoolMember > ( new ConcurrentQueue < PowerShellPoolMember > ( ) ) ;
21
21
public readonly PowerShellPoolStreams Streams = new PowerShellPoolStreams ( ) ;
22
-
23
- public int ProcessedCount => _processedCount ;
22
+ private int _processedCount ;
24
23
25
24
public PowershellPool ( int poolSize , InitialSessionState initialSessionState , CancellationToken cancellationToken )
26
25
{
27
26
_poolMembers = new List < PowerShellPoolMember > ( poolSize ) ;
28
- _processedCount = 0 ;
29
27
_cancellationToken = cancellationToken ;
30
28
31
29
for ( var i = 0 ; i < poolSize ; i ++ )
@@ -39,7 +37,7 @@ public PowershellPool(int poolSize, InitialSessionState initialSessionState, Can
39
37
_runspacePool . SetMaxRunspaces ( poolSize ) ;
40
38
}
41
39
42
- public int GetPartiallyProcessedCount ( )
40
+ private int GetPartiallyProcessedCount ( )
43
41
{
44
42
var totalPercentComplete = 0 ;
45
43
var count = _poolMembers . Count ;
@@ -55,16 +53,24 @@ public int GetPartiallyProcessedCount()
55
53
percentComplete = 100 ;
56
54
}
57
55
totalPercentComplete += percentComplete ;
58
- }
59
- return totalPercentComplete / 100 ;
56
+ }
57
+ var partiallyProcessedCount = totalPercentComplete / 100 ;
58
+ return partiallyProcessedCount ;
59
+ }
60
+
61
+ public int GetEstimatedProgressCount ( )
62
+ {
63
+ lock ( _countLock ) {
64
+ return _processedCount + GetPartiallyProcessedCount ( ) ;
65
+ }
60
66
}
61
67
62
68
public bool TryAddInput ( ScriptBlock scriptblock , PSObject inputObject )
63
69
{
64
70
PowerShellPoolMember poolMember ;
65
71
if ( ! TryWaitForAvailablePowershell ( 100 , out poolMember ) )
66
72
{
67
- return false ;
73
+ return false ;
68
74
}
69
75
70
76
Interlocked . Increment ( ref _busyCount ) ;
@@ -110,7 +116,6 @@ private bool TryWaitForAvailablePowershell(int milliseconds, out PowerShellPoolM
110
116
}
111
117
112
118
poolMember . PowerShell . RunspacePool = _runspacePool ;
113
- Debug . WriteLine ( $ "WaitForAvailablePowershell - Busy: { _busyCount } _processed { _processedCount } , member = { poolMember . Index } ") ;
114
119
return true ;
115
120
}
116
121
@@ -125,13 +130,18 @@ public void Dispose()
125
130
public void ReportAvailable ( PowerShellPoolMember poolmember )
126
131
{
127
132
Interlocked . Decrement ( ref _busyCount ) ;
128
- Interlocked . Increment ( ref _processedCount ) ;
133
+ lock ( _countLock )
134
+ {
135
+ _processedCount ++ ;
136
+ poolmember . PercentComplete = 0 ;
137
+ }
138
+
139
+ poolmember . PercentComplete = 0 ;
129
140
while ( ! _availablePoolMembers . TryAdd ( poolmember , 1000 , _cancellationToken ) )
130
141
{
131
142
_cancellationToken . ThrowIfCancellationRequested ( ) ;
132
143
Debug . WriteLine ( "WaitForAvailablePowershell - TryAdd failed" ) ;
133
144
}
134
- Debug . WriteLine ( $ "ReportAvailable - Busy: { _busyCount } _processed { _processedCount } , member = { poolmember . Index } ") ;
135
145
}
136
146
137
147
public void ReportStopped ( PowerShellPoolMember powerShellPoolMember )
0 commit comments