Выходной регистр модуля Verilog управляет выходным регистром?

Итак, я пытаюсь создать экземпляр модуля внутри модуля. Корневой модуль имеет выходные порты, которые управляют выходными контактами, и я хочу, чтобы внутренний модуль управлял этими портами напрямую, но я все равно не могу заставить его работать.

/*
A root module for the 005_135-scanner_mainboard_revA_sch-pcb. Can be used as a test bench for testing peripheral devices but has been designed to be the master root module for the final code.
All IO is included and reset pins on peripheral devices driven active reset with data lines driven to an appropriate value (located in the ‘initial block’).
George Waller. 09/08/15.
*/

module root_module( ft_reset, ft_usb_prsnt, ft_bus_pwrsav, ft_bus_oe,             ft_bus_clkout, ft_bus_siwu, ft_bus_wr, ft_bus_rd, ft_bus_rxf, ft_bus_txe, ft_bus_d,
                        mtr_fault, mtr_config, mtr_m1, mtr_m0, mtr_rst, mtr_out_en, mtr_step, mtr_dir,
                        ccd_driver_oe, ccd_p1, ccd_p2, ccd_cp, ccd_rs, ccd_sh,
                        dac1_sdin, dac1_sclk, dac1_sync, dac2_sdin, dac2_sclk, dac2_sync,
                        adc_pwrdn, adc_encode, adc_d,
                        fpga_reset,
                        clk,
                        gpio,
                        led_ctrl,
                        leds);

//Input declarations
input wire          ft_usb_prsnt, ft_bus_clkout, ft_bus_rxf, ft_bus_txe,
                        mtr_fault, 
                        fpga_reset,
                        clk;

input wire [7:0]    adc_d;

//Output declarations
output reg          ft_reset, ft_bus_pwrsav, ft_bus_oe, ft_bus_siwu, ft_bus_wr, ft_bus_rd,
                        mtr_config, mtr_m1, mtr_m0, mtr_rst, mtr_out_en, mtr_step, mtr_dir,
                        ccd_driver_oe, ccd_p1, ccd_p2, ccd_cp, ccd_rs, ccd_sh,
                        adc_pwrdn, adc_encode,
                        led_ctrl;

output reg          dac1_sdin, dac1_sclk, dac1_sync, dac2_sdin, dac2_sclk, dac2_sync;

output reg [7:0]    leds;

//Input output declarations.
inout reg  [7:0]    ft_bus_d;

inout reg [16:0]    gpio;

//Variables go here     

integer count, count1, state, pixel_n, line_n, t_int;   
integer data[8];

reg en;

//Initial values on start up.
initial
begin
    //IO initial setup values.
    ft_reset = 1; ft_bus_pwrsav = 1; ft_bus_oe = 1; ft_bus_siwu = 0; ft_bus_wr = 1; ft_bus_rd = 1;  //NEED TO APPLY REAL VAULES!!!
    mtr_config = 1; mtr_m1 = 1; mtr_m0 = 1; mtr_rst = 1; mtr_out_en = 1; mtr_step = 0; mtr_dir = 0;
    ccd_driver_oe = 1; ccd_p1 = 0; ccd_p2 = 0; ccd_cp = 0; ccd_rs = 0; ccd_sh = 0;
    dac1_sdin = 0; dac1_sclk = 0; dac1_sync = 0; dac2_sdin = 0; dac2_sclk = 0; dac2_sync = 0;
    adc_pwrdn = 0; adc_encode = 0;
    led_ctrl = 0;
    leds = 0;
    gpio = 0;
    ft_bus_d = 0;

    //Variables setup values.   
    count = 0;
    count1 = 0;
    state = 0;
    pixel_n = 0;
    line_n = 0;
    t_int = 10000;  //t_int = integration time. integration time (seconds) =                  t_int * 10x10^-9. 
end //End initial

//Some other code goes here.
always @(posedge ft_bus_clkout)
begin
    if(count == 50000000)
        begin
            en <= 1;
            count = 0;
        end
        else
        begin
            en <= 0;
            count = count + 1;
    end 
end //End always

AD5601_module AD5601(.en(en), .clk(clk), .data(127),.sdout(dac1_sdin),
.sclk(dac1_sclk), .sync(dac1_sync));    

endmodule   //End module. 

И внутренний модуль:

module AD5601_module(en, clk, data, sdout, sclk, sync);

        input wire          clk;
        input wire          en;
        input wire [7:0]    data;

        output reg          sdout, sclk, sync;

        integer sclk_count;
        integer data_state;
        integer delay_counter;
        integer pd[2];

        initial
        begin
            sclk_count = 0;
            data_state = 99;
            delay_counter = 0;
            pd[0] = 0;
            pd[1] = 0;

            sdout = 0;
            sclk = 0;
            sync = 1;
        end

        always @ (posedge en)
        begin
            if(data_state == 99)data_state <= 0;
        end


        always @ (posedge clk)
        begin
            if(sclk_count == 49)
            begin
                sclk_count = 0;
                sclk = ~sclk;
            end
            else sclk_count = sclk_count + 1;

        end

        always @ (posedge sclk)
        begin
            case(data_state)
                0:  begin
                    sync = 0;
                    sdout <= pd[1];
                    data_state <= 1;
                end

                1:  begin
                    sdout <= pd[0];
                    data_state <= 2;
                end             

                2:  begin
                    sdout <= data[7];
                    data_state <= 3;
                end             

                3:  begin
                    sdout <= data[6];
                    data_state <= 4;
                end             

                4:  begin
                    sdout <= data[5];
                    data_state <= 5;
                end             

                5:  begin
                    sdout <= data[4];
                    data_state <= 6;
                end             

                6:  begin
                    sdout <= data[3];
                    data_state <= 7;
                end             

                7:  begin
                    sdout <= data[2];
                    data_state <= 8;
                end             
                8:  begin
                    sdout <= data[1];
                    data_state <= 9;
                end             

                10:begin
                    sdout <= 0;
                    if(delay_counter == 6)                          
                    begin
                        data_state <= 99;
                        delay_counter <= 0;
                        sync = 1;
                    end
                    else delay_counter = delay_counter + 1;
                end             
            endcase
        end
endmodule

Так что с кодом как есть я получаю ошибку

'выходной или входной порт должен быть подключен к структурному сетевому выражению'

.

Если я изменяю выходы в корневом модуле или внутреннем модуле на проводные, я получаю сообщение об ошибке «выражение в левой части должно быть переменного типа».

Так что на данный момент я понятия не имею, как вы вкладываете выходные данные! Некоторая помощь будет оценена по достоинству!

Спасибо


person George Waller    schedule 12.08.2015    source источник
comment
Есть выходы с несколькими драйверами dac1_sdin,dac1_sclk и dac1_sync. подключен в вашем внутреннем модуле.   -  person Emman    schedule 12.08.2015
comment
@Emman Не могли бы вы уточнить для меня? Спасибо.   -  person George Waller    schedule 12.08.2015
comment
как упоминал @toolic, я не вижу смысла в inout, а несколько драйверов следует удалить, см. ссылка   -  person Emman    schedule 12.08.2015
comment
Спасибо за ответ, однако мне нужен ввод для другого модуля, который я разработаю позже. Не могли бы вы рассказать мне немного больше о нескольких драйверах? Я понимаю, что вы имеете в виду, что у меня есть более одного источника, управляющего сигналом, но я не могу определить, где я это сделал.   -  person George Waller    schedule 12.08.2015
comment
Это ошибки, которые я получаю точно: Ошибка (10663): ошибка подключения порта Verilog HDL в root_module.v(87): выходной или входной порт sdout должен быть подключен к структурному сетевому выражению Ошибка (10663): ошибка подключения порта Verilog HDL в root_module.v(87): sclk выходного или входящего порта должен быть подключен к выражению структурной сети. Ошибка (10663): ошибка подключения порта Verilog HDL в root_module.v(87): синхронизация выходного или входного порта должна быть подключена к структурной сети. выражение   -  person George Waller    schedule 12.08.2015
comment
Я только что написал еще один модуль, и у меня точно такая же проблема.   -  person George Waller    schedule 12.08.2015


Ответы (1)


inout порты должны быть типа сети (wire или tri), а не reg. А reg не имеет разрешения конфликтов (при наличии двух и более активных драйверов). inout не следует назначать в процедурном блоке (например, always-блок, initial-блок). Это должен быть простой оператор assign, как показано ниже. Разработчик должен обеспечить наличие только активного драйвера на вводе-выводе в любой момент.

assign io_port_name = driver_enable ? io_out_value : 'bz; // io_out_value should be a flop

Выход должен быть объявлен как output reg только в том случае, если он назначен в процедурном блоке (например, always-блок, initial-блок) в текущем модуле. Все остальные выходные данные должны быть output или output wire (эти идентификаторы синонимичны; первый является неявным, а второй — явным). An должен быть назначен только в пределах одного always. ПЛИС допускают initial блоков, ASIC/IC - нет.

Если SystemVerilog включен, замените output reg на output logic. logic можно использовать для флопов и однонаправленных сетей. logic не рекомендуется для inout; logic, как и reg, не имеет разрешения конфликтов.

Массивы integer data[8]; и integer pd[2]; имеют синтаксис SystemVerilog и несовместимы с Verilog. Либо включите SystemVerilog, либо измените на integer data[0:7]; и integer pd[0:1];
SystemVerilog можно включить для каждого файла, изменив расширение файла с .v на .sv; рекомендуемые. Симуляторы / синтезаторы обычно имеют переключатель, который заставляет все Verilog обрабатываться как SystemVerilog; не рекомендуется, обратитесь к руководству по симулятору/синтезатору, если хотите пойти по этому пути.

person Greg    schedule 12.08.2015