Федеральное государственное бюджетное образовательное учреждение высшего профессионального образования «МОСКОВСКИЙ ГОСУДАРСТВЕННЫЙ УНИВЕРСИТЕТ ЛЕСА» Н.В. Ефремов Создание процессорной системы на кристалле ПЛИС и последующее её исследование Рекомендовано к изданию Редакционно-издательским советом университета в качестве учебно - методического пособия для студентов специальности 230100 факультета электроники и системотехники Москва Издательство Московского государственного университета леса 2012 УДК 004.896(075) Е92 Разработано в соответствии с Федеральным государственным образовательным стандартом ВПО 2009 г. по направлению подготовки 230100 «Информатика и вычислительная техника» на основе программы дисциплины «Организация ЭВМ и систем» Рецензент: доцент кафедры управляющих интеллектуальных систем МИФИ Е.Ф. Березкин Работа подготовлена на кафедре вычислительной техники Ефремов Н.В. Е92 Создание процессорной системы на кристалле ПЛИС и последующее её исследование: учебно - методическое пособие. – М.: ФГБОУ ВПО МГУЛ, 2012. -61 с. Приводится описание пяти лабораторных работ по дисциплине «Организация ЭВМ и систем», в которых реализуется процессорная система внутри кристалла ПЛИС и исследуются особенности созданной системы. Предназначено для студентов, обучающихся по специальности «Вычислительные машины, комплексы, системы и сети». Пособие может быть полезным также и для студентов смежных специальностей. УДК 004.896(075) ©Н.В. Ефремов, 2012 ©ФГБОУ ВПО МГУЛ, 2012 4 Предисловие В настоящее время программируемые логические интегральные схемы (ПЛИС) являются одним из наиболее быстро развивающихся направлений современной цифровой микроэлектроники. Привлекательность этой технологии заключается в предоставлении конечному пользователю возможности быстрого создания цифровых устройств с произвольной внутренней структурой, включая законченные системы обработки информации [1,2]. Причем, благодаря мощным системам автоматизации проектирования [3], предоставляемым в минимальной конфигурации производителями ПЛИС бесплатно, проектирование и изготовление законченных устройств стало возможным даже в условиях учебных лабораторий и домашних рабочих мест, оборудованных персональным компьютером. Уровень интеграции современных ПЛИС оценивается десятками миллионов вентилей, а их быстродействие характеризуется рабочими частотами в сотни мегагерц [1]. На кристаллах с подобными параметрами можно реализовать законченную систему обработки информации, обладающую высокими качественными показателями. Такие системы называются системами на программируемом кристалле (SOPC, System On Programmable Chip). Одним из мировых лидеров в области производства ПЛИС, а также систем автоматизации проектирования, средств программирования и отладки является компания Altera . Разработанный ею учебный стенд Altera® DE2-70 [4] используется в качестве технической базы лабораторного практикума по дисциплине «Организация ЭВМ и систем». В состав стенда входит ПЛИС Cyclone® IIC70 FPGA и большое количество дополнительных компонентов, включая микросхемы статической, динамической и флешь памяти, а также типовой периферии, позволяющих создавать на базе стенда широкий диапазон различных проектов. Причем, проекты могут представлять собой сложные аппаратно программные комплексы, включающие полный набор технических средств стенда. Целью лабораторного практикума является получение практических навыков в создании вычислительных систем, реализованных внутри кристалла ПЛИС, и программных приложений, предназначенных для созданных систем. В настоящем пособии содержатся описания первых пяти лабораторных работ, выполняемых студентами по дисциплине «Организация ЭВМ и систем». В первой работе выполняется знакомство с приложением Altera Monitor Program (АМР) [5,6]. С помощью этого средства осуществляется реализация в кристалле ПЛИС процессорной системы «DE2-70 Media 5 Computer» и исследование созданной процессорной системы. В индивидуальном задании предлагается написать программу тестирования оперативной памяти системы с выводом результатов на светодиоды. Во второй работе студенты продолжают знакомство с созданной процессорной системой. Они разрабатывают несложные подпрограммы и изучают на их примере разные способы передачи им параметров. Продолжают знакомство с АМР, получают навыки в использовании файлов с исходными данными и с кодами программ в процессорной системе. Третья работа посвящена изучению возможностей ввода/вывода информации в процессорной системе. В качестве периферийных устройств используются кнопки, переключатели, светодиоды, семисегментные индикаторы, жидкокристаллический монитор LCD, содержащиеся в стенде. Реализуется ввод/вывод в режиме прерываний. Рассматриваются программные прерывания и исключения процессорной системы. В четвертой работе исследуется интервальный таймер, аппаратно реализованный в процессорной системе. Студенты изучают его возможности, после чего используют таймер в своих программных приложениях. В последней части работы им предлагается создать часы реального времени, отображающие текущее время на семисегментных индикаторах стенда. Пятая работа посвящена изучению интерфейса JTAG, посредством которого осуществляется связь процессорной системы, реализованной на стенде, с инструментальным компьютером. В этой же работе исследуются инфракрасный порт и интерфейс RS232, применяемые для сопряжения двух процессорных систем, реализованных на разных стендах. Описание каждой работы содержит раздел подготовки к работе, в который включены пункты заданий по изучению теоретического материала и по уяснению программных фрагментов, представленных в исходных файлах, порядок выполнения работы и требования по оформлению отчета. В приложениях к работам содержатся листинги исходных файлов программ с подробными комментариями. В конце пособия приводится список рекомендуемой для подготовки к лабораторным работам литературы, включая ресурсы сети Интернет. Используемые в лабораторных работах программные заготовки написаны на языке ассемблер, приближенном к аппаратным средствам процессорной системы. Это, по мнению автора, позволит более полно отразить архитектурные особенности процессора NIOSII, являющегося основой исследуемой системы «DE2-70 Media Computer». Планируется создание второй части лабораторного практикума, посвященной обработке мультимедийной информации на реализованной в кристалле процессорной системе. 6 Лабораторная работа №1 Создание процессорной системы на кристалле ПЛИС и первое исследование созданной системы Цель работы: знакомство с процессорной системой «DE2-70 Media Computer» и с программным приложением Altera Monitor Program. Проект, содержащий процессорную систему, предварительно создан с помощью средства SOPC Builder [5,7], входящего в состав пакета Quartus II. Исходные файлы лабораторной работы Исходными являются следующие файлы Project.qpf, Project.ptf, Project.sof, TEST_DE2_70_Media_Computer.s, lab1_part3_DE.s, LCD_DE2_70.s. Первый из них содержит проект процессорной системы, созданный в Quartus II, второй - файл с описанием процессорной системы, созданный SOPC Builder, третий является файлом конфигурирования ПЛИС. Файл TEST_DE2_70_Media_Computer.s содержит программу тестирования процессорной системы. Файл lab1_part3_DE.s содержит программу нахождения наибольшего числа из списка. Файл LCD_DE2_70.s содержит фрагмент программы работы с жидкокристаллическим дисплеем. Подготовка к лабораторной работе 1. Изучите описание процессора NIOS II [5,8]. Включите в отчет описание регистровой структуры процессора, типов используемых команд, форматов команд и способов адресации. Уясните выполнение команд работы с оперативной памятью и с портами ввода вывода. Включите их описание в отчет. Уясните выполнение команд условного перехода. Включите в отчет описание нескольких команд, включая коды операций команд bge и blt. 2. Изучите описание процессорной системы, реализованной на кристалле, соответствующей используемому лабораторному стенду [5,9]. Включите в отчет структурную схему процессорной системы и карту памяти, на которой должны быть отражены адреса оперативной памяти и портов ввода вывода периферийных устройств системы. 3. Прочитайте описание приложения Altera Monitor Program (АМР). Включите в отчет основные команды для отладки программ, выполняющихся на реализованной процессорной системе. 7 4. Уясните пункты задания, выполняемого в текущей лабораторной работе. 5. Уясните, как работает программа lab1_part3_DE, нахождения наибольшего числа из списка. Включите текст этой программы в отчет. Подготовьте новые исходные данные для тестирования программы. Включите их в отчет. 6. Изучите принцип работы жидкокристаллического дисплея [5,9]. Подготовьте коды команд для управления индикатором LCD и коды ASCII для отображения на дисплее LCD Вашей фамилии и имени (для выполнения пунктов части 3 задания). Включите их в отчет. Таблица кодов ASCII находится в приложении. 7. Уясните логику работы программы взаимодействия с LCD индикатором. Она находится в файле LCD_[название вашего стенда].s. Включите текст этой программы в отчет. 8. Напишите фрагменты программ, выполняющие п.19 части 4, части 5 и 6 настоящего описания. Порядок выполнения лабораторной работы Часть 1. Реализация процессорной системы на кристалле, загрузка и выполнение тестовой программы 1. Запустите приложение Altera Monitor Program (AMP) с помощью щелчка мыши по пиктограмме на рабочем столе. 2. Создайте новый проект в приложении AMP. Для этого в окне AMP щелкните по команде File приложения AMP. В появившемся меню выполните команду New Project. Появится окно New Project Wizard. Задайте в нем имя рабочей папки, в которой будет храниться проект и имя проекта. Папка предварительно должна быть создана. Для перехода к следующему окну нажмите Next. 3. В появившемся окне следует определить используемую процессорную систему. Для этого в поле Select a system щелкните мышью по значку раскрытия списка. В появившемся списке выберите строку «DE2-70 Media Computer». В случае если требуется сконфигурировать самостоятельно спроектированную процессорную систему, то следует выбрать строку Custom system. 4. В полях System Details появятся названия файла конфигурирования процессорной системы с расширением .ptf и файла прошивки кристалла с расширением .sof, в случае если в предыдущем пункте была выбрана заранее спроектированная процессорная система из предложенного списка. В случае использования специализированной 8 процессорной системы эти поля следует заполнить самостоятельно. Для перехода к следующему окну нажмите кнопку Next. 5. В появившемся окне следует определить тип используемой программы. Для этого в поле Program Type в предложенном списке выберите тип Assembly Program. Установите галочку в поле Include sample program with the project для включения в следующее поле названий образцов программ. Выберите в этом поле программу Test Media Computer. Для перехода к следующему окну нажмите кнопку Next. 6. В следующем окне следует определить исходные файлы используемой программы. Если в предыдущем пункте была выбрана программа из предложенных образцов, то это поле будет заполнено автоматически. Если в предыдущем пункте не использовалась опция включения образцов программ, то в поле Source files следует добавить имена исходных файлов. Для этого можно использовать кнопку Add.. В случае выбора нескольких исходных файлов их компиляция будет выполняться в том же порядке, что и в списке, а результирующему исполняемому файлу будет присвоено имя первого файла в списке. В разделе Program Options в поле Start symbol следует указать имя метки начальной команды программы. Для перехода к следующему окну нажмите Next. 7. В появившемся окне следует определить параметры системы. Если используется один программатор, то поля Host Connection и Processor будут заполнены автоматически. В противном случае эти поля следует заполнить самостоятельно. В поле Terminal Device следует указать JTAG_UART. Это будет означать, что в качестве терминального устройства будет использоваться соответствующее окно AMP. Для перехода к следующему окну нажмите кнопку Next. 8. В следующем окне следует определить установки памяти процессорной системы. По умолчанию Reset vector address равен 0, а Exception vector address устанавливается равным 0х20. Если эти адреса должны быть изменены, то их следует задать при конфигурировании процессорной системы в SOPC Builder. Далее в разделе Memory options следует указать, какая память будет использоваться для хранения программ и данных. В поле .text sections следует задать память SDRAM/s1, в поле Start offset in device следует задать значение 0х400. Это значит, что сегмент кода будет размещен в динамической памяти, начиная со смещения 0х400. В поле .data sections также следует задать память SDRAM/s1, а в поле Start offset in device следует задать значение 0х400. В случае если использована одна и та же память для размещения сегмента кода и данных, сегмент данных будет размещен сразу после сегмента кода. Для завершения работы New Project Wizard нажмите кнопку Finish. 9. Если в предыдущих пунктах была определена процессорная система из предложенного списка, то появится окно, предлагающее 9 выполнить загрузку процессорной системы в кристалл ПЛИС. В противном случае, для загрузки процессорной системы следует воспользоваться командой Programmer из меню Tools пакета Quartus II. Процесс конфигурирования кристалла сопровождается свечением голубого светодиода, а включение второго голубого светодиода означает успешное завершение процесса конфигурирования кристалла. 10. Для того чтобы загрузить программу в созданную процессорную систему, в основном окне AMP следует выполнить команду Actions > Compile & Load. Убедитесь, что в основном окне AMP появилась выбранная в пункте 5 программа. Причем желтым цветом будет выделена строка, помеченная меткой начала программы (_start). В нашем случае, это будет строка с адресом 0х400. Наблюдайте также, что значение PC в окне отображения и редактирования регистров будет равно 0х400. 11. Чтобы запустить программу выполните команду Actions > Continue или используйте пиктограмму на панели инструментов. Проверьте правильность выполнения программы. Если была запущена программа Test Media Computer, то она выполняет следующее. Тестирует статическую память. Тестирование заключается в заполнении оперативной памяти значениями 0х55555555. Каждый цикл записи сопровождается считыванием записанной информации и сравнением с эталоном. Затем число-заполнитель меняется на инверсное значение, и цикл тестирования продолжается. Отображает бегущую строку на семисегментном дисплее. Если ошибок при тестировании статической памяти не обнаружено, то строка содержит слова "dE2" и "PASSEd". Если обнаружены ошибки, то выводится слово "Error". Включает мерцание зеленых светодиодов. Скорость мерцания светодиодов и прокрутки текста на семисегментных индикаторах регулируется прерываниями от таймера. Подключает переключатели к красным светодиодам. Обрабатывает прерывания от кнопок. Нажатие кнопки KEY1 увеличивает скорость прокрутки строки. Нажатие кнопки KEY2 снижает скорость, нажатие кнопки KEY3 - останавливает прокрутку. Тестирует порты расширения JP1, JP2, если установлены соответствующие перемычки. Принимает данные, вводимые в терминальное окно AMP, и отсылает их обратно, используя интерфейс JTAG UART, и дополнительно пересылает их в com-порт. 12. Остановите выполнение программы. Для этого выполните команду Actions > Stop или используйте пиктограмму на панели инструментов AMP. Перезапустите программу. Для этого выполните 10 команду Actions > Restart или нажмите на пиктограмму на панели инструментов. Обратите внимание на то, что данная команда только изменяет значение счетчика команд на адрес начала программы. Убедитесь, что это произошло. Запустите программу. Часть 2. Использование приложения АМР для работы с портами ввода вывода процессорной системы 1. Остановите выполнение программы. 2. Откройте вкладку Memory основного окна AMP. Для перехода к нужному адресу можно воспользоваться полем Go to в верхней части окна. Наблюдайте состояние переключателей и кнопок на плате, обращаясь к соответствующим адресам портов ввода. Для этого установите галочку в поле Query all devices, и после изменения состояния переключателей и кнопок нажмите кнопку Refresh memory в верхней правой части окна AMP. 3. Управляйте зелеными и красными светодиодами, записывая по соответствующим адресам портов вывода различные наборы данных. Уясните принцип работы светодиодов. 4. Управляйте сегментами индикаторов шестнадцатеричной цифры, подавая различные наборы данных в соответствующие порты вывода данных. Уясните принцип работы индикаторов. 5. Сформируйте наборы данных таким образом, чтобы на индикаторах высветилась дата Вашего рождения в формате дд.мм.гггг. Часть 3. Использование АМР для компиляции, загрузки и отладки программы 1. Завершите сеанс работы с текущей программой. Для этого выполните команду Action > Disconnect или воспользуйтесь пиктограммой на панели инструментов AMP. 2. Выполните команду Settings > Program settings. В появившемся окне в поле Source files удалите содержащиеся там файлы и выберите файл lab1_part3 из папки «Исходные файлы к лабораторным работам», используя команду Add.. Для завершения программных установок нажмите кнопку Ок. 3. Выполните компиляцию и загрузку новой программы, используя соответствующие команды AMP. 4. Чтобы уяснить содержание программы, выполните ее по шагам. Для этого используйте команду Actions > Single Step или пиктограмму на панели инструментов АМР. Наблюдайте результаты 11 выполнения отдельных команд программы, используя окна отображения содержимого регистров и памяти. Обратите внимание на то, как компилятор транслирует псевдокоманды. Запишите в отчет используемые в программе форматы команд. 5. После уяснения структуры программы, установите контрольную точку в начало цикла (метка LOOP). Для этого щелкните мышью в поле, слева от адреса команды. Контрольная точка отображается кружком красного цвета. Чтобы удалить контрольную точку, следует выполнить повторный щелчок по кружку. Выполните программу с использованием контрольной точки. Всякий раз после останова программы, наблюдайте содержимое изменяемых регистров процессора. Для продолжения выполнения программы, используйте команду Actions > Continue или пиктограмму на панели инструментов АМР. 6. Используя окно редактирования памяти, измените количество чисел в обрабатываемом списке и сами числа. Для заполнения памяти можно воспользоваться командой Memory fill из контекстно-зависимого меню. Исследуйте возможности этой команды и включите их описание в отчет. Для наблюдения содержимого ячеек памяти воспользуйтесь командами из меню View. Задавайте разные значения количества отображаемых ячеек на строке экрана и разную форму представления содержимого памяти (двоичную, восьмеричную, шестнадцатеричную, десятичную со знаком и без знака). 7. Исследуйте машинный код команды bge, которая содержится по адресу 0x424. Для этого воспользуйтесь вкладкой Memory. Используйте двоичную форму представления содержимого памяти. Запишите в отчет выделенные поля команды. Осмыслите содержимое поля смещение, которое соответствует разрядам с 6 по 21 кода команды. Убедитесь, что в мнемоническом представлении команды используется именно такое смещение. 8. Измените содержимое кода операции команды (разряды с 0 по 5), рассмотренной в предыдущем пункте, на значение 0х16. Оно соответствует команде blt. 9. Выполните программу повторно. Наблюдайте результат. Запишите в отчет Ваши соображения. 10. Закончите сеанс работы с текущей программой, как это выполнялось ранее. 11. Откройте папку с вашим проектом. Выполните редактирование исходной программы. Измените значение константы LIST, присваиваемое в директиве .equ на значение 0х600. Скомпилируйте, загрузите и выполните программу описанным ранее способом. Отобразите в отчете результат её работы. 12 12. Выполните дополнительное редактирование исходного файла программы так, чтобы работа программы соответствовала первоначальному варианту. Часть 4. Вывод информации на LCD индикатор При выполнении данной части следует обратить внимание на то, что в вкладке Memory приложения AMP можно включить опцию Query all devices. Она означает, что в этой вкладке будет отображаться не только содержимое ячеек памяти, но и портов ввода/вывода. При выполнении записи в порт ввода/вывода AMP автоматически выполняет считывание из этого порта и обновление его содержимого в окне Memory, которое в случае изменения отображается красным цветом. Нажатие кнопки Refresh memory также осуществляет чтение из порта. Поэтому при выполнении данной части лабораторной работы не следует использовать опцию Query all devices и кнопку Refresh memory. Управление LCD осуществляется путем записи информации в регистры управления и данных LCD, а его работа проверяется путем визуального наблюдения отображаемой информации. 1. Выполните очистку LCD-индикатора, записывая соответствующую команду в регистр управления LCD. 2. Установите курсор в начало первой строки, записывая соответствующую команду в регистр управления LCD. 3. Отобразите на первой строке LCD свою фамилию, а на второй строке – имя. Для этого надо отправлять соответствующие коды символов ASCII в регистр данных LCD. Следует заметить, что кодировка русскоязычных символов не поддерживается. Поэтому для выполнения этого пункта задания используйте буквы английского алфавита. Переход к следующей позиции на экране LCD будет осуществляться автоматически. Для заполнения второй строки надо предварительно выполнить команду установки курсора на начало второй строки. 4. Выполните сдвиг отображаемых строк на одну позицию вправо. 5. Выполните сдвиг отображаемых строк на одну позицию влево. 6. Включите мерцание курсора. 7. Погасите мерцание курсора. 8. Выполните очистку LCD-индикатора. 9. Уясните содержание программы LCD_DE2_70, которая находится в папке «Исходные файлы к лабораторным работам» на рабочем столе. 10. Скомпилируйте и загрузите программу LCD_DE2_70 в память процессорной системы. Для этого повторите выполнение пунктов 1-3 части 3. 13 11. Поставьте контрольную точку на команде, помеченной меткой met1. Запустите программу. Наблюдайте результат работы программы и отразите его в отчете. 12. Поставьте контрольную точку на команде, помеченной меткой met2. Запустите программу. Наблюдайте результат работы программы и отразите его в отчете. 13. Продолжите выполнение программы. Наблюдайте результат и отразите его в отчете. 14. Повторите выполнение предыдущего пункта несколько раз. 15. Запишите в счетчик команд (регистр РС в окне регистров) адрес met3. Поставьте контрольную точку по адресу этой команды. Продолжите выполнение программы. Наблюдайте результат и отобразите его в отчете. 16. Продолжите выполнение программы несколько раз. Наблюдайте результат и зафиксируйте его в отчете. 17. Выполните очистку экрана. Для этого осуществите рестарт программы. Поставьте контрольную точку в том месте программы, где завершается очистка экрана. Наблюдайте результат и отразите его в отчете. 18. Измените содержимое текстовых строк исходной программы таким образом, чтобы на индикаторе LCD отображалась Ваша фамилия, имя и отчество на первой строке, а на второй строке в начале слово «nachalo», в конце строки (в невидимой части) слово «konec», а в середине - цифры шестнадцатеричной системы счисления. Причем цифры должны размещаться, строго в середине второй строки. Повторите выполнение пунктов 11-18. Отразите в отчете правильность вывода. 19. Модифицируйте программу из предыдущего пункта таким образом, чтобы на экране LCD выводилась информация из предыдущего пункта в режиме бегущей строки. Используйте программную задержку. Причем экспериментально подберите её величину таким образом, чтобы выводимая информация была легко читаема. Часть 5. Выполнение команд загрузки (load) и сохранения (store) в процессорной системе 1. Завершите сеанс работы с текущей программой, как это описывалось ранее. 2. Напишите фрагмент программы, которая будет сохранять слово по начальному адресу памяти, реализованной на кристалле. Затем выполняется сохранение этого же слова по смещенному на единицу адресу. Затем по адресу, смещенному на 2 и на 3 соответственно. Наблюдайте выполнение программы по шагам. При этом используйте 14 вкладку Memory приложения AMP. Сравнивайте наблюдаемый результат с предполагаемым результатом. Фиксируйте в отчете Ваши наблюдения. 3. Модифицируйте программу из предыдущего пункта таким образом, чтобы обращение к памяти производилось полусловами. Наблюдайте выполнение программы по шагам и фиксируйте Ваши наблюдения в отчете. 4. Модифицируйте программу из предыдущего пункта таким образом, чтобы обращение к памяти производилось байтами. Наблюдайте выполнение программы по шагам и фиксируйте Ваши наблюдения в отчете. 5. Модифицируйте программу из пункта 2 таким образом, чтобы в программе осуществлялось чтение из ОП словами, полусловами, байтами аналогично тому, как это делалось в пунктах 2-4 настоящей части. Часть 6. Тестирование всех типов оперативной памяти, используемой в процессорной системе Напишите фрагмент программы, которая осуществляет запись в последовательные ячейки памяти некоторых значений, используя команды сохранения слов, полуслов, байтов. Программа, после выполнения записи в ячейку памяти, выполняет ее считывание и сравнение с записываемой величиной. При обнаружении несовпадения программа зажигает красные светодиоды и завершает свое выполнение. Записываемые в оперативную память значения получаются путем прибавления 1 (2, 3 и т.д. ) (вычитания 1, 2, 3). Начальное значение задайте в соответствии с вариантом. Если при заполнении заданного диапазона памяти не обнаружено несовпадений записываемых и считываемых значений, то программа зажигает зеленые светодиоды и завершает свое выполнение. В начале программы должен содержаться код, гасящий все светодиоды. 1. Проверьте правильность работы программы, используя в качестве ОП статическую память. 2. Установите конечный адрес диапазона, выходящий за пределы статической памяти. Наблюдайте результаты выполнения программы. Запишите в отчет. 3. Установите начальный адрес диапазона, выходящий за верхнюю границу статической памяти. 4. Повторите выполнение предыдущих пунктов 1-3 задания. Используйте в качестве ОП память внутри кристалла. Отразите в отчете результаты выполнения. 5. Повторите выполнение пунктов 1-3 задания. Используйте в качестве ОП динамическую память. Учтите, что в динамической памяти 15 содержится сама программа. Поэтому в качестве начального адреса ОП используйте адрес ячейки, следующей сразу за программой. Таблица 1 Варианты заданий к части 6 лабораторной работы Номер Номер Начальное Приращение рабочего варианта значение места VT-L14 1 0 +1 VT-L13 2 0 +2 VT-L12 3 0 +3 VT-L11 4 F……F -1 VT-L10 5 F......F -2 VT-L9 6 F……F -3 VT-L8 7 0FFFF +1 Обращение к ОП пословно пополусловно побайтно пословно пополусловно побайтно пословно Отчетные материалы Отчетные материалы должны содержать. 1. Цель лабораторной работы. 2. Материалы, связанные с подготовкой к работе, включая теоретическую часть и исходные заготовки программ. 3. Информацию по выполнению каждого пункта задания. Причем в отчете должны содержаться выполняемые Вами действия, наблюдаемые результаты, и Ваши объяснения. 4. Написанные Вами фрагменты программ, выполняющие п.19 части 4, части 5 и 6 настоящего описания. 5. Краткое заключение. Приложение В приложении содержатся текстовые файлы программ тестирования процессорной системы, нахождения наибольшего числа из списка, работы с дисплеем LCD, таблица кодов ASCII. 16 Листинг 1. Исходный файл программы тестирования процессорной системы TEST_DE2_70_Media_Computer.s .include "address_map.s" .equ RIBBON_CABLE_INSTALLED, 0 /* Программа демонстрирует различные возможности процессорной системы. * Она выполняет следующие действия: * 1. Тестирует статическую память. * 2. Прокручивает текст на семисегментном дисплее. Если ошибок при тестировании * статической памяти не обнаружено, то текст содержит слова "dE2" и "PASSEd". Если * были обнаружены ошибки, то выводится слово "Error". * 3. Мигает зелеными светодиодами. Скорость мигания светодиодов и прокрутки текста на * семисегментных индикаторах регулируется прерываниями таймера. * 4. Подключает переключатели к красным светодиодам. * 5. Обрабатывает прерывания от кнопок. Нажатие кнопки KEY1 увеличивает скорость * прокрутки текста. Нажатие кнопки KEY2 снижает скорость, кнопки KEY3 - останавливает * прокрутку. * 6. Тестирует порты расширения JP1, JP2. * 7.Отсылает обратно данные, полученные по интерфейсу JTAG UART (символы, введенные в терминальном окне программы Altera Monitor Program) и наоборот. */ .text .global _start _start: /* инициализируем регистры sp и fp */ movia sp, 0x03FFFFFC mov fp, sp /* Стек начинается с последнего адреса SDRAM памяти /* инициализируем буфер семисегментных индикаторов */ movia r16, DISPLAY_BUFFER movi r17, 0xde2 stw r17, 0(r16) stw zero, 4(r16) stw zero, 8(r16) /* инициализируем зеленые светодиоды */ movia movia stw r2, 0x55555555 r16, GREEN_LED_PATTERN r2, 0(r16) /* инициализируем счетчик задержки, используемый для определения изменений отображаемого текста */ movia r16, EIGHT_SEC 17 stw zero, 0(r16) /* инициализируем переключатели */ movia stw r16, DISPLAY_TOGGLE zero, 0(r16) /* направление передачи может быть сохранено в SHIFT_DIRECTION, где 0-влево, 1-вправо */ movi movia stw r2, 1 r16, SHIFT_DIRECTION r2, 0(r16) /* запускаем таймер и разрешаем его прерывания */ movia movi sthio r16, INTERVAL_TIMER_BASE r15, 0b0111 /* START = 1, CONT = 1, ITO = 1 r15, 4(r16) /* разрешаем прерывания от кнопок */ movia movi stwio r16, PUSHBUTTON_BASE r15, 0b01110 r15, 8(r16) /* устанавливаем биты маски прерывания в 1 /* разрешаем прерывания процессора */ movi r15, 0b011 .if RIBBON_CABLE_INSTALLED ori r15, r15, 0b1000000000000 расширения JP2 .endif wrctl ienable, r15 movi r15, 1 wrctl status, r15 /* разрешаем прерывания от таймера и кнопок /* также разрешаем прерывания для порта /* цикл, в котором тестируется статическая память и обновляются семисегментные индикаторы */ movia r15, 0x55555555 movia r17, SRAM_END DO_DISPLAY: movia r16, SRAM_BASE movia r17, SRAM_END MEM_LOOP: call UPDATE_HEX_DISPLAY call UPDATE_RED_LED /* подключаем переключатели к красным светодиодам call UPDATE_UARTS /* обновление и JTAG порта и последовательного порта 18 /* тестируем порты расширения, если подключен 40-контактный кабель Ribbon */ .if RIBBON_CABLE_INSTALLED call TEST_EXPANSION_PORTS неудачей beq r2, zero, SHOW_ERROR .endif stw ldw bne addi ble r15, 0(r16) r14, 0(r16) r14, r15, SHOW_ERROR r16, r16, 4 r16, r17, MEM_LOOP xori xorhi r15, r15, 0xFFFF r15, r15, 0xFFFF /*возвращает 0, если тест закончился /* обновляем буфер семисегментных индикаторов примерно каждые 8 секунд */ movia ldw movi ble r16, EIGHT_SEC r17, 0(r16) r14, 80 /* 80 прерываний таймера равны примерно 10 секундам r17, r14, DO_DISPLAY stw zero, 0(r16) /* выводим на семисегментные индикаторы слова dE2 и PASSEd */ movia r16, DISPLAY_TOGGLE ldw r17, 0(r16) beq r17, zero, SHOW_PASSED stw zero, 0(r16) /* выводим dE2 */ movia r16, DISPLAY_BUFFER movi r17, 0xdE2 stw r17, 0(r16) stw zero, 4(r16) stw zero, 8(r16) br DO_DISPLAY SHOW_PASSED: movi r17, 1 stw r17, 0(r16) movia r16, DISPLAY_BUFFER movia r17, 0xbA55Ed stw r17, 0(r16) stw zero, 4(r16) /* слово Passed 19 stw br zero, 8(r16) DO_DISPLAY SHOW_ERROR: movia r16, DISPLAY_BUFFER movia r17, 0xe7787 stw r17, 0(r16) stw zero, 4(r16) stw zero, 8(r16) DO_ERROR: call UPDATE_HEX_DISPLAY br DO_ERROR /* слово Error /******************************************************************************* Обновляем значения, выводимые на семисегментный дисплей. Значения считываются из буфера *******************************************************************************/ .global UPDATE_HEX_DISPLAy UPDATE_HEX_DISPLAY: subi sp, sp, 36 /* резервируем память в стеке /* сохраняем регистры */ stw stw stw stw stw stw stw stw stw addi ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) r20, 28(sp) r21, 32(sp) fp, sp, 36 /* выводим значения на индикаторы */ movia ldw r15, DISPLAY_BUFFER r16, 4(r15) /* Цикл, который заполняет буфер из 2 слов, который подключен к параллельному порту «DE2-70 Media Computer», подключенного к семисегментным индикаторам. Для каждого сегмента отводится 8 бит буфера*/ movia r17, 7 movia r15, HEX3_HEX0 movia r19, SEVEN_SEG_DECODE_TABLE SEVEN_SEG_DECODER: mov r18, r16 andi r18, r18, 0x000F 20 add add ldb stb r20, r19, r18 r21, zero, zero r21, 0(r20) r21, 0(r15) srli addi subi bge r16, r16, 4 r15, r15, 1 r17, r17, 1 r17, zero, SEVEN_SEG_DECODER /* в r21 загружаем код символа /* сохраняем код в буфере /* выводим на семисегментные индикаторы содержимое буфера */ movia ldw movia stwio ldw movia stwio r15, HEX3_HEX0 r16, 0(r15) r17, HEX3_HEX0_BASE r16, 0(r17) r16, 4(r15) r17, HEX7_HEX4_BASE r16, 0(r17) /* извлекаем из стека регистры */ ldw ldw ldw ldw ldw ldw ldw ldw ldw addi ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) r20, 28(sp) r21, 32(sp) sp, sp, 36 /* освобождаем зарезервированную память стека ret /*****************Подключаем переключатели к красным светодиодам****************/ .global UPDATE_RED_LED UPDATE_RED_LED: /* сохраняем регистры в стеке */ subi stw stw stw stw addi sp, sp, 16 ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) fp, sp, 16 /* резервируем область памяти в стеке /* считываем значение с переключателей */ 21 movia ldwio r15, SLIDER_SWITCH_BASE r16, 0(r15) /* выводим его на красные светодиоды */ movia stwio r15, RED_LED_BASE r16, 0(r15) /* извлекаем из стека регистры */ ldw ldw ldw ldw addi ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) sp, sp, 16 ret /******************************************************************************* Считываем символы из JTAG порта и последовательного порта UART и отправляем их обратно в оба порта *******************************************************************************/ .global UPDATE_UARTS UPDATE_UARTS: /* сохраняем регистры в стеке */ subi stw stw stw stw stw stw stw addi /* резервируем область памяти в стеке sp, sp, 28 ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) fp, sp, 28 movia r15, JTAG_UART_BASE movia r19, UART_BASE GET_CHAR: ldwio r17, 0(r15) /* проверяем, имеют ли JTAG или UART порты новые данные andi r18, r17, 0x8000 /* считываем символ beq r18, r0, GET_CHAR_UART andi r16, r17, 0x00ff PUT_CHAR: ldwio r17, 4(r15) /* проверяем, готовы ли порты JTAG UART к приему данных 22 andhi r17, r17, 0xffff beq r17, r0, PUT_CHAR_UART stwio r16, 0(r15) /* отправляем символ обратно PUT_CHAR_UART: ldwio r17, 4(r19) andhi r17, r17, 0xffff beq r17, r0, GET_CHAR_UART stwio r16, 0(r19) GET_CHAR_UART: ldwio r17, 0(r19) andhi r18, r17, 0xFFFF beq r18, r0, NO_CHAR andi r16, r17, 0x00ff ldwio andhi beq stwio r17, 4(r19) r17, r17, 0xffff r17, r0, PUT_CHAR_JTAG r16, 0(r19) PUT_CHAR_JTAG: ldwio r17, 4(r15) andhi r17, r17, 0xffff beq r17, r0, NO_CHAR stwio r16, 0(r15) NO_CHAR: /* восстанавливаем из стека регистры */ ldw ldw ldw ldw ldw ldw ldw addi ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) sp, sp, 28 ret /******************************************************************************* Данный код тестирует порты расширения JP1 и JP2. Для этого должен использоваться кабель Ribbon *******************************************************************************/ 23 .global TEST_EXPANSION_PORTS TEST_EXPANSION_PORTS: /* сохраняем регистры в стеке */ subi stw stw stw stw stw stw addi sp, sp, 24 ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) fp, sp, 24 movia movia movia stwio add stwio movia stwio add ldwio bne movia stwio add ldwio bne movia stwio add ldwio bne r15, JP1_EXPANSION_BASE r16, JP2_EXPANSION_BASE r17, 0xFFFFFFFF r17, 4(r15) r17, zero, zero r17, 4(r16) r17, 0x55555555 r17, 0(r15) zero, zero, zero r18, 0(r16) r17, r18, RET_ERROR r17, 0xAAAAAAAA r17, 0(r15) zero, zero, zero r18, 0(r16) r17, r18, RET_ERROR r17, 0x01234567 r17, 0(r15) zero, zero, zero r18, 0(r16) r17, r18, RET_ERROR add stwio movia stwio movia stwio add ldwio bne movia stwio add ldwio bne r17, zero, zero r17, 4(r15) r17, 0xFFFFFFFF r17, 4(r16) r17, 0x55555555 r17, 0(r16) zero, zero, zero r18, 0(r15) r17, r18, RET_ERROR r17, 0xAAAAAAAA r17, 0(r16) zero, zero, zero r18, 0(r15) r17, r18, RET_ERROR 24 movia stwio add ldwio bne r17, 0x01234567 r17, 0(r16) zero, zero, zero r18, 0(r15) r17, r18, RET_ERROR movi br r2, 1 RET_ERROR: movi RETURN: ldw ldw ldw ldw ldw ldw addi RETURN r2, 0 ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) sp, sp, 24 ret /****************************** DATA SECTION *********************************/ .data .global DISPLAY_BUFFER DISPLAY_BUFFER: .fill 3, 4, 0 .global SHIFT_DIRECTION SHIFT_DIRECTION: .word 0 /* Таблица декодирования семисегментных индикаторов включен(1)/выключен(0) для каждого сегмента индикаторов*/ SEVEN_SEG_DECODE_TABLE: .byte 0b00000000, 0b00000110, 0b01011011, 0b01001111 .byte 0b01100110, 0b01101101, 0b01111100, 0b01010000 .byte 0b01011100, 0b01100111, 0b01110111, 0b01110011 .byte 0b00111001, 0b01011110, 0b01111001, 0b01110001 HEX3_HEX0: .word 0 HEX7_HEX4: .word 0 .global GREEN_LED_PATTERN GREEN_LED_PATTERN: содержит значения 25 .word 0 .global EIGHT_SEC EIGHT_SEC: .word 0 DISPLAY_TOGGLE: .word 0 .end Листинг 2 Исходный файл программы lab1_part3_DE.s /* Программа осуществляет поиск максимального числа в списке целых чисел. */ .equ LIST, 0x500 /* Адрес начала списка в памяти. Первый элемент списка будет содержать максимальное число, 2-ой - количество чисел в списке*/ .global _start _start: movia r4, LIST /* В регистр R4 записывается адрес начала списка */ ldw r5, 4(r4) /* Считываем в регистр R5 значение количества чисел в списке */ addi r6, r4, 8 /* Вычисляем адрес памяти, с которого начинают располагаться числа для поиска*/ ldw r7, (r6) /* В регистр R7 из памяти по адресу R6 считывается первое число списка */ LOOP: subi r5, r5, 1 /* Уменьшаем значение количества чисел в списке */ beq r5, r0, DONE /* Если значение регистра R5 равно 0, то выходим из цикла */ addi r6, r6, 4 ldw r8, (r6) /*Увеличиваем адрес памяти на 4 (переходим к следующему числу */ /* Считываем из памяти следующее число */ bge r7, r8, LOOP /* Если текущее максимальное число больше или равно считанному, то возвращаемся в начало цикла*/ add r7, r8, r0 br LOOP DONE: stw r7, (r4) /* Иначе, записываем в R7 новое максимальное число */ /* Записываем максимальное число в память по адресу 0x500 */ STOP: br .org 0x100 RESULT: STOP /* Бесконечный цикл */ 26 .skip 4 N: .word 7 NUMBERS: .word 4, 5, 3, 6, 1, 8, 2 /* Выделяем 4 байта для хранения максимального числа */ /* Количество чисел в списке */ /* Числа из списка */ .end Листинг 3 Исходный файл программы LCD_DE2_70.s .include "nios_macros.s" .text .equ lcd,0x10003050 .equ clear,0x00000001 .equ set1,0b10000000 строки*/ .equ set2,0b11000000 .equ off,0b00001100 .equ right,0b00011100 .equ left,0b00011000 /*Код команды установки курсора в начало 2 строки*/ /*Код команды выключения курсора*/ /*Код команды сдвига экрана вправо*/ /*Код команды сдвига курсора влево*/ .global _start _start: movia r2,lcd movi r3,clear stbio r3,0(r2) /*Код команды очистки lcd*/ /*Очищаем экран lcd*/ movi r3,set1 stbio r3,0(r2) /*Устанавливаем курсор в начало первой строки*/ movia r4,String1 cikl: ldb r5,0(r4) beq r5,zero,met stbio r5,1(r2) addi r4,r4,1 br cikl met: movi r3,set2 stbio r3,0(r2) movia r4,String2 cikl2: ldb r5,0(r4) beq r5,zero,met1 stbio r5,1(r2) /*Адрес регистра lcd*/ /*Код команды очистки экрана lcd*/ /*Код команды установки курсора в первую позицию первой /*В регистр R4 записываем адрес первой строки*/ /*Считываем символ из строки и помещаем его в R5*/ /*Если считанныцй символ равен 0, то выходим из цикла*/ /*Записываем из R5 в регистр данных lcd*/ /*Инкрементируем адрес символа строки*/ /*Устанавливаем курсор в начало второй строки*/ /*Выводим вторую строку*/ 27 addi r4,r4,1 br cikl2 met1: movi r3,off stbio r3,0(r2) /*Выключаем курсор*/ met2: movi r3,right stbio r3,0(r2) br met2 /*Сдвигаем экран вправо*/ met3: movi r3,left stbio r3,0(r2) br met3 /*Сдвигаем экран влево*/ .data String1: .asciz "Kreitin String2: .asciz "Alexander" .end /*Определяем сегмент данных*/ konec" 28 Таблица 2 ASCII - коды символов Лабораторная работа №2 Использование стека, подпрограмм и вложенных процедур Цель работы: Использование подпрограмм и способов передачи им параметров, использование файлов с исходными данными, и с кодами программ в процессорной системе. В лабораторной работе используется предварительно созданная процессорная система, особенности которой были изучены в предыдущей лабораторной работе. 29 Исходные файлы лабораторной работы Исходным является файл lab1_part3_DE.s. Он содержит программу нахождения наибольшего числа из списка, которая использовалась в первой работе. Подготовка к лабораторной работе 1. Изучите по учебной литературе следующие вопросы: подпрограммы, стек, передача параметров подпрограммам. Поместите в отчет краткое описание. 2. Ознакомьтесь с системой команд процессора NIOS II [5,8], уясните, как происходит выполнение команд вызова процедур call, callr; работа со стеком; регистры, используемые для этого. Поместите в отчет, включая форматы вышеуказанных команд. 3. Включите в отчет структурную схему процессорной системы и карту памяти, на которой должны быть отражены адреса оперативной памяти и портов ввода вывода периферийных устройств системы. 4. Прочитайте описание приложения Altera Monitor Program (АМР) [6]. Уясните, как заполнить память процессорной системы и как выполнить загрузку файлов с исходными данными и с выполнимыми кодами программ в оперативную память процессорной системы. Поместите эти материалы в отчет. 5. Уясните пункты задания, выполняемого в текущей лабораторной работе. 6. Подготовьте файл с исходными данными для выполнения пункта 1 части 4. 7. Подготовьте программные заготовки для выполнения остальных пунктов задания. 8. Уясните индивидуальное задание. Подготовьте программу для его выполнения. Порядок выполнения лабораторной работы Часть 1. Передача параметров через регистры Используйте программу нахождения наибольшего числа в списке, которая выполнялась в 1 лабораторной работе. 1. Запустите Altera Monitor Program. Откройте проект, созданный в 1 лабораторной работе. Выполните программу нахождения наибольшего числа из списка. Она содержится в файле lab1_part3 из папки «Исходные файлы к лабораторным работам». Убедитесь в 30 работоспособности программы, меняя исходные числа во вкладке Memory AMP и наблюдая полученный результат. 2. Модифицируйте программу таким образом, чтобы она была оформлена как подпрограмма с именем Max. Список обрабатываемых чисел разместите в основной программе сразу же после последней команды. Для передачи параметров подпрограмме используйте регистры R5, для указания числа слов в списке, и регистр R6, для указания начального адреса списка. Подпрограмма будет осуществлять анализ содержимого ячеек памяти, и находить наибольшее число. Подпрограмма должна завершаться командой ret. Результат формируется в регистре R7. 3. В основной программе заполняются регистры R5 и R6 для передачи параметров, и осуществляется вызов подпрограммы с использованием команды call. Затем она выводит найденное число на светодиоды. Проверьте правильность работы программы, визуально наблюдая содержимое анализируемой области памяти, используя вкладку Memory, содержимое регистра R7 в регистровом окне приложения AMP и младшую часть результата, отображенную на светодиодах. 4. Выполните предыдущий пункт, используя команду callr. Часть 2. Передача параметров через стек 1. Модифицируйте программу таким образом, чтобы передача параметров осуществлялась через стек. Для этого в основной программе определите в качестве вершины стека адрес последнего слова используемой в процессорной системе оперативной памяти. В качестве указателя стека используется регистр sp процессора. Обратите внимание на то, что после помещения в стек или извлечения из стека автоматического изменения регистра sp не происходит. Это должна выполнить Ваша программа. После записи в стек sp следует уменьшить на 4, перед извлечением из стека – увеличить на 4. Возврат найденного большего числа из списка также должен осуществляться через стек. Причем, результат может быть помещен в то место в стеке, где были размещены передаваемые процедуре параметры. Для этого используйте соответствующее смещение относительно текущего указателя стека. Общепринятый прием – сохранение содержимого регистров, используемых в подпрограмме, в стеке в начале работы подпрограммы и восстановление их при завершении подпрограммы. Непосредственно перед выполнением команды ret, выполните коррекцию указателя стека так, чтобы он указывал на возвращаемый результат. Отладьте программу, убедитесь в ее работоспособности, покажите результат преподавателю. 31 2. Запускайте программу, изменяя исходные данные. Для заполнения памяти используйте соответствующее окно AMP. Часть 3. Использование вложенных процедур 1. Модифицируйте программу из предыдущей части следующим образом. Оформите вывод на светодиоды в качестве самостоятельной процедуры, передав в качестве параметра отображаемое число через какой-либо регистр процессора. Выполните вызов этой процедуры внутри подпрограммы Max. Из основной программы соответствующую часть кода удалите. 2. Поставьте контрольную точку в конце программы. Запустите программу. Убедитесь, что возврат в основную программу не выполняется. Выясните причину и устраните ее. 3. Убедитесь в работоспособности модифицированной программы. Покажите результат ее работы преподавателю. Часть 4. Использование файлов с исходными данными в AMP 1. Создайте файл и поместите в него исходные значения. Для этого используйте любой текстовый редактор и представление чисел в шестнадцатеричной форме. В качестве разделителя может использоваться любой символ. Загрузите файл в оперативную память, начиная с заданного адреса. Используйте команду Load file into memory из меню Action приложения AMP. В появившемся окне задайте имя файла с указанием пути к нему, в поле «формат файла» окна браузера задайте Delimited hexadecimal value file, символ разделителя и начальный адрес оперативной памяти. Убедитесь в правильности заполнения памяти. 2. Модифицируйте программу из предыдущей части таким образом, чтобы она передавала подпрограмме через стек число слов в списке, соответствующее подготовленному Вами файлу и начальный адрес ОП, куда был загружен файл. После получения результата через стек, основная программа выводит его на светодиоды. Покажите результат преподавателю. 3. Используя AMP, загрузите исполняемый код программы (файл c расширением .elf) из предыдущей части в оперативную память, начиная с заданного адреса. Для этого в поле «формат файла» окна браузера, выберите пункт Binary format. Чтобы убедиться в правильности загрузки программы, визуально сравните содержимое областей памяти, в которую вами загружена программа и той, в которой она изначально была загружена AMP. Обратите внимание! Изменения 32 в окне дизассемблирования будут отсутствовать. Также, первые 0х74 байта загруженного кода будут содержать служебную информацию. 4. Выполните программу. Для этого поместите в PC стартовый адрес программы и используйте команду Action > Continue. Предварительно погасите светодиоды так, как это выполнялось в предыдущей лабораторной работе. Для того, чтобы проверить правильность выполнения команды call, поставьте по адресу этой команды контрольную точку. После достижения контрольной точки выполните следующие команды по шагам. Проверьте правильность перехода к процедуре Max. Отразите в отчете. Индивидуальное задание Напишите программу, которая решает какую-либо задачу из нижеприведенного списка. В качестве варианта используйте номер рабочего места. Соответствие номеров вариантов и заданий приводится в таблице 3. 1. Напишите программу, которая использует рекурсию для вычисления факториала числа N. N!=N(N-1)(N-2)…*3*2*1. Заметьте, что N!=N*(N-1)! Программа включает подпрограмму Factor, которая вызывает сама себя до тех пор, пока желаемый факториал не будет получен. Основная программа должна ввести параметр N, задаваемый с помощью переключателей, затем передать N как параметр, размещая его в стеке. Подпрограмма может вернуть результат через регистр R4, либо через стек. Программа Factor вызывает сама себя. Перед вызовом не забудьте сохранять адрес возврата (регистр ra) в стеке и восстанавливать после возврата. Покажите результат работы программы преподавателю. 2. Напишите программу, которая осуществляет вывод на LCD содержимого области памяти, представленного в шестнадцатеричном виде. Оформите ее в виде подпрограммы, которой передаются параметры: начальный адрес области памяти, количество байтов и номер позиции на LCD дисплее. 3. Напишите программу, которая осуществляет вывод на 7сегментные индикаторы содержимого области памяти, представленного в шестнадцатеричном виде. Оформите ее в виде подпрограммы, которой передаются параметры: начальный адрес области памяти, количество отображаемых символов. 4. Напишите программу, которая осуществляет упорядочивание чисел в списке в убывающем порядке. Каждое число представляет собой 32-разрядное число без знака. Оформите ее в виде подпрограммы, которой передаются параметры: адрес списка в ОП, число слов в списке. 33 5. Напишите программу, вычисляющую первые n чисел Фибоначчи. Числа 32 – разрядные. Они вычисляются по формуле An=An-1+An-2 и и записываются в оперативную память. Первые числа выглядят следующим образом: 0,1,1,2,3,5,8…. Оформите в виде подпрограммы, которой передаются параметры: адрес ОП, число n. 6. Напишите программу, вычисляющую максимальное количество повторяющихся нулевых и единичных разрядов в числе, хранящемся в ОП. Адрес числа может быть произвольным. Оформите в виде подпрограммы, передав в качестве параметров: адрес ОП и размер числа в байтах (не более 4). Вывод найденных значений осуществите на красные и зеленые светодиоды. 7. Напишите программу, вычисляющую количество положительных и отрицательных фронтов в числе, хранящемся в ОП. Например, число 0b10010110 содержит 2 положительных и 3 отрицательных фронта. Адрес числа может быть произвольным. Оформите в виде подпрограммы, передав в качестве параметров адрес ОП и размер числа в байтах (не более 4). Вывод найденных значений осуществите на красные и зеленые светодиоды. Таблица 3 Варианты заданий к лабораторной работе № 2 Номер рабочего места VT-L14 VT-L13 VT-L12 VT-L11 VT-L10 VT-L9 VT-L8 Название стенда NEEK miniDiLab DiLab DE2-70 DE2-70 DE0 DE0 Номер задания 4 1 5 6 7 3 2 Отчетные материалы Отчетные материалы должны содержать: 1. Цель лабораторной работы. 2. Материалы, связанные с подготовкой к работе, включая теоретическую часть и заготовку программы. 3. Информацию по выполнению каждого пункта задания. Причем в отчете должны содержаться выполняемые Вами действия, наблюдаемые результаты, и Ваши объяснения. 4. Написанные Вами фрагменты программ, включая программу для выполнения индивидуального задания. 5. Краткое заключение. 34 Лабораторная работа №3 Реализация ввода/вывода информации в процессорной системе Цель работы: изучение возможностей ввода/вывода информации в процессорной системе. Исходные файлы лабораторной работы В приложении приводится исходный файл тестовой программы interrupt_example.s. В программе используются прерывания от таймера и кнопок. Обработчик прерывания от таймера содержится в файле interval_timer.s. Обработчик прерывания от кнопок содержится в файле pushbutton_ISR.s. Обработчик исключений, задачей которого является определение причины прерывания и вызов соответствующей процедуры, содержится в файле exception_handler.s. Подготовка к лабораторной работе Для выполнения лабораторной работы необходимо изучить по материалам лекций и предложенной литературе. 1. Организацию обмена ЭВМ с периферийными устройствами. 2. Реализацию прерываний в процессорной системе NIOSII. Используемые для этого регистры процессора и портов ввода – вывода. 3. Уясните пример программы, в которой используются прерывания, и реализацию обработчика прерываний из описания процессорной системы «DE2- 70 Media Computer»[9]. Вставьте его в отчет. 4. Уясните пункты задания, выполняемого в текущей лабораторной работе, и напишите программные заготовки для их выполнения. 5. Уясните выполнение команды trap. Вставьте в отчет ее формат и краткое описание. Напишите программную заготовку для выполнения пункта 1 части 6. 6. Уясните выполнение команды mul. Вставьте в отчет ее формат и краткое описание. Напишите программу, которая будет выполнять программную эмуляцию команды умножения. 35 В лабораторной работе в качестве устройств ввода будут использоваться переключатели SWITCH и кнопки KEY3, KEY2, KEY1. В качестве устройств вывода – зеленые светодиоды LEDG 7..0, красные светодиоды LEDR 17..0, индикаторы шестнадцатеричной цифры HEX 7..0. Для связи с каждым устройством используются параллельные порты ввода/вывода (PIO). Адреса портов и принцип их работы приведены в описании процессорной системы [9]. В лабораторной работе решается задача сложения 8-разрядных чисел с знаком, которые задаются переключателями SWITCH 7..0. Набранное число отображается на зеленых светодиодах. Вычисленная сумма сохраняется в регистре, младшая часть которого отображается на красных светодиодах. Порядок выполнения лабораторной работы Часть 1. Программно управляемый ввод с переключателей и вывод на светодиоды Используйте 8 переключателей SW 7..0 для задания вводимого числа. Используйте 8 зеленых светодиодов LEDG 7..0 для отображения вводимого числа. Используйте 18 красных светодиодов LEDR 17..0 для отображения младших разрядов вычисленной суммы. Все эти компоненты подключаются через параллельные порты к мультимедийной процессорной системе. 1. Напишите программу на языке ассемблер, которая вначале обнуляет сумму, затем читает 8-разрядное значение (число со знаком в дополнительном коде), задаваемое переключателями SW 7..0, отображает прочитанное значение на зеленых светодиодах, выполняет сложение введенного числа с накопленной суммой, выводит сумму на красные светодиоды. Осуществляет переход на ввод очередного числа, выполняя бесконечный цикл. 2. Создайте новую папку lab3_part1. Поместите Вашу программу в эту папку. 3. Используйте приложение AMP для создания нового проекта part1 в этой папке. Выберите Вашу программу и загрузите процессорную систему в программируемый кристалл ПЛИС. Выберите подходящую память для размещения Вашей программы. Разместите сегменты кода и данных, начиная с адреса 0х1000. Область в начале оперативной памяти понадобится в последующем для размещения обработчиков сброса и прерываний процессорной системы. Скомпилируйте и загрузите Вашу программу. 4. Выполните программу по шагам, задавая различные значения вводимых чисел. 36 5. Поставьте контрольную точку по адресу безусловного перехода на ввод очередного числа. Выполните рестарт программы. Убедитесь в ее работоспособности, каждый раз задавая новое число и нажимая кнопку продолжить. Запишите в отчет вводимые числа и наблюдаемые результаты. 6. Удалите контрольную точку и вновь запустите программу. Запишите в отчет наблюдаемое поведение программы. Часть 2. Ввод информации с переключателей с опросом их готовности 1. Остановите выполнение программы. Наблюдайте состояние регистров данных и захвата фронтов (edge-capture) PIO, соединенного с кнопками на стенде. Для этого используйте вкладку Memory приложения AMP. Установите галочку в окне Query all devices. Сначала нажмите и удерживайте некоторые из кнопок (KEY3-KEY1), затем наблюдайте состояние регистров в окне Memory, затем нажмите кнопку Refresh в окне AMP и снова наблюдайте состояние регистров. Отпустите кнопки, наблюдайте состояние регистров, нажмите Refresh и снова наблюдайте. Уясните принцип их работы и опишите в отчете. 2. Модифицируйте программу из предыдущей части таким образом, чтобы ввод очередного числа осуществлялся только после нажатия кнопки KEY3 на стенде. Используйте соответствующий разряд регистра edge-capture соответствующего PIO как сигнал готовности. Программа опрашивает его непрерывно до тех пор, пока он не установится. После ввода числа не забудьте снять сигнал готовности, записав нулевое значение в регистр edge-capture. Часть 3. Вывод информации на семисегментные индикаторы 1. Напишите программу, которая отображает содержимое 32разрядного регистра процессора на семисегментных индикаторах HEX7HEX0 в виде шестнадцатеричного числа. Оформите ее в виде процедуры HEX_Display, которой передается параметр через регистр. 2. Модифицируйте программу из предыдущей части таким образом, чтобы накопленная сумма дополнительно отображалась на индикаторах HEX7-HEX0. 37 Часть 4. Ввод информации с переключателей в режиме прерывания 1. Выполните задачу из предыдущей части. Используйте вместо опроса готовности устройства ввода формирование прерывания, которое инициируется нажатием кнопки KEY3 на стенде. Основная программа устанавливает все регистры, необходимые для формирования прерывания и выполняет бесконечный цикл. Программа обслуживания прерывания вводит число, вычисляет сумму и отображает ее на светодиодах и индикаторах. 2. Проверьте экспериментально действия программы, выполняемые после формирования прерывания. Для этого поставьте контрольную точку по адресу обработчика прерываний (0x20). После достижения контрольной точки выполните программу по шагам. Фиксируйте в отчете Ваши наблюдения. 3. Чтобы визуально наблюдать работу основной программы, реализуйте в ней вывод на индикатор LCD Вашей фамилии, имени и отчества в режиме бегущей строки. Заготовку программы возьмите из 1 лабораторной работы. Часть 5. Реализация приоритетных прерываний 1. Модифицируйте программу из предыдущей части таким образом, чтобы по кнопке KEY3 осуществлялось сложение нового числа с суммой, по кнопке KEY2 - вычитание нового числа из суммы, по кнопке KEY1 - обнуление суммы. Причем реализуйте приоритетность прерываний в соответствии с указанной последовательностью. 2. Экспериментально определите действия программы при выполнении сброса процессорной системы. Для этого поставьте по нулевому адресу в ОП контрольную точку. Затем запустите программу и нажмите кнопку KEY0. Далее выполните программу по шагам. Фиксируйте в отчете Ваши наблюдения. 3. Запрещайте прерывания от отдельных кнопок, изменяя содержимое регистра маски соответствующего PIO. Для этого поставьте контрольную точку в программе после команды записи соответствующего регистра. Затем модифицируйте регистр в регистровом окне. Далее продолжите выполнение программы. 4. Разрешайте или запрещайте прерывания от кнопок, изменяя содержимое регистра ienable процессора. Для этого используйте прием из предыдущего пункта. 5. Разрешайте или запрещайте прерывания от кнопок, изменяя содержимое бита pie регистра status процессора. Для этого используйте прием из 3 пункта. 38 Часть 6. Программное прерывание trap и невыполнимые команды 1. Вставьте в текст программы команду trap. Экспериментально определите поведение программы при выполнении этой команды. Отразите в отчете. Модифицируйте обработчик прерываний таким образом, чтобы в случае обнаружения команды trap, он передал управление процедуре, которая выведет строку «trap» на экран LCD. Для выполнения оставшихся пунктов задания требуется модифицировать процессорную систему, а именно отключить опцию аппаратной реализации команды умножения процессором NIOS II. Все необходимые файлы для реализации модифицированной системы в кристалле ПЛИС содержатся в папке lab3 на рабочем столе. 2. Выполните загрузку модифицированной процессорной системы в кристалл ПЛИС на стенде. 3. Вставьте в текст программы команду умножения mul. Экспериментально определите поведение программы при выполнении этой команды. Отразите в отчете. Следует напомнить, что в модифицированной процессорной системе не поддерживается аппаратное умножение. 4. Модифицируйте обработчик таким образом, чтобы он передал управление процедуре, которая эмулирует выполнение команды mul. Для этого понадобится написать соответствующую процедуру. Отчетные материалы Отчетные материалы должны содержать: 1. Цель лабораторной работы. 2. Материалы, связанные с подготовкой к работе, включая теоретическую часть и заготовку программы. Обязательно включите в отчет описание регистров, влияющих на прерывания процессора. 3. Информацию по выполнению каждого пункта задания. Причем в отчете должны содержаться выполняемые Вами действия, наблюдаемые результаты и Ваши объяснения. 4. Написанные Вами фрагменты программ. 5. Краткое заключение. Приложение В приложении содержится исходный файл тестовой программы interrupt_example.s. В программе используются прерывания от таймера и 39 кнопок. Обработчик прерываний от таймера содержится в файле interval_timer.s. Обработчик прерываний от кнопок содержится в файле pushbutton_ISR.s. Обработчик исключений, задачей которого является определение причины прерывания и вызов соответствующей процедуры, содержится в файле exception_handler.s. Листинг 4 Текст программы interrupt_example.s .equ .equ KEY1, 0 KEY2, 1 /*************************************************************************** ***** Эта программа демонстрирует использование прерываний на стенде * DE2-70 Media Computer. Вначале запускается таймер, который генерирует * прерывания каждые 33 мс. Затем разрешаются прерывания от таймера и кнопок. * Процедура обработки прерывания таймера отображает текст на 7-сегментных * индикаторах и сдвигает его влево или вправо. Направление сдвига определяется * кнопками. При нажатии кнопки key1 текст сдвигается вправо, при нажатии * key2 – влево, при нажатии key3 изменяется текст, используя данные с переключателей.************************************************************* ***************************************************************************/ text .global _start _start: movia sp, 0x03FFFFFC /* Определяем адрес вершины стека */ movia r16, 0x10002000 /* Определяем период срабатывания интервального таймера */ movia sthio srli sthio r12, 0x190000 /* 1/(50 MHz) x (0x190000) = 33 msec */ r12, 8(r16) /*определяем младшее полуслово как стартовое значение*/ r12, r12, 16 r12, 0xC(r16) /* старшее полуслово как стартовое значение */ /* Запускаем таймер и разрешаем прерывания от него */ movi sthio r15, 0b0111 r15, 4(r16) /* START = 1, CONT = 1, ITO = 1 */ /* Разрешаем прерывания PIO, к которому подсоединены кнопки */ movia movi stwio r15, 0x10000050 /* Адрес регистра кнопок */ r7, 0b01110 r7, 8(r15) /* Устанавливаем 3 бита регистра маски прерывания*/ /* Разрешаем прерывания NIOS 2 процессора */ 40 movi wrctl movi wrctl r7, 0b011 ienable, r7 r7, 1 status, r7 /*Разрешаем прерывания от кнопок*/ /*Разрешаем процессору обрабатывать прерывания */ IDLE: br IDLE data .global PATTERN PATTERN: .word 0x0000000F .global KEY_PRESSED KEY_PRESSED: .word KEY2 .end /* Бесконечный цикл */ Листинг 5 Текст программы exception_handler.s /* СЕКЦИЯ СБРОСА "ax" требуется для того, чтобы определить секцию как исполняемую.AMP автоматически размещает секцию сброса по адресу, определяемому в настройках процессора в SOPC Builder.*/ .section movia jmp .reset, "ax" r2, _start r2 /* Переходим в основную программу */ /*************************************************************************** СЕКЦИЯ ИСКЛЮЧЕНИЙ "ax" требуется для того, чтобы определить секцию как исполняемую.AMP автоматически размещает секцию сброса по адресу, определяемому в настройках процессора в SOPC Builder.***************************************/ section .exceptions, "ax" .global EXCEPTION_HANDLER EXCEPTION_HANDLER: subi sp, sp, 16 stw et, 0(sp) /*Определяем процедуру как глобальную*/ /*Процедура обработки прерываний*/ /* Изменяем адрес указателя стека */ /*Сохраняем содержимое регистра et в стеке*/ rdctl et, ctl4 beq et, r0, SKIP_EA_DEC SKIP_EA_DEC */ /* Если прерывание не внешнее, то переходим на subi ea, ea, 4 SKIP_EA_DEC: stw ea, 4(sp) /* декрементируем регистр ea на 1 команду */ /* Сохраняем регистры в стеке */ 41 stw stw ra, 8(sp) r22, 12(sp) rdctl et, ctl4 bne et, r0, CHECK_LEVEL_0 CHECK_LEVEL_0*/ /* Если прерывание внешнее, то переходим на NOT_EI: /* Прерывание произошло в случае встречи невыполнимой команды или команды TRAP */ br /* Выходим из обработчика прерываний */ END_ISR /* Проверка, является ли прерывание прерыванием от CHECK_LEVEL_0: таймера IRQ0 */ andi r22, et, 0b1 beq r22, r0, CHECK_LEVEL_1 /*Если бит 0b1 регистра et не равен 1, то переходим к проверке, является ли прерывание прерыванием от кнопок*/ call INTERVAL_TIMER_ISR прерывания от таймера*/ br END_ISR CHECK_LEVEL_1: IRQ1*/ процедуру обработки /*Выходим из обработчика прерываний*/ /*Проверка, является ли прерывание прерыванием от кнопок andi r22, et, 0b10 beq r22, r0, END_ISR из обработчика прерываний*/ call кнопок*/ /*Вызываем /* Если бит 0b10 регистра et не равен 10, то выходим PUSHBUTTON_ISR /*Вызываем процедуру обработки прерываний от END_ISR: /*Восстанавливаем из стека все используемые регистры*/ ldw ldw ldw ldw addi et, 0(sp) ea, 4(sp) ra, 8(sp) r22, 12(sp) sp, sp, 16 eret .end /*Выходим из процедуры обработки прерывания*/ Листинг 6 Текст программы interval_timer.s 42 .include "key_codes.s" .extern PATTERN .extern KEY_PRESSED /****************** Процедура обработки прерываний от таймера****************/ .global INTERVAL_TIMER_ISR INTERVAL_TIMER_ISR: subi sp, sp, 40 stw ra, 0(sp) stw r4, 4(sp) stw r5, 8(sp) stw r6, 12(sp) stw r8, 16(sp) stw r10, 20(sp) stw r20, 24(sp) stw r21, 28(sp) stw r22, 32(sp) stw r23, 36(sp) /* Сохраняем регистры в стеке */ movia sthio r10, 0x10002000 r0, 0(r10) movia movia addi movia movia r20, 0x10000020 r21, 0x10000030 r5, r0, 1 r22, PATTERN r23, KEY_PRESSED ldw stwio stwio r6, 0(r22) r6, 0(r20) r6, 0(r21) ldw movi beq rol br LEFT: ror r4, 0(r23) /* Проверяем, какая кнопка была нажата */ r8, KEY1 r4, r8, LEFT /* Если была нажата key1, то сдвигаем текст вправо */ r6, r6, r5 /* иначе, сдвигаем влево */ END_INTERVAL_TIMER_ISR /* загружаем текст для вывода на 7-сегментные индикаторы */ /* выводим на HEX3 ... HEX0 */ /* выводим на HEX7 ... HEX4 */ r6, r6, r5 END_INTERVAL_TIMER_ISR: stw r6, 0(r22) ldw ldw ldw ldw ldw ra, 0(sp) r4, 4(sp) r5, 8(sp) r6, 12(sp) r8, 16(sp) /*адрес регистра HEX3_HEX0 */ /*адрес регистра HEX7_HEX4*/ /* сдвигаем текст вправо*/ /* выводим текст на 7-сегментные индикаторы */ /* Восстанавливаем регистры из стека */ 43 ldw ldw ldw ldw ldw addi ret r10, 20(sp) r20, 24(sp) r21, 28(sp) r22, 32(sp) r23, 36(sp) sp, sp, 40 .end Листинг 7 Текст программы pushbutton_ISR.s .include "key_codes.s" .extern KEY_PRESSED .extern PATTERN /******************* Обработчик прерываний от кнопок************************/ .global PUSHBUTTON_ISR PUSHBUTTON_ISR: subi sp, sp, 20 stw ra, 0(sp) stw r10, 4(sp) stw r11, 8(sp) stw r12, 12(sp) stw r13, 16(sp) movia ldwio stwio r10, 0x10000050 r11, 0xC(r10) r0, 0xC(r10) /* Сохраняем регистры в стеке*/ /* Считываем значение из edge-capture регистра*/ /* Сбрасываем прерывание */ movia r10, KEY_PRESSED CHECK_KEY1: andi r13, r11, 0b0010 /* Если была нажата кнопка key1 */ beq r13, zero, CHECK_KEY2 movi r12, KEY1 stw r12, 0(r10) br END_PUSHBUTTON_ISR CHECK_KEY2: andi r13, r11, 0b0100 /* Если была нажата кнопка key2*/ beq r13, zero, DO_KEY3 movi r12, KEY2 stw r12, 0(r10) br END_PUSHBUTTON_ISR DO_KEY3: movia r13, 0x10000040 44 ldwio movia stw r11, 0(r13) r13, PATTERN r11, 0(r13) END_PUSHBUTTON_ISR: ldw ra, 0(sp) ldw r10, 4(sp) ldw r11, 8(sp) ldw r12, 12(sp) ldw r13, 16(sp) addi sp, sp, 20 /* Считываем значение с переключателей */ /* Сохраняем измененный текст */ /* Восстанавливаем регистры из стека */ ret .end Лабораторная работа №4 Исследование работы интервального таймера и применение его в приложениях пользователя Цель работы: изучение работы интервального применение его в приложениях пользователя. таймера и Исходные файлы лабораторной работы Программа, демонстрирующая использование интервального таймера, входит в состав приложения АМР. Она доступна в разделе Sample program под именем interrupt_example.s. Текст программы приведен в листинге 5 приложения к третьей работе. Подготовка к лабораторной работе Для выполнения лабораторной работы необходимо изучить по материалам лекций и предложенной литературе. 1. Назначение регистров и отдельных полей регистров интервального таймера, входящего в состав процессорной системы «DE2-70 Media Computer»[9]. Включите в отчет. 2. Реализацию прерываний в процессорной системе с процессором NIOSII. Используемые для этого регистры процессора и портов ввода – вывода[8]. 45 3. Уясните принцип действия программы interrupt_example.s., в которой выполняется настройка интервального таймера. Текст программы содержится в листинге 5 приложения к третьей работе. Включите ее в отчет. 4. Уясните пункты задания, выполняемого в текущей лабораторной работе, и напишите программные заготовки для их выполнения. Порядок выполнения лабораторной работы Часть 1. Исследование работы интервального таймера (запуск, считывание текущего состояния и останов) 1. Напишите фрагмент программы, в котором вначале задается максимальное значение счетчика для интервального таймера. Следующая команда выполняет запуск таймера, а следующая – фиксирует его текущее значение. Для этого необходимо выполнить запись в соответствующий регистр таймера (snapshot). Затем выполняется загрузка из регистра snapshot в регистр процессора с использованием операций полусловного чтения и считывание регистра состояния таймера. Следующая команда выполняет безусловный переход сама на себя. 2. Выполните программу из предыдущего пункта по шагам. Запишите в отчет считанные значения со счетчика таймера и состояния битов RUN и TO регистра состояния таймера. 3. Повторите выполнение предыдущего пункта, выдержав паузу перед выполнением команды записи в регистр snapshot таймера. 4. Поставьте контрольную точку на последней команде (команда br) и запустите программу. Запишите в отчет наблюдаемые результаты. Объясните наблюдаемое значение бита ТО. 5. Напишите фрагмент кода, в котором выполняется задание интервала для таймера, старт таймера и его останов с последующим считыванием текущего значения счетчика таймера в регистр процессора по аналогии с пунктом 1. первой части. 6. Выполните программу из предыдущего пункта по шагам. Запишите в отчет считанные значения со счетчика таймера и состояния битов RUN и TO регистра состояния таймера. 7. Повторите выполнение предыдущего пункта, выдержав паузу перед выполнением команды записи в регистр snapshot таймера. 8. Повторите выполнение предыдущих пунктов, вставив после выполнения останова таймера команду записи в регистр snapshot таймера. 46 9. Поставьте контрольную точку на последней команде (команда br) и запустите программу. Запишите в отчет наблюдаемые результаты. Объясните наблюдаемое значение бита ТО. 10. Оцените длительность выполнения команд процессора ldw, stw, ldwio, stwio и некоторых других, вставив их в фрагмент программы из пункта 4 между командами запуска таймера и считыванием его текущего значения. Попробуйте обратиться к памяти, реализованной на кристалле, к статической и динамической памяти. Отразите в отчете наблюдаемые значения. 11. Вставьте в программу из пункта 4 после команды запуска таймера команду вычитания единицы из регистра, например R3, процессора. Повторите выполнение 4 пункта задания. Определите длительность выполнения команды subi. 12. Подтвердите Ваши выводы, вставив в программу подряд несколько команд subi. 13. Добавьте в программу из пункта 6 команду перехода на повтор команды subi, если текущее значение R3 не равно 0. Экспериментально оцените длительность выполнения команды bne в случаях, когда переход на повтор команды вычитания subi не выполняется и когда выполняется. Подтвердите Ваши выводы, задавая разные значения R3. 14. Рассчитайте длительность выполнения цикла уменьшения R3 для случая, когда R3 равняется n, и экспериментально проверьте Ваши расчеты, задавая разные значения n. Рекомендуется эксперимент проводить следующим образом. Первую контрольную точку следует установить перед командой записи начального значения в счетчик таймера. Вторая контрольная точка устанавливается в конце программы. 15. Рассчитайте начальное значение R3 таким образом, чтобы программный цикл выполнялся ровно 1 минуту (90 секунд). Проверьте рассчитанное значение экспериментально, сверяя время выполнения фрагмента программы с наручными часами. Покажите выполнение этого пункта преподавателю. Чтобы более точно обнаружить время завершения, в конце программы используйте включение светодиодов. 16. Повторите выполнение предыдущего пункта, выполнив перед программным циклом запуск таймера, а после выхода из цикла – считывание его значения. Определите правильность работы Вашей программы, сравнив программную задержку с длительностью интервала, зафиксированную таймером. 17. Реализуйте в Вашей программе программный счетчик секунд и выведите его состояние на светодиоды. Проверьте правильность его работы, сверяя с наручными часами. 47 Часть 2. Использование приложениях пользователя интервального таймера в 1. Рассчитайте начальное значение счетчика таймера таким образом, чтобы он подсчитывал интервал длительностью 30 секунд и по окончанию формировал сигнал прерывания. Основная программа разрешает прерывания от таймера, задает длительность интервала для таймера и запускает его. Затем она выводит Ваши фамилию, имя и отчество на экран LCD в режиме бегущей строки. Обработчик прерывания зажигает светодиоды и выполняет возврат в основную программу. Экспериментально проверьте работу программы, сопоставив интервал с Вашими часами. Запишите в отчет значение регистра состояния таймера. 2. Рассчитайте длительность максимального интервала, формируемого таймером, с учетом того, что его тактовая частота равна 50 МГц (для стендов DiLab и miniDilab частота равна 25МГц). Проверьте экспериментально, сопоставив с Вашими часами. 3. Модифицируйте программу из первого пункта таким образом, чтобы прерывания от таймера формировались каждую секунду. Обработчик прерывания реализует счетчик секунд и выводит его значение на светодиоды и HEX-индикаторы в шестнадцатеричном виде. Используйте для этого процедуру из 3 лабораторной работы. Проверьте правильность работы программы, визуально наблюдая отображаемые значения и сопоставляя их с показаниями Ваших часов. 4. Модифицируйте процедуру из 2 лабораторной работы, в которой осуществляется вывод на дисплей LCD текстовой информации в режиме бегущей строки. Используйте для этого прерывания от таймера, формируемые через каждые 200 мс. Часть 3. Создание часов реального времени 1. Модифицируйте программу таким образом, чтобы реализовать на устройствах отображения информации стенда часы реального времени. Причем, для задания текущего значения времени используйте переключатели и кнопки. Рекомендуется использовать переключатели SW для задания значения текущего часа и текущей минуты. Причем ввод их осуществите последовательно, используя двоично – десятичное кодирование (код D1), нажатием кнопок KEY3 и KEY2, соответственно. Для запуска часов, начиная с нулевой секунды 48 иcпользуйте кнопку KEY1. Вывод текущего времени выполните на HEX-индикаторы для стендов DE0 и DE2-70, и на LCD-дисплей для других стендов. Вывод времени должен осуществляться в режиме прерываний на фоне работы другой программы, выполняющей, например, вывод Вашей фамилии имени и отчества на экране LCD в режиме бегущей строки. Отчетные материалы Отчетные материалы должны содержать. 1. Цель лабораторной работы. 2. Материалы, связанные с подготовкой к работе, включая теоретическую часть. 3. Информацию по выполнению каждого пункта задания. Причем в отчете должны содержаться выполняемые Вами действия, наблюдаемые результаты, и Ваши объяснения. 4. Написанные Вами фрагменты программ. 5. Краткое заключение. Лабораторная работа №5 Использование интерфейсов JTAG , RS232 и инфракрасного порта в процессорной системе Цель работы: использование интерфейса JTAG для сопряжения процессорной системы, реализованной на стенде, с инструментальным компьютером и интерфейса RS232 и инфракрасного порта для сопряжения двух процессорных систем. Исходные файлы лабораторной работы Программа, демонстрирующая использование JTAG UART порта в процессорной системе, является составной частью приложения AMP. Она доступна в разделе Sample program под именем JTAG UART.s. Подготовка к лабораторной работе Для выполнения лабораторной работы необходимо изучить по материалам лекций и предложенной литературе. 49 1. Организацию обмена данными между стендом и инструментальным компьютером. 2. Принцип работы и назначение регистров и отдельных полей JTAG UART порта. Эта информация содержится в описании процессорной системы «DE2-70 Media Computer»[9]. Включите ее в отчет. 3. Реализацию прерываний в процессорной системе с процессором NIOSII[8]. Используемые для этого регистры процессора и портов ввода – вывода. 4. Особенности использования вложенных прерываний. 5. Уясните принцип действия программы, работающей с интерфейсом JTAG из файла JTAG UART.s. Включите ее в отчет. 6. Уясните содержимое фрагмента программы TEST_DE2_70_Media_Computer из листинга 9 приложения и включите его в отчет. 7. Уясните пункты задания, выполняемого в текущей лабораторной работе, и напишите программные заготовки для их выполнения. В лабораторной работе ASCII-коды символов, введенных в терминальном окне AMP, отправляются в процессорную систему, реализованную на стенде с использованием UART JTAG интерфейса, отображаются на светодиодах и 7-сегментных индикаторах, затем отправляются обратно в инструментальный компьютер, и отображаются в терминальном окне AMP. Выполняется сопряжение двух процессорных систем, реализованных на разных стендах, через их последовательные COM порты и инфракрасные порты. Порядок выполнения лабораторной работы Часть 1. Запись в UART JTAG (вывод информации) 1. Напишите программу, которая записывает символ z в порт UART JTAG. Предусмотрите в программе анализ поля WSPACE в регистре управления UART, отражающего наличие свободного места в буфере FIFO для записываемых символов. Реализуйте выход из программы, если свободного места нет. 2. Отладьте программу. По содержимому поля WSPACE определите размер буфера FIFO. Используйте для этого окно с содержимым регистров AMP. Измените символ z на другой символ. 3. Модифицируйте программу из предыдущего пункта таким образом, чтобы символы выводились многократно. Реализуйте программную задержку в цикле вывода. Подберите задержку таким образом, чтобы происходило следующее. 50 4. Программа завершалась по переполнению буфера FIFO, и при этом выводилось в терминальное окно AMP минимальное количество символов. Подсчитайте количество выведенных символов. Сравните со значением, полученным в пункте 2. 5. Буфер FIFO никогда не переполняется, и программа реализует бесконечный цикл. 6. Буфер FIFO успевает вывести некоторое количество символов до того, как он переполнится. Запишите в отчет подобранные задержки. 7. Напишите программу, которая выводит в терминальное окно AMP некоторое сообщение. Сообщение поместите в сегменте данных программы. Для этого используйте директиву .ASCIIZ ассемблера. Программа должна анализировать выводимый байт, и если он равен нулю, то вывод должен прекращаться. Оформите эту программу в виде процедуры, которая в последующем может быть использована для вывода из NIOS II процессорной системы различных сообщений. Параметром, передаваемым этой процедуре, является адрес текстовой строки в сегменте данных. В качестве тестового примера выведите свою фамилию, имя и отчество. Часть 2. Чтение из JTAG UART (ввод информации) 1. Напишите подпрограмму, которая выполняет чтение из порта UART JTAG. Подпрограмма должна анализировать бит RVALID в регистре данных UART. Если этот бит равен 1, считанные данные присутствовали в буфере FIFO и они достоверны. В противном случае, данных в буфере нет, и подпрограмма должна ожидать их появления. Принятый из UART JTAG символ, основная программа должна отобразить на светодиодах и двух 7-сегментных индикаторах, записать обратно в JTAG и так далее в цикле. Отладьте подпрограмму. 2. С помощью AMP откомпилируйте программу из предыдущего пункта и загрузите в память. Поставьте контрольную точку в программе после приема первого символа из UART JTAG. Проанализируйте поле RAVAIL. Запишите в отчет. Обратите внимание! Для анализа поля RAVAIL потребуется установить галочку Query all devices и нажать кнопку Refresh. Учтите, что при этом произойдет чтение регистра данных UART JTAG и, следовательно, удаление символа из вершины буфера FIFO и уменьшение поля RAVAIL на 1. Повторите эксперимент, но предварительно напечатайте в терминальном окне AMP несколько символов с клавиатуры. Проанализируйте поле RAVAIL. Уберите галочку Query all devices, уберите контрольную точку и продолжите выполнение программы. Сравните количество выведенных символов в терминальном окне AMP с содержимым поля RAVAIL. Повторите 51 эксперимент. Экспериментально определите размер буфера FIFO для читаемых данных. 3. Модифицируйте программу таким образом, чтобы коды печатаемых символов отображались на светодиодах. Составьте таблицу кодов ASCII для десяти цифр, нескольких букв вашей фамилии. Получите код символа @. В этом пункте было бы полезно использовать вывод на два 7-сегментных индикатора. Получите коды ASCII для одной и той же клавиши прописными и заглавными буквами, в английской и русской раскладке. 4. Модифицируйте подпрограмму чтения из порта UART JTAG таким образом, чтобы ASCII-коды выводимых символов записывались в память побайтно. Ввод должен завершаться при получении специального символа, например @. В конец строки должен быть добавлен нулевой байт. Подпрограмма в последующем будет полезна для реализации ввода информации в NIOS II процессорную систему с клавиатуры инструментального компьютера. Отправьте сохраненную строку в UART JTAG порт, используя подпрограмму, написанную в пункте 7 первой части. Часть 3. Ввод из UART JTAG в режиме прерывания 1. Модифицируйте программу таким образом, чтобы ввод текстовой строки из инструментального компьютера осуществлялся в режиме прерывания. Для этого основная программа разрешает прерывания по чтению от UART JTAG и выполняет вывод строки с Вашей фамилией, именем и отчеством на дисплей LCD в режиме бегущей строки. Ввод текста в терминальную строку приводит к прерыванию основной программы, и обработчик далее осуществляет ввод строки в ОП и вывод в UART JTAG всей строки, пока не обнаружит символ конца строки. 2. Модифицируйте программу таким образом, чтобы после ввода каждого символа обработчик возвращал управление основной программе. В этом случае анализ конца строки не потребуется. Визуально наблюдайте правильность работы программы. Часть 4. Ввод из JTAG UART в режиме прерывания с использованием вложенного прерывания от таймера 1. Модифицируйте программу из предыдущей части так, чтобы реализовать вывод символов в терминальном окне AMP следующим образом. Набранный на клавиатуре символ выводится в терминальном окне AMP каждые 500мс. 52 2. Модифицируйте программу из предыдущей части таким образом, чтобы основная программа разрешила прерывания по чтению от UART JTAG и выводила бегущую строку на LCD. При нажатии клавиши клавиатуры формируется прерывание основной программы. Обработчик прерывания UART JTAG разрешает прерывания от таймера каждые 500 мс и возвращает управление основной программе. Обработчик прерывания от таймера выводит символ в терминальное окно AMP каждые 500 мс, причем, если клавиша не нажата, выводится последний набранный символ. Часть 5. Использование COM-порта для сопряжения двух процессорных систем, реализованных на разных стендах 1. Соедините нуль-модемным кабелем два стенда, используя разъемы RS-232. Включите питание стендов. Обратите внимание, что светодиоды RXD и TXD, расположенные в правой верхней части стенда светятся. Это означает, что тестовая программа, выполняющаяся в процессорной системе на стенде после включения его питания, выполняет отправку и прием данных в/из COM-порта. 2. Запустите приложение AMP и загрузите процессорную систему «DE2-70 Media Computer» в стенд. Выполните аналогичные действия на втором стенде. Используя вкладку Memory AMP, выполните пересылку данных в другую процессорную систему через com-порт. Наблюдайте принятые данные в другой процессорной системе. Следует напомнить, что для отображения содержимого регистров портов ввода/вывода следует установить галочку Query all devices, а для того, чтобы выполнить считывание из порта, следует нажать кнопку Refresh memory. Отразите в отчете значение полей RVALID, RAVAIL и WSPACE COM-порта. Экспериментально определите размер буфера FIFO, используемого на запись. 3. Модифицируйте программу из пункта 2 части 3 так, чтобы реализовать следующий эксперимент. Процессорная система, реализованная на первом стенде, выполняет программу из пункта 2 части 3. Аналогичную программу выполняет вторая процессорная система, реализованная на втором стенде. Дополнительно программа, работающая в процессорной системе на первом стенде, должна передать набираемые в терминальном окне AMP символы в COM-порт. Также она должна разрешить прерывания по чтению при получении символов из com-порта. Обратите внимание! Прерывания будут формироваться при заполнении приемного буфера FIFO более чем на 3/4. Обработчик прерывания должен выполнить вывод принятых из com-порта символов на экран LCD. Чтобы визуально наблюдать вывод на LCD экран по одному символу, используйте в обработчике 53 контрольную точку перед выполнением команды eret. Экспериментально определите порог заполнения входного буфера FIFO, при котором формируется прерывание. Программа на второй процессорной системе выполняет аналогичные действия. Продемонстрируйте совместную работу двух процессорных систем преподавателю. Часть 6. Использование инфракрасного порта для беспроводной передачи данных между процессорными системами Для выполнения этой части работы требуется модификация процессорной системы «DE2- 70 Media Computer». В её состав необходимо добавить контроллер инфракрасного порта, реализованный в виде IP ядра. Соответствующая модификация системы выполнена и все файлы, необходимые для выполнения работы, помещены в папку lab5 на рабочем столе. 1. Разместите два стенда таким образом, чтобы их приемопередатчики инфракрасного порта располагались друг напротив друга на небольшом расстоянии. 2. Произведите запись значения в поле данных регистра инфракрасного порта. На второй процессорной системе выполните команду Refresh memory. Убедитесь, что данные получены. Обратите внимание! Отправляемые данные могут попадать во входной буфер инфракрасного порта первой процессорной системы. 3. Модифицируйте программу из предыдущей части таким образом, чтобы вместо COM-порта использовался инфракрасный порт. Отчетные материалы Отчетные материалы должны содержать: 1. Цель лабораторной работы. 2. Материалы, связанные с подготовкой к работе, включая теоретическую часть. 3. Фрагменты программ JTAG UART.s и TEST_DE2_70_Media_Computer. 4. Информацию по выполнению каждого пункта задания. Причем в отчете должны содержаться выполняемые Вами действия, наблюдаемые результаты, и Ваши объяснения. 5. Написанные Вами фрагменты программ. 6. Краткое заключение. 54 Приложение В приложении содержится файл JTAG UART, встроенный в приложение AMP. В этой программе осуществляется вывод текстовой строки из процессорной системы в JTAG UART, и ввод текстовой строки, набираемой в терминальном окне AMP, через JTAG UART и вывод обратно. В приложении также содержится фрагмент из файла Test_DE2_70_Media_Computer, который полностью приведен в приложении к первой лабораторной работе. В представленном фрагменте выполняется работа с регистрами UART JTAG и com-порта. Листинг 8 Текст программы JTAG UART.s /**************************************************************** * Программа выполняет следующее: * 1. отправляет символьную строку из текстовой строки в JTAG UART * 2. считывает данные из JTAG UART * 3. отправляет считанные данные обратно в JTAG UART ********************************************************************/ .text .global _start _start: movia sp, 0x07FFFFFC movia r6, 0x10001000 movia LOOP: ldb call JTAG */ r8, TEXT_STRING addi r8, r8, 1 br r5, 0(r8) PUT_JTAG LOOP GET_JTAG: ldwio r4, 0(r6) andi r8, r4, 0x8000 beq r8, r0, GET_JTAG /* Определяем адрес вершины стека */ /* адрес текстовой строки в r8 */ /* из текстовой строки в r5*/ /* вызываем процедуру, которая помещает символ в /* переходим на вывод очередного символа */ /*читаем регистр управления JTAG UART*/ /*проверяем есть ли новые данные*/ /*если данных нет, то ожидаем их появления*/ 55 andi r5, r4, 0x00ff /*получаем данные*/ call call PUT_JTAG GET_JTAG /*отправляем символ обратно в JTAG UART*/ .end /******************************************************************** * Подпрограмма, которая выводит символы в JTAG UART * r5 = выводимый символ * r6 = JTAG UART базовый адрес ********************************************************************/ .global PUT_JTAG PUT_JTAG: /* сохраняем используемые регистры */ /* резервирум место в стеке*/ /* сохраняем r4 в стеке */ subi stw sp, sp, 4 r4, 0(sp) ldwio andhi UART */ beq stwio r4, 4(r6) r4, r4, 0xffff /* читаем регистр управления JTAG UART */ /* проверяем есть ли место для записи в буфере r4, r0, KONEC r5, 0(r6) /* если места нет, то переполнение буфера */ /* отправляем символ в UART */ OVERFLOW: /* восстанавливаем содержимое r4 */ ldw addi r4, 0(sp) sp, sp, 4 ret /******************************************************************/ .data TEXT_STRING: .asciz "\nJTAG UART example code\n" .end 56 Листинг 9 Фрагмент программы TEST_DE2_70_Media_Computer /**************************************************************** * Процедура анализирует, имеются ли данные в буфере чтения JTAG порта. * Если есть, то данные отправляются обратно в JTAG порт и дополнительно в * COM-порт. Если новых данных нет, то выполняется проверка, имеются ли данные в буфере чтения com-порта. Если данные есть, то они отправляются обратно в com-порт и дополнительно в JTAG порт. А если нет, то происходит выход из процедуры. ********************************************************************/ .global UPDATE_UARTS UPDATE_UARTS: /* сохраняем регистры в стеке */ subi stw stw stw stw stw stw stw addi /* резервируем область памяти в стеке*/ sp, sp, 28 ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) fp, sp, 28 movia r15, JTAG_UART_BASE movia r19, UART_BASE /* помещаем в r15 адрес JTAG UART*/ /* помещаем в r19 адрес com-порта*/ GET_CHAR: ldwio r17, 0(r15) /* считываем слово из регистра данных JTAG UART*/ andi r18, r17, 0x8000 /* проверяем бит RVALID*/ beq r18, r0, GET_CHAR_UART /* если данных нет в буфере, то переходим на GET_CHAR_UART*/ andi r16, r17, 0x00ff /* выделяем байт данных из считанного из JTAG UART порта слова*/ PUT_CHAR: ldwio r17, 4(r15) /* считываем слово из регистра управления JTAG UART*/ andhi r17, r17, 0xffff /* выделяем значение поля workspace*/ beq r17, r0, PUT_CHAR_UART /* если свободного места в буфере нет, то переходим на PUT_CHAR_UART*/ stwio r16, 0(r15) /* отправляем символ обратно в JTAG UART*/ PUT_CHAR_UART: ldwio r17, 4(r19) andhi r17, r17, 0xffff /* считываем слово из регистра управления*/ com-порта*/ /* выделяем значение поля workspace*/ 57 beq r17, r0, GET_CHAR_UART переходим на GET_CHAR_UART*/ stwio r16, 0(r19) GET_CHAR_UART: ldwio r17, 0(r19) andhi r18, r17, 0xFFFF beq r18, r0, NO_CHAR andi r16, r17, 0x00ff слова*/ /* если свободного места нет в буфере, то /* отправляем символ в com-порт*/ /* считываем слово из регистра данных com-порта*/ /* выделяем значение поля RAVAIL*/ * если новых данных нет, то переходим на NO_CHAR*/ /* выделяем байт данных из считанного из com-порта /* считываем слово из регистра управления com-порта*/ ldwio r17, 4(r19) andhi r17, r17, 0xffff beq r17, r0, PUT_CHAR_JTAG переходим на PUT_CHAR_JTAG*/ stwio r16, 0(r19) PUT_CHAR_JTAG: ldwio r17, 4(r15) JTAG UART*/ andhi r17, r17, 0xffff beq r17, r0, NO_CHAR переходим на NO_CHAR*/ stwio r16, 0(r15) NO_CHAR: /* выделяем значение поля workspace*/ /* если свободного места нет в буфере, то /* отправляем символ в com-порт*/ /* считываем слово из регистра управления /* выделяем значение поля workspace*/ /* если свободного места нет в буфере, то /* отправляем символ в JTAG UART*/ /* извлекаем из стека регистры */ ldw ldw ldw ldw ldw ldw ldw addi ret ra, 0(sp) fp, 4(sp) r15, 8(sp) r16, 12(sp) r17, 16(sp) r18, 20(sp) r19, 24(sp) sp, sp, 28 /* выполняем возврат из процедуры*/ 58 Список литературы 1. Грушвицкий Р.И., Мурсаев А.X. Угрюмов Е.П. Проектирование систем на микросхемах с программируемой структурой. 2-е изд., перераб. и доп. СПб.: БХВ-Петербург, 2006. - 736с. 2. Тарасов И.Е. Разработка цифровых устройств на основе ПЛИС Xilinx с применением языка VHDL. – М.: Горячая линия – Телеком, 2005. 252с. 3. Ефремов Н.В. Введение в систему автоматизированного проектирования Quartus II. Учебное пособие. – М.: ГОУ ВПО МГУЛ, 2011.-147с. 4. DE2-70 Development and Education Board. Интернет ресурс. http://www.altera.com/education/univ/materials/boards/de2-70/unv-de2-70board.html?GSA_pos=1&WT.oss_r=1&WT.oss=de-270 5. Ефремов Н.В., Бородин А.А. Инструментальные средства проектирования и отладки цифровых систем на программируемом кристалле фирмы «Altera». Учебное пособие. – М.: ФГБОУ ВПО МГУЛ, 2012.- 123с. 6. Altera Monitor Program. Интернет ресурс. ftp://ftp.altera.com/up/pub/Altera_Material/11.0/Tutorials/Altera_Monitor_Prog ram.pdf 7. Введение в SOPC Builder. Интернет ресурс. ftp://ftp.altera.com/up/pub/Altera_Material/11.0/Tutorials/VHDL/Introduction_ to_the_Altera_SOPC_Builder.pdf 8. Введение в процессор NIOS II. Интернет ресурс. ftp://ftp.altera.com/up/pub/Altera_Material/11.0/Tutorials/Nios2_ introduction.pdf 9. Процессорная система «DE2-70 Media Computer». Интернет ресурс. ftp://ftp.altera.com/up/pub/Altera_Material/11.0/Examples/DE270/NiosII_Computer_Systems/DE2-70_Media_Computer.pdf 59 Содержание Предисловие Лабораторная работа №1 4 6 Исходные файлы лабораторной работы 6 Подготовка к лабораторной работе 6 Порядок выполнения лабораторной работы 7 Часть 1. Реализация процессорной системы на кристалле, загрузка и выполнение тестовой программы 7 Часть 2. Использование приложения АМР для работы с портами ввода вывода процессорной системы 10 Часть 3. Использование АМР для компиляции, загрузки и отладки программы 10 Часть 4. Вывод информации на LCD индикатор 12 Часть 5. Выполнение команд загрузки (load) и сохранения (store) в процессорной системе 13 Часть 6. Тестирование всех типов оперативной памяти, используемой в процессорной системе 14 Отчетные материалы 15 Приложение 15 Листинг 1. Исходный файл программы тестирования процессорной системы TEST_DE2_70_Media_Computer.s 16 Листинг 2 Исходный файл программы lab1_part3_DE.s 25 Листинг 3 Исходный файл программы LCD_DE2_70.s 26 Лабораторная работа №2 Исходные файлы лабораторной работы Подготовка к лабораторной работе Порядок выполнения лабораторной работы Часть 1. Передача параметров через регистры Часть 2. Передача параметров через стек Часть 3. Использование вложенных процедур Часть 4. Использование файлов с исходными данными в AMP Индивидуальное задание Отчетные материалы Лабораторная работа №3 28 29 29 29 29 30 31 31 32 33 34 Исходные файлы лабораторной работы 34 Подготовка к лабораторной работе 34 Порядок выполнения лабораторной работы 35 Часть 1. Программно управляемый ввод с переключателей и вывод на светодиоды 35 Часть 2. Ввод информации с переключателей с опросом их готовности 36 Часть 3. Вывод информации на семисегментные индикаторы 36 Часть 4. Ввод информации с переключателей в режиме прерывания 37 Часть 5. Реализация приоритетных прерываний 37 60 Часть 6. Программное прерывание trap и невыполнимые команды Отчетные материалы Приложение Листинг 4 Текст программы interrupt_example.s Листинг 5 Текст программы exception_handler.s Листинг 6 Текст программы interval_timer.s Листинг 7 Текст программы pushbutton_ISR.s Лабораторная работа №4 38 38 38 39 40 41 43 44 Исходные файлы лабораторной работы 44 Подготовка к лабораторной работе 44 Порядок выполнения лабораторной работы 45 Часть 1. Исследование работы интервального таймера (запуск, считывание текущего состояния и останов) 45 Часть 2. Использование интервального таймера в приложениях пользователя 47 Часть 3. Создание часов реального времени 47 Отчетные материалы 48 Лабораторная работа №5 48 Исходные файлы лабораторной работы 48 Подготовка к лабораторной работе 48 Порядок выполнения лабораторной работы 49 Часть 1. Запись в UART JTAG (вывод информации) 49 Часть 2. Чтение из JTAG UART (ввод информации) 50 Часть 3. Ввод из UART JTAG в режиме прерывания 51 Часть 4. Ввод из JTAG UART в режиме прерывания с использованием вложенного прерывания от таймера 51 Часть 5. Использование COM-порта для сопряжения двух процессорных систем, реализованных на разных стендах 52 Часть 6. Использование инфракрасного порта для беспроводной передачи данных между процессорными системами 53 Отчетные материалы 53 Приложение 54 Листинг 8 Текст программы JTAG UART.s 54 Листинг 9 Фрагмент программы TEST_DE2_70_Media_Computer 56 Список литературы 58 61 Учебное издание Н.В. Ефремов Создание процессорной системы на кристалле ПЛИС и последующее её исследование В авторской редакции Компьютерный набор и верстка автора По тематическому плану внутривузовских изданий учебной литературы на 2011 г. (поз.248). Подписано в печать Издательство Московского государственного университета леса 141005, Мытищи-5, Московская обл., 1-я Институтская, 1, МГУЛ. E-mail: izdat@mgul.ac.ru