19.3.4.1. `orb_unadvertise()`를 통한 메모리 릭(Memory Leak) 방지

19.3.4.1. orb_unadvertise()를 통한 메모리 릭(Memory Leak) 방지

백그라운드로 100Hz로 미친 듯이 회전하던 워커 스레드의 무자비한 while (!thread_should_exit) 무한 루프 블록이 드디어 통제 변수에 의해 파괴되어 깨지고, 코드 실행 제어권이 루프 바깥 하단부로 툭 하고 떨어졌다면, 이는 시스템 커널 스케줄러가 데몬 모듈에게 **“즉각 미들웨어 동작을 멈추고 짐 싸서 죽어라(Stop)”**라는 사형 선고를 내렸음을 의미한다.
이 찰나의 치명적인 순간에 입문 초심자 코더들은 아무런 죄의식도 없이 그대로 메인 함수 끄트머리에 return 0;를 날려버리고 프로세스 함수를 강제 셧다운(Shutdown)시키는 돌이킬 수 없는 만행을 저지른다. 진정한 코어 아키텍트는 죽는 그 마지막 순간 점멸조차도 자신이 링커에 빌려 쓴 모든 가혹한 커널 자원을 완벽하게 반납해야 할 시스템적 의무가 있다.

1. 광고(Advertisement) 파괴: orb_unadvertise()의 가혹한 의무 호출

당신이 앞선 19.3.3 단원에서 메인 루프 진입 직전 orb_advertise() 함수를 때려서 VFS 링 버퍼망의 파이프 한 줄기를 억지로 열어젖히고 권력을 쥐었던 행위를 똑똑히 기억하는가? 그 무자비한 광고(Advertisement) 대가로 우리는 sensor_pub_handle이라는 VFS 마스터 키 포인터 덩어리를 힙 메모리에 쥐고 있었다. 스레드의 커널 라이프사이클이 셧다운(Shutdown) 되며 죽기 직전, 우리는 오직 우리 손으로 이 핸들을 단독 파괴하여 커널에게 소중한 파일 디스크립터(FD) 메모리를 고스란히 돌려주어야만 한다.

// ... (무자비한 while(!thread_should_exit) 무한 루프가 드디어 종료됨) ...

// 루프를 무사히 빠져나온 직후, 미들웨어에 오만하게 열어두었던 파이프라인의 강제 폭파(Unadvertise) 파멸 시퀀스
if (sensor_pub_handle != nullptr) {
    // 커널 스케줄러에게 "이 핸들이 불법 점유하던 링 버퍼 메모리를 당장 토해내라"고 청소 명령을 때린다
    orb_unadvertise(sensor_pub_handle);
    
    // (선택적이지만 필수적인 안정성 방벽) 
    // 나중에 누가 이 변수를 또 잘못 건드려 댕글링 포인터(Dangling Pointer) 에러 타격을 
    // 유발하지 않도록, 확실하게 nullptr 쓰레기로 덮어씌워 매립해 버린다.
    sensor_pub_handle = nullptr; 
}

orb_unadvertise() C 코어 API 매크로 함수를 단 한 번 코드상에서 정확하게 타격하는 순간, 커널 시스템은 이 스레드 퍼블리셔가 쏘아대던 sensor_test_data 토픽을 위해 억지로 쥐고 수용하고 있던 o_size 바운더리의 링 버퍼 배열 메모리와 뮤텍스(Mutex) 락 제어 장치들을 지체 없이 힙(Heap) 공간에서 산산이 박살 내버리고, OS 시스템의 다음 행동을 위한 가용 자유 램(Free RAM) 캐시 공간으로 즉각 무자비하게 환수 조치시킨다.

2. 단 한 줄의 메모리 릭(Memory Leak)이 초래하는 끔찍한 추락 나비효과

만약 이 치명적인 클린업 코드 한 줄을 까먹고 데몬이 종료된다면 픽스호크 보드에 어떤 끔찍한 잠재적 참사가 들이닥칠까?
코드 개발자가 NSH 터미널 콘솔 디버깅 쉘에서 px4_uorb_example stoppx4_uorb_example start 명령을 그저 디버깅이랍시고 10번만 미친 듯이 껐다 켜보자. 스레드가 파괴되어 죽을 때마다, 이 시스템 링 버퍼 파이프는 같이 파괴되어 닫히지 않고 주인 읽은 고아(Orphan Object) 상태로 메모리에 버려져 널브러져 방치된다.
그리고 새로 켜진 다음 데몬 스레드는 메인 루프 진입 전 orb_advertise()를 때리며 또다시 완전히 새롭고 거대한 새로운 링 버퍼 통로를 시스템 힙에서 무식하게 뜯어내어 강탈해 간다. 결국 단 10번의 재실행만으로 10개의 거대한 유령(Ghost) 파일 디스크립터 파이프라인이 픽스호크 보드 VFS에 무자비하게 그어지는 것이다.

단 몇 분, 몇 시간의 비행 만에 픽스호크의 작디작은 1MB SRAM 칩셋 공간은 OOM(Out of Memory) 폭탄의 직격탄을 그대로 처맞게 되고, 센서 통합 EKF 비행 코어 데몬들이 메모리를 더 이상 할당받지 못해 기체는 그 즉시 수십 미터 상공에서 모터를 끄고 추락 궤도로 곤두박질치게 될 것이다.

따라서 orb_unadvertise() 객체 매립 행위는 개발자의 나태한 선택이 아닌, 전체 시스템 드론 생태계 생존을 위한 절대적인 핏빛 철칙이라는 점을 뼛속에 새겨야 한다.