Чтение секторов SATA HDD

Тема в разделе "WASM.ASSEMBLER", создана пользователем dess, 14 окт 2008.

  1. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    Memphis
    Идика и почитай ты спецификацию.
    Иш ты чего захотел, чтобы тебе ошибке о завершении команды выдовались до ее зовершения.
     
  2. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    Pavia
    Иди и ты и посмотри коды БИОСов.
     
  3. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    Memphis
    Согласен по поводу проверок на ошибки, мой код действительно сильно упрощен (было отсечено много "лишнего" дабы получить быстрый результат). Код заработал, но не учитывает нюансы оборудования. Постепенно, по мере изучения данной темы, буду "интеллектуализировать" его. УДМА конечно-же интересует, но я думал оставить его на потом, что бы не усложнять текущую задачу. Мне кажется, что ПИО для недоразвитой системы - наиболее простое решение. Но я могу пересмотреть свою точку зрения :) По поводу адреса Bus Master контроллера: он находится в конфигурационном пространстве PCI ?
     
  4. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    dess
    Согласен по поводу проверок на ошибки, мой код действительно сильно упрощен - хотелось бы уточнить, чего Вы хотите - чисто теоретическую программку или реально действующий код ? Во втором случае - придется больше анализировать, ведь код должен работать с САТА/ПАТА хардами (старыми/новыми/ЛБА48/ЛБА28). Повторю еще раз - нельзя проверять только биты #80 & #8 !!! Вот живой пример - возьмите ПАТА хард ЛБА48, введите в его регистры чтение одного сектора для ЛБА=0FFFFFFFFFFFF в режиме ЛБА, дайте ему команду 24/29, дождитесь его готовности и посмотрите код статуса - будет код 59 (команда исполнилась с ошибкой - и это естественно - номер ЛБА жутко большой). Но в коде 59 установлен бит #8 (требование трансфера, да еще и ЛЕД харда сияет). Вы не имеете право проводить трансфер, хоть бит и установлен (да и трансфер какого сектора Вы произведете ?) - вначале надо проверить бит #1 - команда завершилась успешно ?

    По поводу адреса Bus Master контроллера: он находится в конфигурационном пространстве PCI ? - совершенно верно. Если у Вас стандартный ИДЕ от Интела, его адрес, скорее всего, будет 0F000h. Уточните. Я просто подстраиваюсь под Вашу конфигурацию, чтобы последующие фрагменты кода можно было испытать вживую.

    Не глядите, что мы с Pavia столкнулись лбами. Для Вас, как лицу незаинтересованному, думаю, истина превыше всего (проверяйте его и мой код, анализируйте).
     
  5. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    Memphis
    На момент создания данной темы мне был необходим наилегчайший код чтения данных с HDD, так-как целью было подгрузить бинарник во время работы ассемблерного кода запущенного из под MS-DOS и выполняющегося в защищенном режиме процессора. В принципе цель достугнута (на моём оборудовании). Но как Вы правильно заметили про САТА/ПАТА/И_ВСЯКИЕ_ТАМ_АТА, для корректной работы функции необходимо нечто большее, чем у меня на данный момент. Беда только в отсутствии должной литературы по различным маркам железа. Поэтому я особо и не рвался. Но раз уж тема продолжает развиваться, то глупо было бы отнекиваться. Я готов проверять всё, что нужно проверять, чтобы всё корректно крутилось и не заедало. Начну с проверки #1-го бита, потом #80, и #8.
    По поводу всё того-же БасМастерса: мне казалось я улавливаю, что это такое, но сейчас не уверен. У меня Интеловский контроллер с одним ИДЕ и тремя САТА/ПАТА (на выбор в БИОСЕ). Я сканирую конфигурационное пространство ПИСИАЙ по всем шинам, устройствам, функциям и нахожу классы различного оборудования. Если речь идет об устройствах класса 01 (устройства массовой памяти), то известны порты контроллера: B800, B400, B000, А800, A400. Но подозреваю, что это не то, что Вас интересует... Если мои подозрения верны, то где мне искать адрес этого Мастера Шины ???
     
  6. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    bus:00, dev:00, fn:0, class:060000, irq:00, 00000000 00000000 00000000 00000000 00000000 00000000
    bus:00, dev:02, fn:0, class:030000, irq:0B, DFE00000 00008801 E0000008 DFE80000 00000000 00000000
    bus:00, dev:1B, fn:0, class:040300, irq:05, DFEF8004 00000000 00000000 00000000 00000000 00000000
    bus:00, dev:1C, fn:0, class:060400, irq:0B, 00000000 00000000 00030300 2000E0E0 0000FFF0 0001FFF1
    bus:00, dev:1C, fn:1, class:060400, irq:0A, 00000000 00000000 00020200 2000D0D0 DFF0DFF0 0001FFF1
    bus:00, dev:1D, fn:0, class:0C0300, irq:03, 00000000 00000000 00000000 00000000 00009001 00000000
    bus:00, dev:1D, fn:1, class:0C0300, irq:0A, 00000000 00000000 00000000 00000000 00009401 00000000
    bus:00, dev:1D, fn:2, class:0C0300, irq:06, 00000000 00000000 00000000 00000000 00009801 00000000
    bus:00, dev:1D, fn:3, class:0C0300, irq:05, 00000000 00000000 00000000 00000000 0000A001 00000000
    bus:00, dev:1D, fn:7, class:0C0320, irq:03, DFEFFC00 00000000 00000000 00000000 00000000 00000000
    bus:00, dev:1E, fn:0, class:060401, irq:FF, 00000000 00000000 20010100 2280C0C0 0000FFF0 0001FFF1
    bus:00, dev:1F, fn:0, class:060100, irq:00, 00000000 00000000 00000000 00000000 00000000 00000000
    bus:00, dev:1F, fn:1, class:01018A, irq:00, 00000001 00000001 00000001 00000001 0000FFA1 00000000
    bus:00, dev:1F, fn:2, class:01018F, irq:0B, 0000B801 0000B401 0000B001 0000A801 0000A401 00000000
    bus:00, dev:1F, fn:3, class:0C0500, irq:0A, 00000000 00000000 00000000 00000000 00000401 00000000
    bus:02, dev:00, fn:0, class:020000, irq:0A, DFFC0004 00000000 00000000 00000000 00000000 00000000
     
  7. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    bus:00, dev:1F, fn:1, class:01018A, irq:00, 00000001 00000001 00000001 00000001 0000FFA1 00000000 это Легаси IDE его порты 1f0h 3f4h 170h 374h и его Bus Master Base Address 0FFA0h - порт
    bus:00, dev:1F, fn:2, class:01018F, irq:0B, 0000B801 0000B401 0000B001 0000A801 0000A401 00000000 это Нативе IDE его порты 0B800h 0B400h 0B000h 0A800h и его Bus Master Base Address 0A400h - порт
     
  8. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    Pavia
    1f0h 3f4h 170h 374h - немного Вас подправлю. Правильно так - 3F6h & 376h.

    dess
    Начну с проверки #1-го бита, потом #80, и #8. - нет. Сначала #80, затем #1 (обязательно по адресам 1F7h & 177h, но не 3F6h & 376 - именно надо для САТА !!!). Если это успешно - только тогда #8 - это гарантирует правильность трансфера для САТА/ПАТА хардов. И еще по ПИО уточните - читать/писать будете посекторно (АТА команды 20/24 & 30/34) или мультиблоком (АТА команды C4/29 & C5/39) ?

    Я сканирую конфигурационное пространство ПИСИАЙ по всем шинам, устройствам, функциям и нахожу классы - сложно и некрасиво. Ваши контроллеры в формате B/D/F & VendorId/DeviceId очень легко увидеть во время POSTа, когда на экран выдается PCI-таблица IRQ-номеров для контроллеров. Так легче детерминировать Ваши контроллеры. Есть второй вариант - в Диспетчере устройств раскроем IDE ATA/ATAPI контроллеры, щелкнем по самому контроллеру, на вкладке "Общие" - видим размещение его в формате B/D/F, на вкладке "Ресурсы" - адреса BMастера (покажите их мне). Затем щелкаем по каналам контроллера и списываем адреса I/O для вкладки "Ресурсы". Это надо проделать для обеих Ваших контроллеров.
     
  9. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    Memphis
    Как раз таки правельно 3f4h.
    3f4h -это база, просто используется только один регистр с индексом 2 (3f4h+2h=3f6h).
    0B400h - это тоже база, а регистр будет 0B402h .
     
  10. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    Pavia
    Вобще-то, 3F4h - регистр статуса флопоконтроллера. Но это не важно. Я указал реальные адреса, с которыми можно работать. Может это и база, спорить не хочу.
     
  11. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    Memphis
    Еще и не такии чудеса есть к примеру порты PCI 0CF8h - 0CFBh задают адреса устройства.
    А intel еще впихнула перезагрузку 0CF9h(Можно сказать PCI reset). Собственно по этой причине у них номера устройств начинаются с 30h =).
    У других вендоров подругому.

    Сразу предвижу вопрос. Насчет портов, можно писать в 4 8-битных порта разом, тем самым объединяя их в 32 битный порт.
    -мануэл на процессор intel.
    Разве что можно вспомнить порт жеских данных где все-таки из одного порта читается 2 байта. Остальные полностью соответсвуют описанному выше.
     
  12. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    Pavia
    можно писать в 4 8-битных порта разом, тем самым объединяя их в 32 битный порт - не для всех, а только для оговоренных особо. К примеру, инициализация таймера (к примеру, 42-й порт - надо дважды вывести по байту. Сразу записать слово не прокатит.

    порт жеских данных где все-таки из одного порта читается 2 байта - не согласен. Харды необычайно гибки. И хотя 40/80 пиновый ПАТА шлейф физически может 16 бит, хард прекрасно исполняет команды по трансферу ПИО типа rep insd/rep outsd (по 2-м фронтам за такт). Забавно, но он может также прокачивать по 16 проводам всего один байт. В моей жутко старой матерной БИОС есть фишка, когда во время ПОСТа тестируется ПАТА шлейф харда. Т.е. если в шлейфе повреждены жилы старшего байта, можно заставить хард производить трансфер байтами по исправным 8-ми младшим. Даже есть такая Set Features. Ну а про САТА совсем интересно говорить - может по кабельку также 8/16/32 бита за такт.
     
  13. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    Memphis
    Ты опять не понял. В таймере один порт. А тут про порты находящиеся рядом.
    Насчет 8 для PATA у меня не работало. А вот 32 работало это давно известно как PIO32.
     
  14. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    Pavia
    В таймере один порт - а мне известны такие адреса: 40/41/42/43 - со всеми приходилось работать. Впрочем, к теме это не относится, вернемся к этому позже, я подберу более удачные примеры.
     
  15. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    IDE ATA/ATAPI контроллеры:
    -------------------------------
    Intel(R) 82801G (ICH7 Family) Ultra ATA Storage Controllers - 27DF
    Размещение: PCI шина 0, устройство 31, функция 1
    Диапазон ввода/вывода (I/O): FFA0 - FFAF

    Intel(R) 82801GB/GR/GH (ICH7 Family) Serial ATA Storage Controller - 27C0
    Размещение: PCI шина 0, устройство 31, функция 2
    Диапазон ввода/вывода (I/O): B800 - B807
    Диапазон ввода/вывода (I/O): B400 - B403
    Диапазон ввода/вывода (I/O): B000 - B007
    Диапазон ввода/вывода (I/O): A800 - A803
    Диапазон ввода/вывода (I/O): A400 - A40F
    IRQ: 23

    Вторичный канал IDE
    Диапазон ввода/вывода (I/O): 0170 - 0177
    Диапазон ввода/вывода (I/O): 0376 - 0376
    IRQ: 15

    Первичный канал IDE
    Диапазон ввода/вывода (I/O): 01F0 - 01F7
    Диапазон ввода/вывода (I/O): 03F6 - 03F6
    IRQ: 14

    По поводу PIO: поскольку хард содержит кластерную структуру FAT32, то думаю, что есть смысл работать с кластерами и оперировать мультиблоками.
     
  16. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    dess
    Замечательно. Все необходимое есть. Стандартный ИДЕ контроллер (27DF) содержит 2 БусМастер канала с адресами FFA0h & FFA8h. Для первичного канала адреса I/O 1F0h/3F6h. Для вторичного канала адреса I/O 170h/376h.

    САТА-контроллер (27C0) содержит 2 БусМастер канала с адресами A400h & A408h. Для первичного канала адреса I/O B800h/???h. Для вторичного канала адреса I/O B000h/???h. С ходу не смог определить у него адреса регистров управления. В принципе, в нашем случае можно обойтись и без них. Но для очистки совести, я позже скажу, что нужно сделать, чтобы найти их.

    Чем будем заниматься - добьем ПИО (мультиблок) или переключимся на УДМА ? Если второе, вопрос - нужно-ли подробно описывать Бус Мастер контроллер или сразу написать рабочий фрагмент кода и на нем проводить разбор полетов - буду пояснять, почему написал именно такие команды и как оно работает (по мере поступления вопросов) ?

    Кстати, немного о себе (в смысле интересов) тут: http://forum.ixbt.com/topic.cgi?id=11:38403
     
  17. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    Memphis
    Здорово !!! Есть желание добить ПИО мультиблок в режиме ЛБА48 :) А дальше - по ходу ситуации. Заранее благодарен !
     
  18. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    dess
    Для успешного чтения харда в режиме ЛБА48/ПИО мультиблоком необходимо
    определиться с размером самого блока. Самый простой путь - прочитать
    паспорт харда (АТА-команда 0ECh), посмотреть значение байта по смещению
    76h - это и будет размер блока в секторах. Как правило, размер равен 10h,
    у некоторых встречал 20h (разумеется, программируется). А вот выше
    наверное не бывает. Собственно посекторное чтение (24h) отличается от
    блочного чтения (29h) незначительно - при посекторном после чтения
    очередного одного сектора надо ждать IRQ (или готовность) харда, при
    блочном - ждем готовность после прочтения всего блока. Для особо ленивых
    и не_любителей читать паспорта есть альтернатива (работа при неизвестном
    размере блока) - прочитали один сектор, проверили/подождали готовность,
    прочитали следующий сектор, опять проверка или если надо, ожидание
    готовности и т.д. Привожу фрагмент кода - чтение для харда Primary Master:
    Код (Text):
    1. start:
    2.                 jmp     short begin
    3. ;------------------------------------------------
    4. sect            db      0FFh            ; количество секторов для чтения
    5. multiple        db      10h             ; размер блока в секторах
    6. segm            dw      6789h           ; сегмент ОЗУ для чтения
    7. offs            dw      870Fh           ; смещение в сегменте для трансфера
    8. LBA_lo          dd      11223344h       ; мл. часть номера ЛБА
    9. LBA_hi          dw      0000h           ; ст. часть номера ЛБА
    10. ;------------------------------------------------
    11.  
    12. begin:
    13.                 mov     al,0E0h
    14.                 mov     dx,1F6h
    15.                 out     dx,al
    16.  
    17.                 inc     dx
    18. lab0:
    19.                 in      al,dx
    20.  
    21.                 test    al,80h
    22.                 jnz     lab0
    23.  
    24.                 mov     al,0
    25.                 sub     dx,6
    26.                 out     dx,al
    27.  
    28.                 inc     dx
    29.                 out     dx,al
    30.                 mov     al,sect
    31.                 out     dx,al
    32.  
    33.                 mov     eax,LBA_lo + 3
    34.                 mov     cx,3
    35. lab1:
    36.                 inc     dx
    37.                 out     dx,al
    38.                 shr     eax,8
    39.                 loop    lab1
    40.  
    41.                 sub     dx,2
    42.                 mov     eax,LBA_lo
    43.                 mov     cl,3
    44. lab1a:
    45.                 out     dx,al
    46.                 shr     eax,8
    47.                 inc     dx
    48.                 loop    lab1a
    49.  
    50.                 mov     al,29h
    51.                 inc     dx
    52.                 out     dx,al
    53.  
    54.                 mov     ax,segm
    55.                 mov     di,offs
    56.                 push    di
    57.                 shr     di,4
    58.                 add     ax,di
    59.                 mov     es,ax           ;       !!!!!
    60.                 pop     di
    61.                 and     di,0Fh
    62.  
    63.                 cld                     ;       !!!!!
    64.                 mov     bx,word ptr sect
    65. lab2:
    66.                 sub     bl,bh
    67.                 ja      short lab3
    68.  
    69.                 add     bh,bl
    70.                 mov     bl,0
    71. lab3:
    72.                 movzx   cx,bh
    73.                 shl     cx,7
    74. lab4:
    75.                 in      al,dx
    76.  
    77.                 test    al,80h
    78.                 jnz     lab4
    79.  
    80.                 test    al,1
    81.                 jnz     short error             ;       !!!!!
    82.  
    83.                 sub     dx,7
    84.                 rep     insd
    85.  
    86.                 test    bl,bl
    87.                 mov     ah,0                    ; код 0 - без ошибок
    88.                 jz      short exit
    89.  
    90.                 mov     ax,es
    91.                 push    di
    92.                 shr     di,4
    93.                 add     ax,di
    94.                 mov     es,ax                   ;       !!!!!
    95.                 pop     di
    96.                 and     di,0Fh
    97.                 add     dx,7
    98.  
    99.                 jmp     lab2
    100. ;------------------------------------------------
    101. error:          mov     ah,0Ah                  ; код ошибки на выход
    102.  
    103. exit:
    104.                 int     3
    Уточните для Вашего харда размер блока в секторах и номер ЛБА (внесите данные в бинарник). Очень хочу, чтобы этот код был испробован на ЛБА48 ПАТА харде, разумеется, отладчиком по шагам с номером сектора 0FFFFFFFFFFFF. Выкладываю полный текст фрагмента с бинарником - не запускайте его как COM-модуль, он заканчивается Int 3 (для отладчика) !!!

    http://slil.ru/26304354
     
  19. dess

    dess New Member

    Публикаций:
    0
    Регистрация:
    22 авг 2008
    Сообщения:
    46
    Memphis
    Привет ! Благодарю за наглядный пример ! Начал разбор кода. Есть несколько вопросов:
    - в тексте используется команда insd - чтение двойного слова, в то время, как порт данных является шестнадцатибитным. Как это ??? Или в режиме LBA48 этот порт является 32-битным ?
    - в примере кода сколько блоков читается, один или несколько ?
     
  20. Memphis

    Memphis New Member

    Публикаций:
    0
    Регистрация:
    23 окт 2008
    Сообщения:
    104
    dess
    в тексте используется команда insd - см. мой пост #52. Хард по умолчанию всегда может insw/insd (если он только не очень старый, не могущий PIO3/4). От моды LBA28/48/CHS НЕ ЗАВИСИТ !!! "D" по сравнению с "W" работает в 2 раза быстрее.

    в примере кода сколько блоков читается, один или несколько ? - читается 0FFh секторов. Они дробятся в мультиблоки по 10h секторов. Хотите прочитать 1 сектор - занесите это значение в переменную Sect. Ноль недопустим и бессмысленен.

    как порт данных является шестнадцатибитным - не факт. Когда я переводил свой IBM-хард в технологический режим, я в порт данных писал DWord !!!