diff --git a/MainController/RAM9X8_PWM.vhd b/MainController/RAM9X8_PWM.vhd new file mode 100644 index 0000000..b72abfa --- /dev/null +++ b/MainController/RAM9X8_PWM.vhd @@ -0,0 +1,208 @@ +entity RAM9X8_PWM is + generic( + REG_ADDR_MODE_CONTROL_UPPER_BYTE : integer := 14; + REG_ADDR_MODE_CONTROL_LOWER_BYTE : integer := 15; + REG_ADDR_MASK_2_UPPER_BYTE : integer := 16; + REG_ADDR_MASK_2_LOWER_BYTE : integer := 17; + REG_ADDR_MASK_1_UPPER_BYTE : integer := 18; + REG_ADDR_MASK_1_LOWER_BYTE : integer := 19; + REG_ADDR_DIRECT_CONTROL_2_UPPER_BYTE : integer := 20; + REG_ADDR_DIRECT_CONTROL_2_LOWER_BYTE : integer := 21; + REG_ADDR_DIRECT_CONTROL_1_UPPER_BYTE : integer := 22; + REG_ADDR_DIRECT_CONTROL_1_LOWER_BYTE : integer := 23; + REG_ADDR_PERIOD_UPPER_BYTE : integer := 24; + REG_ADDR_PERIOD_LOWER_BYTE : integer := 25; + REG_ADDR_DIRECTION_UPPER_BYTE : integer := 26; + REG_ADDR_DIRECTION_LOWER_BYTE : integer := 27; + REG_ADDR_CHANNEL_UPPER_BYTE : integer := 28; + REG_ADDR_CHANNEL_LOWER_BYTE : integer := 29; + REG_ADDR_TIMING_UPPER_BYTE : integer := 30; + REG_ADDR_TIMING_LOWER_BYTE : integer := 31; + REG_ADDR_CMD_UPPER_BYTE : integer := 32; + REG_ADDR_CMD_LOWER_BYTE : integer := 33; + REG_ADDR_CONTROL_UPPER_BYTE : integer := 34; + REG_ADDR_CONTROL_LOWER_BYTE : integer := 35; + + DATA_BUS_WIDTH : integer := 8; + ADDRESS_BUS_WIDTH : integer := 9 + ); + + port( + clk : in std_logic; + + data : inout std_logic_vector(DATA_BUS_WIDTH - 1 downto 0); + address : in std_logic_vector(ADDRESS_BUS_WIDTH - 1 downto 0); + we : in std_logic; + oe : in std_logic; + ce : in std_logic; + + tk : out std_logic_vector(31 downto 0) := (others => '1'); + interrupt : out std_logic := '1'; + pwm : in std_logic_vector(5 downto 0) + ); +end entity; + +architecture behavorial of RAM9X8_PWM is + +signal modeBuf : std_logic_vector(15 downto 0) := (others => '0'); +signal maskBuf : std_logic_vector(31 downto 0) := (others => '1'); +signal directControlBuf : std_logic_vector(31 downto 0) := (others => '1'); +signal periodBuf : std_logic_vector(15 downto 0) := (others => '0'); +signal directionBuf : std_logic_vector(15 downto 0) := (others => '0'); +signal channelBuf : std_logic_vector(15 downto 0) := (others => '0'); +signal cmdBuf : std_logic_vector(15 downto 0) := (others => '0'); +signal controlBuf : std_logic_vector(15 downto 0) := (others => '0'); + +type mem is array (15 downto 0) of std_logic_vector(15 downto 0); +signal memory : mem; + +signal lineBusy : std_logic := '1'; +signal start : std_logic := '0'; +signal startPrev : std_logic := '0'; + +begin + + process (we, oe, ce) + variable addr : integer range 0 to 2**ADDRESS_BUS_WIDTH - 1 := 0; + variable position : integer range 0 to ARRAY_LENGTH - 1 := 0; + begin + if (ce = '0') then -- Если микросхема выбрана + addr := conv_integer(address); + if (addr = REG_ADDR_MODE_CONTROL_UPPER_BYTE or addr = REG_ADDR_MODE_CONTROL_LOWER_BYTE + or addr = REG_ADDR_MASK_2_UPPER_BYTE or addr = REG_ADDR_MASK_2_LOWER_BYTE or addr = REG_ADDR_MASK_1_UPPER_BYTE or addr = REG_ADDR_MASK_1_LOWER_BYTE + or addr = REG_ADDR_DIRECT_CONTROL_2_UPPER_BYTE or addr = REG_ADDR_DIRECT_CONTROL_2_LOWER_BYTE or addr = REG_ADDR_DIRECT_CONTROL_1_UPPER_BYTE or addr = REG_ADDR_DIRECT_CONTROL_1_LOWER_BYTE + or addr = REG_ADDR_PERIOD_UPPER_BYTE or addr = REG_ADDR_PERIOD_LOWER_BYTE or addr = REG_ADDR_DIRECTION_UPPER_BYTE or addr = REG_ADDR_DIRECTION_LOWER_BYTE + or addr = REG_ADDR_CHANNEL_UPPER_BYTE or addr = REG_ADDR_CHANNEL_LOWER_BYTE or addr = REG_ADDR_TIMING_UPPER_BYTE or addr = REG_ADDR_TIMING_LOWER_BYTE + or addr = REG_ADDR_CMD_UPPER_BYTE or addr = REG_ADDR_CMD_LOWER_BYTE or addr = REG_ADDR_CONTROL_UPPER_BYTE or addr = REG_ADDR_CONTROL_LOWER_BYTE) then + if (oe = '0' and we = '1') then -- Если сигнал чтения активен, а записи нет + case addr is + when REG_ADDR_MODE_CONTROL_UPPER_BYTE => + data <= modeBuf(15 downto 8); + when REG_ADDR_MODE_CONTROL_LOWER_BYTE => + data <= modeBuf(7 downto 0); + when REG_ADDR_MASK_2_UPPER_BYTE => + data <= maskBuf(31 downto 24); + when REG_ADDR_MASK_2_LOWER_BYTE => + data <= maskBuf(23 downto 16); + when REG_ADDR_MASK_1_UPPER_BYTE => + data <= maskBuf(15 downto 8); + when REG_ADDR_MASK_1_LOWER_BYTE => + data <= maskBuf(7 downto 0); + when REG_ADDR_DIRECT_CONTROL_2_UPPER_BYTE => + data <= directControlBuf(31 downto 24); + when REG_ADDR_DIRECT_CONTROL_2_LOWER_BYTE => + data <= directControlBuf(23 downto 16); + when REG_ADDR_DIRECT_CONTROL_1_UPPER_BYTE => + data <= directControlBuf(15 downto 8); + when REG_ADDR_DIRECT_CONTROL_1_LOWER_BYTE => + data <= directControlBuf(7 downto 0); + when REG_ADDR_PERIOD_UPPER_BYTE => + data <= periodBuf(15 downto 8); + when REG_ADDR_PERIOD_LOWER_BYTE => + data <= periodBuf(7 downto 0); + when REG_ADDR_DIRECTION_UPPER_BYTEE => + data <= directionBuf(15 downto 8); + when REG_ADDR_DIRECTION_LOWER_BYTE => + data <= directionBuf(7 downto 0); + when REG_ADDR_CHANNEL_UPPER_BYTE => + data <= channelBuf(15 downto 8); + when REG_ADDR_CHANNEL_LOWER_BYTE => + data <= channelBuf(7 downto 0); + when REG_ADDR_TIMING_UPPER_BYTE => + data <= memory(conv_integer(channelBuf)(15 downto 8)); + when REG_ADDR_TIMING_LOWER_BYTE => + data <= memory(conv_integer(channelBuf)(7 downto 0); + when REG_ADDR_CMD_UPPER_BYTE => + data <= cmdBuf(15 downto 8); + when REG_ADDR_CMD_LOWER_BYTE => + data <= cmdBuf(7 downto 0); + when REG_ADDR_CONTROL_UPPER_BYTE => + data <= controlBuf(15 downto 8); + when REG_ADDR_CONTROL_LOWER_BYTE => + data <= controlBuf(7 downto 0); + when others => + data <= (others => 'Z'); -- Запретить запись на шину + end case; + elsif (oe = '1' and we = '0') then -- Если сигнал записи активен, а чтения нет + case addr is + when REG_ADDR_MODE_CONTROL_UPPER_BYTE => + modeBuf(15 downto 8) <= data; + when REG_ADDR_MODE_CONTROL_LOWER_BYTE => + modeBuf(7 downto 0) <= data; + when REG_ADDR_MASK_2_UPPER_BYTE => + maskBuf(31 downto 24) <= data; + when REG_ADDR_MASK_2_LOWER_BYTE => + maskBuf(23 downto 16) <= data; + when REG_ADDR_MASK_1_UPPER_BYTE => + maskBuf(15 downto 8) <= data; + when REG_ADDR_MASK_1_LOWER_BYTE => + maskBuf(7 downto 0) <= data; + when REG_ADDR_DIRECT_CONTROL_2_UPPER_BYTE => + directControlBuf(31 downto 24) <= data; + when REG_ADDR_DIRECT_CONTROL_2_LOWER_BYTE => + directControlBuf(23 downto 16) <= data; + when REG_ADDR_DIRECT_CONTROL_1_UPPER_BYTE => + directControlBuf(15 downto 8) <= data; + when REG_ADDR_DIRECT_CONTROL_1_LOWER_BYTE => + directControlBuf(7 downto 0) <= data; + when REG_ADDR_PERIOD_UPPER_BYTE => + periodBuf(15 downto 8) <= data; + when REG_ADDR_PERIOD_LOWER_BYTE => + periodBuf(7 downto 0) <= data; + when REG_ADDR_DIRECTION_UPPER_BYTEE => + directionBuf(15 downto 8) <= data; + when REG_ADDR_DIRECTION_LOWER_BYTE => + directionBuf(7 downto 0) <= data; + when REG_ADDR_CHANNEL_UPPER_BYTE => + channelBuf(15 downto 8) <= data; + when REG_ADDR_CHANNEL_LOWER_BYTE => + channelBuf(7 downto 0) <= data; + when REG_ADDR_TIMING_UPPER_BYTE => + memory(conv_integer(channelBuf)(15 downto 8)) <= data; + when REG_ADDR_TIMING_LOWER_BYTE => + memory(conv_integer(channelBuf)(7 downto 0) <= data; + when REG_ADDR_CMD_UPPER_BYTE => + cmdBuf(15 downto 8) <= data; + when REG_ADDR_CMD_LOWER_BYTE => + cmdBuf(7 downto 0) <= data; + when REG_ADDR_CONTROL_UPPER_BYTE => + controlBuf(15 downto 8) <= data; + when REG_ADDR_CONTROL_LOWER_BYTE => + controlBuf(7 downto 0) <= data; + when others => + data <= (others => 'Z'); -- Запретить запись на шину + end case; + else + data <= (others => 'Z'); -- Запретить запись на шину + end if;; + else + data <= (others => 'Z'); -- Запретить запись на шину + end if; + else + data <= (others => 'Z'); -- Запретить запись на шину + end if; + end process; + + process(clk) is + variable counter : integer range 0 to 65666 := 0; + begin + if(rising_edge clk) then + if(conv_integer(memory(0)) > counter) then + if(directionBuf(0) = '0') then + pwm3level(0) <= '0'; + else + pwm3level(0) <= '1'; + end if; + else + if(directionBuf(0) = '0') then + pwm3level(0) <= '1'; + else + pwm3level(0) <= '0'; + end if; + end if; + + + + end process; + +end behavorial; \ No newline at end of file diff --git a/MainController/RAM9X8_SerialBusMaster.vhd b/MainController/RAM9X8_SerialBusMaster.vhd index a86e342..f4760e3 100644 --- a/MainController/RAM9X8_SerialBusMaster.vhd +++ b/MainController/RAM9X8_SerialBusMaster.vhd @@ -147,19 +147,23 @@ begin bitCnt := 15; else if count < countValue and state = 1 then - if latch = 0 then - sbdataout <= direction; - else - sbdataout <= addressToTransmit(bitCnt); - end if; - sbclk <= '0'; + if count = 0 then + if latch = 0 then + sbdataout <= direction; + else + sbdataout <= addressToTransmit(bitCnt); + end if; + sbclk <= '0'; + end if; count := count + 1; elsif count = countValue and state = 1 then latch := 1; count := 0; state := 0; elsif count < countValue and state = 0 then - sbclk <= '1'; + if count = 0 then + sbclk <= '1'; + end if; count := count + 1; elsif count = countValue and state = 0 then count := 0; @@ -173,14 +177,18 @@ begin bitCnt := 3; else if count < countValue and state = 1 then - sbdataout <= dataToTransmit(bitCnt); - sbclk <= '0'; + if count = 0 then + sbdataout <= dataToTransmit(bitCnt); + sbclk <= '0'; + end if; count := count + 1; elsif count = countValue and state = 1 then count := 0; state := 0; elsif count < countValue and state = 0 then - sbclk <= '1'; + if count = 0 then + sbclk <= '1'; + end if; count := count + 1; elsif count = countValue and state = 0 then count := 0; @@ -194,14 +202,18 @@ begin CommunicationState <= TransmitCheck; else if count < count and state = 1 then - sbdataout <= CRC(bitCnt); - sbclk <= '0'; + if count = 0 then + sbdataout <= CRC(bitCnt); + sbclk <= '0'; + end if; count := count + 1; elsif count = countValue and state = 1 then count := 0; state := 0; elsif count < countValue and state = 0 then - sbclk <= '1'; + if count = 0 then + sbclk <= '1'; + end if; count := count + 1; elsif count = countValue and state = 0 then count := 0; @@ -215,7 +227,9 @@ begin end if; when TransmitCheck => if count < countValue and state = 1 then - sbclk <= '0'; + if count = 0 then + sbclk <= '0'; + end if; count := count + 1; else count := 0; @@ -233,14 +247,18 @@ begin bitCnt := 3; else if count < countValue and state = 1 then - sbclk <= '0'; + if count = 0 then + sbclk <= '0'; + end if; count := count + 1; elsif count = countValue and state = 1 then dataFromDevices(bitCnt) <= sbdatain; count := 0; state := 0; elsif count < countValue and state = 0 then - sbclk <= '1'; + if count = 0 then + sbclk <= '1'; + end if; count := count + 1; elsif count = countValue and state = 0 then count := 0; @@ -253,7 +271,9 @@ begin CommunicationState <= ReceiveCheck; else if count < countValue and state = 1 then - sbclk <= '0'; + if count = 0 then + sbclk <= '0'; + end if; count := count + 1; elsif count = countValue and state = 1 then bufCRC(BitCnt) <= sbdatain; @@ -266,7 +286,9 @@ begin resetCRC <= '0'; end if; elsif count < countValue and state = 0 then - sbclk <= '1'; + if count = 0 then + sbclk <= '1'; + end if; count := count + 1; elsif count = countValue and state = 0 then count := 0;