|
Атомарность операций |
|
|
|
Oct 2 2009, 07:33
|

Знающий
   
Группа: Свой
Сообщений: 601
Регистрация: 3-07-07
Пользователь №: 28 852

|
Здравствуйте!
Прошу прощения за оффтоп(хотя ОС Windows CE), но проблема такова:
Пишу многопоточную программу под х86 процессор (защищенный режим) на С++. Есть глобальная переменная (назовём её Count) для взаимодействия двух потоков. (в обоих потоках присутствуют операции чтение, запись и чтение-модификация-запись (Count=Count+A)). По логике программы операции чтение и запись не могут привести к нарушению работы, а вот чтение-модификация-запись - может.
Возникла идея реализовать операцию Count=Count+A в виде ассемблерной вставки, где операция выполняется инструкцией Add: __asm{ push eax mov eax,A add Count,eax pop eax }; , т.к. код, генерируемый компилятором по умолчанию сводился к: mov eax,Count mov ebx,A add eax,ebx ; опасная строка 1 mov Count,eax ; опасная строка 2
Все эти заморочки вызваны тем, что в любом месте моя программа может быть прервана планировщиком ОС. Т.е. если планировщик вклиниться между опасными командами 1 и 2, запустит на выполнение второй поток, который выполнит опасные команды 1 и 2, и опять запустит на выполнение первый поток, который выполнит опасную команду 2, возникнет ситуация "пепец".
Теперь внимание вопрос: если операция Count=Count+A в ассемблерном коде представлена одной процессорной командой Add, гарантирует ли это отсутствие ситуации "пепец" ?
Иными словами, можно ли ассемблерную инструкцию считать атомарной (выполняемой как единое целое) ?
Иными словами: планировщик современных ОС вклинивается между инструкциями x86 или между инструкциями внутреннего RISC-ядра процессора?
На всякий случай добавлю: пользоваться объектами синхронизации ОС (критические секции, Interlocked...) не вышло - очень замедляет работу моего RealTime приложения. Приложение запущено в пользовательском режиме (кольцо 3), cli и sti не советовать.
На всякий случай доп. информация (скорее всего не существенно): Среда: Visual Studio 2005 ОС(целевая): Windows CE 6.0 R2 Процессор(целевой): AMD Geode LX800 (x86(набор инструкций P5), FPU, MMX, 3DNow!)
|
|
|
|
|
 |
Ответов
|
Oct 7 2009, 11:56
|

Гуру
     
Группа: Свой
Сообщений: 3 041
Регистрация: 10-01-05
Из: Москва
Пользователь №: 1 874

|
Цитата(Xenia @ Oct 7 2009, 14:56)  Что-то сомнительно. Префикс LOCK блокирует шину только на время выполнения данной инструкции, поэтому здесь это не поможет, поскольку "порча" происходит во время прерывания между соседними инструкциями. Кроме того, у меня противоречивые сведения о том, распространияются ли привилегии на префикс LOCK или нет. Инструкция, разумеется, должна быть одна, а именно, инкремента ячейки памяти командами lock add или lock xadd. Более сложные атомарные конструкции всегда можно сконструировать при помощи lock cmpxchg и цикла. См. IA32 Instruction Set Reference Кстати, борющимся за скорость будет полезно ознакомиться вот с этой статьей из MSDN http://msdn.microsoft.com/en-us/library/2ddez55b(VS.71).aspx
--------------------
Пишите в личку.
|
|
|
|
Сообщений в этой теме
sysel Атомарность операций Oct 2 2009, 07:33 KolyanV Команды процессора с точки зрения прерываний - ато... Oct 4 2009, 06:43 Dima_G Цитата(KolyanV @ Oct 4 2009, 09:43) Коман... Oct 5 2009, 07:20  KolyanV Цитата(Dima_G @ Oct 5 2009, 10:20) В свое... Oct 6 2009, 20:24   Xenia Цитата(KolyanV @ Oct 7 2009, 00:24) 2 xen... Oct 6 2009, 22:08    ReAl Цитата(Xenia @ Oct 7 2009, 01:08) Другое ... Oct 7 2009, 05:52   Dima_G Цитата(KolyanV @ Oct 7 2009, 00:24) Ничег... Oct 7 2009, 07:42 Xenia Если ваш код работает в защищенном режиме, то отче... Oct 4 2009, 07:14 readt Цитата(sysel @ Oct 2 2009, 10:33) Все эти... Oct 4 2009, 13:43
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|