Optimización de la inferencia en el dispositivo para Apple Silicon
Un motor local personalizado que mejora el rendimiento de preparación y decodificación.
Hybrid Compute en Apple silicon orquesta una tarea entre la inteligencia de vanguardia en la nube y un modelo local en el Mac. Los modelos en la nube se encargan de la investigación y el razonamiento, mientras que un modelo local trabaja con archivos y aplicaciones privadas en el Mac.
Para que esta división del trabajo se sienta fluida, la inferencia local debe mantener el ritmo del resto de la tarea. Eso requiere un motor que pueda procesar mensajes rápidamente y sostener una alta tasa de generación de tokens.
Lily, nuestro motor de inferencia local ligero, está diseñado específicamente para Apple Silicon y Qwen3.6-35B-A3B, con optimizaciones independientes para el rellenado (prefill) y la decodificación. Hay una demostración independiente disponible públicamente en GitHub.
Introducción
Una forma común de ejecutar LLMs en un Mac es con MLX, el marco de aprendizaje automático de código abierto de Apple para Apple silicon. Su biblioteca complementaria, MLX-LM, añade los componentes necesarios para cargar y generar texto con una amplia gama de modelos de lenguaje. Juntos, MLX y MLX-LM proporcionan una pila lista para usar y de propósito general para la inferencia de LLMs locales.
Qwen3.6-35B-A3B es un modelo híbrido disperso: utiliza enrutamiento de mezcla de expertos (MoE) y combina estados recurrentes de tamaño fijo con atención completa. Estas decisiones arquitectónicas reducen la cantidad de cómputo necesario, pero también generan cargas de trabajo irregulares. Los tokens se enrutan a diferentes pesos de expertos y los estados recurrentes son de naturaleza secuencial.
MLX-LM ya selecciona núcleos optimizados para las fases de inferencia y las formas de cargas de trabajo comunes, pero sus operaciones reutilizables deben admitir muchas arquitecturas de modelos. Un motor dedicado a Qwen puede especializarse a nivel de modelo y de tiempo de ejecución, coordinando núcleos, movimiento de datos y programación en torno a la estructura fija del modelo.
Lily implementa esta especialización de extremo a extremo en un único proceso. Un tiempo de ejecución en Rust carga el punto de control del modelo y gestiona el estado de la sesión (session state) y el bucle de generación; una API de finalización de chat compatible con OpenAI acepta solicitudes y transmite tokens, y los núcleos Metal personalizados ejecutan operaciones específicas de Qwen. Ni PyTorch ni MLX se encuentran en la ruta de ejecución.
Medimos el rendimiento de preparación y decodificación por separado. El rendimiento de preparación captura la rapidez con la que el motor procesa el mensaje; el rendimiento de decodificación captura la rapidez con la que genera los tokens de salida.
Comparamos Qwen3.6-35B-A3B en una sola MacBook Pro equipada con un M5 Max, una GPU de 40 núcleos y 128 GB de memoria unificada. En diez longitudes de prompt para prefill y diez longitudes de contexto para decode, de 256 a 128K tokens (K = 1,024), el motor promedia 1.22× el rendimiento de prefill de MLX-LM y 1.32× su rendimiento de decode. Con un prompt de 4K tokens y un contexto de decode de 4K tokens, el motor personalizado alcanza 5,749.9 tokens por segundo de prefill y 186.6 tokens por segundo de decode, frente a 4,737.5 y 140.9 de MLX-LM. En una sesión multitarjeta, estos ahorros de tiempo se acumulan con cada llamada adicional al modelo.
A continuación, explicamos cómo la arquitectura de Qwen crea oportunidades de optimización específicas del modelo en Apple silicon. Luego, revisamos los cambios consiguientes en la preparación y la decodificación. También abordamos en qué punto la optimización adicional deja de ser rentable, antes de concluir con una comparación de extremo a extremo frente a MLX-LM.
Oportunidades de optimización específicas de Qwen en Apple silicon
Qwen crea tres formas de carga de trabajo distintas
Qwen3.6-35B-A3B contiene 35 mil millones de parámetros, pero activa solo unos 3 mil millones para cada token. Un enrutador otorga puntuaciones a 256 subredes de expertos y selecciona ocho, además de un experto compartido que procesa cada token. Este diseño MoE disperso reduce el cómputo, pero produce un trabajo desigual: los expertos reciben diferentes números de tokens, y cada token requiere pesos de una combinación diferente de expertos.
Qwen también combina 10 capas de atención completa con 30 capas de Gated DeltaNet. Estos dos tipos de capas retienen información anterior de diferentes maneras.
Las capas de atención utilizan la atención de consultas agrupadas (GQA). Qwen tiene 16 cabezales de consulta y dos cabezales de clave-valor (KV), donde ocho cabezales de consulta comparten cada cabezal KV. Compartir hace que el caché KV sea más pequeño y permite que los datos en caché se reutilicen entre los cabezales de consulta. El caché aún almacena nuevas claves y valores para cada token, por lo que cada paso de decodificación lee más datos a medida que el contexto crece.
En su lugar, Gated DeltaNet comprime la información anterior en un estado recurrente de tamaño fijo. Una puerta aprendida controla cuánto del estado existente se debe retener, mientras que una actualización delta incorpora información del token actual. El modelo define estas actualizaciones de forma recurrente, por lo que cada token depende del estado producido por el token precedente. Sin embargo, durante la preparación, un motor puede evaluar el mismo cálculo de dos maneras. Puede escanear a través de los tokens directamente mientras transporta el estado hacia adelante, o reorganizar las actualizaciones en bloques que exponen más operaciones de matriz y paralelismo a nivel de tokens. Qué enfoque sea más rápido depende de las dimensiones del modelo, la carga de trabajo y el hardware.
En conjunto, estas estructuras crean tres patrones computacionales: grupos de expertos desiguales, atención sobre un caché en crecimiento y una recurrencia de tamaño fijo que se puede evaluar directamente o en bloques.
Apple silicon proporciona diferentes rutas para distintas cargas de trabajo
La preparación procesa muchas filas de activación de tokens de mensajes a la vez. La carga de trabajo local considerada aquí normalmente decodifica una solicitud a la vez (lote 1 / batch 1) y procesa una nueva fila por paso. Esta diferencia cambia la forma en que se utilizan los mismos pesos del modelo. La preparación puede reutilizar cada bloque de pesos en cientos o miles de filas. La decodificación en su mayor parte no puede hacerlo, ya que cada nuevo token requiere otra pasada a través de los pesos.
Apple silicon sitúa la CPU y la GPU detrás de la memoria unificada, un único grupo de memoria física accesible para ambas. Esto permite que el modelo permanezca residente sin mantener una copia de GPU separada, pero no hace que el movimiento de datos sea gratuito. La lectura de pesos y valores intermedios sigue consumiendo ancho de banda de memoria, mientras que los registros y otros almacenamientos en chip son más rápidos pero mucho más pequeños.
La GPU M5 también proporciona diferentes rutas de cómputo. Las capas lineales de la preparación utilizan la multiplicación general de matrices (GEMM), aplicando una matriz de pesos a muchas filas a la vez. Las operaciones GEMM compatibles pueden utilizar el acelerador neuronal (Neural Accelerator) en cada núcleo de GPU a través de operaciones de tensores de Metal 4 (Metal 4 tensor operations). En su lugar, la decodificación de lote 1 (batch-1) utiliza la multiplicación general de matriz-vector (GEMV), aplicando los mismos pesos a una sola fila. Con poca reutilización de pesos, la operación GEMV está limitada principalmente por el ancho de banda de la memoria y se adapta mejor a las unidades aritméticas lógicas (ALU) vectoriales de la GPU que a los aceleradores neuronales diseñados para operaciones de matrices con mayor reutilización de datos.
Estas rutas de ejecución no son exclusivas de Lily. MLX opera sobre la misma memoria unificada y selecciona núcleos de matrices y vectores optimizados según la forma de la carga de trabajo. La implementación de Qwen en MLX-LM ya agrupa el trabajo de los expertos, evalúa Gated DeltaNet con un núcleo Metal recurrente fusionado y utiliza la atención consciente de GQA. Estas capacidades son el punto de partida compartido para una inferencia eficiente de Qwen en Apple silicon.
Estrategia de optimización
El alcance más reducido de Lily le permite coordinar estas rutas de ejecución compartidas en torno a la arquitectura y las dimensiones exactas de Qwen. Utiliza rutas de GPU específicas para cada fase, asigna las cargas de trabajo de expertos, recurrentes y de atención de Qwen para minimizar el movimiento de datos, y selecciona núcleos y diseños a partir de la forma de la carga de trabajo medida. La estrategia consta de tres partes:
- Adaptar la ruta de la GPU a la fase de inferencia. Utilice la ejecución orientada a matrices cuando la preparación pueda reutilizar los pesos en muchas filas, y la ejecución orientada a vectores cuando la decodificación de lote 1 (batch-1) procese una fila a la vez.
- Mapear la estructura de Qwen en la GPU minimizando el movimiento de datos. Mantener los pesos comprimidos hasta que se utilicen, organizar el trabajo de los expertos enrutados sin volver a la CPU, retener el estado de Gated DeltaNet en el chip a través de su escaneo recurrente y reutilizar los datos KV compartidos por la atención de consultas agrupadas.
- Adaptar los núcleos a la forma de la carga de trabajo. Dentro de cada fase, seleccione los tamaños de los mosaicos (tiles), los diseños de ejecución y las rutas de atención a partir del recuento de filas disponible, la distribución de las filas entre los expertos, las dimensiones de la operación y la longitud actual del contexto.
Las siguientes secciones explican estas elecciones. En el caso de las optimizaciones evaluadas en pruebas de ablación emparejadas en un M5 Max, estimamos sus efectos comparando configuraciones de motor por lo demás idénticas que solo difieren en la optimización bajo estudio. Debido a que estos experimentos comparan versiones de nuestro motor consigo mismo, explican los mecanismos en lugar de descomponer los resultados finales frente a MLX-LM.
Preparación: reutilizar pesos y mantener el enrutamiento en la GPU
La preparación expone muchas filas de tokens a la vez, pero Qwen enruta esas filas de manera desigual entre los expertos y actualiza el estado recurrente a lo largo de la secuencia. Sus optimizaciones se dividen en tres grupos: organizar el trabajo de los expertos dispersos en torno a las filas enrutadas, mantener el escaneo de Gated DeltaNet en el chip y dividir los mensajes largos en fragmentos acotados.
Optimizar el cómputo de expertos dispersos
Descuantificar los pesos durante la multiplicación de matrices
El punto de control (checkpoint) Qwen3.6-35B-A3B utiliza cuantificación afín de 4 bits por grupos. Cada peso se almacena como un código entero de 4 bits, mientras que cada grupo de 64 pesos comparte una escala y un sesgo en bfloat16 utilizados para reconstruir sus valores. Esto reduce el modelo de 35 mil millones de parámetros de aproximadamente 70 GB de pesos en bfloat16 a un punto de control de 19.4 GB, lo que hace práctico mantener el modelo residente en el Mac.
La operación de tensores de Metal 4 utilizada para la multiplicación de matrices consume operandos bfloat16 en lugar de la representación empaquetada de 4 bits. Antes de la multiplicación, la GPU debe reconstruir los pesos en bfloat16. La operación GEMM agrupada y optimizada en Lily realiza esta conversión un pequeño mosaico (tile) de pesos a la vez y retiene el resultado en la memoria de grupos de hilos (threadgroup memory) del chip el tiempo suficiente para multiplicarlo por las filas de activación enrutadas. La acumulación utiliza coma flotante de 32 bits, y la salida se escribe en bfloat16. La matriz de pesos expandida completa nunca se crea en la memoria unificada.
En la prueba de ablación, la descuantificación se ejecuta como una operación separada: expande los pesos de 4 bits en una matriz bfloat16 en la memoria unificada, tras lo cual el núcleo de la matriz lee esa matriz de vuelta. Con un mensaje de 512 tokens, trasladar la descuantificación a la operación GEMM agrupada aumentó el rendimiento de la preparación de extremo a extremo en un 77.4 % al eliminar esta escritura y lectura intermedias.
Mantener el enrutamiento de expertos en la GPU
La operación GEMM agrupada requiere que las filas de activación asignadas a cada experto se almacenen juntas. Después de seleccionar ocho expertos por token, un histograma cuenta cuántas asignaciones recibió cada experto. Un escaneo de prefijos convierte esos recuentos en desplazamientos iniciales, un paso de dispersión (scatter) coloca las filas en sus grupos de expertos, y un mapa de bloques enumera los bloques de matriz de tamaño fijo que la operación GEMM agrupada debe procesar.
La ruta optimizada mantiene toda esta secuencia en un único búfer de comandos (command buffer), un lote ordenado de operaciones de GPU, para cada fragmento de mensaje. En su lugar, una prueba de ablación hace una pausa para que la CPU pueda inspeccionar los intermedios de enrutamiento y enviar la siguiente operación. Mantener el histograma y el escaneo de prefijos en la GPU añade dos núcleos, but elimina la sincronización entre CPU y GPU dentro de cada capa MoE.
Con un mensaje de 512 tokens, habilitar el enrutamiento residente en la GPU incrementó la preparación de extremo a extremo en un 89 %. Esto también muestra por qué el recuento de núcleos por sí solo puede ser engañoso: la ruta más rápida lanza más núcleos, pero nunca espera a la CPU dentro de la capa.
Ajustar el tamaño del mosaico (tile) a la carga de expertos
Con un mensaje de 2K tokens, enrutar cada token a ocho de los 256 expertos produce 16,384 asignaciones de token-experto, o un promedio de 64 filas de activación por experto. La distribución real es desigual: algunos expertos reciben muchas filas, mientras que otros reciben pocas.
La operación GEMM agrupada divide la salida de cada experto en mosaicos (tiles), que son pequeños bloques rectangulares de la salida de una multiplicación de matrices. A cada mosaico se le asigna un grupo de hilos (threadgroup) de la GPU. En las GPUs de Apple silicon, un grupo de hilos contiene uno o más grupos SIMD (simdgroups), cada uno de los cuales consta de 32 hilos que ejecutan instrucciones al mismo paso (lockstep).
Los mosaicos (tiles) más grandes reparten el costo de configuración entre más filas y exponen más trabajo en paralelo, pero una parte de un mosaico grande permanece inactiva cuando un experto recibe solo unas pocas filas. Por lo tanto, el tamaño del mosaico y el recuento de grupos SIMD (simdgroup) están acoplados.
Una prueba de ablación fija el mosaico (tile) en 16 filas. Frente a ese control, habilitar el mosaico de 32 filas con cuatro grupos SIMD (simdgroups) mejoró la preparación de extremo a extremo en un 13.2 % con 2K tokens.
Mantener el estado recurrente en el chip
Durante la preparación, cada capa de Gated DeltaNet escanea el mensaje en orden mientras transporta su estado recurrente hacia adelante. Con la residencia en registros desactivada, la prueba de ablación utiliza un escaneo por bloques. Con un mensaje de 2K tokens, esa ruta mueve 256 MiB (mebibytes) de estado por capa y detiene repetidamente los hilos cooperativos en barreras, puntos de sincronización donde todos los hilos participantes deben esperar unos a otros.
El estado recurrente es una matriz. El núcleo optimizado asigna cada columna a un grupo SIMD (simdgroup). El grupo SIMD divide la columna entre sus hilos, carga la columna en sus registros una sola vez y propaga el estado a lo largo de todo el escaneo. Los hilos intercambian resultados intermedios mediante operaciones de grupos SIMD en lugar de memoria de grupos de hilos (threadgroup memory), un almacenamiento en chip compartido entre un grupo de hilos. El estado completado se escribe de vuelta solo después del escaneo.
El estado y su puerta (gate) utilizan un formato de punto flotante de 32 bits porque los pequeños errores de redondeo se acumulan a través de actualizaciones secuenciales. Las activaciones de consulta y clave permanecen en bfloat16.
Con un mensaje de 2K tokens, habilitar el escaneo residente en registros mejoró la preparación de extremo a extremo en un 5.6 %. Las operaciones GEMM de expertos representaron aproximadamente el 90 % del tiempo de preparación. El escaneo secuencial no expone suficiente trabajo matricial reutilizable como para beneficiarse de los aceleradores neuronales (Neural Accelerators).
Limitar la memoria temporal mediante la fragmentación de mensajes
El tiempo de ejecución procesa un mensaje largo como una secuencia de fragmentos acotados en lugar de mantener datos temporales para cada token del mensaje en la memoria a la vez. Los pesos del modelo permanecen residentes en la memoria unificada, mientras que el estado recurrente y el caché KV transportan el contexto de un fragmento al siguiente. No se descarta ningún contexto anterior.
Sin fragmentación, las matrices de activación temporal crecen con el mensaje completo y compiten con los pesos del modelo, el estado recurrente y el caché KV por la memoria unificada. La fragmentación mantiene activos los valores temporales de un solo segmento a la vez, y luego libera o reutiliza ese almacenamiento antes de procesar el siguiente segmento. Esto limita la memoria de trabajo máxima y permite que el motor procese mensajes más largos sin cambiar la salida del modelo.
La preparación fragmentada (chunked prefill) es popular en muchos motores y es crucial para servir trayectorias largas de múltiples turnos en estos entornos con limitaciones de memoria. El tiempo total de preparación para las capas de atención sigue siendo cuadrático respecto a la longitud del mensaje, con cierta sobrecarga adicional debido a las cargas KV repetidas de fragmentos anteriores.
Decodificación: minimizar los bytes transferidos por token
La decodificación de lote 1 (batch-1) procesa una fila nueva a la vez. Con poca reutilización de pesos, su rendimiento depende principalmente de cuántos bytes mueve el motor para cada token. Los cambios de decodificación se dividen en cuatro grupos: optimizar la ruta de peso de una sola fila, mantener cada paso en la GPU, reducir el tráfico de estados y elementos intermedios, y leer el caché de atención de manera eficiente.
Optimizar la ruta de peso de una sola fila
MLX ya distribuye el trabajo de una sola fila a núcleos de matriz-vector especializados. Debido a que Lily no utiliza MLX, el tiempo de ejecución personalizado debe proporcionar la misma estrategia básica. Nuestro GEMV paralelo por filas está diseñado para una sola fila de activación. Un grupo SIMD coopera en el resultado mientras lee diferentes partes de la matriz de pesos en paralelo.
Mantener cada paso de decodificación en la GPU
Mantener la transferencia de tokens en la GPU
Cada paso de decodificación finaliza seleccionando el siguiente token; el siguiente paso comienza con ese token como entrada. Enviar la selección a la CPU y luego de vuelta a la GPU añade un punto de sincronización a cada token. En su lugar, nuestro tiempo de ejecución alterna entre dos búferes de comandos y dos ranuras de tokens residentes en la GPU. La GPU selecciona el token con la puntuación más alta y escribe su ID de token directamente en la ranura de entrada para el próximo paso de decodificación, mientras la CPU prepara el trabajo posterior.
Superponer trabajo independiente de la GPU
En un paso de decodificación con lote 1 registrado, generar un token lanzó 795 núcleos de GPU. Sus dependencias formaron 555 etapas secuenciales, lo que dejó algunos núcleos libres para ejecutarse de forma concurrente. Sin embargo, el modo de ejecución en serie de Metal ejecutó cada núcleo en orden.
La ruta de decodificación optimizada registra las dependencias de datos reales en una pasada de Metal concurrente. Los lanzamientos de núcleos independientes se pueden ejecutar al mismo tiempo cuando los recursos de la GPU lo permiten. Se inserta una barrera solo cuando un trabajo posterior requiere un resultado anterior.
Reducir el tráfico de estados y elementos intermedios
A menudo, los núcleos separados materializan un elemento intermedio: un núcleo escribe un resultado temporal en la memoria y el siguiente lee el resultado de vuelta. La ruta de decodificación optimizada fusiona cuatro cadenas: las dos proyecciones de entrada de expertos con su activación con puertas (gated activation); la proyección de salida de expertos con su puntuación de enrutamiento y el resultado del experto compartido; la preparación de consultas y claves antes de la atención; y la actualización recurrente con su normalización. Cada núcleo fusionado mantiene valores temporales en los registros en lugar de enviarlos a través de la memoria.
La fusión también acorta el gráfico de dependencias: cuando desaparece una escritura intermedia, también lo hace la barrera que protegía a su consumidor.
Leer el caché de atención de manera eficiente
Coalescer las lecturas del caché de atención
La atención lee claves y valores del caché KV durante cada paso de decodificación. En la prueba de ablación, los hilos de la GPU vecinos no siempre solicitan bytes vecinos, lo que obliga al sistema de memoria a atender más transacciones separadas. Habilitar las cargas coalescentes hace que los hilos adyacentes soliciten bytes adyacentes para que el hardware pueda combinar sus lecturas.
En la configuración bfloat16, la coalescencia aumentó el ancho de banda de claves de 33.8 a 47.9 GB/s, aumentó el ancho de banda de valores de 42.0 a 61.8 GB/s y mejoró la decodificación de extremo a extremo en un 2.1 % con un contexto de 3,840 tokens.
Empaquetar los cabezales de consulta para reutilizar las filas KV
La atención de consultas agrupadas (GQA) permite que ocho cabezales de consulta compartan un cabezal KV. En la prueba de ablación, cada cabezal de consulta se ejecuta en un grupo SIMD (simdgroup) separado, por lo que los ocho solicitan de manera independiente la misma fila KV en caché. El núcleo optimizado agrupa cuatro cabezales de consulta en un grupo de hilos (threadgroup), el cual carga cada fila KV una sola vez y la reutiliza en cuatro cálculos de atención. Un segundo grupo de hilos maneja los cuatro cabezales restantes.
Esta técnica, comúnmente llamada empaquetado de GQA, realiza la misma aritmética y produce bytes de salida idénticos al tiempo que reduce ocho solicitudes KV independientes a dos cargas compartidas. Frente a la prueba de ablación sin empaquetar, mejoró el rendimiento de la decodificación de extremo a extremo en un 23.8 % con un contexto de 32K tokens.
Cambiar los diseños de atención en contextos largos
Cada paso de decodificación en una capa de atención completa escanea el caché KV existente. Un diseño de bloques fijos divide dicho caché en partes iguales que la GPU puede procesar en paralelo. Su programación adicional no resulta útil cuando el caché es pequeño, pero el diseño de bloques fijos equilibra el trabajo de manera más uniforme a medida que el contexto crece.
Para este modelo, el tiempo de ejecución mantiene la ruta de atención general por debajo de los 32K tokens y utiliza la ruta de bloques fijos a partir de los 32K tokens. El cambio se aplica cuando cada cabezal tiene 256 valores y ocho cabezales de consulta comparten un cabezal KV; otras formas permanecen en la ruta general. Una prueba de ablación desgrana y deshabilita este cambio, utilizando siempre la ruta general. Habilitar la ruta de bloques fijos mejoró la decodificación de extremo a extremo en un 7.7 % a 32K, un 27.4 % a 64K y un 40.2 % a 128K.
Límites de una mayor optimización
Algunos cambios mejoraron una operación aislada, pero no mejoraron la inferencia de extremo a extremo.
La decodificación especulativa (speculative decoding), que utiliza un modelo más pequeño para proponer tokens para que el modelo completo los verifique, hizo que la decodificación de lote 1 fuera un 18 % más lenta. La verificación procesó grupos de dos a cinco filas, una forma ineficiente para este hardware, y las filas a menudo seleccionaron diferentes expertos, lo que aumentó la cantidad de datos de peso de expertos leídos. Reducir el vocabulario de salida del generador mejoró el rendimiento del generador entre un 4.7 % y un 5.1 %, pero no hizo que el bucle especulativo completo fuera más rápido. Este resultado es específico de la carga de trabajo: nuestro despliegue por lotes de Qwen en Blackwell utiliza la decodificación especulativa bajo diferentes condiciones.
Otros experimentos incluyeron reducir los lanzamientos de GPU, superponer fases completas, usar mosaicos de preparación más grandes, aplicar una fusión más amplia, acelerar el enrutador y combinar la proyección de salida con la selección de tokens. Ninguno mejoró el bucle de inferencia completo.
Las mediciones de los límites del hardware también mostraron poco margen restante en las operaciones principales de preparación y decodificación. Las operaciones GEMM y GEMV de MoE alcanzaron el 97.9 % y el 90.3 % de las tasas de lectura de pesos sostenidas más rápidas para sus patrones de acceso. Eliminar la aritmética del GEMV disperso cambió el rendimiento en solo un 0.2 %, lo que confirma que las lecturas de pesos, en lugar del cómputo, constituían el recurso limitante. De manera similar, la multiplicación de matrices de la preparación alcanzó el 93 % del límite teórico de matrices de forma aislada y entre el 80 % y el 86 % dentro de los modelos probados.
Rendimiento de extremo a extremo
La comparación de extremo a extremo carga bytes de puntos de control de 4 bits idénticos en ambos motores y ejecuta una solicitud a la vez en un M5 Max de 40 núcleos y 128 GB. Dentro de cada ronda, los dos motores se ejecutan en orden alterno para reducir el sesgo de la carga en segundo plano y los cambios en la temperatura del chip. Realizamos la comparación con la ruta de generación directa más rápida de MLX-LM, no con su servidor, por lo que la medición se centra en la ejecución del modelo en lugar de en la sobrecarga del servicio.
El análisis abarca diez longitudes de mensaje para la preparación y diez longitudes de contexto para la decodificación, desde 256 hasta 128K tokens. El rendimiento de preparación aumenta primero a medida que el motor reparte los costos de configuración fijos entre más tokens. La preparación alcanza su punto máximo alrededor de un mensaje de 4K tokens, y luego disminuye porque las diez capas de atención completa realizan más trabajo a medida que el mensaje crece. La decodificación permanece casi plana en contextos cortos y disminuye una vez que la lectura del caché KV en crecimiento adquiere relevancia. El motor personalizado es más rápido en cada longitud registrada.
Debido a que la ejecución especializada puede cambiar el orden de las operaciones de punto flotante, también comprobamos la consistencia numérica frente a MLX-LM. En una comparación con adiestramiento del profesor (teacher-forced), ambos modelos predijeron el siguiente token a partir del mismo prefijo de referencia en cada una de las 192 posiciones, evitando que las diferencias anteriores afectaran a las entradas posteriores. La perplejidad de Lily fue solo un 0.04 % mayor, y seleccionó el mismo token mejor clasificado en el 96.35 % de las posiciones probadas.
Diseñado para la plataforma local
Apple silicon no es una GPU de centro de datos más pequeña. Es una plataforma de inferencia local completa con sus propias características de hardware y software. La memoria unificada otorga a un solo nodo un límite muy elevado en cuanto a la cantidad de modelo y estado que puede contener. Los aceleradores neuronales M5 absorben el trabajo de matrices densas en la preparación. Las unidades aritméticas lógicas (ALU) vectoriales se encargan del remanente vinculado al ancho de banda y de baja reutilización en la decodificación.
Qwen añade más oportunidades de especialización: mantener el enrutamiento de expertos y el estado recurrente en la GPU, eliminar elementos intermedios innecesarios, superponer el trabajo independiente, reutilizar los datos KV compartidos y adaptar los núcleos a la forma de la carga de trabajo.
Con la optimización específica para el modelo y la plataforma, un Mac puede ejecutar un modelo disperso grande de manera eficiente. El trabajo futuro ampliará la cobertura entre modelos, chips y cargas de trabajo de servicio, y convertirá los mecanismos validados aquí en una configuración en una directiva de tiempo de ejecución más general.
El principio general es adaptar el motor tanto a la arquitectura del modelo como a las rutas específicas de cómputo y memoria del hardware. A medida que evolucionen los modelos de pesos abiertos de vanguardia y el hardware, la inferencia local de alto rendimiento dependerá cada vez más de motores adaptados a ambos en lugar de aquellos que abstraigan sus diferencias.
Citación
@online{perplexity2026OptimizingOnDeviceInferenceForAppleSilicon,
author = {{Perplexity} and Yibo Wu and Lequn Chen and Kevin Hu and Phi Hoang and Claire Beamer and Jeremy Yang and Denis Yarats},
title = {{Optimizing on-device inference for Apple Silicon}},
date = {2026-09-01},
url = {https://www.perplexity.ai/hub/blog/optimizing-on-device-inference-for-apple-silicon}
}