Re: Синхронизация доступа к флагу
От: Сергей  
Дата: 29.06.05 20:06
Оценка: 1 (1)
Здравствуйте, Zline, Вы писали:

Z>Вопрос видимо классический, но тем не менее:


Z>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.

Z>В то же время некий другой поток естественно однажды этот флаг выставит.

Z>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять? Вероятность этого конечно весьма и весьма мала (особенно учитывая современные процы), но тем не менее..


Z>Тут же возникает более общий вопрос: а вообще интовый ресурс нужно синхронизировать, если меняет его только один поток, а читают многие?


Если не хочется использовать объекты ядра, можно использовать IntelockedIncrement/InterlockedDecrement
Re: Синхронизация доступа к флагу
От: sercher Украина  
Дата: 30.06.05 09:25
Оценка: +1
Z>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять?

Ничего плохого не случится. Критические секции тут АБСОЛЮТНО не нужны.
Re[5]: Синхронизация доступа к флагу
От: adontz Грузия http://adontz.wordpress.com/
Дата: 30.06.05 10:54
Оценка: -1
Здравствуйте, Andrew S, Вы писали:

AS>Зато возникнут вопросы у того, кто будет просматривать такой код. Вопросы о квалификации того, кто это писал. Не следует использовать объекты ядра где ни попадя.


Межпотоковая синхронизация это как скобки. Лучше поставить лишнюю пару, чем не поставить там где надо.
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[4]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 01.07.05 08:22
Оценка: +1
Z>>Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?

M> Да должен. Иначе словишь глюку с синхронизацией процессорных кэшей на многопроцессорных тачках. Удобнее всего для этого использовать функцию InterlockedExchangeAdd(..., 0).


Нет, не должен. Если для записи значения пользуются InterlockedXxx функции, то кеши процессоров синхронизированы. Соответственно, чтение завсегда дает правильный результат.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Синхронизация доступа к флагу
От: Zline  
Дата: 29.06.05 18:43
Оценка:
Вопрос видимо классический, но тем не менее:

Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.
В то же время некий другой поток естественно однажды этот флаг выставит.

Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять? Вероятность этого конечно весьма и весьма мала (особенно учитывая современные процы), но тем не менее..

Тут же возникает более общий вопрос: а вообще интовый ресурс нужно синхронизировать, если меняет его только один поток, а читают многие?
Re: Синхронизация доступа к флагу
От: Amidlokos Россия  
Дата: 29.06.05 18:50
Оценка:
Здравствуйте, Zline, Вы писали:

Z>Вопрос видимо классический, но тем не менее:


Z>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.

Z>В то же время некий другой поток естественно однажды этот флаг выставит.

Только один вопрос: чем плох мютекс?
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
WARNING: expression "to_be || !to_be" is always true
Re: Синхронизация доступа к флагу
От: adontz Грузия http://adontz.wordpress.com/
Дата: 29.06.05 19:15
Оценка:
Здравствуйте, Zline, Вы писали:

А почему не Autoreset Event или Semaphore?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[2]: Синхронизация доступа к флагу
От: Valery A. Boronin Россия linkedin.com/in/boronin
Дата: 29.06.05 20:31
Оценка:
Здравствуйте, Сергей, Вы писали:

оверквотинг был несколько лишний в принципе...

С>Если не хочется использовать объекты ядра, можно использовать IntelockedIncrement/InterlockedDecrement


...но ответ должен быть именно такой. +1!
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Valery A. Boronin, RSDN Team, linkedin.com\in\boronin
R&D Mgmt & Security. AppSec & SDL. Data Protection and Systems Programming. FDE, DLP, Incident Management. Windows Filesystems and Drivers.
Re[2]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 29.06.05 20:45
Оценка:
Z>>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.
Z>>В то же время некий другой поток естественно однажды этот флаг выставит.

A>Только один вопрос: чем плох мютекс?


Как истинный ариец, отвечу вопросом на вопрос — а чем в данном случае он хорош?
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[3]: Синхронизация доступа к флагу
От: Amidlokos Россия  
Дата: 29.06.05 23:58
Оценка:
Здравствуйте, Andrew S, Вы писали:

AS>Как истинный ариец, отвечу вопросом на вопрос — а чем в данном случае он хорош?


Тем, что таких вопросов не возникнет...
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
WARNING: expression "to_be || !to_be" is always true
Re: Синхронизация доступа к флагу
От: AndreyT  
Дата: 30.06.05 00:46
Оценка:
Здравствуйте, Zline, Вы писали:
Z>Тут же возникает более общий вопрос: а вообще интовый ресурс нужно синхронизировать, если меняет его только один поток, а читают многие?

Если тебе нужен просто вариант "триггера", то можно не синхронизировать.
Даже если обстоятельства позже изменятся и писать в переменную будет не один поток, а несколько, то даже в этом случае вполне можно обойтись без строгой синхронизации.
Поскольку интересен только факт "ноль-не ноль".

Есть только одна потенциальная засада, переменная должна быть объявлена volatile, что от неприятностей с оптимизацией отнюдь не гарантирует.(см. одноимённый многостраницный топик). Я бы всё-таки присоединился к автору, посоветовавшему использовать Interlocked* функции. По той причине, что они содержат примитив, исполняющий роль mfence и может избавить от потенциальных недоразумений с синхронизацией процессорных кэшей.

Пользоваться тяжёлыми методами с привлечением объектов ядра я никакого смысла не вижу.
Re[2]: Синхронизация доступа к флагу
От: Anton Batenev Россия https://github.com/abbat
Дата: 30.06.05 03:14
Оценка:
Здравствуйте, Amidlokos, Вы писали:

Z>>Вопрос видимо классический, но тем не менее:

Z>>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.
Z>>В то же время некий другой поток естественно однажды этот флаг выставит.
A>Только один вопрос: чем плох мютекс?

Тем, что на его создание и обращение к нему требуется, согласно Рихтеру, на много больше времени, нежели при работе с критическими секциями.
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Re: Синхронизация доступа к флагу
От: Anton Batenev Россия https://github.com/abbat
Дата: 30.06.05 03:14
Оценка:
Здравствуйте, Zline, Вы писали:

Z>Вопрос видимо классический, но тем не менее:


И так же классические грабли

Z>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.

Z>В то же время некий другой поток естественно однажды этот флаг выставит.

Кроме того, что он проверяет этот флаг, поток еще что-нибудь делает? В любом случае, я бы воспользовался событиями (CreateEvent / WaitForSingleObject).

Z>Тут же возникает более общий вопрос: а вообще интовый ресурс нужно синхронизировать, если меняет его только один поток, а читают многие?


Да. InterLocked-функции.
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Re: Синхронизация доступа к флагу
От: Zline  
Дата: 30.06.05 04:45
Оценка:
Спасибо всем за ответы. Вопрос даже не в том мьютекс/критическая секция/события, а в том стоит ли париться с этим (вставляя соотв. код во все обращения) — ресурс то интовый, безхитростный

Наверно остановлюсь на InterLocked-функциях. Спасибо за совет.
Re[2]: Синхронизация доступа к флагу
От: Zline  
Дата: 30.06.05 08:25
Оценка:
Z>Наверно остановлюсь на InterLocked-функциях. Спасибо за совет.

Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?

В поисках ответа я наткнулся на ряд дискуссий по поводу того, нужно ли такую переменную объявить volatile, а также на идею, заключающуюся в том, что все переменные, используемые несколькими потоками должны быть volatile. Так ли это? А если так, то что делать со списковыми структурами, которые юзают много потоков (синхронизация через критические секции конечно есть, а нужен ли тут еще volatile?)
Re[3]: Синхронизация доступа к флагу
От: Anton Batenev Россия https://github.com/abbat
Дата: 30.06.05 09:25
Оценка:
Здравствуйте, Zline, Вы писали:


Z>>Наверно остановлюсь на InterLocked-функциях. Спасибо за совет.

Z>Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?

InterLockedExchange?
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Re[4]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 30.06.05 09:28
Оценка:
Z>>>Наверно остановлюсь на InterLocked-функциях. Спасибо за совет.
Z>>Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?

AB>InterLockedExchange?


Чтобы просто читать, никаких примитивов синхронизации не нужно. Модификатор volatile — нужен.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[2]: Синхронизация доступа к флагу
От: TarasCo  
Дата: 30.06.05 09:34
Оценка:
Здравствуйте, sercher, Вы писали:



Z>>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять?


S> Ничего плохого не случится. Критические секции тут АБСОЛЮТНО не нужны.


АБСОЛЮТНО согласен....
Да пребудет с тобою сила
Re[4]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 30.06.05 10:04
Оценка:
AS>>Как истинный ариец, отвечу вопросом на вопрос — а чем в данном случае он хорош?

A>Тем, что таких вопросов не возникнет...


Зато возникнут вопросы у того, кто будет просматривать такой код. Вопросы о квалификации того, кто это писал. Не следует использовать объекты ядра где ни попадя.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[5]: Синхронизация доступа к флагу
От: Zline  
Дата: 30.06.05 11:15
Оценка:
Здравствуйте, Andrew S, Вы писали:

AB>>InterLockedExchange?

угу, но оно меняет и флаг, а оно мне при чтении не нужно

AS>Чтобы просто читать, никаких примитивов синхронизации не нужно. Модификатор volatile — нужен.


Насчет флага понятно, а теперь volatile =)
Ну допустим флагам я его поставлю. А списковым структурам, которые юзает несколько тредов, как прописывать volatile? всем указателям в структуре и корню структуры?
Re[6]: Синхронизация доступа к флагу
От: adontz Грузия http://adontz.wordpress.com/
Дата: 30.06.05 11:43
Оценка:
Здравствуйте, Zline, Вы писали:

Z>Ну допустим флагам я его поставлю. А списковым структурам, которые юзает несколько тредов, как прописывать volatile? всем указателям в структуре и корню структуры?

volatile list<int>

?
A journey of a thousand miles must begin with a single step © Lau Tsu
Re[7]: Синхронизация доступа к флагу
От: Zline  
Дата: 30.06.05 11:52
Оценка:
Здравствуйте, adontz, Вы писали:

A>Здравствуйте, Zline, Вы писали:


Z>>Ну допустим флагам я его поставлю. А списковым структурам, которые юзает несколько тредов, как прописывать volatile? всем указателям в структуре и корню структуры?

A>
A>volatile list<int>
A>

A>?

Нет нет, у меня не шаблоны. Классические списки —

typedef struct SJOB job;
struct SJOB
{
    job    *next;
    dword    id;
    SOCKET    sock;
    string    inbuf;
    string    outbuf;
...
...
    bool    die;
};

По идее при изменении списка естесн меняется только job *next, его и описать как volatile job *next; ?
Re[6]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 30.06.05 15:19
Оценка:
AS>>Зато возникнут вопросы у того, кто будет просматривать такой код. Вопросы о квалификации того, кто это писал. Не следует использовать объекты ядра где ни попадя.

A>Межпотоковая синхронизация это как скобки. Лучше поставить лишнюю пару, чем не поставить там где надо.


Плохое сравнение. Как раз в случае синхронизации надо просчитывать каждую "скобку", поскольку лишняя может настолько убить перфоманс приложения, что и многопоточность будет только лишней. Опять же, есть случаи, когда использование кернел объектов для синхронизации не только нежелательно, но и просто невозможно. За примером ходить далеко не надо — тот же синглтон.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[7]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 30.06.05 15:22
Оценка:
Z>>Ну допустим флагам я его поставлю. А списковым структурам, которые юзает несколько тредов, как прописывать volatile? всем указателям в структуре и корню структуры?
A>
A>volatile list<int>
A>

A>?

При работе с std списками надо использовать критические секции, соответственно, никакой volatile не нужен. volatile в этом смысле применим лишь к встроенным интегральным типам.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[8]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 30.06.05 15:26
Оценка:
Z>Нет нет, у меня не шаблоны. Классические списки —

Z>
Z>typedef struct SJOB job;
Z>struct SJOB
Z>{
Z>    job    *next;
Z>    dword    id;
Z>    SOCKET    sock;
Z>    string    inbuf;
Z>    string    outbuf;
Z>...
Z>...
Z>    bool    die;
Z>};
Z>

Z>По идее при изменении списка естесн меняется только job *next, его и описать как volatile job *next; ?

Я бы использовал тут критические секции для синхронизации доступа к списку. Если очень важна производительность или критические секции использовать невозможно по каким-либо причинам, я бы почитал статьи по "безблокирующим" способам доступа к разделяемым ресурсам. Например, для затравки http://www.cs.chalmers.se/~tsigas/papers/rtcsa99.pdf
Там все более сложно, чем вам кажется
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[9]: Синхронизация доступа к флагу
От: Zline  
Дата: 01.07.05 06:27
Оценка:
Здравствуйте, Andrew S, Вы писали:

Z>>Нет нет, у меня не шаблоны. Классические списки —


Z>>
Z>>typedef struct SJOB job;
Z>>struct SJOB
Z>>{
Z>>    job    *next;
Z>>    dword    id;
Z>>    SOCKET    sock;
Z>>    string    inbuf;
Z>>    string    outbuf;
Z>>...
Z>>...
Z>>    bool    die;
Z>>};
Z>>

Z>>По идее при изменении списка естесн меняется только job *next, его и описать как volatile job *next; ?

AS>Я бы использовал тут критические секции для синхронизации доступа к списку. Если очень важна производительность или критические секции использовать невозможно по каким-либо причинам, я бы почитал статьи по "безблокирующим" способам доступа к разделяемым ресурсам. Например, для затравки http://www.cs.chalmers.se/~tsigas/papers/rtcsa99.pdf

AS>Там все более сложно, чем вам кажется

доступ естественно синхронизируется с помощью критических секций, вопрос в том, нужно ли помимо этого еще объявлять поле job *next как volatile ?
Re[10]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 01.07.05 07:09
Оценка:
Z>доступ естественно синхронизируется с помощью критических секций, вопрос в том, нужно ли помимо этого еще объявлять поле job *next как volatile ?
Нет. Критические секции выступают в роли барьера памяти, так что никаких модификаторов тут не надо.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[3]: Синхронизация доступа к флагу
От: mkopachev  
Дата: 01.07.05 07:23
Оценка:
Здравствуйте, Zline, Вы писали:


Z>>Наверно остановлюсь на InterLocked-функциях. Спасибо за совет.


Z>Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?


Да должен. Иначе словишь глюку с синхронизацией процессорных кэшей на многопроцессорных тачках. Удобнее всего для этого использовать функцию InterlockedExchangeAdd(..., 0).

С уважением Михаил Копачев
... << RSDN@Home 1.1.4 @@subversion >>
Re[3]: Синхронизация доступа к флагу
От: mkopachev  
Дата: 01.07.05 07:27
Оценка:
Здравствуйте, TarasCo, Вы писали:

TC>Здравствуйте, sercher, Вы писали:




Z>>>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять?


S>> Ничего плохого не случится. Критические секции тут АБСОЛЮТНО не нужны.


TC>АБСОЛЮТНО согласен....


Случится, еще как случится — на многопроцессорной тачке. Достаточно в считывающем потоке флагу попасть в процессорный кэш, чтобы он не заметил его изменения.

С уважением Михаил Копачев
... << RSDN@Home 1.1.4 @@subversion >>
Re[4]: Синхронизация доступа к флагу
От: TarasCo  
Дата: 01.07.05 07:56
Оценка:
Здравствуйте, mkopachev, Вы писали:

M>Здравствуйте, TarasCo, Вы писали:


TC>>Здравствуйте, sercher, Вы писали:




Z>>>>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять?


S>>> Ничего плохого не случится. Критические секции тут АБСОЛЮТНО не нужны.


TC>>АБСОЛЮТНО согласен....


M> Случится, еще как случится — на многопроцессорной тачке. Достаточно в считывающем потоке флагу попасть в процессорный кэш, чтобы он не заметил его изменения.


M> С уважением Михаил Копачев


Процессорный кеш имеет свойство синхронизхироваться с памятью.... и с другими процессорными кешами
Если интересует задержка в несколько тактов между установкой флага одним процессором и чтением другим — тогда Вы правы, читающий поток может пролететь мимо флага, но при работе в ОС с вытесняющей многозадачностью, я Вас умоляю, даже если поток, исполняющийся на другом процессоре получит обнавленный флаг хоть через 1 мс ( что по меньшей мере фантастично ) — это не критично, для Windows даже эта величина намного меньше кванта, соответсвенно ее можно считать = 0.

Критично, если из-за оптимизации флаг станет регистровой переменной, тогда возможен дедлок. Но тут поможет volatile .
Да пребудет с тобою сила
Re[5]: Синхронизация доступа к флагу
От: mkopachev  
Дата: 01.07.05 11:20
Оценка:
Здравствуйте, TarasCo, Вы писали:

TC>Здравствуйте, mkopachev, Вы писали:


M>>Здравствуйте, TarasCo, Вы писали:


TC>>>Здравствуйте, sercher, Вы писали:




Z>>>>>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять?


S>>>> Ничего плохого не случится. Критические секции тут АБСОЛЮТНО не нужны.


TC>>>АБСОЛЮТНО согласен....


M>> Случится, еще как случится — на многопроцессорной тачке. Достаточно в считывающем потоке флагу попасть в процессорный кэш, чтобы он не заметил его изменения.


M>> С уважением Михаил Копачев


TC>Процессорный кеш имеет свойство синхронизхироваться с памятью.... и с другими процессорными кешами

TC>Если интересует задержка в несколько тактов между установкой флага одним процессором и чтением другим — тогда Вы правы, читающий поток может пролететь мимо флага, но при работе в ОС с вытесняющей многозадачностью, я Вас умоляю, даже если поток, исполняющийся на другом процессоре получит обнавленный флаг хоть через 1 мс ( что по меньшей мере фантастично ) — это не критично, для Windows даже эта величина намного меньше кванта, соответсвенно ее можно считать = 0.

Любопытная точка зрания. Но дело в том, что я на эти грабли уже наступал, так что с Вами я не соглашусь. Для того чтобы процессорный кэш синхронизировался, нужно принимать специальные меры, в частности префикс lock у команд (кстати именно так все Interlocked — функции и реализуются). Чтобы не разводить флейм просто сошлюсь на руководство по системному программированию процессора Intel — там это все есть.

С уважением Михаил Копачев
... << RSDN@Home 1.1.4 @@subversion >>
Re[5]: Синхронизация доступа к флагу
От: mkopachev  
Дата: 01.07.05 11:20
Оценка:
Здравствуйте, Andrew S, Вы писали:

Z>>>Эм, сори что снова поднимаю тему, но возник еще вопрос: а те потоки, что будут только читать переменную, должны делать какие-либо дополнительные телодвижения? или просто localVar = sharedVar; ?


M>> Да должен. Иначе словишь глюку с синхронизацией процессорных кэшей на многопроцессорных тачках. Удобнее всего для этого использовать функцию InterlockedExchangeAdd(..., 0).


AS>Нет, не должен. Если для записи значения пользуются InterlockedXxx функции, то кеши процессоров синхронизированы. Соответственно, чтение завсегда дает правильный результат.


Согласен.
Есть правда один тонкий момент — начальное значение переменной — нужно присваивать явно через Interloced, если не делать этого явно, то читать нужно тоже через Interlocked.
... << RSDN@Home 1.1.4 @@subversion >>
Re[6]: Синхронизация доступа к флагу
От: TarasCo  
Дата: 01.07.05 12:35
Оценка:
TC>>Процессорный кеш имеет свойство синхронизхироваться с памятью.... и с другими процессорными кешами
TC>>Если интересует задержка в несколько тактов между установкой флага одним процессором и чтением другим — тогда Вы правы, читающий поток может пролететь мимо флага, но при работе в ОС с вытесняющей многозадачностью, я Вас умоляю, даже если поток, исполняющийся на другом процессоре получит обнавленный флаг хоть через 1 мс ( что по меньшей мере фантастично ) — это не критично, для Windows даже эта величина намного меньше кванта, соответсвенно ее можно считать = 0.

M> Любопытная точка зрания. Но дело в том, что я на эти грабли уже наступал, так что с Вами я не соглашусь. Для того чтобы процессорный кэш синхронизировался, нужно принимать специальные меры, в частности префикс lock у команд (кстати именно так все Interlocked — функции и реализуются). Чтобы не разводить флейм просто сошлюсь на руководство по системному программированию процессора Intel — там это все есть.


Это типа RTFM? Возможно, Вы наступили не на грабли а на лопату
Естественно, если префикс lock не используется есть промежуток времени, когда кеши не когерентны. В некоторых случая это чревато ( допустим, счетчик ссылок — можно как недосчитаться, так и пересчитаться ). Но в случае, когда один поток ( процессор ) устанавливает флаг, а другой на это реагирует ( распространенный случай — прекращает свою работу ) такая рассинхронизация кешей не страшна. Самый "страшный" случай — читающий поток среагирует на флаг позже.
Да пребудет с тобою сила
Re[6]: Синхронизация доступа к флагу
От: Andrew S Россия http://alchemy-lab.com
Дата: 01.07.05 12:47
Оценка:
AS>>Нет, не должен. Если для записи значения пользуются InterlockedXxx функции, то кеши процессоров синхронизированы. Соответственно, чтение завсегда дает правильный результат.

M> Согласен.

M> Есть правда один тонкий момент — начальное значение переменной — нужно присваивать явно через Interloced, если не делать этого явно, то читать нужно тоже через Interlocked.

Смотря какая переменная. Если global static — то не надо, это значение заполняется на этапе компиляции и когерентно после загрузки модуля. Если function static — тогда стандарт С++ определяет, что такая переменная инициализируется до вызова этой функции. Но на деле все компиляторы поступают с ней аналогично global static. Если переменная на стеке или в хипе — тогда да, возможен, хотя и совсем невероятен вариант, когда другой тред не увидит правильного ее значения. Я бы не стал на этом акцентировать внимание, тем более что функция создания треда наверняка синхронизирует кеши, уж больно тяжелая это операция.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re: Синхронизация доступа к флагу
От: Alex Alexandrov США  
Дата: 03.07.05 10:46
Оценка:
Здравствуйте, Zline, Вы писали:

Z>Вопрос видимо классический, но тем не менее:


Z>Есть поток, проверяющий несколько раз в секунду некий буловский флаг, и если флаг выставлен, поток завершается.

Z>В то же время некий другой поток естественно однажды этот флаг выставит.

Z>Вопрос: если не делать синхронизацию с помощью критических секций, не случится ли чего плохого, если один поток будет читать флаг в то время как второй будет его выставлять? Вероятность этого конечно весьма и весьма мала (особенно учитывая современные процы), но тем не менее..


Z>Тут же возникает более общий вопрос: а вообще интовый ресурс нужно синхронизировать, если меняет его только один поток, а читают многие?


Эта тема обсуждалась много раз — срочно в поиск! Например, здесь
Автор: Alex Alexandrov
Дата: 22.06.05
и здесь
Автор: Alex Alexandrov
Дата: 22.06.05
.

Кратко: на x86 архитектуре — для булевой переменной можно обойтись без синхронизации. Для выровненного int — тоже. Для невыровненного — надо блокировать шину, т.е. пользоваться Interlocked*. На других архитектурах (например, Итаниум) — возможны нюансы.
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
It's kind of fun to do the impossible (Walt Disney)
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.