Запись в видеопамять

Тема в разделе "WASM.NT.KERNEL", создана пользователем murder, 3 июн 2007.

  1. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Хочу осуществить низкоуровневый вывод на экран (как в SoftIce). Возникли некоторые трудности. Во первых не ясно в какую область памяти записывать данные - у меня на GeForce 7300 их три (тройная буферизация?). Но самое главное - при обращении к этим адресам происходит краш с кодом 50h PAGE_FAULT_IN_NONPAGED_AREA. Как же этого добились в NuMega SoftIce?

    "Самокомпилирующийся" bat-файл

    ;@echo off
    ;goto make


    .386
    .model flat, stdcall
    option casemap:none

    include include\w2k\ntoskrnl.inc
    includelib lib\w2k\ntoskrnl.lib


    .data

    lolimit dw 0FFFFh ;структура дескриптора с базой 0 и лимитом 4Гб
    lobase dw 0
    db 0
    flags1 db 10010011b
    hilmit db 11001111b
    hibase db 0

    SelectorArray dd 0

    .code

    DriverEntry:
    ;Создаю дескриптор
    invoke KeI386AllocateGdtSelectors,addr SelectorArray,1
    invoke KeI386SetGdtSelector,SelectorArray,addr lolimit

    ;записываю в видеопамять
    push es
    push edi

    mov es,SelectorArray
    mov edi,0E0000000h ;этот адрес выводится в свойствах видеокарты
    mov ecx,16000

    fill: ;для надежности не стал ипользовать rep stosd
    mov es:[edi],eax ;потому, что не уверен, как это работает
    add edi,4 ;в защищенном режиме
    loop fill

    pop edi
    pop es
    xor eax,eax ;означает, что драйвер зарегистрирован без ошибок :)
    retn 8 ;у DriverEntry 2 параметра по 4 байта

    end DriverEntry


    :make

    set drv=drv

    bin\ml /nologo /c /coff %drv%.bat
    bin\link /nologo /driver /base:0x10000 /align:4 /out:%drv%.sys /subsystem:native %drv%.obj

    del %drv%.obj

    echo.
    pause
     
  2. rei3er

    rei3er maxim

    Публикаций:
    0
    Регистрация:
    15 янв 2007
    Сообщения:
    917
    Адрес:
    minsk
    murder
    адрес (0xE0000000) то ты получил физический (скорее всего)
    но интерпретируется он как виртуальный
     
  3. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Дык нельзя обращаться по такому виртуальному адресу! Ведь память еще надо промапить и получить виртуальный адрес, который будет транслироваться в такой физический
     
  4. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    murder
    Я немного от жизни отстаю. Обычно там два диапозона. Один это видео память. Другой регистры видео карты отоброженные в память через которые видеться программирование 2D и 3D ускорителей и прочего правда эта область спецефична для каждой видео карты.
     
  5. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Эти области памяти по 16 МБ, то есть это точно не регистры.

    Great
    Чет не понял. Смотри: я создаю новый дескриптор с базой ноль и делаю смещение относительно него. Получается 0+0E0000000h. Помоему никаких преобразований не надо.

    В принципе совсем не обязательно вывести изображение таким способом. Для меня важно реализовать интерфейс пользователя из режима ядра. Может существуют какие-нибудь функции для вывода графики в драйверах?

    PS
    0E0000000h - это не физический адрес. У меня 768 RAM + 256 VRAM, а адрес указывает на 3,5 Гб.
     
  6. rei3er

    rei3er maxim

    Публикаций:
    0
    Регистрация:
    15 янв 2007
    Сообщения:
    917
    Адрес:
    minsk
    murder
    как раз таки это физический адрес
    физически процессор (32-ух разрядный) может адресовать до 4GB (ну или до 64GB с PAE)
    все это адресное пространство разбито на области: внешняя память отображена на одну область адресного пространства CPU, PCI устройства (в том числе твоя видеокарта), APIC - на другие области и т. д
    вообщем, физический адрес - совсем не обязательно относится к внешней памяти
     
  7. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    murder
    Регистры. Просто NVidia любят резервировать под них побольше памяти(вернее диапозон адрессов), а задействована там только небольшая часть.
    0E0000000h - это физический адресс. А в дескрипторе у тебя лежит линейный. Так что тебе требуется создать страницу которая отоброзит физический адрес на линейный.

    Видео память распологается в конце 4Гб диапозона плюс из за выравнивания будет браться удвоенное значение.
    100000000h= 4ГБ 10000000h=256МБ
    100000000h-2*10000000h=0E0000000h
     
  8. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Отнюдь. Видеопамять аппаратно проецируется на физадреса и процу по боку, есть ли там RAM или нету
    + про страничное преобразование я уже сказал, что надо создать страницу виртуальную, которая будет спроецирвана на этот адрес
     
  9. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Pavia
    Это значит, что на разных видеокартах разные диапазоны адресов?

    Подскажите функции для реализации этого или может поделитесь ссылкой?
     
  10. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Про апишки хала такие я не знаю, глянь в MSDN, а про аппаратную часть вот: http://www.wasm.ru/article.php?article=pipm06
     
  11. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Great
    Хм, интересно... Раньше я пропускал эту главу т.к. считал, что страничная адресация связана с файлом подкачки, а к невыгружаемым драйверам это не относится.

    В "хале" помойму нет ничего интересного, а вот в ntoskrnl.exe много функций, имена которых содержат слово "page".

    Что может означать AllocatePagesForMdl?
    Очень рассмешила такая фраза
    После неё идёт список недокументированых функций
     
  12. rei3er

    rei3er maxim

    Публикаций:
    0
    Регистрация:
    15 янв 2007
    Сообщения:
    917
    Адрес:
    minsk
    виртуальная память - это фундаментальное понятие
    а то, что она может использоваться для реализации подкачки, это уже второе...
     
  13. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    К подкачке она никаким раком не относится почти что ) Самое главное - это виртуализация адресного пространства..

    Насколько я помню, есть функция MmMapIoSpace, которая вроде бы как раз проецирует физстраницы на виртуальное пространство... только я точно не помню. Почитай MSDN. На крайняк оперируй структурами сам, получая адрес через CR3 :)
     
  14. Pavia

    Pavia Well-Known Member

    Публикаций:
    0
    Регистрация:
    17 июн 2003
    Сообщения:
    2.409
    Адрес:
    Fryazino
    Да на разных видео картах разне диапозоны. Дак же на разных системах с одинаковыми видео картами диапозоны могут отличаться.
     
  15. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Great
    Адрес в CR3 - физический, то есть круг опять замкнётся! Ммм... MmMapIoSpace, говоришь? Я обязательно попробую. То есть надо просто вызвать эту функцию и всё? А как же преобразование линейного адреса в страничный?
     
  16. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    Тебе система выдаст виртуальный адрес, соответствующий твоему физическому адресу видеобуфера.
    Дальше обращайся по этому виртуальному адресу и все.
     
  17. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    При вызове
    invoke MmMapIoSpace,0E0000000h,65536,0,MmCached
    компьютер просто перезагружается

    Вот прототип
    MmMapIoSpace(IN PHYSICAL_ADDRESS PhysicalAddress,IN ULONG NumberOfBytes,IN MEMORY_CACHING_TYPE CacheType);

    в ntoskrnl.inc определено 16 байт параметров. Я не знаком с C, ULONG - это 8 байт? Нужно ли вызывать MmUnmapIoSpace?
     
  18. wasm_test

    wasm_test wasm test user

    Публикаций:
    0
    Регистрация:
    24 ноя 2006
    Сообщения:
    5.582
    как это ты так передаешь я чета не врубил. и почему адрес физический у тебя 10000E0000000, а не E0000000 ?
    И число байт = 0

    имхо, invoke MmMapIoSpace, 0E0000000h, 0, 65536, MmCached.
     
  19. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Great
    У меня непонятки с параметрами. Передаю так

    Физ. адрес - 4 байта
    число байт - 8 байт
    флажки - 4 байта

    Ты хочешь сказать что физ. адрес - 8 байт? Через какой селектор мне потом обращаться по полученому смещению? Через тот, который я создал с базой=0?
     
  20. murder

    murder Member

    Публикаций:
    0
    Регистрация:
    3 июн 2007
    Сообщения:
    628
    Great
    Ты как всегда прав. Вот что я выяснил экспериментальным путём:
    0E0000000h - регистры или какие-нибудь управляющие структуры (при записи в них монитор отключается)
    0D0000000h - видеопамять
    0E1000000h - не проверял

    Помоги решить проблему переносимости. Я вот, что думаю:

    1) В реестре есть ветка HKEY_LOCAL_MACHINE\HARDWARE\RESOURCEMAP\PnP Manager\PnPManager
    В нём 2 ключа: \Device\Video1.Raw и \Device\Video1.Translated
    Их значения остаются для меня загадкой. Может быть они содержат информацию о адресах памяти?
    2) Можно использовать VBE сервисы для переключения в VGA-режим. В VGA режиме скорее всего память начинается с 0A0000h. Для восстановления предыдущего режима вроде-бы тоже есть спец функции. Но я работал с VBE только в реальном режиме через прерывание 10h. В защищёнке по-мойму используется прерывание 31h для эмуляции прерываний реального режима, но я не понял, как им пользоваться.

    PS
    Искал в реестре параметр со значением "D0000000", а также в двоичной и десятичной системах, ничего не найдено.