Rev 9140 | Rev 9142 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 9140 | Rev 9141 | ||
---|---|---|---|
Line 320... | Line 320... | ||
320 | ahci_callbacks: |
320 | ahci_callbacks: |
321 | dd ahci_callbacks.end - ahci_callbacks |
321 | dd ahci_callbacks.end - ahci_callbacks |
322 | dd 0 ; no close function |
322 | dd 0 ; no close function |
323 | dd 0 ; no closemedia function |
323 | dd 0 ; no closemedia function |
324 | dd ahci_querymedia |
324 | dd ahci_querymedia |
325 | dd ahci_read |
325 | dd 0;ahci_read |
326 | dd 0;ahci_write |
326 | dd 0;ahci_write |
327 | dd 0 ; no flush function |
327 | dd 0 ; no flush function |
328 | dd 0 ; use default cache size |
328 | dd 0 ; use default cache size |
329 | .end: |
329 | .end: |
330 | hd_name db 'hd', 0, 0, 0 |
330 | hd_name db 'hd', 0, 0, 0 |
Line 562... | Line 562... | ||
562 | stdcall ahci_port_identify, ecx |
562 | stdcall ahci_port_identify, ecx |
Line 563... | Line 563... | ||
563 | 563 | ||
564 | cmp [ecx + PORT_DATA.drive_type], AHCI_DEV_SATA |
564 | cmp [ecx + PORT_DATA.drive_type], AHCI_DEV_SATA |
565 | jne .after_add_disk ; skip adding disk code |
565 | jne .after_add_disk ; skip adding disk code |
- | 566 | ; register disk in system: |
|
- | 567 | stdcall ahci_read_first_sector, ecx |
|
566 | ; register disk in system: |
568 | |
567 | push ecx edx |
569 | push ecx edx |
568 | mov eax, [hd_counter] |
570 | mov eax, [hd_counter] |
569 | xor edx, edx |
571 | xor edx, edx |
570 | mov ecx, 10 |
572 | mov ecx, 10 |
Line 586... | Line 588... | ||
586 | 588 | ||
587 | stdcall disk_add, ahci_callbacks, hd_name, ecx, 0 |
589 | stdcall disk_add, ahci_callbacks, hd_name, ecx, 0 |
588 | test eax, eax |
590 | test eax, eax |
589 | jz .disk_add_fail |
591 | jz .disk_add_fail |
- | 592 | stdcall disk_media_changed, eax, 1 ; system will scan for partitions on disk |
|
590 | stdcall disk_media_changed, eax, 1 ; system will scan for partitions on disk |
593 | |
Line 591... | Line 594... | ||
591 | jmp .after_add_disk |
594 | jmp .after_add_disk |
592 | 595 | ||
593 | .disk_add_fail: |
596 | .disk_add_fail: |
Line 736... | Line 739... | ||
736 | pop edx ecx |
739 | pop edx ecx |
737 | xor eax, eax |
740 | xor eax, eax |
738 | ret |
741 | ret |
739 | endp |
742 | endp |
Line 740... | Line -... | ||
740 | - | ||
741 | ; Read sectors |
743 | |
- | 744 | ;------------------------TEST------------------------------- |
|
742 | ; return value: 0 = success, otherwise = error |
745 | |
743 | proc ahci_read stdcall pdata: dword, buffer: dword, startsector: qword, numsectors_ptr:dword |
746 | proc ahci_read_first_sector stdcall pdata: dword |
744 | locals |
747 | locals |
745 | cmdslot dd ? |
748 | cmdslot dd ? |
746 | cmdheader dd ? |
749 | cmdheader dd ? |
747 | cmdtable dd ? |
750 | cmdtable dd ? |
748 | numsectors dd ? |
751 | buf_phys dd ? |
749 | buffer_pos dd ? |
752 | buf_virt dd ? |
750 | buffer_length dd ? |
753 | ;numsectors dd ? |
Line 751... | Line 754... | ||
751 | endl |
754 | endl |
752 | - | ||
753 | pushad |
755 | |
754 | 756 | pushad |
|
Line 755... | Line -... | ||
755 | mov ecx, ahci_mutex |
- | |
756 | call mutex_lock |
- | |
757 | - | ||
758 | ; xor ecx, ecx |
- | |
759 | ; mov esi, [buffer] |
- | |
760 | ; .print_data: |
- | |
761 | ; cmp ecx, 512 |
- | |
762 | ; jae .end_print_data |
- | |
763 | - | ||
764 | ; mov al, byte [esi + ecx] |
- | |
765 | ; mov byte [tmpstr], al |
- | |
766 | ; mov byte [tmpstr + 1], 0 |
- | |
767 | ; DEBUGF 1, "0x%x(%s) ", al:1, tmpstr |
- | |
768 | - | ||
769 | ; inc ecx |
- | |
770 | ; jmp .print_data |
- | |
771 | ; .end_print_data: |
- | |
772 | ; DEBUGF 1, "\n" |
- | |
773 | - | ||
774 | mov eax, [numsectors_ptr] |
- | |
775 | mov eax, [eax] |
- | |
776 | mov [numsectors], eax |
- | |
777 | 757 | mov ecx, ahci_mutex |
|
778 | DEBUGF 1, " ahci_read: buffer = 0x%x, startsector = 0x%x:%x, numsectors = %u\n", [buffer], [startsector], [startsector + 4], eax |
758 | call mutex_lock |
779 | 759 | ||
780 | mov esi, [pdata] ; esi - address of PORT_DATA struct of port |
760 | mov esi, [pdata] ; esi - address of PORT_DATA struct of port |
781 | mov edi, [esi + PORT_DATA.port] ; edi - address of HBA_PORT struct of port |
761 | mov edi, [esi + PORT_DATA.port] ; edi - address of HBA_PORT struct of port |
Line 787... | Line 767... | ||
787 | DEBUGF 1, "No free cmdslot on port %u\n", [esi + PORT_DATA.portno] |
767 | DEBUGF 1, "No free cmdslot on port %u\n", [esi + PORT_DATA.portno] |
788 | jmp .ret |
768 | jmp .ret |
Line 789... | Line 769... | ||
789 | 769 | ||
790 | .cmdslot_found: |
770 | .cmdslot_found: |
791 | mov [cmdslot], eax |
771 | mov [cmdslot], eax |
Line 792... | Line 772... | ||
792 | ; DEBUGF 1, "Found free cmdslot %u on port %u\n", [cmdslot], [esi + PORT_DATA.portno] |
772 | DEBUGF 1, "Found free cmdslot %u on port %u\n", [cmdslot], [esi + PORT_DATA.portno] |
793 | 773 | ||
794 | shl eax, BSF sizeof.HBA_CMD_HDR |
774 | shl eax, BSF sizeof.HBA_CMD_HDR |
795 | add eax, [esi + PORT_DATA.clb] |
775 | add eax, [esi + PORT_DATA.clb] |
Line 806... | Line 786... | ||
806 | mov [eax + HBA_CMD_HDR.flags1], bl |
786 | mov [eax + HBA_CMD_HDR.flags1], bl |
807 | movzx bx, [eax + HBA_CMD_HDR.flags2] |
787 | movzx bx, [eax + HBA_CMD_HDR.flags2] |
808 | btr bx, 2 ; flag C = 0 |
788 | btr bx, 2 ; flag C = 0 |
809 | mov [eax + HBA_CMD_HDR.flags2], bl |
789 | mov [eax + HBA_CMD_HDR.flags2], bl |
Line 810... | Line -... | ||
810 | - | ||
811 | mov ebx, [numsectors] |
- | |
812 | shl ebx, 9 ; *= 512 |
- | |
813 | mov [buffer_length], ebx |
- | |
814 | dec ebx |
- | |
815 | shr ebx, 12 ; /= 4096 |
- | |
816 | inc ebx |
790 | |
817 | mov [eax + HBA_CMD_HDR.prdtl], bx |
- | |
Line 818... | Line 791... | ||
818 | ;DEBUGF 1, " prdtl = %u\n", [eax + HBA_CMD_HDR.prdtl]:2 |
791 | mov [eax + HBA_CMD_HDR.prdtl], 1 |
819 | - | ||
820 | ; zero out the command table with its prdt entries |
- | |
821 | dec ebx |
- | |
822 | shl ebx, BSF sizeof.HBA_PRDT_ENTRY |
792 | |
Line 823... | Line 793... | ||
823 | add ebx, sizeof.HBA_CMD_TBL |
793 | ; zero out the command table |
824 | stdcall _memset, [cmdtable], 0, ebx |
- | |
825 | - | ||
826 | DEBUGF 1, " prdtl = %u\n", [eax + HBA_CMD_HDR.prdtl]:2 |
- | |
827 | ;jmp .ret |
- | |
828 | - | ||
829 | xor ecx, ecx |
- | |
830 | movzx edx, [eax + HBA_CMD_HDR.prdtl] |
- | |
831 | dec edx |
- | |
832 | mov eax, [buffer] |
- | |
833 | mov [buffer_pos], eax |
- | |
834 | - | ||
835 | .prdt_fill: |
- | |
836 | cmp ecx, edx |
- | |
837 | jae .prdt_fill_end |
- | |
838 | - | ||
839 | mov ebx, [buffer_pos] |
- | |
840 | and ebx, 0xFFF |
- | |
841 | call get_pg_addr ; eax = phys addr |
- | |
842 | add eax, ebx |
- | |
843 | DEBUGF 1, " PHYS = 0x%x\n", eax |
- | |
844 | mov ebx, ecx |
- | |
845 | shl ebx, BSF sizeof.HBA_PRDT_ENTRY |
- | |
846 | add ebx, [cmdtable] |
- | |
847 | add ebx, HBA_CMD_TBL.prdt_entry ; now ebx - address of ecx'th prdt_entry |
- | |
848 | - | ||
849 | mov [ebx + HBA_PRDT_ENTRY.dba], eax |
- | |
850 | mov [ebx + HBA_PRDT_ENTRY.dbau], 0 |
- | |
Line 851... | Line 794... | ||
851 | and [ebx + HBA_PRDT_ENTRY.flags], not 0x3FFFFF ; zero out lower 22 bits, they used for byte count |
794 | stdcall _memset, [cmdtable], 0, sizeof.HBA_CMD_TBL |
852 | or [ebx + HBA_PRDT_ENTRY.flags], 4096 - 1 ; reason why -1 see in spec on this field |
795 | |
Line 853... | Line 796... | ||
853 | ; or [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.flags], 1 shl 31 ; enable interrupt on completion |
796 | DEBUGF 1, " prdtl = %u\n", [eax + HBA_CMD_HDR.prdtl]:2 |
854 | 797 | ||
855 | add [buffer_pos], 4096 |
- | |
Line 856... | Line 798... | ||
856 | sub [buffer_length], 4096 |
798 | call alloc_page |
857 | 799 | mov [buf_phys], eax |
|
858 | inc ecx |
- | |
859 | jmp .prdt_fill |
- | |
860 | .prdt_fill_end: |
800 | |
861 | - | ||
862 | mov ebx, [buffer_pos] |
- | |
863 | and ebx, 0xFFF |
- | |
864 | call get_pg_addr ; eax = phys addr |
- | |
865 | add eax, ebx |
801 | stdcall map_io_mem, eax, 4096, PG_NOCACHE + PG_SWR ; map to virt memory so we can work with it |
866 | DEBUGF 1, " PHYS. = 0x%x\n", eax |
802 | mov [buf_virt], eax |
867 | mov ebx, ecx |
803 | |
868 | shl ebx, BSF sizeof.HBA_PRDT_ENTRY |
- | |
869 | add ebx, [cmdtable] |
- | |
870 | add ebx, HBA_CMD_TBL.prdt_entry ; now ebx - address of ecx'th prdt_entry |
- | |
871 | mov [ebx + HBA_PRDT_ENTRY.dba], eax |
804 | mov eax, [cmdtable] |
872 | mov [ebx + HBA_PRDT_ENTRY.dbau], 0 |
805 | mov ebx, [buf_phys] |
Line 873... | Line 806... | ||
873 | and [ebx + HBA_PRDT_ENTRY.flags], not 0x3FFFFF ; zero out lower 22 bits, they used for byte count |
806 | DEBUGF 1, "DBA = 0x%x\n", ebx |
874 | mov eax, [buffer_length] |
807 | mov [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.dba], ebx |
875 | dec eax |
808 | mov [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.dbau], 0 |
876 | DEBUGF 1, " DBC = %u\n", eax |
809 | and [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.flags], not 0x3FFFFF ; zero out lower 22 bits, they used for byte count |
877 | or [ebx + HBA_PRDT_ENTRY.flags], eax ; reason why -1 see in spec on this field |
810 | or [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.flags], 512 - 1 ; reason why -1 see in spec on this field |
Line 878... | Line 811... | ||
878 | ; or [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.flags], 1 shl 31 ; enable interrupt on completion |
811 | ; or [eax + HBA_CMD_TBL.prdt_entry + HBA_PRDT_ENTRY.flags], 1 shl 31 ; enable interrupt on completion |
Line 879... | Line 812... | ||
879 | 812 | ||
880 | mov eax, [cmdtable] |
813 | mov eax, [cmdtable] |
881 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.fis_type], FIS_TYPE_REG_H2D |
- | |
882 | movzx ebx, byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.flags] |
814 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.fis_type], FIS_TYPE_REG_H2D |
883 | bts ebx, bit_AHCI_H2D_FLAG_CMD ; Set Command bit in H2D FIS. |
- | |
884 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.flags], bl |
815 | movzx ebx, byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.flags] |
885 | 816 | bts ebx, bit_AHCI_H2D_FLAG_CMD ; Set Command bit in H2D FIS. |
|
886 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.command], ATA_CMD_READ_DMA_EX |
- | |
887 | 817 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.flags], bl |
|
888 | mov ebx, dword [startsector] |
- | |
889 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba0], bl |
818 | |
890 | shr ebx, 8 |
- | |
891 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba1], bl |
819 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.command], ATA_CMD_READ_DMA_EX |
Line 892... | Line 820... | ||
892 | shr ebx, 8 |
820 | |
893 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba2], bl |
821 | mov ebx, 0 ; start sector is 0 |
- | 822 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba0], bl |
|
- | 823 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba1], bl |
|
894 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.device], 1 shl 6 ; LBA mode |
824 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba2], bl |
895 | shr ebx, 8 |
825 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.device], 1 shl 6 ; LBA mode |
Line 896... | Line 826... | ||
896 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba3], bl |
826 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba3], bl |
897 | mov ebx, dword [startsector + 4] |
827 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba4], bl |
Line 898... | Line 828... | ||
898 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba4], bl |
828 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba5], bl |
899 | shr ebx, 8 |
829 | |
Line -... | Line 830... | ||
- | 830 | ; num sectors to read = 1 |
|
- | 831 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.countl], 1 |
|
900 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.lba5], bl |
832 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.counth], 0 |
901 | 833 | ||
Line 902... | Line 834... | ||
902 | mov ebx, [numsectors] |
834 | ;mov eax, [cmdheader] |
Line 903... | Line 835... | ||
903 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.countl], bl |
835 | ;DEBUGF 1, "PRDBC = %u\n", [eax + HBA_CMD_HDR.prdbc] |
Line -... | Line 836... | ||
- | 836 | ||
- | 837 | ; Wait on previous command to complete, before issuing new command. |
|
- | 838 | stdcall ahci_port_wait, edi, AHCI_PORT_TIMEOUT |
|
904 | shr ebx, 8 |
839 | |
905 | mov byte [eax + HBA_CMD_TBL.cfis + FIS_REG_H2D.counth], bl |
840 | mov eax, [cmdslot] |
906 | 841 | bts [edi + HBA_PORT.command_issue], eax ; Issue the command |
|
907 | ; Wait on previous command to complete, before issuing new command. |
842 | |
908 | stdcall ahci_port_wait, edi, AHCI_PORT_TIMEOUT |
843 | ; mov ebx, 20 |
Line 909... | Line 844... | ||
909 | 844 | ; call delay_hs |
|
910 | mov eax, [cmdslot] |
845 | ; Wait for command completion |
911 | bts [edi + HBA_PORT.command_issue], eax ; Issue the command |
846 | stdcall ahci_port_cmd_wait, edi, eax;, AHCI_PORT_CMD_TIMEOUT |
912 | 847 | ||
Line 913... | Line 848... | ||
913 | ; Wait for command completion |
848 | DEBUGF 1, "sata_error register = 0x%x\n", [edi + HBA_PORT.sata_error] |
914 | stdcall ahci_port_cmd_wait, edi, eax;, AHCI_PORT_CMD_TIMEOUT |
849 | |
915 | 850 | DEBUGF 1, "reading completed\n" |
|
916 | DEBUGF 1, "sata_error register = 0x%x\n", [edi + HBA_PORT.sata_error] |
851 | |
Line 939... | Line 874... | ||
939 | 874 | ||
940 | popad |
875 | popad |
941 | xor eax, eax |
876 | xor eax, eax |
942 | ret |
877 | ret |
943 | endp |
878 | endp |
- | 879 | tmpstr2 rb 16 |
|
Line 944... | Line 880... | ||
944 | tmpstr rb 16 |
880 | ;---------------------------------------------------------- |
945 | 881 | ||
946 | ; Start command engine |
882 | ; Start command engine |
947 | ; in: eax - address of HBA_PORT structure |
883 | ; in: eax - address of HBA_PORT structure |