Как проверить поддержку расширенного режима работы с int 13h из-под Windows?

Тема в разделе "WASM.WIN32", создана пользователем Jin X, 28 июн 2018.

  1. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Всем привет.
    Необходимо из-под Windows (x86 и x64) проверить - поддерживает ли BIOS'овский int 13h расширенные функции работы с дисками (ah=4xh... 64-битную LBA-адресацию, по сути). Можно ли это сделать? И как?

    Т.е. пишется код для MBR, который будет использовать эти функции, но инсталлироваться он будет из-под Windows.
    Соответственно, если BIOS не поддерживает такие функции, загрузка будет невозможна.
    Поэтому нужна предварительная проверка.

    Я понимаю, что такая поддержка появилась уже давным-давно, но всё же для надёжности хочется сделать проверку.
    И я понимаю, что диск можно перенести на другой комп, где может быть по-другому, тем не менее.
     
  2. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.240
    Адрес:
    Fryazino
    Если диск меньше 8.4 ГБ, то виндоус использует базовый сервис Int 13h, а если больше то расширенный. И это правильно по двум причинам во-первых стандарт (см вот эту версию), во-вторых вы можете диск перенести на другой компьютер. И что тогда? Он перестанет работать?

    Функции для проверки в виндоусе насколько помню нет.

    А так у меня свой асcембле/дизассемблер и эмулятор x386 я себе не в чём не отказываю, и даже в трассировки и эмуляции биоса.

    [​IMG]
     
  3. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Pavia, 8.4 ГБ – это имеется в виду 8 ГиБ (тогда 8.5, почти 8.6 получается)?
    А почему диск до 8 Гб должен перестать работать, если его перенести с компа, где используются расширенные функции, на комп, где используются базовые?

    Что за инструменты?
    Поделись с общественностью :)
     
  4. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.240
    Адрес:
    Fryazino
    Я ссылку оставил там все расчёты есть CHS адресация имеет предел в 8.4 ГБ
    Согласно разделу 8 базовый сервис может адресовать только к
    C=16,383, H=16, S=63, откуда в разделе 3٫2٫6 даны следующие расчёты
    resulting in a maximum device capacity of 8.4 gigabytes (16,383 ∗ 16 ∗ 63 ∗ 512 bytes per sector ≈ 8.4
    gigabytes).
    Из практики тех времён. Если диск меньше 8٫4 то биос не предоставляет к нему расширенный сервис. В лучшем случае расширенный возвращает ошибку. В худшем, что было номера дисков не совпадали.
     
    Jin X нравится это.
  5. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Точно, сектора же с 1 считаются!
    p.s. Ссылку гляну, спасибо.
     
  6. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Кстати, ещё вопросы у меня возникли:
    1. Все ли диски имеют 63 сектора на дорожке? Или бывает меньше?
    2. Всегда ли между MBR и первым разделом расстояние минимум 63 сектора (т.е. 62 сектора между ними)? Или бывает меньше (в каких-то системах)?
    3. Возможно ли установить винду на диск с размером сектора, не равным 512 байт (и вообще, встречаются ли такие жёсткие диски?)
    4. Встречается ли между MBR и первым разделом не нулевые заполнители, а какие-либо другие (скажем, из символов 255 или в виде повторяющихся слов а-ля 0x8000)? Кроме секторов со служебными данными, естественно.
    5. Можно ли установить и успешно загружать винду с USB, имеющим формат не HDD-USB, а FDD-USB, т.е. с boot-сектором в начале, а не MBR? Полагаю, что как минимум Win95/98 можно.
     
  7. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.240
    Адрес:
    Fryazino
    Согласно разработчику биоса Phoenix стр 3 (стр 9) всегда 63 сектора.
    http://www-pc.uni-regensburg.de/hardware/TECHDOK/ATA_EDD_11.PDF
    Просто у виндоса крышу сносит если меньше сделать.

    Да встречаются 2К или 4К. Возможно через UEFI - сам не проверял но народ писал что удачно. Там Boot протокол обязан эммулировать размер сектора 512.
    Раз в год и палка стреляет. Но груб всех вытеснил.
    MBR. GPT, загрузчик такой как GRUB ,копия MBR, далее GRUB до 63 сектора включительно. Последнее число в настройках груба задаётся.

    А шаблоны заполнителя всякие бывают. Есть программы для полной очистке где можно свою фразу указать. А заводские диски они идут с 0000h
     
    Jin X нравится это.
  8. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    А у Линукса и пр?

    А, ну то есть мы всё равно будем видеть 512 всегда?

    Кстати, а можно ли вообще заставить грузить систему через MBR, если включен UEFI? Ну, например, убрать раздел GPT из partition table? Или ещё как-то.
    Не меняя настроек BIOS'а.

    А про это что-нибудь знаешь?
     
  9. _edge

    _edge Well-Known Member

    Публикаций:
    1
    Регистрация:
    29 окт 2004
    Сообщения:
    573
    Адрес:
    Russia
    Pavia не ответил, отвечу - загрузить ОС через Mbr, если включена загрузка через Uefi, нельзя, имхо. Оно будет ориентироваться не по секторам, а по файловой системе, находя и загружая EFI-файл. ГУАШ (UEFI в русской раскладке) для того и делался, чтобы сделать все по-новому. Кастомный же EFI-файл, если все правильно понимаю, ГУАШ скормить не получится, он должен быть хитро подписан.

    Повредите таблицу разделов - биос будет тупо искать Windows Boot Manager, и не найдет его.

    Пишете криптоутилиту для разделов?
     
    Последнее редактирование: 1 июл 2018
  10. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Вроде того. Но не для себя.
    Человек пока сам не до конца понимает, что хочет (вернее, хочет нереальных вещей: шифрования ВСЕГО харда на пару минут... или каких-то других альтернатив, но быстрых, при этом надёжных).
     
  11. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Говорят, были раньше диски с 17- и 28-секторными дорожками.

    Посмотрел сейчас XP под виртуалкой. Там первый раздел начинается с 56-го сектора. И всё работает.
    А 7 и 10 (надо думать, и 8-ка) размечают с 2048-го.

    Как я понял, в SSD минимальный блок (стало быть и сектор) – 4Кб. Но под DOS показывает, что сектор имеет размер 512 байт.

    При форматировании (если не перезаписывать потом) сектора вроде как 0E6h заполняются же (источник). Так что действительно лучше рассчитывать на то, что заполнено может быть чем угодно.
     
  12. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Способ найден! Функция GetSystemFirmwareTable для чтения таблицы SMBIOS:
    Код (ASM):
    1. ; fasm 1
    2. format    PE Console 5.0
    3.  
    4. include    'win32axp.inc'
    5. include    'simport.inc'
    6.  
    7. ;-- CODE SECTION -------------------------------------------------------------------------------------------------------
    8.  
    9. FirmText    equ    'RSMB'
    10. FirmSign    =    FirmText shr 24 + (FirmText shr 8) and 0xFF00 + (FirmText shl 8) and 0xFF0000 + (FirmText shl 24) and 0xFF000000
    11. FirmTable    =    0
    12.  
    13. BUFFER_SIZE    =    65536
    14. SHOW_READ_OK    =    1
    15. SAVE_TO_FILE    =    1
    16. SHOW_FLAG_QWORD =    1
    17.  
    18. .code
    19. start:
    20.  
    21.         ; Read raw SMBIOS firmware table
    22.         invoke    GetSystemFirmwareTable, FirmSign, FirmTable, Table, BUFFER_SIZE
    23.         test    eax,eax
    24.         jz    .readerror
    25.         cmp    eax,BUFFER_SIZE
    26.         ja    .toolarge
    27.         mov    [TableSize],eax
    28. if defined SHOW_READ_OK & SHOW_READ_OK
    29.         cinvoke    printf, <FirmText,' table is read (size = %d bytes)!',10>, eax
    30. end if
    31.  
    32. if defined SAVE_TO_FILE & SAVE_TO_FILE
    33.         ; Save table to file
    34.         stdcall    SaveToFile
    35. end if
    36.         ; Check of EDD support and show results
    37.         stdcall    GetBIOSChars
    38.         jc    .notfound
    39.  
    40. if defined SHOW_FLAG_QWORD & SHOW_FLAG_QWORD
    41.         push    eax
    42.         cinvoke    printf, <'BIOS Characteristics QWORD = %08X%08X',10>, edx, eax
    43.         pop    eax
    44. end if
    45.         btc    eax,19
    46.         jnc    @F
    47.         cinvoke    printf, <'EDD is supported!',10>
    48.         jmp    .finish
    49.     @@:    cinvoke    printf, <'EDD is NOT supported :(',10>
    50.  
    51.         ; Finalization
    52.     .finish:
    53.         cinvoke    printf, <'Press a key to exit...',10>
    54.         cinvoke    getch
    55.         invoke    ExitProcess, 0
    56.     .readerror:
    57.         cinvoke    printf, <FirmText,' table read error :(',10>
    58.         jmp    .finish
    59.     .toolarge:
    60.         cinvoke    printf, <FirmText,' table too large (%d bytes)',10>, eax
    61.         jmp    .finish
    62.     .notfound:
    63.         cinvoke    printf, <'No correct BIOS Information structure is found :(',10>
    64.         jmp    .finish
    65.  
    66. ; Get BIOS Characteristic QWORD (EDX:EAX, CF=0) or -1 (CF=1)
    67. proc        GetBIOSChars    uses esi
    68.         ; Search for BIOS Information structure
    69.         cld
    70.         mov    esi,Table
    71.         add    ebx,esi            ; table end
    72.     .next:
    73.         mov    edx,esi            ; structure start
    74.         xor    eax,eax
    75.         lodsb                ; structure type
    76.         cmp    al,127
    77.         je    .notfound        ; jump if end-of-table type
    78.         test    al,al
    79.         lodsb                ; structure size
    80.         lea    esi,[eax+edx]        ; structure end, start of strings
    81.         jnz    .skipstrings        ; jump if type <> 0 (BIOS Information)
    82.         cmp    al,2
    83.         jb    .notfound        ; WTF???
    84.         cmp    al,12h
    85.         jnb    .ok            ; no jump if bad structure (no BIOS Characteristics qword in this structure)
    86.     .skipstrings:
    87.     @@:    mov    ah,al            ; al <> 0 for the first time
    88.         lodsb
    89.         test    eax,eax
    90.         jnz    @B            ; searching for strings end (double 0)
    91.         cmp    esi,ebx
    92.         jb    .next            ; check next structure
    93.         ; Structure is NOT found
    94.     .notfound:
    95.         stc                ; CF=1 (error)
    96.         ret
    97.     .ok:    ; Structure is found (CF=0, because jumped here by jnb = jnc)
    98.         mov    eax,[edx+0Ah]        ; BIOS Characteristics low dword
    99.         mov    edx,[edx+0Eh]        ; BIOS Characteristics high dword
    100.         ret
    101. endp
    102.  
    103. ; Save table to file
    104. proc        SaveToFile    uses ebx
    105.         invoke    CreateFile, <FirmText,#'.bin'>, GENERIC_WRITE, 0, 0, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0
    106.         cmp    eax,INVALID_HANDLE_VALUE
    107.         je    .createerror
    108.         mov    ebx,eax
    109.         invoke    WriteFile, ebx, Table, [TableSize], Written, 0
    110.         test    eax,eax
    111.         jz    .writeerror
    112.         cmp    [Written],ebx
    113.         jb    .writeerror
    114.         cinvoke    printf, <'Table is saved to file!',10>
    115.     .continue:
    116.         invoke    CloseHandle, ebx
    117.         ret
    118.     .createerror:
    119.         cinvoke    printf, <'File create error :(',10>
    120.         ret
    121.     .writeerror:
    122.         cinvoke    printf, <'File write error :(',10>
    123.         jmp    .continue
    124. endp
    125.  
    126. ;-- DATA SECTION -------------------------------------------------------------------------------------------------------
    127.  
    128. .data
    129.  
    130. Written        rd    1
    131. TableSize    rd    1
    132. Table        rb    BUFFER_SIZE
    133. ZeroWord    rw    1
    134.  
    135. simport        kernel32, GetSystemFirmwareTable
    136.  
    137. slibrary    msvcrt, 'msvcrt.dll'
    138. simport        msvcrt,\
    139.         printf, ,\
    140.         getch, '_getch'
    141.  
    142. .end        start
    Единственная непонятка: почему (у меня, по крайней мере) 1-я запись в таблице имеет тип 0 (BIOS Information) и размер 2 (и содержит какую-то хрень вместо строк), а не 12h+, как положено? А уже вторая – нормальная (тоже тип 0).
    Вот первые 16 байт: 00 02 07 00 2B 0C 00 00 00 18 00 00 01 02 00 F0
    Может, кто знает в чём тут прикол?
     
  13. Jin X

    Jin X Active Member

    Публикаций:
    0
    Регистрация:
    15 янв 2009
    Сообщения:
    269
    Адрес:
    Кольца Сатурна
    Блин, тут 4-байтовые табы... вот с пробелами (заодно косячок исправил и include добавил):
    Код (ASM):
    1. ; fasm 1 (Windows Vista/XP Pro x64 +)
    2. format  PE Console 5.0
    3.  
    4. include 'win32axp.inc'
    5. include 'simport.inc'
    6.  
    7. ;-- CODE SECTION -------------------------------------------------------------------------------------------------------
    8.  
    9. FirmText        equ     'RSMB'
    10. FirmSign        =       FirmText shr 24 + (FirmText shr 8) and 0xFF00 + (FirmText shl 8) and 0xFF0000 + (FirmText shl 24) and 0xFF000000
    11. FirmTable       =       0
    12.  
    13. BUFFER_SIZE     =       65536
    14. SHOW_READ_OK    =       1
    15. SAVE_TO_FILE    =       1
    16. SHOW_FLAG_QWORD =       1
    17.  
    18. .code
    19. start:
    20.  
    21.                 ; Read raw SMBIOS firmware table
    22.                 invoke  GetSystemFirmwareTable, FirmSign, FirmTable, Table, BUFFER_SIZE
    23.                 test    eax,eax
    24.                 jz      .readerror
    25.                 cmp     eax,BUFFER_SIZE
    26.                 ja      .toolarge
    27.                 mov     [TableSize],eax
    28. if defined SHOW_READ_OK & SHOW_READ_OK
    29.                 cinvoke printf, <FirmText,' table is read (size = %d bytes)!',10>, eax
    30. end if
    31.  
    32. if defined SAVE_TO_FILE & SAVE_TO_FILE
    33.                 ; Save table to file
    34.                 stdcall SaveToFile
    35. end if
    36.                 ; Check of EDD support and show results
    37.                 stdcall GetBIOSChars
    38.                 jc      .notfound
    39.  
    40. if defined SHOW_FLAG_QWORD & SHOW_FLAG_QWORD
    41.                 push    eax
    42.                 cinvoke printf, <'BIOS Characteristics QWORD = %08X%08X',10>, edx, eax
    43.                 pop     eax
    44. end if
    45.                 btc     eax,19
    46.                 jnc     @F
    47.                 cinvoke printf, <'EDD is supported!',10>
    48.                 jmp     .finish
    49.         @@:     cinvoke printf, <'EDD is NOT supported :(',10>
    50.  
    51.                 ; Finalization
    52.         .finish:
    53.                 cinvoke printf, <'Press a key to exit...',10>
    54.                 cinvoke getch
    55.                 invoke  ExitProcess, 0
    56.         .readerror:
    57.                 cinvoke printf, <FirmText,' table read error :(',10>
    58.                 jmp     .finish
    59.         .toolarge:
    60.                 cinvoke printf, <FirmText,' table too large (%d bytes)',10>, eax
    61.                 jmp     .finish
    62.         .notfound:
    63.                 cinvoke printf, <'No correct BIOS Information structure is found :(',10>
    64.                 jmp     .finish
    65.  
    66. ; Get BIOS Characteristic QWORD (EDX:EAX, CF=0) or CF=1 on error
    67. proc            GetBIOSChars    uses esi
    68.                 ; Search for BIOS Information structure
    69.                 cld
    70.                 mov     esi,Table
    71.                 mov     edx,[TableSize]
    72.                 add     edx,esi                 ; table end
    73.         .next:
    74.                 mov     ecx,esi                 ; structure start
    75.                 xor     eax,eax
    76.                 lodsb                           ; structure type
    77.                 cmp     al,127
    78.                 je      .notfound               ; jump if end-of-table type
    79.                 test    al,al
    80.                 lodsb                           ; structure size
    81.                 lea     esi,[eax+ecx]           ; structure end, start of strings
    82.                 jnz     .skipstrings            ; jump if type <> 0 (BIOS Information)
    83.                 cmp     al,2
    84.                 jb      .notfound               ; WTF???
    85.                 cmp     al,12h
    86.                 jnb     .ok                     ; no jump if bad structure (no BIOS Characteristics qword in this structure)
    87.         .skipstrings:
    88.         @@:     mov     ah,al                   ; al <> 0 for the first time
    89.                 lodsb
    90.                 test    eax,eax
    91.                 jnz     @B                      ; searching for strings end (double 0)
    92.                 cmp     esi,edx
    93.                 jb      .next                   ; check next structure
    94.                 ; Structure is NOT found
    95.         .notfound:
    96.                 stc                             ; CF=1 (error)
    97.                 ret
    98.         .ok:    ; Structure is found (CF=0, because jumped here by jnb = jnc)
    99.                 mov     eax,[ecx+0Ah]           ; BIOS Characteristics low dword
    100.                 mov     edx,[ecx+0Eh]           ; BIOS Characteristics high dword
    101.                 ret
    102. endp
    103.  
    104. ; Save table to file
    105. proc            SaveToFile      uses ebx
    106.                 invoke  CreateFile, <FirmText,#'.bin'>, GENERIC_WRITE, 0, 0, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0
    107.                 cmp     eax,INVALID_HANDLE_VALUE
    108.                 je      .createerror
    109.                 mov     ebx,eax
    110.                 invoke  WriteFile, ebx, Table, [TableSize], Written, 0
    111.                 test    eax,eax
    112.                 jz      .writeerror
    113.                 cmp     [Written],ebx
    114.                 jb      .writeerror
    115.                 cinvoke printf, <'Table is saved to file!',10>
    116.         .continue:
    117.                 invoke  CloseHandle, ebx
    118.                 ret
    119.         .createerror:
    120.                 cinvoke printf, <'File create error :(',10>
    121.                 ret
    122.         .writeerror:
    123.                 cinvoke printf, <'File write error :(',10>
    124.                 jmp     .continue
    125. endp
    126.  
    127. ;-- DATA SECTION -------------------------------------------------------------------------------------------------------
    128.  
    129. .data
    130.  
    131. Written         rd      1
    132. TableSize       rd      1
    133. Table           rb      BUFFER_SIZE
    134. ZeroWord        rw      1
    135.  
    136. simport         kernel32, GetSystemFirmwareTable
    137.  
    138. slibrary        msvcrt, 'msvcrt.dll'
    139. simport         msvcrt,\
    140.                 printf, ,\
    141.                 getch, '_getch'
    142.  
    143. .end            start
    simport.inc:
    Код (ASM):
    1. ; WinAPI function import (written by Tomasz Grysztar, square brackets [] added by Jin X)
    2. ; usage:
    3. ;   simport kernel32, GetFirmwareEnvironmentVariableA  ; function name string can be omitted (like here)
    4. ;   api GetFirmwareEnvironmentVariable  ; only for functions with 'A' or 'W' suffix
    5. macro    simport    library_label*, [label*, string]
    6. {
    7.     match ,string \{ define library_label#.collection label,`label \}
    8.     match any, string \{ define library_label#.collection label,string \}
    9. }
    10.  
    11. ; wrapper of import macros (written by Tomasz Grysztar)
    12. macro    import    library_label*, list&
    13. {
    14.     common
    15.         local all
    16.         define all
    17.         irpv a, library_label#.collection \{ all equ all , a \}
    18.         match a, list \{ all equ , list all \}
    19.         match complete, all \{ import library_label complete \}
    20. }
    21.  
    22. ; DLL library import (written by Tomasz Grysztar)
    23. ; usage:
    24. ;   slibrary msvcrt  ; dll name string can be omitted (like here)
    25. ;   simport msvcrt, printf  ; function name string can be omitted (like here)
    26. ;  or:
    27. ;   simport msvcrt, printf,, getch, '_getch', scanf
    28. macro    slibrary    library_label*, string
    29. {
    30.     match ,string \{ define import_library library_label,`library_label#'.DLL' \}
    31.     match any, string \{ define import_library library_label,string \}
    32. }
    33.  
    34. ; wrapper of library macros (written by Tomasz Grysztar)
    35. macro    library    list&
    36. {
    37.     common
    38.         local all
    39.         define all
    40.         irpv a, import_library \{ all equ all , a \}
    41.         match complete, list all \{ library complete \}
    42.         irpv a, import_library \{ match library_label=,string, a \\{ import library_label \\} \}
    43. }