24.5.1.5 Stack Trace 사용
운영 체제에 따라 mysqld가 예기치 않게 비정상적으로 종료 된 경우 오류 로그에 스택 추적이 포함되어 있습니다. 이것을 사용하여 mysqld가 비정상적으로 종료 된 장소 (및 많은 경우 그 이유)을 찾을 수 있습니다. 섹션 5.2.2 "오류 로그" 를 참조하십시오. 스택 트레이스를 취득하려면 -fomit-frame-pointer
옵션을 gcc로 지정해 mysqld를 컴파일하지 마십시오. 섹션 24.4.1.1 "디버깅을 위해 MySQL의 컴파일" 을 참조하십시오.
오류 로그의 스택 추적은 다음과 같이 출력됩니다.
mysqld got signal 11; Attempting backtrace. You can use the following information to find out where mysqld died. If you see no messages after this, something went terribly wrong... stack_bottom = 0x41fd0110 thread_stack 0x40000 mysqld(my_print_stacktrace+0x32)[0x9da402] mysqld(handle_segfault+0x28a)[0x6648e9] /lib/libpthread.so.0[0x7f1a5af000f0] /lib/libc.so.6(strcmp+0x2)[0x7f1a5a10f0f2] mysqld(_Z21check_change_passwordP3THDPKcS2_Pcj+0x7c)[0x7412cb] mysqld(_ZN16set_var_password5checkEP3THD+0xd0)[0x688354] mysqld(_Z17sql_set_variablesP3THDP4ListI12set_var_baseE+0x68)[0x688494] mysqld(_Z21mysql_execute_commandP3THD+0x41a0)[0x67a170] mysqld(_Z11mysql_parseP3THDPKcjPS2_+0x282)[0x67f0ad] mysqld(_Z16dispatch_command19enum_server_commandP3THDPcj+0xbb7[0x67fdf8] mysqld(_Z10do_commandP3THD+0x24d)[0x6811b6] mysqld(handle_one_connection+0x11c)[0x66e05e]
추적 함수 이름의 해결에 실패 할 경우 추적에 저장되는 정보가 적습니다.
mysqld got signal 11; Attempting backtrace. You can use the following information to find out where mysqld died. If you see no messages after this, something went terribly wrong... stack_bottom = 0x41fd0110 thread_stack 0x40000 [0x9da402] [0x6648e9] [0x7f1a5af000f0] [0x7f1a5a10f0f2] [0x7412cb] [0x688354] [0x688494] [0x67a170] [0x67f0ad] [0x67fdf8] [0x6811b6] [0x66e05e]
후자의 경우는 resolve_stack_dump 유틸리티를 사용하여 다음 단계를 사용하여 mysqld가 비정상적으로 종료 된 위치를 확인할 수 있습니다.
스택 추적에서
mysqld.stack
등의 파일에 수치를 복사합니다. 이 수치에는 둘러싸고 있던 대괄호를 포함하지 마십시오.0x9da402 0x6648e9 0x7f1a5af000f0 0x7f1a5a10f0f2 0x7412cb 0x688354 0x688494 0x67a170 0x67f0ad 0x67fdf8 0x6811b6 0x66e05e
mysqld 서버의 심볼 파일을 만듭니다.
shell>
nm -n libexec/mysqld > /tmp/mysqld.sym
mysqld가 정적으로 링크되어 있지 않으면 대신 다음 명령을 사용합니다.
shell>
nm -D -n libexec/mysqld > /tmp/mysqld.sym
C ++ 심볼을 디코딩하는 경우 nm에
--demangle
을 사용합니다 (사용 가능한 경우). 사용하는 버전 nm에이 옵션이 없으면 스택 덤프가 생성 된 후에 c ++ filt 명령을 사용하여 C ++ 이름을 데만구루해야합니다.다음 명령을 실행합니다.
shell>
resolve_stack_dump -s /tmp/mysqld.sym -n mysqld.stack
데만구루 된 C ++ 이름을 심볼 파일에 포함 할 수 없었던 경우는 c ++ filt를 사용하여 resolve_stack_dump의 출력을 처리합니다.
shell>
resolve_stack_dump -s /tmp/mysqld.sym -n mysqld.stack | c++filt
이렇게하면 mysqld가 비정상적으로 종료 된 장소가 출력됩니다. 이 출력은 mysqld가 비정상적으로 종료 된 이유를 찾기 위해 도움이되지 않는 경우는 버그 리포트를 작성하여 위 명령의 출력을 버그 리포트에 포함해야합니다.
그러나 대부분의 경우 스택 추적 만 있어도 문제의 원인을 찾기 위해 도움이되지 않습니다. 버그를 찾거나 해결 방법을 제공하는 데, 대부분의 경우, mysqld가 종료 된 문을 알아야 문제를 재현 할 수있는 테스트 케이스가 있으면 도움이됩니다. 섹션 1.7 "질문이나 버그를보고하는 방법" 을 참조하십시오.
새로운 버전의 glibc
스택 트레이스 함수는 객체의 상대 주소도 출력됩니다. glibc
기반 시스템 (Linux)는 플러그인에서 충돌 흔적은 다음과 같습니다.
plugin/auth/auth_test_plugin.so(+0x9a6)[0x7ff4d11c29a6]
상대 주소 ( +0x9a6
)를 파일 이름과 행 번호로 변환하려면 다음 명령을 사용합니다.
shell> addr2line -fie auth_test_plugin.so 0x9a6
auth_test_plugin
mysql-trunk/plugin/auth/test_plugin.c:65
addr2line 유틸리티는 Linux의 binutils
패키지의 일부입니다.
Solaris 절차는 다음과 같습니다. Solaris의 printstack()
는 상대 주소가 이미 출력되어 있습니다.
plugin/auth/auth_test_plugin.so:0x1510
이를 변환하려면 다음 명령을 사용합니다.
shell> gaddr2line -fie auth_test_plugin.so 0x1510
mysql-trunk/plugin/auth/test_plugin.c:88
Windows에서 주소, 함수 이름 및 행이 이미 출력되어 있습니다.
000007FEF07E10A4 auth_test_plugin.dll!auth_test_plugin()[test_plugin.c:72]