System.IO.FileSystemWatcher.ReadDirectoryChangesCallback C# (CSharp) Method

ReadDirectoryChangesCallback() private method

Callback invoked when an asynchronous read on the directory handle completes.
private ReadDirectoryChangesCallback ( uint errorCode, uint numBytes, NativeOverlapped overlappedPointer ) : void
errorCode uint
numBytes uint
overlappedPointer NativeOverlapped
return void
        private unsafe void ReadDirectoryChangesCallback(uint errorCode, uint numBytes, NativeOverlapped* overlappedPointer)
        {
            AsyncReadState state = (AsyncReadState)ThreadPoolBoundHandle.GetNativeOverlappedState(overlappedPointer);
            try
            {
                if (IsHandleInvalid(state.DirectoryHandle))
                    return;

                if (errorCode != 0)
                {
                    // Inside a service the first completion status is false;
                    // need to monitor again.

                    const int ERROR_OPERATION_ABORTED = 995;
                    if (errorCode != ERROR_OPERATION_ABORTED)
                    {
                        OnError(new ErrorEventArgs(new Win32Exception((int)errorCode)));
                        EnableRaisingEvents = false;
                    }
                    return;
                }

                // Ignore any events that occurred before this "session",
                // so we don't get changed or error events after we
                // told FSW to stop.  Even with this check, though, there's a small 
                // race condition, as immediately after we do the check, raising
                // events could be disabled.
                if (state.Session != Volatile.Read(ref _currentSession))
                    return;

                if (numBytes == 0)
                {
                    NotifyInternalBufferOverflowEvent();
                }
                else
                {
                    ParseEventBufferAndNotifyForEach(state.Buffer);
                }
            }
            finally
            {
                // Clean up state associated with this one iteration
                state.ThreadPoolBinding.FreeNativeOverlapped(overlappedPointer);

                // Then call Monitor again to either start the next iteration or
                // clean up the whole operation.
                Monitor(state);
            }
        }