Sign Up

Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.

Have an account? Sign In

Have an account? Sign In Now

Sign In

Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.

Sign Up Here

Forgot Password?

Don't have account, Sign Up Here

Forgot Password

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

Have an account? Sign In Now

You must login to ask a question.

Forgot Password?

Need An Account, Sign Up Here

Please briefly explain why you feel this question should be reported.

Please briefly explain why you feel this answer should be reported.

Please briefly explain why you feel this user should be reported.

Sign InSign Up

The Archive Base

The Archive Base Logo The Archive Base Logo

The Archive Base Navigation

  • Home
  • SEARCH
  • About Us
  • Blog
  • Contact Us
Search
Ask A Question

Mobile menu

Close
Ask a Question
  • Home
  • Add group
  • Groups page
  • Feed
  • User Profile
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Buy Points
  • Users
  • Help
  • Buy Theme
  • SEARCH
Home/ Questions/Q 3842114
In Process

The Archive Base Latest Questions

Editorial Team
  • 0
Editorial Team
Asked: May 19, 20262026-05-19T15:44:50+00:00 2026-05-19T15:44:50+00:00

Note first of all that this question is not tagged winforms or wpf or

  • 0

Note first of all that this question is not tagged winforms or wpf or anything else GUI-specific. This is intentional, as you will see shortly.

Second, sorry if this question is somewhat long. I try to pull together various bits of information floating around here and there so as to also provide valuable information. My question, however, is right under “What I would like to know”.

I’m on a mission to finally understand the various ways offered by .NET to invoke a delegate on a specific thread.


What I would like to know:

  • I am looking for the most general way possible (that is not Winforms or WPF-specific) to invoke delegates on specific threads.

  • Or, phrased differently: I would be interested if, and how, the various ways to do this (such as via WPF’s Dispatcher) make use of each other; that is, if there is one common mechanism for cross-thread delegate invocation that’s used by all the others.


What I know already:

  • There’s many classes related to this topic; among them:

    • SynchronizationContext (in System.Threading)
      If I had to guess, that would be the most basic one; although I don’t understand what exactly it does, nor how it is used.

    • AsyncOperation & AsyncOperationManager (in System.ComponentModel)
      These seem to be wrappers around SynchronizationContext. No clue how to use them.

    • WindowsFormsSynchronizationContext (in System.Windows.Forms)
      A subclass of SynchronizationContext.

    • ISynchronizeInvoke (in System.ComponentModel)
      Used by Windows Forms. (The Control class implements this. If I’d have to guess, I’d say this implementation makes use of WindowsFormsSynchronizationContext.)

    • Dispatcher &DispatcherSynchronizationContext (in System.Windows.Threading)
      Seems like the latter is another subclass of SynchronizationContext, and the former delegates to it.

  • Some threads have their own message loop, along with a message queue.

    (The MSDN page About Messages and Message Queues has some introductory background information on how message loops work at the system level, i.e. message queues as the Windows API.)

    I can see how one would implement cross-thread invocation for threads with a message queue. Using the Windows API, you would put a message into a specific thread’s message queue via PostThreadMessage that contains an instruction to call some delegate. The message loop — which runs on that thread — will eventually get to that message, and the delegate will be called.

    From what I’ve read on MSDN, a thread doesn’t automatically have its own message queue. A message queue will become available e.g. when a thread has created a window. Without a message queue, it doesn’t make sense for a thread to have a message loop.

    So, is cross-thread delegate invocation possible at all when the target thread has no message loop? Let’s say, in a .NET console application? (Judging from the answers to this question, I suppose it’s indeed impossible with console apps.)

  • 1 1 Answer
  • 0 Views
  • 0 Followers
  • 0
Share
  • Facebook
  • Report

Leave an answer
Cancel reply

You must login to add an answer.

Forgot Password?

Need An Account, Sign Up Here

1 Answer

  • Voted
  • Oldest
  • Recent
  • Random
  1. Editorial Team
    Editorial Team
    2026-05-19T15:44:51+00:00Added an answer on May 19, 2026 at 3:44 pm

    Sorry for posting such a long answer. But I thought it worth explaining what exactly is going on.

    A-ha! I think I’ve got it figured out. The most generic way of invoking a delegate on a specific thread indeed seems to be the SynchronizationContext class.

    First, the .NET framework does not provide a default means to simply “send” a delegate to any thread such that it’ll get executed there immediately. Obviously, this cannot work, because it would mean “interrupting” whatever work that thread would be doing at the time. Therefore, the target thread itself decides how, and when, it will “receive” delegates; that is, this functionality has to be provided by the programmer.

    So a target thread needs some way of “receiving” delegates. This can be done in many different ways. One easy mechanism is for the thread to always return to some loop (let’s call it the “message loop”) where it will look at a queue. It’ll work off whatever is in the queue. Windows natively works like this when it comes to UI-related stuff.

    In the following, I’ll demonstrate how to implement a message queue and a SynchronizationContext for it, as well as a thread with a message loop. Finally, I’ll demonstrate how to invoke a delegate on that thread.


    Example:

    Step 1. Let’s first create a SynchronizationContext class that’ll be used together with the target thread’s message queue:

    class QueueSyncContext : SynchronizationContext
    {
        private readonly ConcurrentQueue<SendOrPostCallback> queue;
    
        public QueueSyncContext(ConcurrentQueue<SendOrPostCallback> queue)
        {
            this.queue = queue;
        }
    
        public override void Post(SendOrPostCallback d, object state)
        {
            queue.Enqueue(d);
        }
    
        // implementation for Send() omitted in this example for simplicity's sake.
    }
    

    Basically, this doesn’t do more than adding all delegates that are passed in via Post to a user-provided queue. (Post is the method for asynchronous invocations. Send would be for synchronous invocations. I’m omitting the latter for now.)

    Step 2. Let’s now write the code for a thread Z that waits for delegates d to arrive:

    SynchronizationContext syncContextForThreadZ = null;
    
    void MainMethodOfThreadZ()
    {
        // this will be used as the thread's message queue:
        var queue = new ConcurrentQueue<PostOrCallDelegate>();
    
        // set up a synchronization context for our message processing:
        syncContextForThreadZ = new QueueSyncContext(queue);
        SynchronizationContext.SetSynchronizationContext(syncContextForThreadZ);
    
        // here's the message loop (not efficient, this is for demo purposes only:)
        while (true)
        {
            PostOrCallDelegate d = null;
            if (queue.TryDequeue(out d))
            {
                d.Invoke(null);
            }
        }
    }
    

    Step 3. Thread Z needs to be started somewhere:

    new Thread(new ThreadStart(MainMethodOfThreadZ)).Start();
    

    Step 4. Finally, back on some other thread A, we want to send a delegate to thread Z:

    void SomeMethodOnThreadA()
    {
        // thread Z must be up and running before we can send delegates to it:
        while (syncContextForThreadZ == null) ;
    
        syncContextForThreadZ.Post(_ =>
            {
                Console.WriteLine("This will run on thread Z!");
            },
            null);
    }
    

    The nice thing about this is that SynchronizationContext works, no matter whether you’re in a Windows Forms application, in a WPF application, or in a multi-threaded console application of your own devising. Both Winforms and WPF provide and install suitable SynchronizationContexts for their main/UI thread.

    The general procedure for invoking a delegate on a specific thread is the following:

    • You must capture the target thread’s (Z‘s) SynchronizationContext, so that you can Send (synchronously) or Post (asynchronously) a delegate to that thread. The way how to do this is to store the synchronization context returned by SynchronizationContext.Current while you’re on the target thread Z. (This synchronization context must have previously been registered on/by thread Z.) Then store that reference somewhere where it’s accessible by thread A.

    • While on thread A, you can use the captured synchronization context to send or post any delegate to thread Z: zSyncContext.Post(_ => { ... }, null);

    • 0
    • Reply
    • Share
      Share
      • Share on Facebook
      • Share on Twitter
      • Share on LinkedIn
      • Share on WhatsApp
      • Report

Sidebar

Related Questions

Note This is not a REBOL-specific question. You can answer it in any language.
NOTE: I am not exactly sure how to title or tag this question, so
First of all, I don't think this question is a duplicate of Detect 64bit
(NOTE: This question is not about escaping queries, it's about escaping results) I'm using
First of all, i'm a Graphic designer so please ignore if this programming question
First of all, this question is in regards to PHP and MySQL I have
The first thing i would like to say is that this is not exactly
NOTE: I am not set on using VI, it is just the first thing
NOTE: XMLIgnore is NOT the answer! OK, so following on from my question on
Note: Originally this question was asked for PostgreSQL, however, the answer applies to almost

Explore

  • Home
  • Add group
  • Groups page
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Users
  • Help
  • SEARCH

Footer

© 2021 The Archive Base. All Rights Reserved
With Love by The Archive Base

Insert/edit link

Enter the destination URL

Or link to existing content

    No search term specified. Showing recent items. Search or use up and down arrow keys to select an item.