Question

L'API Windows DuplicateHandle () http://msdn.microsoft.com/en-us /library/ms724251(VS.85).aspx Requiert que le descripteur d’objet soit dupliqué et un descripteur du processus original ET de l’autre processus pour lequel vous souhaitez utiliser le descripteur dupliqué.

Je suppose que si j'ai deux processus UNRELATED, je pourrais appeler DuplicateHandle () dans l'un ou l'autre aussi longtemps que les descripteurs requis sont disponibles?

Ma question concerne l'utilisation d'un tuyau pour communiquer entre les deux processus afin d'y parvenir avec un événement.

Dans le premier processus, je CreateEvent (). Maintenant, je veux utiliser WaitForSingleObject () dans le deuxième processus.

Si j'essaie de dupliquer le descripteur dans le premier processus, je devrai d'abord envoyer le deuxième descripteur de processus au premier processus via le canal, dupliquer le descripteur, puis envoyer le descripteur au deuxième processus?

Alternativement, je pourrais commencer par envoyer le premier descripteur de processus et le descripteur d'événement au deuxième processus, puis simplement le dupliquer.

Existe-t-il une raison pour laquelle je devrais choisir l'un plutôt que l'autre?

Pour ajouter un pli, le descripteur d'événement est en fait hérité du processus parent qui a appelé le premier processus (qui est une application CGI). Si ce descripteur d'événement a été créé avec HANDLE_DO_NOT_DUPLICATE (un peu comme cela), puis-je utiliser DuplicateHandle () pour le dupliquer pour le second processus?

Réponse:

Eh bien, je pourrais créer un nouvel événement NAMED dans le premier processus et le trouver dans le second processus comme suggéré, mais j'essaie de dupliquer l'événement créé dans le parent du premier processus et de le transférer au second processus. . Cet événement n'est pas nommé. Je dois donc utiliser DuplicateHandle ().

J'utilise un tuyau pour l'IPC. Je réalise que DuplicateHandle () devra être appelé dans le premier processus car le descripteur d'événement est hors contexte lorsqu'il est envoyé au second processus.

        hProcPseudo  = GetCurrentProcess() 

    //Then call either:
        lpRealHandle = OpenProcess( PROCESS_DUP_HANDLE, 0, hProcPseudo ) 
//This fails with GetLastError= 87 - The parameter is incorrect ???
// same thing with PROCESS_ALL_ACCESS ??


    //OR
        lRet = DuplicateHandle( hProcPseudo, hProcPseudo, hProcPseudo, lpRealHandle, DUPLICATE_SAME_ACCESS, 0, 0 )

    //then I can Duplicate my Event Handle in the first thread with:
        lRet = DuplicateHandle( hLocalProcess, hEvent, lpRealHandle, hDupEvent, DUPLICATE_SAME_ACCESS, 0, 0)

Le second processus convertit son identificateur avec DuplicateHandle () détaillé ci-dessus, en cours de conversion

hProcPseudo = 4294967295

à

hProcess = 152

Ensuite, je passe ce descripteur de processus au premier processus via le canal nommé. Dans le premier processus (où le descripteur d’événement est valide), j’appelle le descripteur en double:

DuplicateHandle( hFirstProcess, hEvent, hSecondProc, hDupEvent, DUPLICATE_SAME_ACCESS, 0, 0)

Malheureusement, j'obtiens l'erreur:

DuplicateHandle hPipeFCGI GetLastError = 6 - Le descripteur n'est pas valide.

D'autres tests (en remplaçant hFirstProcess) révèlent que c'est hSecondProc qui est invalide! ??

Grand mystère.

Était-ce utile?

La solution

Utilisez un canal nommé ou < a href = "http://msdn.microsoft.com/en-us/library/aa365576(VS.85).aspx" rel = "nofollow noreferrer"> mailslots pour IPC, cela devrait fonctionner de manière fiable pour votre objectif. Si vous devez attendre, utilisez des descripteurs d’attente nommés.

Sinon, je choisirais d'effectuer DuplicateHandle dans le deuxième processus afin de définir correctement la propriété du descripteur.

Autres conseils

Le descripteur de processus est différent de l'identificateur de processus. OpenProcess prend l'identifiant du processus. Utilisez quelque chose comme ...

HANDLE hProcess = OpenProcess (PROCESS_DUP_HANDLE, FALSE, GetCurrentProcessId ());

Si j'ai bien compris, vous souhaitez synchroniser deux processus non liés via le même événement. Si tel est le cas, vous pouvez utiliser des événements nommés.

Créez-en un à l'aide de la fonction API CreateEvent . , donnez-lui un nom, puis, à partir du deuxième processus, utilisez OpenEvent fonction API, spécifiant le nom de l'événement.

Vous avez des fonctions similaires pour d'autres objets de synchronisation, tels que les mutex ( OpenMutex ) ou des sémaphores ( OpenSemaphore ) .

  1. D'une manière ou d'une autre, le deuxième processus doit attribuer son ID de processus au premier processus. Ceci peut être obtenu via GetCurrentProcessId ()
  2. Le premier processus doit maintenant utiliser cet ID pour obtenir un HANDLE dans le deuxième processus: hProcess = OpenProcess (PROCESS_DUP_HANDLE, FALSE, dwProcessId);
  3. Vous pouvez désormais dupliquer le descripteur dans le premier processus, à l'aide du descripteur REAL du deuxième processus et du pseudo-descripteur du premier processus: DuplicateHandle (GetCurrentProcess (), hEvent, hProcess, & amp; hDupEvent, 0, FALSE, DUPLICATE_SAME_ACCESS);
  4. N'oubliez pas de libérer le descripteur que vous avez créé avec OpenProcess (je ne sais pas quelle différence cela ferait, mais vous êtes censé le faire ...). De même, relâchez les deux poignées de l'événement: celles données au deuxième processus et le traitement initial.
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top