استكشاف محرك Mediastreamer2 VoIP. الجزء 12

مادة المقال مأخوذة من بلدي قناة زين.

استكشاف محرك Mediastreamer2 VoIP. الجزء 12

في الماضي مقالة، لقد وعدت بالنظر في مسألة تقدير حمل شريط الأسهم وطرق التعامل مع حمل الحوسبة المفرط في غاسل الوسائط. لكنني قررت أنه سيكون من المنطقي أكثر تغطية مشكلات تصحيح أخطاء المرشحات اليدوية المتعلقة بحركة البيانات ، وعندها فقط فكر في مشكلات تحسين الأداء.

تصحيح أخطاء المرشحات الحرفية

بعد أن درسنا آلية حركة البيانات في جهاز بث الوسائط في المقالة السابقة ، سيكون من المنطقي التحدث عن المخاطر المخفية فيها. تتمثل إحدى ميزات مبدأ "تدفق البيانات" في أن تخصيص الذاكرة من الكومة يحدث في المرشحات الموجودة في مصادر تدفق البيانات ، وأن المرشحات الموجودة في نهاية مسار التدفق تقوم بالفعل بإلغاء تخصيص الذاكرة مع الإرجاع إلى الكومة. بالإضافة إلى ذلك ، يمكن أن يحدث إنشاء بيانات جديدة وتدميرها في مكان ما في النقاط الوسيطة. بشكل عام ، يتم تحرير الذاكرة بواسطة مرشح آخر غير المرشح الذي أنشأ كتلة البيانات.

من وجهة نظر المراقبة الشفافة للذاكرة ، سيكون من المعقول أن يقوم المرشح ، عند تلقي كتلة إدخال ، بتدميرها فورًا بعد المعالجة ، وتحرير الذاكرة ، ووضع كتلة تم إنشاؤها حديثًا مع بيانات الإخراج على المخرجات. في هذه الحالة ، يمكن تتبع تسرب الذاكرة في الفلتر بسهولة - إذا اكتشف المحلل تسربًا في الفلتر ، فإن المرشح الذي يتبعه لا يدمر الكتل الواردة بشكل صحيح ويوجد خطأ فيه. ولكن من وجهة نظر الحفاظ على الأداء العالي ، فإن هذا النهج للعمل مع كتل البيانات ليس مثمرًا - فهو يؤدي إلى عدد كبير من العمليات لتخصيص / تحرير ذاكرة لكتل ​​البيانات دون أي عادم مفيد.

لهذا السبب ، تستخدم مرشحات دفق الوسائط ، من أجل عدم إبطاء معالجة البيانات ، عند نسخ الرسائل ، تستخدم الوظائف التي تنشئ نسخًا خفيفة (تحدثنا عنها في مقالة سابقة). تقوم هذه الوظائف فقط بإنشاء نسخة جديدة من عنوان الرسالة عن طريق "إرفاق" كتلة البيانات من الرسالة "القديمة" المنسوخة بها. نتيجة لذلك ، يتم إرفاق رأسين بكتلة بيانات واحدة ويتم زيادة العداد المرجعي في كتلة البيانات. لكنها ستبدو كرسالتين. قد يكون هناك المزيد من الرسائل ذات كتلة البيانات "العامة" ، على سبيل المثال ، يقوم عامل التصفية MS_TEE بتوليد عشر نسخ ضوئية من هذا القبيل دفعة واحدة ، وتوزيعها على مخرجاتها. إذا كانت جميع المرشحات في السلسلة تعمل بشكل صحيح ، في نهاية خط الأنابيب ، يجب أن يصل هذا العدد المرجعي إلى الصفر وسيتم استدعاء وظيفة إلغاء تخصيص الذاكرة: ms_free (). إذا لم تحدث المكالمة ، فلن تعود قطعة الذاكرة هذه إلى الكومة ، أي انه "يتسرب". تكلفة استخدام النسخ الخفيفة هي فقدان القدرة على التحديد بسهولة (كما هو الحال في حالة استخدام النسخ العادية) حيث يتم تسريب مرشح الرسم البياني في الذاكرة.

نظرًا لأن مسؤولية العثور على تسرب الذاكرة في المرشحات "الأصلية" تقع على عاتق مطوري الوسائط ، فعلى الأرجح لن تضطر إلى تصحيحها. ولكن مع مرشح الصياغة الخاص بك ، فأنت نفسك جندب لسعادتك الخاصة ، والوقت الذي تقضيه في البحث عن التسريبات في الكود الخاص بك سيعتمد على دقتك. لتقليل وقت التصحيح ، نحتاج إلى إلقاء نظرة على تقنيات توطين التسرب عند تصميم المرشحات. بالإضافة إلى ذلك ، قد يحدث أن يظهر التسرب نفسه فقط عند تطبيق المرشح في نظام حقيقي ، حيث يمكن أن يكون عدد "المشتبه بهم" كبيرًا ، ويكون وقت التصحيح محدودًا.

كيف يظهر تسرب الذاكرة نفسه؟

من المنطقي أن نفترض ذلك في إخراج البرنامج تيشرت ستظهر نسبة متزايدة من الذاكرة التي يشغلها تطبيقك.

سيتكون المظهر الخارجي في حقيقة أنه في مرحلة ما سيتفاعل النظام ببطء مع حركة الماوس ، ويعيد رسم الشاشة ببطء. من الممكن أيضًا أن ينمو سجل النظام ، ويستهلك مساحة على القرص الصلب. في هذه الحالة ، سيبدأ التطبيق الخاص بك في التصرف بشكل غريب ، ولا يستجيب للأوامر ، ولا يمكنه فتح الملف ، وما إلى ذلك.

لتحديد حقيقة التسرب ، سنستخدم محلل ذاكرة (يشار إليه فيما بعد بالمحلل). يمكن ان تكون Valgrind (جيد مقالة حول ذلك) أو مضمنة في المترجم دول مجلس التعاون الخليجي مطهر الذاكرة أو أي شيء آخر. إذا أظهر المحلل أن التسرب يحدث في أحد مرشحات الرسم البياني ، فهذا يعني أن الوقت قد حان لتطبيق إحدى الطرق الموضحة أدناه.

طريقة ثلاثة باينز

كما هو مذكور أعلاه ، في حالة حدوث تسرب للذاكرة ، سيشير المحلل إلى عامل التصفية الذي طلب تخصيص الذاكرة من الكومة. لكنه لن يشير إلى المرشح الذي "نسي" إعادته ، وهو في الواقع يقع اللوم عليه. وبالتالي ، يمكن للمحلل تأكيد مخاوفنا فقط ، ولكن لا يشير إلى جذورها.

لمعرفة موقع عامل التصفية "السيئ" في الرسم البياني ، يمكنك الانتقال عن طريق تقليل الرسم البياني إلى الحد الأدنى لعدد العقد التي لا يزال المحلل يكتشف فيها تسربًا وتحديد موقع الفلتر الإشكالي في الصنوبر الثلاثة المتبقية.

ولكن قد يحدث أنه من خلال تقليل عدد المرشحات في العمود ، ستؤدي إلى تعطيل المسار الطبيعي للتفاعل بين المرشحات والعناصر الأخرى في نظامك ولن يظهر التسرب مرة أخرى. في هذه الحالة ، سيتعين عليك العمل باستخدام رسم بياني بالحجم الكامل واستخدام الطريقة الموضحة أدناه.

طريقة انزلاق عازل

لتبسيط العرض ، سنستخدم رسمًا بيانيًا يتكون من سلسلة واحدة من المرشحات. تظهر في الصورة.

استكشاف محرك Mediastreamer2 VoIP. الجزء 12

رسم بياني عادي ، يتم فيه ، جنبًا إلى جنب مع مرشحات دفق الوسائط الجاهزة ، استخدام أربعة فلاتر حرفية F1 ... F4 ، أربعة أنواع مختلفة قمت بإنشائها منذ وقت طويل وليس لديك أدنى شك في صحتها. ومع ذلك ، افترض أن العديد منهم لديهم تسرب للذاكرة. عند تشغيل برنامج إشراف المحلل الخاص بنا ، نتعلم من تقريره أن مرشحًا معينًا طلب قدرًا معينًا من الذاكرة ولم يعيده إلى الكومة N من المرات. من السهل تخمين أنه سيكون هناك مرجع لوظائف التصفية الداخلية لنوع MS_VOID_SOURCE. مهمته هي أخذ الذاكرة من الكومة. يجب أن تعيده المرشحات الأخرى هناك. أولئك. سنجد التسرب.

من أجل تحديد الجزء الذي حدث فيه عدم نشاط في خط الأنابيب والذي أدى إلى تسرب الذاكرة ، يُقترح إدخال عامل تصفية إضافي يقوم ببساطة بنقل الرسائل من الإدخال إلى الإخراج ، ولكن في نفس الوقت ينشئ عنصرًا عاديًا غير خفيف نسخة "ثقيلة" من رسالة الإدخال ، ثم حذف الرسالة التي وصلت إلى مدخل الإخراج بالكامل. سوف نسمي هذا المرشح عازلًا. نعتقد أنه نظرًا لأن المرشح بسيط ، يتم استبعاد التسرب فيه. وهناك خاصية أخرى موجبة - إذا أضفناها إلى أي مكان في الرسم البياني ، فلن يؤثر ذلك على عمل الدائرة بأي شكل من الأشكال. سنصور مرشح العازل كدائرة ذات محيط مزدوج.

قم بتمكين المعزل مباشرة بعد مرشح مسار الفراغات:
استكشاف محرك Mediastreamer2 VoIP. الجزء 12

نقوم بتشغيل البرنامج بالمحلل مرة أخرى ، ونرى أنه هذه المرة ، سيضع المحلل اللوم على العازل. بعد كل شيء ، هو الذي ينشئ الآن كتلًا من البيانات ، والتي يتم فقدها بعد ذلك بواسطة مرشح إهمال غير معروف (أو عوامل تصفية). الخطوة التالية هي تحويل العازل على طول السلسلة إلى اليمين ، بواسطة مرشح واحد ، وبدء التحليل مرة أخرى. لذلك ، خطوة بخطوة ، بتحريك المعزل إلى اليمين ، نحصل على موقف عندما ينخفض ​​عدد كتل الذاكرة "المسربة" في التقرير التالي للمحلل. هذا يعني أنه في هذه الخطوة انتهى المطاف بالعازل في السلسلة مباشرة بعد الفلتر المشكل. إذا كان هناك مرشح "سيء" واحد فقط ، فسيختفي التسرب تمامًا. وبالتالي ، قمنا بترجمة عامل التصفية الإشكالي (أو واحد من عدة عوامل). بعد "إصلاح" الفلتر ، يمكننا الاستمرار في تحريك المعزل إلى اليمين على طول السلسلة حتى يتم التخلص تمامًا من تسرب الذاكرة.

تنفيذ مرشح المعزل

يبدو تطبيق المعزل تمامًا مثل المرشح العادي. الملف الاساسي:

/* Файл iso_filter.h  Описание изолирующего фильтра. */

#ifndef iso_filter_h
#define iso_filter_h

/* Задаем идентификатор фильтра. */
#include <mediastreamer2/msfilter.h>

#define MY_ISO_FILTER_ID 1024

extern MSFilterDesc iso_filter_desc;

#endif

المرشح نفسه:

/* Файл iso_filter.c  Описание изолирующего фильтра. */

#include "iso_filter.h"

    static void
iso_init (MSFilter * f)
{
}
    static void
iso_uninit (MSFilter * f)
{
}

    static void
iso_process (MSFilter * f)
{
    mblk_t *im;

    while ((im = ms_queue_get (f->inputs[0])) != NULL)
    {
        ms_queue_put (f->outputs[0], copymsg (im));
        freemsg (im);
    }
}

static MSFilterMethod iso_methods[] = {
    {0, NULL}
};

MSFilterDesc iso_filter_desc = {
    MY_ISO_FILTER_ID,
    "iso_filter",
    "A filter that reads from input and copy to its output.",
    MS_FILTER_OTHER,
    NULL,
    1,
    1,
    iso_init,
    NULL,
    iso_process,
    NULL,
    iso_uninit,
    iso_methods
};

MS_FILTER_DESC_EXPORT (iso_desc)

طريقة استبدال وظائف إدارة الذاكرة

لمزيد من البحث الدقيق ، يوفر مشغل الوسائط القدرة على استبدال وظائف الوصول إلى الذاكرة بوظائفك ، والتي ، بالإضافة إلى العمل الرئيسي ، ستصلح "من وأين ولماذا". يتم استبدال ثلاث وظائف. ويتم ذلك بالطريقة التالية:

OrtpMemoryFunctions reserv;
OrtpMemoryFunctions my;

reserv.malloc_fun = ortp_malloc;
reserv.realloc_fun = ortp_realloc;
reserv.free_fun = ortp_free;

my.malloc_fun = &my_malloc;
my.realloc_fun = &my_realloc;
my.free_fun = &my_free;

ortp_set_memory_functions(&my);

تأتي هذه الميزة للإنقاذ في الحالات التي يقوم فيها المحلل بإبطاء المرشحات بدرجة كبيرة بحيث يتعطل تشغيل النظام الذي تم إنشاء دائرتنا فيه. في مثل هذه الحالة ، يجب عليك التخلي عن المحلل واستخدام استبدال وظائف الذاكرة.

لقد درسنا خوارزمية الإجراءات لرسم بياني بسيط لا يحتوي على فروع. لكن هذا النهج يمكن تطبيقه على حالات أخرى ، مع التعقيد بالطبع ، لكن الفكرة تبقى كما هي.

في المقالة التالية ، سننظر في مسألة تقدير حمل شريط الأسهم وكيفية التعامل مع الحمل الزائد للحوسبة في جهاز بث الوسائط.

المصدر: www.habr.com

إضافة تعليق