Forum: Mikrocontroller und Digitale Elektronik Probleme mit Übergabe


von Knut (Gast)


Angehängte Dateien:

Lesenswert?

Moin,

ich möchte gern zwei Werte an eine Funktion übergeben (7-Segment, 
dreistellig). Das Merkwürdige ist, dass es mit 8-Bit Variablen 
funktioniert. Bei 16-Bit gehts nicht mehr und die Anzeige zeigt Unsinn 
bzw. gar nichts an. Auch scheint der Controller überlastet zu sein.

in 7-Seg.c
1
void Display_Data (uint16_t Ziffer, uint16_t Point)
2
  {
3
    Punktwahl = Point;
4
    Einer = Ziffern_Table[Ziffer%10];
5
    Zehner = Ziffern_Table[(Ziffer/10)%10];
6
    Hunderter = Ziffern_Table[Ziffer/100];
7
  }

die Übergabe sieht so aus (in main.c):
1
Display_Data(Values[Parameter],Kanal);

Alle Variablen sind 16-Bit.

Wenn ich nun in der obing Funktion, "Ziffer" per Hand auf einen Wert 
setze ist alles ok.

Warum klappt die Übergabe nicht? Hier noch der Prototyp (7-Seg.c):
1
void Display_Data (uint16_t, uint16_t);
und die Globalisierung ind der 7-Seg.h welche in main.c includet wird:
1
extern void Display_Data (uint16_t, uint16_t);

Irgendwas hab ich wohl übersehen, finde es aber nicht.

von (prx) A. K. (prx)


Lesenswert?

Welche Version der Entwicklungsumgebung (Compiler)?

Die Division ist die teuerste Operation des Controllers. Einen 
Interrupt-Handler damit vollzustopfen ist nicht ratsam.

NB: count%2048 ergibt bei uint8_t nicht viel Sinn.

von Rolf Magnus (Gast)


Lesenswert?

Stellst du denn sicher, daß dein übergebener Wert kleiner als 1000 
bleibt?

von Knut (Gast)


Lesenswert?

A. K. schrieb:
> Welche Version der Entwicklungsumgebung (Compiler)?
AVR Studio 4.18 SP3 / Win AVR (GCC)

> count%2048 ergibt bei uint8_t nicht viel Sinn.
Jo, stimmt, Count = 16-Bit.

Rolf Magnus schrieb:
> Stellst du denn sicher, daß dein übergebener Wert kleiner als 1000
> bleibt?

Noch nicht, aber wenn ich das mit einer 8-Bit Variable mache, bekomme 
ich bei 255 einen Überlauf, wenn ich die Eingangsgröße (Spannung) 
erhöhe.

Bei 16-Bit geht gar nichts und irgendwo hält er sich übermäßig lange 
auf, da der Multiplex etwas zu haken beginnt.

Selbst wenn ich in der ADC-ISR nur
1
u_ist = ADC;
also keine Rechnung mache, gehts nicht.


Knut

von (prx) A. K. (prx)


Lesenswert?

Von der Struktur her: Die Hauptschleife nur fürs Debouncing zu verwenden 
und dafür das eigentliche Hauptprogramm in den 1ms-Interrupt zu 
verlagern erscheint mir etwas eigenwillig.

von (prx) A. K. (prx)


Lesenswert?

Knut schrieb:

> Noch nicht, aber wenn ich das mit einer 8-Bit Variable mache, bekomme
> ich bei 255 einen Überlauf, wenn ich die Eingangsgröße (Spannung)
> erhöhe.

Wenn du den Parameter 16-bittig machst, aber nicht sicherstellst, dass 
er innerhalb von 0..999 bleibt, dann riskierst du Schrott in den 
Hundertern.

> Selbst wenn ich in der ADC-ISR nur

Die knackigen Divisionen sind nicht die im ADC-Interrupt (weil 
Zweierpotenz), sondern die in der Dezimalkonvertierung.

von (prx) A. K. (prx)


Lesenswert?

Knut schrieb:

> AVR Studio 4.18 SP3 / Win AVR (GCC)

Die Version vom WinAVR wär interessanter. Da gabs vor Jahren mal eine, 
die nicht richtig multiplizieren und dividieren wollte.

von Knut (Gast)


Lesenswert?

Ich verwende die Version 20100110.

A. K. schrieb:
> Wenn du den Parameter 16-bittig machst, aber nicht sicherstellst, dass
> er innerhalb von 0..999 bleibt, dann riskierst du Schrott in den
> Hundertern.

Richtig, aber ich ändere nichts außer dem Datentyp der Übergabefunktion 
und schon gehts nicht mehr?

> Die knackigen Divisionen sind nicht die im ADC-Interrupt (weil
> Zweierpotenz), sondern die in der Dezimalkonvertierung.

Auch wenn ich in der Display_Data Ziffer auf 999 begrenze geht es nicht. 
Setze ich Ziffer jedoch auch eine Zahl zwischen 0...999 gehts.


Knut

von Knut (Gast)


Lesenswert?

Tja, scheinbar gab es Probleme mit der Berechnung :-(.

Ich habe nun die Berechnung der Digits in die main.c verlagert und 
übergebe nun die fertig berechneten Digits, funktioniert.

Offensichtlich macht der Kompiler da Blödsinn...



Knut

von gestresster uC (Gast)


Lesenswert?

Knut schrieb:
> Offensichtlich macht der Kompiler da Blödsinn...

Der Compiler macht - in diesem Fall zumindest - genau was man ihm sagt.

Blödsinnig ist es, eine ISR, die bei 1 MHz Clock alleine schon 850 µs 
dauert, im 1 ms-Takt aufzurufen.

von Knut (Gast)


Lesenswert?

gestresster uC schrieb:
> Blödsinnig ist es, eine ISR, die bei 1 MHz Clock alleine schon 850 µs
> dauert, im 1 ms-Takt aufzurufen.

Das mag sein. Hat jemand noch Verbesserungsvorschläge (Form, Stil, 
Syntax)?



Gruß Knut

von Karl H. (kbuchegg)


Lesenswert?

Dazu müsste man erst mal wissen, was das Ganze überhaupt sein soll und 
worum es da geht.

Dein ganzes Programm kommt mir unnötig und übermässig kompliziert vor. 
Die Logik dahinter ist so dermassen über das komplette Programm 
verstreut und verschmiert, dass es gar nicht so einfach ist, da etwas 
sinnvolles dazu zu sagen.

Alleine schon die Tastenauswertung würde mich wanhsinnig machen :-)

von Knut (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Dazu müsste man erst mal wissen, was das Ganze überhaupt sein soll und
> worum es da geht.

Gern:

Es handelt sich um 3 Schwellwertschalter mit 3 Relaisausgängen, 4 
Tastern, 3 7-Segment-Anzeigen. Einstellbar sollen nun die 
Schaltschwellen sein.
Das ganze hat 2 Messbereiche (70/500V) sowie ein Menü das auf der 
Anzeige zu sehen sein soll. Mit den Tastern soll durcsh Menü navigiert 
werden.

Menü hat natürlich allen Schnick-Schnack (Ziffern Blinken wenn angewält 
usw., ist in dieser Version aber noch nicht implementiert.


Was gibt es gegen meine Tasterabfrage? Einfacher gehts doch nun nicht 
mehr. Drücken, Entprellen und gut.



Gruß Knut

von Knut (Gast)


Lesenswert?

Achso, die Schatschwellen sind natürlich sichtbar wenn man den Menüpunkt 
anwählt. Auch die Istspannung ist im richtigen Menüpunkt zu sehen.

Knut

von Karl H. (kbuchegg)


Lesenswert?

Knut schrieb:

> Was gibt es gegen meine Tasterabfrage? Einfacher gehts doch nun nicht
> mehr. Drücken, Entprellen und gut.

Schau dir die PeDa Entprellung an.
Im Vergleich dazu ist deine einfach nur Müll. Auch (oder gerade 
speziell) was die Verarbeitung von Tastendrücken angeht.

Wenn ich sowas schon sehe
1
  if ( (!(PINB & (1<<DOWN))) && (Debounce_down ==0) ) 
2
  {
3
    Debounce_down = 200;
(verzeih den Ausdruck), dann wird mir schlecht.
Alles viel zu kompliziert und mit viel zu viel Hintergdunwissen zu 
benutzen.

von Knut (Gast)


Lesenswert?

Ich hab die Entprellung nur föüchtig überflogen. Macht er das mit 
delays?
Wenn ja, dann sehe ich nocht was an seiner Version besser sein soll...

Aber wie gesagt, immer her mit der Kritik, ich will ja lernen

von Knut (Gast)


Lesenswert?

Ok, er macht es nicht mit delays...

Aber wo ist das Problem in einem Timer eine Variable zu decrementieren 
(im Hintergrund). Was passiert mit seiner Routine wenn man die Taste 
gedrückt hält? Gilt dann nur ein Anschlag? Währe auch doof...
Will aber Peter nicht runtermachen, er ist echt gut.

Knut

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.