Hypercell ein ] Hypercell aus ] Zeige Navigation ] Verstecke Navigation ]
c++.net  
   

Die mobilen Seiten von c++.net:
https://m.c-plusplus.net

  
C++ Forum :: Assembler ::  bedingtes Assemblieren in einem Makro - wie erkenne ich ein Register?     Zeige alle Beiträge auf einer Seite Auf Beitrag antworten
Autor Nachricht
posti
Unregistrierter




Beitrag posti Unregistrierter 23:53:41 01.12.2016   Titel:   bedingtes Assemblieren in einem Makro - wie erkenne ich ein Register?            Zitieren

Hi

Habe gerade mit AVR-Assembler begonnen, genauer mit einem ATtiny45.
Das Ansprechen eines 8x7Segment-Display (MAX7219 Platine, eBay) klappt auch schon befriedigend.

Nun wollte ich die Routinen für die Ansteuerung des MAX7219 in ein Include-File packen, damit ich Diese einfacher benutzen kann.

Hier fiel mir auf, daß z.B. die Routine:
Code:
1
2
3
4
5
6
7
8
9
10
;Anzeigestellen ändern
.MACRO MAX7219_ScanLimit    ;(i, 0...7// i=immediate = Zahl wird übergeben, @1=Wert)
    ldi MAX7219BEFEHL,@1
.if @0=="i"
   ldi MAX7219Wert,@0           ;wird eine Zahl (kein Register) übergeben, muß das i als erster Parameter angegeben werde
.else
    mov MAX7219Wert,@0          ;wenn ein Register übergeben wurde, dann per mov den ersten Parameter laden
.endif
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO

MAX7219WERT und MAX7219BEFEHL sind definiert sowie die Ausgaberoutine MAX7219_SENDEN ist vorhanden (die Werte werden bitweise MSB...LSB ausgetaktet und dann übernommen)

So aufgerufen:
Code:
MAX7219_ScanLimit   (7) ;(klappt)
MAX7219_ScanLimit ("i", r16) ;(klappt überhaupt nicht)

Ohne den if-Block und ohne das mov klappt die Zahlenübergabe, zum Initiieren wunderbar.
Wenn ich aber den Rest wieder rein bringe, da ich z.B. einige der Stellen im Programm ausschalten will - wofür sich ein Register ganz gut macht - meckert der Kollege Assembler, daß ich einen unerwarteten String im Aufruf habe.

Meine Frage an Euch deshalb:
Wie kann ich überprüfen, ob ein Parameter ein Register oder eine Zahl ist?
Oder: Wie macht Ihr so was?

MfG
posti

PS: fand dieses Forum via Google bei der Suche nach Assembler und AVR, hoffe, Das passt trotz des Namen C++ halbwegs hier her.
posti
Unregistrierter




Beitrag posti Unregistrierter 13:11:18 11.12.2016   Titel:   Nur indirekt eine Lösung, aber klappt. Include zum Download enthalten            Zitieren

Hi

Scheinbar ein doch nicht so einfaches Problem :)

Da es sich um Makros handelt und Diese eh nur bei Nutzung eingebaut werden, habe ich für beide Fälle eigene Makros erstellt.

Wie ich einen übergebenen Wert auf ASCII überprüfen kann, ist mir somit immer noch nicht bekannt, geht aber auch so.

Danke für's Lesen

Code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
;*************************************
;** Routiene dient dem einfachen
;** (und fehlerfreiem) Ansprechen
;** der 8x7Seg-Anzeige MAX7219
;** by posti NOV 2016
;*************************************
;** Einbinden nur per INCLUDE **
;*******************************
;** r16 = Wert      =   7219Wert
;** r17 = Befehl    =   7219Befehl
;** werden zerstört
;*************************************
.EQU PUSHALL=1      ;wenn beim SENDEN die Register NICHT gesichert werden sollen, auskommentieren
 
;30.11.16   Routinen funktioniert und lassen sich per INCLUDE einbinden (hinter .ORG 0 !!)
 
;-----Register-----
;
;r00...r15
;r16...r25
.MESSAGE "**** Register R16 und R17 werden zerstört ****"
.def    MAX7219Wert     =   r16
.def    MAX7219Befehl   =   r17
;r26_r27    X
;r28_r29    Y
;r39_r31    Z
;
;-----Ports, Portbits-----
;Pins für das Display am MAX7219
.equ    pClockD =   DDRB    ;Richtungsport des Clock-Signal
.equ    bClockD =   DDB0    ;Bit der Richtung des Clock-Signal
.equ    pClock  =   PortB   ;Port des Clock-Signal
.equ    bClock  =   PortB0  ;Bit des Port
 
.equ    pOutD   =   DDRB    ;Richtungsport
.equ    bOutD   =   DDB1
.equ    pOut    =   PortB   ;Port des Daten-Signal
.equ    bOut    =   PortB1  ;Bit des Port
 
.equ    pCSD    =   DDRB    ;Richtungsport
.equ    bCSD    =   DDB2
.equ    pCS     =   PortB   ;Port des CS-Signal (Datenübernahme)
.equ    bCS     =   PortB2  ;Bit des Port
;
;
 
 
;Name                           C/M Funktion
;MAX7219_INIT                   C   die PortPins auf OUT und LOW setzen
;MAX7219_OFF                    M   schaltet die Anzeige aus
;MAX7219_ON                     M   schaltet die Anzeige an
;MAX7219_0xBCD                  M   keine Stelle BCD-Decode intern
;MAX7219_1xBCD                  M   nur letzte Stelle BCD-Decode intern
;MAX7219_4xBCD                  M   letzte 4 Stellen BCD-Decode intern
;MAX7219_8xBCD                  M   alle Stellen BCD-Decode intern
;MAX7219_Helligkeit (Register)  M   ändert die Helligkeit
;MAX7219_Helligkeit_i (0...15)  M   ändert die Helligkeit
;MAX7219_ScanLimit  (Register)  M   Anzahl der anzuzeigeden Stellen ändern
;MAX7219_ScanLimit_i (0 ... 7)  M   Anzahl der anzuzeigeden Stellen ändern
;MAX7219_TEST   (0/1)           M   Display-Test 0=aus, 1=an
;MAX7219_SENDEN                 C   r16 (Wert) und r17 (Befehl) an Display senden
 
;C= Call aufrufbar
;M= Makro
 
;r16 als MAX7219_WERT       benannt
;r17 als MAX7219_Befehl     benannt
 
;Pins auf Ausgang einstellen, alle auf LOW
MAX7219_INIT:
    SBI pClockD,bClockD     ;Ausgang für CLK
    SBI poutD,boutD     ;Ausgang für Data
    SBI pcsD,bcs        ;Ausgang für CS
    cbi pclock,bclock   ;Alle aus LOW setzen
    cbi pout,bout
    cbi pcs,bcs
ret
 
;Anzeige AUS
.MACRO MAX7219_OFF
    ldi MAX7219Wert,0           ;0=aus, 1=an
    ldi MAX7219Befehl,12        ;12=Display an/aus
    rcall MAX7219_SENDEN    ;Daten senden
.ENDMACRO
 
;Anzeige AN
.MACRO MAX7219_ON
    ldi MAX7219Wert,1           ;0=aus, 1=an
    ldi MAX7219Befehl,12        ;12=Display an/aus
    rcall MAX7219_SENDEN    ;richtig :) -> Daten senden
.ENDMACRO
 
;Alle Stellen BCD
.MACRO MAX7219_8xBCD
    ldi MAX7219Befehl,0x09
    ldi MAX7219Wert,0xFF        ;alle Stellen BCD-Code
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Alle Stellen ohne interne Decodierung
.MACRO MAX7219_0xBCD
    ldi MAX7219Befehl,0x09
    ldi MAX7219Wert,0x00        ;keine Stellen BCD-Code
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Nur letzte Stelle BCD
.MACRO MAX7219_1xBCD
    ldi MAX7219Befehl,0x09
    ldi MAX7219Wert,0b00000001  ;nur letzte Stellen BCD-Code
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Nur letzten 4 Stelle BCD
.MACRO MAX7219_4xBCD
    ldi MAX7219Befehl,0x09
    ldi MAX7219Wert,0b00001111  ;Stellen 7-4 'normal', 3-0 BCD
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Helligkeit ändern_i
.MACRO MAX7219_Helligkeit_i ;(i, 0...15// i=immediate = Zahl wird übergeben)
    ldi MAX7219Befehl,10
    ldi MAX7219Befehl,@0
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
;Helligkeit ändern
.MACRO MAX7219_Helligkeit   ;(Register = Zahl wird übergeben)
    ldi MAX7219Befehl,10
    mov MAX7219Wert,@0
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Anzeigestellen ändern
.MACRO MAX7219_ScanLimit    ;(Register = Zahl wird übergeben)
    ldi MAX7219BEFEHL,11
    mov MAX7219Wert,@0          ;wenn ein Register übergeben wurde, dann per mov den ersten Parameter laden
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
;Anzeigestellen ändern
.MACRO MAX7219_ScanLimit_i  ;(i, 0...7// i=immediate = Zahl wird übergeben, @1=Wert)
    ldi MAX7219BEFEHL,11
    ldi MAX7219Wert,@0          ;wenn ein Register übergeben wurde, dann per mov den ersten Parameter laden
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
 
;Display-Test an/aus
.MACRO MAX7219_TEST     ;(0/1)
    ldi MAX7219Befehl,15
    ldi MAX7219Wert,@0          ;Wert 0 (Display normal), 1 (alle Segmente an)
    rcall MAX7219_SENDEN        ;Daten an Display senden
.ENDMACRO
   
 
 
 
;Befehl und Wert zum Display senden.
;Nach den 16 bit wird ein CS gesendet,
;wodurch die Daten übernommen werden
MAX7219_SENDEN:
.ifdef PUSHALL
    push MAX7219BEFEHL
    push MAX7219WERT
    .MESSAGE "PUSHALL"
.else
    .MESSAGE "kein PUSHALL"
.endif
    PUSH MAX7219WERT        ;den Wert sichern (wird gleich noch benötigt)
    ldi MAX7219WERT,16      ;ges. 16 Bit austakten
MAX7219_nextbit:
    ROL MAX7219Befehl       ;schiebe Bits H...L der Reihe nach raus
    brcs MAX7219_SET        ;das jetzige Bit=1? (Überlauf? -> nach SET springen)
    cbi pout,bout           ;Port auf LOW
    rjmp MAX7219_TAKT       ;zum Clock-Takt springen
MAX7219_SET:
    sbi pout,bout           ;Port auf HIGH
MAX7219_TAKT:
    sbi pclock,bclock       ;Clock auf HIGH
    cbi pclock,bclock       ;Clock auf LOW  (Bit in Schieberegister übernehmen)
    dec MAX7219WERT         ;Anzahl an Bits -1
    breq MAX7219_Fertig     ;=0? -> Fertig
    cpi MAX7219WERT,8       ;=8?
    brne MAX7219_nextbit    ;nein, dann nächstes Bit
    POP MAX7219Befehl       ;ja, gesicherten Wert zurück holen in 'Befehl', da dieses Register durchgeschoben wird
    rjmp MAX7219_nextbit
MAX7219_Fertig:
    sbi pCS,bCS             ;CS auf HIGH
    cbi pCS,bCS             ;CS auf LOW (Daten aus Schieberegister übernehmen)
.ifdef PUSHALL
    pop MAX7219WERT
    pop MAX7219BEFEHL
.endif
 
ret


TAG: SPI, MAX7219, ATtiny, AVR, Assembler, Include, 7-Segment, Anzeige, 8x7-Segment

Einfach bei eBay 'MAX7219' suchen - gibt Dot-Matrix 8x8 und 7-Segment mit 8 Stellen zur Anzeige bis 99999999
C++ Forum :: Assembler ::  bedingtes Assemblieren in einem Makro - wie erkenne ich ein Register?   Auf Beitrag antworten

Zeige alle Beiträge auf einer Seite




Nächstes Thema anzeigen
Vorheriges Thema anzeigen
Sie können Beiträge in dieses Forum schreiben.
Sie können auf Beiträge in diesem Forum antworten.
Sie können Ihre Beiträge in diesem Forum nicht bearbeiten.
Sie können Ihre Beiträge in diesem Forum nicht löschen.
Sie können an Umfragen in diesem Forum nicht mitmachen.

Powered by phpBB © 2001, 2002 phpBB Group :: FI Theme

c++.net ist Teilnehmer des Partnerprogramms von Amazon Europe S.à.r.l. und Partner des Werbeprogramms, das zur Bereitstellung eines Mediums für Websites konzipiert wurde, mittels dessen durch die Platzierung von Werbeanzeigen und Links zu amazon.de Werbekostenerstattung verdient werden kann.

Die Vervielfältigung der auf den Seiten www.c-plusplus.de, www.c-plusplus.info und www.c-plusplus.net enthaltenen Informationen ohne eine schriftliche Genehmigung des Seitenbetreibers ist untersagt (vgl. §4 Urheberrechtsgesetz). Die Nutzung und Änderung der vorgestellten Strukturen und Verfahren in privaten und kommerziellen Softwareanwendungen ist ausdrücklich erlaubt, soweit keine Rechte Dritter verletzt werden. Der Seitenbetreiber übernimmt keine Gewähr für die Funktion einzelner Beiträge oder Programmfragmente, insbesondere übernimmt er keine Haftung für eventuelle aus dem Gebrauch entstehenden Folgeschäden.