리누스 토르발스가 된다는 것
(이 글은 제 YouTube 영상(https://www.youtube.com/watch?v=l6lxgYeVZqs)의 전사를 바탕으로 다듬은 것입니다.)
리누스 토르발스가 최초의 리눅스 커널을 개발했을 때 그는 Minix 소스를 공부했고 컴퓨터 아키텍처를 공부했으며 필요한 기초 지식을 갖추고 있었습니다. 당연히 그는 매우 뛰어난 프로그래머이기도 했습니다. 하지만 386을 위한 최소한으로 동작하는 유닉스 커널을 작성하는 일—초기의 리눅스는 말하자면 단일 아키텍처였습니다—은 다른 많은 프로그래머와 학생들도 충분히 해낼 수 있는 일이었습니다. 여기서 ‘많은’이란 이를테면 0.1%, 천 명 중 한 명, 만 명 중 한 명 정도를 뜻합니다. 물론 대부분의 사람은 이런 일을 해낼 수 없지만, 할 수 있는 사람도 적지 않습니다. 최근 몇 년간 Hacker News를 보면 C로 작성된 커널, 처음부터 구현한 마이크로커널, Rust로 작성된 커널, 온갖 방식과 형태로 만들어진 커널, 라즈베리 파이를 위해 수직적으로 만든 작은 유닉스 시스템, ESP32용 운영체제 등 얼마나 많은 커널 프로젝트가 있는지 알 수 있습니다. 커널을 작성하는 일은 누구나 할 수 있는 일은 아니지만, 충분히 노력한다면 많은 사람이 완성할 수 있는 일입니다. 물론 모두가 잘하는 것은 아닙니다. 그는 의심의 여지 없이 천재적인 프로그래머였기에 더 잘 해냈을 뿐입니다.
그럼에도 리누스는 단 한 명뿐입니다. 사실 그의 이런 구현 능력만으로는 그를 제대로 설명할 수 없습니다. 우리가 주목해야 할 것은 그 이후에 일어난 일입니다.
그는 코드 작성을 멈췄다
유명한 오픈소스 프로젝트의 메인테이너들 가운데, 그는 리눅스 개발 역사상 아주 이른 시기에 거의 완전히 코드 작성을 멈추고 프로젝트를 이끄는 일에 집중한 몇 안 되는 사람 중 한 명이었습니다. 리더가 되고, 조율자가 되고, 프로젝트의 목표가 무엇이어야 하는지에 대한 명확성을 쥐고 있는 단 하나의 두뇌가 되는 일에 집중한 것입니다. 이는 매우 드문 일입니다. 많은 메인테이너—저 자신도 오랫동안 그랬습니다—는 오히려 직접 구현을 계속하고 위임을 많이 하지 않으려 합니다.
이는 소프트웨어에 대한 다른 생각에서 출발하기도 합니다. 리눅스는 필연적으로 엄청나게 커져야 했습니다. 수많은 장치와 플랫폼, 서브시스템을 포용하고 시대와 새로운 소프트웨어의 요구, 조금씩 등장하는 하드웨어에 끊임없이 적응하려는 커널이라는 존재 자체의 성격이 그렇습니다. 따라서 이는 실수가 아니었습니다. 반면 Redis는 자족적인 무언가로 남을 수 있었습니다. 얼마 전 저는 SQLite의 Richard Hipp 박사로부터 linenoise에 대한 풀 리퀘스트를 받았습니다. 그 역시 안정성과 최소주의, 성능을 추구했지만 코드베이스를 항상 아주 작게 유지했고 아주 오랫동안 직접 코드를 작성해 왔습니다. 반면 리누스는 그렇지 않았습니다. 그는 자신의 시간을 한 사람의 구현 능력에 비해 매우 거대해질 운명인 프로젝트를 위해 더 중요한 일에 써야 한다는 것을 즉시 깨달았습니다.
그리하여 그는 프로젝트의 리더가 되었습니다. 아이디어와 방향을 소유한 사람이 된 것입니다. 그렇다면 리누스는 무엇을 합니까? 그는 매번 모든 패치를 한 줄 한 줄 들여다보지 않습니다. 물론 무슨 일이 일어나고 있는지 이해하기 위해 하나의 구현을 깊이 들여다보는 경우도 있습니다. 세월이 흐르며 그는 새로운 서브시스템을 작성하거나 심지어 다시 작성하기도 했습니다. 제가 알기로는 오래전에 USB 레이어를 한 번 그렇게 했고, 가상 파일 시스템도 어느 시점에 inode와 inode 캐시의 구조를 바꾸며 재구현했다고 생각합니다. 다른 여러 이유로도 그런 일을 했습니다. 가끔은 Git을 만들 때처럼 계속 프로그래밍을 하기도 했습니다. 하지만 대부분의 경우 그는 패치를 하나하나 세세하게, 한 줄씩 들여다보지 않습니다. 그는 각 하위 분야의 메인테이너들과 소통하며 특정 기능이나 특정 방향이 가야 할 길인지 아닌지를 판단합니다.
브룩스의 표현을 빌리자면, 『The Mythical Man-Month』의 언어로 말하자면, 리누스는 커널의 설계 개념을 쥐고 있으며 커널 계층에서 자신 아래에 있는 모든 사람과 계속 대화하면서 커널이 특정한 방향으로 나아가도록 합니다. 개발이 특정한 방향으로 나아가도록 하는 것입니다. 구현 관점—이러한 개발이 어떻게 구현되는지, 품질은 어떤지, 코드가 작성된 방식 자체에 담긴 구현 아이디어는 무엇인지—과 설계 관점—우리가 무엇을 하려 하고 무엇을 하지 않으려 하는지, 모듈과 스케줄러, 하드웨어 지원, Rust 통합 여부에 대한 최선의 전략은 무엇인지—모두를 아우르면서 말입니다.
저는 이것이 리누스의 진정한 천재성이라고 생각합니다. 그는 단순히 매우 뛰어난 프로그래머인 것만이 아닙니다. 그런 사람은 다른 곳에도 있습니다. 그는 또한 메인테이너이자 놀라운 설계자이며, 수많은 사람들과 대화하면서 거대한 프로젝트의 아이디어와 구조를 일관되게 다룰 수 있는 사람입니다. 이는 누구나 할 수 있는 일이 아닙니다.
이제 우리가 리누스다
이제 인공지능과 함께 프로그래밍할 때 우리는 정확히 같은 존재가 됩니다. 우리는 리누스 토르발스입니다. 언제나 그와 같은 재능을 가진 것은 아니지만, 코드의 모든 줄을 일일이 리뷰하지 않는 프로젝트에서 우리가 맡아야 할 역할은 정확히 그런 유형의 역할입니다. 바로 그가 맡고 있는 역할입니다.
다만 다루기는 더 단순합니다. 많은 에이전트를 병렬로 사용하지 않는 한, 여러 경로로 들어오는 수많은 패치를 다루는 것보다 실질적으로 훨씬 단순합니다. 하지만 훨씬 더 빠릅니다. 마치 인간의 속도로 일하는 많은 사람으로 구성된 팀과 상호작용하는 대신, 그 순간 우리가 병렬로 개발하고 있는 브랜치 수에 따라 한두세 명으로 구성된 팀과 상호작용하는 것과 같습니다. 다만 그 팀은 훨씬 더 빠르기 때문에 훨씬 더 빠른 피드백을 즉시 제공합니다. 이는 작업 방식을 조금 바꾸지만, 제 생각에는 더 나은 방향으로 바꿉니다. 더 쉽고, 컨텍스트 전환도 적으며, 상대해야 할 사람도 적고, 성격이나 태도 등으로 인한 문제도 훨씬 적습니다.
따라서 이 역할이 중요하다고 생각한다면, 자동 프로그래밍을 ‘프롬프트를 넣으면 알아서 써준다’는 것으로 생각해서는 안 됩니다. 바이브 코딩은 자동 프로그래밍이 무엇인지, 그리고 대다수에게 자동 프로그래밍이 앞으로 무엇이 될 것인지에 대한 잘못된 생각입니다. 바이브 코딩은 기술적 능력이 없으면서도 자신의 도구를 만드는 데 어쨌든 영향을 주고 싶은 사람들에게는 매우 흥미로운 일입니다. 그러니 가능성을 민주화한다는 점에서 환영할 일입니다. 하지만 본질은 그것이 아닙니다.
반면 숙련된 기술자, 숙련된 프로그래머, 숙련된 설계자, 숙련된 소프트웨어 아키텍트의 손에서 자동 프로그래밍은 리누스의 역할을 맡는 것입니다. 에이전트와 LLM이 서로 다른 서브시스템의 메인테이너 역할을 맡는 구조입니다. 그리고 누구나 그것을 그렇게 잘할 수 있는 것은 아니기에, 자동 프로그래밍 역시 에이전트와 대화하고 아이디어를 검증하며 어떤 구현을 해야 하고 어떤 구현을 해서는 안 되는지 알고, 에이전트가 최고의 작업을 하도록 만드는 소통 방식을 알며, 위대한 프로그래머가 직관하고 좋은 프로그래머가 직관해 미리 헤아리는 그런 설계적 힌트를 불어넣을 수 있는 재능을 필요로 합니다.
그러므로 자동 프로그래밍을 잘한다는 것은 리누스의 역할을 맡는다는 것을 의미합니다. 그리고 이 일은 잘할 수도, 못할 수도, 제대로 이해될 수도, 혹은 오히려 폄하될 수도 있습니다. 또한 이는 훈련이 필요하고 배워야 하는 것이기도 합니다. 리누스 역시 그것을 배워야 했던 것처럼 말입니다. 그는 분명 이 일에 타고난 재능이 있었지만, ‘모든 것을 직접 구현한다’는 상태에서 교향곡을 다루고 오케스트라를 지휘하는 능력으로 나아갔습니다.
저에게는 그것이 리누스의 교훈이며, LLM 덕분에 이제 프로그래밍은 누구에게나 쉽다는 말에 대한 즉각적인 반론으로 사용되어야 할 교훈입니다.
글을 무작위로 읽기