Kommentar: Einfügen von HTML im Kommentar: Link einfügen: <a href="LINKURL" target="_blank">LINKTITEL</a> Bild einfügen: <img src="BILDURL"> Text formatieren: <b>fetter Text</b> <i>kursiver Text</i> <u>unterstrichener Text</u> Kombinationen sind auch möglich z.B.: <b><i>fetter & kursiver Text</i></b> C Quellcode formatieren: <code>Quellcode</code> BASIC Quellcode formatieren: <basic>Quellcode</basic> (Innerhalb eines Quellcodeabschnitts ist kein html möglich.) Wichtig: Bitte mache Zeilenumbrüche, bevor Du am rechten Rand des Eingabefeldes ankommst ! -> I > > Hallo, > > > > ich möchte von der Netzspannung die beiden Scheitelpunkte nach dem Nulldurchgang > > messen. Dabei gebe ich auf den ext.INT4 das Nullspannungssignal (im Bild gelb) > > und starte nach Auslösen des IRQ zwei Timer die dann 5ms und 15ms später > > (im Bild blau) den ADC auslesen. > > Das funktioniert absolut stabil, solange keine LCD-Ausgabe stattfindet. > > Findet eine LCD-Ausgabe statt und ein Hard- oder Software IRQ wird ausgelöst, > > dann zittert das ADC Signal (blau) wie verrückt und eine präzise Messung ist nicht > > mehr möglich. > > > > Kann man der Abarbeitung eines Hard- oder Software IRQ oberste Priorität geben ? > > Eine verzögerte oder unterbrochene LCD-Ausgabe spielt ja sowieso keine Rolle. > > > > > > > > > > > > > > > > //-------------------------------------------------------------------------------- > > #define PORT_LED3 117 // PortBit 117 > > #define PORT_LED4 119 // PortBit 119 > > > > word x; > > > > > > void main(void) > > { > > > > Port_Attribute(10, PORT_ATTR_INPUT); // P15 auf Eingang = Ext_Int4 (Nullsp) > > Port_Attribute(PORT_LED1,PORT_ATTR_OUTPUT|PORT_ATTR_INIT_LOW); // LED 1 > > Port_Attribute(PORT_LED2,PORT_ATTR_OUTPUT|PORT_ATTR_INIT_LOW); // LED 2 > > Port_Attribute(PORT_LED3,PORT_ATTR_OUTPUT|PORT_ATTR_INIT_LOW); // LED 3 > > Port_Attribute(PORT_LED4,PORT_ATTR_OUTPUT|PORT_ATTR_INIT_LOW); // LED 4 > > > > > > Irq_SetVect(INT_100HZ, ISR_10ms); // Interrupt alle 10ms > > > > Irq_SetVect(INT_4, ISR_ZeroCrossing); // Int4 setzen für Nulldurchgang > > Ext_IntEnable(4,2); // Int4: Mode 2 = fallende Flanke > > > > Irq_SetVect(INT_TIMER0, ISR_Timer0); // Timer0 IRQ, 5ms nach Nulldurchg. > > Irq_SetVect(INT_TIMER1, ISR_Timer1); // Timer1 IRQ, 15ms nach Nulldurchg. > > > > LCD_Init(); // Display initialisieren > > LCD_ClearLCD(); > > LCD_CursorOff(); // Display Cursor ausschalten > > > > while(1) > > { > > x++; > > } > > > > > > > > } > > > > // -------------------------- IRQ Nulldurchgang (50Hz) ------------------------------ > > // > > void ISR_ZeroCrossing(void) > > { > > Timer_Set(0, TIM_128, 2579, TIMFLG_IRQ); // 2579*1,939us = 5ms > > Timer_Set(1, TIM_128, 7736, TIMFLG_IRQ); // 7736*1,939us = 15ms > > > > Irq_GetCount(INT_4); > > } > > > > > > // ----------------------- IRQ Timer0, 5ms nach Nulldurchgang ---------------------- > > // den ADC0 auslesen (=Scheitelpunkt der 1.Halbwelle) > > // > > void ISR_Timer0(void) > > { > > Port_WriteBit(PORT_LED2,PORT_ON); > > Irq_GetCount(INT_TIMER0); > > Timer_Disable(0); > > Port_WriteBit(PORT_LED2,PORT_OFF); > > } > > > > // ----------------------- IRQ Timer1, 15ms nach Nulldurchgang ---------------------- > > // den ADC0 auslesen (=Scheitelpunkt der 2.Halbwelle) > > // > > void ISR_Timer1(void) > > { > > Port_WriteBit(PORT_LED2,PORT_ON); > > Irq_GetCount(INT_TIMER1); > > Timer_Disable(1); > > Port_WriteBit(PORT_LED2,PORT_OFF); > > } > > > > // ---------------------------System IRQ 100Hz, alle 10ms -------------------------- > > // > > void ISR_10ms(void) > > { > > > > > > Port_WriteBit(PORT_LED1,PORT_ON); > > > > LCD_CursorPos(0x00); // dauert 1.2ms > > LCD_WriteWord(x, 5); > > > > Port_WriteBit(PORT_LED1,PORT_OFF); > > Irq_GetCount(INT_100HZ); > > > > } > > > > > > > Hallo Hannes, > > um die Störeinflüsse zu verringern ist es auch Möglich > die MCU in den ADC-Sleep-Mode zu setzten während die MCU > schläft wird gemessen und wenn die Messung fertig ist > weckt die MCU über den ADC-Ready-Interrupt wieder auf. > Das Modul "ADCapture-0.06" zeigt einige Varianten. > Es geht aber auch ohne Assembler. Schau dir mal die > Funktionen "Sleep(SMO)" (ADC Noise Reduction) an. > Beim Aufruf von "Sleep(SMO)" sollte die AD-Wandlung > gestartet werden und wenn fertig hoffentlich der > Bytecode-Interpreter-Interrupt "INT_ADC" aufgerufen werden. > Ob dann die MCU wirklich während der Messung geschlafen > hatt weiß ich aber auch nicht. > > Gruß Torsten