Forum Discussion
matrix array in vhdl
Dear all,
I have 4x4 matrix and I want to read this matrix row by row on each clock cycle. For example, row1 is read in cycle1, row2 is read in cycle2 and so on. Can anyone give idea how to write this code? Many thanks22 Replies
- Altera_Forum
Honored Contributor
when trying to compile it, it needs to map each bit to a pin. You need 5185 pins, which are not available. Because you have chosen to use integer, and not limit the size of the integer, each value is 32 bits. You could change this to 8 bits to divide the number of pins required by 4, but this is still too many.
Is this just a temporary solution, or do you expect to actually send the data for this matrix from somewhere? you would neve send an entire matrix like this to an FPGA from a CPU - a CPU simply does not have 5000 IO pins. You'd usually send it via some other transport mechanism. So, the options you have: 1. Reduce the scope of integer to fewer bits. You can do this by saying: type matrix_t is array(0 to 8, 0 to 8) of integer range 0 to 255; --8 bits per integer 2. Specify that all IO pins are virtual via the assignments editor. This is just a temporary solution to allow you to compile the design. It is not a final solution. 3. Install some other mechanism to transport the data into your FPGA that will fit. And finally - Please Please Please go and read up about digital design. - Altera_Forum
Honored Contributor
Dear FvM,
"better use signed or unsigned types for the top entitie's port", can you explain on this? Thanks for reply. - Altera_Forum
Honored Contributor
That's the problem when using abstract data types like integer. You can use them in hardware design, but you should know what you are doing. By default, integer is a signed 32 bit quantity, thus each integer array element is infered as signed(31 downto 0). It's easy to calculate the amount of port bits needed to represent the array.
To learn about reasonable usage of the integer type in hardware designs, you can review the Quartus VHDL binary counter template. Generally you need to constrain it by setting a range in the type definition. My personal opinion is, that you should better use signed or unsigned types for the top entitie's port. Altough the port is represented by a bit_vector, you can't access individual bits without type casting the signal, because integer abstracts from it. Somewhat confusing, I think. Integers are however appropriate for internal signals. - Altera_Forum
Honored Contributor
This is my transpose code:
package newtype is type matrix_t is array (0 to 8, 0 to 8) of integer; end newtype; library ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; use work.newtype.all; entity transpose is port(input: in matrix_t; clk: in std_logic; transposed_matrix: out matrix_t); end transpose; architecture arch of transpose is function change (matrix: matrix_t) return matrix_t is variable ret: matrix_t; begin for i in matrix'range(1) loop for j in matrix'range(2) loop ret (j,i):= matrix (i,j); end loop; end loop; return ret; end function; begin transposed_matrix <= change (input); end arch; The same error with my previous code that not use a function is occurs; Error: Design requires 5185 I/O resources -- too many to fit in 1264 available in the selected device or any device in the device family. Why the same error still occurs? I confuse now, need your helps. Many thanks. - Altera_Forum
Honored Contributor
Dear Tricky,
I will study the code function first before write the transpose code for my system. By the way, many thanks for your help and advice. I appreciate it. Any problem I will let you know later. Thanks for reply. - Altera_Forum
Honored Contributor
you can transpose the entire thing yes. You just need to write a transpose function, like this:
This is not like softwear where you have to move everything around a memory - all you are doing is shifting all the "wires" around, so the data doesnt actually move, the output just connects to different inputs. There is no resource cost involved - its free. one big but: I think we've spoken before on this very subject, and it was clear then you had little understanding of digital logic. That doesnt seem to have changed. I recommend you go and learn about digital logic before you get any further with this. Otherwise you are going to hit some brick walls very quickly and you will not understand why.function transpose( matrix : matrix_t ) return matrix_t is variable ret : matrix_t; begin for i in matrix'range(1) loop for j in matrix'range(2) loop ret(j, i) := matrix(i,j); end loop; end loop; return ret; end function; ..... transposed_matrix <= transpose(input); - Altera_Forum
Honored Contributor
Dear Tricky,
Did you mean I can transpose the whole matrix directly? Even a big input matrix (8x8 matrix). And what do you mean by doesnt need a clock? Thanks for reply. - Altera_Forum
Honored Contributor
you can do it like that, but there is no need to do it row by row, you can do the whole thing in one go via a function. It doesnt need a clock.
- Altera_Forum
Honored Contributor
Dear Tricky,
Yes, I try to do a matrix transpose. Before this I write directly the transpose code but then when I compile for 8x8 input matrix an error occur which is the input pin required is to much. So, I try to transpose the matrix row by row. My idea is when the second row is read, the first row will be read out as a column and so on. It is possible Tricky if I do like that? Thanks for reply. - Altera_Forum
Honored Contributor
temp_row contains the row currently. If you run the simulation for 50ns you can see the row selected changing every clock cycle, as per the attached image (shows its working for me).
For your outputs, you will need to add them to the code. It sounds like you're trying to do a matrix transpose - but there is no need to do a transpose synchronously - because all you are doing is re-wiring the array, it doesnt cost any resources, and doesnt need to be synchronous.