2012-10-15 5 views
0

J'ai une communication de mémoire partagée réussie entre deux processus sur Windows. Je l'écris comme ceci: enter image description hereMémoire partagée de synchronisation

Ne me dérange pas mes commentaires à moi-même. Je pensais que je m'amuserais avec le diagramme. Comment puis-je faire cela plus rapidement? En d'autres termes, comment puis-je le faire en utilisant un Mutex ou un CreateEvent? J'ai essayé dur de comprendre Mutexes et CreateEvent mais il me confond sur MSDN car il emploie sur l'application et un fil. Un exemple serait utile mais pas obligatoire.

La façon dont je fais actuellement le faire est (très lent!):

// Création SharedMemory Nom du fichier + aide KnownProcessID donc je peux avoir plusieurs clients et serveurs avec applications uniques. J'ai déjà ce travail et cette communication réussie.

bool SharedMemoryBusy() 
{ 
    double* Data = static_cast<double*>(pData); //Pointer to the mapped memory. 
    return static_cast<int>(Data[1]) > 0 ? true : false; 
} 

void* RequestSharedMemory() 
{ 
    for (int Success = 0; Success < 50; ++Success) 
    { 
     if (SharedMemoryBusy()) 
      Sleep(10); 
     else 
      break; 
    } 
    return pData; 
} 

bool SharedMemoryReturned() 
{ 
    double* Data = static_cast<double*>(pData); 
    return static_cast<int>(Data[1]) == 2 ? true : false; 
} 

bool SharedDataFetched() 
{ 
    for (int Success = 0; Success < 50; ++Success) 
    { 
     if (SharedMemoryReturned()) 
      return true; 

     if (!SharedMemoryBusy()) 
      return false; 

     Sleep(10); 
    } 
    return false; 
} 

La lecture et l'écriture partie (Juste un exemple de la demande .. Il peut y avoir plusieurs types différents .. Modèles, Points, Lieux, etc.):

void* GLHGetModels() 
{ 
    double* Data = static_cast<double*>(RequestSharedMemory()); 
    Data[0] = MODELS; 
    Data[1] = StatusSent; 

    if (SharedDataFetched()) 
    { 
     if (static_cast<int>(Data[2]) != 0) 
     { 
      unsigned char* SerializedData = reinterpret_cast<unsigned char*>(&Data[3]); 
      MemDeSerialize(ListOfModels, SerializedData, static_cast<int>(Data[2])); 
      return Models.data(); 
     } 
     return NULL; 
    } 
    return NULL; 
} 

void WriteModels() 
{ 
    If (pData[0] == MODELS) 
    { 
     //Write The Request.. 
     Data[1] = StatusReturned; 
     Data[2] = ListOfModels.size(); 
     unsigned char* Destination = reinterpret_cast<unsigned char*>(&Data[3]); 
     MemSerialize(Destination, ListOfModels); //Uses MEMCOPY To copy to Destination. 
    } 
} 

Répondre

1

Vous pouvez utiliser des événements et mutex entre les processus. Cela fonctionne bien. Il vous suffit de dupliquer la poignée de l'objet avant de passer à un autre processus:

BOOL WINAPI DuplicateHandle(
    _In_ HANDLE hSourceProcessHandle, 
    _In_ HANDLE hSourceHandle, 
    _In_ HANDLE hTargetProcessHandle, 
    _Out_ LPHANDLE lpTargetHandle, 
    _In_ DWORD dwDesiredAccess, 
    _In_ BOOL bInheritHandle, 
    _In_ DWORD dwOptions 
); 

Chaque processus fonctionne avec sa propre poignée alors qu'ils se réfèrent tous deux au même objet du noyau.

Ce que vous devez faire est de créer 2 événements. La première partie signale que les données sont prêtes. L'autre côté doit prendre les données, placer ses propres données, réinitialiser le premier événement et signaler le second. Après cela, la première partie fait la même chose. Les fonctions d'événement sont: CreateEvent, SetEvent, ... CloseHandle.

+0

Oui, mais cela nécessite que je prenne les poignées des deux processus que je ne peux pas faire parce que je ne connais pas le ProcessID du client. Seul le serveur. Le client Ouvre la mémoire partagée en fonction de l'ID de processus du serveur. – Brandon

+0

Ensuite, après l'ouverture du client de partage devrait y mettre son ID de processus ou d'autres informations d'identification. Comment le serveur découvre-t-il que ce client veut se connecter? –

+0

Le serveur Crée le fichier de mémoire partagée. Le client se connecte à ce fichier de mémoire partagée lorsqu'un bouton est enfoncé. C'est à peu près ça. De là, le client écrit une requête et le serveur vérifie si le fichier a été écrit en permanence puis répond. Puis-je faire: "OpenEvent (...," EventName ");" saisir l'événement d'un autre processus? – Brandon