Bonjour,
j'ai un service .net qui peut héberger des drivers, chaque driver étant chargé à la manière d'un plugin.
Chaque interaction est géré par un thread de messagerie taggé comme STA et background, qui appelle les méthodes qui vont bien sur le driver.
Je rencontre un souci avec un des drivers. Le driver a besoin d'un context graphique (ActiveX en dessous...), géré par la classe BackStaDispatcher dont la construction est :
L'appel au get sur System.Windows.Threading.Dispatcher.CurrentDispatcher; m'envoie sur les roses, si je démarre mon logiciel en tant que service Windows. Si je le lance en mode console, c'est cool (and wo, WTF ?).
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50 private static BackStaDispatcher _BackStaDispatcher = null; private static System.Windows.Threading.Dispatcher _dispatcher; private System.Threading.Thread _thread = null; private static int _Cpt = 0; private System.Windows.Window _Window = null; private System.Threading.AutoResetEvent are = null; public static BackStaDispatcher GetInstance() { if (_BackStaDispatcher == null) _BackStaDispatcher = new BackStaDispatcher("Another Sta dispatcher"); return _BackStaDispatcher; } private BackStaDispatcher(string name) { Console.WriteLine("BackStaDispatcher.ctor"); are = new System.Threading.AutoResetEvent(false); _thread = new System.Threading.Thread((System.Threading.ThreadStart)delegate { // Create our context, and install it: System.Threading.SynchronizationContext.SetSynchronizationContext( new System.Windows.Threading.DispatcherSynchronizationContext( System.Windows.Threading.Dispatcher.CurrentDispatcher)); _dispatcher = System.Windows.Threading.Dispatcher.CurrentDispatcher; _Window = new System.Windows.Window(); // When the window closes, shut down the dispatcher _Window.Closed += (s, e) => System.Windows.Threading.Dispatcher.CurrentDispatcher.BeginInvokeShutdown(System.Windows.Threading.DispatcherPriority.Background); _Window.Loaded += new System.Windows.RoutedEventHandler(_Window_Loaded); _Window.Show(); _Cpt++; System.Windows.Threading.Dispatcher.Run(); _Cpt--; Console.WriteLine("BackStaDispatcher FIN Dispatcher RUN _Cpt=" + _Cpt); }); _thread.Name = string.Format("BackStaDispatcher({0})", name); _thread.SetApartmentState(System.Threading.ApartmentState.STA); _thread.IsBackground = true; _thread.Start(); are.WaitOne(); } ... Invoke, BeginInvoke et autres joyeusetés....
Symptômes : le process crash sur une erreur Win32, loggée dans le journal d'événements comme suit :
J'en perds mon latin, si un pro des routines internes windowsienne pouvait venir à mon secours, je lui en serai reconnaissant.The process was terminated due to an unhandled exception.
Exception Info: System.ComponentModel.Win32Exception
Stack:
at MS.Win32.UnsafeNativeMethods.RegisterClassEx(WNDCLASSEX_D)
at MS.Win32.HwndWrapper..ctor(Int32, Int32, Int32, Int32, Int32, Int32, Int32, System.String, IntPtr, MS.Win32.HwndWrapperHook[])
at System.Windows.Threading.Dispatcher..ctor()
at System.Windows.Threading.Dispatcher.get_CurrentDispatcher()
at Driver.BackStaDispatcher.<.ctor>b__0()
at System.Threading.ThreadHelper.ThreadStart_Context(System.Object)
Partager