Forum: Mikrocontroller und Digitale Elektronik STM32 - 16Bit Integer Wert über UART senden


von M. G. (ixil96)


Lesenswert?

Hallo,

ich arbeite mich gerade mit dem NUCLEO Board L476RG in die STM32 Welt 
ein.

Gibt es eine einfache Möglichkeit mittels HAL Library einen 16Bit 
Integer Wert über die UART zu senden? Oder muss ich diesen Wert in 8Bit 
Werte vorher zerlegen?

von Jim M. (turboj)


Lesenswert?

Was hängt auf der anderen Seite dran?

Bei einem Terminal will man nämlich eher eine der *printf() Funktionen 
benutzen, um den Wert in ASCII zu wandeln.

von gre (Gast)


Lesenswert?

die HAL_Uart erwartet einen pointer

bei 8N1 werden nur 8 bit gesendet
also übergibst du ihm einfach deinen 16mit wert und castest auf 8bit mit 
der länge 2


kurz gesagt:

uint16_t wert;

HAL_UartSend( UART1 , (uint8_t*) &wert , 2 );

MSB/LSB ist architekturabhängig.. also aufpassen.

von Stefan F. (Gast)


Lesenswert?

M. G. schrieb:
> Gibt es eine einfache Möglichkeit mittels HAL Library einen 16Bit
> Integer Wert über die UART zu senden? Oder muss ich diesen Wert in 8Bit
> Werte vorher zerlegen?

Du solltest neben der HAL Doku unbedingt auch mit dem Reference-Manual 
arbeiten 
https://www.st.com/content/ccc/resource/technical/document/reference_manual/3d/6d/5a/66/b4/99/40/d4/DM00031020.pdf/files/DM00031020.pdf/jcr:content/translations/en.DM00031020.pdf

Die UART Schnittstelle kann laut Kapitel 30.2 nur 8 oder 9 Bits 
übertragen, wobei das 9. Bit normalerweise für die Parität verwendet 
wird.

Also: 16bit geht nicht.

von gre (Gast)


Lesenswert?

Jim M. schrieb:
> Was hängt auf der anderen Seite dran?
>
> Bei einem Terminal will man nämlich eher eine der *printf() Funktionen
> benutzen, um den Wert in ASCII zu wandeln.

Dann wäre die fragestellung eine andere gewesen.

von Axel S. (a-za-z0-9)


Lesenswert?

gre schrieb:
> Jim M. schrieb:
>> Was hängt auf der anderen Seite dran?
>>
>> Bei einem Terminal will man nämlich eher eine der *printf() Funktionen
>> benutzen, um den Wert in ASCII zu wandeln.
>
> Dann wäre die fragestellung eine andere gewesen.

Die Fragestellung suggeriert, daß der TE gar keine Ahnung hat. 
Binärdaten per UART verschicken ist eher ungewöhnlich und zu 99% nicht 
das, was er will.

von gre (Gast)


Lesenswert?

gre schrieb:
> uint16_t wert;
>
> HAL_UartSend( UART1 , (uint8_t*) &wert , 2 );

arrays:
uint8_t array[16];
HAL_UartSend( UART1 , array , 16 );


structs
typedef struct{
  uint8_t  a;
  uint32_t b;
  uint8_t  *c
}mystruct_t;

mystruct_t my;
HAL_UartSend( UART1 , (uint8_t*) &my  , sizeof(mystruct) );

von Aufseher (Gast)


Lesenswert?

gre schrieb:
> Dann wäre die fragestellung eine andere gewesen.

Manche Fragesteller sind jedoch so naiv dass sie die Frage
erst gar nicht korrekt stellen können. Daher halte ich die
Nachfrage von turboj für durchaus berechtigt.

Jim M. schrieb:
> Was hängt auf der anderen Seite dran?

von gre (Gast)


Lesenswert?

Axel S. schrieb:
> Die Fragestellung suggeriert, daß der TE gar keine Ahnung hat.
> Binärdaten per UART verschicken ist eher ungewöhnlich und zu 99% nicht
> das, was er will.

das interpretierst du , ok.
KANN sein , muss aber nicht

binärdaten sind nicht so unüblich /( Modbus , zig andere Protokolle )
UART heißst nicht immer konsole.


und wenn er keine ahnung hat, dann sollte er sich dadurch angeregt 
fühlen seine frage richtig zu stellen.

zB:  ich möchte einen 16bit wert über uart senden und auf eine konsole 
am PC anzeigen

von Niklas Gürtler (Gast)


Lesenswert?

Falls es um Binärdaten geht: Serialisierung

von M. G. (ixil96)


Lesenswert?

Ja, meine Fragestellung war nicht ganz korrekt...
Also ich möchte einen 12Bit ADC-Wert einlesen, in eine Temperatur 
umwandeln und per UART an ein Hyperterminal senden.

Das Senden von 2 Bytes des Arrays my_data funktioniert bereits.
Wie aber sende ich die Daten im ASCII Format zb. Temp = 24,8°C?
1
UART_HandleTypeDef huart2;
2
3
uint8_t my_data[2] = {123, 45};  // 12345 aufgeteilt in 2 Bytes
4
5
6
int main(void)
7
{
8
  HAL_Init();
9
  SystemClockConfig();    // optional
10
  UART2_Init();
11
12
  uint8_t my_data_length = 2;
13
14
  while(1)
15
  {
16
    if (HAL_UART_Transmit(&huart2, (uint8_t*)my_data, my_data_length, HAL_MAX_DELAY) != HAL_OK)
17
    {
18
      Error_handler();
19
    }
20
21
    HAL_Delay(1000);
22
  }
23
24
  return 0;
25
}

von Gurgl (Gast)


Lesenswert?

mit sprintf

von OMG (Gast)


Lesenswert?

M. G. schrieb:
> Ja, meine Fragestellung war nicht ganz korrekt...
> Also ich möchte einen 12Bit ADC-Wert einlesen, in eine Temperatur
> umwandeln und per UART an ein Hyperterminal senden.

Ja, deine Fragestellung ist immer noch nicht korrekt. Danach
möchtest du einen ADC-Wert an ein Hyperterminal senden. Was
keinen Sinn macht. Und darf es auch ein Nicht-Hyper-Terminal sein?

In Wirklichkeit möchtest du einen String an ein Terminal
senden ..... und vorher einen ADC Wert in diesen String drucken.

von M. G. (ixil96)


Lesenswert?

OMG schrieb:

> In Wirklichkeit möchtest du einen String an ein Terminal
> senden ..... und vorher einen ADC Wert in diesen String drucken.

Ja genau. Kannst du mir bitte ein Beispiel geben wie ich das am Besten 
mache?

von Stefan F. (Gast)


Lesenswert?

1
   float temp=24.8;
2
   char buffer[20];
3
   int len=(buffer,"Temp = %3.1f°C\n",temp);
4
5
   if (HAL_UART_Transmit(&huart2, (uint8_t*)buffer, len, HAL_MAX_DELAY) != HAL_OK)
6
   {
7
      Error_handler();
8
   }

Eventuell musst du den Linker noch überzeugen, die Unterstützung für 
float zu aktivieren: http://stefanfrings.de/stm32/stm32f1.html#newlib

von OMG (Gast)


Lesenswert?

M. G. schrieb:
> ich arbeite mich gerade mit dem NUCLEO Board L476RG in die STM32 Welt
> ein.

Nach den hier von der Leserschaft gewonnenen Erkenntnissen
ist es wohl angebracht sich erst mal in die Welt der
C-Programmierung einzuarbeiten.

von M. G. (ixil96)


Lesenswert?

Stefanus F. schrieb:
>
1
>    float temp=24.8;
2
>    char buffer[20];
3
>    int len=(buffer,"Temp = %3.1f°C\n",temp);
4
>

Mit float habe ich kein Problem jedoch bekomme ich in der Zeile
1
int len=(buffer,"Temp = %3.1f°C\n",temp);
die Fehlermeldung "error: initializer element is not constant"

von OMG (Gast)


Lesenswert?

Ich sags ja:

OMG schrieb:
> erst mal in die Welt der
> C-Programmierung einzuarbeiten.

probiers mal hiermit (in etwa):
1
void Temperature_Out (int16_t  temperature)
2
{
3
  float  f_temp;
4
  char   tmpstr[30];
5
  uint16_t  my_data_length;
6
7
  f_temp = (float) temperature;  // irgendwas korrekt umrechnen
8
9
  sprintf (tmpstr, " Temp: %5.2f°C (ADC val: %d) \r\n", f_temp, temperature);
10
  my_data_length = strlen (tmpstr);
11
12
  HAL_UART_Transmit(&huart2, (uint8_t*)tmpstr, my_data_length, HAL_MAX_DELAY);
13
14
}

von S. R. (svenska)


Lesenswert?

Stefanus F. schrieb:
> int len=(buffer,"Temp = %3.1f°C\n",temp);

int len=sprintf(buffer, "Temp = %3.1f°C\n", temp);

Das hat der Stefan wohl vergessen.
Außerdem musst du berücksichtigen, dass ° nicht Teil von ASCII ist und 
daher wahrscheinlich falsch angezeigt wird. Im Zweifelsfall ersetzt du 
das durch ein Leerzeichen.

von Klaus S. (skibby)


Lesenswert?

M. G. schrieb:
> Stefanus F. schrieb:
>>
1
>>    float temp=24.8;
2
>>    char buffer[20];
3
>>    int len=(buffer,"Temp = %3.1f°C\n",temp);
4
>>
>
> Mit float habe ich kein Problem jedoch bekomme ich in der Zeile
>
1
> int len=(buffer,"Temp = %3.1f°C\n",temp);
2
>
> die Fehlermeldung "error: initializer element is not constant"


Da fehlt wohl noch das "sprintf " ...

int len=sprintf(buffer,"Temp = %3.1f°C\n",temp);

von Stefan F. (Gast)


Lesenswert?

S. R. schrieb:
> sprintf
> Das hat der Stefan wohl vergessen.

Huch, das ist irgendwie beim copy/pasten verloren gegangen. Sorry.

von M. G. (ixil96)


Lesenswert?

Ich habe das jetzt ausgebessert, bekomme aber in der Zeile
1
int len=sprintf(buffer,"Temp = %3.1f°C\n",temp);
noch immer die Fehlermeldung "error: initializer element is not 
constant"

von Stefan F. (Gast)


Lesenswert?

Kann es sein, dass der wahre Fehler sich in den Zeilen darüber versteckt 
hat?

von Niklas Gürtler (Gast)


Lesenswert?

M. G. schrieb:
> error: initializer element is not constant"

Steht das vielleicht außerhalb einer Funktion?!

von M. G. (ixil96)


Lesenswert?

Niklas Gürtler schrieb:
> M. G. schrieb:
>> error: initializer element is not constant"
>
> Steht das vielleicht außerhalb einer Funktion?!

Ja, Danke!
Es stand in meinem Fall außerhalb von main()...

von U.G. L. (dlchnr)


Lesenswert?

M. G. schrieb:
>
1
> int len=sprintf(buffer,"Temp = %3.1f°C\n",temp);
2
>
> noch immer die Fehlermeldung "error: initializer element is not
> constant"

Einfach die Zeile splitten - der Compiler mag nur kostanten als 
Initializer.
1
int len;
2
sprintf(buffer,"Temp = %3.1f°C\n",temp);

: Bearbeitet durch User
von leo (Gast)


Lesenswert?

U.G. L. schrieb:
> Einfach die Zeile splitten - der Compiler mag nur kostanten als
> Initializer.
> int len;
> sprintf(buffer,"Temp = %3.1f°C\n",temp);

Schwachsinn. Die Lösung steht schon weiter oben.

leo

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.