Nota
O acesso a esta página requer autorização. Podes tentar iniciar sessão ou mudar de diretório.
O acesso a esta página requer autorização. Podes tentar mudar de diretório.
Uma fonte significativa de problemas de segurança dentro dos drivers é o uso de identificadores passados entre componentes de modo de usuário e de modo kernel. Há uma série de problemas conhecidos com o uso de handle dentro do ambiente do kernel, incluindo o seguinte:
Um aplicativo que passa o tipo errado de identificador para um driver do kernel. O driver do kernel pode falhar ao tentar usar um objeto de evento onde um objeto de arquivo é necessário.
Um aplicativo que passa um identificador para um objeto para o qual ele não tem o acesso necessário. O driver do kernel pode executar uma operação que funciona porque a chamada vem do modo kernel, mesmo que o usuário não tenha permissões adequadas para fazê-lo.
Uma aplicação que passa um valor que não é um identificador válido no seu espaço de endereçamento, mas é marcado como um identificador do sistema para executar uma operação má intencionada contra o sistema.
Um aplicativo que passa um valor que não é um identificador apropriado para o objeto de dispositivo (um identificador que esse driver não criou).
Para se proteger contra esses problemas, um controlador do kernel deve ser particularmente cuidadoso para garantir que os identificadores que lhe são passados sejam válidos. A política mais segura é criar as alças necessárias dentro do contexto do motorista. Esses identificadores, criados por drivers de kernel, devem especificar a opção OBJ_KERNEL_HANDLE, que criará um identificador válido em contexto de processo arbitrário e que só pode ser acessado a partir de um chamador de modo kernel.
Para drivers que utilizam manipuladores criados por um programa de aplicação, a utilização destes manipuladores deve ser feita com extremo cuidado:
A prática recomendada é converter o identificador em um ponteiro de objeto chamando ObReferenceObjectByHandle, especificando os parâmetros AccessMode (geralmente de Irp-RequestorMode>), DesiredAccess e ObjectType corretos, como IoFileObjectType ou ExEventObjectType.
Se um identificador deve ser usado diretamente dentro de uma chamada, é melhor usar funções da variante Nt em vez de funções da variante Zw. Isso irá impor a verificação de parâmetros e manipular a validação pelo sistema operacional, uma vez que o modo anterior será UserMode e, portanto, não confiável. Observe que os parâmetros passados para funções Nt que são ponteiros podem falhar na validação se o modo anterior for UserMode. As rotinas Nt e Zw retornam um parâmetro IoStatusBlock com informações de erro que você deve verificar se há erros.
Os erros devem ser adequadamente corrigidos, bem como usando __try e __except conforme necessário. Muitos dos gerenciadores de cache (Cc), gerenciador de memória (Mm) e rotinas de biblioteca de tempo de execução do sistema de arquivos (FsRtl) geram uma exceção quando ocorre um erro.
Nenhum driver deve confiar em alças ou parâmetros passados de um aplicativo de modo de usuário sem tomar as precauções apropriadas.
Observe que, se a variante Nt for usada para abrir um arquivo, a variante Nt também deverá ser usada para fechar o arquivo.