Ejemplo n.º 1
0
        /// <summary>
        /// Handler to be used in cases, where setting the state is the
        /// only task being performed. This method also asserts
        /// if the specified event is valid for the current state of
        /// the state machine.
        /// </summary>
        /// <param name="sender">Sender of this event.</param>
        /// <param name="eventArgs">Event args.</param>
        private void SetStateHandler(object sender, RemoteSessionStateMachineEventArgs eventArgs)
        {
            switch (eventArgs.StateEvent)
            {
            case RemoteSessionEvent.NegotiationCompleted:
            {
                Dbg.Assert(_state == RemoteSessionState.NegotiationReceived,
                           "State can be set to Established only when current state is NegotiationReceived");
                SetState(RemoteSessionState.Established, null);
            }

            break;

            case RemoteSessionEvent.NegotiationReceived:
            {
                Dbg.Assert(eventArgs.RemoteSessionCapability != null,
                           "State can be set to NegotiationReceived only when RemoteSessionCapability is not null");
                if (eventArgs.RemoteSessionCapability is null)
                {
                    throw PSTraceSource.NewArgumentException(nameof(eventArgs));
                }

                SetState(RemoteSessionState.NegotiationReceived, null);
            }

            break;

            case RemoteSessionEvent.NegotiationSendCompleted:
            {
                Dbg.Assert((_state == RemoteSessionState.NegotiationSending) || (_state == RemoteSessionState.NegotiationSendingOnConnect),
                           "Negotiating send can be completed only when current state is NegotiationSending");

                SetState(RemoteSessionState.NegotiationSent, null);
            }

            break;

            case RemoteSessionEvent.ConnectFailed:
            {
                Dbg.Assert(_state == RemoteSessionState.Connecting,
                           "A ConnectFailed event can be raised only when the current state is Connecting");

                SetState(RemoteSessionState.ClosingConnection, eventArgs.Reason);
            }

            break;

            case RemoteSessionEvent.CloseFailed:
            {
                SetState(RemoteSessionState.Closed, eventArgs.Reason);
            }

            break;

            case RemoteSessionEvent.CloseCompleted:
            {
                SetState(RemoteSessionState.Closed, eventArgs.Reason);
            }

            break;

            case RemoteSessionEvent.KeyRequested:
            {
                Dbg.Assert(_state == RemoteSessionState.Established,
                           "Server can request a key only after the client reaches the Established state");

                if (_state == RemoteSessionState.Established)
                {
                    SetState(RemoteSessionState.EstablishedAndKeyRequested, eventArgs.Reason);
                }
            }

            break;

            case RemoteSessionEvent.KeyReceived:
            {
                Dbg.Assert(_state == RemoteSessionState.EstablishedAndKeySent,
                           "Key Receiving can only be raised after reaching the Established state");

                if (_state == RemoteSessionState.EstablishedAndKeySent)
                {
                    Timer tmp = Interlocked.Exchange(ref _keyExchangeTimer, null);
                    if (tmp != null)
                    {
                        tmp.Dispose();
                    }

                    _keyExchanged = true;
                    SetState(RemoteSessionState.Established, eventArgs.Reason);

                    if (_pendingDisconnect)
                    {
                        // session key exchange is complete, if there is a disconnect pending, process it now
                        _pendingDisconnect = false;
                        DoDisconnect(sender, eventArgs);
                    }
                }
            }

            break;

            case RemoteSessionEvent.KeySent:
            {
                Dbg.Assert(_state >= RemoteSessionState.Established,
                           "Client can send a public key only after reaching the Established state");

                Dbg.Assert(_keyExchanged == false, "Client should do key exchange only once");

                if (_state == RemoteSessionState.Established ||
                    _state == RemoteSessionState.EstablishedAndKeyRequested)
                {
                    SetState(RemoteSessionState.EstablishedAndKeySent, eventArgs.Reason);

                    // start the timer and wait
                    _keyExchangeTimer = new Timer(HandleKeyExchangeTimeout, null, BaseTransportManager.ClientDefaultOperationTimeoutMs, Timeout.Infinite);
                }
            }

            break;

            case RemoteSessionEvent.DisconnectCompleted:
            {
                Dbg.Assert(_state == RemoteSessionState.Disconnecting || _state == RemoteSessionState.RCDisconnecting,
                           "DisconnectCompleted event received while state machine is in wrong state");

                if (_state == RemoteSessionState.Disconnecting || _state == RemoteSessionState.RCDisconnecting)
                {
                    SetState(RemoteSessionState.Disconnected, eventArgs.Reason);
                }
            }

            break;

            case RemoteSessionEvent.DisconnectFailed:
            {
                Dbg.Assert(_state == RemoteSessionState.Disconnecting,
                           "DisconnectCompleted event received while state machine is in wrong state");

                if (_state == RemoteSessionState.Disconnecting)
                {
                    SetState(RemoteSessionState.Disconnected, eventArgs.Reason);         // set state to disconnected even TODO. Put some ETW event describing the disconnect process failure
                }
            }

            break;

            case RemoteSessionEvent.ReconnectCompleted:
            {
                Dbg.Assert(_state == RemoteSessionState.Reconnecting,
                           "ReconnectCompleted event received while state machine is in wrong state");

                if (_state == RemoteSessionState.Reconnecting)
                {
                    SetState(RemoteSessionState.Established, eventArgs.Reason);
                }
            }

            break;
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Load help file for HelpInfo objects. The HelpInfo objects will be
        /// put into help cache.
        /// </summary>
        /// <remarks>
        /// 1. Needs to pay special attention about error handling in this function.
        /// Common errors include: file not found and invalid xml. None of these error
        /// should cause help search to stop.
        /// 2. a helpfile cache is used to avoid same file got loaded again and again.
        /// </remarks>
        private void LoadHelpFile(string helpFile, string helpFileIdentifier)
        {
            Dbg.Assert(!String.IsNullOrEmpty(helpFile), "HelpFile cannot be null or empty.");
            Dbg.Assert(!String.IsNullOrEmpty(helpFileIdentifier), "helpFileIdentifier cannot be null or empty.");

            XmlDocument doc = InternalDeserializer.LoadUnsafeXmlDocument(
                new FileInfo(helpFile),
                false, /* ignore whitespace, comments, etc. */
                null); /* default maxCharactersInDocument */

            // Add this file into _helpFiles hashtable to prevent it to be loaded again.
            _helpFiles[helpFile] = 0;

            XmlNode helpItemsNode = null;

            if (doc.HasChildNodes)
            {
                for (int i = 0; i < doc.ChildNodes.Count; i++)
                {
                    XmlNode node = doc.ChildNodes[i];
                    if (node.NodeType == XmlNodeType.Element && String.Compare(node.LocalName, "helpItems", StringComparison.OrdinalIgnoreCase) == 0)
                    {
                        helpItemsNode = node;
                        break;
                    }
                }
            }

            if (helpItemsNode == null)
            {
                s_tracer.WriteLine("Unable to find 'helpItems' element in file {0}", helpFile);
                return;
            }

            bool isMaml = IsMamlHelp(helpFile, helpItemsNode);

            using (this.HelpSystem.Trace(helpFile))
            {
                if (helpItemsNode.HasChildNodes)
                {
                    for (int i = 0; i < helpItemsNode.ChildNodes.Count; i++)
                    {
                        XmlNode node = helpItemsNode.ChildNodes[i];

                        string nodeLocalName = node.LocalName;

                        bool isClass = (String.Compare(nodeLocalName, "class", StringComparison.OrdinalIgnoreCase) == 0);

                        if (node.NodeType == XmlNodeType.Element && isClass)
                        {
                            MamlClassHelpInfo helpInfo = null;

                            if (isMaml)
                            {
                                if (isClass)
                                {
                                    helpInfo = MamlClassHelpInfo.Load(node, HelpCategory.Class);
                                }
                            }

                            if (helpInfo != null)
                            {
                                this.HelpSystem.TraceErrors(helpInfo.Errors);
                                AddCache(helpFileIdentifier, helpInfo);
                            }
                        }
                    }
                }
            }
        }
Ejemplo n.º 3
0
 internal ThrottlingJobChildAddedEventArgs(Job addedChildJob)
 {
     Dbg.Assert(addedChildJob != null, "Caller should verify addedChildJob != null");
     AddedChildJob = addedChildJob;
 }
Ejemplo n.º 4
0
        /// <summary>
        /// The invocation state of the server powershell has changed.
        /// The state of the client powershell is reflected accordingly
        /// </summary>
        /// <param name="sender">Sender of this event, unused.</param>
        /// <param name="eventArgs">Arguments describing this event.</param>
        private void HandleInvocationStateInfoReceived(object sender,
                                                       RemoteDataEventArgs <PSInvocationStateInfo> eventArgs)
        {
            using (s_tracer.TraceEventHandlers())
            {
                PSInvocationStateInfo stateInfo = eventArgs.Data;

                // we should not receive any transient state from
                // the server
                Dbg.Assert(!(stateInfo.State == PSInvocationState.Running ||
                             stateInfo.State == PSInvocationState.Stopping),
                           "Transient states should not be received from the server");

                if (stateInfo.State == PSInvocationState.Disconnected)
                {
                    SetStateInfo(stateInfo);
                }
                else if (stateInfo.State == PSInvocationState.Stopped ||
                         stateInfo.State == PSInvocationState.Failed ||
                         stateInfo.State == PSInvocationState.Completed)
                {
                    // Special case for failure error due to ErrorCode==-2144108453 (no ShellId found).
                    // In this case terminate session since there is no longer a shell to communicate
                    // with.
                    bool terminateSession = false;
                    if (stateInfo.State == PSInvocationState.Failed)
                    {
                        PSRemotingTransportException remotingTransportException = stateInfo.Reason as PSRemotingTransportException;
                        terminateSession = (remotingTransportException != null) &&
                                           (remotingTransportException.ErrorCode == System.Management.Automation.Remoting.Client.WSManNativeApi.ERROR_WSMAN_TARGETSESSION_DOESNOTEXIST);
                    }

                    // if state is completed or failed or stopped,
                    // then the collections need to be closed as
                    // well, else the enumerator will block
                    UnblockCollections();

                    if (stopCalled || terminateSession)
                    {
                        // Reset stop called flag.
                        stopCalled = false;

                        // if a Stop method has been called, then powershell
                        // would have already raised a Stopping event, after
                        // which only a Stopped should be raised
                        _stateInfoQueue.Enqueue(new PSInvocationStateInfo(PSInvocationState.Stopped,
                                                                          stateInfo.Reason));

                        // If the stop call failed due to network problems then close the runspace
                        // since it is now unusable.
                        CheckAndCloseRunspaceAfterStop(stateInfo.Reason);
                    }
                    else
                    {
                        _stateInfoQueue.Enqueue(stateInfo);
                    }
                    // calling close async only after making sure all the internal members are prepared
                    // to handle close complete.
                    dataStructureHandler.CloseConnectionAsync(null);
                }
            }
        }
        /// <summary>
        /// This is the handler for MessageReceived event. It dispatches the data to various components
        /// that uses the data.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="fsmEventArg">
        /// This parameter contains the FSM event.
        /// </param>
        /// <exception cref="ArgumentNullException">
        /// If the parameter <paramref name="fsmEventArg"/> is null.
        /// </exception>
        /// <exception cref="ArgumentException">
        /// If the parameter <paramref name="fsmEventArg"/> does not contain remote data.
        /// </exception>
        internal void DoMessageReceived(object sender, RemoteSessionStateMachineEventArgs fsmEventArg)
        {
            using (s_trace.TraceEventHandlers())
            {
                if (fsmEventArg == null)
                {
                    throw PSTraceSource.NewArgumentNullException("fsmEventArg");
                }

                if (fsmEventArg.RemoteData == null)
                {
                    throw PSTraceSource.NewArgumentException("fsmEventArg");
                }

                Dbg.Assert(_state == RemoteSessionState.Established ||
                           _state == RemoteSessionState.EstablishedAndKeyExchanged ||
                           _state == RemoteSessionState.EstablishedAndKeyReceived ||
                           _state == RemoteSessionState.EstablishedAndKeySent,  //server session will never be in this state.. TODO- remove this
                           "State must be Established or EstablishedAndKeySent or EstablishedAndKeyReceived or EstablishedAndKeyExchanged");

                RemotingTargetInterface targetInterface = fsmEventArg.RemoteData.TargetInterface;
                RemotingDataType        dataType        = fsmEventArg.RemoteData.DataType;

                Guid clientRunspacePoolId;
                ServerRunspacePoolDriver runspacePoolDriver;
                //string errorMessage = null;

                RemoteDataEventArgs remoteDataForSessionArg = null;

                switch (targetInterface)
                {
                case RemotingTargetInterface.Session:
                {
                    switch (dataType)
                    {
                    // GETBACK
                    case RemotingDataType.CreateRunspacePool:
                        remoteDataForSessionArg = new RemoteDataEventArgs(fsmEventArg.RemoteData);
                        _session.SessionDataStructureHandler.RaiseDataReceivedEvent(remoteDataForSessionArg);
                        break;

                    default:
                        Dbg.Assert(false, "Should never reach here");
                        break;
                    }
                }
                break;

                case RemotingTargetInterface.RunspacePool:
                    // GETBACK
                    clientRunspacePoolId = fsmEventArg.RemoteData.RunspacePoolId;
                    runspacePoolDriver   = _session.GetRunspacePoolDriver(clientRunspacePoolId);

                    if (runspacePoolDriver != null)
                    {
                        runspacePoolDriver.DataStructureHandler.ProcessReceivedData(fsmEventArg.RemoteData);
                    }
                    else
                    {
                        s_trace.WriteLine(@"Server received data for Runspace (id: {0}),
                                but the Runspace cannot be found", clientRunspacePoolId);

                        PSRemotingDataStructureException reasonOfFailure = new
                                                                           PSRemotingDataStructureException(RemotingErrorIdStrings.RunspaceCannotBeFound,
                                                                                                            clientRunspacePoolId);
                        RemoteSessionStateMachineEventArgs runspaceNotFoundArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.FatalError, reasonOfFailure);
                        RaiseEvent(runspaceNotFoundArg);
                    }

                    break;

                case RemotingTargetInterface.PowerShell:
                    clientRunspacePoolId = fsmEventArg.RemoteData.RunspacePoolId;
                    runspacePoolDriver   = _session.GetRunspacePoolDriver(clientRunspacePoolId);

                    runspacePoolDriver.DataStructureHandler.DispatchMessageToPowerShell(fsmEventArg.RemoteData);
                    break;

                default:
                    s_trace.WriteLine("Server received data unknown targetInterface: {0}", targetInterface);

                    PSRemotingDataStructureException   reasonOfFailure2 = new PSRemotingDataStructureException(RemotingErrorIdStrings.ReceivedUnsupportedRemotingTargetInterfaceType, targetInterface);
                    RemoteSessionStateMachineEventArgs unknownTargetArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.FatalError, reasonOfFailure2);
                    RaiseEvent(unknownTargetArg);
                    break;
                }
            }
        }
 private ExecutionContextForStepping(ExecutionContext ctxt)
 {
     Dbg.Assert(ctxt != null, "ExecutionContext cannot be null.");
     _executionContext = ctxt;
 }
Ejemplo n.º 7
0
        /// <summary>
        /// Process data coming from the transport. This method analyses the data
        /// and if an object can be created, it creates one and calls the
        /// <paramref name="callback"/> with the deserialized object. This method
        /// does not assume all fragments to be available. So if not enough fragments are
        /// available it will simply return..
        /// </summary>
        /// <param name="data">
        /// Data to process.
        /// </param>
        /// <param name="callback">
        /// Callback to call once a complete deserialized object is available.
        /// </param>
        /// <returns>
        /// Defragmented Object if any, otherwise null.
        /// </returns>
        /// <exception cref="PSRemotingTransportException">
        /// 1. Fragment Ids not in sequence
        /// 2. Object Ids does not match
        /// 3. The current deserialized object size of the received data exceeded
        /// allowed maximum object size. The current deserialized object size is {0}.
        /// Allowed maximum object size is {1}.
        /// </exception>
        /// <remarks>
        /// Might throw other exceptions as the deserialized object is handled here.
        /// </remarks>
        internal void ProcessRawData(byte[] data, OnDataAvailableCallback callback)
        {
            Dbg.Assert(data != null, "Cannot process null data");
            Dbg.Assert(callback != null, "Callback cannot be null");

            lock (_syncObject)
            {
                if (_isDisposed)
                {
                    return;
                }

                _numberOfThreadsProcessing++;
                if (_numberOfThreadsProcessing > _maxNumberOfThreadsToAllowForProcessing)
                {
                    Dbg.Assert(false, "Multiple threads are not allowed in ProcessRawData.");
                }
            }

            try
            {
                _pendingDataStream.Write(data, 0, data.Length);

                // this do loop will process one deserialized object.
                // using a loop allows to process multiple objects within
                // the same packet
                while (true)
                {
                    if (_pendingDataStream.Length <= FragmentedRemoteObject.HeaderLength)
                    {
                        // there is not enough data to be processed.
                        s_baseTracer.WriteLine("Not enough data to process. Data is less than header length. Data length is {0}. Header Length {1}.",
                                               _pendingDataStream.Length, FragmentedRemoteObject.HeaderLength);
                        return;
                    }

                    byte[] dataRead = _pendingDataStream.ToArray();

                    // there is enough data to process here. get the fragment header
                    long objectId = FragmentedRemoteObject.GetObjectId(dataRead, 0);
                    if (objectId <= 0)
                    {
                        throw new PSRemotingTransportException(RemotingErrorIdStrings.ObjectIdCannotBeLessThanZero);
                    }

                    long fragmentId = FragmentedRemoteObject.GetFragmentId(dataRead, 0);
                    bool sFlag      = FragmentedRemoteObject.GetIsStartFragment(dataRead, 0);
                    bool eFlag      = FragmentedRemoteObject.GetIsEndFragment(dataRead, 0);
                    int  blobLength = FragmentedRemoteObject.GetBlobLength(dataRead, 0);

                    if ((s_baseTracer.Options & PSTraceSourceOptions.WriteLine) != PSTraceSourceOptions.None)
                    {
                        s_baseTracer.WriteLine("Object Id: {0}", objectId);
                        s_baseTracer.WriteLine("Fragment Id: {0}", fragmentId);
                        s_baseTracer.WriteLine("Start Flag: {0}", sFlag);
                        s_baseTracer.WriteLine("End Flag: {0}", eFlag);
                        s_baseTracer.WriteLine("Blob Length: {0}", blobLength);
                    }

                    int totalLengthOfFragment = 0;

                    try
                    {
                        totalLengthOfFragment = checked (FragmentedRemoteObject.HeaderLength + blobLength);
                    }
                    catch (System.OverflowException)
                    {
                        s_baseTracer.WriteLine("Fragment too big.");
                        ResetReceiveData();
                        PSRemotingTransportException e = new PSRemotingTransportException(RemotingErrorIdStrings.ObjectIsTooBig);
                        throw e;
                    }

                    if (_pendingDataStream.Length < totalLengthOfFragment)
                    {
                        s_baseTracer.WriteLine("Not enough data to process packet. Data is less than expected blob length. Data length {0}. Expected Length {1}.",
                                               _pendingDataStream.Length, totalLengthOfFragment);
                        return;
                    }

                    // ensure object size limit is not reached
                    if (_maxReceivedObjectSize.HasValue)
                    {
                        _totalReceivedObjectSizeSoFar = unchecked (_totalReceivedObjectSizeSoFar + totalLengthOfFragment);
                        if ((_totalReceivedObjectSizeSoFar < 0) || (_totalReceivedObjectSizeSoFar > _maxReceivedObjectSize.Value))
                        {
                            s_baseTracer.WriteLine("ObjectSize > MaxReceivedObjectSize. ObjectSize is {0}. MaxReceivedObjectSize is {1}",
                                                   _totalReceivedObjectSizeSoFar, _maxReceivedObjectSize);
                            PSRemotingTransportException e = null;

                            if (_isCreateByClientTM)
                            {
                                e = new PSRemotingTransportException(PSRemotingErrorId.ReceivedObjectSizeExceededMaximumClient,
                                                                     RemotingErrorIdStrings.ReceivedObjectSizeExceededMaximumClient,
                                                                     _totalReceivedObjectSizeSoFar, _maxReceivedObjectSize);
                            }
                            else
                            {
                                e = new PSRemotingTransportException(PSRemotingErrorId.ReceivedObjectSizeExceededMaximumServer,
                                                                     RemotingErrorIdStrings.ReceivedObjectSizeExceededMaximumServer,
                                                                     _totalReceivedObjectSizeSoFar, _maxReceivedObjectSize);
                            }

                            ResetReceiveData();
                            throw e;
                        }
                    }

                    // appears like stream doesn't have individual position marker for read and write
                    // since we are going to read from now...
                    _pendingDataStream.Seek(0, SeekOrigin.Begin);

                    // we have enough data to process..so read the data from the stream and process.
                    byte[] oneFragment = new byte[totalLengthOfFragment];
                    // this will change position back to totalLengthOfFragment
                    int dataCount = _pendingDataStream.Read(oneFragment, 0, totalLengthOfFragment);
                    Dbg.Assert(dataCount == totalLengthOfFragment, "Unable to read enough data from the stream. Read failed");

                    PSEtwLog.LogAnalyticVerbose(
                        PSEventId.ReceivedRemotingFragment, PSOpcode.Receive, PSTask.None,
                        PSKeyword.Transport | PSKeyword.UseAlwaysAnalytic,
                        (Int64)objectId,
                        (Int64)fragmentId,
                        sFlag ? 1 : 0,
                        eFlag ? 1 : 0,
                        (UInt32)blobLength,
                        new PSETWBinaryBlob(oneFragment, FragmentedRemoteObject.HeaderLength, blobLength));

                    byte[] extraData = null;
                    if (totalLengthOfFragment < _pendingDataStream.Length)
                    {
                        // there is more data in the stream than fragment size..so save that data
                        extraData = new byte[_pendingDataStream.Length - totalLengthOfFragment];
                        _pendingDataStream.Read(extraData, 0, (int)(_pendingDataStream.Length - totalLengthOfFragment));
                    }

                    // reset incoming stream.
                    _pendingDataStream.Dispose();
                    _pendingDataStream = new MemoryStream();
                    if (extraData != null)
                    {
                        _pendingDataStream.Write(extraData, 0, extraData.Length);
                    }

                    if (sFlag)
                    {
                        _canIgnoreOffSyncFragments = false; // reset this upon receiving a start fragment of a fresh object
                        _currentObjectId           = objectId;
                        // Memory streams created with an unsigned byte array provide a non-resizable stream view
                        // of the data, and can only be written to. When using a byte array, you can neither append
                        // to nor shrink the stream, although you might be able to modify the existing contents
                        // depending on the parameters passed into the constructor. Empty memory streams are
                        // resizable, and can be written to and read from.
                        _dataToProcessStream = new MemoryStream();
                    }
                    else
                    {
                        // check if the data belongs to the same object as the start fragment
                        if (objectId != _currentObjectId)
                        {
                            s_baseTracer.WriteLine("ObjectId != CurrentObjectId");
                            // TODO - drop an ETW event
                            ResetReceiveData();
                            if (!_canIgnoreOffSyncFragments)
                            {
                                PSRemotingTransportException e = new PSRemotingTransportException(RemotingErrorIdStrings.ObjectIdsNotMatching);
                                throw e;
                            }
                            else
                            {
                                s_baseTracer.WriteLine("Ignoring ObjectId != CurrentObjectId");
                                continue;
                            }
                        }

                        if (fragmentId != (_currentFrgId + 1))
                        {
                            s_baseTracer.WriteLine("Fragment Id is not in sequence.");
                            // TODO - drop an ETW event
                            ResetReceiveData();
                            if (!_canIgnoreOffSyncFragments)
                            {
                                PSRemotingTransportException e = new PSRemotingTransportException(RemotingErrorIdStrings.FragmentIdsNotInSequence);
                                throw e;
                            }
                            else
                            {
                                s_baseTracer.WriteLine("Ignoring Fragment Id is not in sequence.");
                                continue;
                            }
                        }
                    }

                    // make fragment id from this packet as the current fragment id
                    _currentFrgId = fragmentId;
                    // store the blob in a separate stream
                    _dataToProcessStream.Write(oneFragment, FragmentedRemoteObject.HeaderLength, blobLength);

                    if (eFlag)
                    {
                        try
                        {
                            // appears like stream doesn't individual position marker for read and write
                            // since we are going to read from now..i am resetting position to 0.
                            _dataToProcessStream.Seek(0, SeekOrigin.Begin);
                            RemoteDataObject <PSObject> remoteObject = RemoteDataObject <PSObject> .CreateFrom(_dataToProcessStream, _defragmentor);

                            s_baseTracer.WriteLine("Runspace Id: {0}", remoteObject.RunspacePoolId);
                            s_baseTracer.WriteLine("PowerShell Id: {0}", remoteObject.PowerShellId);
                            // notify the caller that a deserialized object is available.
                            callback(remoteObject);
                        }
                        finally
                        {
                            // Reset the receive data buffers and start the process again.
                            ResetReceiveData();
                        }

                        if (_isDisposed)
                        {
                            break;
                        }
                    }
                }
            }
            finally
            {
                lock (_syncObject)
                {
                    if (_isDisposed && (_numberOfThreadsProcessing == 1))
                    {
                        ReleaseResources();
                    }

                    _numberOfThreadsProcessing--;
                }
            }
        }
Ejemplo n.º 8
0
        /// <summary>
        /// Adds a new JobSourceAdapter to the JobManager instance.
        /// After addition, creating a NewJob with a JobDefinition
        /// indicating the JobSourceAdapter derivative type will function.
        /// </summary>
        /// <param name="jobSourceAdapterType">The derivative JobSourceAdapter type to
        /// register.</param>
        /// <exception cref="InvalidOperationException">Throws when there is no public
        /// default constructor on the type.</exception>
        internal void RegisterJobSourceAdapter(Type jobSourceAdapterType)
        {
            Dbg.Assert(typeof(JobSourceAdapter).IsAssignableFrom(jobSourceAdapterType), "BaseType of any type being registered with the JobManager should be JobSourceAdapter.");
            Dbg.Assert(jobSourceAdapterType != typeof(JobSourceAdapter), "JobSourceAdapter abstract type itself should never be registered.");
            Dbg.Assert(jobSourceAdapterType != null, "JobSourceAdapterType should never be called with null value.");
            object instance = null;

            if (jobSourceAdapterType.FullName != null && jobSourceAdapterType.FullName.EndsWith("WorkflowJobSourceAdapter", StringComparison.OrdinalIgnoreCase))
            {
                MethodInfo method = jobSourceAdapterType.GetMethod("GetInstance");
                instance = method.Invoke(null, null);
            }
            else
            {
                ConstructorInfo constructor = jobSourceAdapterType.GetConstructor(PSTypeExtensions.EmptyTypes);
                if (!constructor.IsPublic)
                {
                    string message = String.Format(CultureInfo.CurrentCulture,
                                                   RemotingErrorIdStrings.JobManagerRegistrationConstructorError,
                                                   jobSourceAdapterType.FullName);
                    throw new InvalidOperationException(message);
                }

                try
                {
                    instance = constructor.Invoke(null);
                }
                catch (MemberAccessException exception)
                {
                    _tracer.TraceException(exception);
                    throw;
                }
                catch (TargetInvocationException exception)
                {
                    _tracer.TraceException(exception);
                    throw;
                }
                catch (TargetParameterCountException exception)
                {
                    _tracer.TraceException(exception);
                    throw;
                }
                catch (NotSupportedException exception)
                {
                    _tracer.TraceException(exception);
                    throw;
                }
                catch (SecurityException exception)
                {
                    _tracer.TraceException(exception);
                    throw;
                }
            }

            if (instance != null)
            {
                lock (_syncObject)
                {
                    _sourceAdapters.Add(jobSourceAdapterType.Name, (JobSourceAdapter)instance);
                }
            }
        }
Ejemplo n.º 9
0
        internal static DirectoryInfo CreateModuleDirectory(PSCmdlet cmdlet, string moduleNameOrPath, bool force)
        {
            Dbg.Assert(cmdlet != null, "Caller should verify cmdlet != null");
            Dbg.Assert(!string.IsNullOrEmpty(moduleNameOrPath), "Caller should verify !string.IsNullOrEmpty(moduleNameOrPath)");

            DirectoryInfo directoryInfo = null;

            try
            {
                string rootedPath = Microsoft.PowerShell.Commands.ModuleCmdletBase.ResolveRootedFilePath(moduleNameOrPath, cmdlet.Context);
                if (string.IsNullOrEmpty(rootedPath) && moduleNameOrPath.StartsWith('.'))
                {
                    PathInfo currentPath = cmdlet.CurrentProviderLocation(cmdlet.Context.ProviderNames.FileSystem);
                    rootedPath = Path.Combine(currentPath.ProviderPath, moduleNameOrPath);
                }

                if (string.IsNullOrEmpty(rootedPath))
                {
                    string personalModuleRoot = ModuleIntrinsics.GetPersonalModulePath();
                    rootedPath = Path.Combine(personalModuleRoot, moduleNameOrPath);
                }

                directoryInfo = new DirectoryInfo(rootedPath);
                if (directoryInfo.Exists)
                {
                    if (!force)
                    {
                        string errorMessage = string.Format(
                            CultureInfo.InvariantCulture, // directory name should be treated as culture-invariant
                            PathUtilsStrings.ExportPSSession_ErrorDirectoryExists,
                            directoryInfo.FullName);
                        ErrorDetails details     = new ErrorDetails(errorMessage);
                        ErrorRecord  errorRecord = new ErrorRecord(
                            new ArgumentException(details.Message),
                            "ExportProxyCommand_OutputDirectoryExists",
                            ErrorCategory.ResourceExists,
                            directoryInfo);
                        cmdlet.ThrowTerminatingError(errorRecord);
                    }
                }
                else
                {
                    directoryInfo.Create();
                }
            }
            catch (Exception e)
            {
                string errorMessage = string.Format(
                    CultureInfo.InvariantCulture, // directory name should be treated as culture-invariant
                    PathUtilsStrings.ExportPSSession_CannotCreateOutputDirectory,
                    moduleNameOrPath,
                    e.Message);
                ErrorDetails details     = new ErrorDetails(errorMessage);
                ErrorRecord  errorRecord = new ErrorRecord(
                    new ArgumentException(details.Message, e),
                    "ExportProxyCommand_CannotCreateOutputDirectory",
                    ErrorCategory.ResourceExists,
                    moduleNameOrPath);
                cmdlet.ThrowTerminatingError(errorRecord);
            }

            return(directoryInfo);
        }
        /// <summary>
        /// Verifies the negotiation packet received from the server.
        /// </summary>
        /// <param name="serverRemoteSessionCapability">
        /// Capabilities of remote session
        /// </param>
        /// <returns>
        /// The method returns true if the capability negotiation is successful.
        /// Otherwise, it returns false.
        /// </returns>
        /// <exception cref="PSRemotingDataStructureException">
        /// 1. PowerShell client does not support the PSVersion {1} negotiated by the server.
        ///    Make sure the server is compatible with the build {2} of PowerShell.
        /// 2. PowerShell client does not support the SerializationVersion {1} negotiated by the server.
        ///    Make sure the server is compatible with the build {2} of PowerShell.
        /// </exception>
        private bool RunClientNegotiationAlgorithm(RemoteSessionCapability serverRemoteSessionCapability)
        {
            Dbg.Assert(serverRemoteSessionCapability != null, "server capability cache must be non-null");

            // ProtocolVersion check
            Version serverProtocolVersion = serverRemoteSessionCapability.ProtocolVersion;

            _serverProtocolVersion = serverProtocolVersion;
            Version clientProtocolVersion = Context.ClientCapability.ProtocolVersion;

            if (
                clientProtocolVersion.Equals(serverProtocolVersion) ||
                (clientProtocolVersion == RemotingConstants.ProtocolVersionWin7RTM &&
                 serverProtocolVersion == RemotingConstants.ProtocolVersionWin7RC) ||
                (clientProtocolVersion == RemotingConstants.ProtocolVersionWin8RTM &&
                 (serverProtocolVersion == RemotingConstants.ProtocolVersionWin7RC ||
                  serverProtocolVersion == RemotingConstants.ProtocolVersionWin7RTM
                 )) ||
                (clientProtocolVersion == RemotingConstants.ProtocolVersionWin10RTM &&
                 (serverProtocolVersion == RemotingConstants.ProtocolVersionWin7RC ||
                  serverProtocolVersion == RemotingConstants.ProtocolVersionWin7RTM ||
                  serverProtocolVersion == RemotingConstants.ProtocolVersionWin8RTM
                 ))
                )
            {
                // passed negotiation check
            }
            else
            {
                PSRemotingDataStructureException reasonOfFailure =
                    new PSRemotingDataStructureException(RemotingErrorIdStrings.ClientNegotiationFailed,
                                                         RemoteDataNameStrings.PS_STARTUP_PROTOCOL_VERSION_NAME,
                                                         serverProtocolVersion,
                                                         PSVersionInfo.GitCommitId,
                                                         RemotingConstants.ProtocolVersion);
                throw reasonOfFailure;
            }

            // PSVersion check
            Version serverPSVersion = serverRemoteSessionCapability.PSVersion;
            Version clientPSVersion = Context.ClientCapability.PSVersion;

            if (!clientPSVersion.Equals(serverPSVersion))
            {
                PSRemotingDataStructureException reasonOfFailure =
                    new PSRemotingDataStructureException(RemotingErrorIdStrings.ClientNegotiationFailed,
                                                         RemoteDataNameStrings.PSVersion,
                                                         serverPSVersion.ToString(),
                                                         PSVersionInfo.GitCommitId,
                                                         RemotingConstants.ProtocolVersion);
                throw reasonOfFailure;
            }

            // Serialization Version check
            Version serverSerVersion = serverRemoteSessionCapability.SerializationVersion;
            Version clientSerVersion = Context.ClientCapability.SerializationVersion;

            if (!clientSerVersion.Equals(serverSerVersion))
            {
                PSRemotingDataStructureException reasonOfFailure =
                    new PSRemotingDataStructureException(RemotingErrorIdStrings.ClientNegotiationFailed,
                                                         RemoteDataNameStrings.SerializationVersion,
                                                         serverSerVersion.ToString(),
                                                         PSVersionInfo.GitCommitId,
                                                         RemotingConstants.ProtocolVersion);
                throw reasonOfFailure;
            }

            return(true);
        }
Ejemplo n.º 11
0
 public BracketExpressionElement(Regex regex)
 {
     Dbg.Assert(regex != null, "Caller should verify regex != null");
     _regex = regex;
 }
Ejemplo n.º 12
0
        /// <summary>
        /// Checks if source is known container type and returns appropriate information.
        /// </summary>
        /// <param name="source"></param>
        /// <param name="ct"></param>
        /// <param name="dictionary"></param>
        /// <param name="enumerable"></param>
        private static void GetKnownContainerTypeInfo(
            object source, out ContainerType ct, out IDictionary dictionary, out IEnumerable enumerable)
        {
            Dbg.Assert(source != null, "caller should validate the parameter");

            ct         = ContainerType.None;
            dictionary = null;
            enumerable = null;

            dictionary = source as IDictionary;
            if (dictionary != null)
            {
                ct = ContainerType.Dictionary;
                return;
            }

            if (source is Stack)
            {
                ct         = ContainerType.Stack;
                enumerable = LanguagePrimitives.GetEnumerable(source);
                Dbg.Assert(enumerable != null, "Stack is enumerable");
            }
            else if (source is Queue)
            {
                ct         = ContainerType.Queue;
                enumerable = LanguagePrimitives.GetEnumerable(source);
                Dbg.Assert(enumerable != null, "Queue is enumerable");
            }
            else if (source is IList)
            {
                ct         = ContainerType.List;
                enumerable = LanguagePrimitives.GetEnumerable(source);
                Dbg.Assert(enumerable != null, "IList is enumerable");
            }
            else
            {
                Type gt = source.GetType();
                if (gt.GetTypeInfo().IsGenericType)
                {
                    if (DerivesFromGenericType(gt, typeof(Stack <>)))
                    {
                        ct         = ContainerType.Stack;
                        enumerable = LanguagePrimitives.GetEnumerable(source);
                        Dbg.Assert(enumerable != null, "Stack is enumerable");
                    }
                    else if (DerivesFromGenericType(gt, typeof(Queue <>)))
                    {
                        ct         = ContainerType.Queue;
                        enumerable = LanguagePrimitives.GetEnumerable(source);
                        Dbg.Assert(enumerable != null, "Queue is enumerable");
                    }
                    else if (DerivesFromGenericType(gt, typeof(List <>)))
                    {
                        ct         = ContainerType.List;
                        enumerable = LanguagePrimitives.GetEnumerable(source);
                        Dbg.Assert(enumerable != null, "Queue is enumerable");
                    }
                }
            }

            // Check if type is IEnumerable
            if (ct == ContainerType.None)
            {
                enumerable = LanguagePrimitives.GetEnumerable(source);
                if (enumerable != null)
                {
                    ct = ContainerType.Enumerable;
                }
            }
        }
Ejemplo n.º 13
0
        private bool HandleKnownContainerTypes(object source, string property, int depth)
        {
            Dbg.Assert(source != null, "caller should validate the parameter");

            ContainerType ct         = ContainerType.None;
            PSObject      mshSource  = source as PSObject;
            IEnumerable   enumerable = null;
            IDictionary   dictionary = null;

            // If passed in object is PSObject with no baseobject, return false.
            if (mshSource != null && mshSource.ImmediateBaseObjectIsEmpty)
            {
                return(false);
            }

            // Check if source (or baseobject in mshSource) is known container type
            GetKnownContainerTypeInfo(mshSource != null ? mshSource.ImmediateBaseObject : source, out ct,
                                      out dictionary, out enumerable);

            if (ct == ContainerType.None)
            {
                return(false);
            }

            WriteStartOfPSObject(mshSource ?? PSObject.AsPSObject(source), property, true);
            switch (ct)
            {
            case ContainerType.Dictionary:
            {
                WriteDictionary(dictionary, depth);
            }

            break;

            case ContainerType.Stack:
            case ContainerType.Queue:
            case ContainerType.List:
            case ContainerType.Enumerable:
            {
                WriteEnumerable(enumerable, depth);
            }

            break;

            default:
            {
                Dbg.Assert(false, "All containers should be handled in the switch");
            }

            break;
            }

            // An object which is original enumerable becomes an PSObject
            // with arraylist on deserialization. So on roundtrip it will show up
            // as List.
            // We serialize properties of enumerable and on deserialization mark the object
            // as Deserialized. So if object is marked deserialized, we should write properties.
            // Note: we do not serialize the properties of IEnumerable if depth is zero.
            if (depth != 0 && (ct == ContainerType.Enumerable || (mshSource != null && mshSource.IsDeserialized)))
            {
                // Note:Depth is the depth for serialization of baseObject.
                // Depth for serialization of each property is one less.
                WritePSObjectProperties(PSObject.AsPSObject(source), depth);
            }

            // If source is PSObject, serialize notes
            if (mshSource != null)
            {
                // Serialize instanceMembers
                PSMemberInfoCollection <PSMemberInfo> instanceMembers = mshSource.InstanceMembers;
                if (instanceMembers != null)
                {
                    WriteMemberInfoCollection(instanceMembers, depth, true);
                }
            }

            _writer.WriteEndElement();

            return(true);
        }
Ejemplo n.º 14
0
        /// <summary>
        /// This constructor will be used to created a remote runspace info
        /// object with a auto generated name
        /// </summary>
        /// <param name="remoteRunspace">Remote runspace object for which
        /// the info object need to be created</param>
        internal PSSession(RemoteRunspace remoteRunspace)
        {
            _remoteRunspace = remoteRunspace;

            // Use passed in session Id, if available.
            if (remoteRunspace.PSSessionId != -1)
            {
                Id = remoteRunspace.PSSessionId;
            }
            else
            {
                Id = System.Threading.Interlocked.Increment(ref s_seed);
                remoteRunspace.PSSessionId = Id;
            }

            // Use passed in friendly name, if available.
            if (!string.IsNullOrEmpty(remoteRunspace.PSSessionName))
            {
                Name = remoteRunspace.PSSessionName;
            }
            else
            {
                Name = "Runspace" + Id;
                remoteRunspace.PSSessionName = Name;
            }

            // WSMan session
            if (remoteRunspace.ConnectionInfo is WSManConnectionInfo)
            {
                ComputerType = TargetMachineType.RemoteMachine;

                string fullShellName = WSManConnectionInfo.ExtractPropertyAsWsManConnectionInfo <string>(
                    remoteRunspace.ConnectionInfo,
                    "ShellUri", string.Empty);

                ConfigurationName = GetDisplayShellName(fullShellName);
                return;
            }

            // VM session
            VMConnectionInfo vmConnectionInfo = remoteRunspace.ConnectionInfo as VMConnectionInfo;

            if (vmConnectionInfo != null)
            {
                ComputerType      = TargetMachineType.VirtualMachine;
                ConfigurationName = vmConnectionInfo.ConfigurationName;
                return;
            }

            // Container session
            ContainerConnectionInfo containerConnectionInfo = remoteRunspace.ConnectionInfo as ContainerConnectionInfo;

            if (containerConnectionInfo != null)
            {
                ComputerType      = TargetMachineType.Container;
                ConfigurationName = containerConnectionInfo.ContainerProc.ConfigurationName;
                return;
            }

            // SSH session
            SSHConnectionInfo sshConnectionInfo = remoteRunspace.ConnectionInfo as SSHConnectionInfo;

            if (sshConnectionInfo != null)
            {
                ComputerType      = TargetMachineType.RemoteMachine;
                ConfigurationName = "DefaultShell";
                return;
            }

            // We only support WSMan/VM/Container sessions now.
            Dbg.Assert(false, "Invalid Runspace");
        }
        /// <summary>
        /// Dispatches data when it arrives from the input queue.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="dataArg">
        /// arg which contains the data received from input queue
        /// </param>
        internal void DispatchInputQueueData(object sender, RemoteDataEventArgs dataArg)
        {
            if (dataArg == null)
            {
                throw PSTraceSource.NewArgumentNullException(nameof(dataArg));
            }

            RemoteDataObject <PSObject> rcvdData = dataArg.ReceivedData;

            if (rcvdData == null)
            {
                throw PSTraceSource.NewArgumentException(nameof(dataArg));
            }

            RemotingDestination destination = rcvdData.Destination;

            if ((destination & RemotingDestination.Client) != RemotingDestination.Client)
            {
                throw new PSRemotingDataStructureException(RemotingErrorIdStrings.RemotingDestinationNotForMe, RemotingDestination.Client, destination);
            }

            RemotingTargetInterface targetInterface = rcvdData.TargetInterface;

            switch (targetInterface)
            {
            case RemotingTargetInterface.Session:
            {
                // Messages for session can cause statemachine state to change.
                // These messages are first processed by Sessiondata structure handler and depending
                // on the type of message, appropriate event is raised in state machine
                ProcessSessionMessages(dataArg);
                break;
            }

            case RemotingTargetInterface.RunspacePool:
            case RemotingTargetInterface.PowerShell:
                // Non Session messages do not change the state of the statemachine.
                // However instead of forwarding them to Runspace/pipeline here, an
                // event is raised in state machine which verified that state is
                // suitable for accepting these messages. if state is suitable statemachine
                // will call DoMessageForwading which will forward the messages appropriately
                RemoteSessionStateMachineEventArgs msgRcvArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.MessageReceived, null);
                if (StateMachine.CanByPassRaiseEvent(msgRcvArg))
                {
                    ProcessNonSessionMessages(dataArg.ReceivedData);
                }
                else
                {
                    StateMachine.RaiseEvent(msgRcvArg);
                }

                break;

            default:
            {
                Dbg.Assert(false, "we should not be encountering this");
            }

            break;
            }
        }
Ejemplo n.º 16
0
        /// <summary>
        /// This method is added to be backward compatible with V1 hosts w.r.t
        /// new PromptForChoice method added in PowerShell V2.
        /// </summary>
        /// <param name="caption"></param>
        /// <param name="message"></param>
        /// <param name="choices"></param>
        /// <param name="defaultChoices"></param>
        /// <returns></returns>
        /// <exception cref="ArgumentException">
        /// 1. Choices is null.
        /// 2. Choices.Count = 0
        /// 3. DefaultChoice is either less than 0 or greater than Choices.Count
        /// </exception>
        private Collection <int> EmulatePromptForMultipleChoice(string caption,
                                                                string message,
                                                                Collection <ChoiceDescription> choices,
                                                                IEnumerable <int> defaultChoices)
        {
            Dbg.Assert(_externalUI != null, "externalUI cannot be null.");

            if (choices == null)
            {
                throw PSTraceSource.NewArgumentNullException("choices");
            }

            if (choices.Count == 0)
            {
                throw PSTraceSource.NewArgumentException("choices",
                                                         InternalHostUserInterfaceStrings.EmptyChoicesError, "choices");
            }

            Dictionary <int, bool> defaultChoiceKeys = new Dictionary <int, bool>();

            if (defaultChoices != null)
            {
                foreach (int defaultChoice in defaultChoices)
                {
                    if ((defaultChoice < 0) || (defaultChoice >= choices.Count))
                    {
                        throw PSTraceSource.NewArgumentOutOfRangeException("defaultChoice", defaultChoice,
                                                                           InternalHostUserInterfaceStrings.InvalidDefaultChoiceForMultipleSelection,
                                                                           "defaultChoice",
                                                                           "choices",
                                                                           defaultChoice);
                    }

                    if (!defaultChoiceKeys.ContainsKey(defaultChoice))
                    {
                        defaultChoiceKeys.Add(defaultChoice, true);
                    }
                }
            }

            // Construct the caption + message + list of choices + default choices
            Text.StringBuilder choicesMessage = new Text.StringBuilder();
            char newLine = '\n';

            if (!string.IsNullOrEmpty(caption))
            {
                choicesMessage.Append(caption);
                choicesMessage.Append(newLine);
            }

            if (!string.IsNullOrEmpty(message))
            {
                choicesMessage.Append(message);
                choicesMessage.Append(newLine);
            }

            string[,] hotkeysAndPlainLabels = null;
            HostUIHelperMethods.BuildHotkeysAndPlainLabels(choices, out hotkeysAndPlainLabels);

            string choiceTemplate = "[{0}] {1}  ";

            for (int i = 0; i < hotkeysAndPlainLabels.GetLength(1); ++i)
            {
                string choice =
                    string.Format(
                        Globalization.CultureInfo.InvariantCulture,
                        choiceTemplate,
                        hotkeysAndPlainLabels[0, i],
                        hotkeysAndPlainLabels[1, i]);
                choicesMessage.Append(choice);
                choicesMessage.Append(newLine);
            }

            // default choices
            string defaultPrompt = string.Empty;

            if (defaultChoiceKeys.Count > 0)
            {
                string             prepend = string.Empty;
                Text.StringBuilder defaultChoicesBuilder = new Text.StringBuilder();
                foreach (int defaultChoice in defaultChoiceKeys.Keys)
                {
                    string defaultStr = hotkeysAndPlainLabels[0, defaultChoice];
                    if (string.IsNullOrEmpty(defaultStr))
                    {
                        defaultStr = hotkeysAndPlainLabels[1, defaultChoice];
                    }

                    defaultChoicesBuilder.Append(string.Format(Globalization.CultureInfo.InvariantCulture,
                                                               "{0}{1}", prepend, defaultStr));
                    prepend = ",";
                }

                string defaultChoicesStr = defaultChoicesBuilder.ToString();

                if (defaultChoiceKeys.Count == 1)
                {
                    defaultPrompt = StringUtil.Format(InternalHostUserInterfaceStrings.DefaultChoice,
                                                      defaultChoicesStr);
                }
                else
                {
                    defaultPrompt = StringUtil.Format(InternalHostUserInterfaceStrings.DefaultChoicesForMultipleChoices,
                                                      defaultChoicesStr);
                }
            }

            string messageToBeDisplayed = choicesMessage.ToString() + defaultPrompt + newLine;
            // read choices from the user
            Collection <int> result = new Collection <int>();
            int choicesSelected     = 0;

            do
            {
                string choiceMsg = StringUtil.Format(InternalHostUserInterfaceStrings.ChoiceMessage, choicesSelected);
                messageToBeDisplayed += choiceMsg;
                _externalUI.WriteLine(messageToBeDisplayed);
                string response = _externalUI.ReadLine();

                // they just hit enter
                if (response.Length == 0)
                {
                    // this may happen when
                    // 1. user wants to go with the defaults
                    // 2. user selected some choices and wanted those
                    // choices to be picked.

                    // user did not pick up any choices..choose the default
                    if ((result.Count == 0) && (defaultChoiceKeys.Keys.Count >= 0))
                    {
                        // if there's a default, pick that one.
                        foreach (int defaultChoice in defaultChoiceKeys.Keys)
                        {
                            result.Add(defaultChoice);
                        }
                    }
                    // allow for no choice selection.
                    break;
                }

                int choicePicked = HostUIHelperMethods.DetermineChoicePicked(response.Trim(), choices, hotkeysAndPlainLabels);

                if (choicePicked >= 0)
                {
                    result.Add(choicePicked);
                    choicesSelected++;
                }
                // reset messageToBeDisplayed
                messageToBeDisplayed = string.Empty;
            } while (true);

            return(result);
        }
        // TODO: If this is not used remove this
        // internal override event EventHandler<RemoteDataEventArgs> DataReceived;

        /// <summary>
        /// This processes the object received from transport which are
        /// targeted for session.
        /// </summary>
        /// <param name="arg">
        /// argument contains the data object
        /// </param>
        private void ProcessSessionMessages(RemoteDataEventArgs arg)
        {
            if (arg == null || arg.ReceivedData == null)
            {
                throw PSTraceSource.NewArgumentNullException(nameof(arg));
            }

            RemoteDataObject <PSObject> rcvdData = arg.ReceivedData;

            RemotingTargetInterface targetInterface = rcvdData.TargetInterface;

            Dbg.Assert(targetInterface == RemotingTargetInterface.Session, "targetInterface must be Session");

            RemotingDataType dataType = rcvdData.DataType;

            switch (dataType)
            {
            case RemotingDataType.CloseSession:
                PSRemotingDataStructureException   reasonOfClose   = new PSRemotingDataStructureException(RemotingErrorIdStrings.ServerRequestedToCloseSession);
                RemoteSessionStateMachineEventArgs closeSessionArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.Close, reasonOfClose);
                _stateMachine.RaiseEvent(closeSessionArg);
                break;

            case RemotingDataType.SessionCapability:
                RemoteSessionCapability capability = null;
                try
                {
                    capability = RemotingDecoder.GetSessionCapability(rcvdData.Data);
                }
                catch (PSRemotingDataStructureException dse)
                {
                    // this will happen if expected properties are not
                    // received for session capability
                    throw new PSRemotingDataStructureException(RemotingErrorIdStrings.ClientNotFoundCapabilityProperties,
                                                               dse.Message, PSVersionInfo.GitCommitId, RemotingConstants.ProtocolVersion);
                }

                RemoteSessionStateMachineEventArgs capabilityArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.NegotiationReceived);
                capabilityArg.RemoteSessionCapability = capability;
                _stateMachine.RaiseEvent(capabilityArg);

                RemoteSessionNegotiationEventArgs negotiationArg = new RemoteSessionNegotiationEventArgs(capability);
                NegotiationReceived.SafeInvoke(this, negotiationArg);
                break;

            case RemotingDataType.EncryptedSessionKey:
            {
                string encryptedSessionKey = RemotingDecoder.GetEncryptedSessionKey(rcvdData.Data);
                EncryptedSessionKeyReceived.SafeInvoke(this, new RemoteDataEventArgs <string>(encryptedSessionKey));
            }

            break;

            case RemotingDataType.PublicKeyRequest:
            {
                PublicKeyRequestReceived.SafeInvoke(this, new RemoteDataEventArgs <string>(string.Empty));
            }

            break;

            default:
            {
                throw new PSRemotingDataStructureException(RemotingErrorIdStrings.ReceivedUnsupportedAction, dataType);
            }
            }
        }
Ejemplo n.º 18
0
        static Verbs()
        {
            Type[] verbTypes = new Type[] { typeof(VerbsCommon), typeof(VerbsCommunications), typeof(VerbsData),
                                            typeof(VerbsDiagnostic), typeof(VerbsLifecycle), typeof(VerbsOther), typeof(VerbsSecurity) };

            foreach (Type type in verbTypes)
            {
                foreach (FieldInfo field in type.GetFields())
                {
                    if (field.IsLiteral)
                    {
                        s_validVerbs.Add((string)field.GetValue(null), true);
                    }
                }
            }

            s_recommendedAlternateVerbs.Add("accept", new string[] { "Receive" });
            s_recommendedAlternateVerbs.Add("acquire", new string[] { "Get", "Read" });
            s_recommendedAlternateVerbs.Add("allocate", new string[] { "New" });
            s_recommendedAlternateVerbs.Add("allow", new string[] { "Enable", "Grant", "Unblock" });
            s_recommendedAlternateVerbs.Add("amend", new string[] { "Edit" });
            s_recommendedAlternateVerbs.Add("analyze", new string[] { "Measure", "Test" });
            s_recommendedAlternateVerbs.Add("append", new string[] { "Add" });
            s_recommendedAlternateVerbs.Add("assign", new string[] { "Set" });
            s_recommendedAlternateVerbs.Add("associate", new string[] { "Join", "Merge" });
            s_recommendedAlternateVerbs.Add("attach", new string[] { "Add", "Debug" });
            s_recommendedAlternateVerbs.Add("bc", new string[] { "Compare" });
            s_recommendedAlternateVerbs.Add("boot", new string[] { "Start" });
            s_recommendedAlternateVerbs.Add("break", new string[] { "Disconnect" });
            s_recommendedAlternateVerbs.Add("broadcast", new string[] { "Send" });
            s_recommendedAlternateVerbs.Add("burn", new string[] { "Backup" });
            s_recommendedAlternateVerbs.Add("calculate", new string[] { "Measure" });
            s_recommendedAlternateVerbs.Add("cancel", new string[] { "Stop" });
            s_recommendedAlternateVerbs.Add("cat", new string[] { "Get" });
            s_recommendedAlternateVerbs.Add("change", new string[] { "Convert", "Edit", "Rename" });
            s_recommendedAlternateVerbs.Add("clean", new string[] { "Uninstall" });
            s_recommendedAlternateVerbs.Add("clone", new string[] { "Copy" });
            s_recommendedAlternateVerbs.Add("combine", new string[] { "Join", "Merge" });
            s_recommendedAlternateVerbs.Add("compact", new string[] { "Compress" });
            s_recommendedAlternateVerbs.Add("compile", new string[] { "Build" });
            s_recommendedAlternateVerbs.Add("concatenate", new string[] { "Add" });
            s_recommendedAlternateVerbs.Add("configure", new string[] { "Set" });
            s_recommendedAlternateVerbs.Add("create", new string[] { "New" });
            s_recommendedAlternateVerbs.Add("cut", new string[] { "Remove" });
            // recommendedAlternateVerbs.Add("debug",      new string[] {"Ping"});
            s_recommendedAlternateVerbs.Add("delete", new string[] { "Remove" });
            s_recommendedAlternateVerbs.Add("detach", new string[] { "Dismount", "Remove" });
            s_recommendedAlternateVerbs.Add("determine", new string[] { "Measure", "Resolve" });
            s_recommendedAlternateVerbs.Add("diagnose", new string[] { "Debug", "Test" });
            s_recommendedAlternateVerbs.Add("diff", new string[] { "Checkpoint", "Compare" });
            s_recommendedAlternateVerbs.Add("difference", new string[] { "Checkpoint", "Compare" });
            s_recommendedAlternateVerbs.Add("dig", new string[] { "Trace" });
            s_recommendedAlternateVerbs.Add("dir", new string[] { "Get" });
            s_recommendedAlternateVerbs.Add("discard", new string[] { "Remove" });
            s_recommendedAlternateVerbs.Add("display", new string[] { "Show", "Write" });
            s_recommendedAlternateVerbs.Add("dispose", new string[] { "Remove" });
            s_recommendedAlternateVerbs.Add("divide", new string[] { "Split" });
            s_recommendedAlternateVerbs.Add("dump", new string[] { "Get" });
            s_recommendedAlternateVerbs.Add("duplicate", new string[] { "Copy" });
            s_recommendedAlternateVerbs.Add("empty", new string[] { "Clear" });
            s_recommendedAlternateVerbs.Add("end", new string[] { "Stop" });
            s_recommendedAlternateVerbs.Add("erase", new string[] { "Clear", "Remove" });
            s_recommendedAlternateVerbs.Add("examine", new string[] { "Get" });
            s_recommendedAlternateVerbs.Add("execute", new string[] { "Invoke" });
            s_recommendedAlternateVerbs.Add("explode", new string[] { "Expand" });
            s_recommendedAlternateVerbs.Add("extract", new string[] { "Export" });
            s_recommendedAlternateVerbs.Add("fix", new string[] { "Repair", "Restore" });
            s_recommendedAlternateVerbs.Add("flush", new string[] { "Clear" });
            s_recommendedAlternateVerbs.Add("follow", new string[] { "Trace" });
            s_recommendedAlternateVerbs.Add("generate", new string[] { "New" });
            // recommendedAlternateVerbs.Add("get",        new string[] {"Read"});
            s_recommendedAlternateVerbs.Add("halt", new string[] { "Disable" });
            s_recommendedAlternateVerbs.Add("in", new string[] { "ConvertTo" });
            s_recommendedAlternateVerbs.Add("index", new string[] { "Update" });
            s_recommendedAlternateVerbs.Add("initiate", new string[] { "Start" });
            s_recommendedAlternateVerbs.Add("input", new string[] { "ConvertTo", "Unregister" });
            s_recommendedAlternateVerbs.Add("insert", new string[] { "Add", "Unregister" });
            s_recommendedAlternateVerbs.Add("inspect", new string[] { "Trace" });
            s_recommendedAlternateVerbs.Add("kill", new string[] { "Stop" });
            s_recommendedAlternateVerbs.Add("launch", new string[] { "Start" });
            s_recommendedAlternateVerbs.Add("load", new string[] { "Import" });
            s_recommendedAlternateVerbs.Add("locate", new string[] { "Search", "Select" });
            s_recommendedAlternateVerbs.Add("logoff", new string[] { "Disconnect" });
            s_recommendedAlternateVerbs.Add("mail", new string[] { "Send" });
            s_recommendedAlternateVerbs.Add("make", new string[] { "New" });
            s_recommendedAlternateVerbs.Add("match", new string[] { "Select" });
            s_recommendedAlternateVerbs.Add("migrate", new string[] { "Move" });
            s_recommendedAlternateVerbs.Add("modify", new string[] { "Edit" });
            s_recommendedAlternateVerbs.Add("name", new string[] { "Move" });
            s_recommendedAlternateVerbs.Add("nullify", new string[] { "Clear" });
            s_recommendedAlternateVerbs.Add("obtain", new string[] { "Get" });
            // recommendedAlternateVerbs.Add("out",        new string[] {"ConvertFrom"});
            s_recommendedAlternateVerbs.Add("output", new string[] { "ConvertFrom" });
            s_recommendedAlternateVerbs.Add("pause", new string[] { "Suspend", "Wait" });
            s_recommendedAlternateVerbs.Add("peek", new string[] { "Receive" });
            s_recommendedAlternateVerbs.Add("permit", new string[] { "Enable" });
            s_recommendedAlternateVerbs.Add("purge", new string[] { "Clear", "Remove" });
            s_recommendedAlternateVerbs.Add("pick", new string[] { "Select" });
            // recommendedAlternateVerbs.Add("pop",        new string[] {"Enter", "Exit"});
            s_recommendedAlternateVerbs.Add("prevent", new string[] { "Block" });
            s_recommendedAlternateVerbs.Add("print", new string[] { "Write" });
            s_recommendedAlternateVerbs.Add("prompt", new string[] { "Read" });
            // recommendedAlternateVerbs.Add("push",       new string[] {"Enter", "Exit"});
            s_recommendedAlternateVerbs.Add("put", new string[] { "Send", "Write" });
            s_recommendedAlternateVerbs.Add("puts", new string[] { "Write" });
            s_recommendedAlternateVerbs.Add("quota", new string[] { "Limit" });
            s_recommendedAlternateVerbs.Add("quote", new string[] { "Limit" });
            s_recommendedAlternateVerbs.Add("rebuild", new string[] { "Initialize" });
            s_recommendedAlternateVerbs.Add("recycle", new string[] { "Restart" });
            s_recommendedAlternateVerbs.Add("refresh", new string[] { "Update" });
            s_recommendedAlternateVerbs.Add("reinitialize", new string[] { "Initialize" });
            s_recommendedAlternateVerbs.Add("release", new string[] { "Clear", "Install", "Publish", "Unlock" });
            s_recommendedAlternateVerbs.Add("reload", new string[] { "Update" });
            s_recommendedAlternateVerbs.Add("renew", new string[] { "Initialize", "Update" });
            s_recommendedAlternateVerbs.Add("replicate", new string[] { "Copy" });
            s_recommendedAlternateVerbs.Add("resample", new string[] { "Convert" });
            // recommendedAlternateVerbs.Add("reset",      new string[] {"Set"});
            // recommendedAlternateVerbs.Add("resize",     new string[] {"Convert"});
            s_recommendedAlternateVerbs.Add("restrict", new string[] { "Lock" });
            s_recommendedAlternateVerbs.Add("return", new string[] { "Repair", "Restore" });
            s_recommendedAlternateVerbs.Add("revert", new string[] { "Unpublish" });
            s_recommendedAlternateVerbs.Add("revise", new string[] { "Edit" });
            s_recommendedAlternateVerbs.Add("run", new string[] { "Invoke", "Start" });
            s_recommendedAlternateVerbs.Add("salvage", new string[] { "Test" });
            // recommendedAlternateVerbs.Add("save",       new string[] {"Backup"});
            s_recommendedAlternateVerbs.Add("secure", new string[] { "Lock" });
            s_recommendedAlternateVerbs.Add("separate", new string[] { "Split" });
            s_recommendedAlternateVerbs.Add("setup", new string[] { "Initialize", "Install" });
            s_recommendedAlternateVerbs.Add("sleep", new string[] { "Suspend", "Wait" });
            s_recommendedAlternateVerbs.Add("starttransaction", new string[] { "Checkpoint" });
            s_recommendedAlternateVerbs.Add("telnet", new string[] { "Connect" });
            s_recommendedAlternateVerbs.Add("terminate", new string[] { "Stop" });
            s_recommendedAlternateVerbs.Add("track", new string[] { "Trace" });
            s_recommendedAlternateVerbs.Add("transfer", new string[] { "Move" });
            s_recommendedAlternateVerbs.Add("type", new string[] { "Get" });
            // recommendedAlternateVerbs.Add("undo",       new string[] {"Repair", "Restore"});
            s_recommendedAlternateVerbs.Add("unite", new string[] { "Join", "Merge" });
            s_recommendedAlternateVerbs.Add("unlink", new string[] { "Dismount" });
            s_recommendedAlternateVerbs.Add("unmark", new string[] { "Clear" });
            s_recommendedAlternateVerbs.Add("unrestrict", new string[] { "Unlock" });
            s_recommendedAlternateVerbs.Add("unsecure", new string[] { "Unlock" });
            s_recommendedAlternateVerbs.Add("unset", new string[] { "Clear" });
            s_recommendedAlternateVerbs.Add("verify", new string[] { "Test" });

#if DEBUG
            foreach (KeyValuePair <string, string[]> entry in s_recommendedAlternateVerbs)
            {
                Dbg.Assert(!IsStandard(entry.Key), "prohibited verb is standard");
                foreach (string suggested in entry.Value)
                {
                    Dbg.Assert(IsStandard(suggested), "suggested verb is not standard");
                }
            }
#endif
        }
Ejemplo n.º 19
0
 BindParameters(Collection <CommandParameterInternal> parameters)
 {
     Dbg.Assert(false, "this method should be used");
     return(null);
 }
Ejemplo n.º 20
0
        /// <summary>
        /// Decode object.
        /// </summary>
        internal static object DecodeObject(object obj, Type type)
        {
            if (obj == null)
            {
                return(null);
            }

            Dbg.Assert(type != null, "Expected type != null");
            if (type == typeof(PSObject))
            {
                return(DecodePSObject(obj));
            }
            else if (type == typeof(ProgressRecord))
            {
                return(ProgressRecord.FromPSObjectForRemoting(PSObject.AsPSObject(obj)));
            }
            else if (IsKnownType(type))
            {
                return(obj);
            }
            else if (obj is SecureString)
            {
                return(obj);
            }
            else if (obj is PSCredential)
            {
                return(obj);
            }
            else if (obj is PSObject && type == typeof(PSCredential))
            {
                // BUGBUG: The following piece of code is a workaround
                // because custom serialization is busted. If rehydration
                // works correctly then PSCredential should be available
                PSObject     objAsPSObject = (PSObject)obj;
                PSCredential cred          = null;
                try
                {
                    cred = new PSCredential((String)objAsPSObject.Properties["UserName"].Value,
                                            (SecureString)objAsPSObject.Properties["Password"].Value);
                }
                catch (GetValueException)
                {
                    cred = null;
                }
                return(cred);
            }
            else if (obj is int && type.GetTypeInfo().IsEnum)
            {
                return(Enum.ToObject(type, (int)obj));
            }
            else if (obj is string && type == typeof(CultureInfo))
            {
                return(new CultureInfo((string)obj));
            }
            else if (obj is PSObject && type == typeof(Exception))
            {
                return(DecodeException((PSObject)obj));
            }
            else if (obj is PSObject && type == typeof(object[]))
            {
                return(DecodeObjectArray((PSObject)obj));
            }
            else if (obj is PSObject && type.IsArray)
            {
                return(DecodeArray((PSObject)obj, type));
            }
            else if (obj is PSObject && IsCollection(type))
            {
                return(DecodeCollection((PSObject)obj, type));
            }
            else if (obj is PSObject && IsDictionary(type))
            {
                return(DecodeDictionary((PSObject)obj, type));
            }
            else if (obj is PSObject && IsEncodingAllowedForClassOrStruct(type))
            {
                return(DecodeClassOrStruct((PSObject)obj, type));
            }
            else if (obj is PSObject && IsGenericIEnumerableOfInt(type))
            {
                // we cannot create an instance of interface type like IEnumerable
                // Since a Collection implements IEnumerable, falling back to use
                // that.
                return(DecodeCollection((PSObject)obj, typeof(Collection <int>)));
            }
            else if (obj is PSObject && type == typeof(RemoteHostCall))
            {
                return(RemoteHostCall.Decode((PSObject)obj));
            }
            else if (obj is PSObject && type == typeof(RemoteHostResponse))
            {
                return(RemoteHostResponse.Decode((PSObject)obj));
            }
            else
            {
                throw RemoteHostExceptions.NewRemoteHostDataDecodingNotSupportedException(type);
            }
        }
        /// <summary>
        /// This method is used by the input queue dispatching mechanism.
        /// It examines the data and takes appropriate actions.
        /// </summary>
        /// <param name="dataArg">
        /// The received client data.
        /// </param>
        /// <exception cref="ArgumentNullException">
        /// If the parameter is null.
        /// </exception>
        internal override void RaiseDataReceivedEvent(RemoteDataEventArgs dataArg)
        {
            if (dataArg == null)
            {
                throw PSTraceSource.NewArgumentNullException(nameof(dataArg));
            }

            RemoteDataObject <PSObject> rcvdData = dataArg.ReceivedData;

            RemotingTargetInterface targetInterface = rcvdData.TargetInterface;
            RemotingDataType        dataType        = rcvdData.DataType;

            Dbg.Assert(targetInterface == RemotingTargetInterface.Session, "targetInterface must be Session");

            switch (dataType)
            {
            case RemotingDataType.CreateRunspacePool:
            {
                // At this point, the negotiation is complete, so
                // need to import the clients public key
                CreateRunspacePoolReceived.SafeInvoke(this, dataArg);
            }

            break;

            case RemotingDataType.CloseSession:
                PSRemotingDataStructureException   reasonOfClose   = new PSRemotingDataStructureException(RemotingErrorIdStrings.ClientRequestedToCloseSession);
                RemoteSessionStateMachineEventArgs closeSessionArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.Close, reasonOfClose);
                _stateMachine.RaiseEvent(closeSessionArg);
                break;

            case RemotingDataType.SessionCapability:
                RemoteSessionCapability capability = null;
                try
                {
                    capability = RemotingDecoder.GetSessionCapability(rcvdData.Data);
                }
                catch (PSRemotingDataStructureException dse)
                {
                    // this will happen if expected properties are not
                    // received for session capability
                    throw new PSRemotingDataStructureException(RemotingErrorIdStrings.ServerNotFoundCapabilityProperties,
                                                               dse.Message, PSVersionInfo.GitCommitId, RemotingConstants.ProtocolVersion);
                }

                RemoteSessionStateMachineEventArgs capabilityArg = new RemoteSessionStateMachineEventArgs(RemoteSessionEvent.NegotiationReceived);
                capabilityArg.RemoteSessionCapability = capability;
                _stateMachine.RaiseEvent(capabilityArg);

                if (NegotiationReceived != null)
                {
                    RemoteSessionNegotiationEventArgs negotiationArg = new RemoteSessionNegotiationEventArgs(capability);
                    negotiationArg.RemoteData = rcvdData;
                    NegotiationReceived.SafeInvoke(this, negotiationArg);
                }

                break;

            case RemotingDataType.PublicKey:
            {
                string remotePublicKey = RemotingDecoder.GetPublicKey(rcvdData.Data);
                PublicKeyReceived.SafeInvoke(this, new RemoteDataEventArgs <string>(remotePublicKey));
            }

            break;

            default:
                throw new PSRemotingDataStructureException(RemotingErrorIdStrings.ReceivedUnsupportedAction, dataType);
            }
        }
Ejemplo n.º 22
0
        /// <summary>
        /// </summary>
        /// <param name="buffer"></param>
        /// <param name="offset"></param>
        /// <param name="count"></param>
        /// <returns></returns>
        public override int Read(byte[] buffer, int offset, int count)
        {
            int offSetToWriteTo = offset;
            int dataWritten     = 0;
            Collection <MemoryStream> memoryStreamsToDispose = new Collection <MemoryStream>();
            MemoryStream prevReadStream = null;

            lock (_syncObject)
            {
                // technically this should throw an exception..but remoting callstack
                // is optimized ie., we are not locking in every layer (in powershell)
                // to save on performance..as a result there may be cases where
                // upper layer is trying to add stuff and stream is disposed while
                // adding stuff.
                if (_isDisposed)
                {
                    return(0);
                }

                while (dataWritten < count)
                {
                    if (_readStream == null)
                    {
                        if (_queuedStreams.Count > 0)
                        {
                            _readStream = _queuedStreams.Dequeue();
                            if ((!_readStream.CanRead) || (prevReadStream == _readStream))
                            {
                                // if the stream is disposed CanRead returns false
                                // this will happen if a Write enqueues the stream
                                // and a Read reads the data without dequeuing
                                _readStream = null;
                                continue;
                            }
                        }
                        else
                        {
                            _readStream = _writeStream;
                        }

                        Dbg.Assert(_readStream.Length > 0, "Not enough data to read.");
                        _readOffSet = 0;
                    }

                    _readStream.Position = _readOffSet;
                    int result = _readStream.Read(buffer, offSetToWriteTo, count - dataWritten);
                    s_trace.WriteLine("Read {0} data from readstream: {1}", result, _readStream.GetHashCode());
                    dataWritten     += result;
                    offSetToWriteTo += result;
                    _readOffSet     += result;
                    _length         -= result;

                    // dispose only if we dont read from the current write stream.
                    if ((_readStream.Capacity == _readOffSet) && (_readStream != _writeStream))
                    {
                        s_trace.WriteLine("Adding readstream {0} to dispose collection.", _readStream.GetHashCode());
                        memoryStreamsToDispose.Add(_readStream);
                        prevReadStream = _readStream;
                        _readStream    = null;
                    }
                }
            }

            // Dispose the memory streams outside of the lock
            foreach (MemoryStream streamToDispose in memoryStreamsToDispose)
            {
                s_trace.WriteLine("Disposing stream: {0}", streamToDispose.GetHashCode());
                streamToDispose.Dispose();
            }

            return(dataWritten);
        }
Ejemplo n.º 23
0
        CreateCommandProcessor
        (
            ExecutionContext executionContext,
            bool addToHistory,
            CommandOrigin origin
        )
        {
            Dbg.Assert(executionContext != null, "Caller should verify the parameters");

            CommandProcessorBase commandProcessorBase;

            if (IsScript)
            {
                if ((executionContext.LanguageMode == PSLanguageMode.NoLanguage) &&
                    (origin == Automation.CommandOrigin.Runspace))
                {
                    throw InterpreterError.NewInterpreterException(CommandText, typeof(ParseException),
                                                                   null, "ScriptsNotAllowed", ParserStrings.ScriptsNotAllowed);
                }

                ScriptBlock scriptBlock = executionContext.Engine.ParseScriptBlock(CommandText, addToHistory);
                if (origin == Automation.CommandOrigin.Internal)
                {
                    scriptBlock.LanguageMode = PSLanguageMode.FullLanguage;
                }

                // If running in restricted language mode, verify that the parse tree represents on legitimate
                // constructions...
                switch (scriptBlock.LanguageMode)
                {
                case PSLanguageMode.RestrictedLanguage:
                    scriptBlock.CheckRestrictedLanguage(null, null, false);
                    break;

                case PSLanguageMode.FullLanguage:
                    // Interactive script commands are permitted in this mode.
                    break;

                case PSLanguageMode.ConstrainedLanguage:
                    // Constrained Language is checked at runtime.
                    break;

                default:
                    // This should never happen...
                    Diagnostics.Assert(false, "Invalid language mode was set when building a ScriptCommandProcessor");
                    throw new InvalidOperationException("Invalid language mode was set when building a ScriptCommandProcessor");
                }

                if (scriptBlock.UsesCmdletBinding)
                {
                    FunctionInfo functionInfo = new FunctionInfo(string.Empty, scriptBlock, executionContext);
                    commandProcessorBase = new CommandProcessor(functionInfo, executionContext,
                                                                _useLocalScope ?? false, fromScriptFile: false, sessionState: executionContext.EngineSessionState);
                }
                else
                {
                    commandProcessorBase = new DlrScriptCommandProcessor(scriptBlock,
                                                                         executionContext, _useLocalScope ?? false,
                                                                         origin,
                                                                         executionContext.EngineSessionState);
                }
            }
            else
            {
                // RestrictedLanguage / NoLanguage do not support dot-sourcing when CommandOrigin is Runspace
                if ((_useLocalScope.HasValue) && (!_useLocalScope.Value))
                {
                    switch (executionContext.LanguageMode)
                    {
                    case PSLanguageMode.RestrictedLanguage:
                    case PSLanguageMode.NoLanguage:
                        string message = StringUtil.Format(RunspaceStrings.UseLocalScopeNotAllowed,
                                                           "UseLocalScope",
                                                           PSLanguageMode.RestrictedLanguage.ToString(),
                                                           PSLanguageMode.NoLanguage.ToString());
                        throw new RuntimeException(message);

                    case PSLanguageMode.FullLanguage:
                        // Interactive script commands are permitted in this mode...
                        break;
                    }
                }

                commandProcessorBase = executionContext.CommandDiscovery.LookupCommandProcessor(CommandText, origin, _useLocalScope);
            }

            CommandParameterCollection parameters = Parameters;

            if (parameters != null)
            {
                bool isNativeCommand = commandProcessorBase is NativeCommandProcessor;
                foreach (CommandParameter publicParameter in parameters)
                {
                    CommandParameterInternal internalParameter = CommandParameter.ToCommandParameterInternal(publicParameter, isNativeCommand);
                    commandProcessorBase.AddParameter(internalParameter);
                }
            }

            string       helpTarget;
            HelpCategory helpCategory;

            if (commandProcessorBase.IsHelpRequested(out helpTarget, out helpCategory))
            {
                commandProcessorBase = CommandProcessorBase.CreateGetHelpCommandProcessor(
                    executionContext,
                    helpTarget,
                    helpCategory);
            }

            //Set the merge settings
            SetMergeSettingsOnCommandProcessor(commandProcessorBase);

            return(commandProcessorBase);
        }
Ejemplo n.º 24
0
        Show(PendingProgress pendingProgress)
        {
            Dbg.Assert(pendingProgress != null, "pendingProgress may not be null");

            _bufSize = _rawui.BufferSize;

            // In order to keep from slicing any CJK double-cell characters that might be present in the screen buffer,
            // we use the full width of the buffer.

            int maxWidth  = _bufSize.Width;
            int maxHeight = Math.Max(5, _rawui.WindowSize.Height / 3);

            string[] contents = pendingProgress.Render(maxWidth, maxHeight, _rawui);
            if (contents == null)
            {
                // There's nothing to show.

                Hide();
                _progressRegion = null;
                return;
            }

            // NTRAID#Windows OS Bugs-1061752-2004/12/15-sburns should read a skin setting here...

            BufferCell[,] newRegion = _rawui.NewBufferCellArray(contents, _ui.ProgressForegroundColor, _ui.ProgressBackgroundColor);
            Dbg.Assert(newRegion != null, "NewBufferCellArray has failed!");

            if (_progressRegion == null)
            {
                // we've never shown this pane before.

                _progressRegion = newRegion;
                Show();
            }
            else
            {
                // We have shown the pane before. We have to be smart about when we restore the saved region to minimize
                // flicker. We need to decide if the new contents will change the dimensions of the progress pane
                // currently being shown.  If it will, then restore the saved region, and show the new one.  Otherwise,
                // just blast the new one on top of the last one shown.

                // We're only checking size, not content, as we assume that the content will always change upon receipt
                // of a new ProgressRecord.  That's not guaranteed, of course, but it's a good bet.  So checking content
                // would usually result in detection of a change, so why bother?

                bool sizeChanged =
                    (newRegion.GetLength(0) != _progressRegion.GetLength(0)) ||
                    (newRegion.GetLength(1) != _progressRegion.GetLength(1))
                    ? true : false;

                _progressRegion = newRegion;

                if (sizeChanged)
                {
                    if (IsShowing)
                    {
                        Hide();
                    }
                    Show();
                }
                else
                {
                    _rawui.SetBufferContents(_location, _progressRegion);
                }
            }
        }
        /// <summary>
        /// This method contains all the logic for handling the state machine
        /// for key exchange. All the different scenarios are covered in this
        /// </summary>
        /// <param name="sender">sender of this event, unused</param>
        /// <param name="eventArgs">event args</param>
        private void DoKeyExchange(object sender, RemoteSessionStateMachineEventArgs eventArgs)
        {
            //There are corner cases with disconnect that can result in client receiving outdated key exchange packets
            //***TODO*** Deal with this on the client side. Key exchange packets should have additional information
            //that identify the context of negotiation. Just like callId in SetMax and SetMinRunspaces messages
            Dbg.Assert(_state >= RemoteSessionState.Established,
                       "Key Receiving can only be raised after reaching the Established state");

            switch (eventArgs.StateEvent)
            {
            case RemoteSessionEvent.KeyReceived:
            {
                //does the server ever start key exchange process??? This may not be required
                if (_state == RemoteSessionState.EstablishedAndKeyRequested)
                {
                    // reset the timer
                    Timer tmp = Interlocked.Exchange(ref _keyExchangeTimer, null);
                    if (tmp != null)
                    {
                        tmp.Dispose();
                    }
                }

                // the key import would have been done
                // set state accordingly
                SetState(RemoteSessionState.EstablishedAndKeyReceived, eventArgs.Reason);

                // you need to send an encrypted session key to the client
                _session.SendEncryptedSessionKey();
            }
            break;

            case RemoteSessionEvent.KeySent:
            {
                if (_state == RemoteSessionState.EstablishedAndKeyReceived)
                {
                    // key exchange is now complete
                    SetState(RemoteSessionState.EstablishedAndKeyExchanged, eventArgs.Reason);
                }
            }
            break;

            case RemoteSessionEvent.KeyRequested:
            {
                if ((_state == RemoteSessionState.Established) || (_state == RemoteSessionState.EstablishedAndKeyExchanged))
                {
                    // the key has been sent set state accordingly
                    SetState(RemoteSessionState.EstablishedAndKeyRequested, eventArgs.Reason);

                    // start the timer
                    _keyExchangeTimer = new Timer(HandleKeyExchangeTimeout, null, BaseTransportManager.ServerDefaultKeepAliveTimeoutMs, Timeout.Infinite);
                }
            }
            break;

            case RemoteSessionEvent.KeyReceiveFailed:
            {
                if ((_state == RemoteSessionState.Established) || (_state == RemoteSessionState.EstablishedAndKeyExchanged))
                {
                    return;
                }

                DoClose(this, eventArgs);
            }
            break;

            case RemoteSessionEvent.KeySendFailed:
            {
                DoClose(this, eventArgs);
            }
            break;
            }
        }
Ejemplo n.º 26
0
        /// <summary>
        /// Handle the object obtained from an ObjectStream's reader
        /// based on its type.
        /// </summary>
        /// <param name="cmdlet">Cmdlet to use for outputting the object.</param>
        /// <param name="overrideInquire">Used by Receive-Job to suppress inquire preference.</param>
        public void WriteStreamObject(Cmdlet cmdlet, bool overrideInquire = false)
        {
            if (cmdlet != null)
            {
                switch (this.ObjectType)
                {
                case PSStreamObjectType.Output:
                {
                    cmdlet.WriteObject(this.Value);
                }

                break;

                case PSStreamObjectType.Error:
                {
                    ErrorRecord errorRecord = (ErrorRecord)this.Value;
                    errorRecord.PreserveInvocationInfoOnce = true;
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteError(errorRecord, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.Debug:
                {
                    string            debug             = (string)Value;
                    DebugRecord       debugRecord       = new DebugRecord(debug);
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteDebug(debugRecord, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.Warning:
                {
                    string            warning           = (string)Value;
                    WarningRecord     warningRecord     = new WarningRecord(warning);
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteWarning(warningRecord, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.Verbose:
                {
                    string            verbose           = (string)Value;
                    VerboseRecord     verboseRecord     = new VerboseRecord(verbose);
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteVerbose(verboseRecord, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.Progress:
                {
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteProgress((ProgressRecord)Value, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.Information:
                {
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.WriteInformation((InformationRecord)Value, overrideInquire);
                    }
                }

                break;

                case PSStreamObjectType.WarningRecord:
                {
                    WarningRecord     warningRecord     = (WarningRecord)Value;
                    MshCommandRuntime mshCommandRuntime = cmdlet.CommandRuntime as MshCommandRuntime;
                    if (mshCommandRuntime != null)
                    {
                        mshCommandRuntime.AppendWarningVarList(warningRecord);
                    }
                }

                break;

                case PSStreamObjectType.MethodExecutor:
                {
                    Dbg.Assert(this.Value is ClientMethodExecutor,
                               "Expected psstreamObject.value is ClientMethodExecutor");
                    ClientMethodExecutor methodExecutor = (ClientMethodExecutor)Value;
                    methodExecutor.Execute(cmdlet);
                }

                break;

                case PSStreamObjectType.BlockingError:
                {
                    CmdletMethodInvoker <object> methodInvoker = (CmdletMethodInvoker <object>)Value;
                    InvokeCmdletMethodAndWaitForResults(methodInvoker, cmdlet);
                }

                break;

                case PSStreamObjectType.ShouldMethod:
                {
                    CmdletMethodInvoker <bool> methodInvoker = (CmdletMethodInvoker <bool>)Value;
                    InvokeCmdletMethodAndWaitForResults(methodInvoker, cmdlet);
                }

                break;

                case PSStreamObjectType.Exception:
                {
                    Exception e = (Exception)Value;
                    throw e;
                }
                }
            }
            else if (ObjectType == PSStreamObjectType.Exception)
            {
                Exception e = (Exception)Value;
                throw e;
            }
        }
Ejemplo n.º 27
0
        /// <summary>
        /// Internal proxy for EnterNestedPrompt
        /// </summary>
        /// <param name="callingCommand"></param>
        ///
        internal void EnterNestedPrompt(InternalCommand callingCommand)
        {
            // Ensure we are in control of the pipeline
            LocalRunspace localRunspace = null;

            // This needs to be in a try / catch, since the LocalRunspace cast
            // tries to verify that the host supports interactive sessions.
            // Tests hosts do not.
            try { localRunspace = this.Runspace as LocalRunspace; }
            catch (PSNotImplementedException) { }

            if (localRunspace != null)
            {
                Pipeline currentlyRunningPipeline = this.Runspace.GetCurrentlyRunningPipeline();

                if ((currentlyRunningPipeline != null) &&
                    (currentlyRunningPipeline == localRunspace.PulsePipeline))
                {
                    throw new InvalidOperationException();
                }
            }

            // NTRAID#Windows OS Bugs-986407-2004/07/29 When kumarp has done the configuration work in the engine, it
            // should include setting a bit that indicates that the initialization is complete, and code should be
            // added here to throw an exception if this function is called before that bit is set.

            if (NestedPromptCount < 0)
            {
                Dbg.Assert(false, "nested prompt counter should never be negative.");
                throw PSTraceSource.NewInvalidOperationException(
                          InternalHostStrings.EnterExitNestedPromptOutOfSync);
            }

            // Increment our nesting counter.  When we set the value of the variable, we will replace any existing variable
            // of the same name.  This is good, as any existing value is either 1) ours, and we have claim to replace it, or
            // 2) is a squatter, and we have claim to clobber it.

            ++NestedPromptCount;
            Context.SetVariable(SpecialVariables.NestedPromptCounterVarPath, NestedPromptCount);

            // On entering a subshell, save and reset values of certain bits of session state

            PromptContextData contextData = new PromptContextData();

            contextData.SavedContextData = Context.SaveContextData();
            contextData.SavedCurrentlyExecutingCommandVarValue = Context.GetVariableValue(SpecialVariables.CurrentlyExecutingCommandVarPath);
            contextData.SavedPSBoundParametersVarValue         = Context.GetVariableValue(SpecialVariables.PSBoundParametersVarPath);
            contextData.RunspaceAvailability = this.Context.CurrentRunspace.RunspaceAvailability;
            contextData.LanguageMode         = Context.LanguageMode;

            PSPropertyInfo commandInfoProperty = null;
            PSPropertyInfo stackTraceProperty  = null;
            object         oldCommandInfo      = null;
            object         oldStackTrace       = null;

            if (callingCommand != null)
            {
                Dbg.Assert(callingCommand.Context == Context, "I expect that the contexts should match");

                // Populate $CurrentlyExecutingCommand to facilitate debugging.  One of the gotchas is that we are going to want
                // to expose more and more debug info. We could just populate more and more local variables but that is probably
                // a lousy approach as it pollutes the namespace.  A better way to do it is to add NOTES to the variable value
                // object.

                PSObject newValue = PSObject.AsPSObject(callingCommand);

                commandInfoProperty = newValue.Properties["CommandInfo"];
                if (commandInfoProperty == null)
                {
                    newValue.Properties.Add(new PSNoteProperty("CommandInfo", callingCommand.CommandInfo));
                }
                else
                {
                    oldCommandInfo            = commandInfoProperty.Value;
                    commandInfoProperty.Value = callingCommand.CommandInfo;
                }

#if !CORECLR //TODO:CORECLR StackTrace not in CoreCLR
                stackTraceProperty = newValue.Properties["StackTrace"];
                if (stackTraceProperty == null)
                {
                    newValue.Properties.Add(new PSNoteProperty("StackTrace", new System.Diagnostics.StackTrace()));
                }
                else
                {
                    oldStackTrace            = stackTraceProperty.Value;
                    stackTraceProperty.Value = new System.Diagnostics.StackTrace();
                }
#endif

                Context.SetVariable(SpecialVariables.CurrentlyExecutingCommandVarPath, newValue);
            }

            _contextStack.Push(contextData);
            Dbg.Assert(_contextStack.Count == NestedPromptCount, "number of saved contexts should equal nesting count");

            Context.PSDebugTraceStep  = false;
            Context.PSDebugTraceLevel = 0;
            Context.ResetShellFunctionErrorOutputPipe();

            // Lock down the language in the nested prompt
            if (Context.HasRunspaceEverUsedConstrainedLanguageMode)
            {
                Context.LanguageMode = PSLanguageMode.ConstrainedLanguage;
            }

            this.Context.CurrentRunspace.UpdateRunspaceAvailability(RunspaceAvailability.AvailableForNestedCommand, true);

            try
            {
                _externalHostRef.Value.EnterNestedPrompt();
            }
            catch
            {
                // So where things really go south is this path; which is possible for hosts (like our ConsoleHost)
                // that don't return from EnterNestedPrompt immediately.
                //      EnterNestedPrompt() starts
                //          ExitNestedPrompt() called
                //          EnterNestedPrompt throws

                ExitNestedPromptHelper();
                throw;
            }
            finally
            {
                if (commandInfoProperty != null)
                {
                    commandInfoProperty.Value = oldCommandInfo;
                }
                if (stackTraceProperty != null)
                {
                    stackTraceProperty.Value = oldStackTrace;
                }
            }

            Dbg.Assert(NestedPromptCount >= 0, "nestedPromptCounter should be greater than or equal to 0");
        }
        /// <summary>
        /// Handler which handles transport errors.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        internal void HandleTransportError(object sender, TransportErrorOccuredEventArgs e)
        {
            Dbg.Assert(e != null, "HandleTransportError expects non-null eventargs");
            // handle uri redirections
            PSRemotingTransportRedirectException redirectException = e.Exception as PSRemotingTransportRedirectException;

            if ((redirectException != null) && (_maxUriRedirectionCount > 0))
            {
                Exception exception = null;

                try
                {
                    // honor max redirection count given by the user.
                    _maxUriRedirectionCount--;
                    PerformURIRedirection(redirectException.RedirectLocation);
                    return;
                }
                catch (ArgumentNullException argumentException)
                {
                    exception = argumentException;
                }
                catch (UriFormatException uriFormatException)
                {
                    exception = uriFormatException;
                }
                // if we are here, there must be an exception constructing a uri
                if (exception != null)
                {
                    PSRemotingTransportException newException =
                        new PSRemotingTransportException(PSRemotingErrorId.RedirectedURINotWellFormatted, RemotingErrorIdStrings.RedirectedURINotWellFormatted,
                                                         _session.Context.RemoteAddress.OriginalString,
                                                         redirectException.RedirectLocation);
                    newException.TransportMessage = e.Exception.TransportMessage;
                    e.Exception = newException;
                }
            }

            RemoteSessionEvent sessionEvent = RemoteSessionEvent.ConnectFailed;

            switch (e.ReportingTransportMethod)
            {
            case TransportMethodEnum.CreateShellEx:
                sessionEvent = RemoteSessionEvent.ConnectFailed;
                break;

            case TransportMethodEnum.SendShellInputEx:
            case TransportMethodEnum.CommandInputEx:
                sessionEvent = RemoteSessionEvent.SendFailed;
                break;

            case TransportMethodEnum.ReceiveShellOutputEx:
            case TransportMethodEnum.ReceiveCommandOutputEx:
                sessionEvent = RemoteSessionEvent.ReceiveFailed;
                break;

            case TransportMethodEnum.CloseShellOperationEx:
                sessionEvent = RemoteSessionEvent.CloseFailed;
                break;

            case TransportMethodEnum.DisconnectShellEx:
                sessionEvent = RemoteSessionEvent.DisconnectFailed;
                break;

            case TransportMethodEnum.ReconnectShellEx:
                sessionEvent = RemoteSessionEvent.ReconnectFailed;
                break;
            }

            RemoteSessionStateMachineEventArgs errorArgs =
                new RemoteSessionStateMachineEventArgs(sessionEvent, e.Exception);

            _stateMachine.RaiseEvent(errorArgs);
        }
Ejemplo n.º 29
0
        private void childJob_StateChanged(object sender, JobStateEventArgs e)
        {
            Dbg.Assert(sender != null, "Only our internal implementation of Job should raise this event and it should make sure that sender != null");
            Dbg.Assert(sender is Job, "Only our internal implementation of Job should raise this event and it should make sure that sender is Job");
            var childJob = (Job)sender;

            if ((e.PreviousJobStateInfo.State == JobState.Blocked) && (e.JobStateInfo.State != JobState.Blocked))
            {
                bool parentJobGotUnblocked = false;
                lock (_lockObject)
                {
                    _countOfBlockedChildJobs--;
                    if (_countOfBlockedChildJobs == 0)
                    {
                        parentJobGotUnblocked = true;
                    }
                }
                if (parentJobGotUnblocked)
                {
                    this.SetJobState(JobState.Running);
                }
            }

            switch (e.JobStateInfo.State)
            {
            // intermediate states
            case JobState.Blocked:
                lock (_lockObject)
                {
                    _countOfBlockedChildJobs++;
                }
                this.SetJobState(JobState.Blocked);
                break;

            // 3 finished states
            case JobState.Failed:
            case JobState.Stopped:
            case JobState.Completed:
                childJob.StateChanged -= childJob_StateChanged;
                this.MakeRoomForRunningOtherJobs(childJob);
                lock (_lockObject)
                {
                    if (e.JobStateInfo.State == JobState.Failed)
                    {
                        _countOfFailedChildJobs++;
                    }
                    else if (e.JobStateInfo.State == JobState.Stopped)
                    {
                        _countOfStoppedChildJobs++;
                    }
                    else if (e.JobStateInfo.State == JobState.Completed)
                    {
                        _countOfSuccessfullyCompletedChildJobs++;
                    }

                    if (_actionsForUnblockingChildAdditions.Count > 0)
                    {
                        Action a = _actionsForUnblockingChildAdditions.Dequeue();
                        if (a != null)
                        {
                            a();
                        }
                    }

                    if (_cmdletMode)
                    {
                        foreach (PSStreamObject streamObject in childJob.Results.ReadAll())
                        {
                            this.Results.Add(streamObject);
                        }
                        this.ChildJobs.Remove(childJob);
                        _setOfChildJobsThatCanAddMoreChildJobs.Remove(childJob.InstanceId);
                        childJob.Dispose();
                    }
                }
                this.ReportProgress(minimizeFrequentUpdates: !this.IsThrottlingJobCompleted);
                break;

            default:
                // do nothing
                break;
            }

            this.FigureOutIfThrottlingJobIsCompleted();
        }
Ejemplo n.º 30
0
 /// <summary>
 /// Handle remote host response from client.
 /// </summary>
 internal void HandleRemoteHostResponseFromClient(RemoteHostResponse remoteHostResponse)
 {
     Dbg.Assert(remoteHostResponse != null, "Expected remoteHostResponse != null");
     _serverDispatchTable.SetResponse(remoteHostResponse.CallId, remoteHostResponse);
 }