开发者

Millisecond-Accurate Scheduling of Future Events in C++/CLI

I need to create a C++/CLI mixed assembly that can schedule future calls into a native DLL with millisecond accuracy. 开发者_StackOverflow社区

This will, of course, mean setting a timer (what kind?) for a millisecond or three beforehand, then spinning until the moment and calling the native DLL function.

Based on what I've read, I would guess that the callback that the timer calls will need to be native to make sure there are no thunks or GC to delay handling the timer callback.

Will the entire thread or process need to be native and CLR-free, though, or can this be done just as accurately with #pragma unmanaged or setting one file of the assembly to compile as native?

If so, how?

If there is indeed no way to do this in mixed-mode C++/CLI, what would be the easiest way to set up an app/thread (ie, DLL or exe?) to handle it and to get the data back and forth between the native and managed threads/apps?


You do need the entire thread to be CLR-free. As soon as any managed code runs on the thread, it will get added to the CLR's list of threads to suspend during collection.

Your last question, though, suggests that you have no clue about multithreading. There is no correspondence between threads and DLLs. A DLL can have many threads, and each thread can run code from many DLLs (in fact, always does, if you count Windows DLLs). You're also not using the phrase "critical section" in the usual way.

A mixed-mode C++/CLI assembly can contain a native-only thread (start it using the native CreateThread call, passing a native thread procedure, and don't call any managed code directly or indirectly from that thread). Your life will be a little easier if you write the code for the native thread in one or more files set to compile without /clr, not having managed code visible makes it easier to avoid calling it, although beware of function pointers which might be wrapping managed delegates.

Beyond that, use lock-free synchronization, e.g. SList, or your native thread could end up waiting for a lock held on a mixed-mode thread which has been suspended for garbage collection. Among other things this means not using any of the standard shared allocators, because they use locking internally. Some lock-free allocators do exist though.

EDIT: Function pointers which wrap managed delegates are created by calling Marshal::GetDelegateForFunctionPointer. After that, they act just like pointers to native functions (it is possible to tell them apart) and using the function call operator on such a pointer will cause managed code to run on the sensitive thread. In most cases this won't be a problem, just make sure if you are using delegates as a shortcut to produce callbacks to managed code, that you do so from the mixed thread and not the one you intend to be native-only.

In general, you'll probably want some sort of purely native message passing scheme to exchange data. The mixed thread can make whatever native calls are necessary, you can mix native and managed code on all your other threads, just keep the time-sensitive one native-only.

All thunking should occur on the mixed thread, and it won't delay the time-sensitive native thread unless the mixed thread is holding a lock that the native thread needs. Hence my suggestion to use non-locking data exchange.


It can not be done in windows at all - sorry. Get an OS that fits your requirements.

  • Normal timers in windows havve a 10ms accuracy.
  • Even if you get it working withh high performance timers, there are no accuracy guarantees in windows that the call will be honoured within a specific time - your 1ms call may come in 5ms late.

What you need / seem to need is a real time operating system.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜