كيف أضمن أن برنامجي يعمل من البداية إلى النهاية دون انقطاع؟

StackOverflow https://stackoverflow.com/questions/1215713

  •  06-07-2019
  •  | 
  •  

سؤال

أحاول تحديد الوقت باستخدام RDTSC (لا يوجد برنامج آخر للتوصيف قمت بتجربته قادر على تحديد الوقت بالدقة التي أحتاجها) على Ubuntu 8.10.ومع ذلك، أستمر في الحصول على القيم المتطرفة من تبديل المهام وإطلاق المقاطعات، مما يتسبب في أن تكون الإحصائيات الخاصة بي غير صالحة.

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

الكود ذو الصلة الذي أستخدمه حاليًا هو:

inline uint64_t rdtsc()
{
    uint64_t ret;
    asm volatile("rdtsc" : "=A" (ret));
    return ret;
}

void test(int readable_out, uint32_t start, uint32_t end, uint32_t (*fn)(uint32_t, uint32_t))
{
    int i;
    for(i = 0; i <= 100; i++)
    {
        uint64_t clock1 = rdtsc();
        uint32_t ans = fn(start, end);
        uint64_t clock2 = rdtsc();

        uint64_t diff = clock2 - clock1;

        if(readable_out)
            printf("[%3d]\t\t%u [%llu]\n", i, ans, diff);
        else
            printf("%llu\n", diff);
    }
}

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

القيمة اللطيفة لبرنامجي هي -20.

لذا، للتلخيص، هل من الممكن بالنسبة لي تشغيل هذا الرمز دون انقطاع من نظام التشغيل؟أم سأحتاج إلى تشغيله على الأجهزة العارية في الحلقة0، حتى أتمكن من تعطيل طلبات المقاطعة (IRQs) والجدولة؟شكرا لك مقدما!

هل كانت مفيدة؟

المحلول

إذا كنت استدعاء nanosleep () أن ينام لمدة ثانية أو نحو ذلك فورا قبل كل تكرار الاختبار، يجب أن تحصل على timeslice "جديدة" لكل اختبار. إذا كنت ترجمة النواة مع المقاطعات 100HZ الموقت، وظيفة توقيت الخاص اكتمال في أقل من 10ms، ثم عليك أن تكون قادرا على تجنب المقاطعات الموقت يضربك بهذه الطريقة.

لتقليل المقاطعات الأخرى، deconfigure جميع أجهزة الشبكة، وتكوين النظام الخاص بك دون مقايضة وتأكد من انها هادئة على خلاف ذلك.

نصائح أخرى

وصعب. أنا لا أعتقد أنك يمكن أن تتحول إلى نظام التشغيل "خارج" وضمان جدولة صارمة.

وأود أن تتحول هذه رأسا على عقب: نظرا لأنه يعمل بسرعة تشغيله عدة مرات لجمع توزيع النتائج. وبالنظر إلى أن معيار أوبونتو لينكس ليس OS الوقت الحقيقي بالمعنى الضيق، فإن كل الخوارزميات بديلة تعمل في نفس الإعداد --- ويمكنك بعد ذلك مقارنة التوزيعات (باستخدام أي شيء من إحصاءات موجزة لquantiles إلى qqplots). يمكنك أن تفعل ذلك بالمقارنة مع بيثون، أو R، أو أوكتاف، ... أيهما يناسبك.

وكنت قد تكون قادرة على الابتعاد مع تشغيل فري ، منذ <لأ href = "HTTP: / /groups.google.com/group/alt.os.free-dos/browse_thread/thread/e35dec94e75ca33b؟pli=1 "يختلط =" نوفولو noreferrer "> انها واحدة عملية OS .

وفيما يلي النص ذي الصلة من الوصلة الثانية:

<اقتباس فقرة>   

وتنفيذ DOS مايكروسوفت، والذي هو دي   المعيار الفعلي لأنظمة DOS في   x86 في ويبعد مستخدم واحد،   واحد المهام نظام التشغيل. هذا   يوفر الوصول الخام إلى الأجهزة، و   سوى طبقة الحد الأدنى ل API OS ل   أشياء مثل ملف I / O. هذا ال   شيء جيد عندما يتعلق الأمر جزءا لا يتجزأ من   أنظمة، لأنك غالبا ما تحتاج فقط   للحصول على القيام بشيء ما دون   نظام التشغيل في طريقك.

     

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

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

ولقد يست في الواقع <م> تستخدم فري، ولكن أفترض أنه منذ برنامجك يبدو أن معيار C، عليك أن تكون قادرا على استخدام كل ما المترجم هو معيار لفري.

إذا كان برنامجك يعمل بالمللي ثانية ، وإذا كان يعمل على Linux ، فتأكد من ضبط تردد المؤقت (على Linux) على 100 هرتز (وليس 1000Hz).(cd /usr/src/linux;اصنع menuconfig ، وانظر إلى "نوع المعالج والميزات" -> "تردد المؤقت") بهذه الطريقة سوف تتوقف وحدة المعالجة المركزية الخاصة بك كل 10 مللي ثانية.

علاوة على ذلك، ضع في اعتبارك أن شريحة وقت وحدة المعالجة المركزية الافتراضية على Linux هي 100 مللي ثانية، لذلك مع مستوى جيد يبلغ -20، لن يتم إلغاء جدولتك إذا كنت تعمل لبضعة أجزاء من الثانية.

كما أنك تقوم بالتكرار 101 مرة على fn().يرجى النظر في إعطاء fn() كإجراء محظور لمعايرة نظامك بشكل صحيح.

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

نموذج التعليمات البرمجية المعياري RDTSC

يمكنك استخدام crt -f 99 ./test لتشغيل ./test بأقصى أولوية في الوقت الفعلي.ثم على الأقل لن يتم مقاطعتها بواسطة عمليات مساحة المستخدم الأخرى.

وكذلك تثبيت لينكس-RT ستقوم الحزمة بتثبيت نواة في الوقت الحقيقي، مما سيمنحك المزيد من التحكم في أولوية معالج المقاطعة عبر المقاطعات المترابطة.

إذا قمت بتشغيل كجذر، يمكنك الاتصال sched_setscheduler () وتعطي لنفسك أولوية في الوقت الحقيقي. تحقق من الوثائق.

وربما هناك بعض طريقة لتعطيل جدولة استباقية على لينكس، ولكن قد لا تكون هناك حاجة إلى ذلك. هل يمكن أن يحتمل استخدام المعلومات من /proc/<pid>/schedstat أو بعض وجوه الآخرين في /proc إلى الشعور عندما تم استبقت لك، وتجاهل تلك العينات توقيت.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top