前面分析了AHB总线协议。接下来分析APB总线协议。

  (一) APB总线接口:

  PCLK APB总线时钟。

  PRESETn APB总线复位。低有效。

  PADDR 地址总线。

  PSELx 从设备选择。

  PENABLE APB传输选通。

  PWRITE 高为写传输,低为读。

  PRDATA 读数据总线。

  PWDATA 写数据总线。

  接口信号定义如下:

 interface   apb_slv_intf #(
parameter AW = ,
DW =
) (
input logic PCLK,
input logic PRESETn
);
logic PSEL;
logic PENABLE;
logic [AW-:] PADDR;
logic PWRITE;
logic [DW-:] PWDATA; logic [DW-:] PRDATA; modport m (
input PRDATA,
output PSEL, PENABLE, PADDR, PWRITE, PWDATA
); modport s (
input PSEL, PENABLE, PADDR, PWRITE, PWDATA,
output PRDATA
); endinterface: apb_slv_intf

  (二) APB总线时序图:

写传输

读传输

  注意在PENABLE信号有效后从设备需要给出有效数据/读取有效数据。

  (三) AHB总线到APB总线转换桥

 module ahb2apb_bridge #(
parameter AHB_AW = ,
AHB_DW = ,
APB_AW = ,
APB_DW = ,
NSLV =
) (
input logic HCLK,
input logic HRESETn,
input logic PCLK,
input logic PRESETn,
ahb_slv_intf.s ahb,
apb_slv_intf.m apbv[NSLV]
); logic ahb_work;
logic apb_work; genvar i; typedef enum logic [:] {
AHB_IDLE = 'b00,
AHB_WRITE = 'b01,
AHB_READ = 'b10,
AHB_WAIT = 'b11
} ahb_state_e; // Signal of AHB Domain
struct {
logic work;
logic [AHB_AW-:] addr;
logic [AHB_DW-:] data;
logic write;
ahb_state_e cstate, nstate;
} ahbd; typedef enum logic [:] {
APB_IDLE = 'b00,
APB_WRITE = 'b01,
APB_READ = 'b10
} apb_state_e; // Signal of APB Domain
struct {
logic work;
logic [APB_DW-:] data[NSLV];
logic PSEL[NSLV];
logic PENABLE[NSLV];
apb_state_e cstate, nstate;
} apbd; // AHB Control Logic
always_comb begin
case (ahbd.cstate)
AHB_IDLE: begin
if (ahb.HSEL && ahb.HTRANS == HTRANS_NONSEQ) begin
if (ahb.HWRITE)
ahbd.nstate = AHB_WRITE;
else
ahbd.nstate = AHB_READ;
end
else
ahbd.nstate = AHB_IDLE;
end
AHB_WRITE: begin
if (apbd.work)
ahbd.nstate = AHB_WAIT;
else
ahbd.nstate = AHB_WRITE;
end
AHB_READ: begin
if (apbd.work)
ahbd.nstate = AHB_WAIT;
else
ahbd.nstate = AHB_READ;
end
AHB_WAIT: begin
if (!apbd.work)
ahbd.nstate = AHB_IDLE;
else
ahbd.nstate = AHB_WAIT;
end
default: ahbd.nstate = AHB_IDLE;
endcase
end always_ff @(posedge HCLK or negedge HRESETn) begin
if (!HRESETn)
ahbd.cstate <= AHB_IDLE;
else
ahbd.cstate <= ahbd.nstate;
end always_ff @(posedge HCLK or negedge HRESETn) begin
if (!HRESETn) begin
ahbd.work <= 'b0;
ahbd.addr <= '0;
ahbd.data <= '0;
ahbd.write <= 'b0;
ahb.HREADY <= 'b1;
ahb.HRDATA[APB_DW-:] <= '0;
end
else begin
case (ahbd.cstate)
AHB_IDLE: begin
if (ahb.HSEL && ahb.HTRANS == HTRANS_NONSEQ) begin
ahbd.addr <= ahb.HADDR;
ahbd.write <= ahb.HWRITE;
ahb.HREADY <= 'b0;
end
else begin
ahbd.addr <= '0;
ahbd.write <= 'b0;
ahb.HREADY <= 'b1;
end
ahbd.work <= 'b0;
ahbd.data <= '0;
ahb.HRDATA[APB_DW-:] <= apbd.data[ahbd.addr[AHB_AW-:AHB_AW-]];
end
AHB_WRITE: begin
ahb.HREADY <= 'b0;
ahbd.work <= 'b1;
ahbd.data <= ahb.HWDATA;
ahb.HRDATA[APB_DW-:] <= '0;
end
AHB_READ: begin
ahbd.work <= 'b1;
ahbd.data <= '0;
ahb.HREADY <= 'b0;
ahb.HRDATA[APB_DW-:] <= '0;
end
AHB_WAIT: begin
ahbd.work <= 'b0;
ahb.HREADY <= 'b0;
ahb.HRDATA[APB_DW-:] <= '0;
end
endcase
end
end assign ahb.HRESP = HRESP_OKAY;
// assign ahb.HRDATA[AHB_DW-1:APB_DW] = '0; // APB Control Logic
always_comb begin
case (apbd.cstate)
APB_IDLE: begin
if (ahbd.work) begin
if (ahbd.write)
apbd.nstate = APB_WRITE;
else
apbd.nstate = APB_READ;
end
else
apbd.nstate = APB_IDLE;
end
APB_WRITE: apbd.nstate = APB_IDLE;
APB_READ: apbd.nstate = APB_IDLE;
default: apbd.nstate = APB_IDLE;
endcase
end always_ff @(posedge PCLK or negedge PRESETn) begin
if (!PRESETn)
apbd.cstate <= APB_IDLE;
else
apbd.cstate <= apbd.nstate;
end always_ff @(posedge PCLK or negedge PRESETn) begin
if (!PRESETn) begin
apbd.work <= 'b0;
for (int j = ; j < NSLV; j++) begin
apbd.PSEL[j] <= 'b0;
apbd.PENABLE[j] <= 'b0;
end
end
else begin
case (apbd.cstate)
APB_IDLE: begin
if (ahbd.work) begin
apbd.work <= 'b1;
for (int j = ; j < NSLV; j++)
apbd.PSEL[j] <= (ahbd.addr[AHB_AW-:AHB_AW-] == j) ? 'b1 : 1'b0;
end
else begin
apbd.work <= 'b0;
for (int j = ; j < NSLV; j++)
apbd.PSEL[j] <= 'b0;
end
for (int j = ; j < NSLV; j++)
apbd.PENABLE[j] <= 'b0;
end
APB_WRITE: begin
apbd.work <= 'b1;
for (int j = ; j < NSLV; j++)
apbd.PENABLE[j] <= (ahbd.addr[AHB_AW-:AHB_AW-] == j) ? 'b1 : 1'b0;
end
APB_READ: begin
apbd.work <= 'b1;
for (int j = ; j < NSLV; j++)
apbd.PENABLE[j] <= (ahbd.addr[AHB_AW-:AHB_AW-] == j) ? 'b1 : 1'b0;
end
endcase
end
end generate
for (i = ; i < NSLV; i++) begin: apbv_loop
assign apbv[i].PADDR = {'h0, ahbd.addr[APB_AW-4-1:0]};
assign apbv[i].PWRITE = ahbd.write;
assign apbv[i].PWDATA = ahbd.data[APB_DW-:];
assign apbd.data[i] = apbv[i].PRDATA;
assign apbv[i].PSEL = apbd.PSEL[i];
assign apbv[i].PENABLE = apbd.PENABLE[i];
end
endgenerate endmodule: ahb2apb_bridge

AMBA APB总线的更多相关文章

  1. AHB总线和APB总线

    AHB主要用于高性能模块(如CPU.DMA和DSP等)之间的连接,作为SoC的片上系统总线,它包括以下一些特性:单个时钟边沿操作:非三态的实现方式:支持突发传输:支持分段传输:支持多个主控制器:可配置 ...

  2. APB总线

    APB(Advance Peripheral Bus)是AMBA总线的一部分,从1998年第一版至今共有3个版本. AMBA 2 APB Specfication:定义最基本的信号interface, ...

  3. AMBA AHB总线

    Advanced Microcontroller Bus Architecture, 即AMBA,是ARM公司提出的总线规范,被很多SoC设计所采用,常用的实现有AHB(Advanced High-P ...

  4. STM32WB AHB总线、APB总线与外设

    方框图: 如图所示: 1)APB1外设 2)APB2外设 3)AHB1外设 4)AHB2外设 5)AHB3外设 6)AHB4外设(ABH共享总线外设) 内存映射关系图:

  5. AMBA总线介绍

    The Advanced Microcontroller Bus Architecture (AMBA) specification defines an on- chip communication ...

  6. APB协议

    https://wenku.baidu.com/view/2663f629ef06eff9aef8941ea76e58fafab04592.html https://www.cnblogs.com/l ...

  7. AMBA总线协议AHB、APB

    一.什么是AMBA总线 AMBA总线规范是ARM公司提出的总线规范,被大多数SoC设计采用,它规定了AHB (Advanced High-performance Bus).ASB (Advanced ...

  8. AMBA总线协议AHB、APB、AXI对比分析【转】

    转自:https://blog.csdn.net/ivy_reny/article/details/56274412 一.AMBA概述    AMBA (Advanced Microcontrolle ...

  9. [转]AMBA、AHB、APB、ASB总线简介

    [转]http://www.cnblogs.com/zhaozhong1989/articles/3092140.html 1.前言 随着深亚微米工艺技术日益成熟,集成电路芯片的规模越来越大.数字IC ...

随机推荐

  1. 大型NodeJS项目架构与优化

    使用场景: proxy(API冗余,跨域) vue ssr(服务端渲染) socket(大并发,通讯) 区块链(创业公司,新兴行业) 讨论什么? NodeJS异步IO原理及优化方案 NodeJS内存管 ...

  2. OneNET麒麟座应用开发之八:采集大气压力等环境参数

    采集大气压力和温度也是核算大气标准状况下的各种数据的必须参数,为此我们必须知道压力和温度才能计算标准状况下的各种参数,于此我们需要一个既能检测压力也能检测温度的元件. 1.硬件概述 MS5837压力传 ...

  3. Sandcastle方法生成c#.net帮助类帮助文档chm

    Sandcastle方法生成c#.net帮助类帮助文档即chm后缀的文档,其实是通过C#文档注释生成的XML文件来生成帮助文档的.因此,第一步就是生成XML文档, 步骤1生成XML文档 1.打开VS- ...

  4. python调用修改变量新方法

    def foo(): count = [1] #将变量放在列表中,此时,内部函数就可以修改了 def bar(): count[0] = count[0] + 1 return count[0] re ...

  5. java基础篇---HTTP协议

    java基础篇---HTTP协议   HTTP协议一直是自己的薄弱点,也没抽太多时间去看这方面的内容,今天兴致来了就在网上搜了下关于http协议,发现有园友写了一篇非常好的博文,博文地址:(http: ...

  6. bootstrapTable 参数说明

  7. java利用Jsch实现在windows平台远程操作linux服务器

    说明:exec用于执行命令:sftp用于文件处理 package com.wyg.simple; import java.io.BufferedReader; import java.io.File; ...

  8. c++ primer 笔记 (三)

    标准库类型string 和 vector ,分别定义了大小可变的字符串和集合.                 bitset,提供了一个抽象方法来操作位的集合.提供更方便的处理位的方式(相对于整型值上 ...

  9. POJ2065 SETI 高斯消元

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - POJ2065 题意概括 多组数据,首先输入一个T表示数据组数,然后,每次输入一个质数,表示模数,然后,给出一 ...

  10. js上传图片回显

    $("#file01").change(function(){ var objUrl = getObjectURL(this.files[0]) ; console.log(&qu ...