Forum: Mikrocontroller und Digitale Elektronik Programmierung in c programm teil erklären


von Andrej W. (waltera)


Lesenswert?

Hallo
Ich habe ein Programmausschnitt erhalten wo mir bei meinem Projekt 
helfen soll. Leider verstehe ich nicht genau was in den abschnitt 
passiert. Ich weiß nur das eine RS232 Schnittstelle eingelesen wird. 
Hoffe mir kann da einer helfen und sagen was da genau im Prgramm 
passiert. Ich bedanke mich schin mal im voraus. : )

//Variable erstellen;
bit Takt = 0, RS232Empfang = 0, RS232Sendet = 0, WRS232 = 0;
bit TasterAlt =1;
bit TasterMerker = 1;
sbit LEDRS232Empfangen = P0^5;



void it_RS232 (void) interrupt 4    // Serieller Interrupt hat die 
Nummer 4
{                  // Interrupt ES (TI und RI) wird beim Stop-Bit 
ausgelöst
  if (RI)             // Senden-Interrupt TI ausgelöst
  {
    RS232EmpBuffer = SBUF & 0x7f;    // empfangenes Byte speichern
    LEDRS232Empfangen = !LEDRS232Empfangen;
    RI = 0;            // Interrupt ES zurücksetzen
    RS232Empfang = 1;      // Merker für RS232-Empfang
                // Interrupt ES zurücksetzen
  }
  else   TI = 0;        // kann nur noch Empfang-Interrupt RI sein
}
void DisplayAusgabe(void)
{
  printlcd(buf1,1);
  printlcd(buf2,2);
}
void RS232EmpfangAuswerten(void)
{
  RS232Empfang = 0; // RS232Empfangsmerker zurücksetzen
  if (WRS232)
    {
        RS232EmpfangsText[RS232Zaehler] = RS232EmpBuffer;   // 
empfangenes Zeichen in den Empfangsstring
        RS232EmpfangsText[RS232Zaehler+1] = 0;
        RS232Zaehler++;
        if (RS232Zaehler >= 9)
        {
            //sprintf(buf1,"%s",RS232EmpfangsText);
            Waagenwert = atof(RS232EmpfangsText);
            sprintf(buf1,"%7.1lf  ",Waagenwert);
            DisplayAusgabe();
            WRS232 = 0;
        }
    }
    if (RS232EmpBuffer == '+')
    {
        WRS232 = 1;
        RS232Zaehler = 0;
  }
}
// Funktion wartet auf das Drücken von P0^0 und merkt sich, dass P0^0 
gedrückt wurde
void irq_Timer1(void) interrupt 3    //wird alle 32ms aufgerufen
{
  if ( (Taster != TasterAlt) && !Taster )  //erst beim Drücken des 
Taster P0^0
  {
    TasterMerker = !TasterMerker;
  }
  TasterAlt = Taster;
}
void Initialisierung(void)
{
  BDRCON = 0x1c;          // SPD=0 RBCK=1, TBCK=1 BRR=1  (Seite 76) für 
1200Baud
  PCON   = 0x10;          // SMOD1=0 keinen Teiler 2    (Seite 75) für 
1200Baud
  REN = 1;            // im SCON: Empfang erlauben  (Seite 72)
  SM1 = 1;            //        Mode 1 8-bit UART
  BRL = 202;              // BaudRatenSelektion  1200 Baud (X2 = 0) 
(Seite73)
  sprintf(buf2,"1200Baud");

// Interrupt-Einstellungen
  ES  = 1;            // RS232 Interrupt freigeben
    ET2 = 1;
  TMOD = 0x11;  // Timer0 und Timer1 auf 16 Bit
  ET1 = 1;      // Interruptfreigabe für Timer 1
  EX0 = 1;      // Interruptfreigabe für P3.2
  IT0 = 1;      // Flankentriggerung für P3.2
  EA  = 1;      // allgemeine Interruptfreigabe
    TR1 = 1;      // Timer 1 wird gestartet
// *** allgemeine Initialisierung
  initlcd();            // LCD-Display initialisieren
  testlcd();            //  LCD-Display testen und löschen
  //sprintf(buf1,"Empfang ");
  //DisplayAusgabe();



Ende

von C-Code (Gast)


Lesenswert?

1
//Variable erstellen;
2
bit Takt = 0, RS232Empfang = 0, RS232Sendet = 0, WRS232 = 0;
3
bit TasterAlt =1;
4
bit TasterMerker = 1;
5
sbit LEDRS232Empfangen = P0^5;
6
7
8
9
void it_RS232 (void) interrupt 4    // Serieller Interrupt hat die
10
Nummer 4
11
{                  // Interrupt ES (TI und RI) wird beim Stop-Bit
12
ausgelöst
13
  if (RI)             // Senden-Interrupt TI ausgelöst
14
  {
15
    RS232EmpBuffer = SBUF & 0x7f;    // empfangenes Byte speichern
16
    LEDRS232Empfangen = !LEDRS232Empfangen;
17
    RI = 0;            // Interrupt ES zurücksetzen
18
    RS232Empfang = 1;      // Merker für RS232-Empfang
19
                // Interrupt ES zurücksetzen
20
  }
21
  else   TI = 0;        // kann nur noch Empfang-Interrupt RI sein
22
}
23
void DisplayAusgabe(void)
24
{
25
  printlcd(buf1,1);
26
  printlcd(buf2,2);
27
}
28
void RS232EmpfangAuswerten(void)
29
{
30
  RS232Empfang = 0; // RS232Empfangsmerker zurücksetzen
31
  if (WRS232)
32
    {
33
        RS232EmpfangsText[RS232Zaehler] = RS232EmpBuffer;   //
34
empfangenes Zeichen in den Empfangsstring
35
        RS232EmpfangsText[RS232Zaehler+1] = 0;
36
        RS232Zaehler++;
37
        if (RS232Zaehler >= 9)
38
        {
39
            //sprintf(buf1,"%s",RS232EmpfangsText);
40
            Waagenwert = atof(RS232EmpfangsText);
41
            sprintf(buf1,"%7.1lf  ",Waagenwert);
42
            DisplayAusgabe();
43
            WRS232 = 0;
44
        }
45
    }
46
    if (RS232EmpBuffer == '+')
47
    {
48
        WRS232 = 1;
49
        RS232Zaehler = 0;
50
  }
51
}
52
// Funktion wartet auf das Drücken von P0^0 und merkt sich, dass P0^0
53
gedrückt wurde
54
void irq_Timer1(void) interrupt 3    //wird alle 32ms aufgerufen
55
{
56
  if ( (Taster != TasterAlt) && !Taster )  //erst beim Drücken des
57
Taster P0^0
58
  {
59
    TasterMerker = !TasterMerker;
60
  }
61
  TasterAlt = Taster;
62
}
63
void Initialisierung(void)
64
{
65
  BDRCON = 0x1c;          // SPD=0 RBCK=1, TBCK=1 BRR=1  (Seite 76) für
66
1200Baud
67
  PCON   = 0x10;          // SMOD1=0 keinen Teiler 2    (Seite 75) für
68
1200Baud
69
  REN = 1;            // im SCON: Empfang erlauben  (Seite 72)
70
  SM1 = 1;            //        Mode 1 8-bit UART
71
  BRL = 202;              // BaudRatenSelektion  1200 Baud (X2 = 0)
72
(Seite73)
73
  sprintf(buf2,"1200Baud");
74
75
// Interrupt-Einstellungen
76
  ES  = 1;            // RS232 Interrupt freigeben
77
    ET2 = 1;
78
  TMOD = 0x11;  // Timer0 und Timer1 auf 16 Bit
79
  ET1 = 1;      // Interruptfreigabe für Timer 1
80
  EX0 = 1;      // Interruptfreigabe für P3.2
81
  IT0 = 1;      // Flankentriggerung für P3.2
82
  EA  = 1;      // allgemeine Interruptfreigabe
83
    TR1 = 1;      // Timer 1 wird gestartet
84
// *** allgemeine Initialisierung
85
  initlcd();            // LCD-Display initialisieren
86
  testlcd();            //  LCD-Display testen und löschen
87
  //sprintf(buf1,"Empfang ");
88
  //DisplayAusgabe();

von verwirrt (Gast)


Lesenswert?

Da wären noch ein paar Hinweise gut:
- Controller
- Compiler
- das Programm enthält keine main -> nicht lauffähig

von Patrick (Gast)


Lesenswert?

Was genau willst Du denn wissen? Der Codeschnipsel ist doch bereits sehr 
gut kommentiert, und die Funktionsnamen sind auch "sprechende" deutsche 
Bezeichnungen... Sollte doch - selbst für einen blutigen C-Anfänger - 
kein allzu großes Problem sein, halbwegs zu verstehen, was da passiert.

von Andrej W. (waltera)


Angehängte Dateien:

Lesenswert?

Hi
Ich habe die main nicht rein gemacht weil ich die ja vertsehe. Bei mir 
ist das problem mit dem Abschnitt. Aber ich kann mal das ganze Programm 
Posten.

Hier das Vollständige Programm.

/* Technikerarbeit-Messgerät für Dampfqualität.c 
*********************************************************
 * Prototyp: Das Messgerät soll die Interne Dampfqualität des 
Sterilisatonsraumes messen, und mit einer Berechnungsformel den Wert des 
Dampfqualitäts ausgeben. 
*
 *********************************************************************/

#include <at89c5131.h>    // Registeradressen
#include <cbs5131.h>    // CBS-Platinentreiber
#include <stdio.h>      // für sprintf
#include <string.h>      // für strlen
#include <stdlib.h>      // für atof



//P0_0 = Taster -> "Start der Messung"
//P0_1 = Ventil1 -> "Ventil Kühlwasser"
//P0_2 = Ventil2 -> "Entlüftungs Ventil"
//P0_3 = Ventil3 -> "Ventil Heißdampf"
//P0_4 = Ventil4 -> "Ventil Entleerung"
//P0_5 = Sensor1 -> "Sensor Signal Waage Nullt"
//P0_6 = Sensor2 -> "Sensor Waage nimmt Messwert"
//P0_7 = Sensor3 -> "Sensor Messwert wurde aufgenommen und Berechnung 
des Messwert"


sbit Taster = P3^5;                          //um ändern auf P1^7 wird 
in Taster umdeklariert
sbit Test = P1^7;
sbit Ventil1 = P1^6;            //P0^1 wird in Ventil1 umdeklariert
sbit Ventil2 = P1^5;            //P0^2 wird in Ventil2 umdeklariert
sbit Ventil3 = P1^4;            //P0^3 wird in Ventil3 umdeklariert
sbit Ventil4 = P1^3;            //P0^4 wird in Ventil4 umdeklariert
sbit Sensor1 = P1^2;            //P0^5 wird in Sensor1 umdeklariert
sbit Sensor2 = P1^1;            //P0^6 wird in Sensor2 umdeklariert
sbit Sensor3 = P1^0;            //P0^7 wird in Sensor3 umdeklariert

// globale Variable
unsigned char z = 0,RS232EmpBuffer, RS232Zaehler = 0;
idata unsigned char RS232EmpfangsText[17], buf1[17], buf2[17];
double Waagenwert =0, Waagenwert1 =0, Waagenwert2=0,  Gesamtgasanteil=0, 
Gasanteil1=0, Gasanteil2=0, Prozentwert=0, Mittelwert =0;
double Gas = 20;
//Variable erstellen;
bit Takt = 0, RS232Empfang = 0, RS232Sendet = 0, WRS232 = 0;
bit TasterAlt =1;
bit TasterMerker = 1;
sbit LEDRS232Empfangen = P0^5;



void it_RS232 (void) interrupt 4    // Serieller Interrupt hat die 
Nummer 4
{                  // Interrupt ES (TI und RI) wird beim Stop-Bit 
ausgelöst
  if (RI)             // Senden-Interrupt TI ausgelöst
  {
    RS232EmpBuffer = SBUF & 0x7f;    // empfangenes Byte speichern
    LEDRS232Empfangen = !LEDRS232Empfangen;
    RI = 0;            // Interrupt ES zurücksetzen
    RS232Empfang = 1;      // Merker für RS232-Empfang
                // Interrupt ES zurücksetzen
  }
  else   TI = 0;        // kann nur noch Empfang-Interrupt RI sein
}
void DisplayAusgabe(void)
{
  printlcd(buf1,1);
  printlcd(buf2,2);
}
void RS232EmpfangAuswerten(void)
{
  RS232Empfang = 0; // RS232Empfangsmerker zurücksetzen
  if (WRS232)
    {
        RS232EmpfangsText[RS232Zaehler] = RS232EmpBuffer;   // 
empfangenes Zeichen in den Empfangsstring
        RS232EmpfangsText[RS232Zaehler+1] = 0;
        RS232Zaehler++;
        if (RS232Zaehler >= 9)
        {
            //sprintf(buf1,"%s",RS232EmpfangsText);   kommentiert zum 
testen 20.04.2011
            Waagenwert = atof(RS232EmpfangsText);
            sprintf(buf1,"%7.1lf  ",Waagenwert);
            DisplayAusgabe();
            WRS232 = 0;
        }
    }
    if (RS232EmpBuffer == '+')
    {
        WRS232 = 1;
        RS232Zaehler = 0;
  }
}
// Funktion wartet auf das Drücken von P0^0 und merkt sich, dass P0^0 
gedrückt wurde
void irq_Timer1(void) interrupt 3    //wird alle 32ms aufgerufen
{
  if ( (Taster != TasterAlt) && !Taster )  //erst beim Drücken des 
Taster P0^0
  {
    TasterMerker = !TasterMerker;
  }
  TasterAlt = Taster;
}
void Initialisierung(void)
{
  BDRCON = 0x1c;          // SPD=0 RBCK=1, TBCK=1 BRR=1  (Seite 76) für 
1200Baud
  PCON   = 0x10;          // SMOD1=0 keinen Teiler 2    (Seite 75) für 
1200Baud
  REN = 1;            // im SCON: Empfang erlauben  (Seite 72)
  SM1 = 1;            //        Mode 1 8-bit UART
  BRL = 202;              // BaudRatenSelektion  1200 Baud (X2 = 0) 
(Seite73)
  sprintf(buf2,"1200Baud");

// Interrupt-Einstellungen
  ES  = 1;            // RS232 Interrupt freigeben
    ET2 = 1;
  TMOD = 0x11;  // Timer0 und Timer1 auf 16 Bit
  ET1 = 1;      // Interruptfreigabe für Timer 1
  EX0 = 1;      // Interruptfreigabe für P3.2
  IT0 = 1;      // Flankentriggerung für P3.2
  EA  = 1;      // allgemeine Interruptfreigabe
    TR1 = 1;      // Timer 1 wird gestartet
// *** allgemeine Initialisierung
  initlcd();            // LCD-Display initialisieren
  testlcd();            //  LCD-Display testen und löschen
  //sprintf(buf1,"Empfang ");
  //DisplayAusgabe();
  RS232Empfang = 0;        // Wichtig hier, sonst erstes Zeichen falsch
  Ventil1=0;      //Kühlwasser
  Ventil2=0;      //Entlüftung
  Ventil3=0;      //Heißdampf
  Ventil4=0;      //Entleerung
  Sensor1=0;      //Signal Wagge Nullt
  Sensor2=0;      //Signal Wagge Messwert
  Sensor3=0;      //Signal Messwert aufgenommen und Berechnung des 
Messwert
  Taster = 1;
    Test = 0;
}
void main (void)
{
  Initialisierung();
  while (1)      // Endlosschleife
  {
    if(TasterMerker==0)
    {
      z++;      //zähler plus 1
      TasterMerker = 1;
    }
    //Auswahlmenü durch Switch und Case
    //Je nach der größe von r wird ein Case ausgeführt
    switch (z)
    {
      case 1:
      if(Sensor1==1)      //Sensor1 wird ereicht
      {
        Ventil2=0;      //Entlüftung schließt
        Ventil3=0;      //Heißdampf
        printlcd ("  Waage Nullen ",1);  // Ausgabe an Zeile 1 des LCDs
      }
        else
            Ventil1=1;    //Kühlwasser
      Ventil2=1;    //Entlüftung
      Ventil3=1;    //Heißdampf
      Ventil4=0;      //Entleerung
      printlcd ("     CASE1     ",1);  // Ausgabe an Zeile 1 des LCDs
      printlcd ("                ",2);  // Ausgabe an Zeile 2 des LCDs
      break;
      case 2:
      Ventil3=1;
       printlcd ("     CASE2     ",1);  // Ausgabe an Zeile 1 des LCDs
      printlcd ("               ",2);  // Ausgabe an Zeile 1 des LCDs
      if(Sensor2==1)                 //Sensor2 wird erreicht
        {
        Ventil3=0;
        RS232EmpfangAuswerten();
        Waagenwert1 = Waagenwert;
        printlcd ("Bitte Waage Nullen",2);  // Ausgabe an Zeile 2 des 
LCDs
        }
      break;
      case 3:
      Ventil3=1;
       printlcd ("     CASE3     ",1);  // Ausgabe an Zeile 1 des LCDs
       printlcd ("               ",2);  // Ausgabe an Zeile 1 des LCDs

      if (Sensor3==1)     //Sensor3 wird erreicht
      {
        Ventil3=0;
        RS232EmpfangAuswerten();
        Waagenwert2 = Waagenwert;
        printlcd ("Taster betätigen",2);  // Ausgabe an Zeile 2 des LCDs
      }
      break;
      case 4:
      Ventil3=0;    //Heißdampf schließt
      Ventil4=1;    //Entleerung öffnet
            Ventil2=1;      //Entlüftung öffnet
      Ventil1=0;    //Kühlwasser schließt
                          //Berechnung
      Gasanteil1=Gas/Waagenwert1;          //Gasanteil = Gas / 
Waagenwert1
      Gasanteil2=Gas/Waagenwert2;           //Gasanteil = Gas / 
Waagenwert2

      Gesamtgasanteil=Gasanteil1+Gasanteil2; 
//Gesamtgasanteil=Gasanteil1+Gasanteil2
            Mittelwert=Gesamtgasanteil/2; 
//Mittelwert=Gesamtgasanteil/2
      Prozentwert=Mittelwert*100;          //Prozent = Mittelwert * 100

      sprintf (buf1,"%1i Prozent",Prozentwert);    // Ausgabe an Zeile 1 
des LCDs
      printlcd(buf1,1);
            sprintf (buf2,"M-Wert=%1i",Mittelwert);    // Ausgabe an 
Zeile 2 des LCDs
      printlcd(buf2,2);
      break;

      //Hauptmenue
      default:
      printlcd ("  Systemstart  ",1);  // Ausgabe an Zeile 1 des LCDs
      printlcd ("Taste  Druecken",2);  // Ausgabe an Zeile 2 des LCDs
      Ventil3=0;    //Heißdampf schließt
      Ventil4=1;    //Entleerung öffnet
            Ventil2=0;      //Entlüftung schließt
      Ventil1=0;    //Kühlwasser schließt
            z=0;
      break;
    }
  }  // Ende While-Schleife
}   //Ende Programm

von Andrej W. (waltera)


Lesenswert?

Hi
Ich würd gern wissen wie das mit der Schnittstelle abläuft.

  BDRCON = 0x1c;          // SPD=0 RBCK=1, TBCK=1 BRR=1
1200Baud
  PCON   = 0x10;          // SMOD1=0 keinen Teiler 2
1200Baud
  REN = 1;            // im SCON: Empfang erlauben
  SM1 = 1;            //        Mode 1 8-bit UART
  BRL = 202;              // BaudRatenSelektion  1200 Baud

Was hat das zu bedeuten. Was grob da passiert weiß ich, aber wie des 
genau abläuft.

von verwirrt (Gast)


Lesenswert?

Baudrate wird eingestellt, Modus 1 8bit UART,
der Rest dieses Rätsels wird im Datenblatt deines Controllers aufgelöst.

von Andrej W. (waltera)


Lesenswert?

OK DANKE

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.