J'ai besoin de pomper des messages COM en attendant qu'un événement répare un blocage. Il est préférable de pomper le moins possible de messages juste pour traiter cet appel COM. Le meilleur candidat pour ce rôle est CoWaitForMultipleHandles mais starting from Vista il pompe WM_PAINT en plus des messages COM. Le pompage de WM_PAINT est trop dangereux pour moi du point de vue de la rentrée et je ne veux pas installer une base de données de shim personnalisée comme solution à ce problème. J'essaie de pomper manuellement les messages COM envoyés à la fenêtre des messages masqués uniquement.Comment pompe messages COM dans STA sans pompage WM_PAINT?
J'ai trouvé deux façons d'obtenir HWND de la fenêtre cachée:
((SOleTlsData *) NtCurrentTeb()->ReservedForOle)->hwndSTA
à l'aide de .NET ntinfo.h de base. Cela semble être une solution non documentée et pas fiable en termes de changements futurs.- Trouver la fenêtre de
OleMainThreadWndClass
comme suggéré dans this question. Le problème est queCoInitialize
ne crée pas la fenêtre. Il est créé plus tard lors du premier appel inter-appartement qui peut ou peut ne pas arriver dans ma demande. Exécuter la boucle de recherche chaque fois que j'ai besoin de HWND est mauvais du point de vue des performances, mais la mise en cache de HWND semble impossible parce que je ne sais pas quand il est créé.
Existe-t-il un moyen de déterminer si la fenêtre masquée est créée pour l'appartement actuel? Je suppose que ce sera moins cher que la boucle et puis je pourrais trouver et cache HWND.
Existe-t-il un meilleur moyen de pomper des messages COM sans pomper WM_PAINT?
Mise à jour: Vous pouvez forcer la création de la fenêtre en appelant CoMarshalInterThreadInterfaceInStream
pour n'importe quelle interface. Puis appelez CoReleaseMarshalData
pour libérer le pointeur de flux. C'est ce que je finis par faire avec la recherche de OleMainThreadWndClass
.
Si vous voulez opter pour des routes sombres, vous devriez pouvoir taper AppCompatFlags directement dans la mémoire PEB: https://social.msdn.microsoft.com/Forums/sqlserver/en-US/5a28a9f5-5711-4efa -843e-e98927fa2b92/dcom-dans-vista-spécifiquement-traitement-wmpaint-messages? Forum = windowsgeneraldevelopmentissues. Je pense que vous pouvez désactiver la pompe WM_PAINT si binaire-et actuel AppCompatFlags avec la valeur de l'indicateur 0x100000. Remarque Le décalage d'AppCompatFlags par rapport au début du PEB est différent de x64 et x32. –
Je ne peux pas penser à une seule bonne raison de ne pas traiter les messages WM_PAINT. Si quelque chose est "dangereux" dans votre gestionnaire WM_PAINT, je suppose que vous faites quelque chose dans WM_PAINT que vous ne devriez pas faire. Le gestionnaire WM_PAINT doit uniquement lire l'état (toutes les variables nécessaires pour déterminer ce qu'il doit dessiner) et non modifier l'état. –
@MichaelGunter, les grilles virtuelles font beaucoup de choses intéressantes dans les gestionnaires WM_PAINT. –