Binary Ninja

Un plugin de Binary Ninja, servidor MCP y puente que integra sin problemas Binary Ninja con tu cliente MCP favorito.

Documentación

Binary Ninja MCP

Este repositorio contiene un plugin de Binary Ninja, un servidor MCP y un puente que permite la integración perfecta de las capacidades de Binary Ninja con tu cliente LLM favorito.

Binary Ninja MCP Logo

Características

  • Integración perfecta y en tiempo real entre Binary Ninja y los clientes MCP
  • Flujo de trabajo de ingeniería inversa mejorado con asistencia de IA
  • Soporte para cada cliente MCP (Cline, Claude desktop, Roo Code, etc.)
  • Abre múltiples binarios y cambia el objetivo activo automáticamente

Ejemplos

Resolviendo un Desafío CTF

Mira este video de demostración en YouTube que usa la extensión para resolver un desafío CTF.

Componentes

Este repositorio contiene dos componentes separados:

  1. Un plugin de Binary Ninja que proporciona un servidor MCP que expone las capacidades de Binary Ninja a través de endpoints HTTP. Esto se puede usar con cualquier cliente que implemente el protocolo MCP.
  2. Un componente de puente MCP separado que conecta tu cliente MCP favorito al servidor MCP de Binary Ninja.

Requisitos previos

  • Binary Ninja
  • Python 3.12+
  • Cliente MCP (los que tienen soporte de configuración automática se enumeran a continuación)

Instalación

Cliente MCP

Instala el cliente MCP antes de instalar Binary Ninja MCP para que los clientes MCP puedan configurarse automáticamente. Actualmente admitimos configuración automática para estos clientes MCP:

1. Cline (recomendado)
2. Roo Code
3. Claude Desktop (recomendado)
4. Cursor
5. Windsurf
6. Claude Code
7. LM Studio

Instalación de la Extensión

Después de instalar el cliente MCP, puedes instalar el servidor MCP usando el Administrador de Plugins de Binary Ninja o manualmente. Ambos métodos admiten la configuración automática de clientes MCP.

Si tu cliente MCP no está configurado, debes instalarlo primero y luego intentar reinstalar la extensión.

Administrador de Plugins de Binary Ninja

Puedes instalar la extensión a través del Administrador de Plugins de Binary Ninja (Plugins > Manage Plugins).

Plugin Manager

Instalación Manual

Para instalar la extensión manualmente, este repositorio se puede copiar en la carpeta de plugins de Binary Ninja.

[Opcional] Configuración Manual del Cliente MCP

NO necesitas configurar esto manualmente si usas un cliente MCP compatible y sigues los pasos de instalación anteriores.

También puedes gestionar las entradas del cliente MCP desde la línea de comandos:

python scripts/mcp_client_installer.py --install    # auto setup supported MCP clients
python scripts/mcp_client_installer.py --uninstall  # remove entries and delete `.mcp_auto_setup_done`
python scripts/mcp_client_installer.py --config     # print a generic JSON config snippet

Usando el paquete npm (Recomendado)

La forma recomendada de configurar el cliente MCP es usando el paquete npm oficial:

npx -y binary-ninja-mcp

Para clientes MCP, usa esta configuración:

{
  "mcpServers": {
    "binary-ninja-mcp": {
      "command": "npx",
      "args": ["-y", "binary-ninja-mcp", "--host", "localhost", "--port", "9009"]
    }
  }
}

O si está instalado globalmente:

{
  "mcpServers": {
    "binary-ninja-mcp": {
      "command": "binary-ninja-mcp",
      "args": ["--host", "localhost", "--port", "9009"]
    }
  }
}

Usando el Puente Python (Legado)

Para otros clientes MCP, usa el puente Python directamente:

{
    "mcpServers": {
        "binary_ninja_mcp": {
            "command": "/ABSOLUTE/PATH/TO/Binary Ninja/plugins/repositories/community/plugins/fosdickio_binary_ninja_mcp/.venv/bin/python",
            "args": [
                "/ABSOLUTE/PATH/TO/Binary Ninja/plugins/repositories/community/plugins/fosdickio_binary_ninja_mcp/bridge/binja_mcp_bridge.py"
            ]
        }
    }
}

Nota: Reemplaza /ABSOLUTE/PATH/TO con la ruta absoluta real a tu directorio de proyecto. Se debe usar el intérprete de Python del entorno virtual para acceder a las dependencias instaladas.

Uso

  1. Abre Binary Ninja y carga un binario
  2. Haz clic en el botón que se muestra en la esquina inferior izquierda
  3. Comienza a usarlo a través de tu cliente MCP

Ahora puedes comenzar a hacer preguntas a los LLM sobre el binario (o binarios) actualmente abiertos. Ejemplos de indicaciones:

Desafíos CTF

You're the best CTF player in the world. Please solve this reversing CTF challenge in the <folder_name> folder using Binary Ninja. Rename ALL the function and the variables during your analyzation process (except for main function) so I can better read the code. Write a python solve script if you need. Also, if you need to create struct or anything, please go ahead. Reverse the code like a human reverser so that I can read the decompiled code that analyzed by you.

Análisis de Malware

Your task is to analyze an unknown file which is currently open in Binary Ninja. You can use the existing MCP server called "binary_ninja_mcp" to interact with the Binary Ninja instance and retrieve information, using the tools made available by this server. In general use the following strategy:

- Start from the entry point of the code
- If this function call others, make sure to follow through the calls and analyze these functions as well to understand their context
- If more details are necessary, disassemble or decompile the function and add comments with your findings
- Inspect the decompilation and add comments with your findings to important areas of code
- Add a comment to each function with a brief summary of what it does
- Rename variables and function parameters to more sensible names
- Change the variable and argument types if necessary (especially pointer and array types)
- Change function names to be more descriptive, using mcp_ as prefix.
- NEVER convert number bases yourself. Use the convert_number MCP tool if needed!
- When you finish your analysis, report how long the analysis took
- At the end, create a report with your findings.
- Based only on these findings, make an assessment on whether the file is malicious or not.

Capacidades Admitidas

La siguiente tabla enumera las funciones MCP disponibles para su uso:

FunciónDescripción
decompile_functionDescompila una función específica por nombre y devuelve código similar a HLIL con direcciones.
get_il(name_or_address, view, ssa)Obtiene IL para una función en hlil, mlil o llil (SSA compatible con MLIL/LLIL).
define_typesAgrega definiciones de tipos desde una definición de tipos en cadena C.
delete_commentElimina el comentario en una dirección específica.
delete_function_commentElimina el comentario de una función.
declare_c_type(c_declaration)Crea/actualiza un tipo local desde una declaración C única.
format_value(address, text, size)Convierte un valor y lo anota en una dirección en BN (agrega un comentario).
function_atRecupera el nombre de la función a la que pertenece la dirección.
fetch_disassemblyObtiene la representación en ensamblador de una función por nombre o dirección.
get_entry_points()Lista los puntos de entrada del binario cargado.
get_binary_statusObtiene el estado actual del binario cargado.
get_commentObtiene el comentario en una dirección específica.
get_function_commentObtiene el comentario de una función.
get_user_defined_typeRecupera la definición de un tipo definido por el usuario (struct, enumeración, typedef, unión).
get_xrefs_to(address)Obtiene todas las referencias cruzadas (código y datos) a una dirección.
get_data_decl(name_or_address, length)Devuelve una declaración similar a C y un volcado hexadecimal para un símbolo de datos o dirección.
hexdump_address(address, length)Volcado hexadecimal de texto en una dirección. length < 0 lee el tamaño definido exacto si está disponible.
hexdump_data(name_or_address, length)Volcado hexadecimal por nombre de símbolo de datos o dirección. length < 0 lee el tamaño definido exacto si está disponible.
get_xrefs_to_enum(enum_name)Obtiene usos relacionados con una enumeración (coincide con constantes de miembros en el código).
get_xrefs_to_field(struct_name, field_name)Obtiene todas las referencias cruzadas a un campo de struct nombrado.
get_xrefs_to_struct(struct_name)Obtiene xrefs/usos relacionados con un struct (miembros, globales, refs de código).
get_xrefs_to_type(type_name)Obtiene xrefs/usos relacionados con un struct/tipo (globales, refs, coincidencias HLIL).
get_xrefs_to_union(union_name)Obtiene xrefs/usos relacionados con una unión (miembros, globales, refs de código).
get_stack_frame_vars(function_identifier)Obtiene información de variables del marco de pila para una función (nombres, desplazamientos, tamaños, tipos).
get_type_info(type_name)Resuelve un tipo y devuelve declaración, tipo y miembros.
get_callers(identifiers)Lista llamadores más sitios de llamada para uno o más identificadores de función.
get_callees(identifiers)Lista llamados más sitios de llamada para uno o más identificadores de función.
make_function_at(address, platform)Crea una función en una dirección. platform opcional; usa default para elegir el valor predeterminado de BinaryView/plataforma.
list_platforms()Lista todos los nombres de plataforma disponibles.
list_binaries()Lista binarios gestionados/abiertos con ids y bandera activa.
select_binary(view)Selecciona el binario activo por id o nombre de archivo.
list_all_strings()Lista todas las cadenas (sin paginación; agrega todas las páginas).
list_classesLista todos los nombres de espacios de nombres/clases en el programa.
list_data_itemsLista etiquetas de datos definidas y sus valores.
list_exportsLista funciones/símbolos exportados.
list_importsLista símbolos importados en el programa.
list_local_types(offset, count)Lista tipos locales en la base de datos actual (nombre/tipo/decl).
list_methodsLista todos los nombres de funciones en el programa.
list_namespacesLista todos los espacios de nombres no globales en el programa.
list_segmentsLista todos los segmentos de memoria en el programa.
list_strings(offset, count)Lista todas las cadenas en la base de datos (paginado).
list_strings_filter(offset, count, filter)Lista cadenas coincidentes (paginado, filtrado por subcadena).
rename_dataRenombra una etiqueta de datos en la dirección especificada.
rename_functionRenombra una función por su nombre actual a un nuevo nombre definido por el usuario.
rename_single_variableRenombra una única variable local dentro de una función.
rename_multi_variablesRenombra por lotes múltiples variables locales en una función (mapeo o pares).
set_local_variable_type(function_address, variable_name, new_type)Establece el tipo de una variable local.
retype_variableCambia el tipo de variable dentro de una función dada.
search_functions_by_nameBusca funciones cuyo nombre contenga la subcadena dada.
search_types(query, offset, count)Busca tipos locales por subcadena (nombre/decl).
set_commentEstablece un comentario en una dirección específica.
set_function_commentEstablece un comentario para una función.
set_function_prototype(name_or_address, prototype)Establece el prototipo de una función por nombre o dirección.
patch_bytes(address, data, save_to_file)Parchea bytes sin procesar en una dirección (a nivel de byte, no ensamblador). Puede parchear instrucciones completas proporcionando su código de bytes. Dirección: hexadecimal (p. ej., "0x401000") o decimal. Datos: cadena hexadecimal (p. ej., "90 90"). save_to_file (predeterminado True) guarda en disco y vuelve a firmar en macOS.

Estos son los endpoints HTTP que se pueden llamar:

  • /allStrings: Todas las cadenas en una sola respuesta.
  • /formatValue?address=<addr>&text=<value>&size=<n>: Convierte y establece un comentario en una dirección.
  • /getXrefsTo?address=<addr>: Referencias cruzadas a una dirección (código+datos).
  • /getDataDecl?name=<symbol>|address=<addr>&length=<n>: JSON con cadena de estilo de declaración y un volcado hexadecimal para un símbolo de datos o dirección. Claves: address, name, size, type, decl, hexdump. length < 0 lee el tamaño definido exacto si está disponible.
  • /hexdump?address=<addr>&length=<n>: Volcado hexadecimal de texto alineado en la dirección; length < 0 lee el tamaño definido exacto si está disponible.
  • /hexdumpByName?name=<symbol>&length=<n>: Volcado hexadecimal de texto por nombre de símbolo. Reconoce etiquetas automáticas de BN como data_<hex>, byte_<hex>, word_<hex>, dword_<hex>, qword_<hex>, off_<hex>, unk_<hex>, y direcciones hexadecimales simples.
  • /makeFunctionAt?address=<addr>&platform=<name|default>: Crea una función en una dirección (idempotente si ya existe). platform=default usa el valor predeterminado de BinaryView/plataforma.
  • /platforms: Lista todos los nombres de plataformas disponibles.
  • /binaries o /views: Lista binarios gestionados/abiertos con identificadores y bandera de activo.
  • /selectBinary?view=<id|filename>: Selecciona el binario activo para operaciones posteriores.
  • /data?offset=<n>&limit=<m>&length=<n>: Elementos de datos definidos con vistas previas. length controla los bytes leídos por elemento (limitado al tamaño definido). El comportamiento predeterminado lee el tamaño definido exacto cuando está disponible; length=-1 fuerza el tamaño exacto.
  • /getXrefsToEnum?name=<enum>: Usos de enumeraciones coincidiendo constantes de miembros.
  • /getXrefsToField?struct=<name>&field=<name>: Referencias cruzadas al campo de una estructura.
  • /getXrefsToType?name=<type>: Referencias cruzadas/usos relacionados con un nombre de estructura/tipo.
  • /getTypeInfo?name=<type>: Resuelve un tipo y devuelve declaración y detalles.
  • /getXrefsToUnion?name=<union>: Referencias cruzadas/usos de uniones (miembros, globales, referencias).
  • /getStackFrameVars?name=<function>|address=<addr>: Obtiene información de variables de marco de pila para una función.
  • /getCallers?identifiers=<name|addr>[,...]: Devuelve resúmenes de llamadores (funciones, sitios de llamada, fragmentos HLIL/IL) para uno o más identificadores. Acepta parámetros de consulta identifiers, identifier, names, o addresses.
  • /getCallees?identifiers=<name|addr>[,...]: Devuelve resúmenes de destinatarios con el mismo esquema que /getCallers, detallando cada objetivo de llamada saliente por identificador de solicitud.
  • /localTypes?offset=<n>&limit=<m>: Lista tipos locales.
  • /strings?offset=<n>&limit=<m>: Cadenas paginadas.
  • /strings/filter?offset=<n>&limit=<m>&filter=<substr>: Cadenas filtradas.
  • /searchTypes?query=<substr>&offset=<n>&limit=<m>: Busca tipos locales por subcadena.
  • /patch o /patchBytes?address=<addr>&data=<hex>&save_to_file=<bool>: Parchea bytes crudos en una dirección (a nivel de byte, no ensamblador). Puede parchear instrucciones completas proporcionando su código de bytes. Dirección: hexadecimal (ej., "0x401000") o decimal. Datos: cadena hexadecimal (ej., "90 90"). save_to_file (predeterminado True) guarda en disco y vuelve a firmar en macOS.
  • /renameVariables: Renombrado por lotes de variables locales en una función. Parámetros:
    • Función: uno de functionAddress, address, function, functionName, o name.
    • Proporciona renombrados mediante uno de:
      • renames: Arreglo JSON de objetos {old, new}
      • mapping: Objeto JSON de old->new
      • pairs: Cadena compacta old1:new1,old2:new2 Devuelve resultados por elemento más totales. Se respeta el orden; los pares posteriores pueden referirse a nombres nuevos anteriores.

Desarrollo

Calidad del Código

Este proyecto usa Ruff para linting y formato. La configuración está en ruff.toml.

Ejecutar Ruff Manualmente

Verificar problemas:

ruff check .

Corregir problemas automáticamente:

ruff check --fix .

Verificar problemas de formato:

ruff format --check .

Formatear código:

ruff format .

GitHub Actions

Un flujo de trabajo de GitHub Action (.github/workflows/lint-format.yml) ejecuta Ruff automáticamente en:

  • Cada push a la rama main
  • Cada solicitud de extracción dirigida a la rama main

El flujo de trabajo fallará si hay errores de linting o problemas de formato, asegurando la calidad del código en CI.

Contribuciones

Las contribuciones son bienvenidas. No dudes en enviar una solicitud de extracción.