diff --git a/src/dds_reader.vhd b/src/dds_reader.vhd index 5b88e4f..331dd02 100644 --- a/src/dds_reader.vhd +++ b/src/dds_reader.vhd @@ -15,6 +15,7 @@ entity dds_reader is DESTINATION_ORDER_QOS : std_logic_vector(CDR_ENUMERATION_WIDTH-1 downto 0) := DEFAULT_DESTINATION_ORDER_QOS; COHERENT_ACCESS : boolean := DEFAULT_COHERENT_ACCESS; ORDERED_ACCESS : boolean := DEFAULT_ORDERED_ACCESS; + WITH_KEY : boolean := FALSE; -- TODO: Default ); port ( -- SYSTEM @@ -473,40 +474,41 @@ begin data_out => payload_read_data ); - instance_mem_ctrl_inst : entity work.mem_ctrl(arch) - generic map ( - ADDR_WIDTH => INSTANCE_MEMORY_ADDR_WIDTH, - DATA_WIDTH => WORD_WIDTH, - MEMORY_DEPTH => INSTANCE_MEMORY_SIZE, - MAX_BURST_LENGTH => INSTANCE_FRAME_SIZE - ) - port map ( - clk => clk, - reset => reset or sample_abort_read, - addr => std_logic_vector(sample_addr), - read => instance_read, - ready_in => instance_ready_in, - valid_in => instance_valid_in, - data_in => instance_write_data, - ready_out => instance_ready_out, - valid_out => instance_valid_out, - data_out => instance_read_data - ); - - - key_hash_generator_inst : entity work.key_hash_generator(arch) - port ( - clk => clk, - reset => reset or khg_abort, - data_in => khg_data_in, - valid_in => khg_valid_in, - ready_in => khg_ready_in, - last_word_in => khg_last_word_in, - data_out => khg_data_out, - valid_out => khg_valid_out, - ready_out => khg_ready_out, - last_word_out => khg_last_word_out - ); + gen_instance_mem_ctrl_inst : if WITH_KEY generate + instance_mem_ctrl_inst : entity work.mem_ctrl(arch) + generic map ( + ADDR_WIDTH => INSTANCE_MEMORY_ADDR_WIDTH, + DATA_WIDTH => WORD_WIDTH, + MEMORY_DEPTH => INSTANCE_MEMORY_SIZE, + MAX_BURST_LENGTH => INSTANCE_FRAME_SIZE + ) + port map ( + clk => clk, + reset => reset or sample_abort_read, + addr => std_logic_vector(sample_addr), + read => instance_read, + ready_in => instance_ready_in, + valid_in => instance_valid_in, + data_in => instance_write_data, + ready_out => instance_ready_out, + valid_out => instance_valid_out, + data_out => instance_read_data + ); + + key_hash_generator_inst : entity work.key_hash_generator(arch) + port ( + clk => clk, + reset => reset or khg_abort, + data_in => khg_data_in, + valid_in => khg_valid_in, + ready_in => khg_ready_in, + last_word_in => khg_last_word_in, + data_out => khg_data_out, + valid_out => khg_valid_out, + ready_out => khg_ready_out, + last_word_out => khg_last_word_out + ); + end generate; -- *Main State Machine* -- STATE DESCRIPTION @@ -660,8 +662,21 @@ begin -- Reset Timeout deadline_time_next <= deadline_time + DEADLINE_QOS; - stage_next <= CHECK_DEADLINE; - cnt_next <= 0; + -- Synthesis Guard + if (WITH_KEY) then + stage_next <= CHECK_DEADLINE; + cnt_next <= 0; + else + if (inst_data.status_info(LIVELINESS_FLAG) = '1') then + -- Reset Liveliness Flag + inst_data_next.status_info(LIVELINESS_FLAG) <= '0'; + else + -- Update Requested Deadline Missed Status + status_sig_next(REQUESTED_DEADLINE_MISSED_STATUS) <= '1'; + deadline_miss_cnt_next <= deadline_miss_cnt + 1; + deadline_miss_cnt_change_next <= deadline_miss_cnt_change + 1; + end if; + end if; -- LIFESPAN QoS elsif (lifespan_time <= time) then -- Reset Timeout @@ -687,20 +702,36 @@ begin end if; when REMOVE_WRITER => -- Input and Memory Gurad - if (valid_in_rtps = '1' and inst_op_done = '1') then - -- Latch Writer Pos - writer_pos_next <= to_integer(unsigned(data_in_rtps)); - inst_op_start <= '1'; - inst_opcode <= GET_FIRST_INSTANCE; - inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; - stage_next <= REMOVE_WRITER; + if (valid_in_rtps = '1') then res_rtps <= ACK; + + -- Synthesis Guard + if (WITH_KEY) then + -- Latch Writer Pos + writer_pos_next <= to_integer(unsigned(data_in_rtps)); + stage_next <= REMOVE_WRITER; + cnt_next <= 2; + else + -- Convert Writer Bitmap to SLV + tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); + + -- Remove Writer + tmp_bitmap(to_integer(unsigned(data_in_rtps))) := '0'; + + -- Convert Back + inst_data_next.writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + + -- NOT_ALIVE_NO_WRITERS Transition + if (tmp_bitmap = (tmp_bitmap'range => '0') and inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then + inst_data_next.status_info(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; + end if; + end if; end if; when others => null; end case; -- Unmark Instances - elsif (unmark_instances = '1') then + elsif (WITH_KEY and unmark_instances = '1') then -- Memory Operation Guard if (inst_op_done = '1') then inst_op_start <= '1'; @@ -716,8 +747,8 @@ begin max_samples_next <= unsigned(max_samples_in); -- Reset - single_instance_next <= '0'; - single_instance_next <= '0'; + single_sample_next <= '0'; + single_instance_next <= '0' when WITH_KEY else '1'; collection_cnt_next <= 0; collection_cnt_max_next <= 0; is_first_instance_sample_next <= '1'; @@ -773,37 +804,61 @@ begin stage_next <= GET_NEXT_SAMPLE; cnt_next <= 0; when READ_INSTANCE => - ack_dds <= '1'; - single_instance_next <= '1'; - cur_sample_next <= oldest_sample; - key_hash_next <= instance_handle_in; - stage_next <= CHECK_INSTANCE; - cnt_next <= 0; + -- Synthesis Guard + if (WITH_KEY) then + ack_dds <= '1'; + single_instance_next <= '1'; + cur_sample_next <= oldest_sample; + key_hash_next <= instance_handle_in; + stage_next <= CHECK_INSTANCE; + cnt_next <= 0; + else + ack_dds <= '1'; + stage_next <= UNKNOWN_OPERATION; + end if; when TAKE_INSTANCE => - ack_dds <= '1'; - is_take_next <= '1'; - single_instance_next <= '1'; - cur_sample_next <= oldest_sample; - key_hash_next <= instance_handle_in; - stage_next <= CHECK_INSTANCE; - cnt_next <= 0; + -- Synthesis Guard + if (WITH_KEY) then + ack_dds <= '1'; + is_take_next <= '1'; + single_instance_next <= '1'; + cur_sample_next <= oldest_sample; + key_hash_next <= instance_handle_in; + stage_next <= CHECK_INSTANCE; + cnt_next <= 0; + else + ack_dds <= '1'; + stage_next <= UNKNOWN_OPERATION; + end if; when READ_NEXT_INSTANCE => - ack_dds <= '1'; - single_instance_next <= '1'; - dynamic_next_instance_next <= '1'; - cur_sample_next <= oldest_sample; - key_hash_next <= instance_handle_in; - stage_next <= FIND_NEXT_INSTANCE; - cnt_next <= 0; + -- Synthesis Guard + if (WITH_KEY) then + ack_dds <= '1'; + single_instance_next <= '1'; + dynamic_next_instance_next <= '1'; + cur_sample_next <= oldest_sample; + key_hash_next <= instance_handle_in; + stage_next <= FIND_NEXT_INSTANCE; + cnt_next <= 0; + else + ack_dds <= '1'; + stage_next <= UNKNOWN_OPERATION; + end if; when TAKE_NEXT_INSTANCE => - ack_dds <= '1'; - is_take_next <= '1'; - single_instance_next <= '1'; - dynamic_next_instance_next <= '1'; - cur_sample_next <= oldest_sample; - key_hash_next <= instance_handle_in; - stage_next <= FIND_NEXT_INSTANCE; - cnt_next <= 0; + -- Synthesis Guard + if (WITH_KEY) then + ack_dds <= '1'; + is_take_next <= '1'; + single_instance_next <= '1'; + dynamic_next_instance_next <= '1'; + cur_sample_next <= oldest_sample; + key_hash_next <= instance_handle_in; + stage_next <= FIND_NEXT_INSTANCE; + cnt_next <= 0; + else + ack_dds <= '1'; + stage_next <= UNKNOWN_OPERATION; + end if; when GET_SAMPLE_REJECTED_STATUS => ack_dds <= '1'; stage_next <= GET_SAMPLE_REJECTED_STATUS; @@ -819,7 +874,7 @@ begin end if; when UNKNOWN_OPERATION => done_dds <= '1'; - return_code_dds <= RETCODE_UNSUPPORTED; + return_code_dds <= RETCODE_ILLEGAL_OPERATION; -- DONE stage_next <= IDLE; @@ -958,11 +1013,15 @@ begin -- Memory Flow Control Guard if (sample_ready_in = '1') then -- If Key Hash is available, start the Instance Search first - if (has_key_hash = '1') then + if (WITH_KEY and has_key_hash = '1') then stage_next <= INITIATE_INSTANCE_SEARCH; else - stage_next <= ADD_PAYLOAD; - cnt_next <= 0; + if (has_data = '1' or (WITH_KEY and has_key_hash = '0')) then + stage_next <= ADD_PAYLOAD; + cnt_next <= 0; + else + stage_next <= FILTER_STAGE; + end if; end if; end if; when ADD_PAYLOAD => @@ -988,7 +1047,7 @@ begin cnt2_next <= cnt2 + 1; -- Key Hash needs to be calculated - if (has_key_hash = '0') then + if (WITH_KEY and has_key_hash = '0') then cnt_next <= 1; else ready_in_rtps <= '1'; @@ -1015,45 +1074,48 @@ begin end if; -- Push to KHG when 1 => - assert (valid_in_rtps = '1') severity FAILURE; - - khg_valid_in <= '1'; - khg_data_in <= data_in_rtps; - - -- Output Guard - if (khg_ready_in = '1') then - ready_in_rtps <= '1'; - if (has_data = '1') then - -- End of Payload - if (last_word_in_rtps = '1') then - -- End of Payload Slot - if (cnt2 = PAYLOAD_FRAME_SIZE) then + -- Synthesis Guard + if (WITH_KEY) then + assert (valid_in_rtps = '1') severity FAILURE; + + khg_valid_in <= '1'; + khg_data_in <= data_in_rtps; + + -- Output Guard + if (khg_ready_in = '1') then + ready_in_rtps <= '1'; + if (has_data = '1') then + -- End of Payload + if (last_word_in_rtps = '1') then + -- End of Payload Slot + if (cnt2 = PAYLOAD_FRAME_SIZE) then + -- Fetch the Key Hash + stage_next <= GET_KEY_HASH; + cnt_next <= 0; + else + stage_next <= ZERO_PAYLOAD; + end if; + else + -- End of Payload Slot + if (cnt2 = PAYLOAD_FRAME_SIZE) then + stage_next <= NEXT_PAYLOAD_SLOT; + cnt_next <= 0; + else + -- Next Word + cnt_next <= 0; + end if; + end if; + else + -- End of Payload + if (last_word_in_rtps = '1') then -- Fetch the Key Hash stage_next <= GET_KEY_HASH; cnt_next <= 0; - else - stage_next <= ZERO_PAYLOAD; - end if; - else - -- End of Payload Slot - if (cnt2 = PAYLOAD_FRAME_SIZE) then - stage_next <= NEXT_PAYLOAD_SLOT; - cnt_next <= 0; else -- Next Word - cnt_next <= 0; + cnt_next <= 1; end if; end if; - else - -- End of Payload - if (last_word_in_rtps = '1') then - -- Fetch the Key Hash - stage_next <= GET_KEY_HASH; - cnt_next <= 0; - else - -- Next Word - cnt_next <= 1; - end if; end if; end if; when others => @@ -1106,7 +1168,7 @@ begin if (payload_ready_in = '1') then -- Exit Condition if (cnt2 = PAYLOAD_FRAME_SIZE-1) then - if (has_key_hash = '0') then + if (WITH_KEY and has_key_hash = '0') then stage_next <= GET_KEY_HASH; cnt_next <= 0; else @@ -1115,47 +1177,52 @@ begin end if; end if; when GET_KEY_HASH => - - khg_ready_out <= '1'; - - if (khg_valid_out = '1') then - cnt_next <= cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + khg_ready_out <= '1'; - -- Latch Key Hash - key_hash_next(cnt) <= khg_data_out; - - -- Exit Condition - if (khg_last_word_out = '1') then - -- DONE - stage_next <= INITIATE_INSTANCE_SEARCH; + if (khg_valid_out = '1') then + cnt_next <= cnt + 1; + + -- Latch Key Hash + key_hash_next(cnt) <= khg_data_out; + + -- Exit Condition + if (khg_last_word_out = '1') then + -- DONE + stage_next <= INITIATE_INSTANCE_SEARCH; + end if; end if; end if; when INITIATE_INSTANCE_SEARCH => - -- Memory Operation Guard - if (inst_op_done = '1') then - inst_op_start <= '1'; - inst_opcode <= SEARCH_INSTANCE_HASH; - inst_mem_fields <= IMF_STATUS_FLAG or IMF_SAMPLE_CNT_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG or IMF_IGNORE_DEADLINE_FLAG or IMF_WRITER_BITMAP_FLAG; - - -- Payload not yet stored - if (has_data = '1') then - stage_next <= ADD_PAYLOAD; - cnt_next <= 0; - else - stage_next <= FILTER_STAGE; + -- Synthesis Guard + if (WITH_KEY) then + -- Memory Operation Guard + if (inst_op_done = '1') then + inst_op_start <= '1'; + inst_opcode <= SEARCH_INSTANCE_HASH; + inst_mem_fields <= IMF_STATUS_FLAG or IMF_SAMPLE_CNT_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG or IMF_IGNORE_DEADLINE_FLAG or IMF_WRITER_BITMAP_FLAG; + + -- Payload not yet stored + if (has_data = '1') then + stage_next <= ADD_PAYLOAD; + cnt_next <= 0; + else + stage_next <= FILTER_STAGE; + end if; end if; end if; when FILTER_STAGE => -- Precondition: cur_sample set -- Wait for Instance Search to finish - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then sample_valid_in <= '1'; sample_addr <= cur_sample + SMF_INSTANCE_ADDR_OFFSET; cur_inst_next <= inst_addr_base; -- Instance Found - if (inst_addr_base /= INSTANCE_MEMORY_MAX_ADDRESS) then + if (not WITH_KEY or inst_addr_base /= INSTANCE_MEMORY_MAX_ADDRESS) then -- Store Instance Address sample_write_data <= inst_addr_base; @@ -1167,7 +1234,7 @@ begin res_rtps <= ACCEPTED; stage_next <= IDLE; -- RESOURCE_LIMITS_QOS (MAX_SAMPLES_PER_INSTANCE) - elsif (MAX_SAMPLES_PER_INSTANCE /= LENGTH_UNLIMITED and inst_data.sample_cnt = MAX_SAMPLES_PER_INSTANCE) then + elsif (WITH_KEY and MAX_SAMPLES_PER_INSTANCE /= LENGTH_UNLIMITED and inst_data.sample_cnt = MAX_SAMPLES_PER_INSTANCE) then if (HISTORY_QOS = KEEP_LAST_HISTORY_QOS and RELIABILITY_QOS = RELIABLE_RELIABILITY_QOS) then -- Reject Change res_rtps <= REJECTED; @@ -1289,7 +1356,7 @@ begin end if; when UPDATE_INSTANCE => -- Memory Operation Guard - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then -- DEFAULT tmp_update := (others => '0'); @@ -1298,20 +1365,17 @@ begin -- ALIVE -> NOT_ALIVE_DISPOSED Transition if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) /= '1' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) /= '1') then -- STATUS INFO - tmp_update <= tmp_update or IMF_STATUS_FLAG; - status_info_update <= inst_data.status; - status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '1'; - status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '0'; - status_info_update(LIVELINESS_FLAG) <= '1'; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update <= tmp_update or IMF_STATUS_FLAG; + status_info_update <= inst_data.status; + status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '1'; + status_info_update(LIVELINESS_FLAG) <= '1'; + else + inst_data_next.status_info(NOT_ALIVE_DISPOSED_FLAG) <= '1'; + inst_data_next.status_info(LIVELINESS_FLAG) <= '1'; + end if; end if; - -- WRITER BITMAP - -- Convert Writer Bitmap to SLV - tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); - -- Remove Writer - tmp_bitmap(writer_pos) := '0'; - -- Convert Back - writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); - tmp_update := tmp_update or IMF_WRITER_BITMAP_FLAG; -- Instance UNREGISTERED elsif (sample_status_info(UNREGISTERED_FLAG) = '1') then -- WRITER BITMAP @@ -1319,38 +1383,66 @@ begin tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); -- Remove Writer tmp_bitmap(writer_pos) := '0'; + -- Convert Back - writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); - tmp_update := tmp_update or IMF_WRITER_BITMAP_FLAG; + -- Synthesis Guard + if (WITH_KEY) then + writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + tmp_update := tmp_update or IMF_WRITER_BITMAP_FLAG; + else + inst_data_next.writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + end if; -- ALIVE -> NOT_ALIVE_NO_WRITERS Transition if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) /= '1' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) /= '1' and tmp_bitmap = (tmp_bitmap => '0')) then -- STATUS INFO - tmp_update <= tmp_update or IMF_STATUS_FLAG; - status_info_update <= inst_data.status; - status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '0'; - status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; - status_info_update(LIVELINESS_FLAG) <= '1'; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update <= tmp_update or IMF_STATUS_FLAG; + status_info_update <= inst_data.status; + status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; + status_info_update(LIVELINESS_FLAG) <= '1'; + else + inst_data_next.status_info(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; + inst_data_next.status_info(LIVELINESS_FLAG) <= '1'; + end if; end if; -- Instance ALIVE/FILTERED else -- STATUS INFO - tmp_update <= tmp_update or IMF_STATUS_FLAG; - status_info_update <= inst_data.status; - status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '0'; - status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '0'; - status_info_update(LIVELINESS_FLAG) <= '1'; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update <= tmp_update or IMF_STATUS_FLAG; + status_info_update <= inst_data.status; + status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '0'; + status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '0'; + status_info_update(LIVELINESS_FLAG) <= '1'; + else + inst_data_next.status_info(NOT_ALIVE_DISPOSED_FLAG) <= '0'; + inst_data_next.status_info(NOT_ALIVE_NO_WRITERS_FLAG) <= '0'; + inst_data_next.status_info(LIVELINESS_FLAG) <= '1'; + end if; -- GENERATION COUNTERS -- NOT_ALIVE_DISPOSED -> ALIVE Transition if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1') then - tmp_update := tmp_update or IMF_DISPOSED_CNT_FLAG; - gen_cnt <= inst_data.disposed_gen_cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update := tmp_update or IMF_DISPOSED_CNT_FLAG; + gen_cnt <= inst_data.disposed_gen_cnt + 1; + else + inst_data_next.disposed_gen_cnt <= inst_data.disposed_gen_cnt + 1; + end if; -- NOT_ALIVE_NO_WRITERS -> ALIVE Transition elsif (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then - tmp_update := tmp_update or IMF_NO_WRITERS_CNT_FLAG; - gen_cnt <= inst_data.no_writers_gen_cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update := tmp_update or IMF_NO_WRITERS_CNT_FLAG; + gen_cnt <= inst_data.no_writers_gen_cnt + 1; + else + inst_data_next.no_writers_gen_cnt <= inst_data.no_writers_gen_cnt + 1; + end if; end if; -- WRITER BITMAP @@ -1358,28 +1450,48 @@ begin tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); -- Write if Writer New for Instance if (tmp_bitmap(writer_pos) /= '1') then - -- Remove Writer - tmp_bitmap(writer_pos) := '0'; + -- Insert Writer + tmp_bitmap(writer_pos) := '1'; -- Convert Back - writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); - tmp_update := tmp_update or IMF_WRITER_BITMAP_FLAG; + -- Synthesis Guard + if (WITH_KEY) then + writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + tmp_update := tmp_update or IMF_WRITER_BITMAP_FLAG; + else + inst_data_next.writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + end if; end if; end if; -- INSTANCE SAMPLE COUNT -- NOTE: Ignored when remove_oldest_inst_sample, since it will be decremented again. (Stays same) if (remove_oldest_inst_sample = '0') then - tmp_update := tmp_update or IMF_SAMPLE_CNT_FLAG; - end if; - -- IGNORE DEADLINE - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - tmp_update := tmp_update or IMF_IGNORE_DEADLINE_FLAG; - deadline <= time + TIME_BASED_FILTER_QOS; + -- Synthesis Guard + if (WITH_KEY) then + tmp_update := tmp_update or IMF_SAMPLE_CNT_FLAG; + sample_cnt <= inst_data.sample_cnt + 1; + else + inst_data_next.sample_cnt <= inst_data.sample_cnt + 1; + end if; end if; - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= tmp_update; + -- IGNORE DEADLINE + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + -- Synthesis Guard + if (WITH_KEY) then + tmp_update := tmp_update or IMF_IGNORE_DEADLINE_FLAG; + deadline <= time + TIME_BASED_FILTER_QOS; + else + inst_data_next.ignore_deadline <= time + TIME_BASED_FILTER_QOS; + end if; + end if; + + -- Synthesis Guard + if (WITH_KEY) then + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= tmp_update; + end if; if (has_data = '1') then stage_next <= FINALIZE_PAYLOAD; @@ -1432,61 +1544,55 @@ begin when PRE_SAMPLE_FINALIZE => -- Precondition: cur_sample set - case (cnt) is - -- Disposed Generation Counter - when 0 => - sample_valid_in <= '1'; - sample_addr <= cur_sample + SMF_DISPOSED_GEN_CNT_OFFSET; - - -- NOT_ALIVE_DISPOSED -> ALIVE Transition - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' and sample_status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and sample_status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - sample_write_data <= gen_cnt + 1; - else - sample_write_data <= gen_cnt; - end if; - - -- Memory Flow Control Guard - if (sample_ready_in = '1') then - cnt_next <= cnt + 1; - end if; - -- No Writer Generation Counter - when 1 => - sample_valid_in <= '1'; - sample_addr <= cur_sample + SMF_NO_WRITERS_GEN_CNT_OFFSET; - - -- NOT_ALIVE_NO_WRITERS -> ALIVE Transition - if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1' and sample_status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and sample_status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - sample_write_data <= gen_cnt + 1; - else - sample_write_data <= gen_cnt; - end if; - - -- Memory Flow Control Guard - if (sample_ready_in = '1') then - cnt_next <= cnt + 1; - end if; - when 2 => - -- First Sample - if (newest_sample = SAMPLE_MEMORY_MAX_ADDRESS) then - stage_next <= FINALIZE_SAMPLE; - cur_sample_next <= empty_sample_list_head; - next_sample_next <= SAMPLE_MEMORY_MAX_ADDRESS; - prev_sample_next <= SAMPLE_MEMORY_MAX_ADDRESS; - cnt_next <= 0; - elsif (DESTINATION_ORDER_QOS = BY_RECEPTION_TIMESTAMP_DESTINATION_ORDER_QOS) then - stage_next <= FIX_POINTERS; - prev_sample_next <= newest_sample; - cur_sample_next <= newest_sample; - cnt_next <= 0; - else - stage_next <= FIND_POS; - prev_sample_next <= newest_sample; - cur_sample_next <= newest_sample; - cnt_next <= 0; - end if; - when others => - null; - end case; + -- Wait for instance Update to Complete + if (not WITH_KEY or inst_op_done = '1') then + + case (cnt) is + -- Disposed Generation Counter + when 0 => + sample_valid_in <= '1'; + sample_addr <= cur_sample + SMF_DISPOSED_GEN_CNT_OFFSET; + + sample_write_data <= inst_data.disposed_gen_cnt; + + -- Memory Flow Control Guard + if (sample_ready_in = '1') then + cnt_next <= cnt + 1; + end if; + -- No Writer Generation Counter + when 1 => + sample_valid_in <= '1'; + sample_addr <= cur_sample + SMF_NO_WRITERS_GEN_CNT_OFFSET; + + sample_write_data <= inst_data.no_writers_gen_cnt; + + -- Memory Flow Control Guard + if (sample_ready_in = '1') then + cnt_next <= cnt + 1; + end if; + when 2 => + -- First Sample + if (newest_sample = SAMPLE_MEMORY_MAX_ADDRESS) then + stage_next <= FINALIZE_SAMPLE; + cur_sample_next <= empty_sample_list_head; + next_sample_next <= SAMPLE_MEMORY_MAX_ADDRESS; + prev_sample_next <= SAMPLE_MEMORY_MAX_ADDRESS; + cnt_next <= 0; + elsif (DESTINATION_ORDER_QOS = BY_RECEPTION_TIMESTAMP_DESTINATION_ORDER_QOS) then + stage_next <= FIX_POINTERS; + prev_sample_next <= newest_sample; + cur_sample_next <= newest_sample; + cnt_next <= 0; + else + stage_next <= FIND_POS; + prev_sample_next <= newest_sample; + cur_sample_next <= newest_sample; + cnt_next <= 0; + end if; + when others => + null; + end case; + end if; when FIND_POS => -- Synthesis Guard if (DESTINATION_ORDER_QOS /= BY_RECEPTION_TIMESTAMP_DESTINATION_ORDER_QOS) then @@ -1676,7 +1782,7 @@ begin -- NOTE: added_new_instance and remove_oldest_sample are NOT mutual exclusive, but Instance Removal takes precedence. -- New Instance was added, and Instance Memory is Full - if (added_new_instance = '1' and inst_empty_head = INSTANCE_MEMORY_MAX_ADDRESS) then + if (WITH_KEY and added_new_instance = '1' and inst_empty_head = INSTANCE_MEMORY_MAX_ADDRESS) then -- Memory Operation Guard if (inst_op_done = '1') then inst_op_start <= '1'; @@ -1693,11 +1799,17 @@ begin else cnt_next <= cnt; -- Keep State end if; - elsif (remove_oldest_inst_sample = '1') then + elsif (WITH_KEY and remove_oldest_inst_sample = '1') then cur_sample <= oldest_sample; stage_next <= FIND_OLDEST_INST_SAMPLE; elsif (remove_oldest_sample = '1') then - stage_next <= GET_OLDEST_SAMPLE_INSTANCE; + -- Synthesis Guard + if (WITH_KEY) then + stage_next <= GET_OLDEST_SAMPLE_INSTANCE; + else + cur_sample_next <= oldest_sample; + stage_next <= REMOVE_SAMPLE; + end if; else -- DONE stage_next <= IDLE; @@ -1705,98 +1817,101 @@ begin end if; end case; when GET_OLDEST_SAMPLE_INSTANCE => + -- Synthesis Guard + if (WITH_KEY) then + case (cnt) is + -- GET Instance Pointer (Oldest Sample) + when 0 => + sample_valid_in <= '1'; + sample_addr <= oldest_sample + SMF_INSTANCE_ADDR_OFFSET; + sample_read <= '1'; + + -- Memory Flow Control Guard + if (sample_ready_in = '1') then + cnt_next <= cnt + 1; + end if; + -- READ Instance Pointer (Oldest Sample) + when 1 => + -- Memory Operation Guard + if (inst_op_done = '1') then + sample_ready_out <= '1'; + + -- Memory Flow Control Guard + if (sample_valid_out = '1') then + -- NOTE: We have to initiate an instance "search" despite having direct access to the instance + -- in order to set up the 'previous' instance pointer required by the removal procedure + -- (Since we do not store previous pointers in the memory frame format) + inst_op_start <= '1'; + inst_opcode <= SEARCH_INSTANCE_ADDR; + inst_mem_fields <= IMF_SAMPLE_CNT_FLAG or IMF_WRITER_BITMAP_FLAG; + inst_addr_update <= sample_read_data; + + cur_sample_next <= oldest_sample; + stage_next <= REMOVE_SAMPLE; + end if; + end if; + when others => + null; + end case; + end if; + when FIND_OLDEST_INST_SAMPLE => + -- Precondition: cur_sample set - case (cnt) is - -- GET Instance Pointer (Oldest Sample) - when 0 => - sample_valid_in <= '1'; - sample_addr <= oldest_sample + SMF_INSTANCE_ADDR_OFFSET; - sample_read <= '1'; - - -- Memory Flow Control Guard - if (sample_ready_in = '1') then - cnt_next <= cnt + 1; - end if; - -- READ Instance Pointer (Oldest Sample) - when 1 => - -- Memory Operation Guard - if (inst_op_done = '1') then + -- Synthesis Guard + if (WITH_KEY) then + case (cnt) is + -- GET Instance Pointer + when 0 => + sample_ready_in <= '1'; + sample_addr <= cur_sample + SMF_INSTANCE_ADDR_OFFSET; + sample_read <= '1'; + + -- Memory Flow Control Guard + if (sample_ready_in = '1') then + cnt_next <= cnt + 1; + end if; + -- GET Next Sample + when 1 => + sample_ready_in <= '1'; + sample_addr <= cur_sample + SMF_NEXT_ADDR_OFFSET; + sample_read <= '1'; + + -- Memory Flow Control Guard + if (sample_ready_in = '1') then + cnt_next <= cnt + 1; + end if; + -- READ Instance Pointer + when 1 => sample_ready_out <= '1'; -- Memory Flow Control Guard if (sample_valid_out = '1') then - -- NOTE: We have to initiate an instance "search" despite having direct access to the instance - -- in order to set up the 'previous' instance pointer required by the removal procedure - -- (Since we do not store previous pointers in the memory frame format) - inst_op_start <= '1'; - inst_opcode <= SEARCH_INSTANCE_ADDR; - inst_mem_fields <= IMF_SAMPLE_CNT_FLAG or IMF_WRITER_BITMAP_FLAG; - inst_addr_update <= sample_read_data; - - cur_sample_next <= oldest_sample; - stage_next <= REMOVE_SAMPLE; + -- Oldest Instance Sample Found + if (sample_read_data = cur_inst) then + stage_next <= REMOVE_SAMPLE; + sample_abort_read <= '1'; + else + cnt_next <= cnt + 1; + end if; end if; - end if; - when others => - null; - end case; - when FIND_OLDEST_INST_SAMPLE => - -- Precondition: cur_sample set - - cnt_next <= cnt + 1; - - case (cnt) is - -- GET Instance Pointer - when 0 => - sample_ready_in <= '1'; - sample_addr <= cur_sample + SMF_INSTANCE_ADDR_OFFSET; - sample_read <= '1'; - - -- Memory Flow Control Guard - if (sample_ready_in = '1') then - cnt_next <= cnt + 1; - end if; - -- GET Next Sample - when 1 => - sample_ready_in <= '1'; - sample_addr <= cur_sample + SMF_NEXT_ADDR_OFFSET; - sample_read <= '1'; - - -- Memory Flow Control Guard - if (sample_ready_in = '1') then - cnt_next <= cnt + 1; - end if; - -- READ Instance Pointer - when 1 => - sample_ready_out <= '1'; - - -- Memory Flow Control Guard - if (sample_valid_out = '1') then - -- Oldest Instance Sample Found - if (sample_read_data = cur_inst) then - stage_next <= REMOVE_SAMPLE; - sample_abort_read <= '1'; - else - cnt_next <= cnt + 1; + -- READ Next Sample + when 2 => + sample_ready_out <= '1'; + + -- Memory Flow Control Guard + if (sample_valid_out = '1') then + cur_sample_next <= sample_read_data; + cnt_next <= 0; end if; - end if; - -- READ Next Sample - when 2 => - sample_ready_out <= '1'; - - -- Memory Flow Control Guard - if (sample_valid_out = '1') then - cur_sample_next <= sample_read_data; - cnt_next <= 0; - end if; - when others => - null; - end case; + when others => + null; + end case; + end if; when REMOVE_SAMPLE => -- Precondition: cur_sample set, sample_addr (Previous Pointer of cur_sample) -- Wait for Instance Search to finish - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then case (cnt) is -- GET Previous Sample @@ -1992,19 +2107,24 @@ begin end if; when POST_SAMPLE_REMOVE => -- Memory Operation Guard - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then -- No Instance Change on remove_oldest_inst_sample - if (remove_oldest_inst_sample /= '1') then + if (not WITH_KEY or remove_oldest_inst_sample /= '1') then tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); -- Instance obsolete and Instance Memory Full - if (inst_data.sample_cnt = 1 and tmp_bitmap = (tmp_bitmap'range => '0') and inst_empty_head = INSTANCE_MEMORY_MAX_ADDRESS) then + if (WITH_KEY and inst_data.sample_cnt = 1 and tmp_bitmap = (tmp_bitmap'range => '0') and inst_empty_head = INSTANCE_MEMORY_MAX_ADDRESS) then inst_op_start <= '1'; inst_opcode <= REMOVE_INSTANCE; else - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= IMF_SAMPLE_CNT_FLAG; - sample_cnt <= inst_data.sample_cnt - 1; + -- Synthesis Guard + if (WITH_KEY) then + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= IMF_SAMPLE_CNT_FLAG; + sample_cnt <= inst_data.sample_cnt - 1; + else + inst_data_nextsample_cnt <= inst_data.sample_cnt - 1; + end if; end if; end if; @@ -2069,76 +2189,68 @@ begin null; end case; when REMOVE_WRITER => - -- Memory Operation Guard - if (inst_op_done = '1') then - case (cnt) is - when 0 => - -- No More Instances - if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - -- DONE - stage_next <= IDLE; - else - -- Convert Writer Bitmap to SLV - tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); - - -- Remove Writer - tmp_bitmap(writer_pos) := '0'; - - -- NOTE: writer_bitmap is not latched, since the memory process is latching it at the - -- same clock cycle. - -- Convert Back - writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); - - -- No More Writers for Instance - if (tmp_bitmap = (tmp_bitmap'range => '0')) then - status_info_update <= inst_data.status; - status_info_update(NOT_ALIVE_DISPOSED_FLAG) <= '0'; - status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; - status_info_update(LIVELINESS_FLAG) <= '1'; - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; + -- Synthesis Guard + if (WITH_KEY) then + -- Memory Operation Guard + if (inst_op_done = '1') then + case (cnt) is + when 0 => + -- No More Instances + if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + -- DONE + stage_next <= IDLE; else - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= IMF_WRITER_BITMAP_FLAG; + -- Convert Writer Bitmap to SLV + tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); + + -- Remove Writer + tmp_bitmap(writer_pos) := '0'; + + -- NOTE: writer_bitmap is not latched, since the memory process is latching it at the + -- same clock cycle. + -- Convert Back + writer_bitmap <= from_endpoint_bitmap(tmp_bitmap); + + -- NOT_ALIVE_NO_WRITERS Transition + if (tmp_bitmap = (tmp_bitmap'range => '0') and inst_data.status(NOT_ALIVE_DISPOSED_FLAG) = '0') then + status_info_update <= inst_data.status; + status_info_update(NOT_ALIVE_NO_WRITERS_FLAG) <= '1'; + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; + else + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= IMF_WRITER_BITMAP_FLAG; + end if; + + -- Continue + cnt_next <= 1; end if; - - -- Continue - cnt_next <= 1; - end if; - when 1 => - inst_op_start <= '1'; - inst_opcode <= GET_NEXT_INSTANCE; - inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; - stage_next <= REMOVE_WRITER; - cnt_next <= 0; - when others => - null; - end case; + when 1 => + inst_op_start <= '1'; + inst_opcode <= GET_NEXT_INSTANCE; + inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; + stage_next <= REMOVE_WRITER; + cnt_next <= 0; + when 2 => + inst_op_start <= '1'; + inst_opcode <= GET_FIRST_INSTANCE; + inst_mem_fields <= IMF_STATUS_FLAG or IMF_WRITER_BITMAP_FLAG; + stage_next <= REMOVE_WRITER; + cnt_next <= 0; + when others => + null; + end case; + end if; end if; when REMOVE_STALE_INSTANCE => - -- Wait for Instance Data - if (inst_op_done = '1') then - -- Iterated through all Instances - if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - if (remove_oldest_inst_sample = '1') then - cur_sample <= oldest_sample; - stage_next <= FIND_OLDEST_INST_SAMPLE; - else - -- DONE - stage_next <= IDLE; - end if; - else - -- Convert Writer Bitmap to SLV - tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); - - -- Found Stale Instance (No Samples and No Active Writers) - if (inst_data.sample_cnt = 0 and tmp_bitmap = (tmp_bitmap'range => '0')) then - -- Remove Stale Instance - inst_op_start <= '1'; - inst_opcode <= REMOVE_INSTANCE; - + -- Synthesis Guard + if (WITH_KEY) then + -- Wait for Instance Data + if (inst_op_done = '1') then + -- Iterated through all Instances + if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then if (remove_oldest_inst_sample = '1') then cur_sample <= oldest_sample; stage_next <= FIND_OLDEST_INST_SAMPLE; @@ -2147,10 +2259,28 @@ begin stage_next <= IDLE; end if; else - -- Continue Search - inst_op_start <= '1'; - inst_opcode <= GET_NEXT_INSTANCE; - inst_mem_fields <= IMF_SAMPLE_CNT_FLAG or IMF_WRITER_BITMAP_FLAG; + -- Convert Writer Bitmap to SLV + tmp_bitmap := to_endpoint_bitmap(inst_data.writer_bitmap); + + -- Found Stale Instance (No Samples and No Active Writers) + if (inst_data.sample_cnt = 0 and tmp_bitmap = (tmp_bitmap'range => '0')) then + -- Remove Stale Instance + inst_op_start <= '1'; + inst_opcode <= REMOVE_INSTANCE; + + if (remove_oldest_inst_sample = '1') then + cur_sample <= oldest_sample; + stage_next <= FIND_OLDEST_INST_SAMPLE; + else + -- DONE + stage_next <= IDLE; + end if; + else + -- Continue Search + inst_op_start <= '1'; + inst_opcode <= GET_NEXT_INSTANCE; + inst_mem_fields <= IMF_SAMPLE_CNT_FLAG or IMF_WRITER_BITMAP_FLAG; + end if; end if; end if; end if; @@ -2246,7 +2376,7 @@ begin -- Instance pre-selected if (cur_inst /= INSTANCE_MEMORY_MAX_ADDRESS) then -- Sample has different Instance - if (cur_inst /= sample_read_data) then + if (WITH_KEY and cur_inst /= sample_read_data) then -- Consecutive Instance Sample Order if (not ORDERED_ACCESS or PRESENTATION_QOS = INSTANCE_PRESENTATION_QOS) then -- Skip Sample @@ -2280,23 +2410,31 @@ begin else -- Get Instance Data next_inst_next <= sample_read_data; - cnt_next <= cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + cnt_next <= cnt + 1; + else + cnt_next <= cnt + 2; + end if; end if; end if; -- Get Instance Data when 5 => - -- Memory Operation Guard - if (inst_op_done = '1') then - inst_op_start <= '1'; - inst_opcode <= GET_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; - inst_addr_update <= next_inst; - cnt_next <= cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + -- Memory Operation Guard + if (inst_op_done = '1') then + inst_op_start <= '1'; + inst_opcode <= GET_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; + inst_addr_update <= next_inst; + cnt_next <= cnt + 1; + end if; end if; -- Check Instance Data when 6 => -- Wait for Instance Data - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then -- DEFAULT tmp_bool := TRUE; @@ -2488,7 +2626,7 @@ begin -- Collection Empty if (collection_cnt = 0) then -- READ_NEXT_INSTANCE/TAKE_NEXT_INSTANCE Operation - if (dynamic_next_instance = '1') then + if (WITH_KEY and dynamic_next_instance = '1') then -- NOTE: We selected a compatible instance, but the instance has no compatible samples. -- Find next compatible instance. stage_next <= FIND_NEXT_INSTANCE; @@ -2647,7 +2785,7 @@ begin -- Memory Control Flow Guard if (sample_valid_out = '1') then -- Same Instance - if (sample_read_data = cur_inst) then + if (not WITH_KEY or sample_read_data = cur_inst) then -- Count Sample (No need to check Instance) collection_cnt_max_next <= collection_cnt_max + 1; si_sample_rank_sig_next <= si_sample_rank_sig + 1; @@ -2689,73 +2827,79 @@ begin end if; -- Get Instance Data when 10 => - -- Memory Operation Guard - if (inst_op_done = '1') then - inst_op_start <= '1'; - inst_opcode <= GET_INSTANCE_DATA_2; - inst_mem_fields <= IMF_STATUS_FLAG; - inst_addr_update <= next_inst; - cnt_next <= cnt + 1; + -- Synthesis Guard + if (WITH_KEY) then + -- Memory Operation Guard + if (inst_op_done = '1') then + inst_op_start <= '1'; + inst_opcode <= GET_INSTANCE_DATA_2; + inst_mem_fields <= IMF_STATUS_FLAG; + inst_addr_update <= next_inst; + cnt_next <= cnt + 1; + end if; end if; -- Check Instance Data when 11 => - -- Wait for Instance Data - if (inst_op_done = '1') then - -- DEFAULT - tmp_bool := TRUE; - - -- Check Instance State - case (instance_state) is - when ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then + -- Synthesis Guard + if (WITH_KEY) then + -- Wait for Instance Data + if (inst_op_done = '1') then + -- DEFAULT + tmp_bool := TRUE; + + -- Check Instance State + case (instance_state) is + when ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_DISPOSED_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when ANY_INSTANCE_STATE => + null; + when others => tmp_bool := FALSE; - end if; - when NOT_ALIVE_DISPOSED_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then + end case; + + -- Check View State + case (view_state) is + when NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when ANY_VIEW_STATE => + null; + when others => tmp_bool := FALSE; - end if; - when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when ANY_INSTANCE_STATE => - null; - when others => + end case; + + -- Check Instance Mark + if (inst_data.status_info(MARK_FLAG) = '1') then + -- Skip Marked Instance tmp_bool := FALSE; - end case; - - -- Check View State - case (view_state) is - when NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '1') then - tmp_bool := FALSE; - end if; - when ANY_VIEW_STATE => - null; - when others => - tmp_bool := FALSE; - end case; - - -- Check Instance Mark - if (inst_data.status_info(MARK_FLAG) = '1') then - -- Skip Marked Instance - tmp_bool := FALSE; + end if; + + -- Instance passes Checks + if (tmp_bool) then + -- Count Sample + collection_cnt_max_next <= collection_cnt_max + 1; + end if; + cnt_next <= cnt + 1; end if; - - -- Instance passes Checks - if (tmp_bool) then - -- Count Sample - collection_cnt_max_next <= collection_cnt_max + 1; - end if; - cnt_next <= cnt + 1; end if; -- Exit State when 12 => @@ -2780,9 +2924,9 @@ begin -- Finalize Sample Info Data when 0 => -- Wait for Instance Data - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then -- Instance Data valid - if (inst_addr_base = cur_inst) then + if (not WITH_KEY or inst_addr_base = cur_inst) then -- Sample Info View State if (inst_data.status_info(VIEW_FLAG) = '1') then si_view_state_sig_next <= NEW_VIEW_STATE; @@ -2852,33 +2996,42 @@ begin -- Post-Present Data when 2 => -- Memory Operation Guard - if (inst_op_done = '1') then + if (not WITH_KEY or inst_op_done = '1') then -- NOTE: If we have a presentation of consecutive same instance samples of multiple instances, we have to -- mark the instances we have already handled, in order to prevent the GET_NEXT_SAMPLE state to -- re-process them. -- Last Sample of Instance in Collection if (si_sample_rank_sig = 1) then - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= IMF_STATUS_FLAG; - status_info_update <= inst_data.status_info; - - -- Consecutive Instance Sample Order of multiple Instances - if ((not ORDERED_ACCESS or PRESENTATION_QOS = INSTANCE_PRESENTATION_QOS) and single_instance = '0' and single_sample = '0') then - -- Completed Collection - if (collection_cnt = max_samples) then - -- Unmark Instances - unmark_instances_next <= '1'; - else - -- Mark Instance - status_info_update(MARK_FLAG) <= '1'; + -- Synthesis Guard + if (WITH_KEY) then + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= IMF_STATUS_FLAG; + status_info_update <= inst_data.status_info; + + -- Consecutive Instance Sample Order of multiple Instances + if ((not ORDERED_ACCESS or PRESENTATION_QOS = INSTANCE_PRESENTATION_QOS) and single_instance = '0' and single_sample = '0') then + -- Completed Collection + if (collection_cnt = max_samples) then + -- Unmark Instances + unmark_instances_next <= '1'; + else + -- Mark Instance + status_info_update(MARK_FLAG) <= '1'; + end if; + end if; + + -- Instance is NOT_VIEWED and sample is from last generation of Instance + if (inst_data.status_info(VIEW_FLAG) = '0' and si_absolute_generation_count_sig = 0) then + -- Mark Instance as VIEWED + status_info_update(VIEW_FLAG) <= '1'; + end if; + else + -- Instance is NOT_VIEWED and sample is from last generation of Instance + if (inst_data.status_info(VIEW_FLAG) = '0' and si_absolute_generation_count_sig = 0) then + -- Mark Instance as VIEWED + inst_data_next.status_info(VIEW_FLAG) <= '1'; end if; - end if; - - -- Instance is NOT_VIEWED and sample is from last generation of Instance - if (inst_data.status_info(VIEW_FLAG) = '0' and si_absolute_generation_count_sig = 0) then - -- Mark Instance as VIEWED - status_info_update(VIEW_FLAG) <= '1'; end if; end if; @@ -3020,170 +3173,176 @@ begin cnt_next <= 2; end if; when FIND_NEXT_INSTANCE => - -- Wait for Instance Data - if (inst_op_done = '1') then - case (cnt) is - when 0 => - -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. - inst_op_start <= '1'; - inst_opcode <= GET_FIRST_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; - cnt_next <= 2; - when 1 => - -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. - inst_op_start <= '1'; - inst_opcode <= GET_NEXT_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; - cnt_next <= 2; - when 2 => - -- Instance Found - if (inst_addr_base /= SAMPLE_MEMORY_MAX_ADDRESS) then - -- DEFAULT - tmp_bool := TRUE; - - -- Check Instance Handle (Key Hash) - -- XXX: Posible Worst Case Path (128-bit Comparison) - if (to_unsigned(inst_data.key_hash) =< to_unsigned(key_hash)) then - tmp_bool := FALSE; - end if; - - -- Check Instance State - case (instance_state) is - when ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_DISPOSED_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when ANY_INSTANCE_STATE => - null; - when others => + -- Synthesis Guard + if (WITH_KEY) then + -- Wait for Instance Data + if (inst_op_done = '1') then + case (cnt) is + when 0 => + -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. + inst_op_start <= '1'; + inst_opcode <= GET_FIRST_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; + cnt_next <= 2; + when 1 => + -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. + inst_op_start <= '1'; + inst_opcode <= GET_NEXT_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; + cnt_next <= 2; + when 2 => + -- Instance Found + if (inst_addr_base /= SAMPLE_MEMORY_MAX_ADDRESS) then + -- DEFAULT + tmp_bool := TRUE; + + -- Check Instance Handle (Key Hash) + -- XXX: Posible Worst Case Path (128-bit Comparison) + if (to_unsigned(inst_data.key_hash) =< to_unsigned(key_hash)) then tmp_bool := FALSE; - end case; - - -- Check View State - case (view_state) is - when NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '0') then + end if; + + -- Check Instance State + case (instance_state) is + when ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_DISPOSED_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when ANY_INSTANCE_STATE => + null; + when others => tmp_bool := FALSE; - end if; - when NOT_NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '1') then + end case; + + -- Check View State + case (view_state) is + when NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when ANY_VIEW_STATE => + null; + when others => tmp_bool := FALSE; - end if; - when ANY_VIEW_STATE => - null; - when others => - tmp_bool := FALSE; - end case; - - -- Instance Passes Checks - if (tmp_bool) then - cur_inst <= inst_addr_base; - stage_next <= GET_NEXT_SAMPLE; - else - -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. - inst_op_start <= '1'; - inst_opcode <= GET_NEXT_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; - end if; - else - -- DONE - done_dds <= '1'; - return_code_dds <= RETCODE_NO_DATA; - stage_next <= IDLE; - end if; - when others => - null; - end case; - end if; - when CHECK_INSTANCE => - -- Wait for Instance Data - if (inst_op_done = '1') then - case (cnt) is - when 0 => - -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. - inst_op_start <= '1'; - inst_opcode <= SEARCH_INSTANCE_HASH; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; - cnt_next <= 1; - when 1 => - -- Instance Found - if (inst_addr_base /= SAMPLE_MEMORY_MAX_ADDRESS) then - -- DEFAULT - tmp_bool := TRUE; - - -- Check Instance State - case (instance_state) is - when ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_DISPOSED_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_ALIVE_INSTANCE_STATE => - if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when ANY_INSTANCE_STATE => - null; - when others => - tmp_bool := FALSE; - end case; - - -- Check View State - case (view_state) is - when NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '0') then - tmp_bool := FALSE; - end if; - when NOT_NEW_VIEW_STATE => - if (inst_data.status_info(VIEW_FLAG) = '1') then - tmp_bool := FALSE; - end if; - when ANY_VIEW_STATE => - null; - when others => - tmp_bool := FALSE; - end case; - - -- Instance Passes Checks - if (tmp_bool) then - -- Get Instance Samples - cur_inst <= inst_addr_base; - stage_next <= GET_NEXT_SAMPLE; + end case; + + -- Instance Passes Checks + if (tmp_bool) then + cur_inst <= inst_addr_base; + stage_next <= GET_NEXT_SAMPLE; + else + -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. + inst_op_start <= '1'; + inst_opcode <= GET_NEXT_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; + end if; else -- DONE done_dds <= '1'; return_code_dds <= RETCODE_NO_DATA; stage_next <= IDLE; end if; - else - -- Given Instance does not exist - -- DONE - done_dds <= '1'; - return_code_dds <= RETCODE_BAD_PARAMETER; - stage_next <= IDLE; - end if; - when others => - null; - end case; + when others => + null; + end case; + end if; + end if; + when CHECK_INSTANCE => + -- Synthesis Guard + if (WITH_KEY) then + -- Wait for Instance Data + if (inst_op_done = '1') then + case (cnt) is + when 0 => + -- NOTE: The Generation Counters are not used directly in this state, but will be needed by the FINALIZE_SAMPLE_INFO state. + inst_op_start <= '1'; + inst_opcode <= SEARCH_INSTANCE_HASH; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG or IMF_DISPOSED_CNT_FLAG or IMF_NO_WRITERS_CNT_FLAG; + cnt_next <= 1; + when 1 => + -- Instance Found + if (inst_addr_base /= SAMPLE_MEMORY_MAX_ADDRESS) then + -- DEFAULT + tmp_bool := TRUE; + + -- Check Instance State + case (instance_state) is + when ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '1' or inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_DISPOSED_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_NO_WRITERS_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_ALIVE_INSTANCE_STATE => + if (inst_data.status_info(NOT_ALIVE_DISPOSED_FLAG) = '0' and inst_data.status_info(NOT_ALIVE_NO_WRITERS_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when ANY_INSTANCE_STATE => + null; + when others => + tmp_bool := FALSE; + end case; + + -- Check View State + case (view_state) is + when NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '0') then + tmp_bool := FALSE; + end if; + when NOT_NEW_VIEW_STATE => + if (inst_data.status_info(VIEW_FLAG) = '1') then + tmp_bool := FALSE; + end if; + when ANY_VIEW_STATE => + null; + when others => + tmp_bool := FALSE; + end case; + + -- Instance Passes Checks + if (tmp_bool) then + -- Get Instance Samples + cur_inst <= inst_addr_base; + stage_next <= GET_NEXT_SAMPLE; + else + -- DONE + done_dds <= '1'; + return_code_dds <= RETCODE_NO_DATA; + stage_next <= IDLE; + end if; + else + -- Given Instance does not exist + -- DONE + done_dds <= '1'; + return_code_dds <= RETCODE_BAD_PARAMETER; + stage_next <= IDLE; + end if; + when others => + null; + end case; + end if; end if; when CHECK_LIFESPAN => -- Precondition: cur_sample set, @@ -3357,168 +3516,210 @@ begin end case; end if; when CHECK_DEADLINE => - -- Memory Operation Guard - if (inst_op_done = '1') then - case (cnt) is - -- Get First Instance - when 0 => - inst_op_start <= '1'; - inst_opcode <= GET_FIRST_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG; - cnt_next <= 2; - -- Get Next Instance - when 1 => - inst_op_start <= '1'; - inst_opcode <= GET_NEXT_INSTANCE; - inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG; - cnt_next <= 2; - -- Check Instance - when 2 => - -- Reached End of Instances - if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - -- DONE - stage_next <= IDLE; - else - -- Instance received Sample - if (inst_data.status_info(LIVELINESS_FLAG) = '1') then - -- Reset Liveliness Flag - inst_op_start <= '1'; - inst_opcode <= UPDATE_INSTANCE; - inst_mem_fields <= IMF_STATUS_FLAG; - status_info_update <= inst_data.status_info; - status_info_update(LIVELINESS_FLAG) <= '0'; - cnt_next <= 1; + -- Synthesis Guard + if (WITH_KEY) then + -- Memory Operation Guard + if (inst_op_done = '1') then + case (cnt) is + -- Get First Instance + when 0 => + inst_op_start <= '1'; + inst_opcode <= GET_FIRST_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG; + cnt_next <= 2; + -- Get Next Instance + when 1 => + inst_op_start <= '1'; + inst_opcode <= GET_NEXT_INSTANCE; + inst_mem_fields <= IMF_KEY_HASH_FLAG or IMF_STATUS_FLAG; + cnt_next <= 2; + -- Check Instance + when 2 => + -- Reached End of Instances + if (inst_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + -- DONE + stage_next <= IDLE; else - -- Update Requested Deadline Missed Status - status_sig_next(REQUESTED_DEADLINE_MISSED_STATUS) <= '1'; - deadline_miss_cnt_next <= deadline_miss_cnt + 1; - deadline_miss_cnt_change_next <= deadline_miss_cnt_change + 1; - deadline_miss_last_inst_next <= inst_data.key_hash; - cnt_next <= 1; + -- Instance received Sample + if (inst_data.status_info(LIVELINESS_FLAG) = '1') then + -- Reset Liveliness Flag + inst_op_start <= '1'; + inst_opcode <= UPDATE_INSTANCE; + inst_mem_fields <= IMF_STATUS_FLAG; + status_info_update <= inst_data.status_info; + status_info_update(LIVELINESS_FLAG) <= '0'; + cnt_next <= 1; + else + -- Update Requested Deadline Missed Status + status_sig_next(REQUESTED_DEADLINE_MISSED_STATUS) <= '1'; + deadline_miss_cnt_next <= deadline_miss_cnt + 1; + deadline_miss_cnt_change_next <= deadline_miss_cnt_change + 1; + deadline_miss_last_inst_next <= inst_data.key_hash; + cnt_next <= 1; + end if; end if; - end if; - when others => - null; - end case; + when others => + null; + end case; + end if; end if; when others => null; end case; end process; - -- *Instance Memory Process* - -- STATE DESCRIPTION - -- IDLE Idle State. Done Signal is pulled high and Memory FSM accepts new memory operations - -- SEARCH_INSTANCE_HASH See Memory OPCODE Description - -- SEARCH_INSTANCE_ADDR See Memory OPCODE Description - -- GET_NEXT_INSTANCE See Memory OPCODE Description - -- GET_INSTANCE_DATA Latch specified Instance Data for use by main process - -- FIND_POS Find List position of Instance to be added - -- INSERT_INSTANCE See Memory OPCODE Description - -- UPDATE_INSTANCE See Memory OPCODE Description - -- REMOVE_INSTANCE See Memory OPCODE Description - -- UNMARK_INTANCES See Memory OPCODE Description - inst_ctrl_prc : process(all) - begin - -- DEFAULT Registered - inst_stage_next <= inst_stage; - inst_addr_base_next <= inst_addr_base; - inst_empty_head_next <= inst_empty_head; - inst_occupied_head_next <= inst_occupied_head; - inst_latch_data_next <= inst_latch_data; - inst_next_addr_base_next <= inst_next_addr_base; - inst_prev_addr_base_next <= inst_prev_addr_base; - inst_cnt_next <= inst_cnt; - inst_cnt2_next <= inst_cnt2; - inst_data_next <= inst_data; - inst_long_latch_next <= inst_long_latch; - -- DEFAULT Unregistered - inst_ready_out <= '0'; - inst_valid_in <= '0'; - inst_read <= '0'; - inst_op_done <= '0'; - inst_addr <= (others => '0'); - inst_write_data <= (others => '0'); - - - case (mem_stage) is - when IDLE => - inst_op_done <= '1'; - - if (inst_op_start = '1') then - -- Latch Signals needed for Mermory Operation (Use _next signals, because some signals are set in same clk) - inst_latch_data_next <= ( - key_hash => key_hash_next, - status_info => status_info_update, - sample_cnt => sample_cnt, - gen_cnt => gen_cnt, - deadline => deadline, - writer_bitmap => writer_bitmap, - field_flags => inst_mem_fields, - addr => inst_addr_update - ); + gen_inst_ctrl_prc : if WITH_KEY generate + + -- *Instance Memory Process* + -- STATE DESCRIPTION + -- IDLE Idle State. Done Signal is pulled high and Memory FSM accepts new memory operations + -- SEARCH_INSTANCE_HASH See Memory OPCODE Description + -- SEARCH_INSTANCE_ADDR See Memory OPCODE Description + -- GET_NEXT_INSTANCE See Memory OPCODE Description + -- GET_INSTANCE_DATA Latch specified Instance Data for use by main process + -- FIND_POS Find List position of Instance to be added + -- INSERT_INSTANCE See Memory OPCODE Description + -- UPDATE_INSTANCE See Memory OPCODE Description + -- REMOVE_INSTANCE See Memory OPCODE Description + -- UNMARK_INTANCES See Memory OPCODE Description + inst_ctrl_prc : process(all) + begin + -- DEFAULT Registered + inst_stage_next <= inst_stage; + inst_addr_base_next <= inst_addr_base; + inst_empty_head_next <= inst_empty_head; + inst_occupied_head_next <= inst_occupied_head; + inst_latch_data_next <= inst_latch_data; + inst_next_addr_base_next <= inst_next_addr_base; + inst_prev_addr_base_next <= inst_prev_addr_base; + inst_cnt_next <= inst_cnt; + inst_cnt2_next <= inst_cnt2; + inst_data_next <= inst_data; + inst_long_latch_next <= inst_long_latch; + -- DEFAULT Unregistered + inst_ready_out <= '0'; + inst_valid_in <= '0'; + inst_read <= '0'; + inst_op_done <= '0'; + inst_addr <= (others => '0'); + inst_write_data <= (others => '0'); + + + case (mem_stage) is + when IDLE => + inst_op_done <= '1'; - case(inst_opcode) is - when SEARCH_INSTANCE_HASH => - -- Reset Data - inst_data_next <= ZERO_INSTANCE_DATA; - - -- No Instances avialable - if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - else - inst_prev_addr_base <= INSTANCE_MEMORY_MAX_ADDRESS; - inst_addr_base_next <= inst_occupied_head; - inst_stage_next <= SEARCH_INSTANCE_HASH; - inst_cnt_next <= 0; - end if; - when SEARCH_INSTANCE_ADDR => - -- Reset Data - inst_data_next <= ZERO_INSTANCE_DATA; - - -- No Instances avialable - if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - else - inst_prev_addr_base <= INSTANCE_MEMORY_MAX_ADDRESS; - inst_addr_base_next <= inst_occupied_head; - inst_stage_next <= SEARCH_INSTANCE_ADDR; - inst_cnt_next <= 0; - end if; - when INSERT_INSTANCE => - -- NOTE: Since this process has no way to communicate a failed insert to the main process, it has to be made sure - -- by the main process that the operation can succeed (Memory is available) - assert (inst_empty_head /= INSTANCE_MEMORY_MAX_ADDRESS) report "Instance Insertion while memory Full" severity FAILURE; - - inst_addr_base_next <= inst_occupied_head; - inst_stage_next <= FIND_POS; - inst_cnt_next <= 0; - when UPDATE_INSTANCE => - inst_stage_next <= UPDATE_INSTANCE; - if check_mask(inst_mem_fields.field_flag,IMF_STATUS_FLAG) then + if (inst_op_start = '1') then + -- Latch Signals needed for Mermory Operation (Use _next signals, because some signals are set in same clk) + inst_latch_data_next <= ( + key_hash => key_hash_next, + status_info => status_info_update, + sample_cnt => sample_cnt, + gen_cnt => gen_cnt, + deadline => deadline, + writer_bitmap => writer_bitmap, + field_flags => inst_mem_fields, + addr => inst_addr_update + ); + + case(inst_opcode) is + when SEARCH_INSTANCE_HASH => + -- Reset Data + inst_data_next <= ZERO_INSTANCE_DATA; + + -- No Instances avialable + if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + else + inst_prev_addr_base <= INSTANCE_MEMORY_MAX_ADDRESS; + inst_addr_base_next <= inst_occupied_head; + inst_stage_next <= SEARCH_INSTANCE_HASH; + inst_cnt_next <= 0; + end if; + when SEARCH_INSTANCE_ADDR => + -- Reset Data + inst_data_next <= ZERO_INSTANCE_DATA; + + -- No Instances avialable + if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + else + inst_prev_addr_base <= INSTANCE_MEMORY_MAX_ADDRESS; + inst_addr_base_next <= inst_occupied_head; + inst_stage_next <= SEARCH_INSTANCE_ADDR; + inst_cnt_next <= 0; + end if; + when INSERT_INSTANCE => + -- NOTE: Since this process has no way to communicate a failed insert to the main process, it has to be made sure + -- by the main process that the operation can succeed (Memory is available) + assert (inst_empty_head /= INSTANCE_MEMORY_MAX_ADDRESS) report "Instance Insertion while memory Full" severity FAILURE; + + inst_addr_base_next <= inst_occupied_head; + inst_stage_next <= FIND_POS; + inst_cnt_next <= 0; + when UPDATE_INSTANCE => + inst_stage_next <= UPDATE_INSTANCE; + if check_mask(inst_mem_fields.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 0; + elsif check_mask(inst_mem_fields.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 1; + elsif check_mask(inst_mem_fields.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 2; + elsif check_mask(inst_mem_fields.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 3; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_mem_fields.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 4; + elsif check_mask(inst_mem_fields.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 6; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + when GET_FIRST_INSTANCE => + -- No Instances avialable + if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + else + inst_prev_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + inst_addr_base_next <= inst_occupied_head; + -- Get Instance Data + inst_stage_next <= GET_INSTANCE_DATA; + if check_mask(inst_mem_fields.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 0; + elsif check_mask(inst_mem_fields.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 4; + elsif check_mask(inst_mem_fields.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 5; + elsif check_mask(inst_mem_fields.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 6; + elsif check_mask(inst_mem_fields.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_mem_fields.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_mem_fields.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + when GET_NEXT_INSTANCE => + -- No Instances avialable + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + else + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + inst_stage_next <= GET_NEXT_INSTANCE; + inst_cnt_next <= 0; + end if; + when REMOVE_INSTANCE => + inst_stage_next <= REMOVE_INSTANCE; inst_cnt_next <= 0; - elsif check_mask(inst_mem_fields.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 1; - elsif check_mask(inst_mem_fields.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 2; - elsif check_mask(inst_mem_fields.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 3; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_mem_fields.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 4; - elsif check_mask(inst_mem_fields.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 6; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - when GET_FIRST_INSTANCE => - -- No Instances avialable - if (inst_occupied_head = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - else - inst_prev_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - inst_addr_base_next <= inst_occupied_head; + when GET_INSTANCE => + inst_addr_base_next <= inst_addr_update; -- Get Instance Data inst_stage_next <= GET_INSTANCE_DATA; if check_mask(inst_mem_fields.field_flag,IMF_KEY_HASH_FLAG) then @@ -3540,209 +3741,278 @@ begin -- DONE inst_stage_next <= IDLE; end if; + when UNMARK_INSTANCES => + -- Empty Memory Guard + if (inst_occupied_head /= INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= inst_occupied_head; + inst_stage_next <= UNMARK_INSTANCES; + inst_cnt_next <= 0; + end if; + when others => + null; + end case; + end if; + when SEARCH_INSTANCE_HASH => + + case (inst_cnt) is + -- GET Next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; end if; - when GET_NEXT_INSTANCE => - -- No Instances avialable - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - else - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - inst_stage_next <= GET_NEXT_INSTANCE; - inst_cnt_next <= 0; + -- GET Key Hash 1/4 + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; end if; - when REMOVE_INSTANCE => - inst_stage_next <= REMOVE_INSTANCE; - inst_cnt_next <= 0; - when GET_INSTANCE => - inst_addr_base_next <= inst_addr_update; - -- Get Instance Data - inst_stage_next <= GET_INSTANCE_DATA; - if check_mask(inst_mem_fields.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 0; - elsif check_mask(inst_mem_fields.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 4; - elsif check_mask(inst_mem_fields.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 5; - elsif check_mask(inst_mem_fields.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 6; - elsif check_mask(inst_mem_fields.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_mem_fields.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_mem_fields.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; + -- GET Key Hash 2/4 + when 2 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; end if; - when UNMARK_INSTANCES => - -- Empty Memory Guard - if (inst_occupied_head /= INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= inst_occupied_head; - inst_stage_next <= UNMARK_INSTANCES; - inst_cnt_next <= 0; + -- GET Key Hash 3/4 + when 3 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 4/4 + when 4 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Next Instance + when 5 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_next_addr_base_next <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Key Hash 1/4 + when 6 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- No Match + if (inst_read_data /= inst_latch_data.key_hash(0)) then + -- Reached List Tail, No Match + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match + -- DONE + inst_stage_next <= IDLE; + else + -- Continue Search + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + inst_cnt_next <= 0; + inst_abort_read <= '1'; + end if; + else + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- READ Key Hash 2/4 + when 7 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- No Match + if (inst_read_data /= inst_latch_data.key_hash(1)) then + -- Reached List Tail, No Match + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match + -- DONE + inst_stage_next <= IDLE; + else + -- Continue Search + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + inst_cnt_next <= 0; + inst_abort_read <= '1'; + end if; + else + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- READ Key Hash 3/4 + when 8 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- No Match + if (inst_read_data /= inst_latch_data.key_hash(2)) then + -- Reached List Tail, No Match + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match + -- DONE + inst_stage_next <= IDLE; + else + -- Continue Search + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + inst_cnt_next <= 0; + inst_abort_read <= '1'; + end if; + else + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- READ Key Hash 4/4 + when 9 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- No Match + if (inst_read_data /= inst_latch_data.key_hash(3)) then + -- Reached List Tail, No Match + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match + -- DONE + inst_stage_next <= IDLE; + else + -- Continue Search + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + inst_cnt_next <= 0; + inst_abort_read <= '1'; + end if; + else + -- Get Instance Data + inst_stage_next <= GET_INSTANCE_DATA; + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 0; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 5; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 6; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; end if; when others => null; end case; - end if; - when SEARCH_INSTANCE_HASH => - - case (inst_cnt) is - -- GET Next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 1/4 - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 2/4 - when 2 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 3/4 - when 3 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 4/4 - when 4 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 5 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_next_addr_base_next <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Key Hash 1/4 - when 6 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- No Match - if (inst_read_data /= inst_latch_data.key_hash(0)) then - -- Reached List Tail, No Match - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match - -- DONE - inst_stage_next <= IDLE; - else - -- Continue Search - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - inst_cnt_next <= 0; - inst_abort_read <= '1'; - end if; - else + when SEARCH_INSTANCE_ADDR => + + case (inst_cnt) is + -- GET Next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then inst_cnt_next <= inst_cnt + 1; end if; - end if; - -- READ Key Hash 2/4 - when 7 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- No Match - if (inst_read_data /= inst_latch_data.key_hash(1)) then - -- Reached List Tail, No Match - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match - -- DONE - inst_stage_next <= IDLE; + -- READ Next Instance + when 1 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_read_data; + + -- Match + if (inst_read_data = inst_latch_data.addr) then + -- Get Instance Data + inst_stage_next <= GET_INSTANCE_DATA; + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 0; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 5; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 6; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + -- No Match else - -- Continue Search - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - inst_cnt_next <= 0; - inst_abort_read <= '1'; + -- Reached List Tail, No Match + if (inst_read_data = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match + -- DONE + inst_stage_next <= IDLE; + else + -- Continue Search + inst_cnt_next <= 0; + end if; end if; - else + end if; + when others => + null; + end case; + when GET_NEXT_INSTANCE => + case (inst_cnt) is + -- GET next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then inst_cnt_next <= inst_cnt + 1; end if; - end if; - -- READ Key Hash 3/4 - when 8 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- No Match - if (inst_read_data /= inst_latch_data.key_hash(2)) then - -- Reached List Tail, No Match - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match - -- DONE - inst_stage_next <= IDLE; - else - -- Continue Search - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - inst_cnt_next <= 0; - inst_abort_read <= '1'; - end if; - else - inst_cnt_next <= inst_cnt + 1; - end if; - end if; - -- READ Key Hash 4/4 - when 9 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- No Match - if (inst_read_data /= inst_latch_data.key_hash(3)) then - -- Reached List Tail, No Match - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match - -- DONE - inst_stage_next <= IDLE; - else - -- Continue Search - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - inst_cnt_next <= 0; - inst_abort_read <= '1'; - end if; - else + -- READ Next Instance + when 1 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_next_addr_base_next <= inst_read_data; -- Get Instance Data inst_stage_next <= GET_INSTANCE_DATA; if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then @@ -3765,39 +4035,50 @@ begin inst_stage_next <= IDLE; end if; end if; - end if; - when others => - null; - end case; - when SEARCH_INSTANCE_ADDR => - - case (inst_cnt) is - -- GET Next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 1 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_read_data; - - -- Match - if (inst_read_data = inst_latch_data.addr) then - -- Get Instance Data - inst_stage_next <= GET_INSTANCE_DATA; - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 0; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + when others => + null; + end case; + when GET_INSTANCE_DATA => + case (inst_cnt) is + -- GET Key Hash 1/4 + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 2/4 + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 3/4 + when 2 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 4/4 + when 3 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then inst_cnt_next <= 4; elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then inst_cnt_next <= 5; @@ -3811,258 +4092,101 @@ begin inst_cnt_next <= 10; inst_cnt2_next <= 0; else - -- DONE - inst_stage_next <= IDLE; - end if; - -- No Match - else - -- Reached List Tail, No Match - if (inst_read_data = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; --No match - -- DONE - inst_stage_next <= IDLE; - else - -- Continue Search - inst_cnt_next <= 0; - end if; - end if; - end if; - when others => - null; - end case; - when GET_NEXT_INSTANCE => - case (inst_cnt) is - -- GET next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 1 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_next_addr_base_next <= inst_read_data; - -- Get Instance Data - inst_stage_next <= GET_INSTANCE_DATA; - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 0; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 5; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 6; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - when others => - null; - end case; - when GET_INSTANCE_DATA => - case (inst_cnt) is - -- GET Key Hash 1/4 - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 2/4 - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 3/4 - when 2 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 4/4 - when 3 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 5; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 6; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - inst_cnt_next <= 11; - end if; - end if; - -- GET Status Info - when 4 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 5; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 6; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then inst_cnt_next <= 11; - else - inst_cnt_next <= 15; end if; end if; - end if; - -- GET Sample Count - when 5 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 6; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 11; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 15; - else - inst_cnt_next <= 16; - end if; - end if; - end if; - -- GET Disposed Generation Count - when 6 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_DISPOSED_GEN_CNT_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 7; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 11; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 15; - elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 16; - else - inst_cnt_next <= 17; - end if; - end if; - end if; - -- GET No Writers Generation Count - when 7 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NO_WRITERS_GEN_CNT_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 8; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 10; - inst_cnt2_next <= 0; - else - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 11; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 15; - elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 16; + -- GET Status Info + when 4 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 5; elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 17; + inst_cnt_next <= 6; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; else - inst_cnt_next <= 18; + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 11; + else + inst_cnt_next <= 15; + end if; end if; end if; - end if; - -- GET Ignore Deadline 1/2 - when 8 => - -- Synthesis Guard - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + -- GET Sample Count + when 5 => inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; inst_read <= '1'; -- Memory Flow Control Guard if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; + if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 6; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 11; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 15; + else + inst_cnt_next <= 16; + end if; + end if; end if; - end if; - -- GET Ignore Deadline 2/2 - when 9 => - -- Synthesis Guard - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + -- GET Disposed Generation Count + when 6 => inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + 1; + inst_addr <= inst_addr_base + IMF_DISPOSED_GEN_CNT_OFFSET; inst_read <= '1'; -- Memory Flow Control Guard if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 7; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 11; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 15; + elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 16; + else + inst_cnt_next <= 17; + end if; + end if; + end if; + -- GET No Writers Generation Count + when 7 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NO_WRITERS_GEN_CNT_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 8; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then inst_cnt_next <= 10; inst_cnt2_next <= 0; else @@ -4074,28 +4198,121 @@ begin inst_cnt_next <= 16; elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then inst_cnt_next <= 17; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 18; else - inst_cnt_next <= 19; + inst_cnt_next <= 18; end if; end if; end if; - end if; - -- GET Writer Bitmap - when 10 => - -- XXX: Possible Worst case Path (2 Additions in same clock) - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + inst_cnt2; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- Exit Condition - if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then - if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then - inst_cnt_next <= 11; - elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + -- GET Ignore Deadline 1/2 + when 8 => + -- Synthesis Guard + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- GET Ignore Deadline 2/2 + when 9 => + -- Synthesis Guard + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + 1; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 10; + inst_cnt2_next <= 0; + else + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 11; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 15; + elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 16; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 17; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 18; + else + inst_cnt_next <= 19; + end if; + end if; + end if; + end if; + -- GET Writer Bitmap + when 10 => + -- XXX: Possible Worst case Path (2 Additions in same clock) + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + inst_cnt2; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + -- Exit Condition + if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then + if check_mask(inst_latch_data.field_flag,IMF_KEY_HASH_FLAG) then + inst_cnt_next <= 11; + elsif check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then + inst_cnt_next <= 15; + elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 16; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 17; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 18; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 19; + else + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + end if; + else + inst_cnt2_next <= inst_cnt2 + 1; + end if; + end if; + -- READ Key Hash 1/4 + when 11 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.key_hash(0) <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Key Hash 2/4 + when 12 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.key_hash(1) <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Key Hash 3/4 + when 13 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.key_hash(2) <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Key Hash 4/4 + when 14 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.key_hash(3) <= inst_read_data; + + if check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then inst_cnt_next <= 15; elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then inst_cnt_next <= 16; @@ -4105,666 +4322,524 @@ begin inst_cnt_next <= 18; elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then inst_cnt_next <= 19; - else + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then inst_cnt_next <= 21; inst_cnt2_next <= 0; - end if; - else - inst_cnt2_next <= inst_cnt2 + 1; - end if; - end if; - -- READ Key Hash 1/4 - when 11 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.key_hash(0) <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Key Hash 2/4 - when 12 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.key_hash(1) <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Key Hash 3/4 - when 13 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.key_hash(2) <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Key Hash 4/4 - when 14 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.key_hash(3) <= inst_read_data; - - if check_mask(inst_latch_data.field_flag,IMF_STATUS_FLAG) then - inst_cnt_next <= 15; - elsif check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 16; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 17; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 18; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 19; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ Status Info - when 15 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.status_info <= inst_read_data; - - if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 16; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 17; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 18; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 19; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ Sample Count - when 16 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.sample_cnt <= inst_read_data; - - if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 17; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 18; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 19; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ Disposed Generation Count - when 17 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.disposed_gen_cnt <= inst_read_data; - - if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 18; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 19; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ No Writers Generation Count - when 18 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.no_writers_gen_cnt <= inst_read_data; - - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 19; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ Ignore Deadline 1/2 - when 19 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.ignore_deadline(0) <= inst_read_data; - - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Ignore Deadline 2/2 - when 20 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.ignore_deadline(1) <= inst_read_data; - - if check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 21; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- READ Writer Bitamp - when 21 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_latch_data_next.writer_bitmap(inst_cnt2) <= inst_read_data; - -- Exit Condition - if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then - -- DONE - inst_stage_next <= IDLE; - else - inst_cnt2_next <= inst_cnt2 + 1; - end if; - end if; - end case; - when FIND_POS => - -- NOTE: Instances are inserted in KEY_HASH numerical order. - - -- TODO: Handle inst_next_addr_base = MAX_ADDR - - case (inst_cnt) is - -- GET Next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 1/4 - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 2/4 - when 2 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 3/4 - when 3 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Key Hash 4/4 - when 4 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 5 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_next_addr_base_next <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Key Hash 1/4 - when 6 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- Found Position (Before Current Instance) - if (inst_latch_data.key_hash(0) < inst_read_data) then - inst_next_addr_base_next <= inst_addr_base; - -- Occupied List Head - if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - assert (inst_addr_base = inst_occupied_head) - inst_occupied_head_next <= inst_empty_head; - - inst_addr_base_next <= inst_empty_head; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 1; -- Skip First Step else - inst_addr_base_next <= inst_prev_addr_base; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 0; + -- DONE + inst_stage_next <= IDLE; end if; - -- BIGGER-THAN - elsif (inst_latch_data.key_hash(0) /= inst_read_data) then - -- Continue - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - cnt_next <= 0; - inst_abort_read <= '1'; end if; - end if; - -- READ Key Hash 2/4 - when 7 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- Found Position (Before Current Instance) - if (inst_latch_data.key_hash(1) < inst_read_data) then - inst_next_addr_base_next <= inst_addr_base; - -- Occupied List Head - if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - assert (inst_addr_base = inst_occupied_head) - inst_occupied_head_next <= inst_empty_head; - - inst_addr_base_next <= inst_empty_head; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 1; -- Skip First Step - else - inst_addr_base_next <= inst_prev_addr_base; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 0; - end if; - -- BIGGER-THAN - elsif (inst_latch_data.key_hash(1) /= inst_read_data) then - -- Continue - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - cnt_next <= 0; - inst_abort_read <= '1'; - end if; - end if; - -- READ Key Hash 3/4 - when 8 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- Found Position (Before Current Instance) - if (inst_latch_data.key_hash(2) < inst_read_data) then - inst_next_addr_base_next <= inst_addr_base; - -- Occupied List Head - if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - assert (inst_addr_base = inst_occupied_head) - inst_occupied_head_next <= inst_empty_head; - - inst_addr_base_next <= inst_empty_head; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 1; -- Skip First Step - else - inst_addr_base_next <= inst_prev_addr_base; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 0; - end if; - -- BIGGER-THAN - elsif (inst_latch_data.key_hash(2) /= inst_read_data) then - -- Continue - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - cnt_next <= 0; - inst_abort_read <= '1'; - end if; - end if; - -- Key Hash 4/4 - when 5 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- Found Position - if (inst_latch_data.key_hash(3) < inst_read_data) then - inst_next_addr_base_next <= inst_addr_base; - -- Occupied List Head - if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - assert (inst_addr_base = inst_occupied_head) - inst_occupied_head_next <= inst_empty_head; - - inst_addr_base_next <= inst_empty_head; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 1; -- Skip First Step - else - inst_addr_base_next <= inst_prev_addr_base; - inst_stage_next <= INSERT_INSTANCE; - cnt_next <= 0; - end if; - else - assert (inst_latch_data.key_hash(3) /= inst_read_data) report "Doublicate Instance Detected" severity FAILURE; + -- READ Status Info + when 15 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.status_info <= inst_read_data; - -- Continue - inst_prev_addr_base_next <= inst_addr_base; - inst_addr_base_next <= inst_next_addr_base; - cnt_next <= 0; + if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 16; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 17; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 18; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 19; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; end if; - end if; - when others => - null; - end case; - when INSERT_INSTANCE => - -- Precondition: inst_addr_base set, inst_prev_addr_base set - - case (inst_cnt) is - -- GET Next Pointer - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- Insert to Occupied List Head - if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - inst_cnt_next <= inst_cnt + 2; - else - inst_cnt_next <= inst_cnt + 1; - end if; - end if; - -- Next Pointer (Previous Instance) - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_prev_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_write_data <= inst_addr_base; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Pointer - when 2 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- Fix Empty List Head - inst_empty_head_next <= inst_read_data; - - -- TODO - end if; - -- Key Hash 1/4 - when 3 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; - inst_write_data <= inst_latch_data.key_hash(0); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Key Hash 2/4 - when 4 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; - inst_write_data <= inst_latch_data.key_hash(1); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Key Hash 3/4 - when 5 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; - inst_write_data <= inst_latch_data.key_hash(2); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Key Hash 4/4 - when 6 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; - inst_write_data <= inst_latch_data.key_hash(3); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Status Info - when 7 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_write_data <= inst_latch_data.status_info; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Sample Count - when 8 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_write_data <= std_logic_vector(to_unsigned(1, WORD_WIDTH)); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Disposed Generation Count - when 9 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_write_data <= (others => '0'); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- No Writers Generation Count - when 10 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_write_data <= (others => '0'); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - inst_cnt_next <= inst_cnt + 1; - else - inst_cnt_next <= inst_cnt + 3; - inst_cnt2_next <= 0; - end if; - end if; - - -- Ignore Deadline 1/2 - when 11 => - -- Synthesis Guard - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_write_data <= inst_latch_data.deadline(0); + -- READ Sample Count + when 16 => + inst_ready_out <= '1'; -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; + if (inst_valid_out = '1') then + inst_latch_data_next.sample_cnt <= inst_read_data; + + if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 17; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 18; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 19; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; end if; - end if; - -- Ignore Deadline 2/2 - when 12 => - -- Synthesis Guard - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; - inst_write_data <= inst_latch_data.deadline(1); + -- READ Disposed Generation Count + when 17 => + inst_ready_out <= '1'; -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - inst_cnt2_next <= 0; + if (inst_valid_out = '1') then + inst_latch_data_next.disposed_gen_cnt <= inst_read_data; + + if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 18; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 19; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; end if; - end if; - -- Writer Bitmap - when 13 => - -- XXX: Possible Worst case Path (2 Additions in same clock) - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_WRITER_BITMAP_OFFSET + inst_cnt2; - inst_write_data <= inst_latch_data.writer_bitmap(inst_cnt2); - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- Exit Condition - if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then - -- DONE - inst_stage_next <= IDLE; - else - inst_cnt2_next <= inst_cnt2 + 1; - end if; - end if; - when others => - null; - end case; - when UPDATE_INSTANCE => - case (inst_cnt) is - -- Status Info - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_write_data <= inst_latch_data.status_info; - inst_data_next.status_info <= inst_latch_data.status_info; - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then - inst_cnt_next <= 1; - elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 2; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 3; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 6; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- Sample Count - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_write_data <= inst_latch_data.sample_cnt; - inst_data_next.sample_cnt <= inst_latch_data.sample_cnt; - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then - inst_cnt_next <= 2; - elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 3; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 6; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- Disposed Generation Count - when 2 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_DISPOSED_GEN_CNT_OFFSET; - inst_write_data <= inst_latch_data.gen_cnt; - inst_data_next.disposed_gen_cnt <= inst_latch_data.gen_cnt; - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then - inst_cnt_next <= 3; - elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 6; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- No Writers Generation Count - when 3 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NO_WRITERS_GEN_CNT_OFFSET; - inst_write_data <= inst_latch_data.gen_cnt; - inst_data_next.no_writers_gen_cnt <= inst_latch_data.gen_cnt; - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then - inst_cnt_next <= 4; - elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then - inst_cnt_next <= 6; - inst_cnt2_next <= 0; - else - -- DONE - inst_stage_next <= IDLE; - end if; - end if; - -- Ignore Deadline 1/2 - when 4 => - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET; - inst_write_data <= std_logic_vector(inst_latch_data.ignore_deadline(0)); - inst_data_next.deadline <= inst_latch_data.ignore_deadline(0); + -- READ No Writers Generation Count + when 18 => + inst_ready_out <= '1'; + -- Memory Flow Control Guard - if (inst_ready_in = '1') then + if (inst_valid_out = '1') then + inst_latch_data_next.no_writers_gen_cnt <= inst_read_data; + + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 19; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + -- READ Ignore Deadline 1/2 + when 19 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.ignore_deadline(0) <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; end if; - end if; - -- Ignore Deadline 2/2 - when 5 => - if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + 1; - inst_write_data <= std_logic_vector(inst_latch_data.ignore_deadline(0)); - inst_data_next.deadline <= inst_latch_data.ignore_deadline(0); + -- READ Ignore Deadline 2/2 + when 20 => + inst_ready_out <= '1'; + -- Memory Flow Control Guard - if (inst_ready_in = '1') then + if (inst_valid_out = '1') then + inst_latch_data_next.ignore_deadline(1) <= inst_read_data; + if check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 21; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + -- READ Writer Bitamp + when 21 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_latch_data_next.writer_bitmap(inst_cnt2) <= inst_read_data; + -- Exit Condition + if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then + -- DONE + inst_stage_next <= IDLE; + else + inst_cnt2_next <= inst_cnt2 + 1; + end if; + end if; + end case; + when FIND_POS => + -- NOTE: Instances are inserted in KEY_HASH numerical order. + + -- TODO: Handle inst_next_addr_base = MAX_ADDR + + case (inst_cnt) is + -- GET Next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 1/4 + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 2/4 + when 2 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 3/4 + when 3 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Key Hash 4/4 + when 4 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Next Instance + when 5 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_next_addr_base_next <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Key Hash 1/4 + when 6 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- Found Position (Before Current Instance) + if (inst_latch_data.key_hash(0) < inst_read_data) then + inst_next_addr_base_next <= inst_addr_base; + -- Occupied List Head + if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + assert (inst_addr_base = inst_occupied_head) + inst_occupied_head_next <= inst_empty_head; + + inst_addr_base_next <= inst_empty_head; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 1; -- Skip First Step + else + inst_addr_base_next <= inst_prev_addr_base; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 0; + end if; + -- BIGGER-THAN + elsif (inst_latch_data.key_hash(0) /= inst_read_data) then + -- Continue + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + cnt_next <= 0; + inst_abort_read <= '1'; + end if; + end if; + -- READ Key Hash 2/4 + when 7 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- Found Position (Before Current Instance) + if (inst_latch_data.key_hash(1) < inst_read_data) then + inst_next_addr_base_next <= inst_addr_base; + -- Occupied List Head + if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + assert (inst_addr_base = inst_occupied_head) + inst_occupied_head_next <= inst_empty_head; + + inst_addr_base_next <= inst_empty_head; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 1; -- Skip First Step + else + inst_addr_base_next <= inst_prev_addr_base; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 0; + end if; + -- BIGGER-THAN + elsif (inst_latch_data.key_hash(1) /= inst_read_data) then + -- Continue + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + cnt_next <= 0; + inst_abort_read <= '1'; + end if; + end if; + -- READ Key Hash 3/4 + when 8 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- Found Position (Before Current Instance) + if (inst_latch_data.key_hash(2) < inst_read_data) then + inst_next_addr_base_next <= inst_addr_base; + -- Occupied List Head + if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + assert (inst_addr_base = inst_occupied_head) + inst_occupied_head_next <= inst_empty_head; + + inst_addr_base_next <= inst_empty_head; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 1; -- Skip First Step + else + inst_addr_base_next <= inst_prev_addr_base; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 0; + end if; + -- BIGGER-THAN + elsif (inst_latch_data.key_hash(2) /= inst_read_data) then + -- Continue + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + cnt_next <= 0; + inst_abort_read <= '1'; + end if; + end if; + -- Key Hash 4/4 + when 5 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- Found Position + if (inst_latch_data.key_hash(3) < inst_read_data) then + inst_next_addr_base_next <= inst_addr_base; + -- Occupied List Head + if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + assert (inst_addr_base = inst_occupied_head) + inst_occupied_head_next <= inst_empty_head; + + inst_addr_base_next <= inst_empty_head; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 1; -- Skip First Step + else + inst_addr_base_next <= inst_prev_addr_base; + inst_stage_next <= INSERT_INSTANCE; + cnt_next <= 0; + end if; + else + assert (inst_latch_data.key_hash(3) /= inst_read_data) report "Doublicate Instance Detected" severity FAILURE; + + -- Continue + inst_prev_addr_base_next <= inst_addr_base; + inst_addr_base_next <= inst_next_addr_base; + cnt_next <= 0; + end if; + end if; + when others => + null; + end case; + when INSERT_INSTANCE => + -- Precondition: inst_addr_base set, inst_prev_addr_base set + + case (inst_cnt) is + -- GET Next Pointer + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + -- Insert to Occupied List Head + if (inst_prev_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + inst_cnt_next <= inst_cnt + 2; + else + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- Next Pointer (Previous Instance) + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_prev_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_write_data <= inst_addr_base; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Next Pointer + when 2 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- Fix Empty List Head + inst_empty_head_next <= inst_read_data; + + -- TODO + end if; + -- Key Hash 1/4 + when 3 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET; + inst_write_data <= inst_latch_data.key_hash(0); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Key Hash 2/4 + when 4 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 1; + inst_write_data <= inst_latch_data.key_hash(1); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Key Hash 3/4 + when 5 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 2; + inst_write_data <= inst_latch_data.key_hash(2); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Key Hash 4/4 + when 6 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_KEY_HASH_OFFSET + 3; + inst_write_data <= inst_latch_data.key_hash(3); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Status Info + when 7 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_write_data <= inst_latch_data.status_info; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Sample Count + when 8 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; + inst_write_data <= std_logic_vector(to_unsigned(1, WORD_WIDTH)); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Disposed Generation Count + when 9 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; + inst_write_data <= (others => '0'); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- No Writers Generation Count + when 10 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; + inst_write_data <= (others => '0'); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_cnt_next <= inst_cnt + 1; + else + inst_cnt_next <= inst_cnt + 3; + inst_cnt2_next <= 0; + end if; + end if; + + -- Ignore Deadline 1/2 + when 11 => + -- Synthesis Guard + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; + inst_write_data <= inst_latch_data.deadline(0); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- Ignore Deadline 2/2 + when 12 => + -- Synthesis Guard + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_SAMPLE_CNT_OFFSET; + inst_write_data <= inst_latch_data.deadline(1); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + inst_cnt2_next <= 0; + end if; + end if; + -- Writer Bitmap + when 13 => + -- XXX: Possible Worst case Path (2 Additions in same clock) + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_WRITER_BITMAP_OFFSET + inst_cnt2; + inst_write_data <= inst_latch_data.writer_bitmap(inst_cnt2); + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + -- Exit Condition + if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then + -- DONE + inst_stage_next <= IDLE; + else + inst_cnt2_next <= inst_cnt2 + 1; + end if; + end if; + when others => + null; + end case; + when UPDATE_INSTANCE => + case (inst_cnt) is + -- Status Info + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_write_data <= inst_latch_data.status_info; + inst_data_next.status_info <= inst_latch_data.status_info; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_SAMPLE_CNT_FLAG) then + inst_cnt_next <= 1; + elsif check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 2; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 3; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then inst_cnt_next <= 6; inst_cnt2_next <= 0; else @@ -4772,129 +4847,237 @@ begin inst_stage_next <= IDLE; end if; end if; - end if; - -- Writer Bitmap - when 6 => - -- XXX: Possible Worst case Path (2 Additions in same clock) - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_WRITER_BITMAP_OFFSET + inst_cnt2; - inst_write_data <= inst_latch_data.writer_bitmap(inst_cnt2); - inst_data_next.writer_bitmap <= inst_latch_data.writer_bitmap; - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- Exit Condition - if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then - -- DONE - inst_stage_next <= IDLE; - else - inst_cnt2_next <= inst_cnt2 + 1; + -- Sample Count + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_write_data <= inst_latch_data.sample_cnt; + inst_data_next.sample_cnt <= inst_latch_data.sample_cnt; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_DISPOSED_CNT_FLAG) then + inst_cnt_next <= 2; + elsif check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 3; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 6; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; end if; - end if; - when others => - null; - end case; - when REMOVE_INSTANCE => - -- Precondition: inst_addr_base set, inst_prev_addr_base set - - case (inst_cnt) is - -- GET Next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 1 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_next_addr_base_next <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- Next Pointer (Previous Instance) - when 2 => - -- Point Previous instance to Next Instance (Remove current Instance from inbetween) - inst_valid_in <= '1'; - inst_addr <= inst_prev_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_write_data <= inst_next_addr_base; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- Next Pointer (Current/Removed Instance) - when 3 => - -- Point Current Instance to Empty List Head (Make Removed Instance Head of the Empty List) - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_write_data <= inst_empty_head; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- Fix Empty List Head - inst_empty_head_next <= inst_addr_base; + -- Disposed Generation Count + when 2 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_DISPOSED_GEN_CNT_OFFSET; + inst_write_data <= inst_latch_data.gen_cnt; + inst_data_next.disposed_gen_cnt <= inst_latch_data.gen_cnt; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_NO_WRITERS_CNT_FLAG) then + inst_cnt_next <= 3; + elsif (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 6; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + -- No Writers Generation Count + when 3 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NO_WRITERS_GEN_CNT_OFFSET; + inst_write_data <= inst_latch_data.gen_cnt; + inst_data_next.no_writers_gen_cnt <= inst_latch_data.gen_cnt; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO and check_mask(inst_latch_data.field_flag,IMF_IGNORE_DEADLINE_FLAG)) then + inst_cnt_next <= 4; + elsif check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 6; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + -- Ignore Deadline 1/2 + when 4 => + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET; + inst_write_data <= std_logic_vector(inst_latch_data.ignore_deadline(0)); + inst_data_next.deadline <= inst_latch_data.ignore_deadline(0); + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + end if; + -- Ignore Deadline 2/2 + when 5 => + if (TIME_BASED_FILTER_QOS /= DURATION_ZERO) then + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_IGNORE_DEADLINE_OFFSET + 1; + inst_write_data <= std_logic_vector(inst_latch_data.ignore_deadline(0)); + inst_data_next.deadline <= inst_latch_data.ignore_deadline(0); + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + if check_mask(inst_latch_data.field_flag,IMF_WRITER_BITMAP_FLAG) then + inst_cnt_next <= 6; + inst_cnt2_next <= 0; + else + -- DONE + inst_stage_next <= IDLE; + end if; + end if; + end if; + -- Writer Bitmap + when 6 => + -- XXX: Possible Worst case Path (2 Additions in same clock) + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_WRITER_BITMAP_OFFSET + inst_cnt2; + inst_write_data <= inst_latch_data.writer_bitmap(inst_cnt2); + inst_data_next.writer_bitmap <= inst_latch_data.writer_bitmap; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + -- Exit Condition + if (inst_cnt2 = ENDPOINT_BITMAP_ARRAY_TYPE'length-1) then + -- DONE + inst_stage_next <= IDLE; + else + inst_cnt2_next <= inst_cnt2 + 1; + end if; + end if; + when others => + null; + end case; + when REMOVE_INSTANCE => + -- Precondition: inst_addr_base set, inst_prev_addr_base set + + case (inst_cnt) is + -- GET Next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; - -- Reset - inst_data_next <= ZERO_INSTANCE_DATA; - inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; - - -- DONE - inst_stage_next <= IDLE; - end if; - when others => - null; - end case; - when UNMARK_INSTANCES => - -- Precondition: inst_addr_base set - - case (inst_cnt) is - -- GET Next Instance - when 0 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- GET Status Info - when 1 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_read <= '1'; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Next Instance - when 2 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - inst_next_addr_base_next <= inst_read_data; - inst_cnt_next <= inst_cnt + 1; - end if; - -- READ Status Info - when 3 => - inst_ready_out <= '1'; - - -- Memory Flow Control Guard - if (inst_valid_out = '1') then - -- MARK Flag Set - if (inst_read_data(MARK_FLAG) = '1') then - -- Latch Status Info (With MARK removed) - inst_long_latch_next <= inst_read_data; - inst_long_latch_next(MARK_FLAG) <= '0'; + -- Memory Flow Control Guard + if (inst_ready_in = '1') then inst_cnt_next <= inst_cnt + 1; - else + end if; + -- READ Next Instance + when 1 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_next_addr_base_next <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- Next Pointer (Previous Instance) + when 2 => + -- Point Previous instance to Next Instance (Remove current Instance from inbetween) + inst_valid_in <= '1'; + inst_addr <= inst_prev_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_write_data <= inst_next_addr_base; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- Next Pointer (Current/Removed Instance) + when 3 => + -- Point Current Instance to Empty List Head (Make Removed Instance Head of the Empty List) + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_write_data <= inst_empty_head; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + -- Fix Empty List Head + inst_empty_head_next <= inst_addr_base; + + -- Reset + inst_data_next <= ZERO_INSTANCE_DATA; + inst_addr_base_next <= INSTANCE_MEMORY_MAX_ADDRESS; + + -- DONE + inst_stage_next <= IDLE; + end if; + when others => + null; + end case; + when UNMARK_INSTANCES => + -- Precondition: inst_addr_base set + + case (inst_cnt) is + -- GET Next Instance + when 0 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_NEXT_ADDR_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- GET Status Info + when 1 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_read <= '1'; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Next Instance + when 2 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + inst_next_addr_base_next <= inst_read_data; + inst_cnt_next <= inst_cnt + 1; + end if; + -- READ Status Info + when 3 => + inst_ready_out <= '1'; + + -- Memory Flow Control Guard + if (inst_valid_out = '1') then + -- MARK Flag Set + if (inst_read_data(MARK_FLAG) = '1') then + -- Latch Status Info (With MARK removed) + inst_long_latch_next <= inst_read_data; + inst_long_latch_next(MARK_FLAG) <= '0'; + inst_cnt_next <= inst_cnt + 1; + else + -- End of Instances + if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then + -- DONE + inst_stage_next <= IDLE; + else + -- Continue + inst_addr_base <= inst_next_addr_base; + inst_cnt_next <= 0; + end if; + end if; + end if; + -- Status Info + when 4 => + inst_valid_in <= '1'; + inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; + inst_write_data <= inst_long_latch; + + -- Memory Flow Control Guard + if (inst_ready_in = '1') then -- End of Instances if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then -- DONE @@ -4905,31 +5088,12 @@ begin inst_cnt_next <= 0; end if; end if; - end if; - -- Status Info - when 4 => - inst_valid_in <= '1'; - inst_addr <= inst_addr_base + IMF_STATUS_INFO_OFFSET; - inst_write_data <= inst_long_latch; - - -- Memory Flow Control Guard - if (inst_ready_in = '1') then - -- End of Instances - if (inst_next_addr_base = INSTANCE_MEMORY_MAX_ADDRESS) then - -- DONE - inst_stage_next <= IDLE; - else - -- Continue - inst_addr_base <= inst_next_addr_base; - inst_cnt_next <= 0; - end if; - end if; - when others => - null; - end case; - when others => - null; - end case; - end process; - + when others => + null; + end case; + when others => + null; + end case; + end process; + end generate; end architecture; \ No newline at end of file diff --git a/src/rtps_reader.vhd b/src/rtps_reader.vhd index 05d5de8..77a1490 100644 --- a/src/rtps_reader.vhd +++ b/src/rtps_reader.vhd @@ -21,6 +21,7 @@ entity rtps_reader is HEARTBEAT_SUPPRESSION_DELAY : DURATION_TYPE := TODO; LEASE_DURATION : DURATION_TYPE := DEFAULT_LEASE_DURATION; ENTITYID : std_logic_vector(ENTITYID_WIDTH-1 downto 0) := ENTITYID_UNKNOWN; + WITH_KEY : boolean := FALSE -- TODO: Default ); port ( -- SYSTEM @@ -1158,7 +1159,7 @@ begin when 4 => dds_data_in <= lifespan(1); -- Skip Key Hash, if not received - if (key_hash_rcvd = '0') then + if (not WITH_KEY or key_hash_rcvd = '0') then cnt_next <= 9; end if; -- Key hash 1/4 @@ -1182,7 +1183,7 @@ begin dds_data_in <= std_logic_vector(to_unsigned(mem_pos, CDR_LONG_WIDTH)); -- Payload exists - if (data_flag = '1' or key_flag = '1') then + if (data_flag = '1' or (WITH_KEY and key_flag = '1')) then stage_next <= PUSH_PAYLOAD; else -- DONE