📄 ata.s
字号:
.module ata.c
.area text(rom, con, rel)
.dbfile G:\IccPro\Mp3Ide\ata.c
.dbfunc e init_ata _init_ata fI
; j -> <dead>
; i -> <dead>
; word_read -> <dead>
; device -> R20
.even
_init_ata::
xcall push_gset2
mov R20,R16
.dbline -1
.dbline 18
; #include <iom128v.h>
; #include <string.h>
; #include <stdio.h>
; #include <macros.h>
; #include "ata.h"
; #include "generic.h"
; #include "remote.h"
;
; #define debug
; #define debugport 1
;
; //******************************************************************
; //* INITIALIZE HARDWARE FOR ATA DRIVER
; //*
; //*
; //******************************************************************
; int init_ata(unsigned char device)
; {
.dbline 21
; unsigned int word_read,i,j;
;
; ata_databus_in;
clr R2
out 0x1a,R2
.dbline 21
out 0x14,R2
.dbline 21
.dbline 22
; PORT_ATA_IO_CNTL_DDR = 0xff;
ldi R24,255
sts 97,R24
.dbline 23
; PORT_ATA_IO_CNTL = ATA_IO_HIZ;
sts 98,R24
.dbline 24
; PORT_ATA_RST_CNTL_DDR |= ATA_RESET;
lds R24,100
ori R24,2
sts 100,R24
.dbline 26
;
; ata_hard_reset();
xcall _ata_hard_reset
L2:
.dbline 28
L3:
.dbline 28
;
; while (!ready & busy);
xcall _ata_rdy
tst R16
brne L5
ldi R22,1
ldi R23,0
xjmp L6
L5:
clr R22
clr R23
L6:
xcall _ata_bsy
mov R2,R16
clr R3
movw R4,R22
and R4,R2
and R5,R3
tst R4
brne L2
tst R5
brne L2
X0:
.dbline 29
; ata_select_device(device);
mov R16,R20
xcall _ata_select_device
L7:
.dbline 30
L8:
.dbline 30
; while (!ready & busy);
xcall _ata_rdy
tst R16
brne L10
ldi R22,1
ldi R23,0
xjmp L11
L10:
clr R22
clr R23
L11:
xcall _ata_bsy
mov R2,R16
clr R3
movw R4,R22
and R4,R2
and R5,R3
tst R4
brne L7
tst R5
brne L7
X1:
.dbline 31
; ata_write_byte(ATA_IO_CMD,CMD_RECALIBRATE);
ldi R18,16
ldi R16,253
xcall _ata_write_byte
L12:
.dbline 32
L13:
.dbline 32
; while (busy);
xcall _ata_bsy
tst R16
brne L12
.dbline 33
; ata_write_byte(ATA_IO_SECTORCNT,60); // Sleep after 5 min
ldi R18,60
ldi R16,229
xcall _ata_write_byte
L15:
.dbline 34
L16:
.dbline 34
; while (busy);
xcall _ata_bsy
tst R16
brne L15
.dbline 35
; ata_write_byte(ATA_IO_CMD,CMD_STANDBY2);
ldi R18,150
ldi R16,253
xcall _ata_write_byte
L18:
.dbline 36
L19:
.dbline 36
; while (busy);
xcall _ata_bsy
tst R16
brne L18
.dbline 38
;
; return 1;
ldi R16,1
ldi R17,0
.dbline -2
L1:
xcall pop_gset2
.dbline 0 ; func end
ret
.dbsym l j 1 i
.dbsym l i 1 i
.dbsym l word_read 1 i
.dbsym r device 20 c
.dbend
.dbfunc e ata_hard_reset _ata_hard_reset fV
.even
_ata_hard_reset::
.dbline -1
.dbline 47
; }
;
; //******************************************************************
; //* PERFORM HARDWARE RESET
; //* This routine toggles ATA RESET line low for 10ms.
; //*
; //******************************************************************
; void ata_hard_reset(void)
; {
.dbline 48
; ata_databus_in;
clr R2
out 0x1a,R2
.dbline 48
out 0x14,R2
.dbline 48
.dbline 49
; PORT_ATA_RST_CNTL &= ~ATA_RESET;
lds R24,101
andi R24,253
sts 101,R24
.dbline 50
; delay_ms(10);
ldi R16,10
ldi R17,0
xcall _delay_ms
.dbline 51
; PORT_ATA_RST_CNTL |= ATA_RESET;
lds R24,101
ori R24,2
sts 101,R24
.dbline 52
; delay_ms(10);
ldi R16,10
ldi R17,0
xcall _delay_ms
.dbline -2
L21:
.dbline 0 ; func end
ret
.dbend
.dbfunc e ata_select_device _ata_select_device fV
; device -> R20
.even
_ata_select_device::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 61
; }
;
; //******************************************************************
; //* SELECT ATA DEVICE
; //* This routine defaults to Drive 0 as the target drive.
; //*
; //******************************************************************
; void ata_select_device(unsigned char device)
; {
.dbline 62
; switch (device)
clr R21
cpi R20,0
cpc R20,R21
breq L26
X2:
cpi R20,1
ldi R30,0
cpc R21,R30
breq L27
xjmp L23
X3:
.dbline 63
; {
L26:
.dbline 65
; case 0x00:
; ata_write_byte(ATA_IO_DEVICE_HEAD,ATA_DH_DEV0);
ldi R18,224
ldi R16,245
xcall _ata_write_byte
.dbline 66
; break;
xjmp L24
L27:
.dbline 68
; case 0x01:
; ata_write_byte(ATA_IO_DEVICE_HEAD,ATA_DH_DEV1);
ldi R18,240
ldi R16,245
xcall _ata_write_byte
.dbline 69
; break;
xjmp L24
L23:
.dbline 71
ldi R18,224
ldi R16,245
xcall _ata_write_byte
.dbline 72
L24:
.dbline -2
L22:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r device 20 c
.dbend
.dbfunc e ata_write_word _ata_write_word fV
; wordout -> R20,R21
; reg -> R22
.even
_ata_write_word::
xcall push_gset2
movw R20,R18
mov R22,R16
.dbline -1
.dbline 83
; default:
; ata_write_byte(ATA_IO_DEVICE_HEAD,ATA_DH_DEV0);
; break;
; }
; }
;
; //******************************************************************
; //* WRITE WORD TO ATA DEVICE
; //*
; //* Mapping : D0-PA0,D1-PA2,D2-PA4,D3-PA6,D4-PC7,D5-PC5,D7-PC3,D7-PC1
; //* D8-PC0,D9-PC2,D10-PC4,D11-PC6,D12-PA7,D13-PA5,D14-PA3,D15-PA1
; //******************************************************************
; void ata_write_word(unsigned char reg,unsigned int wordout)
; {
.dbline 84
; WDR();
wdr
.dbline 85
; PORT_ATA_IO_CNTL = reg;
sts 98,R22
.dbline 87
;
; ata_databus_out;
ldi R24,255
out 0x1a,R24
.dbline 87
out 0x14,R24
.dbline 87
.dbline 89
;
; PORT_ATA_DATA1_OUT = 0x00;
clr R2
out 0x1b,R2
.dbline 90
; PORT_ATA_DATA2_OUT = 0x00;
out 0x15,R2
.dbline 92
;
; if (wordout & 0x0001) PORT_ATA_DATA1_OUT |= 0x01;
sbrc R20,0
.dbline 92
sbi 0x1b,0
L29:
.dbline 93
; if (wordout & 0x0002) PORT_ATA_DATA1_OUT |= 0x04;
sbrc R20,1
.dbline 93
sbi 0x1b,2
L31:
.dbline 94
; if (wordout & 0x0004) PORT_ATA_DATA1_OUT |= 0x10;
sbrc R20,2
.dbline 94
sbi 0x1b,4
L33:
.dbline 95
; if (wordout & 0x0008) PORT_ATA_DATA1_OUT |= 0x40;
sbrc R20,3
.dbline 95
sbi 0x1b,6
L35:
.dbline 96
; if (wordout & 0x0010) PORT_ATA_DATA2_OUT |= 0x80;
sbrc R20,4
.dbline 96
sbi 0x15,7
L37:
.dbline 97
; if (wordout & 0x0020) PORT_ATA_DATA2_OUT |= 0x20;
sbrc R20,5
.dbline 97
sbi 0x15,5
L39:
.dbline 98
; if (wordout & 0x0040) PORT_ATA_DATA2_OUT |= 0x08;
sbrc R20,6
.dbline 98
sbi 0x15,3
L41:
.dbline 99
; if (wordout & 0x0080) PORT_ATA_DATA2_OUT |= 0x02;
sbrc R20,7
.dbline 99
sbi 0x15,1
L43:
.dbline 100
; if (wordout & 0x0100) PORT_ATA_DATA2_OUT |= 0x01;
sbrc R21,0
.dbline 100
sbi 0x15,0
L45:
.dbline 101
; if (wordout & 0x0200) PORT_ATA_DATA2_OUT |= 0x04;
sbrc R21,1
.dbline 101
sbi 0x15,2
L47:
.dbline 102
; if (wordout & 0x0400) PORT_ATA_DATA2_OUT |= 0x10;
sbrc R21,2
.dbline 102
sbi 0x15,4
L49:
.dbline 103
; if (wordout & 0x0800) PORT_ATA_DATA2_OUT |= 0x40;
sbrc R21,3
.dbline 103
sbi 0x15,6
L51:
.dbline 104
; if (wordout & 0x1000) PORT_ATA_DATA1_OUT |= 0x80;
sbrc R21,4
.dbline 104
sbi 0x1b,7
L53:
.dbline 105
; if (wordout & 0x2000) PORT_ATA_DATA1_OUT |= 0x20;
sbrc R21,5
.dbline 105
sbi 0x1b,5
L55:
.dbline 106
; if (wordout & 0x4000) PORT_ATA_DATA1_OUT |= 0x08;
sbrc R21,6
.dbline 106
sbi 0x1b,3
L57:
.dbline 107
; if (wordout & 0x8000) PORT_ATA_DATA1_OUT |= 0x02;
sbrc R21,7
.dbline 107
sbi 0x1b,1
L59:
.dbline 109
;
; ata_write_pulse;
lds R24,98
andi R24,127
sts 98,R24
.dbline 109
ldi R16,1
ldi R17,0
xcall _delay_us
.dbline 109
lds R24,98
ori R24,128
sts 98,R24
.dbline 109
.dbline 111
;
; ata_databus_in;
clr R2
out 0x1a,R2
.dbline 111
out 0x14,R2
.dbline 111
.dbline -2
L28:
xcall pop_gset2
.dbline 0 ; func end
ret
.dbsym r wordout 20 i
.dbsym r reg 22 c
.dbend
.dbfunc e ata_write_byte _ata_write_byte fV
; byteout -> R22
; reg -> R20
.even
_ata_write_byte::
xcall push_gset2
mov R22,R18
mov R20,R16
.dbline -1
.dbline 120
; }
;
; //******************************************************************
; //* WRITE BYTE TO ATA DEVICE
; //*
; //*
; //******************************************************************
; void ata_write_byte(unsigned char reg,unsigned char byteout)
; {
.dbline 121
; ata_write_word(reg,(unsigned int)byteout);
mov R18,R22
clr R19
mov R16,R20
xcall _ata_write_word
.dbline -2
L61:
xcall pop_gset2
.dbline 0 ; func end
ret
.dbsym r byteout 22 c
.dbsym r reg 20 c
.dbend
.dbfunc e ata_read_word _ata_read_word fi
; wordin -> R20,R21
; reg -> R22
.even
_ata_read_word::
xcall push_gset2
mov R22,R16
.dbline -1
.dbline 132
; }
;
; //******************************************************************
; //* READ WORD FROM ATA DEVICE
; //*
; //*
; //* Mapping : D0-PA0,D1-PA2,D2-PA4,D3-PA6,D4-PC7,D5-PC5,D7-PC3,D7-PC1
; //* D8-PC0,D9-PC2,D10-PC4,D11-PC6,D12-PA7,D13-PA5,D14-PA3,D15-PA1
; //******************************************************************
; unsigned int ata_read_word(unsigned char reg)
; {
.dbline 133
; unsigned int wordin = 0;
clr R20
clr R21
.dbline 135
;
; WDR();
wdr
.dbline 136
; PORT_ATA_IO_CNTL = reg;
sts 98,R22
.dbline 138
;
; ata_databus_in;
clr R2
out 0x1a,R2
.dbline 138
out 0x14,R2
.dbline 138
.dbline 140
;
; PORT_ATA_IO_CNTL &= ~ATA_IOR;
lds R24,98
andi R24,191
sts 98,R24
.dbline 141
; delay_us(1);
ldi R16,1
ldi R17,0
xcall _delay_us
.dbline 143
;
; if (PORT_ATA_DATA1_IN & 0x01) wordin |= 0x0001;
sbis 0x19,0
rjmp L63
.dbline 143
ori R20,1
L63:
.dbline 144
; if (PORT_ATA_DATA1_IN & 0x02) wordin |= 0x8000;
sbis 0x19,1
rjmp L65
.dbline 144
ori R21,128
L65:
.dbline 145
; if (PORT_ATA_DATA1_IN & 0x04) wordin |= 0x0002;
sbis 0x19,2
rjmp L67
.dbline 145
ori R20,2
L67:
.dbline 146
; if (PORT_ATA_DATA1_IN & 0x08) wordin |= 0x4000;
sbis 0x19,3
rjmp L69
.dbline 146
ori R21,64
L69:
.dbline 147
; if (PORT_ATA_DATA1_IN & 0x10) wordin |= 0x0004;
sbis 0x19,4
rjmp L71
.dbline 147
ori R20,4
L71:
.dbline 148
; if (PORT_ATA_DATA1_IN & 0x20) wordin |= 0x2000;
sbis 0x19,5
rjmp L73
.dbline 148
ori R21,32
L73:
.dbline 149
; if (PORT_ATA_DATA1_IN & 0x40) wordin |= 0x0008;
sbis 0x19,6
rjmp L75
.dbline 149
ori R20,8
L75:
.dbline 150
; if (PORT_ATA_DATA1_IN & 0x80) wordin |= 0x1000;
sbis 0x19,7
rjmp L77
.dbline 150
ori R21,16
L77:
.dbline 152
;
; if (PORT_ATA_DATA2_IN & 0x01) wordin |= 0x0100;
sbis 0x13,0
rjmp L79
.dbline 152
ori R21,1
L79:
.dbline 153
; if (PORT_ATA_DATA2_IN & 0x02) wordin |= 0x0080;
sbis 0x13,1
rjmp L81
.dbline 153
ori R20,128
L81:
.dbline 154
; if (PORT_ATA_DATA2_IN & 0x04) wordin |= 0x0200;
sbis 0x13,2
rjmp L83
.dbline 154
ori R21,2
L83:
.dbline 155
; if (PORT_ATA_DATA2_IN & 0x08) wordin |= 0x0040;
sbis 0x13,3
rjmp L85
.dbline 155
ori R20,64
L85:
.dbline 156
; if (PORT_ATA_DATA2_IN & 0x10) wordin |= 0x0400;
sbis 0x13,4
rjmp L87
.dbline 156
ori R21,4
L87:
.dbline 157
; if (PORT_ATA_DATA2_IN & 0x20) wordin |= 0x0020;
sbis 0x13,5
rjmp L89
.dbline 157
ori R20,32
L89:
.dbline 158
; if (PORT_ATA_DATA2_IN & 0x40) wordin |= 0x0800;
sbis 0x13,6
rjmp L91
.dbline 158
ori R21,8
L91:
.dbline 159
; if (PORT_ATA_DATA2_IN & 0x80) wordin |= 0x0010;
sbis 0x13,7
rjmp L93
.dbline 159
ori R20,16
L93:
.dbline 161
;
; PORT_ATA_IO_CNTL |= ATA_IOR;
lds R24,98
ori R24,64
sts 98,R24
.dbline 162
; return wordin;
movw R16,R20
.dbline -2
L62:
xcall pop_gset2
.dbline 0 ; func end
ret
.dbsym r wordin 20 i
.dbsym r reg 22 c
.dbend
.dbfunc e ata_read_byte _ata_read_byte fc
; reg -> R20
.even
_ata_read_byte::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 172
; }
;
; //******************************************************************
; //* READ BYTE FROM ATA DEVICE
; //*
; //*
; //*
; //******************************************************************
; unsigned char ata_read_byte(unsigned char reg)
; {
.dbline 173
; return (unsigned char)(ata_read_word(reg) & 0x00ff);
mov R16,R20
xcall _ata_read_word
andi R17,0
.dbline -2
L95:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r reg 20 c
.dbend
.dbfunc e ata_rdy _ata_rdy fc
.even
_ata_rdy::
.dbline -1
.dbline 182
; }
;
; //******************************************************************
; //* CHECK ATA READY BIT
; //* Checks READY status bit.
; //* Returns 1 if device is ready.
; //******************************************************************
; unsigned char ata_rdy(void)
; {
.dbline 183
; if (ata_read_byte(ATA_IO_STATUS) & ATA_STAT_RDY) return 1;
ldi R16,253
xcall _ata_read_byte
sbrs R16,6
rjmp L97
.dbline 183
ldi R16,1
xjmp L96
L97:
.dbline 184
; else return 0;
clr R16
.dbline -2
L96:
.dbline 0 ; func end
ret
.dbend
.dbfunc e ata_bsy _ata_bsy fc
.even
_ata_bsy::
.dbline -1
.dbline 193
; }
;
; //******************************************************************
; //* CHECK ATA BUSY BIT
; //* Checks READY status bit.
; //* Returns 1 if device is busy.
; //******************************************************************
; unsigned char ata_bsy(void)
; {
.dbline 194
; if (ata_read_byte(ATA_IO_STATUS) & ATA_STAT_BSY) return 1;
ldi R16,253
xcall _ata_read_byte
sbrs R16,7
rjmp L100
.dbline 194
ldi R16,1
xjmp L99
L100:
.dbline 195
; else return 0;
clr R16
.dbline -2
L99:
.dbline 0 ; func end
ret
.dbend
.dbfunc e ata_drq _ata_drq fc
.even
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -