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

Subversion Repositories altor32

[/] [altor32/] [trunk/] [rtl/] [peripheral/] [intr_periph.v] - Diff between revs 27 and 32

Only display areas with differences | Details | Blame | View Log

Rev 27 Rev 32
//-----------------------------------------------------------------
//-----------------------------------------------------------------
//                           AltOR32 
//                           AltOR32 
//                Alternative Lightweight OpenRisc 
//                Alternative Lightweight OpenRisc 
//                            V2.0
//                            V2.0
//                     Ultra-Embedded.com
//                     Ultra-Embedded.com
//                   Copyright 2011 - 2013
//                   Copyright 2011 - 2013
//
//
//               Email: admin@ultra-embedded.com
//               Email: admin@ultra-embedded.com
//
//
//                       License: LGPL
//                       License: LGPL
//-----------------------------------------------------------------
//-----------------------------------------------------------------
//
//
// Copyright (C) 2011 - 2013 Ultra-Embedded.com
// Copyright (C) 2011 - 2013 Ultra-Embedded.com
//
//
// This source file may be used and distributed without         
// This source file may be used and distributed without         
// restriction provided that this copyright statement is not    
// restriction provided that this copyright statement is not    
// removed from the file and that any derivative work contains  
// removed from the file and that any derivative work contains  
// the original copyright notice and the associated disclaimer. 
// the original copyright notice and the associated disclaimer. 
//
//
// This source file is free software; you can redistribute it   
// This source file is free software; you can redistribute it   
// and/or modify it under the terms of the GNU Lesser General   
// and/or modify it under the terms of the GNU Lesser General   
// Public License as published by the Free Software Foundation; 
// Public License as published by the Free Software Foundation; 
// either version 2.1 of the License, or (at your option) any   
// either version 2.1 of the License, or (at your option) any   
// later version.
// later version.
//
//
// This source is distributed in the hope that it will be       
// This source is distributed in the hope that it will be       
// useful, but WITHOUT ANY WARRANTY; without even the implied   
// useful, but WITHOUT ANY WARRANTY; without even the implied   
// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      
// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      
// PURPOSE.  See the GNU Lesser General Public License for more 
// PURPOSE.  See the GNU Lesser General Public License for more 
// details.
// details.
//
//
// You should have received a copy of the GNU Lesser General    
// You should have received a copy of the GNU Lesser General    
// Public License along with this source; if not, write to the 
// Public License along with this source; if not, write to the 
// Free Software Foundation, Inc., 59 Temple Place, Suite 330, 
// Free Software Foundation, Inc., 59 Temple Place, Suite 330, 
// Boston, MA  02111-1307  USA
// Boston, MA  02111-1307  USA
//-----------------------------------------------------------------
//-----------------------------------------------------------------
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Includes
// Includes
//-----------------------------------------------------------------
//-----------------------------------------------------------------
`include "intr_defs.v"
`include "intr_defs.v"
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Module:
// Module:
//-----------------------------------------------------------------
//-----------------------------------------------------------------
module intr_periph
module intr_periph
(
(
    // General - Clocking & Reset
    // General - Clocking & Reset
    clk_i,
    clk_i,
    rst_i,
    rst_i,
    intr_o,
    intr_o,
 
 
    // Interrupts
    // Interrupts
    intr0_i,
    intr0_i,
    intr1_i,
    intr1_i,
    intr2_i,
    intr2_i,
    intr3_i,
    intr3_i,
    intr4_i,
    intr4_i,
    intr5_i,
    intr5_i,
    intr6_i,
    intr6_i,
    intr7_i,
    intr7_i,
    intr_ext_i,
    intr_ext_i,
 
 
    // Peripheral bus
    // Peripheral bus
    addr_i,
    addr_i,
    data_o,
    data_o,
    data_i,
    data_i,
    wr_i,
    we_i,
    rd_i
    stb_i
);
);
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Params
// Params
//-----------------------------------------------------------------
//-----------------------------------------------------------------
parameter           EXTERNAL_INTERRUPTS = 1;
parameter           EXTERNAL_INTERRUPTS = 1;
parameter           INTERRUPT_COUNT     = EXTERNAL_INTERRUPTS + 8;
parameter           INTERRUPT_COUNT     = EXTERNAL_INTERRUPTS + 8;
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// I/O
// I/O
//-----------------------------------------------------------------
//-----------------------------------------------------------------
input               clk_i /*verilator public*/;
input               clk_i /*verilator public*/;
input               rst_i /*verilator public*/;
input               rst_i /*verilator public*/;
output              intr_o /*verilator public*/;
output              intr_o /*verilator public*/;
 
 
input               intr0_i /*verilator public*/;
input               intr0_i /*verilator public*/;
input               intr1_i /*verilator public*/;
input               intr1_i /*verilator public*/;
input               intr2_i /*verilator public*/;
input               intr2_i /*verilator public*/;
input               intr3_i /*verilator public*/;
input               intr3_i /*verilator public*/;
input               intr4_i /*verilator public*/;
input               intr4_i /*verilator public*/;
input               intr5_i /*verilator public*/;
input               intr5_i /*verilator public*/;
input               intr6_i /*verilator public*/;
input               intr6_i /*verilator public*/;
input               intr7_i /*verilator public*/;
input               intr7_i /*verilator public*/;
input [(EXTERNAL_INTERRUPTS - 1):0] intr_ext_i /*verilator public*/;
input [(EXTERNAL_INTERRUPTS - 1):0] intr_ext_i /*verilator public*/;
input [7:0]         addr_i /*verilator public*/;
input [7:0]         addr_i /*verilator public*/;
output [31:0]       data_o /*verilator public*/;
output [31:0]       data_o /*verilator public*/;
input [31:0]        data_i /*verilator public*/;
input [31:0]        data_i /*verilator public*/;
input [3:0]         wr_i /*verilator public*/;
input               we_i /*verilator public*/;
input               rd_i /*verilator public*/;
input               stb_i /*verilator public*/;
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Registers / Wires
// Registers / Wires
//-----------------------------------------------------------------
//-----------------------------------------------------------------
reg [31:0]                  data_o;
reg [31:0]                  data_o;
reg                         intr_o;
reg                         intr_o;
 
 
// IRQ Status
// IRQ Status
wire                        intr_in;
wire                        intr_in;
reg [INTERRUPT_COUNT-1:0]   irq_status;
reg [INTERRUPT_COUNT-1:0]   irq_status;
reg [INTERRUPT_COUNT-1:0]   irq_mask;
reg [INTERRUPT_COUNT-1:0]   irq_mask;
reg [INTERRUPT_COUNT-1:0]   v_irq_status;
reg [INTERRUPT_COUNT-1:0]   v_irq_status;
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Peripheral Register Write
// Peripheral Register Write
//-----------------------------------------------------------------
//-----------------------------------------------------------------
always @ (posedge rst_i or posedge clk_i )
always @ (posedge rst_i or posedge clk_i )
begin
begin
   if (rst_i == 1'b1)
   if (rst_i == 1'b1)
   begin
   begin
       irq_status       <= {(INTERRUPT_COUNT){1'b0}};
       irq_status       <= {(INTERRUPT_COUNT){1'b0}};
       irq_mask         <= {(INTERRUPT_COUNT){1'b0}};
       irq_mask         <= {(INTERRUPT_COUNT){1'b0}};
       intr_o           <= 1'b0;
       intr_o           <= 1'b0;
   end
   end
   else
   else
   begin
   begin
 
 
       // Get current IRQ status
       // Get current IRQ status
       v_irq_status = irq_status;
       v_irq_status = irq_status;
 
 
       // IRQ0
       // IRQ0
       if (intr0_i == 1'b1)
       if (intr0_i == 1'b1)
           v_irq_status[0] = 1'b1;
           v_irq_status[0] = 1'b1;
 
 
       // IRQ1
       // IRQ1
       if (intr1_i == 1'b1)
       if (intr1_i == 1'b1)
           v_irq_status[1] = 1'b1;
           v_irq_status[1] = 1'b1;
 
 
       // IRQ2
       // IRQ2
       if (intr2_i == 1'b1)
       if (intr2_i == 1'b1)
           v_irq_status[2] = 1'b1;
           v_irq_status[2] = 1'b1;
 
 
       // IRQ3
       // IRQ3
       if (intr3_i == 1'b1)
       if (intr3_i == 1'b1)
           v_irq_status[3] = 1'b1;
           v_irq_status[3] = 1'b1;
 
 
       // IRQ4
       // IRQ4
       if (intr4_i == 1'b1)
       if (intr4_i == 1'b1)
           v_irq_status[4] = 1'b1;
           v_irq_status[4] = 1'b1;
 
 
       // IRQ5
       // IRQ5
       if (intr5_i == 1'b1)
       if (intr5_i == 1'b1)
           v_irq_status[5] = 1'b1;
           v_irq_status[5] = 1'b1;
 
 
       // IRQ6
       // IRQ6
       if (intr6_i == 1'b1)
       if (intr6_i == 1'b1)
           v_irq_status[6] = 1'b1;
           v_irq_status[6] = 1'b1;
 
 
       // IRQ7
       // IRQ7
       if (intr7_i == 1'b1)
       if (intr7_i == 1'b1)
           v_irq_status[7] = 1'b1;
           v_irq_status[7] = 1'b1;
 
 
       // External interrupts
       // External interrupts
       begin : ext_ints_loop
       begin : ext_ints_loop
           integer i;
           integer i;
           for (i=0; i< EXTERNAL_INTERRUPTS; i=i+1)
           for (i=0; i< EXTERNAL_INTERRUPTS; i=i+1)
           begin
           begin
               if (intr_ext_i[i] == 1'b1)
               if (intr_ext_i[i] == 1'b1)
                   v_irq_status[(`IRQ_EXT_FIRST + i)] = 1'b1;
                   v_irq_status[(`IRQ_EXT_FIRST + i)] = 1'b1;
           end
           end
       end
       end
 
 
       // Update IRQ status
       // Update IRQ status
       irq_status <= v_irq_status;
       irq_status <= v_irq_status;
 
 
       // Generate interrupt based on masked status
       // Generate interrupt based on masked status
       intr_o <= ((v_irq_status & irq_mask) != {(INTERRUPT_COUNT){1'b0}}) ? 1'b1 : 1'b0;
       intr_o <= ((v_irq_status & irq_mask) != {(INTERRUPT_COUNT){1'b0}}) ? 1'b1 : 1'b0;
 
 
       // Write Cycle
       // Write Cycle
       if (wr_i != 4'b0000)
       if (we_i & stb_i)
       begin
       begin
           case (addr_i)
           case (addr_i)
 
 
           `IRQ_MASK_SET :
           `IRQ_MASK_SET :
                irq_mask    <= (irq_mask | data_i[INTERRUPT_COUNT-1:0]);
                irq_mask    <= (irq_mask | data_i[INTERRUPT_COUNT-1:0]);
 
 
           `IRQ_MASK_CLR :
           `IRQ_MASK_CLR :
                irq_mask    <= (irq_mask & ~ (data_i[INTERRUPT_COUNT-1:0]));
                irq_mask    <= (irq_mask & ~ (data_i[INTERRUPT_COUNT-1:0]));
 
 
           `IRQ_STATUS : // (IRQ Acknowledge)
           `IRQ_STATUS : // (IRQ Acknowledge)
                irq_status  <= (v_irq_status & ~ (data_i[INTERRUPT_COUNT-1:0]));
                irq_status  <= (v_irq_status & ~ (data_i[INTERRUPT_COUNT-1:0]));
 
 
           default :
           default :
               ;
               ;
           endcase
           endcase
        end
        end
   end
   end
end
end
 
 
//-----------------------------------------------------------------
//-----------------------------------------------------------------
// Peripheral Register Read
// Peripheral Register Read
//-----------------------------------------------------------------
//-----------------------------------------------------------------
always @ (posedge rst_i or posedge clk_i )
always @ *
begin
 
   if (rst_i == 1'b1)
 
   begin
 
       data_o       <= 32'h00000000;
 
   end
 
   else
 
   begin
 
       // Read cycle?
 
       if (rd_i == 1'b1)
 
       begin
       begin
           case (addr_i[7:0])
   case (addr_i[7:0])
 
 
           `IRQ_MASK_SET :
           `IRQ_MASK_SET :
                data_o <= {{(32-INTERRUPT_COUNT){1'b0}}, irq_mask};
        data_o = {{(32-INTERRUPT_COUNT){1'b0}}, irq_mask};
 
 
           `IRQ_MASK_CLR :
           `IRQ_MASK_CLR :
                data_o <= {{(32-INTERRUPT_COUNT){1'b0}}, irq_mask};
        data_o = {{(32-INTERRUPT_COUNT){1'b0}}, irq_mask};
 
 
           `IRQ_STATUS :
           `IRQ_STATUS :
                data_o <= {{(32-INTERRUPT_COUNT){1'b0}}, irq_status};
        data_o = {{(32-INTERRUPT_COUNT){1'b0}}, irq_status};
 
 
           default :
           default :
                data_o <= 32'h00000000;
        data_o = 32'h00000000;
           endcase
           endcase
        end
        end
   end
 
end
 
 
 
endmodule
endmodule
 
 

powered by: WebSVN 2.1.0

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