Kích thước trang 16&KB

Kích thước trang là mức độ chi tiết mà hệ điều hành quản lý bộ nhớ. Hầu hết CPU hiện nay đều hỗ trợ kích thước trang 4 KB, vì vậy, hệ điều hành Android và các ứng dụng trước đây đã được xây dựng và tối ưu hoá để chạy với kích thước trang 4 KB. CPU ARM hỗ trợ kích thước trang lớn hơn là 16 KB và kể từ Android 15, AOSP cũng hỗ trợ việc tạo Android với kích thước trang là 16 KB. Tuỳ chọn này sử dụng thêm bộ nhớ nhưng cải thiện hiệu suất hệ thống. Kể từ Android 15, tuỳ chọn này không được bật theo mặc định, nhưng có sẵn dưới dạng chế độ dành cho nhà phát triển hoặc tuỳ chọn dành cho nhà phát triển để OEM và nhà phát triển ứng dụng chuẩn bị chuyển sang chế độ 16 KB ở mọi nơi trong tương lai.

Android 15 trở lên hỗ trợ việc tạo Android bằng cách căn chỉnh ELF 16 KB. Phương thức này hoạt động với các nhân 4 KB và 16 KB bắt đầu bằng android14-6.1. Khi được sử dụng với hạt nhân 16 KB, cấu hình này sẽ sử dụng thêm bộ nhớ nhưng cải thiện hiệu suất hệ thống.

Đặt không gian người dùng Android thành 16 KB

Trang 16 KB chỉ được hỗ trợ trên các mục tiêu arm64 có nhân 16 KB. Tuy nhiên, bạn cũng có thể chọn mô phỏng không gian người dùng 16 KB trên x86_64 cho Cuttlefish.

Đối với các mục tiêu arm64, nếu bạn sử dụng Kleaf để tạo nhân, --page_size=16k sẽ tạo nhân ở chế độ 16 KB. Nếu đang trực tiếp sử dụng cấu hình hạt nhân Linux, bạn có thể chọn các trang 16 KB bằng cách đặt CONFIG_ARM64_16K_PAGES thay vì CONFIG_ARM64_4K_PAGES.

Để bật tính năng hỗ trợ kích thước trang 16 KB trong không gian người dùng Android, hãy thiết lập các tuỳ chọn bản dựng sau đây trên sản phẩm của bạn:

  • PRODUCT_NO_BIONIC_PAGE_SIZE_MACRO := true xoá định nghĩa PAGE_SIZE và giúp các thành phần xác định kích thước trang trong thời gian chạy.
  • PRODUCT_MAX_PAGE_SIZE_SUPPORTED := 16384 đảm bảo các tệp ELF của nền tảng được tạo bằng cách căn chỉnh 16 KB. Kích thước lớn hơn mức cần thiết này là để đảm bảo khả năng tương thích trong tương lai. Với tính năng căn chỉnh ELF 16 KB, nhân có thể hỗ trợ kích thước trang 4 KB/16 KB.

Xác minh cờ bản dựng

Sau khi chọn mục tiêu lunch, hãy xác minh rằng các cờ bản dựng được thiết lập đúng cách trong môi trường:

$ source build/envsetup.sh
$ lunch target

$ get_build_var TARGET_MAX_PAGE_SIZE_SUPPORTED
16384
$ get_build_var TARGET_NO_BIONIC_PAGE_SIZE_MACRO
true

Nếu hai lệnh trước đó trả về lần lượt 16384true, thì cờ bản dựng của bạn đã được thiết lập chính xác để hoạt động với hạt nhân 16 KB. Tuy nhiên, ngay cả khi bản dựng vượt qua, vẫn có thể có vấn đề về thời gian chạy do sự khác biệt trong môi trường 16 KB.

Lập trình hệ thống kích thước trang 16 KB

Phần lớn mã trên mọi thiết bị chạy Android đều không trực tiếp xử lý kích thước trang. Tuy nhiên, đối với mã xử lý các trang, hành vi phân bổ bộ nhớ của nhân sẽ thay đổi và bạn cần lưu ý điều này để viết mã không chỉ tương thích mà còn có hiệu suất tối đa và sử dụng tài nguyên ở mức tối thiểu.

Nếu bạn gọi mmap trên vùng 1 KB, 2 KB hoặc tối đa 4 KB trên hệ thống 4 KB, thì hệ thống sẽ dành riêng 4 KB để triển khai việc này. Nói cách khác, khi yêu cầu bộ nhớ từ nhân, nhân phải luôn làm tròn bộ nhớ được yêu cầu thành kích thước trang gần nhất. Ví dụ: nếu bạn phân bổ một vùng 5 KB trên một vùng 4 KB, thì nhân sẽ phân bổ 8 KB.

Trên nhân 16 KB, các "đuôi" trang bổ sung này lớn hơn. Ví dụ: tất cả các mức phân bổ này, từ 1 KB đến 5 KB sẽ phân bổ 16 KB khi được sử dụng với hạt nhân 16 KB. Nếu bạn yêu cầu 17 KB, thì hệ thống sẽ phân bổ 32 KB.

Ví dụ: trên hệ thống 4 KB, bạn có thể phân bổ hai vùng ẩn danh đọc-ghi 4 KB. Tuy nhiên, trên nhân hệ điều hành 16 KB, việc này sẽ dẫn đến việc phân bổ hai trang hoặc 32 KB. Trên nhân 16 KB, nếu có thể, bạn có thể kết hợp các vùng này thành một trang có thể đọc hoặc ghi để chỉ sử dụng 16 KB, lãng phí 8 KB so với trường hợp nhân 4 KB. Để giảm mức sử dụng bộ nhớ hơn nữa, bạn có thể kết hợp nhiều trang hơn. Trên thực tế, trên hệ thống 16 KB được tối ưu hoá tối đa, các trang 16 KB yêu cầu ít bộ nhớ hơn so với hệ thống 4 KB vì bảng trang có kích thước bằng 1/4 đối với cùng một bộ nhớ.

Bất cứ khi nào sử dụng mmap, hãy đảm bảo rằng bạn làm tròn kích thước mà bạn đang yêu cầu lên đến kích thước trang gần nhất. Điều này đảm bảo rằng toàn bộ dung lượng bộ nhớ mà nhân phân bổ sẽ hiển thị trực tiếp cho không gian người dùng ở các giá trị thời gian chạy, thay vì được yêu cầu ngầm ẩn và có thể truy cập ngầm ẩn hoặc vô tình.

Tạo thư viện dùng chung có căn chỉnh ELF 16 KB

Để tạo thư viện dùng chung thuộc dự án Android, bạn chỉ cần các chế độ cài đặt trước đó trong phần Bật kích thước trang 16 KB:

  • PRODUCT_NO_BIONIC_PAGE_SIZE_MACRO := true
  • PRODUCT_MAX_PAGE_SIZE_SUPPORTED := 16384

Để tạo thư viện dùng chung không thuộc dự án Android, bạn cần truyền cờ trình liên kết này:

-Wl,-z,max-page-size=16384

Xác minh tệp nhị phân và tệp tạo sẵn để căn chỉnh ELF 16 KB

Cách tốt nhất để xác minh hoạt động căn chỉnh và thời gian chạy là kiểm thử và chạy trên nhân hệ điều hành được biên dịch 16 KB. Tuy nhiên, để phát hiện sớm một số vấn đề, hãy làm như sau:

  • Kể từ Android 16 (thử nghiệm AOSP), bạn có thể đặt PRODUCT_CHECK_PREBUILT_MAX_PAGE_SIZE := true tại thời điểm tạo bản dựng. Sử dụng ignore_max_page_size: true trong Android.bpLOCAL_IGNORE_MAX_PAGE_SIZE := true trong Android.mk để tạm thời bỏ qua các đối tượng này. Các chế độ cài đặt này xác minh tất cả các tệp tạo sẵn và cho phép bạn phát hiện thời điểm một tệp được cập nhật nhưng không được căn chỉnh 16 KB.

  • Bạn có thể chạy atest elf_alignment_test để xác minh việc căn chỉnh các tệp ELF trên thiết bị trên các thiết bị chạy Android 15 trở lên.