in src/PowerShell/PowerShellManagerPool.cs [56:103]
internal PowerShellManager CheckoutIdleWorker(
string requestId,
string invocationId,
string functionName,
ReadOnlyDictionary<string, ReadOnlyBindingInfo> outputBindings)
{
PowerShellManager psManager = null;
// If the pool has an idle one, just use it.
if (!_pool.TryTake(out psManager))
{
// The pool doesn't have an idle one.
if (_poolSize < UpperBound)
{
int id = Interlocked.Increment(ref _poolSize);
if (id <= UpperBound)
{
// If the pool hasn't reached its bounded capacity yet, then
// we create a new item and return it.
var logger = CreateLoggerWithContext(requestId, invocationId);
psManager = new PowerShellManager(logger, id);
RpcLogger.WriteSystemLog(LogLevel.Trace, string.Format(PowerShellWorkerStrings.LogNewPowerShellManagerCreated, id.ToString()));
}
}
if (psManager == null)
{
var logger = CreateLoggerWithContext(requestId, invocationId);
logger.Log(isUserOnlyLog: false, LogLevel.Warning, string.Format(PowerShellWorkerStrings.FunctionQueuingRequest, functionName));
// If the pool has reached its bounded capacity, then the thread
// should be blocked until an idle one becomes available.
psManager = _pool.Take();
}
}
psManager.Logger.SetContext(requestId, invocationId);
// Finish the initialization if not yet.
// This applies only to the very first PowerShellManager instance, whose initialization was deferred.
psManager.Initialize();
// Register the function with the Runspace before returning the idle PowerShellManager.
FunctionMetadata.RegisterFunctionMetadata(psManager.InstanceId, outputBindings);
return psManager;
}