From 123808e457159a80b76cf35dc3d3134ff5ace23e Mon Sep 17 00:00:00 2001 From: Jan Michel Date: Thu, 21 Jan 2016 15:29:08 +0100 Subject: [PATCH] Adding PWM generator incl. temperature compensation for Dirich --- code/pwm_generator.vhd | 104 ++++++++++++++++++++++++++++++++++++++ dirich/diamond/dirich.ldf | 17 ++++--- dirich/dirich.prj | 22 ++++---- dirich/dirich.vhd | 37 ++++++++++---- 4 files changed, 151 insertions(+), 29 deletions(-) create mode 100644 code/pwm_generator.vhd diff --git a/code/pwm_generator.vhd b/code/pwm_generator.vhd new file mode 100644 index 0000000..463c0af --- /dev/null +++ b/code/pwm_generator.vhd @@ -0,0 +1,104 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.numeric_std.all; + +library work; +use work.trb_net_std.all; + + +entity pwm_generator is + generic( + CHANNELS : integer range 1 to 127 := 32 + ); + port( + CLK : in std_logic; + + BUS_RX : in CTRLBUS_RX; + BUS_TX : out CTRLBUS_TX; + TEMP_IN : in std_logic_vector(11 downto 0); + + PWM : out std_logic_vector(CHANNELS-1 downto 0) + + ); +end entity; + + + +architecture pwm_arch of pwm_generator is + +type ram_t is array(0 to CHANNELS-1) of unsigned(15 downto 0); +signal set : ram_t := (others => x"87C1"); +signal set_tmp : ram_t; +signal compensate : signed(15 downto 0) := (others => '0'); +signal set_compensate : signed(15 downto 0) := (others => '0'); +signal temp_i : signed(11 downto 0); +signal temp_calc_i : signed(27 downto 0); + +type cnt_t is array(0 to CHANNELS-1) of unsigned(16 downto 0); +signal cnt : cnt_t := (others => (others => '0')); + +signal last_flag : std_logic_vector(CHANNELS-1 downto 0) := (others => '0'); +signal flag : std_logic_vector(CHANNELS-1 downto 0) := (others => '0'); +signal pwm_i : std_logic_vector(CHANNELS-1 downto 0) := (others => '0'); +signal ci : integer range 0 to CHANNELS-1; + +begin + +PROC_MEM : process + variable chan : integer range 0 to 255; +begin + wait until rising_edge(CLK); + chan := to_integer(unsigned(BUS_RX.addr(7 downto 0))); + BUS_TX.unknown <= '0'; + BUS_TX.ack <= '0'; + BUS_TX.nack <= '0'; + BUS_TX.data <= (others => '0'); + + if BUS_RX.write = '1' then + if chan < CHANNELS then + set(chan) <= unsigned(BUS_RX.data(15 downto 0)); + BUS_TX.ack <= '1'; + elsif chan = 16#80# then + set_compensate <= signed(BUS_RX.data(15 downto 0)); + BUS_TX.ack <= '1'; + else + BUS_TX.unknown <= '1'; + end if; + elsif BUS_RX.read = '1' then + if chan < CHANNELS then + BUS_TX.data(15 downto 0) <= std_logic_vector(set(chan)); + BUS_TX.ack <= '1'; + elsif chan = 16#80# then + BUS_TX.data(15 downto 0) <= std_logic_vector(set_compensate); + BUS_TX.ack <= '1'; + else + BUS_TX.unknown <= '1'; + end if; + end if; +end process; + + +GEN_REAL_VALUES : process begin + wait until rising_edge(CLK); + + set_tmp(ci) <= unsigned(signed(set(ci)) + compensate); + ci <= ci + 1; + + temp_i <= TEMP_IN; + temp_calc_i <= signed(temp_i) * signed(set_compensate); + compensate <= temp_calc_i(27 downto 12); +end process; + + + +gen_channels : for i in 0 to 15 generate + flag(i) <= cnt(i)(16); + last_flag(i) <= flag(i) when rising_edge(CLK); + pwm_i(i) <= (last_flag(i) xor flag(i)) when rising_edge(CLK); + cnt(i) <= cnt(i) + resize(set_tmp(i),17) when rising_edge(CLK); +end generate; + + +PWM <= pwm_i; + +end architecture; \ No newline at end of file diff --git a/dirich/diamond/dirich.ldf b/dirich/diamond/dirich.ldf index 2838e2d..8707113 100644 --- a/dirich/diamond/dirich.ldf +++ b/dirich/diamond/dirich.ldf @@ -2,7 +2,7 @@ - + @@ -96,12 +96,6 @@ - - - - - - @@ -291,6 +285,15 @@ + + + + + + + + + diff --git a/dirich/dirich.prj b/dirich/dirich.prj index 64f6883..12ac83c 100644 --- a/dirich/dirich.prj +++ b/dirich/dirich.prj @@ -65,7 +65,8 @@ add_file -vhdl -lib work "../cores/pll_240_100/pll_240_100.vhd" add_file -vhdl -lib work "../code/clock_reset_handler.vhd" add_file -vhdl -lib work "../../trbnet/special/trb_net_reset_handler.vhd" add_file -vhdl -lib work "../../trbnet/special/spi_flash_and_fpga_reload_record.vhd" -add_file -vhdl -lib work "..//code/sedcheck.vhd" +add_file -vhdl -lib work "../code/sedcheck.vhd" +add_file -vhdl -lib work "../code/pwm_generator.vhd" #Fifos @@ -92,7 +93,7 @@ add_file -vhdl -lib work "../../trbnet/lattice/ecp2m/fifo/fifo_var_oreg.vhd" add_file -vhdl -lib work "../../trbnet/lattice/ecp5/FIFO/fifo_19x16_obuf/fifo_19x16_obuf.vhd" add_file -vhdl -lib work "../../trbnet/lattice/ecp5/FIFO/lattice_ecp5_fifo_16x16_dualport/lattice_ecp5_fifo_16x16_dualport.vhd" add_file -vhdl -lib work "../../trbnet/lattice/ecp5/FIFO/lattice_ecp5_fifo_18x16_dualport/lattice_ecp5_fifo_18x16_dualport.vhd" -add_file -vhdl -lib work "../../trbnet/lattice/ecp5/FIFO/lattice_ecp5_fifo_18x16_dualport_oreg/lattice_ecp5_fifo_18x16_dualport_oreg.vhd" +add_file -vhdl -lib work "../../trbnet/lattice/ecp5/FIFO/lattice_ecp3_fifo_18x16_dualport_oreg/lattice_ecp3_fifo_18x16_dualport_oreg.vhd" #Flash & Reload, Tools @@ -122,15 +123,14 @@ add_file -vhdl -lib work "../../trbnet/trb_net16_addresses.vhd" #Media interface add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/med_sync_define.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/rx_control.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/tx_control.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/rx_reset_fsm.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/tx_reset_fsm.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/sci_reader.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/med_sync_control.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/ecp5/serdes_sync_0/serdes_sync_0.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/ecp3_sfp/serdes_sync_3.vhd" -# add_file -vhdl -lib work "../../trbnet/media_interfaces/med_ecp3_sfp_sync.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/rx_control.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/tx_control.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/rx_reset_fsm.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/tx_reset_fsm.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/sci_reader.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/sync/med_sync_control.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/ecp5/serdes_sync_0/serdes_sync_0.vhd" +add_file -vhdl -lib work "../../trbnet/media_interfaces/med_ecp5_sfp_sync.vhd" #TrbNet Endpoint add_file -vhdl -lib work "../../trbnet/trb_net16_term_buf.vhd" diff --git a/dirich/dirich.vhd b/dirich/dirich.vhd index 7d8e030..f1a182c 100644 --- a/dirich/dirich.vhd +++ b/dirich/dirich.vhd @@ -8,7 +8,6 @@ use work.config.all; use work.trb_net_std.all; use work.trb_net_components.all; use work.trb3_components.all; -use work.version.all; use work.med_sync_define.all; entity dirich is @@ -18,10 +17,10 @@ entity dirich is CLOCK_CAL_IN : in std_logic; --on-board calibration oscillator INPUT : in std_logic_vector(32 downto 1); + PWM : out std_logic_vector(32 downto 1); --Additional IO - SIG : inout std_logic_vector( 8 downto 1); - CTRL : inout std_logic_vector( 4 downto 2); + COM : inout std_logic_vector( 6 downto 1); --LED LED_GREEN : out std_logic; LED_YELLOW : out std_logic; @@ -82,8 +81,8 @@ architecture dirich_arch of dirich is signal readout_rx : READOUT_RX; signal readout_tx : readout_tx_array_t(0 to 0); - signal ctrlbus_rx, bussci_rx, bustools_rx, bustc_rx, bus_master_out : CTRLBUS_RX; - signal ctrlbus_tx, bussci_tx, bustools_tx, bustc_tx, bus_master_in : CTRLBUS_TX; + signal ctrlbus_tx, bussci_tx, bustools_tx, bustc_tx, busthresh_tx, bus_master_in : CTRLBUS_TX; + signal ctrlbus_rx, bussci_rx, bustools_rx, bustc_rx, busthresh_rx, bus_master_out : CTRLBUS_RX; signal common_stat_reg : std_logic_vector(std_COMSTATREG*32-1 downto 0) := (others => '0'); signal common_ctrl_reg : std_logic_vector(std_COMCTRLREG*32-1 downto 0); @@ -94,6 +93,7 @@ architecture dirich_arch of dirich is signal spi_cs, spi_mosi, spi_miso, spi_clk : std_logic_vector(15 downto 0); + signal pwm_i : std_logic_vector(31 downto 0); signal timer : TIMERS; signal lcd_data : std_logic_vector(511 downto 0); signal hdr_io : std_logic_vector(9 downto 0); @@ -163,8 +163,8 @@ THE_CLOCK_RESET : entity work.clock_reset_handler -- CTRL_DEBUG => open -- ); -CTRL(2) <= '0' when link_stat_out = '1' else 'Z'; -link_stat_in <= CTRL(2); +COM(2) <= '0' when link_stat_out = '1' else 'Z'; +link_stat_in <= COM(1); --------------------------------------------------------------------------- -- Endpoint @@ -222,9 +222,9 @@ THE_ENDPOINT : entity work.trb_net16_endpoint_hades_full_handler_record THE_BUS_HANDLER : entity work.trb_net16_regio_bus_handler_record generic map( - PORT_NUMBER => 3, - PORT_ADDRESSES => (0 => x"d000", 1 => x"b000", 2 => x"d300", others => x"0000"), - PORT_ADDR_MASK => (0 => 12, 1 => 9, 2 => 1, others => 0), + PORT_NUMBER => 4, + PORT_ADDRESSES => (0 => x"d000", 1 => x"b000", 2 => x"d300", 3 => x"a000", others => x"0000"), + PORT_ADDR_MASK => (0 => 12, 1 => 9, 2 => 1, 3 => 8, others => 0), PORT_MASK_ENABLE => 1 ) port map( @@ -237,9 +237,11 @@ THE_ENDPOINT : entity work.trb_net16_endpoint_hades_full_handler_record BUS_RX(0) => bustools_rx, --Flash, SPI, UART, ADC, SED BUS_RX(1) => bussci_rx, --SCI Serdes BUS_RX(2) => bustc_rx, --Clock switch + BUS_RX(3) => busthresh_rx, BUS_TX(0) => bustools_tx, BUS_TX(1) => bussci_tx, BUS_TX(2) => bustc_tx, + BUS_TX(3) => busthresh_tx, STAT_DEBUG => open ); @@ -276,7 +278,7 @@ THE_ENDPOINT : entity work.trb_net16_endpoint_hades_full_handler_record --Trigger & Monitor MONITOR_INPUTS => INPUT, TRIG_GEN_INPUTS => INPUT, - TRIG_GEN_OUTPUTS => CTRL(4 downto 3), + TRIG_GEN_OUTPUTS => COM(4 downto 3), --SED SED_ERROR_OUT => sed_error_i, --Slowcontrol @@ -289,6 +291,19 @@ THE_ENDPOINT : entity work.trb_net16_endpoint_hades_full_handler_record DEBUG_OUT => debug_tools ); +--------------------------------------------------------------------------- +-- PWM / Thresh +--------------------------------------------------------------------------- + +THE_PWM_GEN : entity work.pwm_generator + port map( + CLK => clk_sys, + BUS_RX => busthresh_rx, + BUS_TX => busthresh_tx, + TEMP_IN => timer.temperature, + PWM => pwm_i + ); + --------------------------------------------------------------------------- -- 2.43.0