Как на уровне железа конкурируют 2 процесса?

Как на уровне железа реализуется взаимодействие многопоточных\многопроцессорных программ, т.е. хочу представить как это реально происходит, "бегут" 2+ электрических заряда по цепи от 2+ ядерного процессора и все они хотят обратиться к диску, в каком месте они встречаются и как достигается понимания того что кто-то первый, а кто-то второй, третий и т.п. ? и что будет если они будут абсолютно одновременны? Или например тоже самое но с записью в RAM, как каждый процесс успевает занять себе место но которое гарантированно не занял кто-то другой в эту же миллисекунду.


Ответы (2 шт):

Автор решения: gbg

Взаимодействие многопоточных програм реализуется в первую очередь на базе логических примитивов синхронизации, которые в свою очередь реализуются за счет вполне понятных логических узлов. На уровень отдельных электронных компонентов тут уже спускаться не нужно.

Один маленький конкретный пример - логический примитив "атомарная переменная (std::atomic в C++)". Для реализации ее в примитивном процессоре, у которого нет кэша и конвейера инструкций, операции чтения и записи в эту переменную выполнялись за одну машинную инструкцию.

На базе атомарной переменной уже можно сконструировать более сложные примитивы синхронизации - мьютекс и семафор. А уж с таким арсеналом можно много чего натворить.

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

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

→ Ссылка
Автор решения: nick_n_a

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

Касательно RAM. Тут есть три фактора - ЦП, КЕШ, ОС, многоканальность. С RAM всё проще, пока один ЦП делает обращение в физическую память - остальные ЦП - ждут. Каким именно образом организован приоритет ожидания - затрудняюсь сказать. Скорее всего по номеру процессора, и может отличаться от версии ЦП. Так как программа чаще всего не работает исключительно с памятью - то после ожидания другой ЦП получит доступ к RAM. Надо не забывать, что ОС может ограничивать/подавлять излишнюю активность потока, если ей нужно паралельно ещё делать какие-то задачи, в т ч обслуживание ОС. Поэтому приоритет будет зависеть ещё и от версии ОС, её загруженности и колличества одновременно запущенных программ и каких именно программ тоже (т.к. одна программа может грузить ЦП на полную, а другая спать). Так же кеш памяти встроеный в ЦП - очень облегчает операции с памятью. В современных ПК уже нету внешнего кеш. При выключеном кеш ЦП работает в разы медленнее. Обращение в RAM при включеном кеш - могут не происходить, если в КЕШ всё поместилось. При использовании двухканальной памяти, или многоканальной - возможна упаковка обращения к RAM от двух потоков в одно обращение, что так же даст небольшой прирост производительности (т.к. вероятность такой возможноти имеет некоторый % вероятности).

C диском всё гораздо сложнее. Во первых работа с диском идет не напрямую, а через драйвер, поэтому приоритет или одновременность обращения - решает драйвер. Учитывая то что очень часто дисковые операции обьеденяются вместе и кешируется - то вполне возможно что потоки перейдут в ожидание в разнове время, но завершится ожидание дисковой операции примерно в одинаковое время. После физической операции ввода вывода - управление перейдёт драйверу ввода вывода, а уже драйвер ввода вывода передаст управление ОС. Вероятнее всего ОС отдаст предпочтение самому обделённому потоку, что бы выровнять перекос по быстродействию (если у потоков одинаковые приоритеты). Работа с диском напрямую в обход драйвера - задача очень сложная - практически не используется.

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

→ Ссылка