2016-05-26 5 views
-1

Je rencontre des problèmes lors de l'implémentation de la bibliothèque boost/interprocess pour les opérations de mémoire partagée entre deux programmes. C'est la première fois que j'ai utilisé des opérations de mémoire partagée, et j'ai d'abord modifié une partie de l'exemple de code dans la documentation de boost trouvée ici: (http://www.boost.org/doc/libs/1_41_0/doc/html/interprocess/quick_guide.html).Problèmes avec boost: mémoire partagée interprocess

La démo modifiée fonctionne bien, et est essentiellement comme suit:

typedef std::pair<double, int> MyType; 
managed_shared_memory segment(create_only, "MySharedMemory", 65536); 

MyType *instance = segment.construct<MyType> 
    ("MyType instance") //name of the object 
    (12.34, 0);   //ctor first argument 

MyType *instance2 = segment.construct<MyType> 
    ("MyType instance2") //name of the object 
    (56.78, 0);   //ctor first argument 

Et puis dans un autre processus, récupérer ces variables:

managed_shared_memory segment(open_only, "MySharedMemory"); 

std::pair<MyType*, managed_shared_memory::size_type> res; 
std::pair<MyType*, managed_shared_memory::size_type> res2; 

res = segment.find<MyType>("MyType instance"); 
printf("1: %d, %d\n", res.first, res.second); // show pointer and size 
printf("1a: %f\n\n", *res.first); //show double value 


res2 = segment.find<MyType>("MyType instance2"); 
printf("2: %d, %d\n", res2.first, res2.second); // show pointer and size 
printf("2a: %f\n", *res2.first); // show double value 

ok, donc tous les e au regarde ok, et la sortie du terminal est:

1: 196724, 1 
1a: 12.340000 

2: 196780, 1 
2a: 56.780000 

Le problème est lorsque j'essaie de répliquer cela dans un autre (existant) application.

J'ai fait tout de manière presque identique à ce que je peux dire (identiquement en termes de syntaxe peut-être même?), Mais je reçois des résultats différents et inattendus.

typedef std::pair<double, int> myDouble; 
managed_shared_memory segment(create_only, "sharedMemBlock", 65536); 

myDouble *valX = segment.construct<myDouble> 
    ("valX") 
    (1.1, 0); 

myDouble *valY = segment.construct<myDouble> 
    ("valY") 
    (2.2, 0); 

myDouble *valZ = segment.construct<myDouble> 
    ("valZ") 
    (3.3, 0); 

et dans le second processus pour récupérer ces valeurs:

managed_shared_memory segment(open_only, "sharedMemBlock"); 
std::pair<myDouble*, managed_shared_memory::size_type> valShrX; 
std::pair<myDouble*, managed_shared_memory::size_type> valShrY; 
std::pair<myDouble*, managed_shared_memory::size_type> valShrZ; 

valShrX = segment.find<myDouble>("valX"); 
valShrY = segment.find<myDouble>("valY"); 
valShrZ = segment.find<myDouble>("valZ"); 

printf("PtrvalSharedX: %d,PtrvalSharedY: %d, PtrvalSharedZ: %d\n", valShrX.first, valShrY.first, valShrZ.first); 
printf("valSharedX: %f, valSharedY: %f, valSharedZ: %f\n\n", *valShrX.first, *valShrY.first, *valShrZ.first); 

mais les résultats ne sont pas ce que je pense, et viennent comme ça:

PtrvalSharedX: 196724, PtrvalSharedY: 196772, PtrvalSharedZ: 196820 
valSharedX: 1.100000, valSharedY: 0.000000, valSharedZ: 2.200000 

Alors, quel est passe ici? Pourquoi ne reçois-je pas les valeurs 1.1, 2.2 et 3.3 pour valSharedX, valSharedY et valSharedZ respectivement?

Je ne sais pas pourquoi essentiellement le même code fonctionne dans une instance, mais pas dans une autre. J'ai noté que la différence entre les pointeurs dans le premier exemple (196780 - 196724) = 56, mais est plus petite dans le second exemple (196772 - 196724) = (196820 - 196772) = 48. Je ne sais pas si cela est pertinent, mais je pensais valait la peine de souligner (jeu de mots!).

Merci, B

+1

Qu'est-ce que 'myDouble'? –

+0

désolé, j'ai oublié cette ligne en rassemblant l'extrait. défini exactement la même chose que MyType était dans le premier exemple. typedef std :: paire myDouble; – brneuro

+0

Vous devriez [edit] (http://stackoverflow.com/posts/37467004/edit) votre question pour l'inclure maintenant. Cependant, le problème n'est pas immédiatement évident quand je regarde votre code et je n'ai pas de boost pour l'essayer moi-même. –

Répondre

0

Le problème que tout le monde négligé, y compris moi-même, était-ce ...

à cause du type:

std::pair<myDouble*, managed_shared_memory::size_type> valShrX 

obtenir:

valShrX.first 

renvoie un pointeur vers un myDouble, et non le premier double que je sa partie de la std :: paire qui est définie dans:

typedef std::pair<double, int> myDouble; 

Depuis printf ne sait pas ce myDouble de type est vraiment, et puisque ce type ne sait pas nativement par printf, la question présentée uniquement lors de l'impression multiple valeurs dans une séquence et se rapporte à la taille de monDouble ne correspond pas à la taille d'un double.

L'impression de chaque valeur avec sa propre instruction printf (comme dans le premier extrait de code) fonctionne correctement, car le pointeur valShrX.first dit à printf de démarrer correctement. Même si la taille de valShrX.first doit inclure l'int qui fait partie de la paire, printf affiche le% f et s'arrête.Dans le deuxième extrait de code, j'ai essayé d'imprimer les trois valeurs dans la mémoire partagée dans la même instruction printf, et donc la taille complète de std :: pair myDouble (y compris le double et l'int) a été propagée et serait compensée les deuxième et troisième valeurs imprimées.

La déclaration correcte devrait obtenir juste le premier élément de la paire myDouble, qui est dans la paire mère ... En d'autres termes, c'est la syntaxe printf correcte étant donné mes types de données:

printf("valSharedX: %f, valSharedY: %f, valSharedZ: %f\n\n", valShrX.first->first, valShrY.first->first, valShrZ.first->first); 

Ainsi, ma syntaxe printf était incorrecte dans les deux exemples, mais le fonctionnement le plus punitif de printf lors de l'impression de plusieurs valeurs dans une seule instruction était le seul cas à rendre le problème apparent. Ma seule question restante qui chatouille mon cerveau est la suivante: Pourquoi ce problème s'est-il présenté dans Visual Studio 2013, mais le code identique lors de la compilation sous Linux n'a pas montré le problème lorsque printf% f a reçu un myDouble dans une série des valeurs en cours d'impression? Tout a bien fonctionné lorsqu'il est compilé sous Linux. Pourquoi?

+0

puisque les exemples de boost :: interprocess ne montrent que mettre vos données dans la mémoire partagée, et ne démontrent pas comment récupérer vos données dans la mémoire partagée, je dirais que cela est pertinent pour les autres de voir * toux * toux @sehe .... upvotes sur ma question et réponse serait appréciée. – brneuro