www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik printf Funktion C167 Problem Leerzeichen


Autor: Richard Wegener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
ich habe ein Problem mit meinem C167 Microcontroller.
Ich möchte die Signale eines Inkrementalgebers auswerten und die
aktuelle Geschwindigkeit bzw. Position 1 mal pro Sek. über die serielle
Schnittstelle an meinen PC senden. Zur Übertragung möchte ich die printf
funktion nutzen doch mit genau dieser habe ich Probleme. Noch bevor die
Messung und auswertung gestartet wird, also auch vor der while Schleife
in der main Funktion, soll eine Information an das Hyper terminal
gesendet "Inkrementalmessung wird gestartet".
Diese Info wird nie an das terminal gesendet. Es werden fast nur
Leerzeichen versendet und diese Übertragung der Leerzeichen wird nicht
beendet. Also die printf Funktion wird erst gar nicht abgearbeitet bzw
nicht beendet.
Kann mir da vielleicht jemand weiter helfen? Liegt es an den
Einstellungen die ich bei dem Controller machen muss? Die Beispiel
Programme von Phytec kann ich nämlich alle ausführen auch die mit einer
printf funktion.
Gruß
Richard

Autor: Profi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
am besten erlaubst Du uns einen Blick in Deinen Code.
Stimmt die Baudrate?
Kommen wirkleich Spaces (0x20) an oder sind es andere nicht
darstellbare Zeichen?

Autor: Richard Wegener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hier eine vereinfachte version die ich vorab zum laufen bringen möchte.
Wenn ich nur die printf Funktion auskommentiere funktioniert alles.
Greetz


#include <reg167.h>             /* include 80C167 header file*/
#include <stdio.h>

sbit P2_0 = P2^0;               /* declare portpin to use*/
sbit DP2_0 = DP2^0;             /* declare direction bit to use*/
void wait(unsigned int);
void initwait(void);
void initdisplay(void);

void wait (unsigned int ms)     /* wait function */
{
  T3 = 0;
  T3R = 1;
  while(T3<(ms * 480));
}

void initwait(void)
{
  T3CON = 0x007;
  //T3 = 0;
}

void initdisplay(void)
{
  IEN = 0;
  //#ifndef MCB167
  P3  |= 0x0400;
  DP3 |= 0x0400;

  DP3 &= 0xF7FF;

  S0TIC = 0x80;
  S0RIC = 0x00;

  S0BG  = 0x81;         // set baudrate to 9600 baud at 40Mhz
  S0CON = 0x8011;       // set serial mode
    //#endif
    IEN =1;
}

void main (void)
{
  initdisplay();
  initwait();
    DP2_0 = 1;           /* init direction to output */
  P2_0 = 1;
    printf ("\aHello World\n"); /* print 'Hello World' to the
serial*/

  while (1)           /* loop forever */
    {
    wait(150);
    P2_0 = 0;
    wait(150);
    P2_0 = 1;
    }
}

Autor: zverjatko (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Richard,

du mußt noch den Sendebuffer freigeben, wenn du ohne Interrupt
arbeitest.

S0TIR=1;

Gruß
zverjatko

Autor: (geloescht) (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
(Dieser Beitrag wurde geloescht)

Autor: zverjatko (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Nein für C167 gib es nicht freies,
Eval. Version von Keil (www.Keil.com) (limit 8KByte)
oder Compiler von Tasking, vermutlich ähnliche begrenzung.
Gruß
Zverjatko

Autor: (geloescht) (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
(Dieser Beitrag wurde geloescht)

Autor: Robert Teufel (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Guido,

den GNU compiler fuer den 16x gabs mal von
http://www.hightec-rt.com/

Robert

Autor: Steffen (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Guido,

bei PLS war auch immer ein GNU C Compiler für den 16x dabei.
http://www.pls-mc.com/howdoesitwork/index.htm?a_ar...

Autor: Take it Easy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

printf ist eine Funktion, die auf (eine) Grundfunktion(en)
zurückgreift. Je nach Compiler muss eine Funktion z.B. iowrite() erst
definiert werden. Hier wird dann der Output Stream festgelegt.

Woher soll printf denn wissen, wohin die Daten ausgegeben werden sollen
(z.B. RS232, LCD-Display1, LCD-Display2, CAN,...)?

Autor: Richard Wegener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
leider haben Eure Tipps noch nicht geholfen.
@zverjatko
habe S0TIR = 1; eingefügt, leider keine veränderung.

@Take it Easy
Ich kann deinen Hinweis wohl nachvollziehen, aber in den beispielen von
Phytec ist die printf() funktion auch nicht anders konfiguriert worden.

Hat vielleicht noch jemand eine idee ?

Greetz Richard

Autor: zverjatko (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Programmierst du mit Keil ?
Wenn ja, hast du schon mit dem µVision das Programm simuliert ?
Du schreibst:  // set baudrate to 9600 baud at 40Mhz
Der alte C167 so weit ich weiß läuft maximal bis 24Mhz.
Gruß

Autor: Richard Wegener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also ich arbeite mit Keil µVision3 (eval. Vers.).
Wie schon erwähnt kann ich die Beispiel Programme von Phytec auch
compilieren und auf meinem C167 laufen lassen.
hat vielleicht noch jemand eine idee woran es liegen kann ?

Hier habe ich mal das Programm das läuft:
Mein c167HSE hat einen Takt von 40MHz.

#include <REG167.H>         /* Register Set of 80C167 controller   */
#include <stdio.h>          /* Standard I/O functions              */

/* main program  */
void main (void)          /* execution starts here      */
{
                          /* init serial0 port:         */
  P3  |= 0x0400;          /* set port 3.10 output latch (TXD)*/
  DP3 |= 0x0400;          /* configure port 3.10 for output   */
                          /* operation. ( TXD output)         */
  DP3 &= 0xF7FF;          /* configure port 3.11 for input    */
                          /* operation. ( RXD input)          */
  S0TIC = 0x80;           /* set transmit interrupt flag      */
  S0RIC = 0x00;           /* delete receive interrupt flag    */

/*  PLEASE CHECK YOUR phyCORE-167-HS/E Quarz frequency and choose the
right   */
/* reload value to set the baudrate to 9600 Baud  */
//S0BG  = 0x40;         /* set baudrate to 9600 baud at 20Mhz  */
//S0BG  = 0x50;         /* set baudrate to 9600 baud at 25Mhz  */
//S0BG  = 0x6A;         /* set baudrate to 9600 baud at 33Mhz  */
  S0BG  = 0x80;         /* set baudrate to 9600 baud at 40Mhz  */
  S0CON = 0x8011;       /* set serial mode                     */

  putchar(' ');         /* send dummy-Byte for compatibility   */
  printf ("\aHello World\n");   /*print 'Hello World' to the
serial port.*/
  while (1)             /* An embedded program without any     */
  {                     /* operating system usually does not   */
                        /* stop and never returns.             */
                        /* We've used an endless loop in
                           this example.                       */
  printf ("  char = %02bX\n",getchar()); /* print the two digit hex
              code of   */                             /* any received
character              */
  }
}

Autor: Take it Easy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Falsche Baudrate:
--> Keil      S0BG = 0x80;
--> Dein Code S0BG = 0x81;  // Abweichung ein paar Prozent!

Autor: zverjatko (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also ich habe dein Programm jetzt im µVision3 Simuliert und
es fehlte   S0TIR=1.
Das Programm funktioniert.

void main (void)          /* execution starts here      */
{
                          /* init serial0 port:         */
  P3  |= 0x0400;          /* set port 3.10 output latch (TXD)*/
  DP3 |= 0x0400;          /* configure port 3.10 for output   */
                          /* operation. ( TXD output)         */
  DP3 &= 0xF7FF;          /* configure port 3.11 for input    */
                          /* operation. ( RXD input)          */
  S0TIC = 0x80;           /* set transmit interrupt flag      */
  S0RIC = 0x00;           /* delete receive interrupt flag    */
  S0TIR=1;
  S0BG  = 0x81;         /* set baudrate to 9600 baud at 40Mhz  */
  S0CON = 0x8011;       /* set serial mode
 ....

die reale Baudrate beträgt 9615 (+0,15%) d.h jetzt muss es
funktionieren, falls es doch nicht geht,dann hast du ein Hardware
Problemm.
Beim Phytec gibt es aber nur phyCORE-ST10F168/269/276 HS/E  und kein
C167HSE, die schnellsten alten C167 sind mit 25MHz.
Dieses Programm habe ich auch anschliesend  mit einem ST10F269
simuliert.Es funktioniert ebenfalls.


Gruß
zverjatko

Autor: Richard Wegener (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Vielen dank allen denen die mir hier geholfen haben.
Ich habe gestern noch einmal versucht das beispiel programm von Phytec
zu starten und es hatte genau den selbigen Fehler wie das von mir
erstellte Programm !! Daraufhin habe ich alle Programme von Phytec und
Keil gelöscht, neu aufgespielt und anschließend mein Programm wieder
neu und sauber programmiert (incl. S0TIR=1;) !!! und siehe da alles
funzt.
Ich denke das einfach im laufe der Zeit und der unzähligen Versuche von
mir einige Einstellungen so verändert wurden das es einfach nicht mehr
funktionieren konnte. Also nochmal vielen dank für die unterstützung.

Gruß
Richard

Autor: Stefan Neubert (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,
ich beschäftige mich zur Zeit auch mit dem printf Befehl und dem C167 
Controller.
Ich möchte ein Gyroskop steuern und habe auch soweit mit dem Keil 
Compiler einen Quellcode erstellt.
Das Gyroskop gibt einen binären Datenstrom aus, den ich via einem 
Hyperterminal anzeigen möchte. Mit dem Oszilloskop sieht man, dass das 
Gyroskop vom Prinzip her funktioniert und Daten ausgibt.
 Wenn ich mit integer Werten Berechnungen mache, werden diese Variablen 
wunderbar angezeigt. Am Programmcode habe ich mich am Beispiel "Hello 
World" orientiert und möchte eigentlich nur einen Zustand eines Pins mit 
printf anzeigen lassen.
Den Datenstrom des Gyroskop kann man sehr schön sehen, aber leider kann 
ich mit dem printf Befehl nur Nullen ausgeben.

Stefan

Autor: Thomas M. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo!

Ich habe das selbe Problem, allerdings, nach vielen Versuchen und mit 
Hilfe dieses Threads -> noch immer!!!!

Meine Programm laufen zwar im Monitor (Programmiere mit Keil) 
einwandfrei, allerdings im Flash wird nur noch das erste Zeichen normal 
geschickt, dann kommen nur noch Leerzeichen (0x20).

Kann jemand irgend ein kleines funktionierendes Testprojekt zur 
Verfügung stellen? Ich komme z.Zt. echt nicht weiter!

Danke.

Autor: Robert (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo!

Mein Problem ist derzeit noch das einlesen. Ich möchte den Hex-Wert 
einer gedrückten Taste auf der Tastatur über das Hyperterminal einlesen 
und diesen dann im c167 verwerten.

Wie lese ich ich den Wert in S0TIR ein bzw. greife wieder darauf zu um 
ihn auszugeben?

Sorry meine banale Frage aber bin erst Anfänger mit im µC-programmieren.

gtx, Robert



Autor: Thomas M. (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Naja passt zwar nicht unbedingt zum Thema aber egal.

Also erstens geht es nicht um das S0TIR-Register, weil es 1. kein 
InterruptRequest sein soll sondern der Wert aus dem Buffer und zweitens 
geht es hierbei nicht um den Transmitter sondern um den Receiver.

Das Register, welches du auslesen musst ist das S0RBUF. Dies machst du 
am Besten in einer Methode die vom interrupt 43 (0x2B in hex, der 
ReceiverInterrupt) verwendet wird.
Zum Beispiel:
void isr_serial_receive() interrupt 43
{
unsigned char c = S0RBUF;       // Empfangspuffer lesen
....
}


Diesen Interrupt musst du nur noch enablen. Dies schaut bei mir so aus:
S0RIC = 0x56;
und dann dürft eigentlich gar nichts mehr schief gehen (wenn du die 
Serielle schon initialisiert hast).

Was allerdings meist ein Problem ist:
Wenn du einen Monitor verwendest, dann verwendet meist der Monitor 
(zumindest bei mir war es so, ich habe einen Keil-Monitor) diese 
Interrupt-Routine und überschreibt dir quasi deinen Interruptvektor. 
Läuft das Programm von Rom oder Flash läuft es auch so einwandfrei, für 
den Monitor musste ich noch einiges hinzufügen:
unsigned short *p = 0xAC;    // Pointer auf 16 bit Wort
*p = 0x00FA;      // JMPS bits 16 - 23 der Sprungadresse werden hier 0 gesetzt !!!
p++;          // nächstes Wort
*p = (unsigned short)&isr_serial_receive;  //Vector der ISR auf Adresse schreiben

Autor: Moccamixer (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo - ich hatte gestern abend das gleiche problem mit meinem c167:

jedes printf sendet den ersten buchstaben und daraufhin nur noch 0x20 an 
das terminal über die serielle schnittstelle. ich habe neu installiert, 
unterschiedlichste beispielprogramme der evaluation software probiert - 
überall das gleiche problem. Andere Dinge schienen zu funktionieren 
(Blinky etc...) lediglich printf() bereitete die erwähnten probleme.

ich konnte es jedoch wie folgt lösen (mache das alles hier erst seit ein 
paar tagen - den grund konnte ich nicht wirklich ermitteln, aber eine 
lösung - zumindest für mich):

demo software unter http://www.phytec.com/zip/ runterladen - bei mir war 
es http://www.phytec.com/zip/Demos_PCM-009_K.zip (s. Anhang des 
Beitrags). dieses Paket enthält ebenfalls ein Hello World - und zwar 
eins das mit dem C167 CR-LM funktioniert. ich nehme diese demo als 
ausgangsprojekt und füge meinen code hinzu. ich denke es liegt entweder 
an der start167.a66 oder an der projektkonfiguration selbst. wobei ich 
bei letzteren unterschiede finden konnte (Options -> L166 Locate im Feld 
Target Classes und im Feld Linker Control String) jedoch, weiß ich nicht 
wo man diese Werte selbst anpassen kann... Wäre aber interessant, wenn 
mir das jemand sagen könnte, dann brauche ich nicht immer ein kopiertes 
ausgangsprojekt, sondern könnte die einstellungen selbst vornehmen. ich 
bin da wirklich ganz unerfahren und kein c profi, aber ich vermute mal, 
dass da irgendwas falsch gelinkt wird, wenn diese einstellungen nicht 
angepasst werden. ich war hartnäckig, hier ist meine lösung - ich hoffe 
sie hilft einigen.

grüße,

mocca

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.