অডিও ডিবাগিং

এই নিবন্ধটি Android অডিও ডিবাগ করার জন্য কিছু টিপস এবং কৌশল বর্ণনা করে।

টি সিঙ্ক

"টি সিঙ্ক" হল একটি AudioFlinger ডিবাগিং বৈশিষ্ট্য, যা শুধুমাত্র কাস্টম বিল্ডে উপলব্ধ, সাম্প্রতিক অডিওর একটি ছোট অংশ পরবর্তী বিশ্লেষণের জন্য ধরে রাখার জন্য। এটি আসলে যা বাজানো বা রেকর্ড করা হয়েছে বনাম যা প্রত্যাশিত ছিল তার মধ্যে তুলনা করার অনুমতি দেয়।

গোপনীয়তার জন্য কম্পাইল-টাইম এবং রান-টাইম উভয় সময়েই টি সিঙ্ক ডিফল্টরূপে নিষ্ক্রিয় থাকে। টি সিঙ্ক ব্যবহার করার জন্য, আপনাকে এটি পুনরায় কম্পাইল করে এবং একটি সম্পত্তি সেট করে সক্ষম করতে হবে। আপনি ডিবাগিং সম্পন্ন করার পরে এই বৈশিষ্ট্যটি নিষ্ক্রিয় করতে ভুলবেন না; টি-সিঙ্ককে প্রোডাকশন বিল্ডে সক্রিয় রেখে দেওয়া উচিত নয়।

এই বিভাগে নির্দেশাবলী Android 7.x এবং উচ্চতর সংস্করণের জন্য। Android 5.x এবং 6.x-এর জন্য, /data/misc/audioserver কে /data/misc/media /media দিয়ে প্রতিস্থাপন করুন। অতিরিক্তভাবে, আপনাকে অবশ্যই একটি userdebug বা eng বিল্ড ব্যবহার করতে হবে। আপনি যদি একটি userdebug বিল্ড ব্যবহার করেন, তাহলে এর সাথে সত্যতা অক্ষম করুন:

adb root && adb disable-verity && adb reboot

কম্পাইল-টাইম সেটআপ

  1. cd frameworks/av/services/audioflinger
  2. Configuration.h সম্পাদনা করুন।
  3. #define TEE_SINK .
  4. libaudioflinger.so পুনরায় তৈরি করুন।
  5. adb root
  6. adb remount
  7. নতুন libaudioflinger.so ডিভাইসের /system/lib lib-এ পুশ বা সিঙ্ক করুন।

রান-টাইম সেটআপ

  1. adb shell getprop | grep ro.debuggable
    নিশ্চিত করুন যে আউটপুট হল: [ro.debuggable]: [1]
  2. adb shell
  3. ls -ld /data/misc/audioserver

    নিশ্চিত করুন যে আউটপুট হল:

    drwx------ media media ... media
    

    যদি ডিরেক্টরিটি বিদ্যমান না থাকে তবে এটি নিম্নরূপ তৈরি করুন:

    mkdir /data/misc/audioserver
    chown media:media /data/misc/audioserver
    
  4. echo af.tee=# > /data/local.prop
    যেখানে af.tee মান নিচে বর্ণিত একটি সংখ্যা।
  5. chmod 644 /data/local.prop
  6. reboot

af.tee সম্পত্তি জন্য মান

af.tee এর মান হল 0 এবং 7-এর মধ্যে একটি সংখ্যা, যা বিভিন্ন বিটের সমষ্টি প্রকাশ করে, প্রতি বৈশিষ্ট্যে একটি। প্রতিটি বিটের ব্যাখ্যার জন্য AudioFlinger.cppAudioFlinger::AudioFlinger() দেখুন, কিন্তু সংক্ষেপে:

  • 1 = ইনপুট
  • 2 = ফাস্টমিক্সার আউটপুট
  • 4 = প্রতি-ট্র্যাক AudioRecord এবং AudioTrack

ডিপ বাফার বা সাধারণ মিক্সারের জন্য এখনও কোনও বিট নেই, তবে আপনি "4" ব্যবহার করে একই ফলাফল পেতে পারেন।

পরীক্ষা এবং তথ্য অর্জন

  1. আপনার অডিও পরীক্ষা চালান.
  2. adb shell dumpsys media.audio_flinger
  3. dumpsys আউটপুটে একটি লাইন সন্ধান করুন যেমন:
    tee copied to /data/misc/audioserver/20131010101147_2.wav
    এটি একটি PCM .wav ফাইল।
  4. তারপর adb pull আগ্রহের যেকোনো /data/misc/audioserver/*.wav ফাইল টানুন; মনে রাখবেন যে ট্র্যাক-নির্দিষ্ট ডাম্প ফাইলের নাম dumpsys আউটপুটে প্রদর্শিত হয় না, তবে ট্র্যাক বন্ধ করার পরেও /data/misc/audioserver এ সংরক্ষিত হয়।
  5. অন্যদের সাথে ভাগ করার আগে গোপনীয়তার উদ্বেগের জন্য ডাম্প ফাইলগুলি পর্যালোচনা করুন৷

পরামর্শ

আরও দরকারী ফলাফলের জন্য এই ধারণাগুলি চেষ্টা করুন:

  • পরীক্ষার আউটপুটে বাধা কমাতে স্পর্শ শব্দ এবং কী ক্লিকগুলি অক্ষম করুন৷
  • সমস্ত ভলিউম সর্বাধিক করুন।
  • মাইক্রোফোন থেকে শব্দ বা রেকর্ড করে এমন অ্যাপগুলি অক্ষম করুন, যদি সেগুলি আপনার পরীক্ষায় আগ্রহী না হয়।
  • ট্র্যাক-নির্দিষ্ট ডাম্প শুধুমাত্র সংরক্ষিত হয় যখন ট্র্যাক বন্ধ থাকে; একটি অ্যাপের ট্র্যাক-নির্দিষ্ট ডেটা ডাম্প করার জন্য আপনাকে জোর করে বন্ধ করতে হতে পারে
  • পরীক্ষার পর অবিলম্বে dumpsys করুন; রেকর্ডিং স্থান সীমিত পরিমাণ উপলব্ধ আছে.
  • আপনি আপনার ডাম্প ফাইলগুলি হারাবেন না তা নিশ্চিত করতে, পর্যায়ক্রমে আপনার হোস্টে আপলোড করুন। শুধুমাত্র সীমিত সংখ্যক ডাম্প ফাইল সংরক্ষণ করা হয়; সেই সীমাতে পৌঁছানোর পরে পুরানো ডাম্পগুলি সরানো হয়।

পুনরুদ্ধার করুন

উপরে উল্লিখিত হিসাবে, টি সিঙ্ক বৈশিষ্ট্যটি সক্ষম করা উচিত নয়। নিম্নলিখিত হিসাবে আপনার বিল্ড এবং ডিভাইস পুনরুদ্ধার করুন:

  1. সোর্স কোড পরিবর্তনগুলি Configuration.h এ ফিরিয়ে দিন।
  2. libaudioflinger.so পুনরায় তৈরি করুন।
  3. পুনরুদ্ধার করা libaudioflinger.so ডিভাইসের /system/lib lib-এ পুশ বা সিঙ্ক করুন।
  4. adb shell
  5. rm /data/local.prop
  6. rm /data/misc/audioserver/*.wav
  7. reboot

media.log

ALOGx ম্যাক্রো

অ্যান্ড্রয়েড এসডিকে-তে স্ট্যান্ডার্ড জাভা ল্যাঙ্গুয়েজ লগিং API হল android.util.Log

Android NDK-তে সংশ্লিষ্ট C ভাষা API হল __android_log_print ঘোষিত <android/log.h>

অ্যান্ড্রয়েড ফ্রেমওয়ার্কের স্থানীয় অংশের মধ্যে, আমরা ALOGE , ALOGW , ALOGI , ALOGV , ইত্যাদি নামের ম্যাক্রো পছন্দ করি। সেগুলি <utils/Log.h> -এ ঘোষণা করা হয়েছে, এবং এই নিবন্ধটির উদ্দেশ্যে আমরা তাদের সম্মিলিতভাবে ALOGx হিসাবে উল্লেখ করব .

এই সমস্ত APIগুলি ব্যবহার করা সহজ এবং ভালভাবে বোঝা যায়, তাই তারা অ্যান্ড্রয়েড প্ল্যাটফর্ম জুড়ে বিস্তৃত৷ বিশেষ করে mediaserver প্রক্রিয়া, যার মধ্যে অডিওফ্লিংগার সাউন্ড সার্ভার রয়েছে, ব্যাপকভাবে ALOGx ব্যবহার করে।

তবুও, ALOGx এবং বন্ধুদের কিছু সীমাবদ্ধতা রয়েছে:

  • তারা "লগ স্প্যাম"-এর জন্য সংবেদনশীল: লগ বাফার একটি শেয়ার্ড রিসোর্স তাই এটি অসংলগ্ন লগ এন্ট্রির কারণে সহজেই ওভারফ্লো হতে পারে, ফলে তথ্য মিস হয়ে যায়। ALOGV ভেরিয়েন্ট ডিফল্টরূপে কম্পাইল-টাইমে নিষ্ক্রিয় করা হয়। তবে অবশ্যই এটি সক্রিয় থাকলে লগ স্প্যাম হতে পারে।
  • অন্তর্নিহিত কার্নেল সিস্টেম কলগুলি ব্লক করতে পারে, সম্ভবত অগ্রাধিকার বিপরীতে পরিণত হতে পারে এবং ফলস্বরূপ পরিমাপের ব্যাঘাত এবং ভুল। FastMixer এবং FastCapture মতো সময়-সমালোচনামূলক থ্রেডগুলির জন্য এটি বিশেষ উদ্বেগের বিষয়।
  • যদি লগ স্প্যাম কমাতে একটি নির্দিষ্ট লগ অক্ষম করা হয়, তাহলে সেই লগ দ্বারা ক্যাপচার করা যেকোন তথ্য হারিয়ে যাবে। লগটি আকর্ষণীয় হবে তা স্পষ্ট হয়ে যাওয়ার পরে পূর্ববর্তীভাবে একটি নির্দিষ্ট লগ সক্রিয় করা সম্ভব নয়।

NBLOG, media.log, এবং MediaLogService

NBLOG APIs এবং সংশ্লিষ্ট media.log প্রক্রিয়া এবং MediaLogService পরিষেবা একসাথে মিডিয়ার জন্য একটি নতুন লগিং সিস্টেম গঠন করে, এবং বিশেষভাবে উপরের সমস্যাগুলি সমাধান করার জন্য ডিজাইন করা হয়েছে৷ আমরা তিনটির উল্লেখ করার জন্য "media.log" শব্দটি ঢিলেঢালাভাবে ব্যবহার করব, কিন্তু কঠোরভাবে বলতে গেলে NBLOG হল C++ লগিং API, media.log হল একটি Linux প্রক্রিয়ার নাম, এবং MediaLogService হল লগগুলি পরীক্ষা করার জন্য একটি Android বাইন্ডার পরিষেবা৷

একটি media.log "টাইমলাইন" হল লগ এন্ট্রিগুলির একটি সিরিজ যার আপেক্ষিক ক্রম সংরক্ষিত থাকে৷ নিয়ম অনুসারে, প্রতিটি থ্রেডের নিজস্ব টাইমলাইন ব্যবহার করা উচিত।

সুবিধা

media.log সিস্টেমের সুবিধা হল এটি:

  • মূল লগ স্প্যাম করে না যদি না এবং যতক্ষণ না এটি প্রয়োজন হয়।
  • mediaserver ক্র্যাশ বা হ্যাং হয়ে গেলেও পরীক্ষা করা যেতে পারে।
  • টাইমলাইন প্রতি অ-ব্লক করা হয়.
  • কর্মক্ষমতা কম ব্যাঘাত অফার. (অবশ্যই কোন প্রকার লগিং সম্পূর্ণরূপে অ-অনুপ্রবেশকারী নয়।)

স্থাপত্য

নিচের চিত্রটি media.log mediaserver এবং init প্রক্রিয়ার সম্পর্ক দেখায়:

media.log এর আগে আর্কিটেকচার

চিত্র 1. media.log এর আগে আর্কিটেকচার

উল্লেখযোগ্য পয়েন্ট:

  • init forks এবং execs mediaserver
  • init mediaserver মৃত্যু শনাক্ত করে এবং প্রয়োজনে পুনরায় কাঁটাচামচ করে।
  • ALOGx লগিং দেখানো হয় না।

media.log আর্কিটেকচারে যোগ করার পরে নীচের চিত্রটি উপাদানগুলির নতুন সম্পর্ক দেখায়:

media.log পরে আর্কিটেকচার

চিত্র 2. media.log এর পরে আর্কিটেকচার

গুরুত্বপূর্ণ পরিবর্তন:

  • ক্লায়েন্টরা লগ এন্ট্রি তৈরি করতে NBLOG API ব্যবহার করে এবং শেয়ার করা মেমরিতে একটি বৃত্তাকার বাফারে যুক্ত করে।
  • MediaLogService যেকোনো সময় সার্কুলার বাফারের বিষয়বস্তু ডাম্প করতে পারে।
  • সার্কুলার বাফারটি এমনভাবে ডিজাইন করা হয়েছে যাতে শেয়ার করা মেমরির কোনো দুর্নীতি MediaLogService ক্র্যাশ করবে না এবং এটি এখনও ততটা বাফার ডাম্প করতে সক্ষম হবে যা দুর্নীতি দ্বারা প্রভাবিত হয় না।
  • নতুন এন্ট্রি লেখা এবং বিদ্যমান এন্ট্রি পড়ার জন্য সার্কুলার বাফারটি নন-ব্লকিং এবং লক-মুক্ত।
  • সার্কুলার বাফার থেকে (ঐচ্ছিক টাইমস্ট্যাম্প ছাড়া) লিখতে বা পড়ার জন্য কোন কার্নেল সিস্টেম কলের প্রয়োজন নেই।

কোথায় ব্যবহার করতে হবে

অ্যান্ড্রয়েড 4.4 হিসাবে, AudioFlinger-এ শুধুমাত্র কয়েকটি লগ পয়েন্ট রয়েছে যা media.log সিস্টেম ব্যবহার করে। যদিও নতুন API গুলি ALOGx এর মতো ব্যবহার করা সহজ নয়, তবে সেগুলি খুব কঠিনও নয়৷ আমরা আপনাকে সেই অনুষ্ঠানগুলির জন্য নতুন লগিং সিস্টেম শিখতে উত্সাহিত করি যখন এটি অপরিহার্য। বিশেষ করে, এটি অডিওফ্লিঙ্গার থ্রেডগুলির জন্য সুপারিশ করা হয় যেগুলি অবশ্যই ঘন ঘন, পর্যায়ক্রমে এবং ব্লক না করে যেমন FastMixer এবং FastCapture থ্রেডগুলি চালাতে হবে৷

ব্যবহারবিধি

লগ যোগ করুন

প্রথমত, আপনাকে আপনার কোডে লগ যোগ করতে হবে।

FastMixer এবং FastCapture থ্রেডগুলিতে, কোড ব্যবহার করুন যেমন:

logWriter->log("string");
logWriter->logf("format", parameters);
logWriter->logTimestamp();

যেহেতু এই NBLog টাইমলাইনটি শুধুমাত্র FastMixer এবং FastCapture থ্রেড দ্বারা ব্যবহৃত হয়, তাই পারস্পরিক বর্জনের কোন প্রয়োজন নেই।

অন্যান্য AudioFlinger থ্রেডে, mNBLogWriter ব্যবহার করুন:

mNBLogWriter->log("string");
mNBLogWriter->logf("format", parameters);
mNBLogWriter->logTimestamp();

FastMixer এবং FastCapture ব্যতীত অন্য থ্রেডগুলির জন্য, থ্রেডের NBLog টাইমলাইন থ্রেড নিজেই এবং বাইন্ডার অপারেশন উভয় দ্বারা ব্যবহার করা যেতে পারে। NBLog::Writer প্রতি টাইমলাইনে কোনো অন্তর্নিহিত পারস্পরিক বর্জন প্রদান করে না, তাই নিশ্চিত হন যে সমস্ত লগ এমন একটি প্রেক্ষাপটের মধ্যে ঘটে যেখানে থ্রেডের mLock রাখা হয়।

আপনি লগ যোগ করার পরে, AudioFlinger পুনরায় তৈরি করুন.

সতর্কতা: একটি পৃথক NBLog::Writer টাইমলাইন প্রয়োজন, যেহেতু টাইমলাইন ডিজাইন অনুসারে মিউটেক্স বাদ দেয়। আপনি যদি একই টাইমলাইনে একাধিক থ্রেড ব্যবহার করতে চান তবে আপনি একটি বিদ্যমান মিউটেক্সের সাথে রক্ষা করতে পারেন (যেমন mLock জন্য উপরে বর্ণিত হয়েছে)। অথবা আপনি NBLog::Writer এর পরিবর্তে NBLog::LockedWriter র্যাপার ব্যবহার করতে পারেন। যাইহোক, এটি এই API এর একটি প্রধান সুবিধাকে অস্বীকার করে: এর অ-ব্লকিং আচরণ।

সম্পূর্ণ NBLog API frameworks/av/include/media/nbaio/NBLog.h

media.log সক্ষম করুন

media.log ডিফল্টরূপে নিষ্ক্রিয় করা হয়। এটি শুধুমাত্র সক্রিয় হয় যখন প্রপার্টি ro.test_harness 1 হয়। আপনি এটি দ্বারা সক্ষম করতে পারেন:

adb root
adb shell
echo ro.test_harness=1 > /data/local.prop
chmod 644 /data/local.prop
reboot

রিবুট করার সময় সংযোগটি হারিয়ে গেছে, তাই:

adb shell
কমান্ড ps media এখন দুটি প্রক্রিয়া দেখাবে:
  • media.log
  • মিডিয়া সার্ভার

পরবর্তীতে mediaserver প্রসেস আইডি নোট করুন।

টাইমলাইন প্রদর্শন করা হচ্ছে

আপনি যেকোনো সময় ম্যানুয়ালি লগ ডাম্পের অনুরোধ করতে পারেন। এই কমান্ডটি সমস্ত সক্রিয় এবং সাম্প্রতিক টাইমলাইন থেকে লগ দেখায় এবং তারপরে সেগুলি সাফ করে:

dumpsys media.log

নোট করুন যে ডিজাইনের টাইমলাইনগুলি স্বাধীন, এবং টাইমলাইনগুলিকে একত্রিত করার কোনও সুবিধা নেই৷

মিডিয়া সার্ভারের মৃত্যুর পর লগ পুনরুদ্ধার করা হচ্ছে

এখন mediaserver প্রক্রিয়াকে হত্যা করার চেষ্টা করুন: kill -9 # , যেখানে # আপনি আগে উল্লেখ করেছেন প্রসেস আইডি। আপনি প্রধান logcatmedia.log থেকে একটি ডাম্প দেখতে পাবেন, যা ক্র্যাশের দিকে অগ্রসর হওয়া সমস্ত লগ দেখাচ্ছে৷

dumpsys media.log