Si je comprends bien, le modèle de mémoire .NET sur une machine 32 bits garantit des écritures et des lectures de 32 bits comme étant des opérations atomiques, mais pas fournir cette garantie sur des mots de 64 bits. J'ai écrit un outil rapide pour démontrer cet effet sur un système d'exploitation Windows XP 32 bits et obtenir des résultats cohérents avec cette description du modèle de mémoire.Modèle de mémoire 64 bits .NET 3.5SP1 vs. modèle de mémoire 32 bits
Cependant, j'ai pris l'exécutable de ce même outil et l'ai exécuté sur un système d'exploitation Windows 7 Enterprise 64-bit et obtient des résultats très différents. Les deux machines sont des spécifications identiques seulement avec différents systèmes d'exploitation installés. Je m'attendais à ce que le modèle de mémoire .NET garantirait que les écritures et les lectures de TOUS les mots 32 bits et 64 bits soient atomiques sur un système d'exploitation 64 bits. Je trouve des résultats complètement contraires aux deux hypothèses. Il n'est pas démontré que les lectures et les écritures 32 bits soient atomiques sur ce système d'exploitation. Est-ce que quelqu'un peut m'expliquer pourquoi cela échoue sur un système d'exploitation 64-bit?
Code Tool:
using System;
using System.Threading;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var th = new Thread(new ThreadStart(RunThread));
var th2 = new Thread(new ThreadStart(RunThread));
int lastRecordedInt = 0;
long lastRecordedLong = 0L;
th.Start();
th2.Start();
while (!done)
{
int newIntValue = intValue;
long newLongValue = longValue;
if (lastRecordedInt > newIntValue) Console.WriteLine("BING(int)! {0} > {1}, {2}", lastRecordedInt, newIntValue, (lastRecordedInt - newIntValue));
if (lastRecordedLong > newLongValue) Console.WriteLine("BING(long)! {0} > {1}, {2}", lastRecordedLong, newLongValue, (lastRecordedLong - newLongValue));
lastRecordedInt = newIntValue;
lastRecordedLong = newLongValue;
}
th.Join();
th2.Join();
Console.WriteLine("{0} =? {2}, {1} =? {3}", intValue, longValue, Int32.MaxValue/2, (long)Int32.MaxValue + (Int32.MaxValue/2));
}
private static long longValue = Int32.MaxValue;
private static int intValue;
private static bool done = false;
static void RunThread()
{
for (int i = 0; i < Int32.MaxValue/4; ++i)
{
++longValue;
++intValue;
}
done = true;
}
}
}
Résultats sur Windows XP 32 bits:
Windows XP 32-bit
Intel Core2 Duo P8700 @ 2.53GHz
BING(long)! 2161093208 > 2161092246, 962
BING(long)! 2162448397 > 2161273312, 1175085
BING(long)! 2270110050 > 2270109040, 1010
BING(long)! 2270115061 > 2270110059, 5002
BING(long)! 2558052223 > 2557528157, 524066
BING(long)! 2571660540 > 2571659563, 977
BING(long)! 2646433569 > 2646432557, 1012
BING(long)! 2660841714 > 2660840732, 982
BING(long)! 2661795522 > 2660841715, 953807
BING(long)! 2712855281 > 2712854239, 1042
BING(long)! 2737627472 > 2735210929, 2416543
1025780885 =? 1073741823, 3168207035 =? 3221225470
Remarquez comment BING (int) est jamais écrit et démontre que 32 bits lecture/écriture sont atomiques sur ce système d'exploitation 32 bits.
Résultats sur Windows 7 Enterprise 64 bits:
Windows 7 Enterprise 64-bit
Intel Core2 Duo P8700 @ 2.53GHz
BING(long)! 2208482159 > 2208121217, 360942
BING(int)! 280292777 > 279704627, 588150
BING(int)! 308158865 > 308131694, 27171
BING(long)! 2549116628 > 2548884894, 231734
BING(int)! 534815527 > 534708027, 107500
BING(int)! 545113548 > 544270063, 843485
BING(long)! 2710030799 > 2709941968, 88831
BING(int)! 668662394 > 667539649, 1122745
1006355562 =? 1073741823, 3154727581 =? 3221225470
Remarquez que BING (long) et BING (int) sont tous deux affichés! Pourquoi les opérations 32 bits échouent, et encore moins les 64 bits?
Est-il possible que vous puissiez éditer votre question pour utiliser le format 'Exemple de code' dans la barre d'outils? C'est incroyablement difficile à lire .. – JBRWilkinson
Je l'avais formaté correctement mais avec des caractères TAB initialement au lieu d'espaces et l'aperçu avait l'air bien. J'ai été choqué quand j'ai découvert qu'il avait complètement échoué en postant. Je l'ai réparé maintenant. –
Je l'avais déjà corrigé: D – Femaref