Bug O нотация отладочная сложность программных интерфейсов


Оглавление (нажмите, чтобы открыть):

Отладочный интерфейс

В данном разделе приведено описание отладочного интерфейса процессора ARM7TDMI в следующей последовательности:

В разделе также описывается модуль эмуляции EmbeddedICE, который входит в состав процессора ARM7TDMI, в следующих параграфах:

1. Общие сведения об отладочном интерфейсе

Отладочный интерфейс процессора ARM7TDMI выполнен на основе стандарта IEEE 1149.1 — 1990, Стандарт архитектуры порта доступа к функциям тестирования и граничного сканирования. Рекомендуется обратиться к данному стандарту для ознакомления с толкованием используемых терминов и для изучения состояний контроллера Порта доступа к функциям тестирования (TAP-контроллер). Блок-схема изменений состояний TAP-контроллера представлена на рисунке 5.2.

Процессор ARM7TDMI содержит аппаратные расширения для выполнения расширенных функций отладки. Это существенно упрощает разработку программного обеспечения, операционных систем и собственно аппаратной части.

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

1.1 Стадии отладки

Запрос, поступивший через один из сигналов интерфейса отладки или внутренний функциональный блок, именуемый логикой эмуляции EmbeddedICE Logic, переводит процессор ARM7TDMI в состояние отладки. Ниже приведены события, которые активизируют отладку:

  • точка прерывания, выборка инструкции
  • точка наблюдения (watchpoint), доступ к данным
  • внешний запрос отладки.

После перевода в состояние отладки внутреннее состояние процессора ARM7TDMI может управляться с помощью последовательного интерфейса JTAG. Он позволяет загружать в последовательном формате инструкции в конвейер процессора без использования внешней шины данных. Например, после перевода в состояние отладки, инструкция Многократной записи (STM) может быть помещена на конвейер инструкций и это приведет к экспорту содержимого регистров ядра ARM7TDMI. Эти данные могут быть переданы в последовательном формате отладчику, не нарушая работы остальной части системы.

Ядро ARM7TDMI использует два сигнала синхронизации:

  • MCLK — синхронизация памяти;
  • DCLK — внутренняя синхронизация отладки, генерируемая тестовой синхронизацией TCK.

В нормальном режиме работы ядро тактируется сигналом MCLK, а внутренняя логика удерживает DCLK в низком состоянии.

Если процессор ARM7TDMI находится в состоянии отладки, то ядро синхронизируется DCLK под управлением цифрового автомата TAP-контроллера, а MCLK может работать вхолостую. Выбранный сигнал синхронизации присутствует на выходе внешней синхронизации ECLK для использования внешней системой.

Прим.: nWAIT не оказывает должного влияния, если ядро ЦПУ находится в состоянии отладки и тактируется сигналом DCLK.

2. Отладочные системы

На рисунке 5.1 показана типичная отладочная система с использованием ядра ARM.

Рисунок 5.1. Типичная отладочная система

Отладочная система обычно состоит из трех частей:

  1. Отладчик
  2. Преобразователь протокола
  3. Отлаживаемое целевое устройство

Отладчик и преобразователь протокола являются системно-зависимыми.

В качестве отладчика выступает компьютер, на котором запущена отладочная программа, например, ARM Debugger for Windows (ADW). Отладчик позволяет вводить такие команды высокого уровня, как установка точки прерывания или проверка содержимого памяти.

2.2 Преобразователь протокола

Преобразователь протокола отвечает за преобразование команды высокого уровня отладчика в команды низкого уровня интерфейса JTAG процессора ARM7TDMI.

Как правило, подключение к компьютеру выполняется через расширенный параллельный порт (ЕРР).

Процессор ARM7TDMI содержит аппаратные расширения, которые упрощают отладку на самом низком уровне. Отладочные расширения:

  • позволяют приостановить выполнение программы;
  • проверить и модифицировать внутреннее состояние ядра;
  • просмотреть и изменить состояние системы памяти;
  • возобновить выполнение программы.

2.3 Отлаживаемое целевое устройство

Основные блоки отлаживаемого целевого устройства показаны на рисунке 5.2.

Рисунок 5.2. Блок-схема ARM7TDMI

Ядро содержит аппаратную часть, поддерживающая отладку.

Это набор регистров и компараторов, используемых для генерации отладочных исключительных ситуаций, как, например, точки прерывания. Описание этого блока приведено в параграфе «Общие сведения о логике эмуляции EmbeddedICE».

ТАР-контроллер управляет действием цепей сканирования через последовательный интерфейс JTAG.

3. Сигналы интерфейса отладки

Отладочный интерфейс состоит из трех основных внешних сигналов:

  • BREAKPT и DBGRQ — системные запросы процессора на ввод состояния отладки;
  • DBGACK — используется для сигнализации о нахождении ядра в состоянии отладки.

Прим.: Для полного разрешения отладочных функций процессора DBGEN необходимо перевести в высокое состояние. См. «Отключение EmbeddedICE».

3.1 Переход в состояние отладки

Процессор ARM7TDMI переходит в состояние отладки после запроса со стороны точек прерывания или точек наблюдения, а также при запросе отладки. Для программирования условий активизации точек прерывания или точек наблюдения необходимо использовать логику EmbeddedICE. Альтернативно, вы можете использовать сигнал BREAKPT, который позволяет внешней логике устанавливать точки прерывания или точки наблюдения, а также контролировать:

  • шину адреса
  • шину данных
  • сигналы управления.

Временная диаграмма аналогична внешне-сгенерированным точкам прерывания и наблюдения. Данные должны быть действительными по падающему фронту MCLK. Если инструкцию необходимо снабдить точкой прерывания, то сигнал BREAKPT должен иметь высокий уровень при следующем нарастающем фронте MCLK. Аналогично, при чтении или записи данных установка BREAKPT во время нарастающего фронта MCLK маркирует данные, как точка наблюдения.

Когда процессор переходит в состояние отладки, устанавливается сигнал DBGACK.

Временная диаграмма внешне-сгенерированных точек прерывания показана на рисунке 5.3.

Рисунок 5. Вход в состояние отладки

Вход в состояние отладки по точке прерывания

Ядро ARM7TDMI определяет, что инструкция содержит точку прерывания еще при поступлении на конвейер, но ядро переходит в состояние отладки только при достижении такой инструкцией ступени исполнения.

Инструкция с точкой прерывания не выполняется. Вместо этого процессор переходит в состояние отладки.

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

Прим.: Процессор переходит в состояние отладки независимо от выполнения условия.

Инструкция с точкой прерывания не вызывает переход ядра ARM7TDMI в состояние отладки в следующих случаях:

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

Вход в состояние отладки по точке наблюдения

Точки наблюдения активизируются при осуществлении доступа к данным. Точки наблюдения проверяются постоянно, но не всегда вводят состояние отладки незамедлительно. Как минимум во всех случаях ожидается завершение выполнения текущей инструкции. Если текущая инструкция — многословное чтение или запись (LDM или STM), то до срабатывания точки наблюдения пройдет еще множество циклов.

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

Прим.: Точки наблюдения похожи на Авар. данные. Отличие заключается в том, что при возникновении ситуации Авар. данных, несмотря на завершение выполнения инструкции, процессор предотвращает любые последующие изменения состояния процессора ARM7TDMI. Данное действие позволяет вызвать обработчик аварийной исключительной ситуации, устранить причину аварийной ситуации и повторно выполнить инструкцию.

Если точка наблюдения срабатывает после начала обработки исключительной ситуации, то ядро вводит состояние отладки в том же режиме, что и исключительная ситуация.

Вход в состояние отладки по запросу отладки

Процессор ARM7TDMI может быть переведен в состояние отладки при запросе отладки одним из следующих способов:

  • путем программирования логики EmbeddedICE (см. «Программирование точек прерывания» и «Программирование точек наблюдения»)
  • путем установки вывода DBGRQ.

Вывод DBGRQ — асинхронный вход и, поэтому, он вступает в силу с учетом синхронизации внутри процессора ARM7TDMI. Следуя синхронизации, ядро, как правило, вводит состояние отладки по окончании текущей инструкции. Однако, если текущая инструкция — доступ к сопроцессору с ожиданием состояния занятости, то выполнение инструкции прекращается и процессор ARM7TDMI вводит состояние отладки незамедлительно. Это аналогично действию nIRQ и nFIQ.

3.2 Действие процессора в состоянии отладки

Когда ядро ARM7TDMI вводит состояние отладки, сигналы nMREQ и SEQ индицируют внутренние циклы. Это позволяет оставшейся части системы памяти игнорировать ядро и функционировать в нормальном режиме. Поскольку, оставшаяся часть системы продолжает функционировать, то ARM7TDMI игнорирует аварийные ситуации и прерывания.

Система не должна изменять сигнал BIGEND в процессе отладки, поскольку отладчик не подозревает о реконфигурации ядра.

nRESET должен оставаться стабильным в процессе отладки, т.к. сброс ядра в состоянии отладки вызывает потерю слежения за ядром со стороны отладчика.

Если система устанавливает активный низкий уровень сброса на входе nRESET процессора ARM7TDMI, то процессор изменяет свое состояние, в то время как отладчик не имеет информации об этом.


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

4. Домены синхронизации ядра ARM7TDMI

Синхронизация ARM7TDMI описана в параграфе «Синхронизация».

4.1 Переключение синхронизации в состоянии отладки

При переходе процессора ARM7TDMI в состояние отладки происходит автоматическое переключение сигналов синхронизации с MCLK на DCLK, после чего устанавливается сигнал DBGACK во время высокого полупериода MCLK. Переключение между двумя сигналами синхронизации возникает при следующем падающем фронте MCLK. Это демонстрируется на рисунке 5.4.

До завершения отладки ядро использует сигнал DCLK в качестве основного сигнала синхронизации. При выходе из состояния отладки возобновляется синхронизация ядра сигналом MCLK. Это выполняется отладчиком следующим образом:

  1. Вводится последняя инструкция отладочной последовательности в цепь сканирования шины данных и синхронизируется путем установки DCLK.
  2. В регистр инструкции ТАР-контроллера записывается команда RESTART.

В этом случае ядро автоматически возвращается к синхронизации сигналом MCLK и запускает выборку инструкций из памяти на частоте MCLK.

См. «Выход из состояния отладки».

Рисунок 5.4. Переключение синхронизации при входе в состояние отладки

4.2 Переключение синхронизации в процессе тестирования

Когда последовательная тестовая комбинация поступает в ядро ARM7TDMI через интерфейс JTAG, то процессор должен тактироваться сигналом DCLK, а MCLK должен находится в низком состоянии.

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

TAP-контроллер может использоваться для проверки процессора. Если выбраны цепь сканирования 0 и INTEST, то DCLK генерируется, когда цифровой автомат находится в состоянии RUN-TEST/IDLE (запуск тестирования/холостой ход). В состоянии EXTEST DCLK не генерируется.

При выходе из состояния тестирования необходимо ввести в ТАР-контроллер инструкцию RESTART, после чего возобновляется работа MCLK. После проверки INTEST необходимо убедиться, что перед возвращением к нормальной работе ядро находится в восприимчивом состоянии. Наиболее безопасными способами для этого являются следующие:

  • выбор RESTART, что вызывает системный сброс
  • вставка инструкции MOV PC, #0 в конвейер инструкций перед возвратом в обычное состояние.

5. Определение состояния ядра и системы

Когда ядро находится в состоянии отладки, можно проверить состояние ядра и системы путем размещения нескольких инструкций чтения и записи на конвейере инструкций.

Перед тем как проверить состояние ядра и системы, отладчик путем проверки 4-го бита регистра статуса отладки логики EmbeddedICE должен определить, процессор введен в состояние отладки из состояния Thumb или ARM. Если этот бит равен 1, то ядро введено в состояние отладки из состояния Thumb.

Более детальная информация по определению состояния ядра приведена в параграфе «Определение состояния ядра и системы».

6. Общие сведения о логике EmbeddedICE

Логика EmbeddedICE процессора ARM7TDMI поддерживает встроенные функции отладки ядра ARM7TDMI.

Логика EmbeddedICE программируется последовательно с помощью ТАР-контроллера процессора ARM7TDMI. На рисунке 5.5 иллюстрируется соотношение между ядром, логикой EmbeddedICE и TAP-контроллером с указанием только используемых сигналов.

Рисунок 5.5. ARM7TDM, TAP-контроллер и логика EmbeddedICE

Логика EmbeddedICE содержит:

  • два блока реально-временных точек наблюдения
  • два раздельных регистра: — регистр управления отладкой — регистр состояния отладки.
  • Отладочный коммуникационный канал (DCC).

Регистр управления отладкой и регистр состояния отладки полностью управляют работой EmbeddedICE.

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

Прим.: Можно маскировать любой бит для его исключения из процесса сравнения.

Каждый блок точек наблюдения можно конфигурировать как блок точек наблюдения или как блок точек прерывания.

Точки прерывания и точки наблюдения могут быть зависимыми от данных.

7. Отключение EmbeddedICE

Логика EmbeddedICE отключается путем установки низкого уровня на DBGEN.

Замечание: если на вход DBGEN подать непрерывный низкий уровень, то это приведет к отключению логики EmbeddedICE.

Однако этим лучше не пользоваться для повышения безопасности системы.

Если DBGEN в низком состоянии, то:

  • BREAKPT и DBGRQ поступают в ядро в низком состоянии
  • DBGACK выходит из ядра ARM7TDMI в низком состоянии
  • прерывания обходят процессор, не задерживаясь логикой отладки
  • логика EmbeddedICE переходит в маломощный режим.

8. Отладочный коммуникационный канал

Логика EmbeddedICE процессора ARM7TDMI содержит DCC для передачи информации между целевым отлаживаемым устройством и отладчиком. Он реализован как сопроцессор 14 (CP14).

  • 32-разрядный коммуникационный регистр чтения данных
  • 32-разрядный коммуникационный регистр записи данных
  • 6-разрядный коммуникационный регистр управления для синхронизированного подтверждения установления связи между процессором и асинхронным отладчиком.

Данные регистры размещены в фиксированных позициях карты регистров логики EmbeddedICE, как показано на рисунке 5.7. Доступ к регистрам со стороны процессора выполняется с помощью инструкций MCR и MRC к сопроцессору 14.

DCC-регистр управления доступен только для чтения. Он управляет синхронизированным подтверждением связи между процессором и отладчиком. Формат регистра управления показан на рисунке 5.6.

Рисунок 5.6. Формат DCC-регистра управления

Ниже приведено назначение каждого бита регистра:

Биты 31:28 Содержит фиксированную комбинацию, которая определяет номер версии EmbeddedICE, в данном случае 0001.
Биты 27:2 Зарезервировано.
Бит 1 Если W сброшен, то DCC-регистр записи данных готов для получения данных от процессора. Если W установлен, то данные в DCC-регистре записи данных готовы для сканирования отладчиком.
Бит 0 Если R сброшен, DCC-регистр чтения данных свободен и данные могут быть помещены в него из отладчика.
Если R установлен, то DCC-регистр чтения данных не могут быть считаны процессором и отладчик должен ожидать.

Если смотреть со стороны отладчика, то доступ к регистрам выполняется через цепь сканирования 2 обычным образом. Со стороны процессора, доступ к данным регистрам выполняется с помощью инструкций передачи регистра сопроцессора.

Доступ к DCC-регистрам необходимо осуществлять с помощью инструкций из таблицы 5.1.

Таблица 5.1. Инструкции доступа к DCC-регистру

Инструкции Описание
MRC CP14, 0, Rd, C0, C0, 0 Помещает значение из DCC-регистра управления в регистр назначения (Rd)
MCR CP14, 0, Rn, C1, C0, 0 Запись значения из регистра-источника (Rn) в DCC-регистр записи данных
MRC CP14, 0, Rd, C1, C0, 0 Возвращает значение из DCC-регистра чтения данных в Rd

Поскольку набор инструкций Thumb не содержит сопроцессорных инструкций, то в этом случае рекомендуется выполнять доступ с помощью инструкции SWI.

8.2 Связь через DCC

DCC позволяет принять и отправить сообщение.

Отправка сообщения в отладчик

Когда процессору необходимо отправить сообщение в отладчик, он должен убедится в том, что регистр записи данных свободен. Это выполняется путем опроса бита W в регистре управления, который должен быть сброшен.

Процессор считывает регистр управления для проверки состояния бита 1:

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

Поскольку передача данных выполняется от процессора к DCC-регистру записи данных, то устанавливается бит W в DCC-регистре управления. Когда отладчик опрашивает данный регистр, он наблюдает синхронизированные версии бит R и W. Если отладчик определяет, что бит W установлен, то он может считать DCC-регистр записи данных и выполнить его последовательный вывод. По завершении чтения данного регистра данных происходит сброс бита W в DCC-регистре управления. На данном этапе коммуникационный процесс может начаться заново.

Прием сообщения из отладчика

Передача сообщения из отладчика похожа на отправку сообщения в отладчик. В этом случае, отладчик опрашивает бит R в DCC-регистре управления:

  • если бит R сброшен, то DCC-регистр чтения данных свободен и данные могут быть считаны процессором;
  • если бит R установлен, то данные находятся в стадии накопления и отладчик должен ожидать.

Если DCC-регистр чтения данных свободен, то данные записываются в него с помощью интерфейса JTAG.

Со стороны процессора бит R DCC-регистра управления используется следующим образом.

Процессор опрашивает DCC-регистр управления. Если бит R установлен, то имеются данные, которые могут быть считаны с помощью инструкции MRC в сопроцессор 14. После выполнения чтения сбрасывается бит R в DCC-регистре управления. Когда отладчик опрашивает данный регистр и определяет, что бит R сброшен, то это означает, что данные были приняты и процесс можно повторить заново.

Использование DCC с управлением по прерываниям

Альтернативным и потенциально более эффективным методом опроса регистра управления является использование выходов COMMTX и COMMRX процессора ARM7TDMI. Вы можете использовать данные выходы для прерывания процессора, когда:

  • слово доступно для чтения из DCC-регистра чтения данных
  • DCC-регистр записи данных свободен и доступен для использования.


Данные выходы, как правило, подключаются к системному контроллеру прерываний, управляя входами nIRQ и nFIQ процессора ARM7TDMI.

О — нотация оценки сложности алгоритмов.

О-нотация

Для оценивания трудоемкости алгоритмов была введена специальная система обозначений – так называемая О-нотация. Эта нотация позволяет учитывать в функции f (n) лишь наиболее значимые элементы, отбрасывая второстепенные.
Например, в функции f (n) = 2n2 + n – 5 при достаточно больших n компонента n2 будет значительно превосходить остальные слагаемые, и поэтому характерное поведение этой функции определяется именно этой компонентой. Остальные компоненты можно отбросить и условно записать, что данная функция имеет оценку поведения (в смысле скорости роста ее значений) вида О(n2 ).
Аналогично, для функции f (n) = 2n + 3n3 – 10 начиная с некоторого n первое слагаемое будет превосходить второе и поэтому данную функцию можно описать оценкой О(2n).
Важность О-оценивания состоит в том, что оно позволяет описывать характер поведения функции f(n) с ростом n: насколько быстро или медленно растет эта функция.
О-оценка позволяет разбить все основные функции на ряд групп в зависимости от скорости их роста:

  1. постоянные функции типа О(1), которые с ростом n НЕ растут (в оценивании алгоритмов этот случай встречается крайне редко, но все-таки встречается!)
  2. функции с логарифмической скоростью роста О(log 2 n)
  3. функции с линейной скоростью роста О(n)
  4. функции с линейно–логарифмической скоростью роста О(n*log 2 n)
  5. функции с квадратичной скоростью роста О(n2 )
  6. функции со степенной скоростью роста О(na) при а>2
  7. функции с показательной или экспоненциальной скоростью роста О(2n)
  8. функции с факториальной степенью роста О(n!)

В этом списке функции упорядочены именно по критерию скорости роста: сначала идут медленно растущие функции, потом – все более быстро растущие. Графики некоторых функций приведены на рисунке.

Мастер Йода рекомендует:  Идеи для дизайна сайтов

Отсюда можно сделать несколько выводов.

  1. При выборе однотипных алгоритмов предпочтение (при прочих равных условиях) следует отдавать алгоритмам с наименьшей скоростью роста трудоемкости, поскольку они позволят за одно и то же время решить задачи с большей размерностью
  2. Если заранее известно, что размерность решаемых задач невелика, но зато число их повторений очень большое, имеет смысл рассмотреть возможность использования алгоритмов не с самой лучшей оценкой, поскольку при малых n “лучшие” алгоритмы могут вести себя хуже, чем “плохие” (это можно заметить по графику в области начала координат)
  3. Алгоритмы класса О(2n) и О(n!) следует использовать с большой осторожностью, учитывая катастрофический рост их трудоемкости уже при n>100. Например, если число базовых операций определяется соотношением 2n, то при n=100 это число будет примерно равно 1030, и если одна базовая операция выполняется за 1 микросекунду, то это потребует около 1024 секунд, т.е. порядка 1016 лет. К сожалению, задачи с подобной трудоемкостью довольно часто встречаются на практике и их точное решение пока невозможно даже на сверхбыстрых суперкомпьютерах!

Как быть с оценкой трудоемкости программы в целом, если в программе используется несколько алгоритмов, решающих свои конкретные задачи? Есть два основных способа взаимодействия алгоритмов – последовательное и вложенное. При последовательном выполнении алгоритмов с оценками O(f1), O(f2), …, O(fk) общая трудоемкость определяется трудоемкостью алгоритма с максимальным значением:
O (программы) = Max (O(f1), O(f2), . . ., O(fk))
При вложенном выполнении общая трудоемкость есть произведение оценок вложенных друг в друга алгоритмов: O(программы) = O(f1)*O(f2)*O(f3)

Отладка программ с использованием отладчика.

При использовании интегрированной среды программирования предоставляется удобный интерфейс, позволяющий легко отлаживать разрабатываемую программу. В настоящее время стандартом де-факто стал интерфейс, похожий на программную оболочку Visual C.

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

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

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

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

Способы отладки программ.

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

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

Для отладки программ обычно применяют три способа:

1. Пошаговая отладка программ с заходом в подпрограммы;

2. Пошаговая отладка программ с выполнением подпрограммы как одного оператора;

3. Выполнение программы до точки останова.

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

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

Если в программе существует достаточно большой участок программы, уже отлаженный ранее, то его можно выполнить, не контролируя переменные, на которые он воздействует. Использование точек останова позволяет пропускать уже отлаженную часть программы. Точка останова устанавливается в местах, где необходимо проверить содержимое переменных или просто проконтролировать, передаётся ли управление данному оператору.

Практически во всех отладчиках поддерживается это свойство (а также выполнение программы до курсора и выход из подпрограммы). Затем отладка программы продолжается в пошаговом режиме с контролем локальных и глобальных переменных, а также внутренних регистров микроконтроллера и напряжений на выводах этой микросхемы.

Контроль данных при пошаговой отладке. При использовании встроенного отладчика программ для контроля переменных можно воспользоваться окном Watch. В большинстве случаев это намного выгоднее, чем использовать просмотр памяти данных. Переменные в этом окне отображаются в том формате, в котором они были объявлены в программе. Преобразование данных из одной формы представления в другую осуществляется встроенными средствами отладчика. Если же отладочная информация по какой либо причине была потеряна или программирование ведётся на языке программирования ассемблер, то состояние переменных можно проконтролировать просмотром содержимого внутренней и внешней памяти микроконтроллера. Для определения конкретной ячейки памяти микроконтроллера, занятой под переменную можно воспользоваться листингом, создаваемым редактором связей компилятора или самим компилятором, если не используется многомодульное программирование.

Не нашли то, что искали? Воспользуйтесь поиском:

Лучшие изречения: Для студентов недели бывают четные, нечетные и зачетные. 9435 — | 7438 — или читать все.

Bug O нотация: отладочная сложность программных интерфейсов

Big O нотация — это запись в математических выражениях, которая может быть применена к алгоритмам для описания их вычислительной сложности. Она дает возможность получать масштабируемость алгоритма по мере увеличения количества элементов во входных данных, которые он обрабатывает.

Что такое Big O нотация?

Big O notation — это математическая запись, которая может быть применена к алгоритмам, которые мы используем при разработке программного обеспечения. В этом контексте его целью является описание вычислительной сложности алгоритма. В частности, он позволяет оценить, насколько масштабируемым будет алгоритм по мере роста объема обрабатываемых данных. Масштабируемость, указанная нотацией big O, может использоваться для описания различных вещей, таких как время или циклы обработки, необходимые для расширения набора данных, или увеличение использования памяти или ресурсов.

Big O принадлежит к семейству так называемых асимптотических обозначений. Это включает в себя ряд различных обозначений, каждый с другой целью. Цель нотации Big O — указать верхнюю границу или наихудший сценарий для скорости роста алгоритма. Это не точная мера производительности или использования ресурсов. Например, рассмотрим алгоритм, который предлагает Big O notation, имеет линейный рост времени обработки. Удвоение размера набора данных не обязательно означает, что время работы алгоритма удвоится. Это просто означает, что время обработки верхней границы для большего набора данных будет в два раза больше, чем в худшем случае для меньшего ввода.

В нотации Big O используется заглавная буква «O», за которой следует функция в круглых скобках. Это функция, которая описывает масштабируемость. Функция почти всегда включает в себя букву «n», которая представляет собой количество элементов в обрабатываемых данных. В следующих подразделах описываются некоторые из наиболее часто встречающихся примеров.

O(1) алгоритмы — это те, которые не имеют увеличения сложности, связанной с размером входных данных; время обработки, использование памяти или другой измеряемый элемент фиксированы. Простым примером может служить интегрированный в язык запрос (LINQ), оператор «First». Он возвращает первый элемент из последовательности. Наличие большей последовательности не увеличивает время, необходимое для извлечения первого элемента.

O(log n) описывает алгоритмы с логарифмической масштабируемостью. Они увеличиваются в сложности по мере увеличения количества элементов в наборе данных, но на относительно меньшую величину по мере увеличения размера. Простой пример — алгоритм бинарного поиска для отсортированной последовательности. Каждая итерация этого алгоритма может игнорировать половину оставшихся деталей. Удвоение размера данных поиска добавляет только одну дополнительную итерацию к худшему сценарию поиска.

O(n) алгоритмы показывают линейный рост. Простой пример — поиск по несортированному набору данных путем чтения одного элемента за другим, пока не будет найден определенный элемент. В худшем случае, когда искомый элемент является последним в наборе. Добавление дополнительного элемента добавляет одну дополнительную потенциальную итерацию поиска. Этот пример подчеркивает идею о том, что Big O описывает только верхнюю границу. Набор из тысячи или миллиона элементов можно найти за одну итерацию, если элемент, который вы ищете, является первым в списке.

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

O(n 2 ), или квадратичные, алгоритмы увеличивают сложность пропорционально квадрату числа элементов во входных данных. Если у вас есть два вложенных цикла для входных данных в вашем алгоритме, например, с пузырьковой сортировкой, это, вероятно, будет O(n 2 ). Другие варианты этого — O(n x ) или полиномиальные алгоритмы. Например, три вложенных цикла будут O(n 3 ), четыре вложенных цикла — O (n 4 ) и так далее.

O (2 n ) алгоритмы дают экспоненциальный рост и очень плохую масштабируемость. Каждый дополнительный элемент входных данных может удвоить количество времени или ресурсов, используемых алгоритмом. Постоянное значение 2 может быть изменено для алгоритмов с еще более низкой масштабируемостью. Например, O(3 n ) указывает, что сложность может утроиться с каждым дополнительным элементом.

Алгоритмы, которые могут рассматривать каждую перестановку элементов в наборе входных данных, являются O(n!), давая факторный рост сложности. Примером такой масштабируемости является попытка решить задачу коммивояжера грубой силой.

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

При рассмотрении масштабируемости алгоритма для определения правильного варианта big O следует игнорировать константы. Например, представьте, что у вас есть линейный алгоритм, где каждая итерация занимает одну секунду для выполнения. Это O (n). Если вы улучшите код и уменьшите вдвое циклы обработки, необходимые для каждой итерации, вы не будете считать это O(0.5 n). Алгоритм по-прежнему O(n), хотя он работает быстрее.

При вычислении формулы для наихудшего плана выполнения для вашего алгоритма он часто не будет соответствовать одному из вышеупомянутых вариантов. В этих случаях в качестве функции используется только самый бедный элемент масштабируемости. Например, у вас может быть алгоритм, который включает в себя три вложенных цикла, за которыми следуют два вложенных цикла. Наихудший сценарий для количества итераций будет (n 3 + n 2 ). Однако, поскольку n 3 является более низкой масштабируемостью, вы бы сказали, что алгоритм был O(n 3 ).

Bug O нотация: отладочная сложность программных интерфейсов

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

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

Естественно, в короткой статье невозможно полностью объяснить все приемы и передать все те знания, что необходимы для полного понимания вопроса. Например, в Массачусетском технологическом институте (MIT), оценке сложности посвящен целый курс, причем не такой уж маленький. Крайне рекомендую его изучить, надеюсь, знания английского вам позволят. Кстати, о необходимости языка для программиста тоже хочется много всего сказать, но не сейчас.

Цель статьи, — на простых примерах познакомить читателя с самим понятием и дать полезные ссылки для более тщательного, изучения.

Когда задача имеет несколько похожих на первый взгляд алгоритмических решений, бывает сложно понять, какое из них на практике окажется наиболее оптимальным.

С этой целью, используются математические обозначения, самым известным из которых является «большое О» (Big O), для оценки асимптотики функций. Под асимптотикой понимается характер изменения функции при ее стремлении к определенной точке.

Говоря проще, мы пытаемся проанализировать, как будет расти наш график (чаще всего нагрузки на ЦП), с ростом входных данных, которые обозначаются буквой n.

Исходя из вышесказанного, O(ƒ(n)) и есть сложность алгоритма.

На самом деле, существует на только «большое О», но и ряд других обозначений. Рассмотрим их:

O(ƒ(n)) – (Big-O) – верхняя граница, «не хуже чем»
o(ƒ(n)) – (Little-o) – верхняя граница, «лучше чем»
Ω(ƒ(n)) – (Omega) – нижняя граница, «не лучше чем»
Θ(ƒ(n)) – (Theta) – точная оценка.

На практике, в подавляющем большинстве, используют оценку Big O, как наиболее простую в вычислении. Нам ведь важен не столько точный математический результат, сколько приблизительная оценка «качества» нашего алгоритма.

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

Сложность printArray будет O(n), потому что количество операций равно количеству элементов. Про такой рост еще говорят, что он — линейный. Или, например, у нас имеется вложенный цикл такого вида:

Здесь мы выполнили n операций n раз. Сложность в данном случае ужасная, она показывает степенной рост – O(n²). Если нам требуется еще один такой же вложенный цикл, получится n³ и так далее.

Простые решения можно оценивать по количеству вложенных циклов

Существуют «стандартные» оценочные значения, на которые принято ориентироваться (от лучшего к худшему):

O(1), O(log n), O(n), O(n log n), O(n^2), O(2^n), O(n!)

То есть, приблизительно прикинув сложность нашего алгоритма, мы можем говорить про Big O, что он, допустим, O(n log n). То есть, ни при каких обстоятельствах не хуже. Но в то же время, недостаточно хорош, чтобы оцениваться как O(n).

Обычно анализу подвергают не всю программу целиком, а отдельные ее части

Рассмотрим еще один интересный пример вычисления произвольно взятого элемента ряда Фибоначчи. Классическая формула гласит: Fn = Fn-1 + Fn-2 для n >= 2.

Данный алгоритм можно реализовать с помощью рекурсии:

Кажется нормальное решение, даже красивое для неопытного взгляда. Но что если потребуется вычислить 100-е число? Не так уж и много, подумаешь, всего лишь сотое. Однако, сложность данного алгоритма настолько высока, что даже незначительное увеличение входного числа, дает огромный рост.

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

На каждой «итерации» рекурсии, мы удваиваем количество операций, вызываем ее дважды. То есть 2*2*2*2… Получается дерево. Поскольку условием задано, что если n n ). Можно рассчитать более точно


Θ(1.6 n ), но на практике чаще всего достаточно приблизительной оценки. Видим экспоненциальный рост, который еще хуже степенного.

Итак, мы выяснили, что наш алгоритм расчета числа Фибоначчи ужасен. Что делать? Очевидно, разработать более эффективное решение!

Попробуем сделать по-другому, просто возьмем да просуммируем в цикле все числа, начиная с нуля, вплоть до искомого:

Решение не блещет изяществом, однако его эффективность можно оценить как O(n). То есть оно, на самом деле, гораздо лучше предыдущего. В принципе, на этом можно было бы остановиться, мы добились вполне хороших результатов. Далеко не каждый алгоритм, в реальной жизни, удается оптимизировать до такого состояния. Но мы попробуем пойти дальше.

Задача в примере чисто математическая, посмотрим, что еще написано в справочнике. Ага, оказывается, есть куда более эффективное, с точки зрения алгоритмов, решение: формула Бине. Из нее следует, что для всех n >= 0, Fn — есть ближайшее целое число к φn/√5, где φ – золотое сечение.

Перепишем нашу функцию:

Теперь у нас самый лучший по эффективности алгоритм, который только можно себе представить. Его сложность вообще не зависит от n, количество операций константно и ничтожно мало. Про такие обычно пишут O(1).

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

Влияние плохого алгоритма, в таком случае, начинает ощущаться лишь на больших нагрузках. Однако, даже в этом случае, часто слабым звеном системы становится совершенно не ЦП, а, допустим, пропускная способность интернет подключения. Или объем RAM, хотя BigO вычисляют и для оперативной памяти, да и вообще для потребления любых ресурсов компьютера.

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

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

Отладка. Общие принципы, методы отладки. Взаимосвязь процессов тестирования и отладки, использование автоматических средств отладки

Читайте также:

  1. A) оказывают непосредственное влияние на рост производительности труда предприятия и учитываются при определении показателей эффективности использования основного капитала.
  2. Hеречевые (невербальные) средства общения
  3. I. Исцеление золотушных посредством возложения рук в английских счетах
  4. I. Лекарственные средства и лекарственные препараты.
  5. I. Методы формирования сознания, методы убеждения
  6. I. Механика. Общие понятия
  7. I. Общие положения
  8. I. Общие положения
  9. I. Общие положения
  10. I. Общие положения
  11. I. ОБЩИЕ ПОЛОЖЕНИЯ
  12. I. Общие положения

Отладка (debug, debugging) — этап разработки компьютерной программы, на котором обнаруживают, локализуют и устраняют ошибки. Чтобы понять, где возникла ошибка, приходится: узнавать текущие значения переменных; выяснять, по какому пути выполнялась программа.

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

1) Использование отладчиков — программ, которые включают в себя пользовательский интерфейс для пошагового выполнения программы: оператор за оператором, функция за функцией, с остановками на некоторых строках исходного кода или при достижении определённого условия.

2) Вывод текущего состояния программы с помощью расположенных в критических точках программы операторов вывода — на экран, принтер, громкоговоритель или в файл. Вывод отладочных сведений в файл называется журналированием.

1. Отладчик – программный инструмент, позволяющий программисту наблюдать за выполнением исследуемой программы, останавливать и перезапускать её, прогонять в замедленном темпе, изменять значения в памяти и даже, в некоторых случаях, возвращать назад по времени.

2. Профилировщики – позволяют определить сколько времени выполняется тот или иной участок кода, а анализ покрытия позволит выявить неисполняемые участки кода.

3. API логгеры – позволяют программисту отследить взаимодействие программы и Windows API при помощи записи сообщений Windows в лог.

4. Дизассемблеры позволят программисту посмотреть ассемблерный код исполняемого файла

Мастер Йода рекомендует:  Гламурная ретушь

5. Сниферы помогут программисту проследить сетевой трафик генерируемой программой

6. Сниферы аппаратных интерфейсов позволят увидеть данные которыми обменивается система и устройство.

Использование языков программирования высокого уровня, таких как Java, обычно упрощает отладку, поскольку содержат такие средства как обработка исключений, сильно облегчающие поиск источника проблемы. В некоторых низкоуровневых языках, таких как Ассемблер, ошибки могут приводить к незаметным проблемам — например, повреждениям памяти или утечкам памяти, и бывает довольно трудно определить, что стало первоначальной причиной ошибки. В этих случаях, могут потребоваться изощрённые приёмы и средства отладки.

Отладка = Тестирование + Поиск ошибок + Редактирование

Виды отладки ПО, включая тестирование (в нашей стране).

1.1. Автономная отладка. Последовательное раздельное тестирование различных частей программ, входящих в ПО, с поиском и исправлением в них фиксируемых при тестировании ошибок. Она фактически включает отладку каждого программного модуля и отладку сопряжения модулей.

1.2. Комплексная отладка. Тестирование ПО в целом с поиском и исправлением фиксируемых при тестировании ошибок во всех документах (включая тексты программ ПО), относящихся к ПО в целом. К таким доку-ментам относятся определение требований к ПО, спецификация качества ПО, функциональная спецификация ПО, описание архитектуры П.О. и тексты программ ПО.

2.1. Синтаксическая отладка. Синтаксические ошибки выявляет компилятор, поэтому исправлять их достаточно легко.

2.2. Семантическая (смысловая) отладка. Ее время наступает тогда, когда синтаксических ошибок не осталось, но результаты программа выдает неверные. Здесь компилятор сам ничего выявить не сможет, хотя в среде программирования обычно существуют вспомогательные средства отладки, о которых мы еще поговорим.

Взаимосвязь процессов тестирования и отладки через алгоритм отладки.

После того как написан рабочий код производятся тестовые запуски программы на различных наборах тестовых данных.

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

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

Средства автоматического тестирования исходного кода программ.

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

Примерами таких систем могут быть: встроенный модуль doctest в Python и мультиязыковая библиотека тестирования xUnit, распространяемая на условиях GNU/GPL и LGPL. Основа применения всех этих средств и техник это разбиение одной большой задачи на ряд четких и более маленьких задач.

23. Основные принципы объектно-ориентированного программирования: инкапсуляция, наследование, полиморфизм. Отличие объектно-ориентированного подхода от модульного при разработке программ

Объектно-ориентированное программирование (ООП) — парадигма программирования, в которой основными концепциями являются понятия объектов и классов (либо, в менее известном варианте языков с прототипированием, — прототипов).

Прототип — это объект-образец, по образу и подобию которого создаются другие объекты.

Класс — это структурный тип данных, который включает описание полей данных, а также процедур и функций, работающих с этими полями данных (методов).

Поля, описанные в классе, используют для хранения составляющих состояния объекта, т.е. поля определяют состояние объектов.

Методы, описанные в классе, определяют поведение объектов. Каждый метод определяет реакцию объекта на некоторое внешнее или внутреннее сообщение.

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

Принципы объектно-ориентированного программирования.

1. Абстракция. Абстрагирование — это способ выделить набор значимых характеристик объекта, исключая из рассмотрения незначимые. Соответственно, абстракция – это набор всех таких характеристик.

2. Инкапсуляция. Инкапсуляция — это свойство системы, позволяющее объединить данные и методы, работающие с ними, в классе и скрыть детали реализации от пользователя.

Инкапсуляция — принцип ООП, согласно которому в классе объединяются поля и методы.

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

3. Наследование. Наследование — это свойство системы, позволяющее описать новый класс на основе уже существующего с частично или полностью заимствующейся функциональностью.

Наследование — возможность конструирования новых более сложных классов из уже имеющихся посредством добавления полей и определения новых методов (принцип иерархичности).

Класс, от которого производится наследование, называется базовым, родительским или суперклассом. Новый класс – потомком, наследником или производным классом. Механизм наследования обеспечивает классу-потомку возможность использования полей и методов родительских классов. Цепочки наследования могут быть неограниченной длины. При этом различные методы для каждого из наследников разрешается переопределять.

4. Полиморфизм. Полиморфизм — это свойство системы использовать объекты с одинаковым интерфейсом без информации о типе и внутренней структуре объекта.

Полиморфизм (“многообразие”) в программировании — возможность изменения кода программы в соответствии со значением некоторых параметров.

4.1. Чистый полиморфизм — возможность различной интерпретации кода функции в зависимости от типа аргументов.

4.2. Перегрузка (полиморфные имена) функций — возможность определения нескольких функций с одним именем; выбор нужной функции может определяться типами аргументов, областью видимости (внутри модуля, файла, класса и т.д.); если выбор определяется типом аргументов, то перегрузка называется параметрической.

4.3. Переопределение методов — в ООП — возможность различных определений методов в классе-потомке и классе-родителе; конкретный метод определяется классом объекта, для которого он вызывается. При переопределении методов различают простой и сложный полиморфизм.

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

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

4.4. Обобщенные функции (шаблоны) — возможность описания параметризованных классов и шаблонов функций, параметрами таких описаний являются типы аргументов методов или функций.

Отличие объектно-ориентированного подхода от модульного.

1) Объектно-ориентированный подход к проектированию прогр. продуктов основан на:

− выделении классов объектов;

− установлении характерных свойств объектов и методов их обработки;

− создании иерархии классов, наследовании свойств объектов и методов их обработки.

2) Модульное программирование — это организация программы как совокупности небольших независимых блоков, модулей, структура и поведение которых подчиняется определенным правилам.

Следует заметить, что понятие «модуль» не совпадает в данном случае с понятием «модуль» (в смысле «библиотека») языка Паскаль. Это должна быть простая, замкнутая (независимая) программная единица (процедура или функция), обозримая, реализующая только одну функцию. Для написания одного модуля должно быть достаточно минимальных знаний о тексте других, как вызывающих, так и вызываемых.

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

24. Классы и объекты: их определение, соотношение между ними. Роль составляющих класса – полей, свойств, методов. Спецификаторы доступа published, public, private, protected. Конструкторы и деструкторы, их роль. События и их использование в управлении программой

Класс — это структурный тип данных, который включает описание полей данных, а также процедур и функций, работающих с этими полями данных (методов).

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

Соотношение класса и объекта:


Понятие класса является более общим, чем понятие объекта. Объект является экземпляром класса. Класс может рассматриваться как совокупность объектов (подобно тому, как множество есть совокупность элементов). Класс может быть элементарным или подразделяться на подклассы (подобно тому как множество подразделяется на подмножества). Например, класс PERSON содержит подкласс STUDENT, который, в свою очередь, содержит объект John_Smith.

Классы имеют (например, в Delphi):

Поле класса (атрибут) в ООП — переменная, связанная с классом или объектом. Поля, описанные в классе, используются для хранения составляющих состояния объекта, т.е. поля определяют состояние объектов. Доступ к полям осуществляется по их имени.

Методы, описанные в классе (подпрограммы, которые обрабатывают поля и свойства класса), определяют поведение объектов. Каждый метод определяет реакцию объекта на некоторое внешнее или внутреннее сообщение.

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

Поля, свойства и методы класса называются членами класса.

Переменная, описанная как класс, фактически является указателем на экземпляр класса. В объектно-ориентированной программе с применением классов каждый объект является «экземпляром» некоторого конкретного класса, и других объектов не предусмотрено.

Спецификаторы доступа published, public, private, protected.

Инкапсуляция — это свойство системы, позволяющее объединить данные и методы, работающие с ними, в классе и скрыть детали реализации от пользователя.

По умолчанию (в Delphi) видимость родительских членов класса наследуется в точности, однако разрешено повышать видимость — делать поля, свойства и методы более доступными. Понижение видимости не допускается.

Уровни инкапсуляции (доступность любых членов класса):

1) Public. Члены класса, находящиеся в данном разделе, доступны из любой точки программы.

2) Private. Члены класса доступны только в том модуле, где данный класс описан. По умолчанию считается, что все поля класса расположены в разделе private.

3) Protected. Члены класса доступны в том модуле, где данный класс описан, а также внутри методов классов, являющихся наследниками данного класса и описанных в других модулях.

4) Published. Члены класса, находящиеся в данном разделе, доступны из любой точки программы. В этом разделе располагаются свойства класса: поля, доступные для редактирования и изменения значений во время проектирования и из Инспектора объектов.

5) Automated. Члены класса, находящиеся в данном разделе, доступны из любой точки программы. Описания разрешается размещать в этом разделе, только если класс является наследником стандартного класса TAutoObject(в Delphi), предназначенного для создания так называемых серверов автоматизации при использовании технологии СОМ (Competent Object Model).

Конструкторы и деструкторы.

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

Когда объект уничтожается (например, он был описан внутри процедуры как локальная переменная и удаляется из памяти при ее завершении), вызывается другой метод — деструктор, который выполняет различные дополнительные действия по освобождению памяти, если это необходимо.

События и их использование в управлении программой.

Событие в ООП — это сообщение, которое возникает в различных точках исполняемого кода при выполнении определённых условий.

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

Для решения поставленной задачи создаются обработчики событий: как только программа попадает в заданное состояние, происходит событие, посылается сообщение, а обработчик перехватывает это сообщение.

25. Основные отличия языка Object Pascal (Delphi) от Turbo Pascal. Динамические массивы в Delphi: описание, особенности, применение

Turbo Pascal — интегрированная среда разработки для языка программирования Pascal и язык программирования в этой среде, диалект языка Паскаль от фирмы Borland.

Delphi — среда программирования, в которой используется язык программирования Object Pascal.

Object Pascal — результат развития языка Turbo Pascal, который, в свою очередь, развился из языка Pascal. Pascal был полностью процедурным языком.

Turbo Pascal, начиная с версии 5.5, добавил в Pascal объектно-ориентированные свойства, а в Object Pascal — динамическую идентификацию типа данных с возможностью доступа к метаданным классов (то есть к описанию классов и их членов) в компилируемом коде, также называемом интроспекцией — данная технология получила обозначение RTTI.

Так как все классы наследуют функции базового класса TObject, то любой указатель на объект можно преобразовать к нему, после чего воспользоваться методом ClassType и функцией TypeInfo, которые и обеспечат интроспекцию.

Object Pascal (Delphi) является результатом функционального расширения Turbo Pascal.

Объектная модель Delphi Pascal по сравнению с моделью, использованной Borland Pascal 7.0, является более полной:

− ограничение доступа к полям и методам за счет определения собственного интерфейса к каждому полю класса (пять типов секций при объявлении класса, использование свойств);

− более развитые механизмы реализации полиморфных методов (абстрактные, динамические методы)’,

− средства работы с метаклассами (переменные метаклассов, методы классов, механизм RTTI).

Динамические массивы в Delphi.

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

Объявление массива: var My_Array: array of BaseType;

При таком объявлении память не выделятся, и первоначальный размер массива — нулевой.

Установка размера массива: SetLength(My_Array,100);

Получение числа элементов массива: n:=Length(My_Array);

Обращение к первому элементу массива: My_Array[0]:=10; x:=My_Array[0];

Объявление двумерного массива: var A: array of array of BaseType;

Если присвоить переменной динамический массив, то его содержимое не копируется, присваивается только указатель на массив. А вот если применить к новому массиву SetLength, то тогда и произойдет копирование.

26. Структура модулей в Delphi. Интерфейсная, исполняемая части, инициирующая и завершающая части. Процедуры и функции: особенности в Delphi

Проект в Delphi представляет собой набор программных единиц – модулей.

Delphi позволяет поместить свои функции и процедуры в отдельный модуль (Unit), а затем использовать процедуры и функции модуля в своих программах, указав имя модуля в списке модулей, необходимых программе (инструкция uses). Модуль – это файл с расширением *.pas.

Начинается модуль заголовком — инструкцией unit, в которой указано имя модуля.

Модуль состоит из последовательности разделов. Каждый раздел начинается ключевым словом и продолжается до начала следующего раздела. В раздел implementation (реализация) нужно поместить процедуры и функции, объявленные в разделе interface.

Структура модулей в Delphi.

Interface

Implementation

initialization

finalization

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

unit ИмяМодуля;

interface // раздел интерфейса

const // раздел объявления констант

type // раздал объявления типов

var // раздел объявления переменных

implementation // раздел реализации

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

Процедуры и функции в Delphi.

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

Процедура — это разновидность подпрограммы. Обычно подпрограмма реализуется как процедура в двух случаях:

− когда подпрограмма не возвращает в основную программу никаких данных;

− когда подпрограмма возвращает в вызвавшую ее программу больше чем одно значение.

Параметры – это входные данные.

Дата добавления: 2015-04-24 ; Просмотров: 4026 ; Нарушение авторских прав? ;

Нам важно ваше мнение! Был ли полезен опубликованный материал? Да | Нет

Средства отладки. Программные, внутрисхемные симуляторы, отладочные платы

Рассматриваемые в этом разделе 8–разрядные микроконтроллеры (МК) ис­пользуются во встраиваемых системах управления, разработка которых затраги­вает все этапы проектирования: составление алгоритма функционирования и исход­ного текста программы, выбор элементной базы, автономную и полную отладку аппаратных средств и программного обеспечения системы, вплоть до совмест­ной отладки с объектом управления в реальном времени. Ниже рассматриваются основные средства и способы, используемые для отладки микроконтроллерных систем управления.

Программные симуляторы.

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


На основе тестирования модели ведется разработка реального устройства уп­равления. Программные симуляторы используется на начальной стадии проекти­рования реального устройства. Полноэкранный графический интерфейс пользователя современных симуляторов позволяет:

● быстро проверить правильность алгоритма выполнения программы и отдель­ных операций;

● вести наблюдение за исполнением любого фрагмента программы и реакцией микроконтроллера на различные события;

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

● загрузка файлов программ управления в широко распространенных форматах,

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

● контроль и модификация состояния ресурсов симулируемого микроконтрол­лера, содержимого ячеек памяти и регистров; встроенных периферийных устройств (таймеров, портов, АЦП, систем прерываний и др.). В процессе вы­полнения программы на экране компьютера отображается текущее состояние модели;

● высокоуровневая символьная отладка программ при условии использования компиляторов, поставляющих необходимую отладочную информацию. Такую возможность предоставляют высокоуровневые симуляторы–отладчики (High–Level Debuggers);

● вывод статистической информации по результатам прогона отлаживаемой программы. Эта информация необходима для оптимизации структуры программы. Дополнительные возможности. К ним следует отнести:

● использование специальных файлов входных воздействий, которые позволяют задать симулятору различные комбинации входных потоков данных и формы сигналов. Входные сигналы изменяют состояние устройства в различные мо­менты времени и позволяют контролировать выполнение операций в течение определенного числа машинных циклов. Для понимания работы устройства эти файлы обычно пишутся в текстовом формате, поэтому на их создание затрачивается много времени;

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

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

● перечень поддерживаемых микроконтроллеров и встроенных узлов периферии, а также компиляторов и форматов;

● скорость, детальность и точность симуляции. К достоинствам программной симуляции следует отнести:

● возможность детального исследования и анализа алгоритма работы проекти­руемого устройства, многократного воспроизведения рабочих ситуаций бла­годаря вмешательству в процесс исполнения тестируемой программы;

● отсутствие в ограничении ресурсов МК при отладке программы управления;

● использование при симуляции исходного текста программы, а не файлов, сгенерированных компилятором (объектного кода) значительно упрощает контроль выполнения программы;

● сравнительно низкая стоимость;

● расширение воспроизводимости путем использования файлов входных воз­действий. Недостатки программной симуляции:

Мастер Йода рекомендует:  5 вопросов по React, которые могут попасться на собеседовании

● невозможность использования реальных источников входных сигналов и фор­мирования реальных выходных сигналов управления. Разработка файла вход­ных воздействий может потребовать много времени и больших затрат;

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

● имеются широкие дополнительные возможности по вмешательству в процесс исполнения тестируемой программы управления;

● отсутствуют ограничения в использовании ресурсов, связанных с обслужива­нием процесса отладки. Этап моделирования на программном симуляторе проводится на самой ран­ней стадии работы над проектом, когда аппаратная часть находится еще в стадии проектирования. Для иллюстрации возможностей внутрисхемных эмуляторов, приведем крат­кое описание программного отладчика–симулятора PDS–PIC, разработанного и поставляемого российской фирмой «Фитон».

Программный отладчик–симулятор PDS–PIC

Отладчик–симулятор PDS–PIC работает в среде Windows® и предназначен для написания и отладки программ, ориентированных на микроконтроллеры PICMicro фирмы Microchip. В его состав входят:

● встроенный многооконный редактор, поддерживающий операции с блоками текста поиск/замену, цветовое выделение синтаксических конструкций ас­семблера;

● встроенный менеджер проектов, поддерживающий автоматическую компиля­цию программ, написанных для макроассемблера PASM–PIC и для макроас­семблера MPASM фирмы Microchip;

● средства отладки программ, обеспечивающие отслеживание выполнения программы по ее исходному тексту, просмотр и изменение значений любых переменных, анализ эффективности программного кода, точку останова по условию и доступу к ячейкам памяти, просмотр стека вызовов подпрограмм, точный подсчет интервалов времени, выполнение программы назад в поша­говом и непрерывном режиме и многое другое;

● средства моделирования встроенных в микроконтроллер периферийных уст­ройств (таймеров, АЦП, системы прерываний, портов и др.) и внешней среды (например, можно задавать различные периодические и непериодические внешние сигналы на выводах микроконтроллера, моделировать работу внеш­ней логики, наглядно отображать различные индикаторы, строить графики, моделировать клавиатуру);

● средства пользовательского интерфейса, обеспечивающего:

• сохранение конфигурации окон и параметров настройки;

• сохранение и восстановление неограниченного количества файлов конфи­гурации;

• настройку цветов, шрифтов и других параметров для всех окон одновре­менно и для каждого окна в отдельности;

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

● программное обеспечение для инструментального (обычно персонального) компьютера, который имитирует программно–логическую модель целевого МК, включая алгоритмы работы периферийных модулей. На основе целевого МК ведется разработка устройства управления;

● аппаратные средства, размещенные на отдельной плате. Основным элемен­том платы является реальный МК, в качестве которого может быть использо­ван как целевой (разрабатываемый) контроллер, так и замещающий контрол­лер. В последнем (более распространенном) случае периферийные модули должны быть идентичны модулям целевого контроллера. Число линий портов ввода/вывода замещающего МК может превышать аналогичное число целе­вого МК.

Дополнительные линии используются для обмена с инструменталь­ным компьютером. Выводы замещающего контроллера, которые по функцио­нальному назначению совпадают с выводами целевого МК, должны быть вы­ведены на разъем с цоколевкой последнего. Разъем служит для подключения целевого (разрабатываемого) контроллера.

Особенности отладки

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

● загрузку и выполнение (в пошаговом или непрерывном режимах) прикладной программы;

● остановку в контрольных точках;

● модификацию прикладной программы;

● чтение/запись памяти и регистров. Программа монитора хранится в ПЗУ замещающего МК. При прогонке прикладной программы:

● состояния входов целевого МК считываются с входов замещающего МК и пе­редаются в инструментальный компьютер;

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

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

Достоинство внутрисхемных симуляторов: возможность совместной отладки аппаратной и программной частей устройства с объектом управления при сохра­нении доступа разработчика ко всем внутренним ресурсам МК; недостаток — замедленное исполнение алгоритма управления, что заставляет предъявлять оп­ределенные требования к быстродействию объекта управления и МК. Отладочные платы. Особенности отладочных плат. Основные особенности отладочных плат (Evaluation Board), или оценочных модулей, состоят в следующем:

● подлежащую отладке программу управления исполняет реальный целевой микроконтроллер (МК), используемый в разрабатываемом устройстве;

● отладка программного обеспечения и аппаратной части разрабатываемого устройства (приложения) реализуется в реальном времени;

● параметры входных и выходных сигналов МК отладочной платы совпадают с аналогичными параметрами целевого МК на плате конечного изделия. Отладочные платы включают аппаратные и программные средства. Аппаратные средства отладки содержат:

микроконтроллер. Как правило, на плате устанавливается контроллер с от­крытой архитектурой, допускающий подключение внешней памяти и распола­гающий внешними шинами адреса и данных. Микроконтроллер отладочной платы должен принадлежать к тому же семейству, что и целевой (разрабаты­ваемый) контроллер;

память программ, состоящая из постоянной и оперативной памяти. В посто­янной памяти размещаются программа обмена с персональным компьюте­ром и программа монитора отладки, в оперативной памяти — разрабатывае­мая программа управления;

● набор периферийных средств: простейшая клавиатура, индикаторы в виде светодиодов и др.;

● последовательный интерфейс для связи с инструментальным (персональным) компьютером. Программное обеспечение для инструментального компьютера, вклю­чающее программу монитора отладки, которая позволяет:

● загрузить код прикладной программы из инструментального компьютера в оперативную память отладочной платы, а также внутренние регистры микро­контроллера требуемыми данными (с консоли);

● запустить прикладную программу на исполнение в непрерывном режиме, по шагам или с остановом в контрольных точках;

● передавать в инструментальный компьютер состояния внутренних программ­но доступных регистров и ячеек памяти контроллера после останова в конт­рольных точках для отображения их состояния на экране дисплея.

Достоинство отладочных плат — прикладная программа целиком или ее от­дельные фрагменты выполняются в реальном времени, поэтому управляемый объект может работать непосредственно под управлением отладочной платы.

Недостаток состоит в том, что часть ресурсов МК (например, контроллер последовательного интерфейса, таймер, ячейки оперативной памяти) задейство­вана для выполнения программы монитора отладки и не может быть использова­на разработчиком при моделировании прикладной программы.

Схемные эмуляторы

Назначение. Схемный (внутрисхемный) эмулятор (ln–Circuit Emulator — ICE) представляет собой программно–аппаратный комплекс, предназначенный для отладки программного обеспечения и аппаратной части разрабатываемого устройства в реальном времени. При эмуляции связь с инст­рументальным компьютером и управление режимами отладки возложены на за­мещающий контроллер, входящий в состав схемного эмулятора, благодаря чему:

при отладке разрабатываемой программы отсутствуют ограничения в исполь­зовании внутренних ресурсов моделируемого микроконтроллера;

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

● можно получить параметры входных и выходных сигналов, совпадающие с аналогичными параметрами целевого МК на плате конечного изделия. Схемные эмуляторы используются на этапе комплексной отладки всей системы:

● для проведения отладки в непрерывном режиме и между точками останова;

● для выполнения отлаживаемой программы управления с использованием замещающего микроконтроллера, полностью идентичного (или близкого по параметрам) к целевому микроконтроллеру;

● для получения параметров входных и выходных сигналов МК отладочной пла­ты, совпадающих с аналогичными параметрами целевого МК на плате конеч­ного изделия. Функциональные возможности. Схемный эмулятор позволяет:

● загружать отлаживаемую программу в память системы и выполнять ее в по­шаговом или непрерывном режиме, останавливать программу при выполне­нии заданных условий;

● выводить на монитор состояния и содержимое всех регистров и памяти и при необходимости модифицировать их;

● вести символьную отладку, т. е. одновременно контролировать ход выполнения программы и наблюдать соответствие между исходным текстом программы и состоянием всех ресурсов эмулируемого микроконтроллера. Символьная отладка позволяет оперировать с более приемлемыми для человека символь­ными именами, не требуя запоминания машинных кодов команд и адресов;

● выполнять трассировку, т. е. вести для последующего анализа запись внеш­них сигналов и (или) состояния внутренних регистров микроконтроллера;

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

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


Состав и устройство эмулятора

В состав эмулятора входят следующие блоки:

● замещающий контроллер (эмуляторный кристалл), размещенный в эмуляторной головке. Замещающий контроллер работает под управлением компьютера. Для работы с семейством микроконтроллеров используется определенный тип эмуляторов, причем для эмуляции каждой модели семейства предусмот­рена соответствующая эмуляторная головка;

● блок памяти трассы, в котором хранятся значения сигналов, устанавливаемых на выводах микроконтроллера в процессе выполнения программы (возможно содержимое некоторых регистров);

● блок контрольных прерываний для останова в контрольных точках, заданных пользователем с клавиатуры компьютера;

● оперативная память (ОЗУ), которая заменяет в процессе отладки внутреннее ПЗУ команд микроконтроллеров (возможно, другие разделы памяти, внешний доступ к которым в процессе отладки ограничен). Благодаря такой замене можно в процессе отладки производить оперативное изменение содержимо­го этой памяти. После отладки содержимое эмуляционного ОЗУ переносится в рабочее ПЗУ системы;

● таймер для контроля времени выполнения отлаживаемых фрагментов про­граммы. Конструктивно схемный эмулятор представляет собой прибор, размещенный в отдельном корпусе с автономным источником питания. С инструментальным компьютером он связан через последовательный или параллельный порт. Эмуляторная головка с помощью плоского кабеля соединена с корпусом прибора. За­мещающий контроллер, подключается:

● с одной стороны к внешней памяти программ ОЗУ, используемой вместо внутренней памяти EPROM или ROM целевого МК, и схеме управления. Внеш­няя память ОЗУ подключена к инструментальному компьютеру;

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

Процесс отладки

С помощью схемного эмулятора в систему вводится те­стовая (или рабочая) программа и контролируется ее выполнение путем преры­ваний в контрольных точках. Условиями прерываний служат различные комбина­ции значений адреса, данных и управляющих сигналов, поступающих на выводы эмулирующего микроконтроллера. Эти комбинации могут быть заданы пользова­телем с клавиатуры управляющего компьютера.

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

Число устанавливаемых контрольных точек обычно составляет несколь­ко десятков. Время выполнения фрагментов программы задает таймер с учетом реальной тактовой частоты системы. Дизассемблер дает возможность анализи­ровать выполнение программы в соответствии с ее исходным текстом на языке ассемблера. Программные средства. Программное обеспечение эмулятора включает в себя:

● служебную программу (монитор), которая обеспечивает работу всех блоков под управлением базового компьютера;

● компилятор (или ассемблер), который позволяет программировать работу си­стемы на языке высокого уровня (или ассемблера);

● отладчик. Эти программные средства обычно функционируют в составе интегрирован­ной среды проектирования/отладки и обеспечивают в процессе отладки выдачу данных на экран монитора в удобном для пользователя многооконном формате. Большинство современных эмуляторов используют символьные отладчики и дизас­семблеры, применение которых делает процесс отладки более простым и на­глядным.

Упрощенные модели эмуляторов

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

Введение в программирование. Отладка

Древние легенды повествуют о знаменитом мотыльке, попавшем в реле компьютера Mark II. Именно с него и начали называть «багами» ошибки в программах (англ. bug — насекомое).

Много других интересных вещей об отладке расскажет профессор MIT Джон Гуттаг.

Трудились над этой лекцией:

перевод — Асель Марченко;

редактура — Вероника Бородкина и Зоя Дрепина;

корректура — Елена Кадырова;

монтаж — Олег Жданов.

Хочешь больше интересных переводов? Создай их сам! Пиши в сообщения нашей группы vk!

Дубликаты не найдены

замечательное начинание. буду ждать продолжения 🙂

Использовать бинарный поиск — худшее что он мог посоветовать. В первую очередь покрывать тестами/дебажить надо точки входа/выхода.

Надеялся найти новые методики отладки или хотя бы классификацию/анализ существующих подходов — но к сожалению лекция для совсем начинающих.

P.S. За перевод всё равно спасибо, это очень круто что кто-то занялся переводом лекций по программированию.

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

1. Очень распространено мнение, что код надо писать так, чтобы каждая функция не занимала больше строчек чем вмещается в условный монитор. Например лично для себя я поставил планку в 40-50 строк. Если какая-то функция разрастается больше этого размера — значит ее можно и нужно оптимизировать и разбивать на функицональные части.
Так вот — бинарный поиск вот именно что эффективен в БОЛЬШИХ функциях. Чем более мелкий кусок кода нужно отдебажить — тем менее удобен и эффективен данный метод.

2. Этот пункт про грабли — каждый разработчик/менеджер/тестировщик должен на них наступить. Потому как без осознания следующих двух предложений работа в более/менее крупном проекте противопоказана.
ВСЕГДА есть время написать тесты. Их НАДО писать.
Тут не должно быть оправданий — потратить 10% от общего времени на задачу на написание тестов — это гораздо лучше/выгоднее чем тратить многократно больше ПОТОМ. К тому же цена ошибок/багов/недоработок на продакшене — вполне ощутимая и осязаемая сумма в долларах.
Из личных наблюдений — разработчики которые следуют методе TDD, выполняют свою работу быстрее чем прочие другие. Даже с учетом времени написания тестов. Потому что они, начав с написания тестов — уже знают для чего они пишут этот код и какой результат он должен выдавать.

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

Каждое мнение имеет право быть. И я вполне понимаю ваши аргументы — потому как и сам часто шел по пути наименьшего сопротивления в разработке. Но со временем они, лично для меня, стали не убедительными.

Bug O нотация: отладочная сложность программных интерфейсов

Другое направление — сделать, чтобы отладка нужна была как можно реже. Для этого применяются:

  • Контрактное программирование — чтобы программист подтверждал другим путём, что ему на выходе нужно именно такое поведение программы. В языках, в которых контрактного программирования нет, используется самопроверка программы в ключевых точках.
  • Модульное тестирование — проверка поведения программы по частям.
  • Статический анализ кода — проверка кода на стандартные ошибки «по недосмотру».
  • Высокая культура программирования, в частности, паттерны проектирования, соглашения об именовании и прозрачное поведение отдельных блоков кода — чтобы объявить себе и другим, каким образом должна вести себя та или иная функция.
  • Широкое использование проверенных внешних библиотек.

Безопасность программного кода и отладка

В программном коде может быть так называемое недокументированное поведение — серьёзные ошибки, которые не проявляются при нормальном ходе выполнения программы, однако весьма опасны для безопасности всей системы в случае целенаправленной атаки. Чаще всего это результат ошибок программиста. Наиболее известные примеры — это SQL-инъекция и переполнение буфера. В данном случае задача отладки это:

  • Выявление недокументированного поведения системы
  • Устранение небезопасного кода

Bug O нотация: отладочная сложность программных интерфейсов

Группа: Главные администраторы
Сообщений: 14349
Регистрация: 12.10.2007
Из: Twilight Zone
Пользователь №: 1

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

Чуть больше правды о багах — под катом

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

Поскольку работал в web-разработке, примеры взяты из web’а, но, думаю, не так сложно спроецировать их и на системное и прикладное ПО

По степени критичности (Severity)

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

Группы ошибок могут быть очень разные, где-то они закреплены корпоративным стандартом, где-то — ограничениями действующей системы багтрекинга, где-то — договоренностью команды. Привожу наш вариант.

Блокирующие (Blocker) – Ошибки, из-за которых дальнейшая работа с системой становится невозможной.

Пример: Работа на сайте доступна только зарегестрированным пользователям, а вход возможен только после подтверждения e-mail, указанного при регистрации. На почту не приходит письмо. Работа с системой, соответственно, невозможна.

Важные (Major) — Из-за таких ошибок система, в целом, работает, но что-то работает не так.

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

Обычные (Normal) — Как правило, к этой категории баги относят очень редко. В качестве примера, могу написать что-то вроде не работает кнопка «Запомнить меня» на сайте.

Малозначимые (Minor) — к таким, как правило, относятся небольшие баги, типа опечаток, «плавания» вёрстки в IE6 на определенной странице в админке и т.п. Редко исправляются по одному, собираются в несколько десятков/сотен/тысяч в зависимости от продукта и фиксятся «пачкой»

По приоритету (Priority)

Как быстро надо пофиксить тот или иной баг.

FIX IN RELEASE — Пофиксить в новой версии продукта. Как правило, относится к багам, обнаруженным в процессе тестирования нового функционала.

MUST FIX — Пофиксить как можно быстрее. Как правило включает в себя блокирующие баги, которые должны быть исправлены в специальном сервис паке, до выхода новой версии.

FIX IF TIME — «Пофиксить, если есть врёмя» — к этой категории как правило относятся минорные баги.

NEVER FIX — «Не фиксить никогда». Например, какая та фича будет удалена из следующей версии продукта, либо найдена в продукте, который уже более не поддерживается, или его поддержка прекратится в ближайшее время.

Конечно, есть еще куча разных вариантов классификаций. Собственно, этот пост и не претендовал на роль Библии тестировщика. Просто, решил поделиться тем, чем пользовался сам.

Пользователь Ocelot предложил следующее:

Забыли классификацию багов по частоте возникновения:

1) Возникает у всех всегда.

2) Возникает у всех время от времени.

3) Возникает на определенной конфигурации всегда.

4) Возникает на определенной конфигурации иногда.

Добавить комментарий