A long-running task, whether running in a dedicated background thread or not, may want to communicate with the caller in one of two ways:
To report progress (with a BackgroundWorker this corresponds to calling BackgroundWorker.ReportProgress)
To check if cancellation has been requested (with a BackgroundWorker this corresponds to examining the CancellationPending property).
It's sometimes useful for a long-running process to be able to communicate with the caller in this way without knowing or caring if it is being run from a BackgroundWorker. I have therefore created an interface IProgress which abstracts this functionality with a method ReportProgress and a property CancellationPending. I have an enhanced version of BackgroundWorker that implements this interface, and also alternative implementations that do not use a BackgroundWorker.
For example, a console application might run a long-running task in the foreground. Its implementation of IProgress.ReportProgress could e.g. use Console.WriteLine if running in verbose mode. Its implementation of IProgress.CancellationPending could check if CTRL-C has been pressed. The same long-running task could be called from this console application and from a WinForms application that uses a BackgroundWorker.
Personally I think an abstraction like this should have been included in the .NET Framework when BackgroundWorker was designed.