2009-12-26 6 views
1

Какова связь между регистрами ЦП и кэшем ЦП, когда речь идет о протоколах когерентности кеширования, таких как MESI? Если определенное значение хранится в кеше ЦП и также сохраняется в регистре, то что произойдет, если строка кэша будет отмечена как «грязная»? к моему пониманию, нет никаких указаний на то, что регистр обновит его значение, даже несмотря на то, что кеш обновлен (из-за MESI).Регистры процессора и когерентность

Хенч этот код:

static void Main() 
    { 
    bool complete = false; 
    var t = new Thread (() => 
    { 
    bool toggle = false; 
    while (!complete) toggle = !toggle; 
    }); 
    t.Start(); 
    Thread.Sleep (1000); 
    complete = true; 
    t.Join();  // Blocks indefinitely 
} 

(давайте предположим, что компилятор не оптимизировал нагрузки для «полного» вне цикла)
моему пониманию, обновление до «полной» не видно во второй поток, так как его значение хранится внутри регистра (однако, кэш ЦП 2 был обновлен).

действительно ли помещает заслон памяти, чтобы «смыть» все регистры? Каково отношение регистров к кешу? и как насчет регистров и барьеров памяти?

ответ

5

Отношения нет. Используйте ключевое слово «volatile».

0

Протокол MESI, используемый на платформе x86, гарантирует согласованность когерентности, то есть изменения в одном кэше ЦП автоматически распространяются на другие кэши ЦП. Поэтому volatile ключевое слово на x86 и x64 полезно только для предотвращения переупорядочения.

+0

С многократным потоком, работающим на нескольких ядрах, volatile не спасет вас от повторного заказа; разные ядра будут переупорядочивать по-разному и где они не знают о повторных заказах друг друга, волатильность не может спасти вас. С несколькими потоками на одном процессоре volatile гарантирует, что компилятор всегда получает значение переменной, но я не думаю, что это совсем не так, как * не переупорядочивание *. На самом деле, я подозреваю, что он не предлагает никаких указаний о переупорядочении поведения ... – 2009-12-28 01:15:25

+0

http://software.intel.com/en-us/blogs/2007/11/30/volatile-almost-useless-for- многопоточное программирование/ – 2009-12-28 01:17:41

+0

Это похоже на код C#. volatile имеет значение в C#, отличном от C/C++. Я на самом деле думаю, что это ошибка в том, как MS создает закрытие для функции потока. Так как полный попадает в закрытие, его следует рассматривать как глобальный. Мы увидели бы те же результаты (блоки навсегда), если бы полный был глобальным? – tony