Hallo! Beim Programmieren eines TI MSP430F169 bin ich auf folgendes Problem gestossen: Ich nütze UART, um den uP mit einem PC über RS232 zu verbinden. Nun geht das ab und zu sehr gut, aber manchmal spinnt es auch, wie z.b. im Moment. Ich sende aus MATLAB zehn 8-Bit-Bytes am Stück, die vom uP aufgenommen werden sollten. Dort existiert eine switch-Anweisung in der Interrupt-Service-Routine, die ein Byte nach dem andern ausliest aus dem RXBUF. Nun steht aber in einigen erhaltenen Bytes (beim 5., 7. und 8.) der Terminator (in meinem Fall 127) drin anstatt der effektive Wert. Irgendwie scheint da ein Timing-Problem vorzuliegen. Da ich einen 4MHz-Quartz benütze, müsste 115200 Baud doch funktionieren. Ich habe das auch so eingestellt über: UBR00 = 0x22; UBR10 = 0x00; UMCTL0 = 0x00; Müsste ich die Modulation noch irgendwie anpassen, da die Division von 4MHz durch 115200 Baud keinen Integer gibt? Ich hab's auch schon mit tieferen Baudraten probiert, was aber nichts nützte. Vielen Dank für die Hilfe, Markus
Also bei 8Mhz und 115,2kBit/s ist auch im Modulator was drinne, ich glaube 0x2C. Deshalb wirst du wohl bei 4MHz auch einen Modulatorwert brauchen.
Danke. Hast du eine Ahnung, welchen Modulator-Wert ich für 4 MHz einstellen müsste? Verstehe diesen Modulator ehrlich gesagt nicht so ganz...
Weiß ich leider nicht. Hab mich damit noch nicht so genau beschäftigt. Bei 8Mhz ist der Teiler ja auch 0x45, also genau die Hälfte geht da schon mal nicht. Da musst du wohl mal versuchen den Algorithmus zu verstehn. Sorry.
Es gibt ja ein JavaScript, der so was kann: http://msp430.info/modules.php?name=Gadgets&op=uart Der gibt folgende Werte aus: UBR00=0x22; UBR10=0x00; UMCTL0=0xDD; /* uart0 4000000Hz 115200bps (115274bps) */
Danke, habe die gegebenen Modulator-Werte aus dem Skript mal eingestellt. Anscheinend hat mein Problem aber nichts damit zu tun, da die Übertragung immer noch Fehler hat. Aber nicht zufällige, sondern reproduzierbare. Es scheinen immer genau die selben Bits falsch übertragen zu werden. Ist komisch. Ich lese ja ein paar Bytes (also Characters) nacheinander aus und bei gewissen Werten dieser Bytes passiert es bei gewissen, dass mein Terminator-Byte 127 statt dem effektiven Wert drin steht. Aber immer bei denselben...
Habe mittlerweile gesehen, dass der auftretende Fehler ein UART overrun error ist, da das OE Flag gesetzt wird. Habe die Baudrate auch mal auf 9k6 runtergeschraubt, aber genau dasselbe. Es scheinen einfach Bytes verschluckt zu werden beim Empfang... Das einzige, das ich im Moment tue in der UART RX ISR, ist, den RXBUF0 auslesen und in ein array abspeichern und dann einen Counter erhöhen. Ich weiss nicht, wie da ein overrun passieren kann. Weniger kann ich ja nicht machen in der ISR wenn ich mehrere Bytes nacheinander empfangen will... oder???
Nein, die Interrupt-Service-Routine wird schon ausgeführt, aber es landen einfach nicht alle Bytes in tTemp. Im Moment besteht sie nur aus einem Auslesen des Buffers: #pragma vector=UART0RX_VECTOR __interrupt void usart0_rx (void) { tTemp[RXCounter] = RXBUF0; RXCounter++; } Aus MATLAB schicke ich die Daten mit fprintf(serobj,packet), wobei packet = ['z' Int Int Int ...] aus characters und Integer-Werten besteht...
Hiho nochmal, weitere Möglichkeit ist noch, dass das Format nicht stimmt (Anzahl Stop-bits, Parity). Ansonsten bitte mal den ganzen Code, falls es möglich ist, bitte zusenden.
Ich habe den Sourcecode angehängt. Habe alle irrelevanten Funktionen etc. ausgehöhlt, damit es ein bisschen übersichtlicher ist. Die verbliebene USART ISR sollte die 12 Bytes von MATLAB erhalten. Stopbits, Databits, Parity sind identisch auf MSP und MATLAB. Könnte es ev. etwas mit dem Terminator Byte zu tun haben? Wie sieht das beim MSP aus? Danke
Hiho, haette da ein paar Vorschlaege: 1. auf ein __disable_interrupt(); sollte auch irgendwann ein enable folgen 2. du musst den RXBUF0 immer leeren, am besten am Anfang der ISR mit z.B. cRxBuf = RXBUF0; und dann mit cRxBuf weiterarbeiten. Es gibt einige Stellen, wo Du den RXBUF0 nicht ausliest z.B. case 11 oder wenn keiner Deiner Vergleich zuschlägt. Dann kommt z.B. ein Buffer overflow. Zieh das mal grade, wenns dann immer noch nicht funktioniert, greife ich mal zum aeussersten, dann denke ich nach :-)
Danke für die Vorschläge. Habe beides gemacht, hat aber leider keinen Unterschied gemacht. Da ich nur 9600 Baud eingestellt habe, kommt es mir wirklich komisch vor, dass da ein Overrun stattfindet. Was ich auch schon probiert habe, war, dass ich den ganzen ISR-Inhalt ersetzt habe durch ein Rausschreiben in ein Array (siehe frühere Beitrag). Und das war ja das Minimale, das ich tun könnte.... Oder gibt es grundsätzlich eine bessere Variante, um mehrere Bytes zu empfangen und aus dem RXBUF0 zu lesen? Wäre DMA nötig?
Oerks, in so einem hartnaeckigem Fall wuerde ich zum Oszi greifen und sowohl die Pattern ueberpruefen, die vom PC geschickt werden als auch im MSP-Programm eine Sequenz einfuehren, wo Zeichen geschickt werden und auch die mit dem Oszi überprüfen. Vielleicht hast Du ja diese Moeglichkeit...
Ich hab den Fehler gefunden! Ich hatte in den zu übermittelnden Daten ab und zu die 10 als Byte drin, was im ASCII Code dem Line Feed entspricht. Offensichtlich interpretiert der MSP dies als Terminator. Das kann man wohl nicht umstellen?? Aber es geht noch weiter :--) Nachdem nun dieses Problem softwaremässig behoben ist, bin ich auf ein Weiteres gestossen: Die 8-Bit-Werte von 128 bis 159 werden falsch im MSP430 empfangen, sie betragen immer 26 oder 63 anstatt des effektiven Wertes. Sämtliche anderen Werte werden absolut fehlerfrei übertragen (1-127, 160-255). Ich habe den 8-Bit-Modus natürlich eingestellt auf dem MSP. Hat da jemand eine Ahnung, was schiefläuft???
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.