Lieber Besucher, herzlich willkommen bei: RCLine Forum. Falls dies Ihr erster Besuch auf dieser Seite ist, lesen Sie sich bitte die Hilfe durch. Dort wird Ihnen die Bedienung dieser Seite näher erläutert. Darüber hinaus sollten Sie sich registrieren, um alle Funktionen dieser Seite nutzen zu können. Benutzen Sie das Registrierungsformular, um sich zu registrieren oder informieren Sie sich ausführlich über den Registrierungsvorgang. Falls Sie sich bereits zu einem früheren Zeitpunkt registriert haben, können Sie sich hier anmelden.

Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

1

Samstag, 1. Januar 2005, 17:45

Servoimpuls mit Atmel Mega8 auswerten ?!

Hallo,

gleich noch eine Frage. Es ist mir sehr einfach gelungen, ein Servo mit dem Mega8 anzusteuern.
Aber kann mir jemand einen Tip geben, wie ich am besten die vom Empfänger kommenden Impulse analysiere (also eine Pulslängenmessung) ?
Ich möchte den Mega8 zwischen zwei Empfängerausgänge und zwei Servos setzen, um einen speziellen Mischer zu realisieren (Klapptriebwerkssteuerung mit autom. Positionierung des Propellers).

Matthias Huck

2

Samstag, 1. Januar 2005, 20:35

Hallo Matthias

In welcher Programmiersprache willst du das programm schreiben ?

Im Prinzip geht das einfach :

Signal an den InputCapturePin anschliessen und die CaptureUnit
auf steigende Flanke einstellen (Bit 6 TCCR1B=1) und den Interrupt
freigeben.

INCL(TIMSK,5); // input Capture enable PD4
TCCR1B:=10+64; // Timer1=Run mit 8MHZ

Jetzt wird bei steigender Flanke ein Interrupt ausgelöst und der Timer
gelöscht und bei der fallenden Flanke der Capturewert ausgelesen und
zwar 1500 bei 1,5 msec.

Interrupt Timer1Capt; // Int bei Capture
begin
if Bit(TCCR1B,6) then
EXCL(TCCR1B,6); // jetzt auf fallende Flanke warten
Timer1:=0;
Return;
endif;
INCL(TCCR1B,6); // jetzt wieder auf steigende Flanke warten
Endwert:=InputCapture;
end;

Und da bis zum nächsten Impuls 20mSec Zeit vergehen kann mit dem selben Timer jetzt der Servo Ausgang realisiert werden. Leider habe ich kein fertiges
Beispiel dafür. Aber etwa so müsste es gehen :

PWMRegister Init auf 20MSec
//PWM 4 20mSec // 20mSec PWM

ICR1H:=HI(20000); // HI immer zu erst beim schreiben
ICR1l:=LO(20000);
TCCR1A:=%10100010;
TCCR1B:=%00011010;

und jetzt den PWM setzen PWM(1500) für 1,5 msec


procedure PWM1(wert : word);
begin
OCR1AH:=HI(Wert); // HI immer zu erst beim schreiben
OCR1Al:=LO(Wert);
end;
procedure PWM2(wert : word);
begin
OCR1BH:=HI(Wert); // HI immer zu erst beim schreiben
OCR1Bl:=LO(Wert);
end;


Ich hoffe du kannst damit etwas anfangen !

mfg
Peter :ok:

Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

3

Samstag, 1. Januar 2005, 22:23

Erstmal vielen Dank für die schnelle Antwort!
Ja, es hilft mir sehr weiter zu wissen, daß ich den InputCapturePin verwenden kann. Ich nutze den Pascal Compiler von e-lab, und jetzt habe ich einen guten Anhaltspunkt, um in den umfangreichen Dokumenten und Beispielen zu suchen. Es gibt ja bestimmt etliche Möglichkeiten an das Problem heranzugehen, aber dies klingt wrklich schön einfach.
Zum Ansteuern der Servos gibt es bereits eine fertige Funktion, die auch gut funktioniert. Ob sich das dann mit dem Einlesen der Impulse beißt, wird sich zeigen ...

MfG,
Matthias

4

Samstag, 1. Januar 2005, 22:39

Hallo Matthias

Das passt ja ! Das Beispiel ist in Pascal von E-Lab !!
Wenn du noch Hilfe brauchst kein Problem !!

mfg
Peter

Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

5

Samstag, 1. Januar 2005, 22:46

OK,
ich werd's morgen mal ausprobieren.

Matthias

Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

6

Sonntag, 2. Januar 2005, 12:30

Hilfe, Problem !

Ich hab's noch nicht ausprobiert, weil ich gerade lese, daß die Servoansteuerungs-Libraryfunktion den Timer1 vollständig für sich beansprucht. Somit kann ich ihn nicht mehr für die Capture-Funktion einsetzen.
Da ich mindestens 2 Servo-Ausgänge brauche (wohingegen 1 Eingang reichen würde) und die Libraryfunktion schon so gut funktioniert, schrecke ich vor hardwarenahen eigenen Prozeduren zurück.
Gibt es nicht noch andere Möglichkeiten für die Pulslängenmessung (z.B. Empfängerimpuls am Interrupteingang, und mit SysTick zählen, oder so ?). Dabei müßte natürlich auch wieder berücksichtigt sein, daß die Interruptroutine nicht zu lang ausfällt, damit die Servos am Ausgang nicht zittern...

Meine Hoffnung wäre, daß schon mal jemand Ein- und Ausgang am Mega8 realisiert hat, von wegen Rad neu erfinden :) ...
Ja, ok, ich bin auch faul.

Matthias

7

Sonntag, 2. Januar 2005, 13:01

Da ein Servoimpuls ja nur ca. alle 15ms kommt und dann 1 bis 2 ms dauert, hast du genug zeit nacheinander den Impuls zu messen und zwei Servoimpulse auszugeben. Sowas geht dann auch völlig ohne Interrupts, ohne Timer und sequentiell = viel einfacher. Der Ablauf sieht dann so aus (in Pseudosprache):

Hauptschleife:
Warten bis Servosignal Low ist.
Warten bis Servosignal High ist.
ServoPos = 0;
while(Servosignal == 1)
{
ServoPos=ServoPos+1;
Warte 10µS (z.B. 10 nop ausführen minus Schleifenoverhead, je nach MC)
}
// jetzt hast du in Servopos die Position zwischen 100 (min) und 200 (max).

// 1. servopuls ausgeben:
var = servopos;
Output1 = 1;
while(var > 0)
{
Warte 10µS;
var--;
}
Output1 = 0;

// 2. servopuls ausgeben:
var = 200-(servopos-100); // beispiel: Output2 ist invertierte Servoposition
Output2 = 1;
while(var > 0)
{
Warte 10µS;
var--;
}
Output2 = 0;

goto Hauptschleife;

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »andix« (2. Januar 2005, 13:06)


Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

8

Sonntag, 2. Januar 2005, 13:22

Hallo Andix,

sowas ähnliches hatte ich auch schon im Sinn, habe aber Zweifel, ob das in Pascal (e-lab Compiler) schnell genug geht, und daran habe ich mich gerade mühsam gewöhnt.
Deswegen wollte ich Assembler gern vermeiden (da der Controller nebenbei auch noch anderes, rechenintensiveres erledigen soll, was mir in Assembler zu schwierig ist).

Vielleicht werde ichs als erstes nochmal mit der Interruptleitung versuchen ...

Matthias

9

Sonntag, 2. Januar 2005, 22:15

Hallo,

ich hab mal was mit avrgcc gemacht, läuft auf einem 2313 mit 10MHz. Nicht ganz sauber programmiert, die Konstanten hängen zb von der Taktfrequenz ab, aber es funktioniert.

Ich lese 4 Kanäle ein und gebe 6 aus, mit Verzögerung aber das ist in meiner Anwendung unkritisch (Feuerlöschboot). Mit 2 Kanälen solltest du eine angepasste Ausgaberoutine verwenden.

Sorry die Tabulatoren schluckt das Forum wohl.

Andi


#include <inttypes.h>
#include <avr/io.h>
#include <avr/wdt.h>
#include <main.h>

void checkLimits(int16_t *checkvalue){
if(*checkvalue>5000)
*checkvalue=5000;
if(*checkvalue<-5000)
*checkvalue=-5000;
}

int16_t rc_read(uint8_t *port, uint8_t pin){
loop_until_bit_is_set(*port,pin); // warten auf Eingangspin HIGH
TCNT1=0; // Timer auf 0 setzen
TCCR1A=0; // Timer 1 ist normaler Timer
TCCR1B=1; // Starten mit Prescaler 1
loop_until_bit_is_clear(*port,pin);// warten auf Eingangspin LOW
TCCR1B=0; // Timer stoppen
return (uint16_t) (TCNT1-rc_center); // Neutralstellung abziehen
}

void rc_write(int16_t *out){
TCCR1B=0;
TCCR1A=0;
TCNT1=0;
int16_t counter;
TCCR1B=1;
sbi(PORTB,AD);
sbi(PORTB,BD);
sbi(PORTB,CD);
sbi(PORTB,AV);
sbi(PORTB,BV);
sbi(PORTB,CV);
while(TCNT1<21550){
counter=TCNT1-15200;
if(*(out)<counter)
cbi(PORTB,AD);
if(*(out+1)<counter)
cbi(PORTB,BD);
if(*(out+2)<counter)
cbi(PORTB,CD);
if(*(out+3)<counter)
cbi(PORTB,AV);
if(*(out+4)<counter)
cbi(PORTB,BV);
if(*(out+5)<counter)
cbi(PORTB,CV);
}
TCCR1B=0;
TCNT1=0;
}


void ioinit(void){
outb(DDRB,0xff);
outb(DDRD,0x40); /* Pin 7 ist Ausgang */
}


int main(void)
{
ioinit();
int16_t in[eingange];
int16_t out[ausgaenge];

// Hauptschleife
//wdt_enable(WDTO_120MS);

while(1){
in[K8] = rc_read(&PIND,in8);
in[K1] = rc_read(&PIND,in1);
in[K2] = rc_read(&PIND,in2);


// Hier die ganze Rechnerei, hab ich wegen der Uebersicht gelöscht

rc_write(&out);

//wdt_reset();
}
}



und aus main.h:

#define in1 0
#define in2 1
#define in8 2

#define ausgaenge 6
#define eingange 3

#define K1 0
#define K2 1
#define K8 2
#define AD 7
#define BD 5
#define CD 3
#define AV 6
#define BV 4
#define CV 2

#define A 0
#define B 2
#define C 4
#define rc_min 8850
#define rc_center 15000
#define rc_max 22500
glaube keinem der dauernd mit seinen Fachkenntnissen prahlt...

Dieser Beitrag wurde bereits 3 mal editiert, zuletzt von »andig« (2. Januar 2005, 22:26)


Prof._Dr._YoMan

RCLine User

Wohnort: D-76137 Karlsruhe

Beruf: Hard-/Software Ingenieur

  • Nachricht senden

10

Sonntag, 2. Januar 2005, 22:21

Quellcode

1
2
3
PS: Es gibt die formieranweisung [ code ] (ohne spaces).
   Dann sieht das so aus und die Einrückungen
      gehen nicht verloren.


Edit: Tja sie wird angeboten, aber wie man sieht funktioniert sie hier nicht. :) AAAADDDDMIIIIIIN!?!
Meistens haben Platzhirsche eine hohe Beratungsresistenz, dafür eine geringe Wahrnehmungsfähigkeit..... (Claus Eckert)

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »Prof._Dr._YoMan« (2. Januar 2005, 22:22)


11

Sonntag, 2. Januar 2005, 22:27

Ja leider... jetzt weiss ich auch wieso man unbedingt tabs verwenden sollte beim Programmieren :nuts:
glaube keinem der dauernd mit seinen Fachkenntnissen prahlt...

12

Sonntag, 2. Januar 2005, 22:30

CODE geht wirklich seit geraumer Zeit nicht. Muss ich mir mal in Ruhe anschauen.
Gruss
Thomas

🖖
So long, and thanks for all the fish.


Prof._Dr._YoMan

RCLine User

Wohnort: D-76137 Karlsruhe

Beruf: Hard-/Software Ingenieur

  • Nachricht senden

13

Sonntag, 2. Januar 2005, 22:35

Nicht schlecht. Admin schreien und 9 Minten später ist einer da. Wenn es nur immer und überall so wäre. :)
Meistens haben Platzhirsche eine hohe Beratungsresistenz, dafür eine geringe Wahrnehmungsfähigkeit..... (Claus Eckert)

14

Sonntag, 2. Januar 2005, 22:59

Einrueckungen dauert noch ein bisschen. Vorerst wird code erst mal als courier Schrift dargestellt damit ueberhaupt ein Unterschied zu sehen ist.
Gruss
Thomas

🖖
So long, and thanks for all the fish.


Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

15

Montag, 3. Januar 2005, 10:18

Erst nochmal vielen Dank an alle!

Ich habe jetzt einige Möglichkeiten aufgezeigt bekommen und sehe auch etwas klarer. Da ich nicht auf schnelle Auswertung der eingehenden Impulse angewiesen bin (keine Ruder, nur Gas und Klapptriebwerk) werde ich es wohl erstmal mit einer simplen Zeitmessung an einem normalen Einganpspin versuchen. Die Prozedur müßte nicht allzu schnell hintereinander aufgerufen werden, die zeitkritische Ausgabe der Servoimpulse könnte ich dann dem 16bit Hardwaretimer überlassen. Inwischen habe ich herausgefunden, daß man dem Pascalcompiler auch ganz einfach Assemblercode unterjubeln kann, wenn also Pascal nicht schnell genug sein sollte, schreibe ich diese einzelne Prozedur in Assembler. Wie genau die Auswertung dann ist, wird sich zeigen müssen.
Wenn es klappt, sag ich's.

Matthias

Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

16

Montag, 3. Januar 2005, 21:47

Erster simpel-Versuch hat funktioniert, etwa so:

puls := 0; { Pulslängenzähler }
repeat until KanalImpuls1 = false ; { auf low warten }
repeat until KanalImpuls1 = true ; { auf high warten = Puls Anfang}
repeat
Inc(puls);
until KanalImpuls1 = false ; { auf low warten = Puls Ende}
Return(puls); { Pulslänge angeben }

Dabei liegt der Impuls an einem simplen Eingangspin; Pascal ist schnell genug, um ca. 700 Zählerwerte unterscheiden zu können; allerdings muß man noch einiges an Rauschen und Zählfehler durch Interrupts (die ich wegen der Servoimpulsausgabe nicht unterbinden darf) rausmittlen, bleiben etwa 170 Schritte. Reicht für meinen Zweck allemale, auch die Zeitverzögerungen durch die nur relativ seltene Auswertung des Pulses stört mich nicht.

Allerdings habe ich noch eine Frage:
Sollte ich schaltungstechnisch etwas besonderes beachten beim Anschluß des Eingangspins vom Controller an den Empfängerausgang (Widerstand, Kondensator etc.) ? Mir kommt es insbesondere darauf an, keine Störungen in den Empfänger einzustreuen.

Matthias

17

Montag, 3. Januar 2005, 22:45

Ansich solltest du ohne besondere Beschaltung auskommen.

Ich würde keinerlei Interrupts und Timer benutzen, dann hast du auch keine Störungen bei der Impulserfassung. Den Dreh für die Impuls-Erfassung hast du ja heraus, also schreibe die Impuls-Ausgabe einfach entsprechend genauso, und es läuft perfekt und einfach.

K_Mar

RCLine User

Wohnort: D-76337 Waldbronn-Reichenbach (Karlsruhe) 1988-2005 Seesen/Harz; davor Hannover Modellbau seit 1974

Beruf: Dipl.Ing./Leistungselektr.entw. mW-MW z.Z.Antriebstechn.,früher Stromvers. (incl.Treiber+Messtechn.)

  • Nachricht senden

18

Dienstag, 4. Januar 2005, 09:02

Hallo,
pollen ist bei mir etwas ungeliebt, was haltet Ihr vom Mega 162, der hat zwei 16bit-Timer mit capture und compare. 1xmessen ; 1x ausgeben.
Wenn ich Zeit habe werde ich auch ins Programmieren einsteigen, habe den Mega 8 aber beiseite gelegt und werde den Mega88 und Mega162, je nach Anwendung nehmen, die bieten mehr Möglichkeiten

Gruß Klaus
Fahrzeuge auf dem Wasser bewegen macht Spaß und ist ein optimaler Testbereich für Elektronikentwicklungen

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »K_Mar« (4. Januar 2005, 09:05)


Matthias

RCLine User

  • »Matthias« ist der Autor dieses Themas

Wohnort: Oelde, NRW

Beruf: Medizinphysiker

  • Nachricht senden

19

Dienstag, 4. Januar 2005, 10:08

Ja, wäre wirklich gut, aber ich habe mir nun mal gerade das fertige Mega8 Modul gekauft und wirklich keine Lust, schon wieder was Neues anzufangen.

Matthias

K_Mar

RCLine User

Wohnort: D-76337 Waldbronn-Reichenbach (Karlsruhe) 1988-2005 Seesen/Harz; davor Hannover Modellbau seit 1974

Beruf: Dipl.Ing./Leistungselektr.entw. mW-MW z.Z.Antriebstechn.,früher Stromvers. (incl.Treiber+Messtechn.)

  • Nachricht senden

20

Dienstag, 4. Januar 2005, 10:54

Hallo Matthias,
ich hab eine Leiterplatte 27x28mm (1mmFR4) für einen Mega162 im TSSOP, die ich für Multiprop+-switch - Anwendungen entwickelt habe, vielleicht ist die nützlich.
Laß mir mal ne PN mit Deiner Mail-Adresse zukommen, dann schicke ich Dir den Schaltplan.

Gruß Klaus
Fahrzeuge auf dem Wasser bewegen macht Spaß und ist ein optimaler Testbereich für Elektronikentwicklungen