RTX 3090 하나에 코딩 에이전트 4개 구동: Qwen3.8-27B용 커스텀 CUDA 엔진으로 총 약 290 tok/s 달성
요약
로컬 코딩 에이전트 OpenJet은 Qwen3.8-27B를 위한 커스텀 CUDA 엔진을 개발하여 단일 GPU에서 여러 에이전트를 병렬 구동할 수 있게 되었습니다. 이 엔진은 모든 활성 에이전트의 작업을 하나의 행 배치로 쌓아 공유 가중치 읽기를 활용함으로써, 4개 에이전트 동시 구동 시 총 256-288 tok/s라는 높은 처리량을 달성했습니다.
핵심 포인트
- OpenJet은 Qwen3.8-27B용 커스텀 CUDA 메가커널 엔진을 사용합니다.
- 단일 GPU에서 여러 코딩 에이전트를 동시에 구동하는 것이 핵심입니다.
- 공유 가중치 읽기 방식을 통해 병렬 디코딩 시 속도 저하를 최소화했습니다.
- 4개 에이전트 동시 구동 시 총 처리량은 256-288 tok/s에 달합니다.
저는 OpenJet이라는 로컬 코딩 에이전트를 구축해 왔는데, 이 에이전트는 Qwen3.8-27B Q4_K_M을 위한 자체 CUDA 메가커널 엔진을 사용합니다. 이전까지는 한 번에 하나의 대화만 처리할 수 있었습니다. 새로운 버전에서는 단일 GPU에서 여러 에이전트를 동시에 구동할 수 있습니다. https://reddit.com/link/1xgs8hp/video/p0zd2rxse0yh1/player
[RTX 3090, Qwen3.8-27B Q4_K_M 기준]:
- per agent llama-server --parallel 4 OpenJet --agents 4
- decode, short prompts: 18-20 tok/s vs 64-72 tok/s decode, 23K context each: 15-16 tok/s vs 52-55 tok/s
- first token of the next request on those contexts: 13.4 s vs 0.2-0.5 s another agent decoding while a 20K prompt is processed: 0.6 tok/s vs 9.5 tok/s
총합적으로는 4개 에이전트에서 256-288 tok/s를 달성했으며, 이는 llama-server의 총 72-80 tok/s와 비교됩니다. 단일 에이전트만으로도 여전히 117 tok/s를 기록합니다. 도구 실행 및 테스트를 위해 일시 중지하는 실제 코딩 에이전트 4개의 경우, 총합은 150-200 tok/s입니다.
병렬 디코딩 작동 방식: GPU에서 토큰을 생성하는 것은 메모리 대역폭에 의해 제한됩니다. 모든 디코드 단계는 VRAM의 전체 16.7 GB 가중치를 읽어오는데, 이는 3090(936 GB/s)에서는 자체적으로 약 18ms가 소요됩니다. 이 가중치 위에서 수행되는 수학적 연산은 이에 비해 적습니다. 따라서 엔진은 에이전트들을 순차적으로 실행하지 않습니다. 매 단계마다 모든 활성 에이전트의 작업을 하나의 행 배치로 쌓습니다: 각 에이전트의 다음 토큰과 그 2개의 MTP/프롬프트 조회 초안 토큰을 더하여 총 12개의 행이 됩니다. 엔진은 가중치를 한 번 스트리밍하며, 로드되는 모든 가중치는 온칩(on chip)에 있는 동안 텐서 코어와 함께 12개 행 모두에 곱해집니다. 4개 에이전트가 비용을 발생시키는 것은 네 배가 아니라 하나의 가중치 읽기 정도입니다. 이것이 각 에이전트의 속도가 117 tok/s에서 ~30 tok/s로 떨어지는 대신 64-72 tok/s를 유지하는 이유입니다: 공유된 가중치 읽기가 단계 비용의 대부분을 차지하기 때문입니다. 더 많은 에이전트를 사용할 때 증가하는 부분은 어텐션(각 에이전트가 자체 KV 캐시를 읽음)과 추가 행의 계산량입니다. 전체 단계는 레이어별 실행 없이 하나의 지속적인 CUDA 커널로 실행되며, 초안들은 같은 패스에서 검증되므로, 승인된 모든 초안은 동일한 가중치 읽기에서 나온 추가 토큰이 됩니다.
실제 에이전트와 함께 빠르게 유지하는 비결: 새로운 프롬프트가 다른 모든 에이전트를 멈추게 하지 않습니다. 에이전트가 새 프롬프트를 보내면, 각 단계는 해당 프롬프트의 다음 청크를 다른 에이전트들의 행과 함께 전달하므로, 처리되는 동안에도 계속 생성할 수 있습니다. 그 결과는 해당 프롬프트를 단독으로 처리했을 때와 비트 단위로 동일합니다.
공유된 132K 토큰 KV 풀 (q8_0)을 사용합니다. 이는 페이지(paged) 방식으로 작동하여, 한 에이전트가 대부분을 사용할 수 있는 반면 다른 에이전트는 짧게 유지됩니다. 고정된 4 x 32K 분할은 없습니다. 공유 시스템 프롬프트는 한 번만 저장됩니다. 에이전트들이 공통으로 사용하는 1024 토큰 이상의 시스템 프롬프트와 도구 목록은 모든 에이전트를 위해 한 번 처리 및 저장됩니다.
대화는 자신의 슬롯에 유지됩니다. 후속 요청은 이미 대화를 담고 있는 슬롯으로 돌아가므로, 새로운 토큰만 처리됩니다.
또한 새로 추가된 기능: 샘플링된 MTP 초안(iiLaurens 덕분): 온도가 0보다 클 때, 초안은 이제 초안 헤드에서 샘플링되고 거부 샘플링(rejection sampling)을 통해 검증됩니다. 출력 분포는 변경되지 않으며 더 많은 초안이 수락됩니다.
mk_top: 각 에이전트의 토큰/초(tok/s), 컨텍스트 사용량, 현재 작업 및 최신 출력과 GPU 통계를 보여주는 실시간 터미널 보기입니다. mk_top --run 4는 서버와 4개의 에이전트를 평가 작업에 시작하여 모니터링할 수 있게 합니다.
정확도: 산술 연산 순서가 다르기 때문에 출력은 llama.cpp와 바이트 단위로 동일하지 않습니다. llama.cpp 자체의 다음 토큰 분포와 비교했을 때, KL 발산(KL divergence) 값은 llama.cpp의 배치 처리 방식과 토큰별 처리 방식 간에 같은 범위에 있습니다. 전체 정확도 표는 README를 참조하십시오.
사용 방법 (Linux, 24GB 메모리 RTX 30/40/50, CUDA 12+): python3 megakernel/server/mk_server.py -m Qwen3.8-27B-Q4_K_M.gguf --agents 4를 실행하고, 이어서 python3 megakernel/tools/mk_top.py를 실행합니다. 그런 다음 http://127.0.0.1:18080/v1에서 최대 4개의 OpenAI 호환 에이전트를 연결하십시오. 제한 사항: Q4_K_M 엔진만 사용 가능합니다 (혼합 양자화 빌드는 한 번에 하나의 대화만 처리). 최대 8개 에이전트까지 지원하며, 존재(presence)/반복(repetition) 페널티는 무시됩니다.
저장소(Repo): https://github.com/l-forster/open-jet 저는 또한 다음으로 TurboQuant 지원을 추가할 계획입니다. 이를 통해 단일 카드에서 최대 컨텍스트 윈도우를 256K까지 확보하고 출력 저하를 최소화하는 것이 목표입니다. 제출자: /u/Adorable_Weakness_39 [링크] [댓글]
AI 자동 생성 콘텐츠
본 콘텐츠는 Reddit AI Engineering의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기