Computer >> 컴퓨터 >  >> 프로그램 작성 >> Ruby

TCmalloc을 사용하여 Ruby의 메모리 할당 프로파일링

Ruby에서 메모리 할당은 어떻게 작동합니까?

Ruby는 페이지라고 하는 청크로 메모리를 가져오고 여기에 새 개체가 저장됩니다.

그럼...

이 페이지가 가득 차면 더 많은 메모리가 필요합니다.

Ruby는 malloc을 사용하여 운영 체제에서 더 많은 메모리를 요청합니다. 기능.

malloc 기능은 운영 체제 자체의 일부이지만 사용할 수 있는 대체 구현이 있습니다.

이러한 구현 중 하나는 Google의 tcmalloc입니다.

TCmalloc은 Google 성능 도구 제품군의 일부입니다.

이러한 도구를 사용하여 Ruby가 메모리를 할당하는 방법을 정확히 탐색할 수 있습니다.

그리고 LD_PRELOAD 덕분에 환경 변수(Linux에서) 시스템의 malloc을 대체할 수 있습니다. tcmalloc과 함께 사용합니다.

좋아요 :

LD_PRELOAD="/usr/lib/libtcmalloc.so" ruby -e "puts 123"

그러나 이는 라이브러리만 로드하고 아직 데이터 수집을 활성화하지 않습니다.

어떻게 했는지 봅시다.

프로파일러 활성화

추가 환경 변수(HEAPPROFILE)로 tcmalloc의 프로파일러를 활성화할 수 있습니다. ).

LD_PRELOAD="/usr/lib/libtcmalloc.so" HEAPPROFILE=/tmp/profile ruby -e "puts 123"

그러면 다음과 같은 출력이 생성됩니다.

Starting tracking the heap
123
Dumping heap profile to /tmp/profile.0001.heap (Exiting, 2 MB in use)

여기에 프로파일러가 활성화되었다는 확인 메시지가 표시됩니다.

그러면 :

  • 프로그램의 출력
  • 파일 이름(profile.0001.heap )
  • 프로그램에서 사용하는 메모리 양(2 MB )

이 파일을 읽으려면 tcmalloc에 ​​포함된 다른 도구가 필요합니다.

pprof --text `which ruby` /tmp/profile.0001.heap | head -10

그러면 다음과 같은 출력이 생성됩니다.

Total: 2.4 MB
   1.1  44.7%  44.7%      1.1  44.7% 0x00005570fa4df074
   0.7  27.8%  72.5%      0.7  27.8% 0x00005570fa4e0c09
   0.4  15.3%  87.8%      0.4  15.3% 0x00005570fa4db460
   0.1   5.9%  93.7%      0.1   5.9% 0x00005570fa4df19f
   0.1   3.2%  96.9%      0.1   3.2% 0x00005570fa6349a0
   0.0   1.4%  98.3%      0.0   1.4% 0x00005570fa589924
   0.0   0.3%  98.6%      0.0   0.3% 0x00005570fa59c4f2
   0.0   0.3%  98.8%      0.0   0.3% 0x00005570fa4db48a
   0.0   0.2%  99.0%      0.0   0.2% 0x00005570fa4dbaa5
   0.0   0.2%  99.1%      0.0   0.2% _dl_new_object

글쎄, 그것은 단지 많은 메모리 주소입니다! 함수 이름을 보려면 디버깅 기호가 있는 Ruby 버전이 필요합니다.

이 결과를 얻을 수 있습니다. :

Using local file ruby.
Using local file /tmp/profile.0001.heap.
Total: 2.9 MB
   1.0  36.2%  36.2%      1.0  36.2% objspace_xmalloc0
   0.7  26.1%  62.4%      0.7  26.1% aligned_malloc
   0.5  18.8%  81.1%      0.5  18.8% objspace_xcalloc
   0.3   9.9%  91.0%      0.3   9.9% stack_chunk_alloc
   0.1   3.7%  94.7%      0.1   3.7% objspace_xrealloc
   0.1   2.7%  97.4%      0.1   2.7% Init_Method
   0.0   1.3%  98.7%      0.0   1.7% onig_new_with_source
   0.0   0.4%  99.2%      0.8  26.6% heap_page_allocate
   0.0   0.2%  99.4%      0.0   0.2% add_bitset

여기에서 볼 수 있는 것은 MRI의 기능에 의해 할당된 메모리의 양입니다.

aligned_malloc Ruby 객체, stack_chunk_alloc에 새 페이지를 할당하는 데 사용되는 함수입니다. 마킹 단계에서 GC 자체에서 사용되며 objspace_xmalloc0 / objspace_xcalloc RVALUE에 맞지 않는 문자열, 배열 및 기타 데이터를 위한 공간 할당 구조체.

지금:

TCmalloc은 Ruby 객체에 대해 아무 것도 모르고, 요청되는 메모리의 양을 찾기 위해 malloc, calloc 및 realloc에 ​​대한 호출을 추적하는 것만 합니다.

Ruby 수준에서 힙 덤프를 얻으려면 ObjectSpace.dump_all을 사용할 수 있습니다. . 이렇게 하면 애플리케이션의 모든 라이브 개체와 메모리 크기가 포함된 JSON 파일이 제공됩니다.

하지만 tcmalloc 메모리를 요청하는 모든 C 함수의 시각화임을 보여줄 수 있습니다.

pprof --web `which ruby` /tmp/profile.0001.heap

그러면 다음과 같은 SVG 파일이 있는 Chrome 또는 Firefox가 열립니다.

TCmalloc을 사용하여 Ruby의 메모리 할당 프로파일링

TCmalloc은 이 멋진 프로파일링 기능을 제공할 뿐만 아니라 이를 사용하여 애플리케이션의 성능을 4-9%까지 높일 수 있습니다! jemalloc을(를) 사용해 볼 수도 있습니다. , 이는 또 다른 malloc 프로파일러도 포함하는 구현

요약

gperftools(Google 성능 도구)를 사용하여 Ruby 인터프리터의 메모리 사용량을 시각화하고 분석하는 방법을 배웠습니다.

읽어 주셔서 감사합니다! 🙂