На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Перед отправкой сообщения внимательно прочтите правила раздела!!!
1. Все статьи должны быть оформлены согласно Правил оформления статей.
2. Любые обсуждения должны происходить в специальной теме, обсуждение в любых других темах раздела запрещены.
3. Запрещается писать статьи о создании и распространении вирусов, троянов и других вредоносных программ!
4. За грамотно написанные и правильно оформленные статьи авторы награждаются DigiMoney.

Дополнительные ссылки:
Желаю творческих успехов! ;)
Модераторы: Jin X
  
    > Получение нулевого уровня привилегий , Windows, Zen
       
      Получение нулевого уровня привилегий

      Я не буду объяснять, что такое нулевой уровень привилегий (нулевое кольцо, ring 0), т.к. если Вы этого не знаете, значит Вам там (в ring 0) делать нечего. Но если Вам всё же интересно, почитайте про защищённый режим ;) .
      Самый простой, на мой взгляд, способ попасть в ring 0 под Windows 9X - это перехватить обработку прерывания и вызвать это прерывание. Т.к. все прерывания выполняются в ring 0, то и наш обработчик будет выполняться в нём же. Реализовать это очень просто: достаточно подправить таблицу дескрипторов прерываний IDT. Однако проделать такое можно только под Windows 9X, т.к. Windows NT не разрешит нам редактировать IDT, но это совсем не означает, что под Windows NT попасть в ring 0 невозможно (только описывать эту процедуру я даже не буду пытаться, и не просите!). Но есть ещё один вопрос: какое прерывание выбрать? Я предлагаю int 3. Кстати говоря, в примере Как написать резидентную программу (под Windows)? обработчик прерывания работает как раз в ring 0.

      Итак, вот простой пример программы попадания в ring 0:
      ExpandedWrap disabled
        ; ml /c /coff /Ic:\masm32\include ring0.asm
        ; link /subsystem:console /libpath:c:\masm32\lib ring0.obj
         
        .586P
        .MODEL Flat,StdCall
        OPTION CASEMAP:NONE
         
        INCLUDE     WINDOWS.INC
        INCLUDE     KERNEL32.INC
        INCLUDE     USER32.INC
        INCLUDELIB  KERNEL32.LIB
        INCLUDELIB  USER32.LIB
         
        ; Номер перехватываемого прерывания
        Intr        =   3
         
        .DATA
         
        Text        db  'Эта прога не пашет в Windows NT/2K/XP :(',0
        Caption     db  'Облом, да?',0
         
        .CODE
         
        ; Вызов процедуры, которая должная выполниться в Ring 0
        ; В качестве параметра передаётся адрес процедуры
        CallInRing0 proc    R0Proc: DWORD
                pushf                  ; Сохраняем флаги
                cli                    ; Запрещаем аппаратные прерывания
        ; Получаем адрес IDT
                push    eax            ; Сохраняем в стеке что-нибудь (*)
                sidt    [esp-2]        ; Записываем в стек предел и адрес (на место (*)) IDT
                pop eax            ; Записываем в EAX адрес IDT из (*)
         
        ; Сохраняем адрес старого обработчика и устанавливаем новый
                add eax,Intr*8     ; EAX = адрес дескриптора нужного прерывания
                mov ebx,R0Proc     ; EBX = адрес нашей процедуры
                xchg    [eax+0],bx     ; Читаем и записываем младшее слово адреса обработчика
                ror ebx,16
                xchg    [eax+6],bx     ; Читаем и записываем старшее слово адреса обработчика
         
                int Intr           ; Вызываем нашу процедуру
                popf                   ; Восстанавливаем флаги
                ret                    ; Выходим из процедуры
        CallInRing0 endp
         
        ; Процедура восстановления прерывания (см. ниже)
        RestInt     proc
                mov [eax+6],bx     ; Восстанавливаем старшее слово адреса обработчика
                ror ebx,16
                mov [eax+0],bx     ; Восстанавливаем младшее слово адреса обработчика
                sti                    ; Разрешаем аппаратные прерывания
                ret                    ; Выходим из процедуры
        RestInt     endp
         
        ;----------------------------------------------------------------------------;
         
        ; Процедура, выполняемая в Ring 0
        Ring0Proc   proc
        ; Восстанавливаем дескриптор прерывания (эту процедуру необходимо вызывать
        ; всегда в самом начале процедуры, которая вызывается в нулевом кольце!!!)
                call    RestInt
         
                ;----------------------------------------;
                ;    ВСЁ, МЫ В НУЛЕВОМ КОЛЬЦЕ, УРА!!!    ;
                ; ЗДЕСЬ МОЖНО ДЕЛАТЬ ВСЁ, ЧТО УГОДНО! ;) ;
                ;----------------------------------------;
         
        ; Выходим из процедуры (а также из обработчика прерывания и из Ring 0)
        ; Выходить из такой процедуры нужно через iretd, (никаких ret и retf!)
                iretd
        Ring0Proc   endp
         
        ;----------------------------------------------------------------------------;
        ;                         Начало основной программы                          ;
        ;----------------------------------------------------------------------------;
         
        Start:
         
        ; Проверяем платформу (Windows 9X или NT)
                invoke  GetVersion     ; Узнаем номер версии
                or  eax,eax        ; Старший бит установлен?
                js  @@Continue     ; Да, это Windows 9X, ура! :)
         
                invoke  MessageBox, NULL, offset Text, offset Caption, MB_OK+MB_ICONERROR
                jmp @@Exit         ; Выходим
        @@Continue:
        ; Запускаем процедуру в Ring 0
                invoke  CallInRing0, offset Ring0Proc
         
        @@Exit:
        ; Выходим из программы
                invoke  ExitProcess, NULL ; Goodbye!
         
        END     Start
        Продолжив тему получения R-0 привилегий, рассмотрим пример для win2000/xp/2003.
        (Во всех примерах компилятор fasm 1.62)

        Самый простой способ это, естественно написание кода в драйвере:
        ExpandedWrap disabled
          format      PE native 4.0
          include     "%fasminc%/win32a.inc"
          proc        main,object,regpath  
          ;здесь мог бы быть ваш код
          mov eax,STATUS_DEVICE_CONFIGURATION_ERROR
          ret    
          mov eax,main
          section '.reloc' data fixups readable discardable

        но, такой способ требует хорошего знания архитектуры Windows, т.к. использование "обычных"(ring-3) api функций из ring-0 проблематично.

        По этому удобней использовать драйвера, "пробивающие бреж" в ring-0 для обычных приложений ring-3.
        Например:
        ExpandedWrap disabled
          format      PE native 4.0
          include     "%fasminc%/win32a.inc"
          ;***************main**********************
          proc main,pDriverObject,pDriverPath
          pushfd ; сохраняем флаги
          pushad ; сохраняем регистры
           
          mov eax,[pDriverObject] ; получаем указатель на DriverObject
          add eax,34h ;смещение на адрес для функции выгрузки драйвера
          mov dword[eax],UnloadDriver ; записываем адрес выгрузки
           
          mov eax,[INTnum] ; номер прерывания
          stdcall SetInt,INT_Service,eax,ioldhandler,11101110b ; установим обработчик прерываний для R-3, сохранив старый в ioldhandler
          ; INT_Service - новый обработчик прерывания
          popad
          popfd
          mov eax,0
          ret
          endp
          ;***************unload**********************
          proc UnloadDriver,pDriverObject
          pushad
           
          mov eax,[INTnum] ; номер прерывания
          stdcall RestoreInt,eax,ioldhandler ; восстановим обработчик прерываний
           
          popad
          mov eax,0
          ret
          endp
          ;*******************proc*****************
          include 'setints.inc'
          ;******************service***************
          INT_Service:
          cli ; сбросим флаг прерываний
          call eax ; перейдём на код, который должен выполнится в R-0
          sti ; восстановим флаг прерываний
          iret ; выйдем из обработчика прерываний
          ;*********************************************
          ;******************data***********************
          PADR                     dd 0h
          INTnum                   dd 20h
          ioldhandler              dd 0
          ;*********************************************
          ;*********************************************
          mov eax,main
          ;*********************************************
          section '.reloc' data fixups readable discardable

        Файл setints.inc:
        ExpandedWrap disabled
          proc SetInt,INT_ADR,IntNum,Int_alt,option
          pushad
          ;*********************************************
          ;*********** установка обработчика прерывания*
          ;*********************************************
          cli
          mov eax,cr0
          push eax
          and eax,0xFFFEFFFF ; clear WP
          mov cr0,eax
           
          mov al,byte[option]
          mov byte[.opt+1],al
           
          ; вычисление адреса
          mov eax,[INT_ADR]
          mov [.IAdressAll],eax
          mov ax,word[.IAdressAll]
          mov [.ladr],ax
          mov ax,word[.IAdressAll+2]
          mov [.hadr],ax
           
          mov [.seg],cs
          push ebx             ; получить адрес IDT
          sidt [esp-2]
          pop  ebx
          xor eax,eax
          mov al,byte[IntNum]           ; номер прерывания
          mov ah,8h
          mul ah
          add ebx,eax ;8*ints                 ; адрес int xx
           
          ;сохраним старый адрес Exception
          mov edi, [Int_alt]
          mov esi, ebx
          movsd
          movsd
          ;установим новый адрес Exception
          mov edi, ebx
          mov esi, .Int_new
          movsd
          movsd
          sti
          pop eax
          mov cr0,eax ; restore WP
          popad
          ret
          ;*********************************************
          ;*********************************************
          ;*********************************************
          .IAdressAll dd 0
          .Int_new:
          .ladr       dw 0
          .seg        dw 0                  ; p AC   Type
          .opt        db 00000000b,11101110b; 1|11|0|1110|
          ;Type GrapG16 -0111; GrapG32 -1111; IntG32 -1110; CallG32 - 1100;
          .hadr       dw 0
          endp
           
          proc RestoreInt,IntNum,Int_alt
          pushad
          ;**********************************************************
          ;*****************восстановим обработчик прерывания*********
          ;**********************************************************
          cli
          mov eax,cr0
          push eax
          and eax,0xFFFEFFFF ; clear WP
          mov cr0,eax
           
          mov [.seg],cs
          push ebx             ; получить адрес IDT
          sidt [esp-2]
          pop  ebx
          xor eax,eax
          mov al,byte[IntNum]           ; номер прерывания
          mov ah,8h
          mul ah
          add ebx,eax ;8*ints                 ; адрес int xx
          ;восстановим старый адрес Exception
          mov edi, ebx
          mov esi, [Int_alt]
          movsd
          movsd
          sti
          pop eax
          mov cr0,eax ; restore WP
          popad
          ret
          ;**********************************************************
          ;**********************************************************
          ;**********************************************************
          .IAdressAll dd 0
          .Int_new:
          .ladr       dw 0
          .seg        dw 0                  ; p AC   Type
          .opt        db 00000000b,11101110b; 1|11|0|1110|
          ;Type GrapG16 -0111; GrapG32 -1111; IntG32 -1110; CallG32 - 1100;
          .hadr       dw 0
          endp

        Загруженный драйвер использовать так:
        ExpandedWrap disabled
          include '%fasminc%/win32ax.inc'
          .data
          StrMsgBoxText           DB      'CR0=%08XH',0DH,0AH
                                  DB      'CR2=%08XH',0DH,0AH
                                  DB      'CR3=%08XH',0DH,0AH,0
          StrTemp                 RB      128
          .code
           
          proc    ExceptCallBack
                  invoke  MessageBox,0,"Not Ring-0!","Test Ring-0 Programm",0
                  invoke  ExitProcess, -1
          ret
          endp
           
          start:
          invoke  SetUnhandledExceptionFilter,ExceptCallBack ; установим обработчик ошибок
           
          mov eax,tests ; адрес функции для R-0
          int 20h ; вызов драйвера
           
          invoke wsprintf,StrTemp,StrMsgBoxText,eax,ebx,edx ; конвертируем значения
          invoke  MessageBox,HWND_DESKTOP,StrTemp,"Ring-0!",MB_OK
          invoke  ExitProcess,0
           
          proc tests
          ; считываем регистры, доступные только в R-0
                  mov     eax,cr0
                  mov     ebx,cr2
                  mov     edx,cr3
          ret
          endp
          .end start
          Загрузить драйвер можно например так:
          ExpandedWrap disabled
            ; example of simplified Win32 programming using complex macro features
             
            include '%fasminc%/win32ax.inc'
            ; Server Constant
            SC_MANAGER_CONNECT     = 01h
            SC_MANAGER_CREATE_SERVICE     = 02h
            SC_MANAGER_ENUMERATE_SERVICE     = 04h
            SC_MANAGER_LOCK      = 08h
            SC_MANAGER_QUERY_LOCK_STATUS     = 10h
            SC_MANAGER_MODIFY_BOOT_CONFIG     = 20h
            SERVICE_DEMAND_START     = 03h
            SERVICE_KERNEL_DRIVER     = 01h
            DELETE     = 10000h
            SERVICE_QUERY_CONFIG       equ 0001h
            SERVICE_CHANGE_CONFIG       equ 0002h
            SERVICE_QUERY_STATUS       equ 0004h
            SERVICE_ENUMERATE_DEPENDENTS   equ 0008h
            SERVICE_START       equ 0010h
            SERVICE_STOP       equ 0020h
            SERVICE_PAUSE_CONTINUE       equ 0040h
            SERVICE_INTERROGATE       equ 0080h
            SERVICE_USER_DEFINED_CONTROL   equ 0100h
            SERVICE_ERROR_IGNORE       equ 00000000
            SERVICE_ERROR_NORMAL       equ 00000001
            SERVICE_ERROR_SEVERE       equ 00000002
            SERVICE_ERROR_CRITICAL       equ 00000003
             
            SERVICE_CONTROL_STOP       equ 00000001h
            SERVICE_CONTROL_PAUSE       equ 00000002h
            SERVICE_CONTROL_CONTINUE       equ 00000003h
            SERVICE_CONTROL_INTERROGATE    equ 00000004h
            SERVICE_CONTROL_SHUTDOWN       equ 00000005h
            SERVICE_CONTROL_PARAMCHANGE    equ 00000006h
            SERVICE_CONTROL_NETBINDADD     equ 00000007h
            SERVICE_CONTROL_NETBINDREMOVE  equ 00000008h
            SERVICE_CONTROL_NETBINDENABLE  equ 00000009h
            SERVICE_CONTROL_NETBINDDISABLE equ 0000000Ah
             
            .data
            szFileNamerb200h
            FileNamedb     'DriverNT.sys',0
            ServiceNamedb     '!Driver',0
            DisplayNamedb     'Äðàéâ',0
            shndd 0
            chndd 0
            Errrb 6
            ;***********************************
            ; SERVICE_STATUS
            _ss:
            .dwServiceType    dw ?
            .dwCurrentState     dw ?
            .dwControlsAccepted    dw ?
            .dwWin32ExitCode    dw ?
            .dwServiceSpecificExitCode  dw ?
            .dwCheckPoint    dw ?
            .dwWaitHint    dw ?
            db 0
            ;***********************************
            .code
             
             start:
            mov Dword[Err],'ER-1'
            invoke OpenSCManager,0,0,SC_MANAGER_CREATE_SERVICE
            mov [chn],eax
            test eax,eax
            je ERR
             
            invoke GetFullPathName,FileName ,200h,szFileName,esp
            ;xor     eax,eax
            ;and     [esp],eax
             
            mov Dword[Err],'ER-2'
             
            invoke CreateService,[chn],ServiceName ,DisplayName , \
            SERVICE_START + SERVICE_STOP + DELETE,\
            SERVICE_KERNEL_DRIVER, SERVICE_DEMAND_START, \
            SERVICE_ERROR_IGNORE,szFileName, NULL, NULL, NULL, NULL,NULL
             
            test eax,eax
            je ERR
             
            mov [shn],eax
            mov Dword[Err],'ER-3'
            invokeStartService,[shn],0,0
            test eax,eax
            je ERR
             
            invokeMessageBox,HWND_DESKTOP,"Выгрузить драйвер?","DRIVER",MB_OK
            mov Dword[Err],'ER-4'
            invoke ControlService,[shn], SERVICE_CONTROL_STOP,_ss
            test eax,eax
            je ERR
            mov Dword[Err],'ER-5'
            invokeDeleteService,[shn]
            test eax,eax
            je ERR
            invokeCloseServiceHandle,[shn]
            invokeExitProcess,0
             
            ERR:
            invokeMessageBox,HWND_DESKTOP,Err,"DRIVER",MB_OK
            invokeDeleteService,[shn]
            invokeCloseServiceHandle,[shn]
            invokeExitProcess,0
            .end start
          0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
          0 пользователей:


          Рейтинг@Mail.ru
          [ Script execution time: 0,0290 ]   [ 16 queries used ]   [ Generated: 26.04.24, 05:45 GMT ]