Mantenha tudo organizado com as coleções Salve e categorize o conteúdo com base nas suas preferências.

Visão geral da linguagem YARA-L 2.0

O YARA-L 2.0 é uma linguagem de computador usada para criar regras de pesquisa em dados de registro corporativos à medida que eles são ingeridos na sua conta do Chronicle. A sintaxe YARA-L é derivada da linguagem YARA desenvolvida pelo VirusTotal. A linguagem funciona em conjunto com o Chronicle Detection Engine (Mecanismo de detecção do Chronicle) e permite buscar ameaças e outros eventos em grandes volumes de dados. Veja também Sintaxe de idiomas YARA-L 2.0

Regras de exemplo de YARA-L 2.0

Os exemplos a seguir mostram regras escritas em YARA-L 2.0. Cada um demonstra como correlacionar eventos dentro da linguagem de regras.

Logins de diferentes cidades

A regra a seguir pesquisa usuários que fizeram login na sua empresa em duas ou mais cidades em menos de cinco minutos:

rule DifferentCityLogin {
  meta:

  events:
    $udm.metadata.event_type = "USER_LOGIN"
    $udm.principal.user.userid = $user
    $udm.principal.location.city = $city

  match:
    $user over 5m

  condition:
    $udm and #city > 1
}

Variável de correspondência: $user

Variável de evento:$udm

Variável do marcador: $city e $user

Veja a seguir como essa regra funciona:

  • Agrupa eventos com nome de usuário ($user) e o retorna ($user) quando uma correspondência é encontrada.
  • O período é de 5 minutos, o que significa que apenas os eventos com menos de 5 minutos de distância estão correlacionados.
  • Pesquisando um grupo de eventos ($udm) com o tipo de evento USER_LOGIN.
  • Para esse grupo de eventos, a regra chama o ID do usuário como $user e a cidade de login como $city.
  • Retorna uma correspondência se o número distinto de valores $city for maior que um no grupo de eventos ($udm) no intervalo de tempo de cinco minutos.

Criação e exclusão rápidas de usuários

A regra a seguir pesquisa os usuários que foram criados e excluídos em até quatro horas:

rule UserCreationThenDeletion {
  meta:

  events:
    $create.target.user.userid = $user
    $create.metadata.event_type = "USER_CREATION"

    $delete.target.user.userid = $user
    $delete.metadata.event_type = "USER_DELETION"

    $create.metadata.event_timestamp.seconds <=
       $delete.metadata.event_timestamp.seconds

  match:
    $user over 4h

  condition:
    $create and $delete
}

Variáveis de evento:$create e $delete

Variável de correspondência: $user

Variável do marcador: N/A

Veja a seguir como essa regra funciona:

  • Agrupa eventos com nome de usuário ($user) e o retorna ($user) quando uma correspondência é encontrada.
  • A janela de tempo é de 4 horas, o que significa que apenas os eventos separados por menos de 4 horas são correlacionados.
  • Pesquisa por dois grupos de eventos ($create e $delete, em que $create é equivalente a #create >= 1).
  • $create corresponde a eventos USER_CREATION e chama o ID do usuário como $user.
  • $user é usado para unir os dois grupos de eventos.
  • $delete corresponde a eventos USER_DELETION e chama o ID do usuário como $user. Essa regra procura uma correspondência em que o identificador do usuário nos dois grupos de eventos é o mesmo.
  • Essa regra procura casos em que o evento de $delete ocorre depois do evento de $create, retornando uma correspondência quando descoberto.

Regra de evento único

As regras de evento único são correlacionadas com um único evento. Uma regra de evento única pode ser:

  • Qualquer regra sem uma seção de correspondência.
  • Regra com uma seção de correspondência e uma seção de condição verificando apenas a existência de um evento (por exemplo, "$e", "#e > 0", "#e >= 1", "1 <= #e", "0 < #e&#;

Por exemplo, a seguinte regra simplesmente pesquisa um evento de login do usuário e retorna o primeiro evento encontrado nos dados corporativos armazenados na sua conta do Chronicle:

rule SingleEventRule {
  meta:
    author = "noone@altostrat.com"

  events:
    $e.metadata.event_type = "USER_LOGIN"

  condition:
    $e
}

Veja outro exemplo de uma única regra de evento com uma seção de correspondência. Esta regra procura um usuário que fez login pelo menos uma vez em menos de cinco minutos. Ela verifica a existência simples de um evento de login do usuário.

rule SingleEventRule {
  meta:
    author = "noone@google.com"
    description = "windowed single event example rule"

  events:
    $e.metadata.event_type = "USER_LOGIN"
    $e.principal.user.userid = $user

  match:
    $user over 5m

  condition:
    #e > 0
}

Regra de vários eventos

Use várias regras de eventos para agrupar muitos eventos em uma janela de tempo especificada e tentar encontrar correlações entre eventos. Uma regra típica de vários eventos terá o seguinte:

  • Seção de correspondência que especifica o período em que os eventos precisam ser agrupados.
  • Seção de condição especificando a condição que deve acionar a detecção e verificar a existência de vários eventos.

Por exemplo, a seguinte regra pesquisa um usuário que fez login pelo menos 10 vezes em menos de 10 minutos:

rule MultiEventRule {
  meta:
    author = "noone@altostrat.com"

  events:
    $e.metadata.event_type = "USER_LOGIN"
    $e.principal.user.userid = $user

  match:
    $user over 10m

  condition:
    #e >= 10
}

Evento único dentro do intervalo de endereços IP

O exemplo a seguir mostra uma única regra de evento que pesquisa uma correspondência entre dois usuários específicos e um intervalo específico de endereços IP:

rule OrsAndNetworkRange {
  meta:
    author = "noone@altostrat.com"

  events:
    // Checks CIDR ranges.
    net.ip_in_range_cidr($e.principal.ip, "203.0.113.0/24")

    // Detection when the hostname field matches either value using or.
    $e.principal.hostname = /pbateman/ or $e.principal.hostname = /sspade/

  condition:
    $e
}

todo e qualquer exemplo de regra

A regra a seguir pesquisa eventos de login em que todos os endereços IP de origem não correspondem a um endereço IP conhecido como seguro em um período de cinco minutos.

rule SuspiciousIPLogins {
  meta:
    author = "noone@google.com"

  events:
    $e.metadata.event_type = "USER_LOGIN"

    // Detects if all source IP addresses in an event do not match "100.97.16.0"
    // For example, if an event has source IP addresses
    // ["100.97.16.1", "100.97.16.2", "100.97.16.3"],
    // it will be detected since "100.97.16.1", "100.97.16.2",
    // and "100.97.16.3" all do not match "100.97.16.0".

    all $e.principal.ip != "100.97.16.0"

    // Assigns placeholder variable $ip to the $e.principal.ip repeated field.
    // There will be one detection per source IP address.
    // For example, if an event has source IP addresses
    // ["100.97.16.1", "100.97.16.2", "100.97.16.3"],
    // there will be one detection per address.

    $e.principal.ip = $ip

  match:
    $ip over 5m

  condition:
    $e
}

Expressões regulares em uma regra

O exemplo de expressão regular YARA-L 2.0 a seguir pesquisa eventos com e-mails recebidos do domínio altostrat.com. Como nocase foi adicionado à comparação da variável $host regex e da função regex, essas duas comparações não diferenciam maiúsculas de minúsculas.

rule RegexRuleExample {
  meta:
    author = "noone@altostrat.com"

  events:
    $e.principal.hostname = $host
    $host = /.*HoSt.*/ nocase
    re.regex($e.network.email.from, `.*altostrat\.com`) nocase

  match:
    $host over 10m

  condition:
    #e > 10
}

Exemplo de regra de janela deslizante

O exemplo de janela deslizante YARA-L 2.0 a seguir pesquisa a ausência de eventos firewall_2 após eventos firewall_1. A palavra-chave after é usada com a variável de evento dinâmico $e1 para especificar que apenas janelas de 10 minutos após cada evento firewall_1 precisam ser verificadas no evento correspondente.

rule SlidingWindowRuleExample {
  meta:
    author = "noone@google.com"

  events:
    $e1.metadata.product_name = "firewall_1"
    $e1.principal.hostname = $host

    $e2.metadata.product_name = "firewall_2"
    $e2.principal.hostname = $host

  match:
    $host over 10m after $e1

  condition:
    $e1 and !$e2
}

Exemplo de exclusão de valor zero

Se a regra não especificar opções de allow_zero_values, nenhum valor será retornado dos valores da variável de correspondência. No entanto, para outros campos de evento referenciados, os valores zero não são excluídos, a menos que você especifique explicitamente essas condições. Veja mais detalhes.

rule ExcludeZeroValues {
  meta:
    author = "noone@google.com"

  events:
    $e1.metadata.event_type = "NETWORK_DNS"
    $e1.principal.hostname = $hostname

    // $e1.principal.user.userid may be empty string.
    $e1.principal.user.userid != "Guest"

    $e2.metadata.event_type = "NETWORK_HTTP"
    $e2.principal.hostname = $hostname

    // $e2.target.asset_id cannot be empty string as explicitly specified.
    $e2.target.asset_id != ""

  match:
    // $hostname cannot be empty string.
    $hostname over 1h

  condition:
    $e1 and $e2
}

Exemplo de regra com seção de resultados

É possível adicionar a seção opcional outcome na regra YARA-L 2.0 para extrair mais informações de cada detecção. Na seção de condições, também é possível especificar condicionais em variáveis de resultado.

Para ver mais informações, consulte os seguintes tópicos:

Regra de vários eventos com seção de resultados:

rule OutcomeRuleMultiEvent {
    meta:
      author = "noone@google.com"
    events:
      $u.udm.principal.hostname = $hostname
      $asset_context.graph.entity.hostname = $hostname

      $severity = $asset_context.graph.entity.asset.vulnerabilities.severity

    match:
      $hostname over 5m

    outcome:
      $risk_score =
        max(
            100
          + if($hostname = "my-hostname", 100, 50)
          + if($severity = "HIGH", 10)
          + if($severity = "MEDIUM", 5)
          + if($severity = "LOW", 1)
        )

      $asset_id_list =
        array(
          if($u.principal.asset_id = "",
             "Empty asset id",
             $u.principal.asset_id
          )
        )

      $asset_id_distinct_list = array_distinct($u.principal.asset_id)

      $asset_id_count = count($u.principal.asset_id)

      $asset_id_distinct_count = count_distinct($u.principal.asset_id)

    condition:
      $u and $asset_context and $risk_score > 50 and not arrays.contains($asset_id_list, "id_1234")
}

Regra de evento único com seção de resultado:

rule OutcomeRuleSingleEvent {
    meta:
        author = "noone@google.com"
    events:
        $u.metadata.event_type = "FILE_COPY"
        $u.principal.file.size = $file_size
        $u.principal.hostname = $hostname

    outcome:
        $suspicious_host = $hostname
        $severity_tag = if($file_size > 1024, "SEVERE", "MODERATE")

    condition:
        $u
}

Refatorar uma regra de resultado de vários eventos em uma regra de resultado de evento único.

Você pode usar a seção de resultados para regras de evento único (regras sem uma configuração de correspondência) e regras de vários eventos (regras com uma seção de correspondência). Se você já tiver projetado uma regra para ser de vários eventos para que possa usar a seção de resultados, é possível refatorar essas regras excluindo a seção de correspondência para melhorar o desempenho. Como sua regra não tem mais uma seção de correspondência que aplique o agrupamento, você pode receber mais detecções. Essa refatoração só é possível para regras que usam uma variável de evento, conforme mostrado no exemplo a seguir.

Regra de resultado de vários eventos que usa apenas uma variável de evento (um bom candidato para uma refatoração):

rule OutcomeMultiEventPreRefactor {
    meta:
      author = "noone@google.com"
      description = "Outcome refactor rule, before the refactor"

    events:
      $u.udm.principal.hostname = $hostname

    match:
      $hostname over 5m

    outcome:
      $risk_score = max(if($hostname = "my-hostname", 100, 50))

    condition:
      $u
}

É possível refatorar a regra excluindo a seção de correspondência. Também é necessário remover o agregado na seção de resultados, já que a regra agora será de evento único. Consulte nossa documentação sobre agregações de resultados para mais informações sobre agregações.

rule OutcomeSingleEventPostRefactor {
    meta:
      author = "noone@google.com"
      description = "Outcome refactor rule, after the refactor"

    events:
      $u.udm.principal.hostname = $hostname

    // We deleted the match section.

    outcome:
      // We removed the max() aggregate.
      $risk_score = if($hostname = "my-hostname", 100, 50)

    condition:
      $u
}

Exemplo de função para regra de marcador

Você pode atribuir uma variável de marcador ao resultado de uma chamada de função e usar a variável em outras seções da regra, como as seções de correspondência, de resultado ou de condição. Veja o exemplo a seguir:

rule FunctionToPlaceholderRule {
    meta:
      author = "noone@google.com"
      description = "Rule that uses function to placeholder assignments"

    events:
        $u.metadata.event_type = "EMAIL_TRANSACTION"

        // Use function-placeholder assignment to extract the
        // address from an email.
        // address@website.com -> address
        $email_to_address_only = re.capture($u.network.email.from , "(.*)@")

        // Use function-placeholder assignment to normalize an email:
        // uid@??? -> uid@company.com
        $email_from_normalized = strings.concat(
            re.capture($u.network.email.from , "(.*)@"),
            "@company.com"
        )

        // Use function-placeholder assignment to get the day of the week of the event.
        // 1 = Sunday, 7 = Saturday.
        $dayofweek = timestamp.get_day_of_week($u.metadata.event_timestamp.seconds)

    match:
        // Use placeholder (from function-placeholder assignment) in match section.
        // Group by the normalized from email, and expose it in the detection.
        $email_from_normalized over 5m

    outcome:
        // Use placeholder (from function-placeholder assignment) in outcome section.
        // Assign more risk if the event happened on weekend.
        $risk_score = max(
            if($dayofweek = 1, 10, 0) +
            if($dayofweek = 7, 10, 0)
        )

    condition:
        // Use placeholder (from function-placeholder assignment) in condition section.
        // Match if an email was sent to multiple addresses.
        #email_to_address_only > 1
}

Regra de exemplo com condicionais de resultado

Na seção de condições, é possível usar as variáveis de resultado que foram definidas na seção de resultados. No exemplo a seguir, demonstramos como filtrar pontuações de risco para reduzir ruído em detecções usando condicionais de resultados.

rule OutcomeConditionalRule {
    meta:
        author = "noone@google.com"
        description = "Rule that uses outcome conditionals"

    events:
        $u.metadata.event_type = "FILE_COPY"
        $u.principal.file.size = $file_size
        $u.principal.hostname = $hostname

        // 1 = Sunday, 7 = Saturday.
        $dayofweek = timestamp.get_day_of_week($u.metadata.collected_timestamp.seconds)

    outcome:
        $risk_score =
            if($file_size > 500*1024*1024, 2) + // Files 500MB are moderately risky
            if($file_size > 1024*1024*1024, 3) + // Files over 1G get assigned extra risk

            if($dayofweek=1 or $dayofweek=7, 4) + // Events from the weekend are suspicious

            if($hostname = /highly-privileged/, 5) // Check for files from highly privileged devices

    condition:
        $u and $risk_score >= 10
}