Hallo, also ich möchte einen (oder viele) 32Bit Zähler. Ich habe dazu einen signal buffer: std_logic_vector(31 downto 0); und zu dem zähle ich 1 dazu, also buffer <= buffer + 1; Ja das geht auch jedoch zählt er nur bis 255 und fängt dann wieder bei 0 an. Woran liegt das und wie kann ich das lösen? Wenn ich noch einen signal x: unsigned(31 downto 0); dazuhole und dann in drei aufeinanderfolgenden Takten x <= unsigned(buffer); x <= x + 1; buffer <= std_logic_vector(x); mache, dann wird weiterhin nur bis 255 gezählt?!
Der Fehler ist eigentlich ziemlich offensichtlich. Wenn man ein bisschen programmieren kann. Schon mal darüber nachgedacht, was für einen Typ von Variable du da hochzählst...
Integer sollte doch 32Bit sein, dann ist Unsigned doch eigentlich weil ohne Vorzeichen auch 32Bits aber nur positiv. Gut ich habe gelesen es sich scheinbar 31 Bit. std_logic_vector sollte aber doch immer die Länge haben die man angibt. Und wenn ich da dann einen mit 31 downto 0) machen, warum zählt auch der dann nur bis 255? wird da immer 1 als "00000001" hinzuaddiert? Und kein Übertrag ins 8. und höhere Bit mitgenommen? Und wenn das der Fehler ist, wie mache ich das richtig? Muss ich die Zahl/Vector in kleine 8-Bit Vektoren zerlegen?!
Woher weist Du das er nur bis 355 zählt hast Du es mal simuliert und hast Du vielleicht ein Reset den Du uns verschwiegen hast?
Klar verschweige ich etwas, aber nur damit es vielleicht einfacher wird und der Fehler eingegrenzt wird. signal buffer: std_logic_vector(31 downto 0); buffer <= buffer + 1; Das zählt nur bis 255 und dann wieder von 0 hoch. Getestet habe ich das eben mit einem Spektrum. Da wird in jedem Kanals eine solche 32 Bit Zahl hochgezählt wenn ein entsprechendes Bitmuster reinkommt. Und dann kann ich das Spektrum zum PC schicken und da angucken - und da war in jedem Kanal etwas kleiner 256 drinnen - zum Glück haben wir noch alte Messgeräte die auch zeigen was jeweils in einem Kanals ist. Und da steht dass in dem Kanal x eben z.B. y drinnen ist. Und bei mir hier am FPGA Board wird angezeigt, dass in demselben Kanal x der Wert z drinnen ist. Und komischwerweise ist der Zusammenhang z = y - (n*255) - und das bei jedem Kanal in dem mehr wie 255 drin sein sollte. Gut ein Schreib oder Leseproblem mit dem RAM ist es nicht, weil wenn ich statt buffer <= buffer + 1; ein buffer <= "110000010000010001001000"; hinschreibe bekomme ich auch für den entsprechenden Kanal in dem hochgezählt werden sollte konstant diesen Wert am PC. Ich will wirklich nur eine 32 Bit Zahl hochzählen. Und ist Integer immer unterschiedlich? Wo gibt es eine Übersicht über die Datentypen in VHDL? Beim AVR hätte ich gedacht, dass der dann eben mehr Register braucht wie bei 64Bit Zahlen auf einem 32Bit System.
Gustl Buheitel schrieb: > Und ist Integer immer unterschiedlich? Wo gibt es eine Übersicht über > die Datentypen in VHDL? Beim AVR hätte ich gedacht, dass der dann eben > mehr Register braucht wie bei 64Bit Zahlen auf einem 32Bit System. Bei VHDL hat ein Integer keine feste Größe, wie auch der FPGA keine Register hat. Das ist halt kein Prozessor sondern ein PLD. Integer heißt in dem Zusammenhang nur "Ganzzahl", sonst nichts. Auch ist ein Integer hardwaretechnisch nichts anderes als ein STD_LOGIC_VECTOR. Poste den Code, sonst wird das nichts mit der Hilfe hier.
Gustl Buheitel schrieb: > hochgezählt wenn ein entsprechendes Bitmuster reinkommt. Und dann kann > ich das Spektrum zum PC schicken und da angucken - und da war in jedem > Kanal etwas kleiner 256 drinnen M.a.W: Es existieren noch ungezählte andere potentielle Fehlerquellen zwischen Zähler und PC-Bildschirm.
Wenn ihr wirklich wollt ... mir geht es aber nur um den Zähler oder müsste das so richtig funktionieren?
1 | library ieee; |
2 | use ieee.std_logic_1164.all; |
3 | use IEEE.std_logic_arith.all; |
4 | use IEEE.std_logic_unsigned.all; |
5 | use IEEE.numeric_std.all; |
6 | |
7 | entity spek is |
8 | |
9 | port (clock: in std_logic; |
10 | oe, wr, ce, neues: out std_logic; |
11 | addr: out std_logic_vector(23 downto 1); |
12 | data: inout std_logic_vector(15 downto 0); |
13 | pins12: in std_logic_vector(11 downto 0); |
14 | -- pins8: in std_logic_vector(7 downto 0);
|
15 | trigger: in std_logic; |
16 | output, rs232data : out std_logic_vector(7 downto 0); |
17 | input: in std_logic_vector(7 downto 0); |
18 | i,rdy: in std_logic); |
19 | end spek; |
20 | |
21 | architecture Behavioral of spek is |
22 | |
23 | signal c: integer range 0 to 7 := 7; --counter von init |
24 | signal c1: integer range 0 to 12 := 0; --counter von rs232 |
25 | signal c2: integer range 0 to 25 := 25; --counter beim messen |
26 | signal cv: std_logic_vector(23 downto 1); --counter rs232 |
27 | signal o: std_logic_vector(15 downto 0); --output rs232 |
28 | signal buff: std_logic_vector(31 downto 0); --buffer beim messen |
29 | signal pins: std_logic_vector(11 downto 0); --pin IO |
30 | signal ipins: std_logic_vector(11 downto 0); --pin IO invertiert |
31 | signal sigc: integer range 0 to 300 := 0; --impulszähler |
32 | |
33 | signal count: integer range 0 to 50 := 50; --trigger latenz |
34 | signal doc: integer range 0 to 50000000; --auslesebuttoncounter |
35 | signal do2: std_logic; --auslesesignal, sync |
36 | signal b,neu,fall: std_logic; --r,w flag |
37 | signal send: std_logic_vector(7 downto 0):= "00000000"; --output von init |
38 | signal adc: std_logic_vector(23 downto 1):= "00000000000000000000000"; --addrcount von init |
39 | signal ad1: std_logic_vector(23 downto 1):= "00000000000000000000000"; --addr1 |
40 | signal ad2: std_logic_vector(23 downto 1):= "00000000000000000000000"; --addr2 |
41 | signal sro: std_logic_vector(15 downto 0); --sram out |
42 | signal sri: std_logic_vector(15 downto 0); --sram in |
43 | |
44 | signal ac: integer range 0 to 50000000; --auslesebuttoncounter |
45 | |
46 | begin
|
47 | |
48 | pins <= pins12; --pinmap |
49 | ipins <= "111111111111" - pins; --addresse an der gezählt wird bzw. invertierte pins |
50 | |
51 | data <= sro when b = '0' else "ZZZZZZZZZZZZZZZZ"; |
52 | sri <= data when b = '1'; |
53 | |
54 | output <= send; |
55 | |
56 | process --auslesebutton einsyncen |
57 | begin
|
58 | wait until rising_edge(clock); |
59 | if (doc<10000000) then |
60 | doc <= doc + 1; |
61 | end if; |
62 | if (i ='1') then |
63 | doc <= 0; |
64 | end if; |
65 | if doc = 9999999 then --neu! |
66 | do2 <= '1'; |
67 | end if; |
68 | if doc = 10000000 then |
69 | do2 <= '0'; |
70 | end if; |
71 | end process; |
72 | |
73 | process --falling edge einsyncen |
74 | variable sr : std_logic_vector (3 downto 0) := "0000"; |
75 | begin
|
76 | wait until rising_edge(clock); |
77 | fall <= not sr(2) and sr(3); |
78 | sr := sr(2 downto 0) & trigger; |
79 | end process; |
80 | |
81 | process --falling edge einsyncen |
82 | begin
|
83 | wait until rising_edge(clock); |
84 | if count < 50 then |
85 | count <= count + 1; |
86 | neu <= '0'; |
87 | end if; |
88 | if fall='1' then |
89 | count <= 0; |
90 | end if; |
91 | if count = 49 then |
92 | neu <= '1'; |
93 | end if; |
94 | if count = 50 then |
95 | neu <= '0'; |
96 | end if; |
97 | end process; |
98 | |
99 | |
100 | process begin |
101 | wait until rising_edge(clock); |
102 | |
103 | if input /= "00000010" then |
104 | neues <= '0'; |
105 | end if; |
106 | |
107 | -------------------------------------------------------------------------------------------------------------------------------------------
|
108 | |
109 | if input = "00000001" then --RAM Nullen |
110 | |
111 | if c < 7 then |
112 | c <= c + 1; |
113 | elsif c = 7 and adc < 2097153 then --spektrumlänge x2 BIG |
114 | c <= 0; |
115 | elsif c = 7 and adc = 2097153 and do2 = '1' then |
116 | adc <= "00000000000000000000000"; |
117 | end if; |
118 | |
119 | if c = 0 then --leds geben status aus |
120 | if adc = 1 then |
121 | send <= "00000000"; |
122 | elsif adc = 262144 then |
123 | send <= "00000001"; |
124 | elsif adc = 524288 then |
125 | send <= "00000011"; |
126 | elsif adc = 786432 then |
127 | send <= "00000111"; |
128 | elsif adc = 1048576 then |
129 | send <= "00001111"; |
130 | elsif adc = 1310720 then |
131 | send <= "00011111"; |
132 | elsif adc = 1572864 then |
133 | send <= "00111111"; |
134 | elsif adc = 1835008 then |
135 | send <= "01111111"; |
136 | elsif adc = 2097152 then |
137 | send <= "11111111"; |
138 | end if; |
139 | |
140 | elsif c = 1 then --1. schreibzugriff |
141 | ce <= '1'; |
142 | oe <= '0'; |
143 | wr <= '0'; |
144 | b <= '1'; |
145 | elsif c = 2 then |
146 | ce <= '0'; |
147 | oe <= '0'; |
148 | wr <= '1'; |
149 | b <= '1'; |
150 | addr <= adc; |
151 | elsif c = 3 then |
152 | ce <= '0'; |
153 | oe <= '0'; |
154 | wr <= '0'; |
155 | b <= '0'; |
156 | addr <= adc; |
157 | sro <= "0000000000000000"; |
158 | elsif c = 4 then |
159 | ce <= '1'; |
160 | oe <= '0'; |
161 | wr <= '0'; |
162 | b <= '0'; |
163 | addr <= adc; |
164 | sro <= "0000000000000000"; |
165 | |
166 | elsif c = 5 then |
167 | adc <= adc + 1; |
168 | b <= '1'; |
169 | end if; |
170 | |
171 | -------------------------------------------------------------------------------------------------------------------------------------------
|
172 | |
173 | elsif input = "00000010" then --lesen und über rs232 ausgeben |
174 | |
175 | if do2 = '1' then |
176 | c1 <= 0; |
177 | cv <= "00000000000000000000000"; |
178 | end if; |
179 | if c1 = 12 and cv < 2097151 then --BIG |
180 | c1 <= 0; |
181 | cv <= cv + 1; |
182 | rs232data <= "00000000"; |
183 | end if; |
184 | |
185 | if cv = 0 then --nur ausgabe |
186 | send <= "00000000"; |
187 | elsif cv = 262144 then |
188 | send <= "00000001"; |
189 | elsif cv = 524288 then |
190 | send <= "00000011"; |
191 | elsif cv = 786432 then |
192 | send <= "00000111"; |
193 | elsif cv = 1048576 then |
194 | send <= "00001111"; |
195 | elsif cv = 1310720 then |
196 | send <= "00011111"; |
197 | elsif cv = 1572864 then |
198 | send <= "00111111"; |
199 | elsif cv = 1835008 then |
200 | send <= "01111111"; |
201 | elsif cv = 2097151 then |
202 | send <= "11111111"; |
203 | end if; |
204 | |
205 | if c1 = 0 then --1. lesezugriff |
206 | ce <= '1'; |
207 | oe <= '1'; |
208 | wr <= '1'; |
209 | b <= '1'; |
210 | c1 <= c1 + 1; |
211 | o <= "0000000000000000"; |
212 | elsif (c1 = 1 or c1 = 2) then |
213 | ce <= '0'; |
214 | oe <= '1'; |
215 | wr <= '1'; |
216 | b <= '1'; |
217 | addr <= cv; |
218 | c1 <= c1 + 1; |
219 | elsif (c1 = 3 or c1 = 4 or c1 = 5) then |
220 | ce <= '0'; |
221 | oe <= '0'; |
222 | wr <= '1'; |
223 | b <= '1'; |
224 | addr <= cv; |
225 | o <= sri; |
226 | c1 <= c1 + 1; |
227 | neues <= '0'; |
228 | |
229 | elsif c1 = 6 and rdy = '1' then |
230 | neues <= '1'; |
231 | rs232data <= o(7 downto 0); |
232 | c1 <= c1 + 1; |
233 | elsif c1 = 7 then |
234 | neues <= '1'; |
235 | c1 <= c1 + 1; |
236 | elsif c1 = 8 then |
237 | neues <= '0'; |
238 | c1 <= c1 + 1; |
239 | |
240 | elsif c1 = 9 and rdy = '1' then |
241 | neues <= '1'; |
242 | rs232data <= o(15 downto 8); |
243 | c1 <= c1 + 1; |
244 | elsif c1 = 10 then |
245 | neues <= '1'; |
246 | c1 <= c1 + 1; |
247 | elsif c1 = 11 then |
248 | neues <= '0'; |
249 | c1 <= c1 + 1; |
250 | end if; |
251 | |
252 | -------------------------------------------------------------------------------------------------------------------------------------------
|
253 | |
254 | elsif input > "01000000" then --messen! zwei lese und zwei schreibzugriffe |
255 | |
256 | if c2 < 25 then |
257 | c2 <= c2 + 1; |
258 | elsif c2 = 25 and neu = '1' then |
259 | c2 <= 0; |
260 | ad1(1) <= '0'; |
261 | ad1(13 downto 2) <= ipins; |
262 | ad1(23 downto 14) <= "0000000000"; |
263 | ad2(1) <= '1'; |
264 | ad2(13 downto 2) <= ipins; |
265 | ad2(23 downto 14) <= "0000000000"; |
266 | end if; |
267 | |
268 | if c2 = 0 then |
269 | b <= '1'; |
270 | buff <= "00000000000000000000000000000000"; |
271 | |
272 | elsif c2 = 1 then --1. lesezugriff |
273 | ce <= '1'; |
274 | oe <= '1'; |
275 | wr <= '1'; |
276 | b <= '1'; |
277 | elsif (c2 = 2 or c2 = 3) then |
278 | ce <= '0'; |
279 | oe <= '1'; |
280 | wr <= '1'; |
281 | b <= '1'; |
282 | addr <= ad1; |
283 | elsif (c2 = 4 or c2 = 5 or c2 = 6) then |
284 | ce <= '0'; |
285 | oe <= '0'; |
286 | wr <= '1'; |
287 | b <= '1'; |
288 | addr <= ad1; |
289 | buff(15 downto 0) <= sri; |
290 | |
291 | elsif c2 = 7 then --2. lesezugriff |
292 | ce <= '1'; |
293 | oe <= '1'; |
294 | wr <= '1'; |
295 | b <= '1'; |
296 | elsif (c2 = 8 or c2 = 9) then |
297 | ce <= '0'; |
298 | oe <= '1'; |
299 | wr <= '1'; |
300 | b <= '1'; |
301 | addr <= ad2; |
302 | elsif (c2 = 10 or c2 = 11 or c2 = 12) then |
303 | ce <= '0'; |
304 | oe <= '0'; |
305 | wr <= '1'; |
306 | b <= '1'; |
307 | addr <= ad2; |
308 | buff(31 downto 16) <= sri; |
309 | |
310 | elsif c2 = 13 and buff /= "11111111111111111111111111111111" then |
311 | buff <= buff + 1; |
312 | |
313 | elsif c2 = 14 then --1. schreibzugriff |
314 | ce <= '1'; |
315 | oe <= '0'; |
316 | wr <= '0'; |
317 | b <= '1'; |
318 | elsif c2 = 15 then |
319 | ce <= '0'; |
320 | oe <= '0'; |
321 | wr <= '1'; |
322 | b <= '1'; |
323 | addr <= ad1; |
324 | elsif c2 = 16 then |
325 | ce <= '0'; |
326 | oe <= '0'; |
327 | wr <= '0'; |
328 | b <= '0'; |
329 | addr <= ad1; |
330 | sro <= buff(15 downto 0); |
331 | elsif c2 = 17 then |
332 | ce <= '1'; |
333 | oe <= '0'; |
334 | wr <= '0'; |
335 | b <= '0'; |
336 | addr <= ad1; |
337 | sro <= buff(15 downto 0); |
338 | |
339 | elsif c2 = 18 then --2. schreibzugriff |
340 | ce <= '1'; |
341 | oe <= '0'; |
342 | wr <= '0'; |
343 | b <= '1'; |
344 | elsif c2 = 19 then |
345 | ce <= '0'; |
346 | oe <= '0'; |
347 | wr <= '1'; |
348 | b <= '1'; |
349 | addr <= ad2; |
350 | elsif c2 = 20 then |
351 | ce <= '0'; |
352 | oe <= '0'; |
353 | wr <= '0'; |
354 | b <= '0'; |
355 | addr <= ad2; |
356 | sro <= buff(31 downto 16); |
357 | elsif c2 = 21 then |
358 | ce <= '1'; |
359 | oe <= '0'; |
360 | wr <= '1'; |
361 | b <= '0'; |
362 | addr <= ad2; |
363 | sro <= buff(31 downto 16); |
364 | |
365 | elsif c2 = 22 then |
366 | b <= '1'; |
367 | buff <= "00000000000000000000000000000000"; |
368 | end if; |
369 | |
370 | |
371 | if sigc < 300 and ac /= 50000000 and neu = '1' then |
372 | sigc <= sigc + 1; |
373 | elsif ac = 49999999 then |
374 | if sigc = 0 then |
375 | send(5 downto 0) <= "000000"; |
376 | elsif sigc > 0 and sigc < 50 then |
377 | send(5 downto 0) <= "000001"; |
378 | elsif sigc > 49 and sigc < 100 then |
379 | send(5 downto 0) <= "000011"; |
380 | elsif sigc > 99 and sigc < 150 then |
381 | send(5 downto 0) <= "000111"; |
382 | elsif sigc > 149 and sigc < 200 then |
383 | send(5 downto 0) <= "001111"; |
384 | elsif sigc > 199 and sigc < 250 then |
385 | send(5 downto 0) <= "011111"; |
386 | elsif sigc > 249 and sigc < 300 then |
387 | send(5 downto 0) <= "111111"; |
388 | elsif sigc > 299 then |
389 | send(5 downto 0) <= "110011"; |
390 | end if; |
391 | elsif ac = 50000000 then |
392 | sigc <= 0; |
393 | end if; |
394 | |
395 | if ac < 50000000 then |
396 | ac <= ac + 1; |
397 | elsif ac = 50000000 then |
398 | ac <= 0; |
399 | end if; |
400 | |
401 | if input = "10000000" and ac > 25000000 then |
402 | send(7 downto 6) <= "10"; |
403 | elsif input = "10000000" and ac < 25000000 then |
404 | send(7 downto 6) <= "00"; |
405 | end if; |
406 | |
407 | |
408 | |
409 | end if; |
410 | end process; |
411 | |
412 | |
413 | end Behavioral; |
Natürlich gibt es noch mehr Komponenten, aber die gehen, also Senden über rs232 geht, die Leds und 7Seg-Displays auch.
Gustl Buheitel schrieb: > Ich habe dazu einen > signal buffer: std_logic_vector(31 downto 0); > und zu dem zähle ich 1 dazu, also > buffer <= buffer + 1; Mit Vektoren rechnet man nicht. raketenfred schrieb: > Sicher, dass ein Integer 32bit auf einem 8-Bit AVR hat ?! Was hat VHDL mit AVR zu tun? Gustl Buheitel schrieb: > Und ist Integer immer unterschiedlich? Nein. Da sind offenbar ein paar Softwerker reingerutscht. Und da sind in C Integer mindestens 2 Byte breit. > Beim AVR hätte ich gedacht, dass der dann eben > mehr Register braucht wie bei 64Bit Zahlen auf einem 32Bit System. Das kommt auf den Compiler an... > Wo gibt es eine Übersicht über die Datentypen in VHDL? Weil du jederzeit selber jede Menge Typen definieren kannst, ist die Frage an sich ungünstig... Zeig mal etwas mehr Code. Und am besten auch, wie du siehst, dass da nur bis 255 gezählt wird (Testbench).
Eine Testbench habe ich nicht, da wird ja auch nur immer in dem Kanal hochgezählt für den das passende Bitmuster anliegt. Und dass nur bis 255 gezählt wird sehe ich aus dem Spektrum, dass hier gebaut wird und aus dem Vergleichsspektrum, da kann man schön sehen, dass hier im Spektrum nach 255 in dem entsprechenden Kanal wieder bei 0 begonnen wird. Wenn z.B. im vergleichsspektrum in einem Kanal 1234 drinnen sein sollte, dann ist hier 210 = 1234 - 4*256 drinnen. Und das geht bei jedem Kanal nur dass 4 eben nicht immer 4 ist. Ok mit was rechnet man denn was 32 Bit ist und wirklich 32 Bit verwendet werden können, also nicht wie mit Vorzeichen nur 31?
1 | [...] |
2 | if c2 < 25 then |
3 | c2 <= c2 + 1; |
4 | [...] |
5 | end if; |
6 | [...] |
7 | if c2 = 13 and buff /= "11111111111111111111111111111111" then |
8 | buff <= buff + 1; |
9 | [...] |
10 | end if; |
11 | [...] |
Das läuft parallel. Kannst mir das mal erklären?
Ja was ist damit? Das eine zählt hoch und das andere guckt wo der Zähler ist und macht dann was. Das ist quasi eine Sequenz aus 25 Takten in denen der Reihe nach die Ramzugriffe abgearbeitet werden. Also das sollte nicht das Problem sein.
Gustl Buheitel schrieb: > Ja was ist damit? Das eine zählt hoch und das andere guckt wo der Zähler > ist und macht dann was. Das ist quasi eine Sequenz aus 25 Takten in > denen der Reihe nach die Ramzugriffe abgearbeitet werden. Also das > sollte nicht das Problem sein. Das Problem sehe ich darin, dass du etwas weiter unten schreibst
1 | elsif c2 = 22 then |
2 | b <= '1'; |
3 | buff <= "00000000000000000000000000000000"; |
Naja, es wird c2 so wie ich das sehe ja in jedem Takt inkrementiert. Also trift c2=13 ja nur einen einzigen Takt zu, danach wird buf wieder auf 0 zurückgesetzt. Oder übersehe ich da gerade etwas?
Ja. Da wird vor Takt 13 aus dem RAM in den buff gelesen, bei Takt 13 sollte buff um 1 erhöht werden, zwischen Takt 13 und 22 wird buff dann wieder in den RAM geschrieben und bei Takt 22 wird buff geleert. Das ist eben nicht nur ein 32 Bit Zähler sondern sehr viele (hier 2^20) und da die nicht im FPGA Platz haben liegen die im RAM und brauchen 4MBytes.
Gustl Buheitel schrieb: > Wenn ihr wirklich wollt ... Das wäre jetzt aber besser als Anhang (mit Endung .vhd) aufgehoben gewesen... Ich habe eher den Eindruck, da passt was mit dem Zusammenbauen des 32-Bit Weerts nicht so richtig. Aber ich würde dir hier eine Testbench unbedingt empfehlen... BTW: buff <= "00000000000000000000000000000000"; So gehts übersichtlicher: buff <= (others=>'0'); Oder statt dem: buff /= "11111111111111111111111111111111" wenigstens so: buf /= x"FFFFFFFF"
Lothar Miller schrieb: > Ich habe eher den Eindruck, da passt was mit dem Zusammenbauen des > 32-Bit Weerts nicht so richtig. Er sagt allerdings dass wenn er buff einen Festen Wert zuweist alles stimmt. Mach doch bitte mal buff zu einem integer bevor du da was dazuzählst. Vielleicht gehts ja dann.
Julian X. schrieb: > Mach doch bitte mal buff zu einem integer bevor du da was dazuzählst. > Vielleicht gehts ja dann. Das geht aber schon sehr in Richtung "Handauflegen"... Und zudem ist es gar nicht gut, eine vorzeichenlose 32-Bit Zahl als vorzeichenbehafteten 32-Bit Integer zu interpretieren... Für solche Wortbreiten gibt es den Datentyp UNSIGNED. BTW: Das hier
1 | signal sigc: integer range 0 to 300 := 0; --impulszähler |
2 | :
|
3 | if sigc = 0 then |
4 | send(5 downto 0) <= "000000"; |
5 | elsif sigc > 0 and sigc < 50 then |
6 | send(5 downto 0) <= "000001"; |
7 | elsif sigc > 49 and sigc < 100 then |
8 | send(5 downto 0) <= "000011"; |
9 | elsif sigc > 99 and sigc < 150 then |
10 | send(5 downto 0) <= "000111"; |
11 | elsif sigc > 149 and sigc < 200 then |
12 | send(5 downto 0) <= "001111"; |
13 | elsif sigc > 199 and sigc < 250 then |
14 | send(5 downto 0) <= "011111"; |
15 | elsif sigc > 249 and sigc < 300 then |
16 | send(5 downto 0) <= "111111"; |
17 | elsif sigc > 299 then |
18 | send(5 downto 0) <= "110011"; |
19 | end if; |
ginge auch so:
1 | if sigc = 0 then send(5 downto 0) <= "000000"; |
2 | elsif sigc < 50 then send(5 downto 0) <= "000001"; |
3 | elsif sigc < 100 then send(5 downto 0) <= "000011"; |
4 | elsif sigc < 150 then send(5 downto 0) <= "000111"; |
5 | elsif sigc < 200 then send(5 downto 0) <= "001111"; |
6 | elsif sigc < 250 then send(5 downto 0) <= "011111"; |
7 | elsif sigc < 300 then send(5 downto 0) <= "111111"; |
8 | else send(5 downto 0) <= "110011"; |
9 | end if; |
Dann sieht man auch ein Muster...
Ähm ja richtig Integer, und da ist meine Frage, wie mache ich das mit 32 Bit?
1 | elsif c2 = 13 then |
2 | |
3 | buff_i <= to_integer(unsigned(buff)); --hier geht nicht |
4 | |
5 | elsif c2 = 14 then |
6 | |
7 | buff_i <= buff_i + 1; |
8 | |
9 | elsif c2 = 15 then |
10 | |
11 | buff <= conv_std_logic_vector(buff_i,32); |
So sieht das doch aus mit signal buff_i: integer; Aber ich bekomme immer ein "to_integer can not have such operands in this context.". Das in Bytes zerlegen und lesen und schreiben geht vermutlich, da ich den selben Code ja zweimal verwende, also auch in der Funktion die nacheinander den RAM ließt und über rs232 ausgibt was funktioniert und geschrieben wird wenn der RAM genullt wird, da kann ich den RAM ja auch alternativ mit z.B. lauter "1100110011001100" beschreiben und mir ausgeben lassen und das funktioniert, nur dieser Zähler eben nicht.
Zunächst machst du aus
1 | library ieee; |
2 | use ieee.std_logic_1164.all; |
3 | use IEEE.std_logic_arith.all; |
4 | use IEEE.std_logic_unsigned.all; |
5 | use IEEE.numeric_std.all; |
dieses
1 | library ieee; |
2 | use ieee.std_logic_1164.all; |
3 | use IEEE.numeric_std.all; |
Die Libs std_logic_arith & std_logic_unsigned sind ganz großer Mist, weil nicht standardisiert. Wenn man die numeric_std benutzt hat man alles was man braucht. Dann dürfte auch
1 | buff_i <= to_integer(unsigned(buff)); |
funktionieren.
Achso, aus
1 | buff <= conv_std_logic_vector(buff_i,32); |
wird dann
1 | buff <= std_logic_vector(to_unsigned(buff_i, 32)); |
Du hast in deinem Code oben munter durcheinander Konvertierungsfunktionen der drei Libraries benutzt, da kann die Synthese schonmal durcheinander kommen. Wie gesagt, NUR die numeric_std benutzen und die darin enthaltenen Funktionen. Siehe: http://wiki.jhor.de/images/d/d6/Numeric_std.jpg
Ja ... super, jetzt kann ich aber kein +, - oder = verwenden also die bräuchte ich schon irgendwie. Also vor allem sowas wie ein std_logic_vector minus ein anderer std_logic_vector oder auch plus.
Gustl Buheitel schrieb: > Ja ... super, jetzt kann ich aber kein +, - oder = verwenden also die > bräuchte ich schon irgendwie. Also vor allem sowas wie ein > std_logic_vector minus ein anderer std_logic_vector oder auch plus. Du sollst ja auch nicht mit Vektoren rechnen, sondern mit unsigned und signed.
Wenn du unbedingt zwei als std_logic_vector definierte Signale zB. addieren willst, kannst du das dann über Konvertierungsfunktionen weiterhin machen:
1 | signal a, b, c: std_logic_vector(31 downto 0); |
2 | ....
|
3 | c <= std_logic_vector(unsigned(a) + unsigned(b)); |
4 | c <= std_logic_vector(signed(a) + signed(b)); |
Die kannst durch die Konvertierungsfunktionen also selbst entscheiden, ob du signed oder unsigned arbeiten willst, eine Möglichkeit, die du mit dieser, ich nenne sie jetzt einfach mal Wurstbibliothek, std_logic_unsigned nicht hast, weil du dich da für die ganze architecture auf unsigned festnagelst.
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.