나는 Linux 4.0이 메인라인에 진입하면서 최근에 배운 새로운 개념인 "라이브 패치"를 이해하려고 노력하고 있습니다.
이는 리눅스 커널의 새로운 기능 향상이라고 합니다. 원래 약 1년 전에 Red Hat과 Open SUSE가 독립적으로 개발했습니다.
모든 기능 개발/버그 수정은 일반적으로 패치를 통해 Linux 커널에서 구현된다는 것을 알고 있습니다. 즉, 관련 Linux 커널 버전에 대한 패치를 적용하고 커널 소스 코드를 다시 컴파일한 후 일반적인 방법을 통해 설치합니다 $make;sudo make install
.
소위 "라이브 패치" 메커니즘의 흥미로운 부분은 새 커널 버전을 다시 컴파일하고 설치할 필요가 없다는 것입니다. 내 말은, GRUB에는 최신 커널 버전에 대한 항목이 표시되지 않는다는 것입니다. 그렇죠? 설치하지 않으셨기 때문입니다.
이제 이것은 제가 소화해야 할 심각한 개념입니다. 어떻게 그럴 수 있습니까? , 어떻게 구현하나요?
Red Hat과 Open SUSE는 각각 Kpatch와 kGraft를 사용하여 이를 구현합니다.
간단한 커널 모듈을 사용해 보고 Kpatch 또는 kGraft 중 하나를 사용하여 구현하고 싶습니다. 하지만 Ubuntu 14.04 시스템이 있는데 Ubuntu에 대한 대안이 있습니까?
이 새로운 개념에 대해 내가 이해하는 가장 가까운 것은 ftrace와 같은 새로운 프레임워크에서 패치를 작성하고 컴파일해야 한다는 것입니다. 따라서 "버그가 있는" 커널 모듈의 사용자 공간에서 이 패치(빌드된 패치를 "만" 설치하는 방법)를 사용하여 방금 설치한 최신 API/ABI 구현으로 API/ABI를 특수 프레임워크에서 리디렉션하게 됩니다. ). 내가 여기 있나요?
Linux 커널 전문가가 이에 대해 알고 있다면 이 "라이브 패치"가 정확히 무엇인지, 라이브 패치가 어떻게 생성되는지, 시스템 사용자가 이 패치를 설치하고 기능을 확인하는 방법에 대한 귀하의 의견을 듣고 싶습니다. (테스트해 보세요)?
이 개념을 이해하면서, 이런 "라이브 패치"를 어떻게 작성하는지 궁금합니다. 이 작업을 수행하려면 어떤 다른 환경이 필요합니까?
답변1
커널이 완전히 다시 작성되지 않은 경우(함수 이름 변경, 함수에 전달된 인수 순서 변경) 원래 커널과 패치된 커널의 바이너리를 분석하고 어떤 함수가 변경되었는지 확인할 수 있습니다.
그런 다음 변경된 루틴의 시작 부분을 덮어써서 메모리에 로드된 루틴의 변경된 버전으로 이동합니다. 이는 다른 프로세스가 실행되고 있지 않을 때 수행됩니다.
Wikipedia에 관한 기사케스 스티칭좀 더 이해하기 쉽게 설명되어 있습니다.
확실히 패치 작성을 시도하고 더 작은 패치를 생각해 낼 수 있습니다(완전한 기능보다는 기계어 코드 몇 줄 변경). 이러한 작은 패치는 패치된 함수 호출에서 단순히 복귀하는 것이 아니라 원래 루틴으로 조심스럽게 다시 점프해야 합니다.
새로운 버전 번호를 얻기 위해 grub 메뉴를 패치하는 것은 커널 바이너리를 분석하고 패치하는 것에 비해 쉽습니다. 메뉴는 텍스트로만 제공됩니다. 하지만 무슨 일이 있어도 첫 번째 부팅 후에는 그럽 메뉴가 절대 표시되지 않을 것이라는 생각입니다.
이는 Red Hat 및 Open SuSE의 새로운 기능일 수 있지만 1년 전에 발명된 것은 아닙니다. 예를 들어 ksplice는 2008년에 커널 실행 패치를 시작했습니다. 메모리 내 프로그램(반드시 Linux 커널일 필요는 없음)을 패치하는 개념은 훨씬 오래되었습니다. 나 자신도 이미 1984년부터 수동 분석을 기반으로 한 인메모리 프로그램 패치(6502 기계 코드 패치)를 사용하고 있었는데, 그 당시에는 확실히 할 생각이 없었습니다.