notícias

Mestre Karpathy: Fiz ataques de "injeção de SQL" em modelos grandes e não foi nada fácil

2024-08-16

한어Русский языкEnglishFrançaisIndonesianSanskrit日本語DeutschPortuguêsΕλληνικάespañolItalianoSuomalainenLatina



Relatório do coração da máquina

Editor: Du Wei, Zenan

Pode-se dizer que a segurança dos modelos grandes tem “muito espaço para melhorias”.

O guru da IA ​​Andrej Karpathy está aqui para popularizar novamente o conhecimento científico. Desta vez o tema é ".Usando tokens especiais para realizar ataques semelhantes a injeção de SQL no LLM」。

O chamado ataque de injeção SQL é uma tecnologia de ataque de rede. O invasor engana o banco de dados back-end para que execute instruções SQL maliciosas, inserindo-as nos campos de entrada do aplicativo. Esse tipo de ataque geralmente explora o tratamento inadequado da entrada do usuário pelo aplicativo, como não filtrar adequadamente ou escapar da entrada, permitindo que o invasor acesse, modifique ou até mesmo exclua dados do banco de dados.



Devido à crescente conscientização das pessoas sobre segurança, a injeção de SQL não deve ocorrer atualmente na maioria dos produtos de software.

Mas no mundo dos grandes modelos, tudo ainda está engatinhando. O tokenizer LLM é responsável por analisar tokens especiais (como <|endoftext|>, etc.) na string de entrada. Embora isso possa parecer conveniente, na melhor das hipóteses pode levar a erros de julgamento e, na pior das hipóteses, a uma vulnerabilidade de segurança do LLM, equivalente a um ataque de injeção de SQL.

É importante observar aqui: as strings de entrada do usuário são dados não confiáveis.

Na injeção de SQL, você pode usar o ataque "DROP TABLE" para quebrar códigos incorretos. O mesmo problema será encontrado no LLM. O código incorreto analisará o descritor de token especial da string no token especial real, confundindo a representação de entrada, fazendo com que o LLM não consiga distribuir modelos de bate-papo.

Abaixo está um exemplo usando o padrão atual do tokenizer huggingface Llama 3.

Como você pode ver, duas situações não intuitivas ocorrem ao mesmo tempo:

  • O token <|begin_of_text|> é (128000) adicionado à frente da sequência
  • O token <|end_of_text|> (128001) é analisado a partir da string e o token especial é inserido. Agora o texto (possivelmente do usuário) pode ser confundido com o protocolo de token e fazer com que o LLM não seja distribuído, resultando em uma saída indefinida.

Portanto, Karpathy recomenda sempre usar dois sinalizadores extras para operações de tokenização, desabilitando add_special_tokens=False e split_special_tokens=True, e adicionando você mesmo tokens especiais no código. Ele achou que a nomeação das duas opções seria um pouco confusa. Para o modelo de chat, você também pode usar o modelo de chat apply_chat_template.

Ao fazer o que foi dito acima, você pode obter algo mais correto para ver. Por exemplo, <|end_of_text|> agora é tratado como qualquer outra sequência de strings e dividido pelo tokenizer BPE subjacente como qualquer outra string.



Karpathy acredita que as chamadas para codificação e decodificação nunca devem analisar strings para lidar com tokens especiais, e precisamos descontinuar totalmente essa funcionalidade. Em vez disso, eles só devem ser adicionados de forma explícita e programática por meio de um caminho de código separado. No tiktoken, use sempre encode_ordinary em huggingface, é mais seguro usar a flag mencionada acima. Pelo menos fique atento a esse problema e sempre mantenha seus tokens visíveis e teste seu código.

Karpathy acredita que essas coisas são muito sutis e mal documentadas, e estima que cerca de 50% do código agora contém bugs causados ​​pelos problemas acima.

Até o ChatGPT, que passou por testes rigorosos antes de sair da fábrica, apresenta alguns problemas estranhos. Na melhor das hipóteses, apenas exclui o token; na pior, confunde o LLM de uma forma indefinida. Karpathy não sabia o que estava acontecendo nos bastidores, mas ChatGPT não conseguiu enviar a string <|endoftext|> repetidamente. Portanto, preste atenção extra aqui.



Assim que o artigo de Andrej Karpathy foi publicado, imediatamente suscitou discussão. Alguém perguntou: Então, quais medidas os desenvolvedores de LLM precisam tomar para melhorar a segurança?

Karpathy acha que é fácil dizer, apenas marque sempre as strings da maneira "normal", ou seja, sequências de bytes utf8. Isto é uma reminiscência do princípio do “privilégio mínimo” em segurança – essencialmente, ao limitar a funcionalidade ao que é absolutamente necessário, você minimiza a chance de consequências indesejadas.



Algumas pessoas também disseram: “Já estamos caminhando nessa direção”. Lucas Beyer, autor do modelo VLM PaliGemma e cientista do Google DeepMind, disse que melhoramos o mecanismo de segurança no novo código de trabalho, o que será um pouco problemático, especialmente ao suportar vários tokenizadores, mas no geral vale a pena. Também torna o código mais direto.



Alguns internautas também perguntaram: o que acontece se o código estiver correto, mas <|endoftext|> for inserido durante o treinamento dos dados?

Karpathy diz que se o código estiver correto nada acontecerá. Mas o problema é que grande parte do código pode não estar correta, o que pode destruir silenciosamente a visão de mundo do modelo grande.



O que você acha dos novos problemas descobertos por Karpathy?

Conteúdo de referência:

https://twitter.com/karpathy/status/1823418177197646104