এই পৃষ্ঠাটি অ্যান্ড্রয়েড ১২-তে প্রবর্তিত বিভিন্ন মেমরি অ্যাকাউন্টিং উন্নতির বর্ণনা দেয়।
sysfs-এ DMA-BUF পরিসংখ্যান
অ্যান্ড্রয়েড ১১ এবং অ্যান্ড্রয়েড ১২-তে, ব্যবহারকারী বিল্ডগুলিতে debugfs মাউন্ট করা যাবে না। তাই অ্যান্ড্রয়েড ১২-তে /sys/kernel/dmabuf/buffers ডিরেক্টরিতে sysfs এ DMA-BUF পরিসংখ্যান যোগ করা হয়েছে।
| পথ | বিবরণ |
|---|---|
/sys/kernel/dmabuf/buffers | /sys/kernel/dmabuf/buffers ডিরেক্টরিতে প্রতিটি DMA-BUF-এর অভ্যন্তরীণ অবস্থার একটি স্ন্যাপশট থাকে। /sys/kernel/dmabuf/buffers/<inode_number> অনন্য ইনোড নম্বর <inode_number> সহ DMA-BUF-এর পরিসংখ্যান থাকে। |
/sys/kernel/dmabuf/buffers/<inode_number>/exporter_name | এই পঠনযোগ্য ফাইলটিতে DMA-BUF রপ্তানিকারকের নাম রয়েছে। |
/sys/kernel/dmabuf/buffers/<inode_number>/size | এই পঠনযোগ্য ফাইলটি বাইটে DMA-BUF এর আকার নির্দিষ্ট করে। |
libdmabufinfo API প্রতি-রপ্তানিকারী এবং প্রতি-বাফার পরিসংখ্যান প্রকাশ করার জন্য DMA-BUF sysfs পরিসংখ্যান বিশ্লেষণ করে।
DMA-BUF এক্সপোর্টকারী কার্নেল ড্রাইভারদের DMA-BUF তৈরি করার জন্য dma_buf_export() API ব্যবহার করার আগে struct dma_buf_export_info এর exp_name ফিল্ডটি সঠিকভাবে এক্সপোর্টার নামের সাথে সেট করতে হবে। libdmabufinfo এবং dmabuf_dump টুলের জন্য প্রতি-এক্সপোর্টার পরিসংখ্যান বের করার জন্য এটি প্রয়োজন, যা পরে বাগ রিপোর্টে প্রকাশিত হয়।
dmabuf_dump টুলটি একটি নতুন আর্গুমেন্ট, -b দিয়ে এই তথ্য আউটপুট করার জন্য পরিবর্তন করা হয়েছে।
DMA-BUF হিপস ফ্রেমওয়ার্কের পরিসংখ্যান
GKI 2.0-এ ION DMA-BUF হিপস ফ্রেমওয়ার্কের পক্ষে অবচিত হচ্ছে, যা আপস্ট্রিম লিনাক্স কার্নেলের অংশ।
নিম্নলিখিত বিশ্বব্যাপী ION পরিসংখ্যানগুলি Android 11-এ ট্র্যাক করা হয়েছে:
- প্রতিটি ION হিপ দ্বারা রপ্তানি করা DMA-BUF-এর মোট আকার
- প্রতিটি ION হিপ দ্বারা সঞ্চিত অব্যবহৃত পূর্ব-বরাদ্দকৃত মেমরির মোট আকার
অ্যান্ড্রয়েড ১১-এ প্রতি-আইওএন হিপ পরিসংখ্যান প্রকাশ করার জন্য কোনও ইন্টারফেস উপলব্ধ নেই।
নিম্নলিখিত সারণীটি অ্যান্ড্রয়েড ১২-তে DMA-BUF হিপ ফ্রেমওয়ার্ক ব্যবহার করে এমন ডিভাইসগুলির জন্য ION পরিসংখ্যান ইন্টারফেসগুলির সাথে তাদের প্রতিরূপগুলির তুলনা করে।
| অ্যান্ড্রয়েড ১১ অথবা অ্যান্ড্রয়েড ১২-তে আইওএন সাপোর্ট সহ লঞ্চ হওয়া ডিভাইসগুলি | অ্যান্ড্রয়েড ১২-তে DMA-BUF হিপস সহ লঞ্চ হওয়া ডিভাইসগুলি | |
|---|---|---|
| প্রতি-হিপ আইওএন পরিসংখ্যান | কোনটিই নয় | DMA-BUF sysfs পরিসংখ্যান থেকে বিশ্লেষণ করা হয়েছে |
| রপ্তানি করা মোট DMA-BUF-এর আকার | /sys/kernel/ion/total_heap_size_kb(আইওএন-বহির্ভূত রপ্তানিকারকদের দ্বারা রপ্তানি করা DMA-BUF-এর আকার অন্তর্ভুক্ত নয়) | DMA-BUF sysfs পরিসংখ্যান থেকে বিশ্লেষণ করা হয়েছে (রপ্তানি করা সমস্ত DMA-BUF-এর আকার অন্তর্ভুক্ত)। |
| হিপ দ্বারা পুল করা মোট মেমোরি | /sys/kernel/ion/total_pool_size_kb | /sys/kernel/dma_heap/total_pool_size_kb |
হারানো RAM গণনার নির্ভুলতা উন্নত করুন
পূর্বে হারানো RAM গণনা নিম্নরূপ করা হত:
চূড়ান্ত দীর্ঘ lostRAM = memInfo.getTotalSizeKb( ) - ( totalPss - totalSwapPss )
- memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
- kernelUsed - memInfo.getZramTotalSizeKb() ;
totalPss কম্পোনেন্টে GPU মেমোরি ব্যবহার অন্তর্ভুক্ত ছিল (Memtrack HAL এর getMemory() ইন্টারফেস দ্বারা ফেরত পাঠানো হয়েছে)। kernelUsed কম্পোনেন্টে মোট DMA-BUF মেমোরি ব্যবহার অন্তর্ভুক্ত ছিল। তবে, অ্যান্ড্রয়েড ডিভাইসের জন্য, GPU মেমোরি নিম্নলিখিত থেকে এসেছে:
- ফিজিক্যাল পেজ অ্যালোকেটর ব্যবহার করে GPU ড্রাইভার দ্বারা সরাসরি বরাদ্দকরণ
- GPU ঠিকানা স্থানে DMA-BUF ম্যাপ করা হয়েছে
অতএব, GPU ঠিকানা স্পেসে মেমরি-ম্যাপ করা DMA-BUF গুলি হারানো RAM গণনা করার সময় দুবার বিয়োগ করা হয়েছিল। Android 12 GPU ঠিকানা স্পেসে ম্যাপ করা DMA-BUF গুলির আকার গণনা করার জন্য একটি সমাধান প্রয়োগ করে, যার অর্থ হল হারানো RAM গণনায় এটি শুধুমাত্র একবারের জন্য হিসাব করা হয়েছে।
সমাধানের বিস্তারিত নিম্নরূপ:
- Memtrack HAL API
getMemory()যখন PID 0 দিয়ে কল করা হয় তখনMemtrackType::GLএবংMemtrackRecord::FLAG_SMAPS_UNACCOUNTEDজন্য বিশ্বব্যাপী মোট GPU-প্রাইভেট মেমরি রিপোর্ট করতে হবে। -
GLব্যতীত অন্য কোনওMemtrackTypeজন্যPID 0দিয়ে কল করা হলেgetMemory()অবশ্যই ব্যর্থ হবে না। বরং এটি অবশ্যই 0 প্রদান করবে। - অ্যান্ড্রয়েড ১২-তে যোগ করা GPU মেমোরি ট্রেসপয়েন্ট/eBPF সলিউশন মোট GPU মেমোরির জন্য হিসাব করে। মোট GPU মেমোরি থেকে মোট GPU প্রাইভেট মেমোরি বিয়োগ করলে GPU অ্যাড্রেস স্পেসে ম্যাপ করা DMA-BUF-এর আকার পাওয়া যায়। এরপর GPU মেমোরি ব্যবহারের সঠিক হিসাব করে লস্ট র্যাম গণনার নির্ভুলতা উন্নত করতে মানটি ব্যবহার করা যেতে পারে।
- বেশিরভাগ Memtrack HAL বাস্তবায়নে
totalPssএ প্রাইভেট GPU মেমরি অন্তর্ভুক্ত থাকে এবং তাইlostRAMথেকে অপসারণের আগে এটিকে ডিডুপ্লিকেট করতে হবে।
বাস্তবায়িত সমাধানটি পরবর্তী বিভাগে বিস্তারিতভাবে বর্ণনা করা হয়েছে।
হারানো RAM থেকে Memtrack পরিবর্তনশীলতা সরান
যেহেতু Memtrack HAL বাস্তবায়নগুলি অংশীদারদের মধ্যে পরিবর্তিত হতে পারে, তাই HAL থেকে totalPSS এ অন্তর্ভুক্ত GPU মেমরি সর্বদা সামঞ্জস্যপূর্ণ নয়। lostRAM থেকে পরিবর্তনশীলতা অপসারণ করতে, lostRAM গণনার সময় MemtrackType::GRAPHICS এবং MemtrackType::GL এ থাকা মেমরিটি totalPss থেকে সরানো হয়।
নিম্নলিখিত কোডে দেখানো হয়েছে, ActivityManagerService.java- তে lostRAM গণনায় MemtrackType::GRAPHICS মেমরি totalPss থেকে সরানো হয়েছে এবং totalExportedDmabuf মেমরি দিয়ে প্রতিস্থাপিত হয়েছে:
final long totalExportedDmabuf = Debug.getDmabufTotalExportedKb();
. . .
final long dmabufUnmapped = totalExportedDmabuf - dmabufMapped;
. . .
// Account unmapped dmabufs as part of the kernel memory allocations
kernelUsed += dmabufUnmapped;
// Replace Memtrack HAL reported Graphics category with mapped dmabufs
totalPss -= totalMemtrackGraphics;
totalPss += dmabufMapped;
নিম্নলিখিত কোডে দেখানো হয়েছে, ActivityManagerService.java- তে lostRAM গণনায় MemtrackType::GL মেমরি totalPss থেকে সরানো হয়েছে এবং private GPU মেমরি ( gpuPrivateUsage ) দিয়ে প্রতিস্থাপিত হয়েছে:
final long gpuUsage = Debug.getGpuTotalUsageKb();
. . .
final long gpuPrivateUsage = Debug.getGpuPrivateMemoryKb();
. . .
// Replace the Memtrack HAL-reported GL category with private GPU allocations.
// Count it as part of the kernel memory allocations.
totalPss -= totalMemtrackGl;
kernelUsed += gpuPrivateUsage;
হারানো RAM গণনা আপডেট করা হয়েছে
মোট প্রাইভেট GPU মেমোরি এবং মোট এক্সপোর্ট করা DMA বাফার মেমোরি উভয়ই kernelUsed + totalPss এ থাকে যা lostRAM থেকে সরানো হয়। এটি হারানো RAM গণনা থেকে ডাবল-কাউন্টিং এবং Memtrack পরিবর্তনশীলতা উভয়ই দূর করে।
final long lostRAM = memInfo.getTotalSizeKb() - (totalPss - totalSwapPss)
- memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb()
- kernelUsed - memInfo.getZramTotalSizeKb();
বৈধতা
VTS পরীক্ষাগুলি এই নিয়মটি প্রয়োগ করে যে Android 12-এ Linux কার্নেল সংস্করণ 5.4 বা উচ্চতর সংস্করণ সহ লঞ্চ হওয়া ডিভাইসগুলি getGpuDeviceInfo() API সমর্থন করে।
একটি নতুন Memtrack HAL API getGpuDeviceInfo() অবশ্যই ব্যবহৃত GPU ডিভাইস সম্পর্কে তথ্য প্রদান করবে।
এটি DMA বাফার এবং GPU মেমরি ব্যবহারের ক্ষেত্রে আরও ভালো মেমরি অ্যাকাউন্টিং এবং দৃশ্যমানতা প্রদান করে। হারিয়ে যাওয়া RAM এবং মেমরি অ্যাকাউন্টিংয়ের জন্য memtrack AIDL HAL প্রয়োগ করুন। এই বৈশিষ্ট্যটি Google পরিষেবার উপর নির্ভরশীল নয়।
বাস্তবায়ন
এই বৈশিষ্ট্যটি AIDL Memtrack HAL এর উপর নির্ভর করে, এবং Android 12 এ এটি বাস্তবায়নের নির্দেশাবলী মন্তব্য হিসাবে কোডে অন্তর্ভুক্ত করা হয়েছে। ভবিষ্যতের রিলিজে সমস্ত HIDL HAL কে AIDL এ রূপান্তর করার পরিকল্পনা করা হয়েছে।
core/java/android/os/Debug.java তে নিম্নলিখিত API গুলি যোগ করা হয়েছে:
/**
* Return total memory size in kilobytes for exported DMA-BUFs or -1 if
* the DMA-BUF sysfs stats at /sys/kernel/dmabuf/buffers could not be read.
*
* @hide
*/
public static native long getDmabufTotalExportedKb();
/**
* Return memory size in kilobytes allocated for DMA-BUF heap pools or -1 if
* /sys/kernel/dma_heap/total_pools_kb could not be read.
*
* @hide
*/
public static native long getDmabufHeapPoolsSizeKb();
আপনার সংস্করণটি উদ্দেশ্য অনুযায়ী কাজ করছে কিনা তা যাচাই করতে, আপনার GPU ড্রাইভারগুলিতে ট্রেসপয়েন্টগুলি একীভূত করুন এবং MemtrackType::GL এবং MemtrackRecord::FLAG_SMAPS_UNACCOUNTED এর জন্য PID 0 দিয়ে কল করার সময় বিশ্বব্যাপী মোট GPU-প্রাইভেট মেমরি সঠিকভাবে ফেরত দিতে AIDL memtrack HAL getMemory() API প্রয়োগ করুন।