OpenCores
URL https://opencores.org/ocsvn/scct/scct/trunk

Subversion Repositories scct

[/] [scct/] [trunk/] [verilog/] [scct_counter.v] - Rev 2

Compare with Previous | Blame | View Log

// $Id: scct_counter.v 2 2015-06-15 13:52:02Z fkluge $
// simple counter
 
`include "scct_constants.v"
 
module scct_counter (
		     clk,
		     rst,
		     counter,
		     counter_changed,
		     irq_enable_i, irq_enable_i_wen,
		     irq_status_i, irq_status_i_wen,
		     prescaler_i, prescaler_i_wen,
		     irq_enable_o,
		     irq_status_o,
		     prescaler_o
		     );
 
   input 	 clk;
   input 	 rst;
   output [`SCCT_COUNTER_CTR_WIDTH-1:0] counter;
   // TODO: replace single-bit X_i, X_i_wen signals by a single signal
   input 				irq_enable_i;
   input 				irq_enable_i_wen;
   input 				irq_status_i;
   input 				irq_status_i_wen;
   input [`SCCT_COUNTER_PSC_WIDTH-1:0] 	prescaler_i;
   input 				prescaler_i_wen;
   output 				irq_enable_o;
   output 				irq_status_o;
   output [`SCCT_COUNTER_PSC_WIDTH-1:0] prescaler_o;
   output 				counter_changed;
 
 
   // The actual counter register is 1 bit wider to account for overflows
   reg [`SCCT_COUNTER_CTR_WIDTH:0] 	my_counter;
   // this signals is set to 1 when the counter value has changed. After one cycle it is reset to 0
   reg 					counter_changed;
 
   reg [`SCCT_COUNTER_PSC_WIDTH-1:0] 	prescaler;
   reg [`SCCT_COUNTER_PSC_WIDTH-1:0] 	prescaler_shadow; // used for actual prescaling
   reg [`SCCT_COUNTER_PSC_WIDTH-1:0] 	prescaler_count;
   reg 					irq_enable;
   reg 					irq_status;
 
   wire 				prescaler_match;
   wire 				counter_overflow;
 
 
   assign prescaler_match = (prescaler_count == prescaler_shadow);
   assign counter[`SCCT_COUNTER_CTR_WIDTH-1:0] = my_counter[`SCCT_COUNTER_CTR_WIDTH-1:0];
   assign counter_overflow = my_counter[`SCCT_COUNTER_CTR_OV_BIT];
   assign prescaler_o = prescaler;
   //assign irq_status_o = irq_enable ? irq_status : 0;
   assign irq_status_o = irq_status;
 
   // writing to registers
   always @(posedge clk or posedge rst)
     begin
	if (rst)
	  begin
	  end
	else
	  begin
	  end // else: !if(rst)
     end // always @ (posedge clock or psedge reset_n)
 
 
   // counter operation
   always @(posedge clk or posedge rst)
     begin
	if(rst)
	  begin
	     prescaler_shadow <= `SCCT_COUNTER_PSC_WIDTH'b0;
	     prescaler_count <= `SCCT_COUNTER_PSC_WIDTH'b0;
	     my_counter <= 0;
	     irq_status <= 0;
	     prescaler <= `SCCT_COUNTER_PSC_WIDTH'b0;
	     irq_enable <= 0;
	     counter_changed <= 0;
	  end // if (rst)
	else
	  begin
	     prescaler_count <= prescaler_count + 1;
 
	     if (prescaler_match)
	       begin
		  my_counter <= my_counter + 1;
		  prescaler_count <= `SCCT_COUNTER_PSC_WIDTH'b0;
		  prescaler_shadow <= prescaler;
		  counter_changed <= 1;
	       end
	     else
	       begin
		  counter_changed <= 0;
	       end // else: !if(prescaler_match)
 
 
	     if (counter_overflow)
	       begin
		  my_counter[`SCCT_COUNTER_CTR_OV_BIT] <= 0;
		  irq_status <= irq_enable ? 1 : 0;
	       end
	     // write requests
	     if (irq_enable_i_wen)
	       irq_enable <= irq_enable_i;
 
	     // if an overflow occurs in the same cycle as the reset request
	     // for irq_status, ignore the reset.
	     if ( (irq_status_i_wen) && (irq_status_i == 1) && (!counter_overflow))
	       begin
		  irq_status <= 0;
	       end
	     if (prescaler_i_wen)
	       prescaler <= prescaler_i;
	  end // else: !if(rst)
     end // always @ (posedge clk or posedge rst)
 
endmodule // counter
 

Compare with Previous | Blame | View Log

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.