Code übersetzen - C --> BASCOM

Gast #2089890
Lesenswert?

Hallo alle,

ich probiere gerade einen Code von C in BASCOM zu übersetzen. Der Code 
ist fürs Charlieplexing. Originalquelle hier: 
http://www.dgoersch.info/codesammlung/avr-gcc/50-charlieplexing
Mein Problem ist nun die einzelne Steps. Wie übersetze ich das in 
BASCOM. Mein bisheriger Code sieht so aus:
1
$regfile = "attiny2313.dat"
2
$hwstack = 32
3
$swstack = 32
4
$crystal = 8000000
5

6
Dim Chstep As Byte
7
Dim Temp As Byte
8

9
Config Timer0 = Timer , Prescale = 1024
10
On Timer0 Timerisr
11

12
Enable Timer0
13
Enable Interrupts
14

15

16
Do
17

18

19

20
Loop
21

22
Timerisr:
23
   Temp = Bits(chstep)
24

25
   If Chstep = 0 Then
26

27
      
28
   Elseif Chstep = 1 Then
29

30
     
31
   Elseif Chstep = 2 Then
32

33

34
   Elseif Chstep = 3 Then
35

36
      
37
   Elseif Chstep = 4 Then
38

39
    
40
   End If
41
   Ddrb = Temp : Portb = Bits(chstep)
42
   If Chstep = 5 Then
43
      Chstep = 0
44
   Else
45
      Chstep = Chstep + 1
46
   End If
47
Return
48

49
End

Wäre nett, wenn mir jmd. helfen könnte
Gast #2089920
Lesenswert?

Textersetzung reicht

C        BASCOM
0x00001  &H1
0x00004  &H4
0x00010  &H10
0x00040  &H40


1<<0     &B1
1<<1     &B10
1<<2     &B100
1<<3     &B1000
            ^ achte mal auf die Zahl der Nullen
Bzw. ist es noch einfacher, wenn BITS() benutzt werden kann
Gast #2090009
Lesenswert?

Bekomm leider mehrere Errors:
1
error : 35  Line : 28  3 parameters expected , in File : C:\charlieplexing.bas
2

3
error : 35  Line : 28  3 parameters expected , in File : C:\charlieplexing.bas
4

5
error : 28  Line : 28  IF THEN expected , in File : C:\charlieplexing.bas
6

7
error : 35  Line : 28  3 parameters expected , in File : C:\charlieplexing.bas
8

9
error : 350  Line : 0 Interrupt needs return , in File:

Hier mein Code:
1
$regfile = "attiny2313.dat"
2
$hwstack = 32
3
$swstack = 32
4
$crystal = 8000000
5

6
Dim Chstep As Byte
7
Dim Temp As Byte
8
Dim Lights As Byte
9

10
Config Timer0 = Timer , Prescale = 1024
11
On Timer0 Timerisr
12

13
Enable Timer0
14
Enable Interrupts
15

16
Lights = &B11111
17

18
Do
19

20

21

22
Loop
23

24
Timerisr:
25
   Temp = Bits(chstep)                                      ' in step x pbx as output
26

27
   If Chstep = 0 Then
28
      If Lights And &H1 Then Tmp = Tmp Or Bits(1) End If
29

30
   Elseif Chstep = 1 Then
31

32

33
   Elseif Chstep = 2 Then
34

35

36
   Elseif Chstep = 3 Then
37

38

39
   Elseif Chstep = 4 Then
40

41

42
   End If
43
   Ddrb = Temp : Portb = Bits(chstep)                       ' temp to ddrb ; pbx (step) high
44
   If Chstep = 5 Then
45
      Chstep = 0                                            ' back to 1st step after 5
46
   Else
47
      Chstep = Chstep + 1                                   ' next step
48
   End If
49
Return
50

51
End
Gast #2090079
Lesenswert?

Du kannst jetzt jeden einzelnen Befehl nach Bascom übersetzen. Z.B.
If lights.0 = 1 Then Tmp.1 = 1
entspricht deiner Abfrage.
Allerdings wird das ziemlich ineffizient. Und Charlieplexing riecht per 
se zunächst mal zeitkritisch.
Daher wäre es besser, den Sinn zu verstehen und dann in Bascom neu zu 
schreiben.

lights ist ein Long Typ in Bascom (uint32_t in C). Wenn du da jedesmal 
Operationen auf Long machst, nur um ein Bit abzufragen, dauert das sehr 
lange.
Alternativ kannst du 4 Byte Variable per Overlay drüberlegen und diese 
dann manipulieren. Geht wesentlich schneller.
Gast #2090175
Lesenswert?

-.- schrieb:
> ich probiere gerade einen Code von C in BASCOM zu übersetzen. Der Code
> ist fürs Charlieplexing. Originalquelle hier:
> http://www.dgoersch.info/codesammlung/avr-gcc/50-c...

Ist Dir eigentlich bei dem verlinkten "Programmwerk" aufgefallen, daß 
die Verwendung des Output Compare Int völlig sinnfrei ist ? Wär' genauso 
ein Ovfl Int gegangen.

Zur Übersetzung, der Code kommt mit <= 240 Takten aus, ginge also auch 
noch bei Prescale = 1. Allerdings scheint mir die Charlyplexingfrequenz 
bei 8MHz Takt unnötig hoch, da könnte man also einen Prescale von 8 oder 
16 nehmen und es wär' immer noch ok.
1
tmp1 = 0
2
tmp1.steps = 1
3
tmp = tmp1
4
Select Case steps
5
   Case 0:
6
      tmp.1 = lights.0
7
      tmp.2 = lights.2
8
      tmp.3 = lights.4
9
      tmp.4 = lights.6
10
   Case 1:
11
      tmp.0 = lights.1
12
      tmp.2 = lights.8
13
      tmp.3 = lights.10
14
      tmp.4 = lights.12
15
   Case 2:
16
' usw.
17
End Select
18
  DDRB = tmp
19
  PORTB = tmp1
20
    If steps = 4 Then
21
      steps = 0
22
    Else
23
      Incr steps
24
    End If
Gast #2092370
Lesenswert?

Na klar habe ich Ideen, nur wenn weder Danke für das Fetzerl Code noch 
sonstwas kommt, vergess' ich die alle. Außerdem reagier' ich nicht auf 
jmd., niemand, keiner usw.

Geb' Dir aber trotzdem 'nen Tip: Nimm den wissenschaftlichen Windows 
Taschenrechner, schalt' auf Hex-Eingabe, gibt die Konstante hinter
If (lights &
ein und konvertier's in Binär.
Mal schauen, ob's dann heller wird...
Gast #2092384
Lesenswert?

Die Variable.Zahl Schreibweise ist wohl eine nützliche Spracherweiterung 
in BASCOM (Beitrag "Bascom Bit und Byte")

Die Doku dazu finde ich in dem BASCOM Manual auf die Schnelle nicht. Mal 
selber suchen.

Auf die Zahlen kommt man einfach, wenn man das Binärsystem und das 
Hexadezimalsystem für die Zahlendarstellung kennt. Beides müsste in 
wikipedia ausführlich erklärt sein, deshalb hier kurz:

>>> if (lights & 0x00001) tmp |= (1<<1);
>> tmp.1 = lights.0

Hexadezimal 0x00001 ist Binär 0b01, d.h. 0. Bit gesetzt. lights.0 ist 
das 0. Bit von lights.

(1<<1) ist 1 (Binär: 0b01) um eine Stelle nach links geshiftet also 
0b010, d.h. 1. Bit gesetzt. tmp.1 ist das 1. Bit von tmp.

MWS benutzt jetzt einen "Trick": statt bei der Zuweisung in tmp den Wert 
(1<<1) zu benutzen, verwendet er den bekannten Wert aus lights.

Damit spart er sich die if Abfrage für lights und kann die 
Bitmanipulation schön elegant in dem case Fall unterbringen.
Gast #2092394
Lesenswert?

Gut, dann bedank ich mich erstmal für den Code. Funktioniert alles, bis 
auf das, dass die anderen Zahlen fehlen.

Zu dem Tipp:
Komisch, wenn ich den ersten Step in Dezimal umrechne, dann komme ich 
auf 1,4,16,64. Du hast jedoch in deinem Code 0,2,4,6. Wie kommst du da 
drauf. Hab ich irgenwas falsch gemacht. Oder muss ich da die Anzahl der 
Nullen in Binär hinschreiben?
Gast #2092404
Lesenswert?

> Oder muss ich da die Anzahl der Nullen in Binär hinschreiben?

Das wird dir helfen. Dann siehst du an welcher Position die einzelne 1 
steht. Und das ist dann genau die .Zahl

Beim abzählen der Position beachten, dass von rechts nach links 
beginnend mit 0 gezählt wird. 00100000 ist Bitposition 5

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren