مراقبة رفع تردد التشغيل

رفع تردد التشغيل المعالج أو الذاكرة أمر مفهوم ، ولكن لماذا رفع تردد التشغيل الإضاءة الخلفية للشاشة؟



يتعلق الأمر بشاشة Samsung SyncMaster BX2340 القديمة مقاس 23 بوصة (التي تم إصدارها في يناير 2011) باستخدام الإضاءة الخلفية LED. مع مرور الوقت ، بدأ يلاحظ أن العمل من أجله كان متعباً ، والتركيز أكثر وأكثر صعوبة. وليس العمل فقط ، مجرد قراءة ، على سبيل المثال. ظلت الشاشة نفسها كما هي ، لكنها أصبحت أكثر صعوبة بالنسبة لي. وبالنسبة للشاشات الأخرى ، عملت بشكل جيد جدًا.

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

بعد ذلك ، حصلت على مقطع فيديو على YouTube حول إعادة إنشاء الإضاءة الخلفية للشاشة للتيار المباشر. وكان التدخل في مخطط الكاردينال. تحت الفيديو ، كانت هناك تعليقات حول تحول اللون عند التيارات المنخفضة على الأسلاك. وتعمل الإضاءة الخلفية الخاصة بي بنسبة 10-25 ٪ ، لأن الغرفة مظلمة للغاية. محدث : في الفيديو ، كان للمؤلف إكليل واحد فقط من المصابيح ، وكان لي 4.

تقرر ترك التحكم في السطوع باستخدام PWM ، ولكن زيادة التردد. لم أبدأ حتى في قياس وميض بطريقة غير غازية باستخدام مقاوم ضوئي أو ثنائي ضوئي ، لقد قمت على الفور بتفكيك الشاشة.



وحدة تحكم الإضاءة الخلفية - OZ9993CN. لم يكن هناك ورقة بيانات عادية ، فقط سائق مجموعة الخلفية التي أدلى بها O 2 مايكرو. اتضح أن السائق يشارك أيضًا في زيادة الجهد (وفقًا للقياسات من 14.4 فولت إلى 54.6 فولت) باستخدام ترانزستور وتأثير قوي للمجال الخارجي.

تشبه إحدى الدوائر معنى السائق ؛ أرقام الدبوس غير متطابقة:



على السبورة ، يتم توقيع مسار إشارة PWM إلى برنامج التشغيل على أنه B-Dim (يعتم الإضاءة الخلفية؟) ، ولم أضطر إلى البحث. بعد ذلك ، بدأ استنساخ من الذبذبات الرقمية USBee AX USB مع سيجروك على جانب الكمبيوتر. أظهر القياس أن تردد الإضاءة الخلفية هو 180 هرتز (لن يكون كافيًا!). مستوى إشارة عالية - 5 فولت.



أنت الآن بحاجة إلى رفع تردد PWM بطريقة ما إلى قيم كيلو هرتز ، مرة واحدة كل 16 عامًا. وأول ما يتبادر إلى الذهن هو وضع متحكم في فجوة مسار PWM لاستقبال الإشارة وتشغيلها بشكل أسرع 16 مرة. نحتاج إلى مؤقتين ، أحدهما سيقيس مدة المستويات المنخفضة والعالية ، والآخر سيعطي إشارة PWM. بعد التقاط معاملات المقسم ، يمكننا الاستغناء عن الحساب على الإطلاق ، فقط عن طريق النسخ. لا ، لن اردوينو. لن يكون هناك مجمع أيضا ، سيكون هناك دول مجلس التعاون الخليجي. كان عضو الكنيست الصغير مع مؤقتين على الأقل (من المخزون) ATtiny15. لكن WinAVR لا ترغب في العمل معها ، لذلك اضطررت إلى استخدام إصدار أقدم - ATtiny45 (ستعمل ATtiny25 / 85 أيضًا).

القيادة:

100n ┌───────┤├───────┐ │ ┌────────────┐ │ │ │ 1 8 ├─┴─ VCC │ │ 2 7 ├─ PB2 (INT0) INPUT │ │ 3 6 ├─ PB1 (OC1A) OUTPUT GND ─┴─┤ 4 5 │ └────────────┘ ATtiny45 

نختار عوامل فواصل الموقت. تأخذ تردد وحدة المعالجة المركزية من حوالي 8 ميغاهيرتز ، من المدمج في مولد RC.

  • قياس الموقت. كم عدد التدابير في فترة يعتم؟ 8000000/180 دولار / حوالي 44444 دولار . لكي يتم احتواء هذا في سجل الموقت ذي الثمانية بتات مع فقدان الحد الأدنى من الدقة ، نأخذ المقسّم الأولي 256 ، وستكون القيمة القصوى للعداد 8000000 / 180/256 دولار / حوالي 173.6 دولار .
  • PWM الموقت سنجعل التردد أكبر 16 مرة: 180 دولار \ cdot 16 = 2880 هرتز دولار ، يكون المقسم المسبق أصغر عدد المرات: 256/16 دولار = 16 دولار .

يتم توصيل إشارة الإدخال إلى الساق المقاطعة الخارجية. معالجها:

 /* External Interrupt 0 */ ISR(INT0_vect, ISR_NAKED) { uint8_t timer = TCNT0; //     if (PINB & 1<<PB2) { //  .   -    OCR1C = timer; //   TCNT0 = 0; //     } else { //   -  OCR1A = timer; //   } reti(); } 

ما هو ISR_NAKED؟
يُقصد بـ "ISR_NAKED" حفظ / استعادة السجلات والأعلام الخاصة بالمعالج ، ويتم ذلك من أجل الإسراع. يمكن القيام بذلك عن طريق التأكد من عدم تأثرهم في الحلقة الرئيسية (لدينا فقط حلقة لا نهاية لها while(1) {} ) ، ولن تكون هناك مكالمات من الروتين الفرعي. حسنًا ، في النهاية ، نوصيك بالعودة من الوظيفة باستخدام reti() مقاطعة reti() .

ملحوم ، وميض - وعملت!



لكن الخانق بدأ في الصرير. ننظر إلى ما يوجد على بوابة وحدة التحكم الميدانية التي تتحكم في التيار من خلال محث الطاقة:



كل شيء يتوافق مع دواسة الوقود ، فهو مستمر في العمل بتردد 320 كيلو هرتز ، لكن إذا كان تردد PWM في وقت سابق 180 هرتز وكان غير مسموع تقريبًا (فقط إذا أحضرت أذنك) ، فسيصبح 2.9 كيلو هرتز مسموعًا جدًا. والراحة بوضوح لم تزيد. ولكن ماذا لو أحضرت التردد الحد الأعلى المسموح به؟ على سبيل المثال 180 هيرتز \ cdot 128 = 23040 هيرز دولار ؟ نحن نغير مضاعف مقسم مؤقت PWM من 16 إلى 2 ، ونومضه. اتضح أن كل شيء كان في النظام. تقريبا.

أجهزة ضبط الوقت ذات الثمانية بت في هذه الحالة ليست كافية ، فأنت بحاجة إلى المزيد من المعادن . يتجلى هذا في شكل تقلبات منخفضة التردد في السطوع ، مع زيادة واختفاء سلسين لعدة ترددات. للتعامل مع هذه الآفة ، يمكنك أن تأخذ البدانة الكريستالية ، لكن هذا ليس هو طريقنا. سنزيد عمق البت في مؤقت القياس بشكل برمجي ونقدم عتبة (التباطؤ) للكشف الموثوق عن تبديل السطوع بواسطة المستخدم (0–100 بدقة 1). نرفع دقة مؤقت القياس بمقدار 256 مرة ، ويصبح عامل المضاعف يساوي 1.

قياس معالج تجاوز سعة الموقت مع خيار "حدث خطأ ما ومدة المستوى":

 /* Timer/Counter0 Overflow */ ISR(TIM0_OVF_vect, ISR_NAKED) { #define TIME_H_LIM (UCHAR_MAX-1) if (time_h < TIME_H_LIM) { // Normal way time_h += 1; } else { // High part overflowed if (PINB & 1<<PB2) { OCR1A = TIME_H_LIM; // Always on } else { OCR1A = 0; // Always off } OCR1C = TIME_H_LIM; time_h = 0; time_cycle = 0; time_on = 0; } reti(); // Because ISR_NAKED } 

الانقطاع الخارجي أصبح الآن أكثر تعقيدًا:

 /* External Interrupt 0 */ ISR(INT0_vect, ISR_NAKED) { // F_CPU / Timer1 prescaler / F_PWM_IN / grades / 4 #define THRESHOLD (F_CPU / 1 / F_PWM_IN / 100 / 4) uint16_t time; uint8_t time_l = TCNT0; if ((TIFR & 1<<TOV0) && (time_l <= UCHAR_MAX/2)) { // Overflow occured right now time_l = UCHAR_MAX; // 0xff } time = (time_h << 8) + time_l; if (PINB & 1<<PB2) { // Risen if (abs(time - time_cycle) > THRESHOLD) { time_cycle = time; OCR1C = time_h; } TCNT0 = 0; time_h = 0; if (TIFR & 1<<TOV0) { TIFR = 1<<TOV0; // Clear Timer0 overflow flag } } else { // Falled if (abs(time - time_on) > THRESHOLD) { time_on = time; OCR1A = time_h; } } reti(); // Because ISR_NAKED } 

هناك متغيرات عالمية دفعتها إلى سجلات ، لدينا رفع تردد التشغيل بعد كل شيء. يستخدم SRAM فقط لتخزين عنوان المرسل عند إدخال معالجات المقاطعة. الجزء الأعلى من عداد القياس الفاصل الزمني هو في time_h المتغير ، وقيم طول دورة PWM المقاسة ودائرة التشغيل في وقت_دورة زمنية- على التوالي. عتبة - عتبة للكشف عن التغييرات في السطوع.

الآن كل شيء يعمل ، على النحو المنشود.

كود كامل
 /* PWM frequency multiplier x128 100n ┌───────┤├───────┐ │ ┌────────────┐ │ │ │ 1 8 ├─┴─ VCC │ │ 2 7 ├─ PB2 (INT0) INPUT │ │ 3 6 ├─ PB1 (OC1A) OUTPUT GND ─┴─┤ 4 5 │ └────────────┘ ATtiny45 fuses: lfuse=0xe2 hfuse=0xdf */ #include <avr/interrupt.h> #include <avr/wdt.h> #include <stdlib.h> #include <limits.h> #define F_CPU 8000000UL #define F_PWM_IN 180U register uint8_t time_h asm("r4"); // High part of time counter register uint16_t time_cycle asm("r12"); // Period register uint16_t time_on asm("r14"); // H level duration __attribute__((naked)) int main(void) { time_h = 0; time_cycle = 0; time_on = 0; ACSR |= 1<<ACD; // Comparator disable // Timer0 TCCR0A = 0; // CK/1 TCCR0B = 1<<CS00; // Timer1 DDRB |= 1<<PB1; // PWM output // CK/2, Clear the OC1A output line TCCR1 = 1<<CTC1|1<<PWM1A|2<<COM1A0|2<<CS10; TIMSK |= 1<<TOIE0; // Timer0 overflow // Ext int 0 MCUCR |= 1<<ISC00; // Any logical change on INT0 generates an interrupt request GIMSK |= 1<<INT0; // External Interrupt Request 0 Enable PORTB |= 1<<PB2; // Input wdt_enable(WDTO_120MS); // Watchdog on sei(); // Interrupts enable while (1) { // Do not use flags or registers wdt_reset(); // Watchdog reset } } /* External Interrupt 0 */ ISR(INT0_vect, ISR_NAKED) { // F_CPU / Timer1 prescaler / F_PWM_IN / grades / 4 #define THRESHOLD (F_CPU / 1 / F_PWM_IN / 100 / 4) uint16_t time; uint8_t time_l = TCNT0; if ((TIFR & 1<<TOV0) && (time_l <= UCHAR_MAX/2)) { // Overflow occured right now time_l = UCHAR_MAX; // 0xff } time = (time_h << 8) + time_l; if (PINB & 1<<PB2) { // Risen if (abs(time - time_cycle) > THRESHOLD) { time_cycle = time; OCR1C = time_h; } TCNT0 = 0; time_h = 0; if (TIFR & 1<<TOV0) { TIFR = 1<<TOV0; // Clear Timer0 overflow flag } } else { // Falled if (abs(time - time_on) > THRESHOLD) { time_on = time; OCR1A = time_h; } } reti(); // Because ISR_NAKED } /* Timer/Counter0 Overflow */ ISR(TIM0_OVF_vect, ISR_NAKED) { #define TIME_H_LIM (UCHAR_MAX-1) if (time_h < TIME_H_LIM) { // Normal way time_h += 1; } else { // High part overflowed if (PINB & 1<<PB2) { OCR1A = TIME_H_LIM; // Always on } else { OCR1A = 0; // Always off } OCR1C = TIME_H_LIM; time_h = 0; time_cycle = 0; time_on = 0; } reti(); // Because ISR_NAKED } 


يمكنك تسميتها اقتراحًا تلقائيًا ، لكن النتيجة هي: أصبحت الحياة أفضل ، وأصبحت الحياة أكثر متعة! انتقلت حتى مشاريع طويلة معلقة.

إذا كان تردد الإضاءة الخلفية في حالتك لا يؤثر على رفاهيتك وإنتاجيتك بأي شكل من الأشكال - فاعتبر نفسك محظوظًا. ربما. وكذلك الأشخاص الذين يؤكدون أنهم مرتاحون تمامًا عندما يزيد محتوى ثاني أكسيد الكربون في الغرفة عن 0.2٪ (2000 جزء في المليون ).

ولكن ماذا عن رابط جيثب؟

Source: https://habr.com/ru/post/ar448730/


All Articles