2011-09-22 24 views
71

Ai đó có thể giải thích tùy chọn JVM ReservedCodeCacheSizeInitialCodeCacheSize là gì? Cụ thể khi nào/tại sao tôi muốn thay đổi nó? Làm cách nào để quyết định kích thước phù hợp là gì?ReservedCodeCacheSize và InitialCodeCacheSize là gì?

Đây là những gì các tài liệu nói:

-XX: ReservedCodeCacheSize = 32m reserved mã kích thước bộ nhớ cache (theo byte) - mã kích thước bộ nhớ cache tối đa. [Solaris 64 bit, amd64 và máy chủ x86: 2048m; trong 1.5.0_06 trở về trước, Solaris 64-bit và and64:. 1024M]

+2

OP của bài đăng này đã viết:> -XX: ReservedCodeCacheSize = 32m Kích thước bộ nhớ cache dành riêng cho mã (theo byte) - kích thước bộ nhớ cache mã tối đa. [Solaris 64 bit, amd64 và máy chủ x86: 48m; trong 1.5.0_06 và trước đó, Solaris 64-bit và and64: 1024m.] Tôi chỉ muốn sửa rằng giới hạn trên được đề cập ở 48m phải là lỗi đánh máy. Đó là 2048m. –

Trả lời

66

ReservedCodeCacheSize (và InitialCodeCacheSize) là một lựa chọn cho các trình biên dịch (just-in-time) của Java Hotspot VM. Về cơ bản nó đặt kích thước tối đa cho bộ đệm mã của trình biên dịch.

Bộ nhớ cache có thể trở nên đầy đủ, mà kết quả trong những cảnh báo như sau:

Java HotSpot(TM) 64-Bit Server VM warning: CodeCache is full. Compiler has been disabled. 
Java HotSpot(TM) 64-Bit Server VM warning: Try increasing the code cache size using -XX:ReservedCodeCacheSize= 
Code Cache [0x000000010958f000, 0x000000010c52f000, 0x000000010c58f000) 
total_blobs=15406 nmethods=14989 adapters=362 free_code_cache=835Kb largest_free_block=449792 

Nó còn tồi tệ hơn nhiều khi tiếp theo Java HotSpot(TM) Client VM warning: Exception java.lang.OutOfMemoryError occurred dispatching signal SIGINT to handler- the VM may need to be forcibly terminated.

Khi nào đặt tùy chọn này?

  1. khi có thất bại biên dịch Hotspot
  2. để giảm bộ nhớ cần thiết bởi JVM (và do đó rủi ro thất bại trình biên dịch JIT)

Thông thường bạn sẽ không thay đổi giá trị này. Tôi nghĩ rằng các giá trị mặc định là khá cân bằng bởi vì vấn đề này xảy ra vào những dịp rất hiếm chỉ (trong experince của tôi).

+1

Rất đẹp. Giá trị mặc định là gì và chúng sẽ được tăng lên như thế nào nếu chúng ta thấy "CodeCache đã đầy." cảnh báo? – axel22

+2

@ axel22: Các giá trị thực sự phụ thuộc vào nền tảng và phiên bản JVM; các giá trị từ tài liệu cho Sun JVM: 'Kích thước bộ nhớ cache mã dự trữ (tính bằng byte) - kích thước bộ nhớ cache mã tối đa. [Solaris 64 bit, amd64 và máy chủ x86: 48m; trong 1.5.0_06 trở về trước, Solaris 64-bit và amd64: 1024m.] 'Không biết các giá trị OpenJDK. Một sự gia tăng vừa phải là đủ (thiết lập trước đó của 1024m là vượt quá tốt một điều ác). – jeha

12

@jeha trả lời mọi thứ tôi muốn biết từ câu hỏi này, ngoài giá trị để đặt tham số. Vì tôi đã không viết mã tôi đã triển khai, tôi không có nhiều khả năng hiển thị trong bộ nhớ mà nó có.

Tuy nhiên, bạn có thể sử dụng jconsole để đính kèm vào quá trình java đang chạy của mình, sau đó sử dụng tab 'Bộ nhớ' để tìm hiểu kích thước Bộ nhớ cache của mã. Cho đầy đủ, các bước (Linux VM môi trường, mặc dù tôi chắc chắn rằng các môi trường khác cũng tương tự):

  1. cháy lên jconsole trên máy tính của bạn
  2. Tìm quá trình ID đúng và đính kèm jconsole với nó (điều này sẽ dành một vài phút)
  3. Điều hướng đến tab 'Memory'
  4. Từ 'Chart:' danh sách thả xuống, chọn 'Memory Pool 'Mã cache''
  5. một lần nữa, điều này có thể mất một vài khoảnh khắc để màn hình làm mới, và sau đó bạn sẽ thấy một cái gì đó như: jconsole code cache image

    Như bạn thấy, bộ nhớ cache mã của tôi đang sử dụng xấp xỉ 49 MB. Tại thời điểm này tôi vẫn có mặc định mà tài liệu (và @ jeha) nói là 48 MB. Chắc chắn là một động lực tuyệt vời cho tôi để tăng cường các thiết lập!

    Ben.


    1024 MB theo mặc định có thể đã lạm dụng nó, nhưng 48 MB theo mặc định có vẻ là không làm điều đó ...

+0

Đề nghị tốt .... Tôi đang thử với -J-XX: ReservedCodeCacheSize = 512m – MarcoZen

+0

Netbeans sẽ không bắt đầu với 512m, đã làm với 256m – MarcoZen

+0

Và sau khi thử nghiệm trong khoảng 2 ngày tôi có thể nói rằng cài đặt không hiển thị bất kỳ/bất kỳ cải thiện đáng chú ý và thay vào đó làm netbeans tipsy. Tôi đã kết thúc chỉ cần loại bỏ nó. – MarcoZen

11

Khi JVM biên dịch mã, nó giữ tập hợp các hướng dẫn lắp ráp trong bộ đệm mã . Bộ nhớ cache mã có kích thước cố định và khi nó đã được lấp đầy, JVM không phải là có thể biên dịch bất kỳ mã bổ sung nào.

Kích thước tối đa của bộ đệm mã được đặt qua -XX: ReservedCodeCacheSize = N cờ (trong đó N là mặc định vừa được đề cập cho trình biên dịch cụ thể). Bộ nhớ cache mã là được quản lý giống như hầu hết bộ nhớ trong JVM: có kích thước ban đầu ( -XX: InitialCodeCacheSize = N). Phân bổ kích thước bộ nhớ cache mã bắt đầu ở kích thước ban đầu là và tăng lên khi bộ nhớ cache đầy. Kích thước ban đầu của bộ nhớ cache mã thay đổi dựa trên kiến ​​trúc và trình biên dịch chip được sử dụng. Thay đổi kích thước bộ nhớ cache xảy ra trong nền và không thực sự ảnh hưởng đến hiệu suất, vì vậy, hãy đặt kích thước ReservedCodeCacheSize (tức là, đặt kích thước bộ nhớ cache tối đa) là tất cả là thường cần thiết.

Theo mặc định cho máy chủ 64 bit, kích thước Java 7 là 48 MB (với trình biên dịch theo cấp là 96 MB). Trong Java 8 cho máy chủ 64 bit, dung lượng bộ nhớ là 240 MB.

- Pinaki

+2

+1 để đề cập đến sự khác biệt về kích thước Java 7/Java 8. Tôi nghi ngờ điều này là do biên dịch theo tầng được bật theo mặc định trong Java 8. – jdv

+0

Bạn đã biên dịch theo tầng chính xác được ổn định sau 1.7.40 trước khi chúng có một số vấn đề với nó. Việc biên dịch theo tầng có thể dễ dàng sử dụng toàn bộ bộ đệm mã trong cấu hình mặc định của nó, do đó chúng tăng lên mức an toàn hơn ở Java8. –

1

Một kinh nghiệm học tập tốt từ thực tế đội ngũ kỹ thuật và thách thức mà họ phải đối mặt khi chuyển sang JDK 8.

http://engineering.indeedblog.com/blog/2016/09/job-search-web-app-java-8-migration/

Kết luận: JDK 8 cần nhớ cache nhiều mã han JDK 7

Kích thước codecache mặc định cho JRE 8 là khoảng 250MB, khoảng năm lần lớn hơn 48MB mặc định cho JRE 7. Kinh nghiệm của chúng tôi là JRE 8 cần thêm codecache đó. Chúng tôi đã chuyển khoảng mười dịch vụ sang JRE 8 cho đến nay và tất cả chúng đều sử dụng codecache gấp bốn lần so với trước đây.

0

từ https://blogs.oracle.com/poonam/entry/why_do_i_get_message:

Sau đây là hai vấn đề được biết đến trong jdk7u4 + Đối với việc xả CodeCache với:

  1. Trình biên dịch có thể không được khởi động lại ngay cả sau khi tỷ lệ lấp đầy CodeCache giảm xuống gần một nửa sau khi xả nước khẩn cấp.
  2. Việc xả khẩn cấp có thể gây ra việc sử dụng CPU cao bởi các luồng trình biên dịch dẫn đến suy giảm hiệu suất tổng thể.

Vấn đề về hiệu suất này và sự cố của trình biên dịch không được kích hoạt lại đã được giải quyết trong JDK8. Để giải quyết vấn đề này trong JDK7u4 +, chúng tôi có thể tăng kích thước bộ nhớ cache của mã bằng cách sử dụng tùy chọn ReservedCodeCacheSize bằng cách đặt nó thành giá trị lớn hơn dấu vết mã được biên dịch để CodeCache không bao giờ đầy. Một giải pháp khác cho việc này là vô hiệu hóa tính năng CodeCache Flushing bằng cách sử dụng tùy chọn JVM--seCodeCacheFlushing JVM.

Các vấn đề đã đề cập ở trên đã được khắc phục trong JDK8 và các bản cập nhật của nó.

Vì vậy, thông tin đó có thể đáng nhắc đến đối với các hệ thống chạy trên JDK 6 (đã tắt chức năng xả mã) và 7.