#heading[Функциональные схемы.]
#emph[Функциональные схемы. Комбинационные схемы (мультиплексор, демультиплексор, дешифратор, сумматоры). Последовательные схемы (RS-триггер, JK-триггер, T-триггер, D-триггер). Схемы для выполнения арифметических операций (каскадный сумматор, АЛУ).]

#set par(justify: true)
#import "/commons.typ": imagebox

== Комбинационные схемы
=== Мультиплексор

_Мультиплексор_ --- схема, позволяющая передавать сигнал с одного из $2^n$ входов на единственных выход. При этом выбор желаемого входа осуществляется подачей соответствующей комбинации управляющих сигналов. Для этого на вход также подаются $n$ бит.
#columns(2)[
  #imagebox("mux_outside.png", height: 170pt)
  #colbreak()
  #imagebox("mux_inside.png", height: 170pt)
]
Внутренняя реализация для $2^n$ значений использует n инверторов, $2^n$ ($n+1$)-битных and'ов и единственный $2^n$-битный or.

=== Шифратор
_Шифратор_ --- схема из функциональных элементов, которая позволяет по $n$-битному двоичному числу, в котором установлен ровно 1 бит, получить номер этого бита. Таким образом, при подаче сигнала на один из n входов (обязательно на один, не более) на выходе появляется двоичный код номера активного входа.
#columns(2)[
  #imagebox("encoder_outside_scheme.jpg", height: 100pt, label: [Обозначение шифратора на схемах.])
  #colbreak()
  #imagebox("encoder_outside.png", height: 100pt, label: [Таблица истинности шифратора.])
]

#columns(2)[
  #imagebox("encoder_inside.jpg", width: 270pt);
  #colbreak()

  _Внутреннее устройство схемы_ может показаться запутанным. На самом деле, чтобы её реализовать, достаточно посмотреть на двоичную запись чисел от 0 до $n-1$:

  #columns(2)[
    $0_10 = 000_2$\
    $1_10 = 001_2$\
    $2_10 = 010_2$\
    $3_10 = 011_2$
    #colbreak()
    $4_10 = 100_2$\
    $5_10 = 101_2$\
    $6_10 = 110_2$\
    $7_10 = 111_2$ 
  ]
]

- При подаче бита 0 не требуется устанавливать никакой бит, этот провод не участвует.
- При подаче бита 1 требуется установить только нулевой бит, поэтому провод идёт в $"or"_0$.
- При подаче бита 2 требуется установить только первый бит, поэтому провод идёт в $"or"_1$.
- При подаче бита 3 требуется установить биты 0 и 1, поэтому провод идёт в $"or"_0$ и $"or"_1$.
Реализация более сложных шифраторов $forall n in NN$ проводится по такому же принципу.

=== Дешифратор
_Дешифратор_ --- схема из функциональных элементов, имеющая $n$ входов и $2^n$ выходов. Позволяет по $n$-битному двоичному числу установить единицу имеено в тот выход, номеру которого соответвует двоичное число на входе.
#columns(2)[
  #imagebox("decoder_outside.png", height: 150pt)
  #colbreak()
  #imagebox("decoder_inside.png", height: 130pt)
]
Внутренняя реализация для $n$ входов использует n инверторов и $2^n$ $n$-битных and'ов. Легко заметить, что никакие 2 входа одновременно не могут быть выставлены как 1.

=== Демультиплексор
#emph[Демультиплексор] --- это логическое устройство, предназначенное для переключения сигнала с ровно одного информационного входа на один из информационных выходов. Таким образом, демультиплексор в функциональном отношении противоположен мультиплексору.

Схема демультиплексора легко строится, если вы ознакомились со схемой дешифратора. Достаточно в каждый из and'ов подключить бит, который мы передаём. Таким образом схема принимает вид, подозрительно напоминабщая дешифратор:
#columns(2)[
  #imagebox("demux_outside.png", height: 150pt)
  #colbreak()
  #imagebox("demux_inside.jpg", height: 150pt)
]

== Сумматоры
#v(10pt)
#columns(2)[
  #align(center)[
    *Частичный сумматор*
    #imagebox("half_adder.png", height: 70pt)
  ]
  #colbreak()
  #align(center)[
    *Полный сумматор*
    #imagebox("full_adder.png", width: 200pt)
  ]
]

#emph[Частичный сумматор] реализован просто: бит результата получается, как _xor_ входных битов. Бит переноса же устанавливается только тогда, когда оба входных бита установлены.

#emph[Полный сумматор] предназначен для суммирования длинных чисел (длина > 1), так как в нём бит переноса может приходить из предыдущего разряда в следующий. Заметим в схеме аспекты:
+ Результирующий бит числа получается, как _xor_ $i$-х битов с $(i-1)$-м битом переполнения (тем, который пришел с предыдущего разряда).
+ Бит переполнения устанавливается в тех случаях, если:
  - входные биты установлены ($A = 1 and B = 1$);
  - входные биты различны $(A = 1 and B = 0) or (A = 0 and B = 1)$ и бит переполения установлен ($C = 1$).
Таким образом, полный сумматор корректен. Подлючив несколько таких последовательно, мы можем складывать $n$-битный числа $forall n in NN$.

== Последовательные схемы
_Последовательной_ логической схемой называется схема с памяьтю.

=== RS-триггер
#columns(2)[
  #imagebox("rs-trigger_assync.jpg", height: 170pt, label: [
    ассинхронный #emph[RS-триггер]
  ])
  #colbreak()
  #imagebox("rs-trigger_sync.gif", height: 170pt, label: [
    синхронный #emph[RS-триггер]
  ])
]

Принцип работы _RS-триггера_ заключается в том, что он может сохранять своё предыдущее состояние пока оба входа неактивны и изменять его при подаче на один из входов единицы. При подаче единицы на оба входа состояние триггера вообще говоря неопределено.

У _RS-триггера_ есть 2 возможных состояния:
- Если подать на $S$ (set) 1, а на $R$ (reset) 0, то $Q$ станет 1, а $not Q$ станет 0.
- Если подать на $S$ (set) 0, а на $R$ (reset) 1, то $Q$ станет 0, а $not Q$ станет 1.

Такие значения сохранятся даже, когда $R$ и $S$ переключатся на 0. 

Существуют два способа реализации #emph[RS-триггера]: _синхронный_ и _ассинхронный_. Отличие у них лишь в том, что в случае _синхронного RS-триггера_ значения на $Q$ и $not Q$ не изменятся, пока не будет подан сигнал синхронизации $C$, в то время как у _ассинхронного RS-триггера_ значения меняются сразу при изменении $R$ или $S$.
#pagebreak()

=== JK-триггер
#imagebox("jk-trigger.png", height: 170pt, label: [JK-триггер])

Работа _JK-триггера_ практически совпадает с тем, как работает _синхронный RS-триггер_. Для того чтобы исключить запрещённое состояние(когда $R = 1 and S = 1$), его схема изменена таким образом, что при подаче двух единиц _JK-триггер_ инвертирует хранимое значение: $Q$ превращается в $not Q$, а $not Q$ в $Q$.

=== T-триггер
#imagebox("t-trigger.png", height: 135pt, label: [T-триггер])

_T-триггер_ --- это _JK-триггер_, в который на $J$ и $K$ подаются *только одинаковые* значения. Таким образом, мы можем только инвертировать хранимый бит. 

=== D-триггер
#imagebox("d-trigger.png", height: 135pt, label: [D-триггер])

_D-триггер_ --- это _JK-триггер_, в который на $J$ и $K$ подаются *только различные* значения. Таким образом, мы можем только устанавливать хранимый бит нулём либо единицей. 
#pagebreak()

== Схемы для выполнения арифметических операций
=== Каскадный сумматор

_Каскадный сумматор_ --- логическая схема, осуществляющая сложение многоразрядных двоичных чисел. Реализуется простой цепочкой полных однобитных сумматоров.
#imagebox("cascade_adder.png", height: 100pt)

=== АЛУ (арифметико-логическое устройство)
#imagebox("alu_outside.png", height: 150pt)
_Арифметико-логическое устройство_ --- блок процессора, который служит для выполнения арифметических и логических преобразований (начиная от элементарных) над данными, называемыми в этом случае операндами.

#imagebox("alu_inside.png", height: 300pt)
Легко заметить, внутреннее устройство _АЛУ_ элементарно и крайне понятно. Если вы по каким то причинам не понимаете, как работает данная логическая схема, авторы статьи коллективно рекомендуют вам пойти и написать свой 32-х разрядный многотактовый процессор на архитектуре MIPS, используя язык :sparkles: #text(red)[verilog] :sparkles:.













