AVX와 CUDA를 활용한 셀룰러 오토마타 시뮬레이션 가속화
초록
본 논문은 유체 흐름 모델링에 사용되는 Frish‑Hasslacher‑Pomeau(FHP) 셀룰러 오토마타 알고리즘을 CPU와 GPU에서 가속화하는 방법을 비교한다. SSE·AVX 기반의 SIMD 구현과 POSIX 스레드, 그리고 CUDA 구현을 평가한 결과, AVX·SSE를 사용해야 현대 CPU의 성능을 충분히 끌어낼 수 있으며, AVX가 SSE 대비 눈에 띄는 이득을 제공하지 않음을 확인하였다. 또한 AVX·SSE를 적용한 CPU 코드와 CUDA GPU 코드가 비용·성능 면에서 비슷한 수준임을 보고한다.
상세 분석
FHP 알고리즘은 격자 기반의 입자 이동·충돌 연산을 반복 수행하는 전형적인 셀룰러 오토마타이며, 각 격자 셀은 6개의 이동 방향과 정지 상태를 가질 수 있다. 이 특성 때문에 각 타임스텝에서 수행되는 연산은 기본적으로 “비트 마스크와 시프트, 그리고 조건부 합산” 형태이며, 데이터 종속성이 비교적 낮아 SIMD 및 다중 스레드화에 적합하다. 논문은 먼저 순차 구현을 기준으로, SSE(128‑bit)와 AVX(256‑bit) 명령어 집합을 이용해 8비트 정수 배열을 동시에 처리하도록 최적화하였다. 핵심은 충돌 규칙을 사전 계산된 룩업 테이블에 매핑하고, 각 워드에 대해 _mm_load_si128/_mm256_load_si256 로 메모리를 로드한 뒤, _mm_and_si128, _mm_or_si128, _mm_slli_epi16 등으로 비트 연산을 수행하는 방식이다.
CPU 측면에서는 POSIX Threads를 이용해 격자 행을 여러 스레드에 균등 분배했으며, 스레드 간 동기화는 배리어(barrier)만 사용해 오버헤드를 최소화했다. 실험 결과, 단일 코어에서 AVX가 SSE 대비 약 1.05배 정도의 속도 향상만을 보였으며, 이는 메모리 대역폭이 병목으로 작용하고 SIMD 레지스터 활용률이 256‑bit에 비해 크게 증가하지 않기 때문이다. 반면, 멀티코어 환경에서 AVX·SSE를 적용한 코드는 코어 수가 증가함에 따라 거의 선형적인 스케일링을 보였고, 8코어(16스레드) 시스템에서 최대 12배 정도의 가속을 달성했다.
GPU 구현은 CUDA를 사용해 각 격자 셀을 하나의 스레드 블록에 매핑하고, 전역 메모리에서 충돌 테이블을 읽어와 공유 메모리로 복사한 뒤, 스레드 간 동기화(_syncthreads())를 통해 충돌 연산을 수행했다. GPU는 대규모 병렬성을 활용해 1,024개의 스레드 블록(각 256개의 스레드) 구성을 기본으로 하였으며, 메모리 접근 패턴을 최적화하기 위해 구조체‑오브‑배열(SOA) 형태로 데이터를 재배열했다. 결과적으로, CUDA 구현은 동일한 격자 크기(예: 1024×1024)에서 AVX·SSE를 적용한 8코어 CPU 대비 약 1.2배 정도 빠른 실행 시간을 보였지만, 전력 소비와 하드웨어 비용을 고려하면 비용 효율성은 비슷한 수준으로 평가되었다.
핵심 인사이트는 다음과 같다. 첫째, 현대 CPU에서 SIMD 확장은 필수이며, AVX가 반드시 SSE보다 월등히 빠른 것은 아니다; 메모리 대역폭과 캐시 활용이 더 큰 영향을 미친다. 둘째, 멀티코어와 SIMD를 결합하면 GPU와 경쟁할 수 있는 성능을 얻을 수 있다. 셋째, CUDA 구현은 높은 스루풋을 제공하지만, 개발 복잡도와 하드웨어 의존성이 크다. 이러한 결과는 유사한 격자 기반 시뮬레이션(예: Lattice Boltzmann, Ising 모델)에도 적용 가능함을 시사한다.