Development Tip

소켓 파일을 열 수없는 jmap 실행

yourdevel 2020. 10. 22. 22:58
반응형

소켓 파일을 열 수없는 jmap 실행


jmap내 프로세스의 힙 덤프를 가져 오기 위해 실행해야했습니다 . 그러나 jvm반환 :

Unable to open socket file: target process not responding or HotSpot VM not loaded
The -F option can be used when the target process is not responding

그래서 나는 다음을 사용했습니다 -F.

./jmap -F -dump:format=b,file=heap.bin 10330
Attaching to process ID 10331, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 24.51-b03
Dumping heap to heap.bin ...
  1. -F힙 덤프를 사용하는 것은 괜찮습니까?
  2. 20 분을 기다렸는데 아직 끝나지 않았습니다. 이유는 무엇입니까?

jmapjmap -F뿐만 아니라 jstack대를 jstack -F사용하는 완전히 다른 메커니즘은 목표 JVM과 communcate한다.

jmap / jstack

-F이러한 도구 없이 실행 하는 경우 동적 연결 메커니즘을 사용 합니다 . 이것은 다음과 같이 작동합니다.

  1. Java 프로세스 1234에 연결하기 전에, jmap파일 생성 .attach_pid1234대상 프로세스의 또는 작업 디렉토리에서를 /tmp.

  2. 그런 다음 대상 프로세스로 jmap보냅니다 SIGQUIT. JVM이 신호를 포착하고를 찾으면 스레드를 .attach_pid1234시작 AttachListener합니다.

  3. AttachListener스레드 /tmp/.java_pid1234는 외부 도구의 명령을 수신하기 위해 UNIX 도메인 소켓 만듭니다 .

  4. 연결 (에서 jmap)이 승인 될 때 보안상의 이유로 JVM은 소켓 피어의 신임 정보 가 JVM 프로세스 euid동일한 지 확인합니다 egid. 그렇기 때문에 jmap다른 사용자가 (루트에서도) 실행하면 작동하지 않습니다.

  5. jmap소켓에 연결하고 dumpheap명령을 보냅니다 .

  6. 이 명령은 AttachListenerJVM 스레드에서 읽고 실행합니다 . 모든 출력은 소켓으로 다시 전송됩니다. 힙 덤프는 JVM에서 직접 처리되므로 작업이 정말 빠릅니다. 그러나 JVM은 safepoints 에서만이를 수행 할 수 있습니다 . Safepoint에 도달 할 수없는 경우 (예 : 프로세스가 중단되거나 응답하지 않거나 긴 GC가 진행 중임) jmap시간이 초과되고 실패합니다.

Dynamic Attach의 장점과 단점을 요약 해 보겠습니다.

찬성.

  • 힙 덤프 및 기타 작업은 JVM에서 최대 속도로 공동으로 실행됩니다.
  • jmap또는의 모든 버전 jstack을 사용하여 다른 버전의 JVM에 연결할 수 있습니다 .

단점.

  • 도구는 대상 JVM과 동일한 사용자 ( euid/ egid) 가 실행해야합니다 .
  • 활성 상태의 정상 JVM에서만 사용할 수 있습니다.
  • 대상 JVM이로 시작되면 작동하지 않습니다 -XX:+DisableAttachMechanism.

jmap -F / jstack -F

-F도구를 사용 하여 실행하면 HotSpot Serviceability Agent 기능이있는 특수 모드로 전환됩니다 . 이 모드에서는 대상 프로세스가 고정됩니다. 도구 ptrace는 Linux에서 OS 디버깅 기능을 통해 메모리를 읽습니다 .

  1. jmap -FPTRACE_ATTACH대상 JVM에서 호출합니다 . 대상 프로세스는 SIGSTOP신호 에 응답하여 무조건 중단됩니다 .

  2. 이 도구는를 사용하여 JVM 메모리를 읽습니다 PTRACE_PEEKDATA. ptrace한 번에 한 단어 만 읽을 수 있으므로 대상 프로세스의 큰 힙을 읽는 데 너무 많은 호출이 필요합니다. 이것은 매우 느립니다.

  3. 이 도구는 특정 JVM 버전에 대한 지식을 기반으로 JVM 내부 구조를 재구성합니다. JVM의 버전마다 메모리 레이아웃이 다르기 때문에 -F모드 jmap는 대상 Java 프로세스와 동일한 JDK에서 온 경우에만 작동합니다 .

  4. 이 도구는 자체적으로 힙 덤프를 만든 다음 대상 프로세스를 다시 시작합니다.

찬성.

  • 대상 JVM의 협력이 필요하지 않습니다. 매달린 프로세스에서도 사용할 수 있습니다.
  • ptraceOS 수준 권한이 충분할 때마다 작동합니다. 예를 들어 root다른 모든 사용자의 프로세스를 덤프 할 수 있습니다.

단점.

  • 큰 힙의 경우 매우 느립니다.
  • 도구와 대상 프로세스는 동일한 버전의 JDK에 있어야합니다.
  • 도구가 강제 모드로 부착되면 Safepoint가 보장되지 않습니다. jmap모든 특수한 경우를 처리하려고 시도 하지만 때때로 대상 JVM이 일관된 상태가 아닌 경우가 발생할 수 있습니다.

노트

강제 모드에서 힙 덤프를 가져 오는 더 빠른 방법이 있습니다. 먼저를 사용하여 코어 덤프를 gcore만든 다음 jmap생성 된 코어 파일에서 실행 합니다. 관련 질문을 참조하십시오 .


방금 jmap (그리고 힙 덤프를 생성하는 데 사용할 때 jvisualvm)이 jmap을 실행하는 사용자가 덤프를 시도하는 프로세스를 실행하는 동일한 사용자 여야한다는 것을 확인했습니다.

제 경우에는 힙 덤프를 원하는 jvm이 리눅스 사용자 "jboss"에 의해 실행되고 있습니다. 그래서 sudo jmap -dump:file.bin <pid>"Unable to open socket :"을보고 한 에서 다음을 사용하여 힙 덤프를 가져올 수있었습니다.

sudo -u jboss jmap -dump:file.bin <pid>

ben_wing이 말한 것처럼 다음과 같이 실행할 수 있습니다.

sudo -u jboss-as jmap -dump:file.bin <pid>

(제 경우 사용자는 jboss-as이지만 귀하는jboss 또는 다른 .)

But it was not enough, because it asked me for a password ([sudo] password for ec2-user:), although I could run sudo without prompting me for a password with other commands.

I found the solution here, and I just needed to add another sudo first:

sudo sudo -u jboss-as jmap -dump:file.bin <pid>

It works with other commands like jcmd and jinfo too.


If your application is runing as a systemd service.You should open service file that under /usr/lib/systemd/system/ and named by your service name. Then check whether privateTmp attribute is true.

If it is true,you shoud change it to false,then refresh service by command as follow: systemctl daemon-reload systemctl restart [servicename] If you want runing jmap/jcmd before restart, you can make use of the execStop script in the service file. Just put command in it and to execute systemctl stop [service name]

참고URL : https://stackoverflow.com/questions/26140182/running-jmap-getting-unable-to-open-socket-file

반응형