Forum: Mikrocontroller und Digitale Elektronik Quelltext von C nach Mikrobasic umwandeln -> Brauche Hilfe


von Tid (Gast)


Lesenswert?

Hallo Leute,

Habe ein Problem. Ich will mit einem PIC ein OPEL TID Display ansteuern.
Das Interface ist ein abgewandelter I2C Bus.
Das größte Problem ist, das ich einen Quellcode gefunden habe, welchen 
ich annähernd lesen kann.
Aber eben nur annähernd.
C kann ich gar nicht.
Das Programm soll aber mal auf Mikrobasic basierend sein.
Eine komplett neue Sprache zu lernen fällt flach, wegen Zeitmangel.

Ich habe folgenden Code in C:
1
uint8_t tid_send_byte(uint8_t byte)
2
{
3
  // assuming SDA and SCL low
4
  uint8_t mask = (1 << 6); // MSB first
5
  uint8_t ack; // TID ack value
6
  for(; mask != 0x00; mask = (mask >> 1)) // shift towards LSB
7
  {
8
    if(mask & byte)
9
      TID_SDA_1();
10
    else
11
      TID_SDA_0();
12
    delay_us(45);
13
    TID_SCL_1();
14
    loop_until_bit_is_set(TID_PIN,TID_SCL); // IMPORTANT!
15
    delay_us(50);
16
    TID_SCL_0();
17
    delay_us(5); // Th
18
  }
19
  if(!parity_even_bit(byte & 0x7F)) // odd partition
20
    TID_SDA_1();
21
  else
22
    TID_SDA_0();
23
  delay_us(45);
24
  TID_SCL_1();
25
  loop_until_bit_is_set(TID_PIN,TID_SCL); // IMPORTANT!
26
  delay_us(50);
27
  TID_SCL_0();
28
  TID_SDA_1(); // we will read ack
29
  delay_us(50);
30
  TID_SCL_1();
31
  loop_until_bit_is_set(TID_PIN,TID_SCL); // IMPORTANT!
32
  // read ack byte, 0 means acknowledged - data OK
33
  if(bit_is_set(TID_PIN,TID_SDA))
34
  {
35
    ack = 1;
36
  }
37
  else
38
  {
39
    ack = 0;
40
  }
41
  delay_us(50);
42
  TID_SCL_0();
43
  delay_us(50);
44
  TID_SDA_0();
45
  delay_us(50);
46
  return ack; // 0 == ok
47
}

Nun möchte ich ihn in Mikrobasic umwandeln:
1
 
2
Sub function tid_send_byte(byval ByteToSend as byte) as byte 'Gibt Ack zurück
3
    ' assuming SDA and SCL low
4
    dim i as integer 'Zählervariable
5
    
6
    for i = 0 to 6
7
        if ByteToSend.i = 1 then
8
           TID_SDA_1()
9
        else
10
            TID_SDA_0()
11
        end if
12
        delay_us(45)
13
        TID_SCL_1()
14
        do
15
          NOP
16
        loop until TID_SCL = 1
17
        delay_us(50)
18
        TID_SCL_0()
19
        delay_us(5)
20
    next i
21
    if TestParityBit(ByteToSend) = 0
22
       TID_SDA_0()
23
    else
24
        TID_SDA_1()
25
    end if
26
    delay_us(45)
27
    TID_SCL_1()
28
    Do
29
      NOP
30
    Loop until TID_SCL = 1
31
    delay_us(50)
32
    TID_SCL_0()
33
    TID_SDA_1()  ' we will read ack
34
    delay_us(50)
35
    TID_SCL_1()
36
    do
37
      NOP
38
    loop until TID_SCL = 1
39
    ' read ack byte, 0 means acknowledged - data OK
40
    if TID_SDA = 1 then
41
       tid_send_byte = 1
42
    else
43
        tid_send_byte = 0
44
    end if
45
    delay_us(50)
46
    TID_SCL_0()
47
    delay_us(50)
48
    TID_SDA_0()
49
    delay_us(50)
50
End sub

Wo liegt mein Problem:
Ich kapieren nicht die Schleife in C nicht.
läuft die von 0 bis 6 , von 1 bis 7 ????

Habe ich diese richtig umgesetzt?

Wie funktioniert das Schieben?

Habe ich das Schieben in meiner Schleife richtig nachgestellt?

Über die Performance des Quelltextes soll hier nicht gestritten werden. 
Genausowenig über die Sinnhaftigkeit von Basic.

Würde mich über eine Erklärung freuen.

mfG

von Oliver (Gast)


Lesenswert?

Tid schrieb:
> Eine komplett neue Sprache zu lernen fällt flach, wegen Zeitmangel.

Es dürfte ausreichen, nur das nachzuschlagen, was in dem Quelltext oben 
benutzt wurde. So viel ist das ja nicht.

Das hier sollte neben google dabei helfen:
http://openbook.galileocomputing.de/c_von_a_bis_z/


Die Schleife
>uint8_t mask = (1 << 6); // MSB first
>for(; mask != 0x00; mask = (mask >> 1))

startet mit mask = 01000000, und schiebt in jedem Umlauf die 1 eins nach 
rechts. Wenn mask dann gleich 0 ist, bricht die Schleife ab. Einen 
Durchlauf mit 0 gibt es dabei nicht mehr.

Oliver

von Karl H. (kbuchegg)


Lesenswert?

for SChleifen in C


   for( Initialisierung;  Bedingung;  Aktion bei jedem Durchlauf )


Initialisierung: Also der Teil, der nur einmal ausgeführt wird, ehe die 
Schleife überhaupt beginnt

Bedingung: die Bedingung muss erfüllt sein, damit der Schleifenkörper 
betreten wird

Aktion: Diese Aktion wird am Ende des Schleifenkörpers ausgeführt, noch 
ehe as an den Anfang zurückgeht und die Bedingung erneut geprüft wird.


   for( Init; Bedingung; Aktion )
      ....

ist also gleichwertig zu


   Init
   while( Bedingung ) {
      .....
      Aktion
   }


Jeder der 3 Teile kann fehlen, lediglich die Strichpunkte bleiben dann 
als die Trenner erhalten. Fehlt der Init Teil, dann sieht das dann eben 
so aus

    for( ; Bedingung; Aktion )

fehlt die Bedingung, dann eben so

    for( Init; ; Aktion )

fehlt Init und Aktion, dann eben so

    for( ; Bedingung; )

bzw. dann sinngemäss für alle anderen Kombinationen

von Karl H. (kbuchegg)


Lesenswert?

Tid schrieb:

> Habe ich das Schieben in meiner Schleife richtig nachgestellt?

ich würde sagen nein.
Du behandelst du Bits genau verkehrt rum.

Das original behandelt die Bits
    6, 5, 4, 3, 2, 1, 0
dein Code behandelt die Bits
    0, 1, 2, 3, 4, 5, 6

und zwar jeweils genau in dieser Reihenfolge. Ergo: Deine Bits sind 
genau gespiegelt ausgegeben.

von Tid (Gast)


Lesenswert?

Also muss es in diese Reihe:
1
for i = 6 to 0 step -1
2
        if ByteToSend.i = 1 then
3
           TID_SDA_1()
4
        else
5
            TID_SDA_0()
6
        end if
7
        delay_us(45)
8
        TID_SCL_1()
9
        do
10
          NOP
11
        loop until TID_SCL = 1
12
        delay_us(50)
13
        TID_SCL_0()
14
        delay_us(5)
15
next i

von Durtl (Gast)


Lesenswert?

Glaube nicht das das stimmt.
Deine MASK fehlt.

von Karl H. (kbuchegg)


Lesenswert?

Durtl schrieb:
> Glaube nicht das das stimmt.
> Deine MASK fehlt.

Das macht nichts.
Funktional sind die beiden Versionen identisch. Also in dem Sinne, dass 
sie das gleiche machen.
Die C Version benutzt eine Maske um ein Bit nach dem anderen 
freizustellen und entsprechend den Ausgang zu schalten und im Basic 
Programm macht das eben das Zusammenspiel aus i und ByteToSend.i

D.h. der Effekt müsste der gleiche sein.

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.