Структурные конфликты

Структурные конфликты возникают, если на различных участках конвейера производится обращение к одному, недублированому ре­сурсу. Подобная ситуация возникает, например, если процессор имеет единую кэш-память для команд и для данных. Если в момент выборки очередной команды производится попытка обращения к кэш-памяти за данными, то возникает структурный конфликт. Одна из команд должна быть задержана, возникает простой конвейера. Избежать структурных конфликтов из-за ресурсов можно, если пол­ностью дублировать все ресурсы процессора так, чтобы все возмож­ные комбинации команд могли быть приняты на обработку в любых сочетаниях. Однако некоторые разработчики процессоров созна­тельно допускают возможность подобных конфликтов с целью удешевления и упрощения процессора.

Другой причиной структурных конфликтов является неполная конвейеризация функциональных устройств. Например, описывая выше простой процессор, мы предполагали, что любая команда должна быть выполнена за один такт работы процессора. Однако это не всегда возможно, так как некоторые команды, например ум­ножение или деление, могут выполняться значительно дольше од­ного такта. Если, скажем, деление будет выполняться дольше од­ного такта, то все команды, следующие за делением, должны быть задержаны до тех пор, пока команда деления не покинет блок вы­полнения. Подобная ситуация показана на рис. 26. Звездочками на рисунке показаны такты, в течение которых обработка задержанных команд не производится.

№ такта
«Длинная» команда IF ID RD EX EX EX WR    
Следующая команда   IF ID RD * * EX WR  
Следующая команда     IF ID * * RD EX WR

Рис 26. Простой процессора из-за структурного конфликта

Можно избежать конфликтов, связанные с различной длительно­стью команд, если совместить начальные и конечные стадии выпол­нения команд, в общих функциональных устройствах, а для стадии выполнения реализовать различные функциональные устройства, каждое со своей длительностью обработки. Можно выделить, на­пример, следующие функциональные блоки:

1) блок обращения к памяти;

2) блок арифметики с фиксированной точкой;

3) блок операций целочисленного умножения / деления;

4) блок операций с плавающей точкой.

Пример такой схемы процессора показан на рис. 27.

Отметим, что в процессоре, реализованном по подобной схеме, возможен структурный конфликт на входе последнего этапа – за­писи в регистры. Чтобы избежать конфликта, узел должен иметь столько входов, сколько конвейеров могут одновременно к нему об­ращаться.

Существует еще одна существенная проблема, которая может возникать в системе с несколькими длинными функциональными конвейерами. Пусть процессор выполняет некоторую «длинную» операцию, например, деление с плавающей точкой. В то время, пока операция деления выполняется на «своем» функциональном конвей­ере, процессор может успеть выполнить несколько простых арифме­тических команд с фиксированной точкой. Предположим, что в конце операции деления происходит некоторое исключение, напри­мер, переполнение, вызывающее прерывание. Как уже описывалось выше, процессор должен сохранить адрес текущей команды и свое состояние на момент прерывания, чтобы обработчик прерываний мог проанализировать его, обработать исключение и, при необхо­димости начать выполнение прерванных команд заново. Однако счетчик команд содержит не адрес команды «виноватой» в преры­вании, а адрес некоторой следующей команды. Более того, команды, которые следовали за командой деления, уже успели сформировать свои результаты в регистры процессора и флаги во флаговом реги­стре соответствуют полученным результатам. Указанная проблема носит название проблемы точных прерываний на конвейере. Воз­можно нескольких путей решения данной проблемы.

Первый состоит в том, что проблема просто игнорируется. Про­цессор реализует неточные прерывания. Обработчик прерывания вынужден анализировать состояние процессора и «отматывать на­зад» в поисках команды, вызвавшей прерывание. Возможен вариант такого подхода, когда прерывание не генерируется совсем, а в ре­зультате операции, получается некоторое «специальное», зарезерви­рованное значение, по которому можно судить о причинах, вызвав­ших исключение.

Второй возможный подход – сохранять результаты команд в спе­циальном буфере. Значения из буфера в регистры процессора пере­писываются только тогда, когда все команды, предшествующие данной, завершены. Такой подход ведет к существенному усложне­нию схемы процессора, поскольку необходимо хранить большое ко­личество промежуточных результатов, более того, промежуточ­ные результаты могут требоваться для выполнения новых команд.

Третий возможный подход является некоторой комбинацией двух предыдущих. При этом разрешаются неточные прерывания, но сохраняется достаточное количество информации, чтобы в случае прерывания начать выполнение программы заново с команды вы­звавшей прерывание. Минимальный набор хранимой информации – адрес каждой из выполняемых в текущий момент времени команд.