NVC code coverage report

File:  /__w/ctu-can-regression/ctu-can-regression/src/rx_buffer/rx_buffer_fsm.vhd

     0:   -------------------------------------------------------------------------------- 
     1:   -- 
     2:   -- CTU CAN FD IP Core 
     3:   -- Copyright (C) 2021-2023 Ondrej Ille 
     4:   -- Copyright (C) 2023-     Logic Design Services Ltd.s 
     5:   -- 
     6:   -- Permission is hereby granted, free of charge, to any person obtaining a copy 
     7:   -- of this VHDL component and associated documentation files (the "Component"), 
     8:   -- to use, copy, modify, merge, publish, distribute the Component for 
     9:   -- non-commercial purposes. Using the Component for commercial purposes is 
    10:   -- forbidden unless previously agreed with Copyright holder. 
    11:   -- 
    12:   -- The above copyright notice and this permission notice shall be included in 
    13:   -- all copies or substantial portions of the Component. 
    14:   -- 
    15:   -- THE COMPONENT IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 
    16:   -- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 
    17:   -- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 
    18:   -- AUTHORS OR COPYRIGHTHOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 
    19:   -- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 
    20:   -- FROM, OUT OF OR IN CONNECTION WITH THE COMPONENT OR THE USE OR OTHER DEALINGS 
    21:   -- IN THE COMPONENT. 
    22:   -- 
    23:   -- The CAN protocol is developed by Robert Bosch GmbH and protected by patents. 
    24:   -- Anybody who wants to implement this IP core on silicon has to obtain a CAN 
    25:   -- protocol license from Bosch. 
    26:   -- 
    27:   -- ------------------------------------------------------------------------------- 
    28:   -- 
    29:   -- CTU CAN FD IP Core 
    30:   -- Copyright (C) 2015-2020 MIT License 
    31:   -- 
    32:   -- Authors: 
    33:   --     Ondrej Ille <ondrej.ille@gmail.com> 
    34:   --     Martin Jerabek <martin.jerabek01@gmail.com> 
    35:   -- 
    36:   -- Project advisors: 
    37:   -- 	Jiri Novak <jnovak@fel.cvut.cz> 
    38:   -- 	Pavel Pisa <pisa@cmp.felk.cvut.cz> 
    39:   -- 
    40:   -- Department of Measurement         (http://meas.fel.cvut.cz/) 
    41:   -- Faculty of Electrical Engineering (http://www.fel.cvut.cz) 
    42:   -- Czech Technical University        (http://www.cvut.cz/) 
    43:   -- 
    44:   -- Permission is hereby granted, free of charge, to any person obtaining a copy 
    45:   -- of this VHDL component and associated documentation files (the "Component"), 
    46:   -- to deal in the Component without restriction, including without limitation 
    47:   -- the rights to use, copy, modify, merge, publish, distribute, sublicense, 
    48:   -- and/or sell copies of the Component, and to permit persons to whom the 
    49:   -- Component is furnished to do so, subject to the following conditions: 
    50:   -- 
    51:   -- The above copyright notice and this permission notice shall be included in 
    52:   -- all copies or substantial portions of the Component. 
    53:   -- 
    54:   -- THE COMPONENT IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 
    55:   -- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 
    56:   -- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 
    57:   -- AUTHORS OR COPYRIGHTHOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 
    58:   -- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 
    59:   -- FROM, OUT OF OR IN CONNECTION WITH THE COMPONENT OR THE USE OR OTHER DEALINGS 
    60:   -- IN THE COMPONENT. 
    61:   -- 
    62:   -- The CAN protocol is developed by Robert Bosch GmbH and protected by patents. 
    63:   -- Anybody who wants to implement this IP core on silicon has to obtain a CAN 
    64:   -- protocol license from Bosch. 
    65:   -- 
    66:   -------------------------------------------------------------------------------- 
    67:    
    68:   -------------------------------------------------------------------------------- 
    69:   -- Module: 
    70:   --  RX Buffer FSM. 
    71:   -- 
    72:   -- Purpose: 
    73:   --  Reacts on commands from CAN Core and controls storing of CAN frame 
    74:   --  continusly to RX Buffer RAM. 
    75:   -------------------------------------------------------------------------------- 
    76:    
    77:   Library ieee; 
    78:   use ieee.std_logic_1164.all; 
    79:   use ieee.numeric_std.ALL; 
    80:   use ieee.math_real.ALL; 
    81:    
    82:   Library ctu_can_fd_rtl; 
    83:   use ctu_can_fd_rtl.can_constants_pkg.all; 
    84:   use ctu_can_fd_rtl.can_types_pkg.all; 
    85:    
    86:   use ctu_can_fd_rtl.CAN_FD_register_map.all; 
    87:   use ctu_can_fd_rtl.CAN_FD_frame_format.all; 
    88:    
    89:   entity rx_buffer_fsm is 
    90:       port ( 
    91:           ------------------------------------------------------------------------------------------- 
    92:           -- Clocks and reset 
    93:           ------------------------------------------------------------------------------------------- 
    94:           clk_sys                 : in  std_logic; 
    95:           res_n                   : in  std_logic; 
    96:    
    97:           ------------------------------------------------------------------------------------------- 
    98:           -- Memory registers interface 
    99:           ------------------------------------------------------------------------------------------- 
   100:           mr_mode_erfm            : in  std_logic; 
   101:    
   102:           ------------------------------------------------------------------------------------------- 
   103:           -- Control signals from CAN Core (Filtered by Frame filters) 
   104:           ------------------------------------------------------------------------------------------- 
   105:           -- Start Storing of Metadata to RX Buffer (first 4 words of frame) 
   106:           store_metadata_f        : in  std_logic; 
   107:    
   108:           -- Store Data word to RX Buffer 
   109:           store_data_f            : in  std_logic; 
   110:    
   111:           -- Received frame valid 
   112:           rec_valid_f             : in  std_logic; 
   113:    
   114:           -- Abort storing of RX Frame to RX Buffer. 
   115:           rec_abort_f             : in  std_logic; 
   116:    
   117:           ------------------------------------------------------------------------------------------- 
   118:           -- FSM outputs 
   119:           ------------------------------------------------------------------------------------------- 
   120:           -- Intent to write to RX Buffer RAM 
   121:           write_raw_intent        : out std_logic; 
   122:    
   123:           -- Select Timestamp write pointer 
   124:           select_ts_wptr          : out std_logic; 
   125:    
   126:           -- Intend to comit frame to RX Buffer 
   127:           commit_intent           : out std_logic; 
   128:    
   129:           -- Data selector for selection of memory word to be stored in RX Buffer 
   130:           -- RAM (one hot coded) 
   131:           data_selector           : out std_logic_vector(4 downto 0); 
   132:    
   133:           -- Load timestamp write pointer from regular write pointer 
   134:           store_ts_wr_ptr         : out std_logic; 
   135:    
   136:           -- Increment timestamp write pointer by 1 
   137:           inc_ts_wr_ptr           : out std_logic; 
   138:    
   139:           -- Error frame type 
   140:           rec_erf                 : out std_logic; 
   141:    
   142:           -- Reset internal overrun flag 
   143:           reset_overrun_flag      : out std_logic 
   144:       ); 
   145:   end entity; 
   146:    
   147:   architecture rtl of rx_buffer_fsm is 
   148:    
   149:       -- RX Buffer FSM 
   150:       signal curr_state   : t_rx_buf_state; 
   151:       signal next_state   : t_rx_buf_state; 
   152:    
   153:       -- Clock enable for state register 
   154:       signal rx_fsm_ce    : std_logic; 
   155:    
   156:   begin 
   157:    
   158:       ----------------------------------------------------------------------------------------------- 
   159:       -- Next State process 
   160:       ----------------------------------------------------------------------------------------------- 
   161:       next_state_proc : process(curr_state, store_metadata_f, rec_abort_f, rec_valid_f, mr_mode_erfm) 
   162:       begin 
   163:           next_state <= curr_state; 
   164:    
   165:           case curr_state is 
   166:    
   167:           ------------------------------------------------------------------------------------------- 
   168:           -- Idle, waiting for "store_metada" to start storing first 4 words. 
   169:           ------------------------------------------------------------------------------------------- 
   170:           when s_rxb_idle => 
   171:               if (store_metadata_f = '1') then 
   172:                   next_state <= s_rxb_store_frame_format; 
   173:               elsif (mr_mode_erfm = ERFM_ENABLED and rec_abort_f = '1') then 
   174:                   next_state <= s_rxb_store_err_frame_format; 
   175:               end if; 
   176:    
   177:           ------------------------------------------------------------------------------------------- 
   178:           -- Storing FRAME_FORM_W. Proceed execpt if error ocurrs. 
   179:           ------------------------------------------------------------------------------------------- 
   180:           when s_rxb_store_frame_format => 
   181:               if (rec_abort_f = '1') then 
   182:                   if (mr_mode_erfm = ERFM_ENABLED) then 
   183:                       next_state <= s_rxb_store_err_frame_format; 
   184:                   else 
   185:                       next_state <= s_rxb_idle; 
   186:                   end if; 
   187:               else 
   188:                   next_state <= s_rxb_store_identifier; 
   189:               end if; 
   190:    
   191:           ------------------------------------------------------------------------------------------- 
   192:           -- Storing IDENTIFIER_W. 
   193:           -- Move to storing timestamp words. Note that if SW configured timestamp from end of the 
   194:           -- frame, we dont have it yet! We store invalid timestamp and later (if the frame is 
   195:           -- received OK), we repeat the writes with timestamp captured at the end of frame! 
   196:           ------------------------------------------------------------------------------------------- 
   197:           when s_rxb_store_identifier => 
   198:               next_state <= s_rxb_skip_ts_low; 
   199:    
   200:           ------------------------------------------------------------------------------------------- 
   201:           -- Skip through TIMESTAMP_L_W, store only zeroes. 
   202:           ------------------------------------------------------------------------------------------- 
   203:           when s_rxb_skip_ts_low => 
   204:               next_state <= s_rxb_skip_ts_high; 
   205:    
   206:           ------------------------------------------------------------------------------------------- 
   207:           -- Skip through TIMESTAMP_U_W, store only zeroes. 
   208:           ------------------------------------------------------------------------------------------- 
   209:           when s_rxb_skip_ts_high => 
   210:               next_state <= s_rxb_store_data; 
   211:    
   212:           ------------------------------------------------------------------------------------------- 
   213:           -- Store DATA_W. If error ocurrs, abort the storing. If storing is finished, go to idle or 
   214:           -- again timestamp storing depending on the timestamp option configuration. Note that now 
   215:           -- timestamp storing is realized via different states! 
   216:            ------------------------------------------------------------------------------------------- 
   217:           when s_rxb_store_data => 
   218:               if (rec_abort_f = '1') then 
   219:                   if (mr_mode_erfm = ERFM_ENABLED) then 
   220:                       next_state <= s_rxb_store_err_frame_format; 
   221:                   else 
   222:                       next_state <= s_rxb_idle; 
   223:                   end if; 
   224:    
   225:               elsif (rec_valid_f = '1') then 
   226:                   next_state <= s_rxb_store_end_ts_low; 
   227:               end if; 
   228:    
   229:           ------------------------------------------------------------------------------------------- 
   230:           -- Store TIMESTAMP_L_W. 
   231:           ------------------------------------------------------------------------------------------- 
   232:           when s_rxb_store_end_ts_low => 
   233:               next_state <= s_rxb_store_end_ts_high; 
   234:    
   235:           ------------------------------------------------------------------------------------------- 
   236:           -- Store first TIMESTAMP_U_W. 
   237:           ------------------------------------------------------------------------------------------- 
   238:           when s_rxb_store_end_ts_high => 
   239:               next_state <= s_rxb_idle; 
   240:    
   241:           ------------------------------------------------------------------------------------------- 
   242:           -- Store FRAME_FORMAT_W of an Error frame 
   243:           ------------------------------------------------------------------------------------------- 
   244:           when s_rxb_store_err_frame_format => 
   245:               next_state <= s_rxb_store_err_identifier; 
   246:    
   247:           ------------------------------------------------------------------------------------------- 
   248:           -- Store IDENTIFIER_W of an Error frame 
   249:           ------------------------------------------------------------------------------------------- 
   250:           when s_rxb_store_err_identifier => 
   251:               next_state <= s_rxb_store_err_ts_low; 
   252:    
   253:           ------------------------------------------------------------------------------------------- 
   254:           -- Store TIMESTAMP_L_W of an Error frame 
   255:           ------------------------------------------------------------------------------------------- 
   256:           when s_rxb_store_err_ts_low => 
   257:               next_state <= s_rxb_store_err_ts_high; 
   258:    
   259:           ------------------------------------------------------------------------------------------- 
   260:           -- Store TIMESTAMP_U_W of an Error frame 
   261:           ------------------------------------------------------------------------------------------- 
   262:           when s_rxb_store_err_ts_high => 
   263:               next_state <= s_rxb_idle; 
   264:    
   265:           end case; 
   266:       end process; 
   267:    
   268:    
   269:       ----------------------------------------------------------------------------------------------- 
   270:       -- Current State process (outputs) 
   271:       ----------------------------------------------------------------------------------------------- 
   272:       curr_state_proc : process(curr_state, store_data_f, rec_abort_f) 
   273:       begin 
   274:           write_raw_intent <= '0'; 
   275:           select_ts_wptr <= '0'; 
   276:           data_selector <= (others => '0'); 
   277:           commit_intent <= '0'; 
   278:           store_ts_wr_ptr <= '0'; 
   279:           inc_ts_wr_ptr <= '0'; 
   280:           reset_overrun_flag <= '0'; 
   281:           rec_erf <= '0'; 
   282:    
   283:           case curr_state is 
   284:           when s_rxb_idle => 
   285:               reset_overrun_flag <= '1'; 
   286:    
   287:           when s_rxb_store_frame_format => 
   288:               if (rec_abort_f = '0') then 
   289:                   write_raw_intent <= '1'; 
   290:               end if; 
   291:               data_selector <= "00001"; 
   292:    
   293:           when s_rxb_store_identifier => 
   294:               write_raw_intent <= '1'; 
   295:               data_selector <= "00010"; 
   296:    
   297:           when s_rxb_skip_ts_low => 
   298:               write_raw_intent <= '1'; 
   299:    
   300:               -- Here we capture value of Raw write pointer to Timestamp write pointer 
   301:               -- so that it can be later used for Timestamp storing. 
   302:               store_ts_wr_ptr <= '1'; 
   303:    
   304:           when s_rxb_skip_ts_high => 
   305:               write_raw_intent <= '1'; 
   306:    
   307:           when s_rxb_store_data => 
   308:               data_selector <= "00100"; 
   309:    
   310:               if (store_data_f = '1') then 
   311:                   write_raw_intent <= '1'; 
   312:               end if; 
   313:    
   314:           when s_rxb_store_end_ts_low => 
   315:               data_selector <= "01000"; 
   316:    
   317:               -- Raw write pointer points to the last data frame word 
   318:               -- when timestamp is stored at the end of frame. Need to 
   319:               -- use backed-up timestamp write pointer. 
   320:               select_ts_wptr <= '1'; 
   321:    
   322:               -- Timestamp write pointer is incremented once more when lower 
   323:               -- timestamp word was stored, to point to higher timestamp word. 
   324:               inc_ts_wr_ptr <= '1'; 
   325:    
   326:           when s_rxb_store_end_ts_high => 
   327:               data_selector <= "10000"; 
   328:    
   329:               -- Raw write pointer points to the last data frame word 
   330:               -- when timestamp is stored at the end of frame. Need to 
   331:               -- use backed-up timestamp write pointer. 
   332:               select_ts_wptr <= '1'; 
   333:    
   334:               commit_intent <= '1'; 
   335:    
   336:           when s_rxb_store_err_frame_format => 
   337:               write_raw_intent <= '1'; 
   338:               data_selector <= "00001"; 
   339:               rec_erf <= '1'; 
   340:    
   341:           when s_rxb_store_err_identifier => 
   342:               write_raw_intent <= '1'; 
   343:               data_selector <= "00010"; 
   344:    
   345:           when s_rxb_store_err_ts_low => 
   346:               write_raw_intent <= '1'; 
   347:               data_selector <= "01000"; 
   348:    
   349:           when s_rxb_store_err_ts_high => 
   350:               write_raw_intent <= '1'; 
   351:               data_selector <= "10000"; 
   352:    
   353:               commit_intent <= '1'; 
   354:           end case; 
   355:    
   356:       end process; 
   357:    
   358:    
   359:       ----------------------------------------------------------------------------------------------- 
   360:       -- State register process 
   361:       ----------------------------------------------------------------------------------------------- 
   362:       state_reg_proc : process(clk_sys, res_n) 
   363:       begin 
   364:           if (res_n = '0') then 
   365:               curr_state <= s_rxb_idle; 
   366:           elsif (rising_edge(clk_sys)) then 
   367:               if (rx_fsm_ce = '1') then 
   368:                   curr_state <= next_state; 
   369:               end if; 
   370:           end if; 
   371:       end process; 
   372:    
   373:       -- Clock enable for State reg 
   374:       rx_fsm_ce <= '1' when (next_state /= curr_state) else 
   375:                    '0'; 
   376:    
   377:       ----------------------------------------------------------------------------------------------- 
   378:       -- Assertions 
   379:       ----------------------------------------------------------------------------------------------- 
   380:    
   381:       -- pragma translate_off 
   382:    
   383:       assertions_block : block 
   384:           -- Joined commands 
   385:           signal cmd_join     : std_logic_vector(3 downto 0); 
   386:       begin 
   387:           -- psl default clock is rising_edge(clk_sys); 
   388:    
   389:           -- Joined commands, for assertions only 
   390:           cmd_join <= store_metadata_f & store_data_f & rec_valid_f & rec_abort_f; 
   391:    
   392:           -- psl store_metadata_in_idle_asrt : assert never 
   393:           --  (store_metadata_f = '1' and (curr_state /= s_rxb_idle)) 
   394:           -- report "RX Buffer: Store metadata command did NOT come when RX buffer is idle!"; 
   395:    
   396:           -- psl commit_or_store_data_asrt : assert never 
   397:           --  ((rec_valid_f = '1' or store_data_f = '1') and curr_state /= s_rxb_store_data) 
   398:           -- report "RX Buffer: Store data or frame commit commands did not come when RX Buffer is receiving data!"; 
   399:    
   400:           -- psl rxb_not_storing_err_frm_when_next_occurs_asrt : assert never 
   401:           --  (curr_state = s_rxb_store_err_frame_format or 
   402:           --   curr_state = s_rxb_store_err_identifier or 
   403:           --   curr_state = s_rxb_store_err_ts_low or 
   404:           --   curr_state = s_rxb_store_err_ts_high) and (rec_abort_f = '1') 
   405:           -- report "Error frame was not yet fully stored when another one occured."; 
   406:    
   407:           -- coverage off 
   408:           process (cmd_join) 
   409:           begin 
   410:               if (now > 0 ps) then 
   411:                   if (cmd_join /= "0000" and cmd_join /= "0001" and 
   412:                       cmd_join /= "0010" and cmd_join /= "0100" and 
   413:                       cmd_join /= "1000") 
   414:                   then 
   415:                       report "RX Buffer: RX Buffer commands should be one-hot encoded!" 
   416:                       severity error; 
   417:                   end if; 
   418:               end if; 
   419:           end process; 
   420:           -- coverage on 
   421:    
   422:           -- psl rx_no_abort_after_metadata_cov : assert never 
   423:           --  (rec_abort_f = '1') and 
   424:           --  (curr_state = s_rxb_store_identifier or curr_state = s_rxb_skip_ts_low or 
   425:           --   curr_state = s_rxb_skip_ts_high or curr_state = s_rxb_store_end_ts_low or 
   426:           --   curr_state = s_rxb_store_end_ts_high) 
   427:           --  report "RX Buffer abort not supported storing of Identifier and Timestamp"; 
   428:    
   429:           -- psl rx_never_abort_and_store_in_idle : assert never 
   430:           --  (curr_state = s_rxb_idle and store_metadata_f = '1' and rec_abort_f = '1') 
   431:           --  report "When RX Buffer FSM is s_rxb_idle, store_metadata_f and rec_abort_f can't be simultaneous!"; 
   432:    
   433:           -- psl store_metadata_and_rec_abort_back_to_back_cov : cover 
   434:           --  {mr_mode_erfm = ERFM_ENABLED and rec_abort_f = '1' and curr_state = s_rxb_store_frame_format} 
   435:           --  report "rec_abort_f = 1 and curr_state = s_rxb_store_frame_format"; 
   436:    
   437:           -- psl rec_abort_in_idle_cov : cover 
   438:           --  {mr_mode_erfm = ERFM_ENABLED and rec_abort_f = '1' and curr_state = s_rxb_idle} 
   439:           --  report "rec_abort_f = 1 and curr_state = s_rxb_idle"; 
   440:    
   441:           -- psl rec_abort_in_store_data_cov : cover 
   442:           --  {mr_mode_erfm = ERFM_ENABLED and rec_abort_f = '1' and curr_state = s_rxb_store_data} 
   443:           --  report "rec_abort_f = 1 and curr_state = s_rxb_store_data"; 
   444:    
   445:       end block assertions_block; 
   446:    
   447:       -- pragma translate_on 
   448:    
   449:   end architecture;