音乐程序课程设计.docx
- 文档编号:10776698
- 上传时间:2023-02-22
- 格式:DOCX
- 页数:23
- 大小:54.26KB
音乐程序课程设计.docx
《音乐程序课程设计.docx》由会员分享,可在线阅读,更多相关《音乐程序课程设计.docx(23页珍藏版)》请在冰豆网上搜索。
音乐程序课程设计
学号:
兰州理工大
课程设计
题目
音乐程序设计
教学院
山丹培黎学校
专业
应用电子技术
班级
09)秋大专电子班
姓名
贾高强
指导教师
王文珍
2010
年
10
月
1
日
一概述
1背景分析
汇编语言是一种功能很强的程序设计语言,也是利用运算机所有硬件特性并能直接操纵硬件的语言。
汇编语言,作为一门语汇编语言言,对应于高级语言的编译器,需要一个“汇编器”来把汇编语言原文件汇编成机械可执行的代码。
高级的汇编器如MASM,TASM等等为咱们写汇编程序提供了很多类似于高级语言的特点,比如结构化、抽象等。
在如此的环境中编写的汇编程序,有专门大一部份是面向汇编器的伪指令,已经类同于高级语言。
此刻的汇编环境已经如此高级,即便全数用汇编语言来编写windows的应用程序也是可行的,但这不是汇编语言的优势。
汇编语言的优势在于编写高效且需要对机械硬件精准操纵的程序。
大多数情形下Linux程序员不需要利用汇编语言,因为即即是硬件驱动如此的底层程序在Linux操作系统中也能够用完全用C语言来实现,再加上GCC这一优秀的编译器目前已经能够对最终生成的代码进行专门好的优化,的确有足够的理由让咱们能够临时将汇编语言抛在一边了。
但实际情形是Linux程序员有时仍是需要利用汇编,或不能不利用汇编,理由很简单:
精简、高效和libc无关性。
假设要移植Linux到某一特定的嵌入式硬件环境下,第一必然面临如何减少系统大小、提高执行效率等问题,现在或许只有汇编语言能帮上忙了
《音乐演奏程序设计》课程设计是在教学实践基础上进行的一次大型实验,也是对该课程所学理论知识的深化和提高。
因此,要求咱们能综合应用所学知识,设计与制造出具有较复杂功能的应用系统,而且在实验的大体技术方面上进行一次全面的训练。
通过具体的问题分析、设计、调试、运行程序。
在实际问题中锻炼提高自己,增加了对本门课程内容的明白得,锻炼了动手能力。
就那个程序具体而言:
明白了音调与频率和时刻的关系,就能够够依照乐曲的乐谱将每一个音符的频率和持续时刻概念成两个数据表;然后编写程序一次掏出表中的频率值和时刻值,挪用GENSOUDF程序发出各类声音。
那个程序最终通过菜单所提示的信息选取所欣赏的音乐,是执行此程序后,会很有速且有效的使扬声器接通并发出音频位896Hz的声音。
2课程设计目的
汇编语言是运算性能够提供用户利用的最快而又最有效的语言,也是能够用运算机所有特性能直接操纵硬件的唯一语言。
通过这次实验要求咱们:
(1)了解通用发声程序。
(2)了解与把握按时、计数、音乐、频率、时刻之间的关系。
(3)学会用发声程序的设计方式。
(4)学会用汇编编辑音乐程序。
那个地址要紧用到MASM来进行程序的调试和运行,在程序测试通事后,最后运行查看最终结果。
为了编写一个流行音乐乐曲演奏程序,分析时依照课程设计的要求必需要有操作提示、输入和输出。
在界面设计时应该追求友好,能够利用户便于利用该程序。
而且依照课题要求最好能够实现菜单式的界面,进一步提高该程序界面的友好性。
同时,在设计分析时也必需解决发声问题。
分析设计时依照讲义P383(通用发声程序)所示的设计方式解决发声问题。
通过音乐程序设计熟悉并把握用汇编语言编程的方式和特点,借此来比较高级语言低级语言的优缺点,以便更好运用各类语言来开发应用软件通过实际动手能力的培育,进一步熟悉汇编语言的结构和利用方式。
达到能独立阅读、编制和调试必然规模的汇编语言程序的水平,能用汇编语言熟练地运用三大结构,进一步把握各个指令的功能,专门是转向指令,能把握子程序的概念及调试,包括段间及段内挪用,和正确地运用DEBUG指令,进一步明白得和把握程序直接操纵I/O方式。
3课程设计要求及功能
3.1在本次课程设计中,编写源程序,并要求实现以下功能:
3.1.1采纳位触发方式编写程序,使运算机发出音响并奏出几首可选的乐曲。
(1)通过查阅相关资料,进一步明白得程序直接操纵I/O方式和位触发方式操纵声音的工作原理(两种方式的概念及工作进程)。
并要求如何实现,了解把握其运行各自的情形,在什么要的情形下利用。
(2)一首乐曲是由不同频率和节拍的音调组成,因此操纵脉冲的频率和持续时刻是编写乐曲程序的关键。
依照已知的音符频率对照表,给出乐曲的频率表:
设二分音符持续时刻为0。
5秒(50*10ms),50作为2拍的计数值,给出乐曲的节拍时刻表。
[1]
(3)用MASM进行调试,反复测试,不断反复的测试各个功能,看是不是会有程序运行错误。
例如:
极限值的设置等。
在不断测试程序直到正确时,测试工作才算完成,能够供以后的利用。
3.1.2进一步学习利用按时器产生声音的方式,使运算机奏出乐曲。
3.1.3必需全面了解MASM的功能,并能熟练利用MASM完成汇编程序的编译、调试、运行。
3.2MASM软件简介
3.2.1MASM的要紧版本:
2000年微软发布了MASM6。
15版本,后来显现MASM64位元版。
版是放在VisualC++6。
0ProcessorPack中。
版是放在VisualC++。
NET2002。
版是放在VisualC++。
NET2003。
版是放在VisualC++。
NET2005,它也能够组译x64的程式码。
3.2.2特点及功能介绍:
4.x1980年代末期最流行的版本,很多组合语言入门书都以它为范本。
5.x开始强化组译器简易指令(点指令),以简化程式架构。
稍晚的组合语言入门书亦大量运用此一版本。
6.x版本为了支援Windows,有几个重大特色:
(1)支援flat与386以上CPU爱惜模式。
整合PWB(Programmer'sWorkBench)开发环境。
这软件在同时期的QuickBASIC也找取得。
(2)支援DOSExtender,内建DOS/16M。
(3)开始支援OS/2与WinAPI。
(4)简易指令加入流程操纵表达,如。
IF、。
While、。
Exit。
。
。
。
。
。
等。
(5)强化对外部函式库的支援命令,如proto与invoke等指令,其中最核心的是将proc指令包装成符合高阶语言风格(支援C与Pascal风格)的形式,且invoke指令从头包装call与push/pop指令,能够更直观、高阶地运用函式。
这对呼唤高阶语言写成的函式、专门是繁复的WinAPI超级重要。
(6)masm与link整合为ML。
(7)NMake的makefile描述结构也产生了庞大的转变。
二整体方案设计
1设计思路
本程序应用了BIOS中断功能的字符显示和乐曲演奏程序。
并利用运算机操纵发声原理,在运算机中有一个可编程时刻距离按时器,它能依照程序提供的记数值和工作模式,产生各类形状和各类频率的记数按时脉冲,提供给系统各个部份利用。
该乐曲点播程序曲一个主程序和4个子程序组成。
其中前三个子程序为乐曲演奏子程序,接着是发声程序和清屏子程序,最后是一个回车换行程序。
1.1概念频率表和时刻表
依照音阶表和简谱位演奏的乐曲概念一个频率freg和一个节拍时刻表time。
频率表中的数据能够才书本查到,节拍时刻表中的数据是延迟时刻10ms的倍数。
1.2将两个表的偏移地址放入SI和DI
LEASLMUS_FREQ
LEABPDSMUS_TIME
1.3取频率和时刻
从表中掏出音符的频率放入DI,掏出音符的持续时刻(事实上是10ms的倍数)放入BX。
MOVDI,[SI]
MOVBX,DS:
[BP]
频率表中最后一个数据-1作为乐曲的终止符,也能够用0或其他的特殊值来代替。
1.4挪用SOUND子程序发出音调
挪用通用发声子程序GENSOUND发声音调。
那个程序比较简单,若是想演奏另一个乐曲,只需把freg和两个表中的数据换成另一个乐曲的频率和节拍时刻就能够够了。
2程序流程图如下:
图1程序流程图
Y
N
N
Y
三详细设计
1可编程时刻距离按时器8253
在通用个人运算机中,有一个可编程时刻距离按时器8253,它能够依照程序提供的计数值和工作方式,产生各类形状和各类频率的计数/按时脉冲,提供给系统各个部件利用。
本设计是利用运算机操纵发声的原理,编写演奏乐曲的程序。
在8253/54按时器内部有3个独立工作的计数器:
计数器0,计数器1和计数器2,每一个计数器都分派有一个断口地址,别离为40H,41H和54内部还有一个公用的操纵寄放器,端地址为43H.端口地址输入到8253/54的CS,AL,A0端,别离对3个计数器和操纵器寻址.
对8353/54编程时,先要设定操纵字,以选择计数器,确信工作方式和计数值的格式.每计数器由三个引脚与外部联系,见教材第320页图为时钟输入端,GATE为门控信号输入端,OUT为计数/按时信号输入端.每一个计数器中包括一个16位计数寄放器,那个计数器时以倒计数的方式计数的,也确实是说,从计数初值逐次减1,直到减为0为止.
8253/54的三个计数器是别离编程的,在对任一个计数器编程时,必需第一讲操纵字节写入操纵寄放器.操纵字的作用是告知8253/54选择哪个计数器工作,要求输出什么样的脉冲波形.另外,对8253/54的初始化工作还包括,向选定的计数器输入一个计数初值,因为那个计数值能够是8为的,也能够是16为的,而8253/5的数据总线是8位的,因此要用两条输出指令来写入初值.下面给出8253/54初始化程序段的一个例子,将计数器2设定为方式3,
MOVAL,B
OUT43H,AL
OUT42H,AL
MOVAL,AH
OUT42H,AL
在IBMPC中8253/54的三个时钟端CLK0,CLK1和CLK2的输入频率都是.PC机上的大多数I/O都是由主板上的8255(或8255A)可编程序外围接口芯片(PPI)治理的.关于8255A的结构和工作原理及应用举例参阅教材第340—373页.教材第364页的”PC/XT机中的扬声器接口电路”一节介绍了扬声器的驱动原理,并给出了通用发声程序.本设计正是基于那个原理,通过编程,操纵加到扬声器上的信号的频率,奏出乐曲的.
2发声程序设计
2.1扬声器驱动方式
利用计算机操纵发声的原理,能够编写演奏乐曲的程序。
PC机上的大多数都是由主板上的8255(或8255A)可编程序外围接口芯片(PPI)治理的。
PPI包括三个8位寄放器,两个用于输入功能,一个用于输出功能。
输入寄放器分派的I/O端口号60H和62,输出寄放器分派的I/O端口号位61H。
由PPI输出寄放器的0或1两位来操纵扬声器的驱动方式。
2.1.1采纳按时器方式:
它是利用8253/54按时器驱动扬声器。
连接到扬声器上的是2。
从扬声器的驱动系统图中能够明白,GATE2与端口61H的PBO相连,当PB0=1时,GATE2取得高电平,使按时器2能够在模板3下工作。
按时器2的OUT2与端口61H的PB1=1是,语序OUT2的输出信号抵达扬声器电路。
当通道2用于发声是,一样采纳模式3下,输出线为“1”和“0”的时刻各占计数时刻的一半,因此产生一系列距离均匀的脉冲。
2.1.2采纳位触发方式
程序直接操纵PPI(8255A可编程序外围接口芯片)的输出操纵寄放器(I/O端口位61H)的第一名,使该位按所需的频率进行1和0的交替转变,从而操纵开关电路产生遗传脉冲形,这些脉冲经放大后驱动扬声器发作声音。
若是操纵着一脉冲波形的脉宽和长度就能够够产生不同频率和不同音长的声音。
乐曲是依照必然的高低、长短和强弱关系组成的音调。
在一首乐曲中,每一个音符的音高和音长与频率和节拍有关。
组成乐曲的每一个音符的频率值和持续时刻是乐曲程序发声所需要的两个数据。
音符的频率能够从乐谱中查到,但事实上送入计数器2的是输入频率1。
1931MHz与音符频率相除的值,通过发生程序SOUNDF的前半部份确实是完成那个计算,并将计数值送入计数器2的功能。
音符的持续时刻是依照乐曲的速度及每一个音符的节拍数来确信的。
在4/4(四四拍)中,四分音符为1拍,每末节四拍,全音符持续4拍,二分音符持续2拍,四分音符持续1拍,八分音符持续半拍等。
若是给全音符分派1s(100*10ms)的时刻,那么二分音符的持续时刻为0。
5s(50*10ms),四分音符的持续时刻为0。
25s(25*10ms),八分音符的持续时刻为0。
125s(12。
5*10ms)。
明白了音调和频率的关系,就能够够依照乐曲的乐谱将每一个音符的频率和持续的时刻概念成两个数据表;然后编写程序依次掏出表中的频率值和时刻值,挪用程序发出各类声音。
[5]
380x86的时刻延迟
利用CPU循环执行一条或几条指令来产生延迟时刻是最经常使用的一种方式,但对8088/86,80286,80386,80486和pentiumIV来讲,由于它们的工作频率不同及有些指令执行周期的不同,执行一样的延迟程序,产生的延迟时刻都不一样。
为了成立一个与处置器无关的时刻延迟,1BM采纳了一种利用硬件产生时刻延迟的方式,即通过监视端口61H的PB4,使PB4每触发一次,以产生一个固定不变的时刻基准,。
下面的WAITF程序确实是一个产生Nx时刻延迟的程序。
挪用WALTF子程序时,CX寄放器必需装入的倍数N。
CX=的倍数
WAITFPROCNEAR
PUSHAX
WALTF1:
INAL,61H
ANDAL,10H;检测PB4的状态
CMPAL,AH;是不是发生转变
JEWAITF1;等待转变
MOVAH,AL;存入新的PB4的状态
LOOPWAITF1;循环,直到CX=0为止
POPAX
RET
WAITFENDP
当CX中的计数值N=663时,挪用WAITF子程序,可延迟10ms,假设要延迟1s,可挪用WAITF子程序100次,假设要延迟,可挪用WAITF子程序50次,依从类推,只要设置WAITF子程序的挪用次数,就可取得所需的延迟时刻。
4宏概念
宏是源程序中一段有独建功能的代码程序。
它只需要在源程序中概念一次,就能够够多次挪用它,调历时只需要用一个宏指令语句就能够够了。
宏概念是用一组微操作来实现的。
其格式是:
macronameMACRO[dummyparameterlist]
·
·
·
ENDM
其中MACRO和ENDM是一对伪操作。
这对伪操作之间是宏概念体——是一组有独建功能的程序代码。
宏指令名(macroname)给出该宏概念的名称,调历时确实是用宏指令名来挪用该宏概念。
宏指令名的第一个符号必需是字母,其后能够跟字母、数字或下划线字符。
其中哑元表(dummyparameterlist)给出了宏概念中所能用到的形式参数(或称虚参),每一个亚元之间用逗号隔开。
经宏概念后的宏指令就能够够在源程序中挪用。
这种对宏指令的挪用称为宏挪用,宏挪用的格式是:
macroname[actualparameterlist]
实元表(actualparameterlist)中的每一项为实元,彼此之间用逗号隔开。
当源程序被汇编时,汇编程序将对每一个宏挪用做宏展开。
宏展开确实是用宏概念取代原程序中的宏指令名,而且用实元取代宏概念中的哑元。
在取代时,实元和哑元是一一对应的,即第一个实元取代第一个哑元,第二个哑元取代第二个哑元···以此类推。
一样来讲,实元的个数应该和哑元的个数相等,但汇编程序并非要求他们必需相等。
假设实元个数大于哑元个数,那么多余的实元不予考虑;假设实元个数小于哑元个数,那么多余的哑元个数做“空”处置。
[6]
在程序中,咱们利用宏概念来实现字符串的输出功能,如此在输出提示语言时,不用每次都写一段很长的代码,而只需要改变宏概念中的参数即可。
具体的宏概念代码如下:
SHOWMACROb
LEADX,b
MOVAH,9
INT21H
ENDM
假设要调历时HELLO字符串,只须一句语句:
SHOWHELLO
那个地址需要注意的是,宏概念终止利用关键字NEDM,而不子程序终止时的ENDP。
5清屏子程序设计
屏幕的其实行列不为(0,0)终止的行列不为(24,79),那么屏幕上只有指定的一部份具有上卷的功能,那个屏幕伤的部份区域叫做窗口(window)像如此的窗口能够在屏幕上设置多个,这些窗口都能够独立利用。
若是上卷超过指定窗口的顶部,这些行的内容就消失,出此刻窗口底部的新行被填为空格,其属性用BH寄放器决定。
若是AL=0,那么实现完成的工作是清楚屏幕的功能,它将按AL中的Blank字符(0)使指定的窗口为空白。
CLEARPROCNEAR
PUSHAX
PUSHBX
PUSHCX
PUSHDX
MOVAH,6
MOVAL,0
MOVCH,0
MOVCL,0
MOVDH,48
MOVDL,158
MOVBH,7
INT10H
POPDX
POPCX
POPBX
POPAX
RET
CLEARENDP
四详细的算法描述
1主程序表述
codesegment
assumecs:
code,ds:
data
begin:
movax,data
movds,ax
next:
dispmsgmsgmenu
dispmsgmsgchoose;提示菜单及输入数字
inputbegin:
movah,01h
int21h
cmpal,'q';输入q那么退出
jeexit
cmpal,'1';比较数字<1?
jbdoagain
cmpal,'4';比较数字>4?
jadoagain
andax,000fh;将ASCII码转换成数字,以便后面指向table内外对应的地址
decax;减1,对应地址
shlax,1;相当于ax*2,因为table里的相邻偏移地址是2
movbx,ax
jmptable[bx];间接转移:
IP<--[table+bx]跳到table里面对应的程序段
exit:
movah,4ch
int21h
2音乐处置程序详细描述
music1:
dispmsgmsgdoing
movsi,offsetfreq_dahai
movdi,offsettime_dahai
m1:
movcx,[si]
cmpcx,-1
jenext
movbx,[di]
callgensound
addsi,2
adddi,2
jmpm1
music2:
dispmsgmsgdoing
movsi,offsetfreq_dongfengpo
movdi,offsettime_dongfengpo
m2:
movcx,[si]
cmpcx,-1
jenext
movbx,[di]
callgensound
addsi,2
adddi,2
jmpm2
music3:
dispmsgmsgdoing
movsi,offsetfreq_dashetou
movdi,offsettime_dashetou
m3:
movcx,[si]
cmpcx,-1
jexx
jmpxx1
xx:
jmpnext
xx1:
movbx,[di]
callgensound
addsi,2
adddi,2
jmpm3
3音乐处置程序详细描述
gensoundprocnear
pushdx
moval,0b6h;向计数器写操纵数
out43h,al;方式3、双字节写和二进制计数方式写操纵口
movdx,08h;设置被除数
movax,3208h
divcx;其商为预置值
out42h,al;先送LSB
moval,ah
out42h,al;后送MSB
inal,61h;读端口原值
movah,al
oral,3
out61h,al;接通扬声器
l2:
pushdx
pushax
movdx,8h
movax,0f05h
s1:
subax,1
sbbdx,0
jnzs1
popax
popdx
decbx
jnzl2
moval,ah;写回61h端口值,关闭扬声器
out61h,al
popdx
ret
gensoundend
五程序的调试与运行结果说明
4.1执行程序时,用户界面如下:
5.二、歌曲选择“1”时,以下图所示:
(张宇生《大海》)
5.3、歌曲选择“2”时,以下图所示:
(周杰伦《东风破》)
5.4、歌曲选择“3”时,以下图所示:
(吴克群《大舌头》)
5.5输入“q”程序返回DOS环境
5.6输入其他未概念字符,那么显示犯错
六使用说明
流行音乐乐曲演奏程序的歌曲清单如下:
1、张宇生《大海》
2、周杰伦《东风破》
3、吴克群《大舌头》
操作说明如下表:
输入
操作
字符“1”
播放张宇生《大海》
字符“2”
播放周杰伦《东风破》
字符“3”
播放吴克群《大舌头》
字符“q”
返回到DOS环境
其他字符
程序提示出错,返回菜单
七课程设计总结
通过了一周的汇编语言程序设计课程,使我能够如期地完成教师布置的课题,同时通过这次流行乐曲演奏程序的实习动手操作,使我解决了运算机是如何产生声音和乐曲的。
原先再运算机中有一个可编程时刻距离按时器8253/54(PIT),它能够依照程序提供的计数值和工作模式,产生各类形状和各类频率的计数/按时脉冲,提供给系统的各个部件利用。
明白了运算机是如何发作声音的,可是若是不明白如何编曲确实是一个大的问题了?
通过温习了书本上的乐曲程序这一末节,和通过互联网上的查找学习,使我在很短的时刻内把握了演奏乐曲的程序。
可是一周的时刻仍是超级的短暂,我也只能够把教师布置的课题大体地完成了。
在编程的进程中,我也碰到了一些比较头疼的问题,可是通过检查发觉原先都是比较细小的地址显现了问题。
通过那个发觉,使我意识到在编写代码的进程中必需时刻维持清醒的头脑,切忌细小的地址显现过失。
在接下来的两天内我一边编写程序代码,一边也在学习汇编语言的一些大体知识。
因此通过这一周的课程设计,在实际动手编程中,使我的汇编编程知识取得了进一步的提高和升华,同时也使我对汇编学习充满了浓厚的爱好。
可是时刻毕竟是有限,本来我的很多假想并无取得实践,关于那个流行音乐乐曲演奏程序,我还希望能够编写更多的歌曲曲目,同时也希望能够提高程序的可行性和友好性,提高界面的可视化成效。
参考文献
[1]沈美明,温冬婵,IBM-PC汇编语言程序设计(第2
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 音乐程序 课程设计
![提示](https://static.bdocx.com/images/bang_tan.gif)