Verwendung von Ein-/Ausgängen in C-Unterfunktion

OP #2559421
Hallo,

ich möchte in einer C-Unterfunktion wechselnde Ein-Ausgangswerte 
verarbeiten.

Definiert ist z.B. ein Eingang im main.c
1
#define  IN2      PORTAbits.RA1

Diesen möchte ich in einer Funktion für eine Operation abfragen.

"25:Error [1105] symbol 'IN2' has not been defined" ist die Antwort beim 
Übersetzen. IN2 ist demnach nur im Main definiert.

Ist es gundsätzlich nicht möglich einen Eingang in einer Unterfunktion 
zu nutzen?

Danke,
Basti
Gast #2559428
Wo steht denn deine Unterfunktion - wahrscheinlich in einer anderen 
c-Datei? Und was meinst du mit Unterfunktion überhaupt?
Als Stichwort für google: Headerfile


Grüße
Gast #2559433
Also ich habe es genauso gemacht wie du: Eingänge am Anfagn der main.c 
definiert und ich kann sie später in jeder Unterfunktion beliebig 
abfragen...

LG Hubert
Gast #2559450
Bastian B. schrieb:
> Aber was mache ich mit globalen Variablen?

versuchen, ohne sie auszukommen
der funktion als parameter übergeben
versuchen, sie nur in einer *.c-Datei zu benötigen und dort als static 
deklarieren
dich mit "extern" auseinandersetzen
#2559473
Bastian B. schrieb:
> hm. das klingt schwierig.

Ist es aber nicht.
Du musst dich nur ein wenig mit den Grundlagen auseinandersetzen.

Die erste und wichtigste Grundlage lautet:

# wenn der Compiler ein *.c File übersetzt, dann übersetzt er auch
  nur dieses eine File.
  Was in anderen *.c Files steht, ist zu diesem Zeitpunkt völlig
  uninteressant und kümmert den Compiler nicht die Bohne.

# daraus folgt:
  jedes *.c File muss für sich alleine gesehen in sich vollständig
  sein.

# Jedes *.c File wird von oben nach unten compiliert.
  Daraus folgt: Bevor etwas verwendet werden kann, muss es dem
  Compiler bekannt gemacht werden.
  Es gibt dafür 2 Möglichkeiten
  + Definition
    Eine Definition veranlasst, dass auch im Speicher dafür
    Platz reserviert wird. Eine Variablendefinition ist daher
    dasjenige, welches dafür sorgt, dass eine Variable auch
    tatsächlich erzeugt wird.
  + Deklaration
    Eine Deklaration teilt dem Compiler zur geschätzten Kentnisnahme
    mit, dass etwas woanders existiert und wie es aussieht.
    Eine Deklaration sorgt nicht dafür, dass dafür Speicherplatz
    reserviert wird. Das muss durch eine Definition geschehen

# Aus dem letzten folgt wiederrum
  Alles, auch Variablen, darf nur einmal definiert werden. Man
  kann sich aber mit beliebig vielen Deklarationen darauf beziehen.

# Eine (gloable) Variable wird definiert, indem man sie ausserhalb
  einer Funktion als Variablendefinition, zb
1
    int MeineVar;
  hinschreibt.

# Eine Variablendeklaration wird gebildet, indem man einer gedachten
  Definition das Schlüsselwort 'extern' voranstellt.
  Um sich also aus einem anderen *.c File auf die soeben definierte
  Variable mittels einer Deklaration zu beziehen, schreibt man
1
    extern int MeineVar;

Lies dir in der >>> FAQ <<< die entsprechenden Abschnitte durch:

Punkt 8: Globale Variablen über mehrere Dateien
Punkt 9: Was hat es mit volatile auf sich
Punkt 6: Header File, wie geht das?
Gast #2559474
dann mußt du dich auch noch mit "volatile" außeinandersetzen

horst schrieb:
> versuchen, sie nur in einer *.c-Datei zu benötigen und dort als static
> deklarieren
> dich mit "extern" auseinandersetzen

ist immer noch aktuell

vermutlich nicht so praktikabel in dieser situation sind named pipes als 
alternative zur parameterübergabe
OP #2559673
ok.  Das habe ich gemacht.

Jetzt gibt es nurnoch ein Problem mit dem Rückgabewert der Funktion.

Der Compiler bringt dieses jedoch in Zusammenhang mit der 
Interruptvariable meines Timers

"Error [1521] This feature is not implemented in compiler. There may be 
a definition of external symbol 'timer' found instead of its 
declaration"

Meine Interruptvariable ist jetzt im Main als
1
volatile unsigned char timer=0

und in der .c Funktion als
1
extern volatile unsigned char timer=0

die Rückgabevariable habe ich schon versucht als alles mögliche zu 
definieren.
1
return x
Gast #2559679
Bastian B. schrieb:

> Meine Interruptvariable ist jetzt im Main als
> volatile unsigned char timer=0
> und in der .c Funktion als
> extern volatile unsigned char timer=0
> die Rückgabevariable habe ich schon versucht als alles mögliche zu
> definieren.
> return x

Ist das hier die "kleine Horrorshow der C Programmierung"? Brrr lern 
doch mal anständig programmieren das ziehts einem ja die Schuhe aus.
#2559686
Bastian B. schrieb:

> und in der .c Funktion als
>
>
1
extern volatile unsigned char timer=0
>

Du hast im Link etwas überlesen (oder nicht darauf geachtet).
Sobald eine Initialisierung vorhanden ist, wird aus einer Deklaration 
eine Definition.

(ABer das hat nichts damit zu tun, worauf sich der COmpiler in der 
Fehlermeldung bezieht. Da kann man nur raten, weil wir ... KEINE 
HELLSEHER SIND! Zeige deinen Code, dann kann man auch was dazu sagen)
OP #2559716
hier der ganze kram in gekürzter Form...
1
//globale Variablen
2
volatile unsigned char timer=0, i=0, sekunde=0;
3
//Funktionen
4
void intcounter(void);              // Aufruf des Serviceroutinenprogramms
5
int Empfang (void);
6
//Interrupt
7

8
#pragma code Timer=0x0008      // Interrupt to CPU Vector to Location 0008h (DB S.98)
9
void High (void)                 
10
{
11
 _asm goto intcounter _endasm       // 
12
}
13

14
//Interrupt-Routine
15

16
#pragma code                     // System Codebereich
17
#pragma interrupt Test        // Kennwort interrupt veranlasst
18

19
void Test ()
20
{
21
    PIR1bits.TMR1IF=0;
22
  timer=1;
23
  if (i==76)
24
  {
25
    sekunde=1;
26
    i=0;
27
  }
28
  else
29
    i++;   
30
}
31

32

33
//Main
34

35
void main (void)
36
{
37

38
  TRISA=0b11100111;     //PORTA Ein-/Ausgänge
39
  PORTA=0;      //PORTA ausschalten
40
  ADCON1=0x0F;               //Alle Port Pins digital
41
  TRISB=0;       //PORTB - Ausgang
42
  PORTB=0;      //PORTB ausschalten
43
        CMCON = 0x07;         //Komparatoreinänge deaktivieren
44
  T1CON=0b10000001;    //Timer1 - 16bit - kein Voteiler - aktiv
45
  TMR1H=0;            //Timer1 - Highbyte = 0
46
  TMR1L=0;      //Timer1 - Lowbyte = 0
47
  INTCON=0b11000000;    //Interrupts zulassen
48
  PIE1=0b00000001;          
49

50

51
  while (1)
52
  {  
53
    if       (IN1==1)  //definierter Eingang in defines.h
54
      PORTB=Empfang();
55
  }
56
}

und nun die Funktion. ist erstmal egal was die macht. Ich will 
nurverstehen, warum es keinen rückgabewert gibt.
1
#include <p18f2550.h>
2
#include "defines.h"
3

4
extern volatile unsigned char timer=0;
5

6
int Empfang (void)
7
{
8
  unsigned int Zyklus=0;    //Zeitwert der Zeitmerssung
9

10

11

12
  while (Sender==1)
13
  {
14
          if (timer==1)   //Synchronisationsbitlänge messen (Zyklus)
15
    {
16
      timer=0;
17
      Zyklus++;
18
    }
19
  }
20
return Zyklus;
21
}

Vielen Dank
#2559725
Bastian B. schrieb:

> extern volatile unsigned char timer=0;


Fehlermeldung

"Error [1521] This feature is not implemented in compiler. There may be
a definition of external symbol 'timer' found instead of its
declaration"

Bei nochmaligem Drüber-Nachdenken könnte das trotzdem stimmen (Ich hatte 
den GCC im Hinterkopf).
Der Compiler beschwert sich, dass du versuchst in einer Deklaration eine 
Initialisierung zu machen.

Schmeiss die Initialisierung weg, so wie das in C vorgesehen ist.
#2559764
Bastian B. schrieb:
> Damit ist die Fehlermeldung schonmal weg.
>
> Dafür gibt es eine Neue.


Wird das jetzt ein Ratespielchen:

Ich programmiere und ihr sucht in meinem Code nach den Fehlern, die mir 
der Compiler meldet.

> Error - could not find definition of symbol 'intcounter' in file
> './main.o'.

Was bedeutet die Fehlermeldung, welche Wörter kommen vor, wovon ist die 
Rede.
Danach gehst du in deinen Code und siehst nach wo spezfische Wörter aus 
der Fehlermeldung (intcounter) vorkommen und wie das mit deiner 
Rohübersetzung der Fehlermeldung zuammenhängt.
Gast #2559784
Bastian B. schrieb:

> void High (void)
> {
>  _asm goto intcounter _endasm       //
> }

> //Interrupt-Routine
>
> #pragma code                     // System Codebereich
> #pragma interrupt Test        // Kennwort interrupt veranlasst
>
> void Test ()
> {
>     PIR1bits.TMR1IF=0;
>   timer=1;
>   if (i==76)
>   {
>     sekunde=1;
>     i=0;
>   }
>   else
>     i++;
> }

Siehst du den Fehler??

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 14 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.