Forum: FPGA, VHDL & Co. Vektorinhalt variabel zuweisen


von erwin86 (Gast)


Lesenswert?

Hallo,

ich bin noch Anfänger in VHDL und habe folgendes Problem:

Ich habe zwei Eingangsvektoren, der eine stellt die Daten dar (8 Bit) 
und der andere gibt einen möglichen Offset an(4 Bit). Ich möchte mit 
Hilfe des Offsets den Eingangsvektor variabel einem Ausgangsvektor 
zuweisen, der 16 Bit hat.

Dabei soll z. B. bei einer "1" auf dem Offset Vektor die Daten des 8Bit 
Vektors auf das 2-9. Stelle des Ausgangsvektor zugewiesen werden.

Mit welchen Anweisungen kann ich das am Besten realisieren?

Meine Idee wäre das mit einer Statemachine zu machen, die aber ja dann 
so viel Zustände haben muss, wie ich mit dem Offset Werte darstellen 
kann.

Gibt es eventuell noch eine elegantere Methode?

Vielen Dank für eure Hilfe.

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

erwin86 schrieb:
> Dabei soll z. B. bei einer "1" auf dem Offset Vektor die Daten des 8Bit
> Vektors auf das 2-9. Stelle des Ausgangsvektor zugewiesen werden.
Und was sollte ab einem Wert Offset>=9 passieren?

> Dabei soll z. B. bei einer "1" auf dem Offset Vektor die Daten des 8Bit
> Vektors auf das 2-9. Stelle des Ausgangsvektor zugewiesen werden.
Das ist erstmal ein "Verschieben". Damit würde ich mit einem 
Schieberegister anfangen...
1
std_logic_vector Vin(7 downto 0);
2
std_logic_vector Offset(3 downto 0);
3
std_logic_vector Vout(15 downto 0);
4
5
process (Vin, Offset) 
6
variable sr:  std_logic_vector(15 downto 0);
7
variable cnt: integer;
8
begin
9
   sr  := x"00" & Vin;
10
   cnt := to_integer(unsigned(Offset));
11
   while (cnt/=0) loop
12
      sr  := sr(14 downto 0) & '0';
13
      cnt := cnt-1;
14
   end loop;
15
   Vout <= sr;
16
end process;

Allerdings könnte die Aufgabe auch als Mux ausgeführt werden. Hier wäre 
es aber schön, den Offset auf 0..8 zu begrenzen, dann werden die Grenzen 
des Zielvektors nicht so leicht angekratzt...
Siehe dort im Abschnitt Vektormanipulation:
http://www.lothar-miller.de/s9y/categories/16-Numeric_Std

von Marcus H. (mharnisch) Benutzerseite


Lesenswert?

Würde soetwas nicht genügen?
1
    variable shift_i : integer range 0 to dout'length - din'length;
2
    variable din_u   : unsigned(dout'range);  -- same range as dout!
und weiter unten:
1
    shift_i := to_integer(unsigned(shift));
2
    din_u   := resize(unsigned(din), dout'length);
3
4
    dout    <= std_logic_vector(shift_left(din_u, shift_i));
Gruß
Marcus

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Marcus Harnisch schrieb:
> Würde soetwas nicht genügen?
Manchmal sieht man die naheliegendste Lösung nicht... :-/
> Würde soetwas nicht genügen?
Doch, das ist sogar so einfach, dass sofort ein Barrelshifter erkannt 
und implementiert wird...

> variable shift_i : integer range 0 to dout'length - din'length;
Nicht, wenn der Offset auch mal 15 werden kann (und das kann er 
eigentlich schon bei einem 4 Bit Vektor)...
Ich würde hier range 0 to 15 vorschlagen...

Und ganz kompakt wäre dann
1
      Vout <= std_logic_vector( shift_left( resize(unsigned(Vin),Vout'length), to_integer(unsigned(Offset)) ) );

von Marcus H. (mharnisch) Benutzerseite


Lesenswert?

Lothar Miller schrieb:
>> variable shift_i : integer range 0 to dout'length - din'length;
> Nicht, wenn der Offset auch mal 15 werden kann (und das kann er
> eigentlich schon bei einem 4 Bit Vektor)...

Ja, ich habe mich durch Deinen Beitrag irritieren lassen, in dem Du
schriebst: "Hier wäre es aber schön, den Offset auf 0..8 zu begrenzen,"
Wenn man das nicht will, dann lässt man es natürlich bleiben :-)

--
Marcus

von Thomas R. (Firma: abaxor engineering) (abaxor)


Lesenswert?

erwin86 schrieb:
> Dabei soll z. B. bei einer "1" auf dem Offset Vektor die Daten des 8Bit
> Vektors auf das 2-9. Stelle des Ausgangsvektor zugewiesen werden.

bei Offset = 2 auf Stelle 3..10 Multiplikation mit 8
bei Offset = 3 auf Stelle 4..11 Multiplikation mit 16
bei Offset = 4 auf Stelle 5..12 Multiplikation mit 32
bei Offset = 5 auf Stelle 6..13 Multiplikation mit 64

usw.

Das Schieben lässt sich mit einer Multiplikation innerhalb eines Taktes 
erledigen. Und alle modernen FPGAs haben einen Multiplizierer. Du musst 
dir nur aus deinem Offset den richtigen Faktor bauen.

Tom

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Thomas Reinemann schrieb:
> Das Schieben lässt sich mit einer Multiplikation innerhalb eines Taktes
> erledigen
Hier ist noch nirgends ein Takt beteiligt...  :-o

Seis drum, der Multiplizierer arbeitet auch kombinatorisch. Und dann 
ergibt sich folgendes Bild:
1
library IEEE;
2
use IEEE.STD_LOGIC_1164.ALL;
3
use IEEE.NUMERIC_STD.ALL;
4
5
entity Shifter is
6
    Port ( Vin : in  STD_LOGIC_VECTOR (7 downto 0);
7
           Offset : in  STD_LOGIC_VECTOR (3 downto 0);
8
           Vout : out  STD_LOGIC_VECTOR (15 downto 0));
9
end Shifter;
10
11
architecture Behavioral of Shifter is
12
begin
13
14
-- Number of Slices 8
15
-- Number of 4 input LUTs 15
16
-- S3AN 12.005ns
17
   process (Vin, Offset) 
18
   variable m       : integer;
19
   variable din_u   : unsigned(Vout'range);  
20
   begin
21
      case Offset is
22
         when "0000" => m := 1;
23
         when "0001" => m := 2;
24
         when "0010" => m := 4;
25
         when "0011" => m := 8;
26
         when "0100" => m := 16;
27
         when "0101" => m := 32;
28
         when "0110" => m := 64;
29
         when "0111" => m := 128;
30
         when "1000" => m := 256;
31
         when "1001" => m := 512;
32
         when "1010" => m := 1024;
33
         when "1011" => m := 2048;
34
         when "1100" => m := 4096;
35
         when "1101" => m := 8192;
36
         when "1110" => m := 16348;
37
         when others => m := 32786;
38
      end case;  
39
      din_u := resize(unsigned(Vin), Vout'length);
40
      din_u := din_u * m;
41
      Vout    <= std_logic_vector(din_u);
42
   end process;
43
44
45
-- Number of Slices 20
46
-- Number of 4 input LUTs 37
47
-- S3AN 10.270ns
48
   process (Vin, Offset) 
49
   variable shift_i : integer range 0 to 15;
50
   variable din_u   : unsigned(Vout'range);  
51
   begin
52
      shift_i := to_integer(unsigned(Offset));
53
      din_u   := resize(unsigned(Vin), Vout'length);
54
      Vout    <= std_logic_vector(shift_left(din_u, shift_i));
55
   end process;
56
57
-- Kurzschreibweise des vorigen Prozesses:
58
-- Number of Slices 20
59
-- Number of 4 input LUTs 37
60
-- S3AN 10.270ns
61
   Vout    <= std_logic_vector( shift_left(resize(unsigned(Vin),Vout'length), to_integer(unsigned(Offset))) );
62
   
63
-- Number of Slices 147
64
-- Number of 4 input LUTs 269
65
-- S3AN 34.314ns
66
   process (Vin, Offset) 
67
   variable sr:  std_logic_vector(15 downto 0);
68
   variable cnt: integer;
69
   begin
70
      sr  := x"00" & Vin;
71
      cnt := to_integer(unsigned(Offset));
72
      for i in 0 to 15 loop
73
         if (cnt=0) then 
74
            exit; 
75
         end if;
76
         sr  := sr(14 downto 0) & '0';
77
         cnt := cnt-1;
78
      end loop;
79
      Vout <= sr;
80
   end process;
81
82
-- Number of Slices 117
83
-- Number of 4 input LUTs 214
84
-- S3AN 29.115ns
85
   process (Vin, Offset) 
86
   variable sr:  std_logic_vector(15 downto 0);
87
   variable cnt: integer;
88
   begin
89
      sr  := x"00" & Vin;
90
      cnt := to_integer(unsigned(Offset));
91
      for i in 0 to 15 loop
92
         if (cnt/=0) then
93
            sr  := sr(14 downto 0) & '0';
94
         end if;
95
         cnt := cnt-1;
96
      end loop;
97
      Vout <= sr;
98
   end process;
99
100
-- Synthese funktioniert nicht...
101
   process (Vin, Offset) 
102
   variable sr:  std_logic_vector(15 downto 0);
103
   variable cnt: integer;
104
   begin
105
      sr  := x"00" & Vin;
106
      cnt := to_integer(unsigned(Offset));
107
      while (cnt/=0) loop
108
         sr  := sr(14 downto 0) & '0';
109
         cnt := cnt-1;
110
      end loop;
111
      Vout <= sr;
112
   end process;
113
end Behavioral;
Fazit: die Multiplizierer-Lösung ist die kompakteste,
die Schieberegisterlösung die schnellste... ;-)
Und meine beiden sind Schrott...  :-(
(Mich hatten die unerträglich langen Durchlaufzeiten schon sehr 
gewundert...)

von Ütze (Gast)


Lesenswert?

bei 8 rein und 16 raus hab ich sowas im kopf:
1
  subtype shift is integer range 0 to 8;
2
  signal my_shift : shift := to_integer(unsigned(shift_vector));
3
4
  dout(0 + my_shift to 7 + my_shift)<= acht_bit_invector;

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

erwin86 schrieb:
>>>> gibt einen möglichen Offset an(4 Bit)
Ütze schrieb:
> bei 8 rein und 16 raus hab ich sowas im kopf:
Das geht aber schief, wenn shift mal >8 wird.
Und das kann es bei 4 Bit... :-o

Ütze schrieb:
> dout(0 + my_shift to 7 + my_shift)
Üblicher wäre die umgekehrte Reihenfolge:
 dout(7 + my_shift downto my_shift)

von Ütze (Gast)


Lesenswert?

ok, dann
1
  signal my_shift : integer := 0;
2
  signal to_much : integer := 0;
3
  
4
  my_shift:=to_integer(unsigned(shift_vector));
5
  
6
  if my_shift < 9 then
7
  dout(0 + my_shift to 7 + my_shift)<= acht_bit_invector;
8
  else
9
  to_much=my_shift-8;
10
  dout(my_shift to 7 + (my_shift-to_much)) <= acht_bit_invector(0 to 7-to_much);
11
  dout(0 to 7 -(my_shift-to_much))<= acht_bit_invector( 7-to_much to 7);
12
  end if;

wenn es "ringsrum" gehen soll

sonst
1
  if my_shift < 9 then
2
  dout(0 + my_shift to 7 + my_shift)<= acht_bit_invector;
3
  else
4
  "error_led, interrupt, was weiss ich - an"
5
  end if;

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ütze schrieb:
> dout(0 + my_shift to 7 + my_shift)
Warum immer diese verkehrte Bitreihenfolge?
Das gibt doch eh' nur Fehler:
1
ERROR:HDLParsers:807 - "/Projekte/FPGA/Shifter/Shifter.vhd" Line 22. Vout can not be used with range to.
2
ERROR:HDLParsers:807 - "/Projekte/FPGA/Shifter/Shifter.vhd" Line 25. Vout can not be used with range to.
3
ERROR:HDLParsers:807 - "/Projekte/FPGA/Shifter/Shifter.vhd" Line 25. Vin can not be used with range to.
4
ERROR:HDLParsers:807 - "/Projekte/FPGA/Shifter/Shifter.vhd" Line 26. Vout can not be used with range to.
5
ERROR:HDLParsers:807 - "/Projekte/FPGA/Shifter/Shifter.vhd" Line 26. Vin can not be used with range to.

OK, das Ganze korrigiert, Latches entfernt, simuliert und 2 Minuten 
später:
1
-- Number of Slices  23
2
-- Number of 4 input LUTs  42
3
-- S3AN 11.503ns
4
   process (Vin, Offset) 
5
   variable my_shift : integer;
6
   variable to_much : integer;
7
   variable dout    : unsigned(Vout'range);  
8
   begin
9
      my_shift := to_integer(unsigned(Offset));
10
  
11
      Vout <= (others => '0'); --- sonst gibt das hier boese Latches!!!!
12
      if my_shift < 9 then
13
         Vout(7+my_shift downto 0 + my_shift) <= Vin;
14
      else
15
         to_much := my_shift-8;
16
         Vout(7+(my_shift-to_much) downto my_shift) <= Vin(7-to_much downto 0);
17
         Vout(7-(my_shift-to_much) downto 0)        <= Vin( 7 downto 7-to_much);
18
      end if;
19
   end process;
auch hier findet der Synthesizer eine sehr effiziente Lösung, allerdings 
ist die Multiplizierer-Geschichte eigentlich unschlagbar...

BTW:
> wenn es "ringsrum" gehen soll
Das tut es trotzdem nicht, ich suche jetzt aber den Fehler nicht...

von Ütze (Gast)


Angehängte Dateien:

Lesenswert?

Lothar Miller schrieb:
> Ütze schrieb:
>> dout(0 + my_shift to 7 + my_shift)
> Warum immer diese verkehrte Bitreihenfolge?
> Das gibt doch eh' nur Fehler:

also bei mir nicht, der Unterschied ist doch nur "little/big-endian"
aber war noch n logischer Fehler drin, weswegen "ringsrum" nicht ging, 
die variablen statt signalen sind zwecks latches sicher besser, nu 
lupts

1
entity shifter is
2
Port (
3
acht_bit_invector : in std_logic_vector(0 to 7);
4
shift_vector : in std_logic_vector(0 to 3);
5
out_vector : out std_logic_vector(0 to 15)
6
);
7
end shifter;
8
9
architecture Behavioral of shifter is
10
11
signal dout : unsigned(out_vector'range):= (others => '0');
12
  
13
begin 
14
  process(acht_bit_invector,shift_vector)
15
  variable my_shift : integer := 0;
16
  variable to_much : integer := 0;
17
  begin
18
  dout<=(others => '0');
19
  my_shift:=to_integer(unsigned(shift_vector));
20
  if my_shift < 9 then
21
  dout(0 + my_shift to 7 + my_shift)<=unsigned(acht_bit_invector);
22
  else
23
  to_much:=my_shift-8;
24
  dout(my_shift to 7 + (my_shift-to_much)) <= unsigned(acht_bit_invector(0 to 7-to_much));
25
  dout(0 to to_much)<= unsigned(acht_bit_invector( 7-to_much to 7));
26
  end if; 
27
end process;
28
29
out_vector<=std_logic_vector(dout);
30
end Behavioral;

von Ütze (Gast)


Angehängte Dateien:

Lesenswert?

so passts:
1
entity shifter is
2
Port (
3
acht_bit_invector : in std_logic_vector(0 to 7);
4
shift_vector : in std_logic_vector(0 to 3);
5
out_vector : out std_logic_vector(0 to 15)
6
);
7
end shifter;
8
9
architecture Behavioral of shifter is
10
11
 signal sdout : unsigned(out_vector'range):= (others => '0');
12
  
13
begin 
14
  process(acht_bit_invector,shift_vector)
15
  variable my_shift : integer := 0;
16
  variable to_much : integer := 0;
17
   variable dout : unsigned(out_vector'range):= (others => '0');
18
  begin 
19
  dout:=(others => '0');
20
  my_shift:=to_integer(unsigned(shift_vector));
21
  if my_shift < 9 then
22
  dout(0 + my_shift to 7 + my_shift):=unsigned(acht_bit_invector);
23
  else
24
  to_much:=my_shift-8;
25
  dout(my_shift to 7 + (my_shift-to_much)) := unsigned(acht_bit_invector(0 to 7-to_much));
26
  dout(0 to to_much):= unsigned(acht_bit_invector( 7-to_much to 7));
27
  end if; 
28
  sdout<=dout;
29
end process;
30
31
out_vector<=std_logic_vector(sdout);
32
end Behavioral;

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ütze schrieb:
> acht_bit_invector : in std_logic_vector(0 to 7);
So definiert ehrlich gesagt niemand Vektoren... :-/
Für mich ist das höchstwertige Bit immer das mit dem höchsten Index und 
beim Lesen das Linke (so wie im Dezimalsystem der Tausender links vom 
Zehner ist)...

> der Unterschied ist doch nur "little/big-endian"
Nein.
Mal davon abgesehen, dass little- und big-endian ganz was anderes ist, 
ist der Unterschied viel tiefgehender...
Ich verwende sowas auch mal ausnahmsweise zum Umdrehen der 
Bitreihenfolge, wenn ich keine for-Schleife machen will (in der unteren 
Hälfte):
http://www.lothar-miller.de/s9y/categories/50-RC-5

Aber welchen Grund hast du, die Vektorwertigkeit dauernd so zu 
definieren?

> die variablen statt signalen sind zwecks latches sicher besser
Die Latches kommen von woanders her...  :-/

von Duke Scarring (Gast)


Lesenswert?

Lothar Miller schrieb:
>> acht_bit_invector : in std_logic_vector(0 to 7);
> So definiert ehrlich gesagt niemand Vektoren... :-/
Doch, leider. Xilinx beim Microblaze :-(
Wahrscheinlich war da grad der Praktikant am Werk...

Duke

von Ütze (Gast)


Lesenswert?

Lothar Miller schrieb:
> Ütze schrieb:
>> acht_bit_invector : in std_logic_vector(0 to 7);
> So definiert ehrlich gesagt niemand Vektoren... :-/

Wenn man im xps mit dem Wizzard einen Peripheral Core exportiert wird 
unter anderem das generiert:
1
entity user_logic is
2
  generic
3
  (
4
    -- ADD USER GENERICS BELOW THIS LINE ---------------
5
    --USER generics added here
6
    -- ADD USER GENERICS ABOVE THIS LINE ---------------
7
8
    -- DO NOT EDIT BELOW THIS LINE ---------------------
9
    -- Bus protocol parameters, do not add to or delete
10
    C_SLV_DWIDTH                   : integer              := 32;
11
    C_NUM_REG                      : integer              := 1
12
    -- DO NOT EDIT ABOVE THIS LINE ---------------------
13
  );
14
  port
15
  (
16
    -- ADD USER PORTS BELOW THIS LINE ------------------
17
    --USER ports added here
18
    -- ADD USER PORTS ABOVE THIS LINE ------------------
19
20
    -- DO NOT EDIT BELOW THIS LINE ---------------------
21
    -- Bus protocol ports, do not add to or delete
22
    Bus2IP_Clk                     : in  std_logic;
23
    Bus2IP_Reset                   : in  std_logic;
24
    Bus2IP_Data                    : in  std_logic_vector(0 to C_SLV_DWIDTH-1);
25
    Bus2IP_BE                      : in  std_logic_vector(0 to C_SLV_DWIDTH/8-1);
26
    Bus2IP_RdCE                    : in  std_logic_vector(0 to C_NUM_REG-1);
27
    Bus2IP_WrCE                    : in  std_logic_vector(0 to C_NUM_REG-1);
28
    IP2Bus_Data                    : out std_logic_vector(0 to C_SLV_DWIDTH-1);
29
    IP2Bus_RdAck                   : out std_logic;
30
    IP2Bus_WrAck                   : out std_logic;
31
    IP2Bus_Error                   : out std_logic
32
    -- DO NOT EDIT ABOVE THIS LINE ---------------------
33
  );


> Für mich ist das höchstwertige Bit immer das mit dem höchsten Index und
> beim Lesen das Linke (so wie im Dezimalsystem der Tausender links vom
> Zehner ist)...
>
>> der Unterschied ist doch nur "little/big-endian"
> Nein.

glaube mich zu erinnern in dem "VHDL-Synthese"-Buch gelesen zu haben das 
der zuerstgenannten Zahl das am weitest links stehende Element 
zugeordnet wird. So ziemlich genau in den Worten.

> Mal davon abgesehen, dass little- und big-endian ganz was anderes ist,

Byte nicht Bit order deswegen die Anführungszeichen

> ist der Unterschied viel tiefgehender...
> Ich verwende sowas auch mal ausnahmsweise zum Umdrehen der
> Bitreihenfolge, wenn ich keine for-Schleife machen will (in der unteren
> Hälfte):
> http://www.lothar-miller.de/s9y/categories/50-RC-5
>
> Aber welchen Grund hast du, die Vektorwertigkeit dauernd so zu
> definieren?

weil ich hauptsächlich an solchen Periphären Cores arbeite

>> die variablen statt signalen sind zwecks latches sicher besser
> Die Latches kommen von woanders her...  :-/
bitte genauer, da fehlt mir noch Erfahrung: ich bekomme bei der Synthese 
mit Signalen Warnungen wegen Einfügen von Latches bei to_much( was ich 
wegen unvollständiger Zuweisung nachvollziehen kann), mit Variablen gibt 
es keine Warnung -> daher meine Annahme

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ütze schrieb:
> mit Variablen gibt es keine Warnung
Dort erkennt die Synthese, dass dieser Wert im nicht verwendeten Zweig 
unnötig ist, und macht die Variable daher nicht speichernd...
Eine Variable ist nur dann speichernd, wenn sie vor der ersten Zuweisung 
gelesen wird. Und das ist bei dir nicht der Fall.

> ich bekomme bei der Synthese mit Signalen Warnungen
> wegen Einfügen von Latches bei to_much
Du meinst also, wenn to_much ein Signal ist?
BTW: falls das so wäre, müsste es auf jeden Fall auch in die 
Sensitivliste, sonst ist die Simulation falsch...

Duke Scarring schrieb:
>> So definiert ehrlich gesagt niemand Vektoren... :-/
> Doch, leider. Xilinx beim Microblaze :-(
Es gibt Sachen, die sind zum Glück unnötig wie ein Kropf.
Und der Microblaze ist eine davon...

von Marcus H. (mharnisch) Benutzerseite


Lesenswert?

Lothar Miller schrieb:
> -- Number of Slices 8
> -- Number of 4 input LUTs 15
> -- S3AN 12.005ns
>    process (Vin, Offset)
>    variable m       : integer;
>    variable din_u   : unsigned(Vout'range);
>    begin
>       case Offset is
>          [...]
>          when "1110" => m := 16348;
>          when others => m := 32786;
>       end case;
>       din_u := resize(unsigned(Vin), Vout'length);
>       din_u := din_u * m;
>       Vout    <= std_logic_vector(din_u);
>    end process;

Vielleicht verbessert sich das Ergebnis ja noch, wenn Du die beiden 
Zahlendreher im case entfernst.

Gruß
Marcus

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Marcus Harnisch schrieb:
> Vielleicht verbessert sich das Ergebnis ja noch, wenn Du die beiden
> Zahlendreher im case entfernst.
Ups..  :-o
Glaube ich zwar nicht, probiers trotzdem aus...

Buäääh...  :-(
Alles ist schlechter geworden:
1
-- Number of Slices 9
2
-- Number of 4 input LUTs 16
3
-- S3AN 12.047ns
4
:
5
         when "1110" => m := 16384;
6
         when others => m := 32768;
7
:

von Ütze (Gast)


Lesenswert?

Lothar Miller schrieb:
> Es gibt Sachen, die sind zum Glück unnötig wie ein Kropf.
> Und der Microblaze ist eine davon..

veto,z.B. lassen sich protokollbasierte Kommunikationen ( z.B. mit PC) 
wesentlich leichter (zeitsparender) in c/c++ implementieren als in vhdl

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ütze schrieb:
> veto,z.B. lassen sich protokollbasierte Kommunikationen ( z.B. mit PC)
> wesentlich leichter (zeitsparender) in c/c++ implementieren als in vhdl
Man kann aber doch nicht das Fehlen eines geeigneten 
Kommunikationsprozessors und dessen anschliessende aufwendige 
Implementation als Vorteil verkaufen...

von Ütze (Gast)


Lesenswert?

Nein, da hab ich mich missverständlich ausgedrückt: Ich meine nicht 
etabliert Schnittstellen(meinetwegen USB,Ethernet) im Microblaze 
nachzubilden, sondern darauf aufsätzende (eigene) Protokolle darüber zu 
sprechen. Microblaze empfängt Anfragen, ereugt Header und konfiguriert 
DMA (gib mir nur jeden 5. Wert oder jeden 10.). Klar geht das alles auch 
in vhdl doch ungleich aufwendiger

von Ütze (Gast)


Lesenswert?

edit: "aufsätzende" ist sehr schön :-D

von Oliver P. (Firma: UAS Merseburg) (olipunk)


Lesenswert?

Lothar Miller schrieb:
> Es gibt Sachen, die sind zum Glück unnötig wie ein Kropf.
> Und der Microblaze ist eine davon...

<OT>
Da verstehe ich Dich nicht. Der Microblaze ist doch perfekt zum Testen 
von eigener Hardware (IP) in einer komplexen OS (z.B. Linux) Umgebung. 
Natürlich macht es nicht immer Sinn, einen Prozessor zu verwenden, aber 
wenn man für solche Aufgaben erstmal ein ein PLB Design entwerfen muss, 
um einen ARM an die FPGA zu bekommen ... . Ohne böse klingen zu wollen: 
das hört sich ein bisschen an wie die "ewig Gestrigen", die ihre GUI in 
C machen und das ganze ".NET Geraffel" verurteilen, ohne einen Blick auf 
die Entwicklungs-Ersparnis in MM ( < n^2 und n ist groß) im Sinne des 
RAD zu werfen. Für den Hobby-Frickler und gleichzeitigen 
Open-Source-Fetischisten mag das reichen; im kommerziellen Umfeld würde 
man dafür gehenkt werden. Und das zu recht!
<OT>

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Oliver Punk schrieb:
> wenn man für solche Aufgaben erstmal ein ein PLB Design entwerfen muss,
> um einen ARM an die FPGA zu bekommen
Wie wäre es mit "Kaufen"?
Seit wann ist jetzt der Microblaze eine ARM-Architektur?

Ich schließe das FPGA einfach mit PCI(e) an einen PC an und fertig. Da 
bekomme ich für die Entwicklung für kleines Geld Rechenleistung satt und 
kann alle Tools incl. Entwicklungsumgebung direkt auf dem Zielsystem 
laufen lassen...

Da freut man sich, wenn der Microblaze mit 100MHz (von mir aus auch 200) 
läuft, das war auf dem PC Technik von vor 20 Jahren...
Ein Prozessor auf dem FPGA ist Verschwendung von Silizium.
Nur das ist meine Aussage...   ;-)

von Thomas R. (Firma: abaxor engineering) (abaxor)


Lesenswert?

Lothar Miller schrieb:

> Es gibt Sachen, die sind zum Glück unnötig wie ein Kropf.
> Und der Microblaze ist eine davon...

Da gehe ich nicht mit. Es gibt schon Probleme, da benötigt man einen 
Microblaze oder anders herum, andere Lösungen (FPGA + externer 
Prozessor) sind deutlich aufwändiger.
Folgende Aufgabenstellung

Ein 12 Bit ADC erfasst Daten mit 250 MS/s. Ein Fenster von bis zu 2 ms 
muss abgespeichert werden, d.h. man braucht für 2ms eine 
Speicherbandbreite von 500MB/s. Die Menge passt nicht in den FPGA, d.h. 
man braucht externen RAM. Die Daten aus dem externen RAM müssen dann per 
UDP an einen PC verschickt werden. Für die Erstellung der Datagramme 
benötigt man einen Prozessor. Es gibt noch zwei weitere Speicherbereiche 
über die der Microblaze mit der Logik für die Signalverarbeitung 
kommuniziert.

Wie soll man es besser mit einem Prozessor und FPGA hin bekommen?

Das Ganze wird in einem Virtex 5 LXT umgesetzt. Ein V5 FXT (der mit PPC) 
ist deutlich teurer und benötigt deutlich mehr Strom, letzteres spielt 
eine besondere Rolle. Der Platz auf der Leiterplatte ist auch begrenzt.

Tom

von Marcus H. (mharnisch) Benutzerseite


Lesenswert?

Könnte ein Moderator bitte mal die ganzen off-topic Beiträge 
verschieben, oder löschen?

Danke
Marcus

von D. I. (Gast)


Lesenswert?

Thomas Reinemann schrieb:
> Ein 12 Bit ADC erfasst Daten mit 250 MS/s. Ein Fenster von bis zu 2 ms
> muss abgespeichert werden, d.h. man braucht für 2ms eine
> Speicherbandbreite von 500MB/s. Die Menge passt nicht in den FPGA, d.h.
> man braucht externen RAM. Die Daten aus dem externen RAM müssen dann per
> UDP an einen PC verschickt werden. Für die Erstellung der Datagramme
> benötigt man einen Prozessor. Es gibt noch zwei weitere Speicherbereiche
> über die der Microblaze mit der Logik für die Signalverarbeitung
> kommuniziert.

Eine einseitige UDP Kommunikation geht auch locker ohne Prozessor, man 
muss nur gültige Frames erzeugen. Du hast auch nicht gesagt wie schnell 
diese Daten an den PC geschickt werden müssen.
Und der Rest hängt nur davon ab ob der Speicher das mitmacht.

von Thomas R. (Firma: abaxor engineering) (abaxor)


Lesenswert?

D. I. schrieb:
> Eine einseitige UDP Kommunikation geht auch locker ohne Prozessor, man
> muss nur gültige Frames erzeugen. Du hast auch nicht gesagt wie schnell
> diese Daten an den PC geschickt werden müssen.
> Und der Rest hängt nur davon ab ob der Speicher das mitmacht.

Ja es wird beidseitig kommuniziert, es werden auch noch einige 
Berechnung im Prozessor gemacht. Die gesamte Spezifikation ist 50 Seiten 
lang.

Tom

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.