⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sd.s

📁 mp3源码,是自己写的,关于vs1001与CD卡的读取歌曲,和播放.
💻 S
字号:
	.module sd.c
	.area text(rom, con, rel)
	.dbfile F:\mine\mp3\MP3\sd.c
	.dbfunc e sd_wait_nobusy _sd_wait_nobusy fV
	.even
_sd_wait_nobusy::
	.dbline -1
	.dbline 14
; #include<all.h>
; #include<vs1001k.h>
; #include<sd.h>
; #define SD_INIT_TRY   50
; #define SD_IDLE_WAIT_MAX  100 //等待进入IDLE次数
; #define SD_CMD_TIMEOUT    100 //读CMD次数
; #define TIMEOUT_WRITE  10000   // 8M/8
; #define TIMEOUT_READ   400000  // 8M/20
; 
; uchar mp3_data[DATA_LENGTH];
; uchar response[5];
; 
; void sd_wait_nobusy(void)
; {
L2:
	.dbline 15
L3:
	.dbline 15
;   while(read_single()!=0xff);
	xcall _read_single
	cpi R16,255
	brne L2
	.dbline 16
;   select_vs;
	sbi 0x18,3
	.dbline -2
	.dbline 17
; }
L1:
	.dbline 0 ; func end
	ret
	.dbend
	.dbfunc e sd_delay _sd_delay fV
;              n -> R20,R21
;            dat -> R22
	.even
_sd_delay::
	xcall push_gset2
	mov R22,R16
	.dbline -1
	.dbline 19
; void sd_delay(uchar dat)
; { uint n;
	.dbline 20
;   for(n=0;n<dat;n++)
	clr R20
	clr R21
	xjmp L9
L6:
	.dbline 21
	ldi R16,255
	xcall _write_single
L7:
	.dbline 20
	subi R20,255  ; offset = 1
	sbci R21,255
L9:
	.dbline 20
	mov R2,R22
	clr R3
	cp R20,R2
	cpc R21,R3
	brlo L6
	.dbline -2
	.dbline 22
;    write_single(0xff);
; }   
L5:
	xcall pop_gset2
	.dbline 0 ; func end
	ret
	.dbsym r n 20 i
	.dbsym r dat 22 c
	.dbend
	.dbfunc e sd_write_command _sd_write_command fc
; response_length -> R14
;            dat -> R22
;              n -> R20,R21
;       response -> R10,R11
;            arg -> y+10
;  response_type -> R12
;            cmd -> R20
	.even
_sd_write_command::
	xcall push_gset5
	mov R12,R18
	mov R20,R16
	ldd R10,y+14
	ldd R11,y+15
	.dbline -1
	.dbline 25
; /****************sd 发命令**********************/
; uchar sd_write_command(uchar cmd,uchar response_type,ulong arg,uchar *response)
; { uchar response_length,dat;
	.dbline 27
;   int n;
;   select_sd;//选择SD
	cbi 0x18,3
	.dbline 28
;   write_single(cmd|0x40);
	mov R16,R20
	ori R16,64
	xcall _write_single
	.dbline 29
;   write_single(arg>>24);
	ldi R24,24
	ldi R25,0
	movw R30,R28
	ldd R2,z+10
	ldd R3,z+11
	ldd R4,z+12
	ldd R5,z+13
	st -y,R24
	movw R16,R2
	movw R18,R4
	xcall lsr32
	xcall _write_single
	.dbline 30
;   write_single(arg>>16);
	movw R30,R28
	ldd R2,z+10
	ldd R3,z+11
	ldd R4,z+12
	ldd R5,z+13
	movw R2,R4
	clr R4
	clr R5
	mov R16,R2
	xcall _write_single
	.dbline 31
;   write_single(arg>>8);
	ldi R24,8
	ldi R25,0
	movw R30,R28
	ldd R2,z+10
	ldd R3,z+11
	ldd R4,z+12
	ldd R5,z+13
	st -y,R24
	movw R16,R2
	movw R18,R4
	xcall lsr32
	xcall _write_single
	.dbline 32
;   write_single(arg);
	movw R30,R28
	ldd R16,z+10
	xcall _write_single
	.dbline 33
;   write_single(0x95);//CRC 对于CMD0有效,SPI忽略
	ldi R16,149
	xcall _write_single
	.dbline 34
;   response_length=0;
	clr R14
	.dbline 35
;   switch(response_type)
	mov R20,R12
	clr R21
	cpi R20,1
	ldi R30,0
	cpc R21,R30
	breq L14
	cpi R20,2
	ldi R30,0
	cpc R21,R30
	breq L14
	cpi R20,3
	ldi R30,0
	cpc R21,R30
	breq L15
	cpi R20,4
	ldi R30,0
	cpc R21,R30
	breq L16
	xjmp L12
X0:
	.dbline 36
;   { case R1: 
L14:
	.dbline 37
;     case R1B:response_length=1;break;
	clr R14
	inc R14
	.dbline 37
	xjmp L12
L15:
	.dbline 38
; 	case R2: response_length=2;break;
	ldi R24,2
	mov R14,R24
	.dbline 38
	xjmp L12
L16:
	.dbline 39
; 	case R3: response_length=5;break;
	ldi R24,5
	mov R14,R24
	.dbline 39
	.dbline 40
; 	default: break;
L12:
	.dbline 42
;   }	
;   n=0;
	clr R20
	clr R21
L17:
	.dbline 44
;   do                              //等待响应
;   { dat=read_single();
	.dbline 44
	xcall _read_single
	mov R22,R16
	.dbline 45
;     n++;
	subi R20,255  ; offset = 1
	sbci R21,255
	.dbline 46
;   }
L18:
	.dbline 47
;   while(((dat&0x80)!=0)&&(n<SD_CMD_TIMEOUT));
	sbrs R22,7
	rjmp L20
	cpi R20,100
	ldi R30,0
	cpc R21,R30
	brlt L17
L20:
	.dbline 48
;   if(n>=SD_CMD_TIMEOUT)	//超时
	cpi R20,100
	ldi R30,0
	cpc R21,R30
	brlt L21
	.dbline 49
;   { select_vs;
	.dbline 49
	sbi 0x18,3
	.dbline 50
;     return 0;
	clr R16
	xjmp L10
L21:
	.dbline 52
;   }	
;   for(n=response_length-1;n>=0;n--)//取数据
	mov R20,R14
	clr R21
	subi R20,1
	sbci R21,0
	xjmp L26
L23:
	.dbline 53
	.dbline 53
	movw R30,R20
	add R30,R10
	adc R31,R11
	std z+0,R22
	.dbline 54
	xcall _read_single
	mov R22,R16
	.dbline 55
L24:
	.dbline 52
	subi R20,1
	sbci R21,0
L26:
	.dbline 52
	cpi R20,0
	ldi R30,0
	cpc R21,R30
	brge L23
	.dbline 56
;   { response[n]=dat;
;     dat=read_single();
;   }	
;   if(response_type==R1B)//忙等待结束
	mov R24,R12
	cpi R24,2
	brne L27
	.dbline 57
;   { do
L29:
	.dbline 58
;     { dat=read_single();}
	.dbline 58
	xcall _read_single
	mov R22,R16
	.dbline 58
L30:
	.dbline 59
; 	while(dat!=0xff);
	cpi R22,255
	brne L29
	.dbline 60
; 	write_single(0xff);
	ldi R16,255
	xcall _write_single
	.dbline 61
;   }
L27:
	.dbline 62
;   select_vs;//释放SD
	sbi 0x18,3
	.dbline 63
;   return 1;	  
	ldi R16,1
	.dbline -2
L10:
	xcall pop_gset5
	.dbline 0 ; func end
	ret
	.dbsym r response_length 14 c
	.dbsym r dat 22 c
	.dbsym r n 20 I
	.dbsym r response 10 pc
	.dbsym l arg 10 l
	.dbsym r response_type 12 c
	.dbsym r cmd 20 c
	.dbend
	.dbfunc e read_block _read_block fc
;            dat -> R12
;              n -> y+6
;       mp3_data -> R10,R11
;         length -> y+22
;       blockadd -> y+18
	.even
_read_block::
	xcall push_arg4
	xcall push_gset4
	sbiw R28,10
	ldd R10,y+26
	ldd R11,y+27
	.dbline -1
	.dbline 67
; }
; 
; uchar read_block(ulong blockadd,ulong length,uchar *mp3_data) 
; { uchar dat;
	.dbline 69
;   ulong n;  
;   sd_wait_nobusy();
	xcall _sd_wait_nobusy
	.dbline 70
;   if(sd_write_command(CMD16,CMD16_R,length,response)==0)//设置读取数据的长度
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	movw R30,R28
	ldd R2,z+22
	ldd R3,z+23
	ldd R4,z+24
	ldd R5,z+25
	std y+0,R2
	std y+1,R3
	std y+2,R4
	std y+3,R5
	ldi R18,1
	ldi R16,16
	xcall _sd_write_command
	tst R16
	brne L33
	.dbline 71
;     return 0; 
	clr R16
	xjmp L32
L33:
	.dbline 73
;   //blockadd<<=9;//增加512B
;   if(sd_write_command(CMD17,CMD17_R,blockadd,response)==0)
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	movw R30,R28
	ldd R2,z+18
	ldd R3,z+19
	ldd R4,z+20
	ldd R5,z+21
	std y+0,R2
	std y+1,R3
	std y+2,R4
	std y+3,R5
	ldi R18,1
	ldi R16,17
	xcall _sd_write_command
	tst R16
	brne L35
	.dbline 74
;     return 0;
	clr R16
	xjmp L32
L35:
	.dbline 75
;   if(response[0]!=0)//出现error
	lds R2,_response
	tst R2
	breq L37
	.dbline 76
;     return 0;
	clr R16
	xjmp L32
L37:
	.dbline 77
;   select_sd;
	cbi 0x18,3
	.dbline 78
;   n=0;
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	movw R30,R28
	std z+6,R20
	std z+7,R21
	std z+8,R22
	std z+9,R23
L39:
	.dbline 80
;   do
;   { dat=read_single();
	.dbline 80
	xcall _read_single
	mov R12,R16
	.dbline 81
;     n++;
	ldi R20,1
	ldi R21,0
	ldi R22,0
	ldi R23,0
	movw R30,R28
	ldd R2,z+6
	ldd R3,z+7
	ldd R4,z+8
	ldd R5,z+9
	add R2,R20
	adc R3,R21
	adc R4,R22
	adc R5,R23
	movw R30,R28
	std z+6,R2
	std z+7,R3
	std z+8,R4
	std z+9,R5
	.dbline 82
;   }
L40:
	.dbline 83
;   while((dat==0xff)&&(n<TIMEOUT_READ));//读出数据的头0xfe	
	mov R24,R12
	cpi R24,255
	brne L42
	ldi R20,128
	ldi R21,26
	ldi R22,6
	ldi R23,0
	movw R30,R28
	ldd R2,z+6
	ldd R3,z+7
	ldd R4,z+8
	ldd R5,z+9
	cp R2,R20
	cpc R3,R21
	cpc R4,R22
	cpc R5,R23
	brlo L39
L42:
	.dbline 84
;   for(n=0;n<length;n++)
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	movw R30,R28
	std z+6,R20
	std z+7,R21
	std z+8,R22
	std z+9,R23
	xjmp L46
L43:
	.dbline 85
	.dbline 85
	xcall _read_single
	movw R30,R28
	push R26
	push R27
	ldd R26,z+6
	ldd R27,z+7
	movw R30,R26
	pop R27
	pop R26
	add R30,R10
	adc R31,R11
	std z+0,R16
	.dbline 85
L44:
	.dbline 84
	ldi R20,1
	ldi R21,0
	ldi R22,0
	ldi R23,0
	movw R30,R28
	ldd R2,z+6
	ldd R3,z+7
	ldd R4,z+8
	ldd R5,z+9
	add R2,R20
	adc R3,R21
	adc R4,R22
	adc R5,R23
	movw R30,R28
	std z+6,R2
	std z+7,R3
	std z+8,R4
	std z+9,R5
L46:
	.dbline 84
	movw R30,R28
	ldd R2,z+22
	ldd R3,z+23
	ldd R4,z+24
	ldd R5,z+25
	movw R30,R28
	ldd R6,z+6
	ldd R7,z+7
	ldd R8,z+8
	ldd R9,z+9
	cp R6,R2
	cpc R7,R3
	cpc R8,R4
	cpc R9,R5
	brsh X1
	xjmp L43
X1:
	.dbline 86
;   { mp3_data[n]=read_single();}
;   read_single();//CRC 16bit
	xcall _read_single
	.dbline 87
;   read_single();
	xcall _read_single
	.dbline 88
;   select_vs;
	sbi 0x18,3
	.dbline 89
;   return 1;
	ldi R16,1
	.dbline -2
L32:
	adiw R28,10
	xcall pop_gset4
	adiw R28,4
	.dbline 0 ; func end
	ret
	.dbsym r dat 12 c
	.dbsym l n 6 l
	.dbsym r mp3_data 10 pc
	.dbsym l length 22 l
	.dbsym l blockadd 18 l
	.dbend
	.dbfunc e sd_read_block _sd_read_block fV
;       mp3_data -> R20,R21
;         length -> y+12
;       blockadd -> y+8
	.even
_sd_read_block::
	xcall push_arg4
	xcall push_gset1
	sbiw R28,6
	ldd R20,y+16
	ldd R21,y+17
	.dbline -1
	.dbline 93
L48:
	.dbline 93
L49:
	.dbline 93
; }
; 
; void sd_read_block(ulong blockadd,ulong length,uchar *mp3_data)//读SD数据
; { while(read_block(blockadd,length,mp3_data)==0);}
	std y+5,R21
	std y+4,R20
	movw R30,R28
	ldd R2,z+12
	ldd R3,z+13
	ldd R4,z+14
	ldd R5,z+15
	std y+0,R2
	std y+1,R3
	std y+2,R4
	std y+3,R5
	movw R30,R28
	ldd R16,z+8
	ldd R17,z+9
	ldd R18,z+10
	ldd R19,z+11
	xcall _read_block
	tst R16
	breq L48
	.dbline -2
	.dbline 93
L47:
	adiw R28,6
	xcall pop_gset1
	adiw R28,4
	.dbline 0 ; func end
	ret
	.dbsym r mp3_data 20 pc
	.dbsym l length 12 l
	.dbsym l blockadd 8 l
	.dbend
	.dbfunc e do_sd_init _do_sd_init fc
;              n -> R10
	.even
_do_sd_init::
	xcall push_gset3
	sbiw R28,6
	.dbline -1
	.dbline 96
; 
; uchar do_sd_init(void)//sd初始化
; { uchar n;
	.dbline 97
;   delay(200);
	ldi R16,200
	ldi R17,0
	xcall _delay
	.dbline 98
;   select_sd;
	cbi 0x18,3
	.dbline 99
;   sd_delay(100);
	ldi R16,100
	xcall _sd_delay
	.dbline 100
;   select_vs;
	sbi 0x18,3
	.dbline 101
;   sd_delay(2);
	ldi R16,2
	xcall _sd_delay
	.dbline 102
;   if(sd_write_command(CMD0,CMD0_R,0,response)==0)
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	std y+0,R20
	std y+1,R21
	std y+2,R22
	std y+3,R23
	ldi R18,1
	clr R16
	xcall _sd_write_command
	tst R16
	brne L52
	.dbline 103
;     return 0;
	clr R16
	xjmp L51
L52:
	.dbline 104
;   n=0;
	clr R10
L54:
	.dbline 106
;   do
;   { n++;
	.dbline 106
	inc R10
	.dbline 107
;     if(sd_write_command(CMD55,CMD55_R,0,response)==1)//进入special command
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	std y+0,R20
	std y+1,R21
	std y+2,R22
	std y+3,R23
	ldi R18,1
	ldi R16,55
	xcall _sd_write_command
	cpi R16,1
	brne L57
	.dbline 108
; 	 { /*getin OCR*/
	.dbline 109
; 	  sd_write_command(ACMD41,ACMD41_R,0,response);
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	std y+0,R20
	std y+1,R21
	std y+2,R22
	std y+3,R23
	ldi R18,1
	ldi R16,41
	xcall _sd_write_command
	.dbline 110
; 	 }
	xjmp L58
L57:
	.dbline 112
; 	else
; 	  n=SD_IDLE_WAIT_MAX;  //no response
	ldi R24,100
	mov R10,R24
L58:
	.dbline 113
; 	delay(500);//经调试需要加延迟
	ldi R16,500
	ldi R17,1
	xcall _delay
	.dbline 114
;   }
L55:
	.dbline 115
;   while(((response[0]&MSK_IDLE)==MSK_IDLE)&&(n<SD_IDLE_WAIT_MAX));
	lds R24,_response
	andi R24,1
	cpi R24,1
	brne L59
	mov R24,R10
	cpi R24,100
	brlo L54
L59:
	.dbline 116
;   if(n>=SD_IDLE_WAIT_MAX)
	mov R24,R10
	cpi R24,100
	brlo L60
	.dbline 117
;     return 0;
	clr R16
	xjmp L51
L60:
	.dbline 118
;   if(sd_write_command(CMD58,CMD58_R,0,response)==0)//读取OCR
	ldi R24,<_response
	ldi R25,>_response
	std y+5,R25
	std y+4,R24
	ldi R20,0
	ldi R21,0
	ldi R22,0
	ldi R23,0
	std y+0,R20
	std y+1,R21
	std y+2,R22
	std y+3,R23
	ldi R18,4
	ldi R16,58
	xcall _sd_write_command
	tst R16
	brne L62
	.dbline 119
;     return 0;
	clr R16
	xjmp L51
L62:
	.dbline 120
;   if((response[2]&MSK_OCR_33)!=MSK_OCR_33)//电压最低为3.3V
	lds R24,_response+2
	andi R24,192
	cpi R24,192
	breq L64
	.dbline 121
;     return 0;
	clr R16
	xjmp L51
L64:
	.dbline 126
;   /*set block length			
;   if(sd_write_command(CMD16,CMD16_R,DATA_LENGTH,response)==0)
;     return 0;
;   */
;   return 1;    
	ldi R16,1
	.dbline -2
L51:
	adiw R28,6
	xcall pop_gset3
	.dbline 0 ; func end
	ret
	.dbsym r n 10 c
	.dbend
	.dbfunc e sd_init _sd_init fc
;              j -> R20
;              n -> R22
	.even
_sd_init::
	xcall push_gset2
	.dbline -1
	.dbline 130
; }
; 
; uchar sd_init(void)
; { uchar n,j;
	.dbline 131
;   j=0;
	clr R20
	.dbline 132
;   for(n=0;(n<SD_INIT_TRY)&&(j!=1);n++)
	clr R22
	xjmp L71
L68:
	.dbline 133
	xcall _do_sd_init
	mov R20,R16
L69:
	.dbline 132
	inc R22
L71:
	.dbline 132
	cpi R22,50
	brsh L72
	cpi R20,1
	brne L68
L72:
	.dbline 134
;     j=do_sd_init();
;   if(n>=SD_INIT_TRY)//超次数
	cpi R22,50
	brlo L73
	.dbline 135
;     return 0;	
	clr R16
	xjmp L67
L73:
	.dbline 136
;   return 1;
	ldi R16,1
	.dbline -2
L67:
	xcall pop_gset2
	.dbline 0 ; func end
	ret
	.dbsym r j 20 c
	.dbsym r n 22 c
	.dbend
	.area bss(ram, con, rel)
	.dbfile F:\mine\mp3\MP3\sd.c
_response::
	.blkb 5
	.dbsym e response _response A[5:5]c
_mp3_data::
	.blkb 512
	.dbsym e mp3_data _mp3_data A[512:512]c

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -