|
EDA365欢迎您登录!
您需要 登录 才可以下载或查看,没有帐号?注册
x
4 I" h9 v, S/ G8 `
+ d" w$ _% ?$ ?$ S0 C: c5 N一、实现步骤:4 p8 p# j/ D% W) r0 C1 ?' G9 v
+ B. d4 }# ?4 c$ h$ X
1.查看了中值滤波实现相关的网站和paper;
9 o) S, ?6 p _/ G; o' c) u9 I* m7 h2 U$ X; K6 b# z7 X2 g
2.按照某篇paper的设计思想进行编程实现;
3 V, ]0 `. U$ k* F: A
' z1 i/ p- {9 q% n& u( M3.对各个模块进行语法检查、波形仿真、时序设计、调试验证;( \1 |6 F% `6 c+ P7 x
: K8 o$ S+ K" u4.与matlab的中值滤波结果进行比较。. r/ p! G& e7 S. m* `9 r0 G. L
4 V0 O5 ~) @% U* n( m# v9 s( ^' H/ l; b2 z! h
二、实现过程:
- E( H3 v. ~% S* m- @ l1 b
) J. q/ U$ E3 D- b/ a) I1.查看了中值滤波实现相关的网站和paper;; D% N6 H' P! z& n f
+ T+ x# m( K) n1 z/ X" i% a% Z在网上看了很多中值滤波的设计,也有一些代码可以下载,也有一片讲解的,只是感觉讲解的比较模糊而且不完整,最后看了几篇硕士论文,论文竟然主要做了中值滤波的工作,发现了一些设计思路,然后就按照自己的想法进行设计。
' x5 e5 R2 [, o* `/ k' V
! C# G& G" B/ V: X* l2.按照某篇paper的设计思想进行编程实现;
: k* e8 o i: R) K3 f) E- j) |$ ]0 w" Z) e% E
整个中值滤波模块分为几个小的模块:3*3窗口生成模块、计数器控制模块、3*3中值滤波模块、顶层模块以及最后的测试模块testbench的编写。
6 W/ A4 m! E' d- n* B8 E
, F& Q; p( ]7 n' v整个框架的设计如下图所示(使用visio画的框架图):
8 ?" H# Z1 ^+ f1 [& s$ x
4 p; s# I- H" z% I9 i9 J' ^
" e3 A* }: c! J) E# _- |! ~8 h4 m" g% l* l& d1 T! a
各个模块的设计:
# }7 X7 b" i3 o# H a: z; a& [+ r5 J# h; |5 @" D7 h, I
1)ROM IP核的生成,用于存储原始灰度图像的数据。
7 x3 [+ D! Z5 J9 Y2 G3 N( n9 Z使用matlab生成.coe图像数据文件,然后使用Xilinx ISE工具将.coe文件添加到ROM核进行数据初始化,按步骤得到ROM模块,参考生成的.v文件在顶层模块直接调用即可。
/ l" [5 N& y) B( \! _, i: }/ t' g2 Y) K+ N2 ~* j
rom_512by512 rom_512by512_inst
# Q3 \# [7 [2 o; S (
. e* [2 r" s0 P0 Z7 ?3 b: c/ C5 g) n .clka(CLK), //input clka;6 i( s3 g6 a* n: ~7 M
.addra(rom_addr), //input-from
% w" Q1 i1 l8 V$ E6 R0 E8 w .douta(rom_data) //output-to
2 e5 Q) c2 w k- \ );. D5 I' v& U6 Y0 r6 X$ v
9 I: w- E/ P. P- n$ G
" N( r; x! e+ k9 b注意ROM的存储空间的大小;+ A' s3 P. D% y$ A! ~7 `
! k- J8 y1 ]6 ~7 \
2)3*3窗口生成模块,用于生成滤波的滑动窗口,得到窗口内的所有元素数据。
* Z' k) w, G. l# g1 Q* e; F
' X" H4 T0 i1 X功能:/ I: d* p( R0 m! @" [( X1 u% x
0 v: W1 d9 ~) y% ^% H8 N" t% p(1)根据中心像素点得到所在其所在的行、列位置;/ y( z" W8 S# g7 N0 S# t8 _
6 D7 f) w9 i5 c. O
(2)根据该模块的开始信号设计得到获取数据的有效时间序列;! x5 C# m& {3 ]: j
% x& m( Z. E8 |5 g(3)在读取数据的有效时序内,得到窗口内的所有元素数据;) A! `! P# m7 r f, a: l, N- Z! T
6 R$ v) ~6 W6 `/ ^(4)窗口数据的获取按照一定的时序顺序来获得,类似于黑金推荐的“仿顺序操作”,这个比较适合my style;不过后来发现调试的过程中被项目组的硬件人员改动了一些,甚至说不好,感觉可能是本人还没有理解掌握吃透“仿顺序操作”的精髓吧。
$ ~$ z+ j7 `: d4 m
/ i- l7 S; U6 @(5)根据中心像素点的行、列位置信息得到每个窗口元素的ROM地址,根据某一时刻ROM地址,下一时刻调用ROM模块得到对应的元素数据,下一时刻将数据锁存,然后再读取该地址的数据;所以要注意地址和数据的获取不是在同一时刻,而是需要延迟两个时刻;
- p! u" l' g( t( ?
# ~( G, M2 n9 A: _2 l4 `, a(6)还需要注意的是图像的边界问题的特殊化处理;一般图像处理都会遇到边界问题,这个需要谨慎;5 J( k; U/ C& e G: l! e3 T
) S. T i$ G- C
(7)对matlab的中值滤波函数medfilt2原理的深入掌握对我们编写这一模块非常重要。matlab并没有主要过程的代码,看注释默认情况下边界元素设置为0,这也可以通过结果反推回去发现的。. x* E0 e K6 |- o5 n9 S5 v1 }
4 v+ V3 Z/ P- n: U! [( s4 y' y
1 `timescale 1ns / 1ps: T, _. i2 H& ]# a$ i* M& N
2 //////////////////////////////////////////////////////////////////////////////////. A9 N9 p8 R$ U1 O, n4 g
3 // Company:
; P" H: s0 Y* ?' a" M% L, T" C 4 // Engineer:
, ]: X' H! J2 o! Z 5 // ) b; i& G. Z# q6 S* k1 V
6 // Create Date:
9 Y: Q% o+ [3 t% O6 G" S 7 // Design Name:
/ ?+ X7 W" c$ p+ q( Q 8 // Module Name: win3by3_gen
% g" Q7 k( X- d( Q 9 // Project Name:
, J) ~% I& [! h; O3 m9 Y" P# [10 // Target Devices:
6 Q4 S- @$ K9 [0 w1 E11 // Tool versions: ' t" b+ g# ~) G2 F% }- e
12 // Description: 0 C* M0 A' H" z( f3 {% {$ Q3 Q7 M& d: _
13 //! X. w1 s8 ^% i& H5 M
14 // Dependencies:
{4 }- T3 Z! Y9 j; h& d15 //
2 f& Y" Y4 M% D2 B& K16 // Revision: ! u3 Q. v6 E# R0 i8 p
17 // Revision 0.01 - File Created$ m. _/ _$ C& \$ ]1 a1 @1 q
18 // Additional Comments:
( g5 ?9 Q) ~& e$ _+ ]2 n19 //
7 z! \2 k* @' [20 //////////////////////////////////////////////////////////////////////////////////
8 P: V4 _4 p: Q: ~1 i- ?3 L2 \21 module win3by3_gen(
7 E! R, {4 B+ `7 C22 CLK,
) K, L) {9 ?: \2 B1 @* \' b23 RSTn,
" ]9 G" c9 k. Q# f, D24 center_pix_sig,& S* z9 i9 g `0 G
25 cols, // the column numbers of the input image2 B( o2 |6 j+ I' ^1 v
26 rows,7 b8 E. k0 P& U& O1 o
27 rom_data_win, //input-from U1; ! p+ r) A1 C# _$ Q F* t
28 column_addr_sig, //input-from U3; //output [9 : 0] addra;
7 G% a: e' Z p9 ]29 row_addr_sig, //input-from U3; //output [9 : 0] addra;, U0 G+ a4 _( G, x* e$ B9 m
30 rom_addr_sig, //output-to U1;
8 z: I9 f. S+ c0 r- o31 data_out0, //output-to U4;
$ m3 n7 k( A" ~! E32 data_out1,
9 e4 y% [2 X" m7 n/ t33 data_out2," h) ` K# h9 r; V2 q
34 data_out3,
/ b0 _2 x" q) @$ N# ~# r35 data_out4,
5 M. M! O" a7 o- T, |36 data_out5,( n# L1 M/ a" Q3 }$ ^
37 data_out6,* |' M( z" e4 h0 n
38 data_out7,
0 p) s% ]7 B" b39 data_out8,
" L8 `( r z L8 v, ]: v/ q! F40 win_data_done_sig //output-to U4/U3;complete the win data;
c$ g8 C2 B J& ~; Q8 k41 );
# Z& I9 x8 L" E4 |: z( ~ a42 - @% W( ?: b% [( B
43 input CLK;
) Z+ [2 Q. O4 B44 input RSTn;
+ S/ I0 W4 `: F45 input [7:0] rom_data_win;) x. \$ ]+ `( L& B: h2 ]" b
46 input [9:0] cols;
0 a+ B# k& |6 A- x47 input [9:0] rows;
, R8 j% H4 z9 n) n4 U$ Z2 |48 input center_pix_sig; // 0 O& t+ P) o4 r9 [
49 input [9:0] column_addr_sig;
. U' V: a8 k; t5 x" ^5 k. x9 R- k% h50 input [9:0] row_addr_sig;
0 J! t2 m( i" H( G- p51
! K8 i5 u" [: N3 z52 output [7:0] data_out0; //output-to U4;4 \0 d N9 j! Y: Q$ V b- _' O
53 output [7:0] data_out1;
; S3 l! q4 Q: }54 output [7:0] data_out2;, G @. [- d1 a( n, p, b4 u
55 output [7:0] data_out3;
6 K3 ?2 r6 A/ ~56 output [7:0] data_out4;* n d% q$ v4 m0 S
57 output [7:0] data_out5;" a9 }4 f1 @/ F
58 output [7:0] data_out6;
% v3 c- Q Q2 c1 I$ w59 output [7:0] data_out7;- V7 F, A3 O: w/ A* P% a I
60 output [7:0] data_out8;- t- R% Z3 q$ h7 Q0 ~. k' E. u$ S
61 output [17:0] rom_addr_sig;; H7 E0 z! p9 L8 c g
62 output win_data_done_sig;: r4 \6 L9 `, j* O, f& ?1 _
63 , a) A* ^$ R* z d
64 /******************************************************************************************************************************/ 0 ^2 F2 U* ^8 |
65
- c5 H: N. t9 C$ [# y2 k66 reg [9:0] m;2 H+ ?4 @" D, w5 L5 z
67 ]4 }' `. z4 ?/ E/ u* m' R
68 always @ ( posedge CLK or negedge RSTn )
: \( W; z6 s8 {& [4 `4 G$ z69 if ( !RSTn )9 k0 I$ T' S, M W# `
70 m <= 10'd1;
& S( G- `5 d* g8 p: m1 `- u. R9 s71 else if ( center_pix_sig )7 l" A. y4 b, o) z
72 m <= row_addr_sig[9:0]; P0 b4 `* h; ] C
73 4 }$ M0 L% _) K7 u, t
74 /******************************************************************************************************************************/ 5 n7 y* P7 n/ w& J# ?# _/ M9 w
75 " G/ Q- H$ T9 G; s' `! Y7 U
76 reg [9:0] n;, [ i1 H5 K5 ]8 Z" M
77 " I" r( ]8 z! _1 C+ I
78 always @ ( posedge CLK or negedge RSTn )
- V5 C# s& S# `* j, o6 |) j79 if ( !RSTn )3 B) C+ E* o* t0 w4 }
80 n <= 10'd1;9 J: _4 }0 ` c5 K* C. r+ m) j
81 else if ( center_pix_sig ), Z" ]7 Q( R5 f0 n a4 y r
82 n <= column_addr_sig[9:0];
3 M: T7 N) L2 c83 ; v# Q" X& p4 X% O8 L& S3 U v$ v
84 /*****************************************************************************************************************************/ - b5 p* n0 T5 }/ p
85 / v4 g7 `. M/ v0 e0 P9 c
86 reg [3:0] i;
* a& d9 T! E" Z0 ?6 Y# a) {8 S87 reg isWinDone;
) l+ o& H3 \( x+ O) F88 reg [17:0] rom_addr;
; P8 I8 `" _8 Z6 q: F89 reg [7:0] a11;% H- M% l+ X7 |5 f6 c2 {
90 reg [7:0] a12;
. N2 e% D N6 F, S( ?: w. Z( w8 Z91 reg [7:0] a13;% ^( r( h" E/ A' q7 W* Z/ a: s
92 reg [7:0] a21;
- @' y" g; n B4 p/ k9 b% R93 reg [7:0] a22;. K' A+ D8 S. ]4 b& g- O" \
94 reg [7:0] a23;
6 r2 K7 Y; {+ M95 reg [7:0] a31;
. ~1 L' k5 J3 P2 Z) f) k' c7 o3 K7 W96 reg [7:0] a32;
u" [9 U2 }& p% _97 reg [7:0] a33;
) {0 a# Y4 A/ v4 p6 f( {98
# g, c0 e3 d O, [: k* D5 e99 /*****************************************************************************************************************************/
# T" l4 C+ |% m; Q100
) p$ s* |3 A# k% E101 reg get_9point_vld;0 V; v9 h! ` a6 D+ L; H" q1 T
102 5 q) ^& q3 d6 t5 n1 h3 t
103 always @ ( posedge CLK or negedge RSTn )
7 R1 z- t5 g- I, L104 if (!RSTn)
$ u! ~) j8 ^3 q105 get_9point_vld <= 1'b0;
+ t: v7 z. P" @0 O9 C2 }106 else if ( center_pix_sig )
' n9 J# u% [6 F. L107 get_9point_vld <= 1'b1;
% W; c$ J d+ @108 else if ( i==4'd10 )
0 \+ [' H% T/ d. n) C109 get_9point_vld <= 1'b0;/ M. G9 b @( H; A/ o. u+ G
110
, ~( H: E5 `- E! F, V3 C111 " D3 S( \& @, B. s
112 always @ ( posedge CLK or negedge RSTn )
/ _) T# K) |! T% |2 R+ F113 if ( !RSTn )2 D7 B- b- z0 I* ]$ o" o
114 isWinDone <= 1'b0;
7 j% V& V5 I* P, S5 y115 else if ( i==4'd10 )
% c3 R5 G: l& c: d! b9 w* \0 G# w) G116 isWinDone <= 1'b1;8 a4 i! }6 I8 j5 ?" W8 L& v2 @: }6 [
117 else
# ~' ]) ?) k( q118 isWinDone <= 1'b0;
- v9 J$ f- ~8 v, D$ h7 d119
* A; i }7 N4 f5 `& Y# {: u. v2 I120
8 Q( h0 t7 ]6 Y+ o t4 x121 # C# Y8 i* }3 X
122 always @ ( posedge CLK or negedge RSTn )
7 k) `+ ]) a3 H' _+ o123 if ( !RSTn )3 @( m5 Z/ x! P* a' Z( M; q
124 i <= 4'd0;: F2 ~& z! o+ H+ L' A+ y- f7 g; F, H
125 else if (i == 4'd10) * h9 y' q0 Y8 q( x
126 i <= 4'd0;9 z% @8 J4 g r
127 else if ( get_9point_vld ) 3 S7 X8 _: `5 y
128 i <= i + 1'b1;4 l, t& A2 V% H/ r
129
0 a4 u U. ~8 v0 k, N130
0 d2 E& @9 Q1 \* G4 E) j131
4 l: t, A: p2 n0 i% l2 a132
# w2 M3 }4 J ?$ M2 V7 f9 f133 always @ ( posedge CLK or negedge RSTn )
9 u5 M5 t$ h+ h ?- d6 \134 if (!RSTn)
/ |' G M0 p- o2 J" ]) V6 t9 U6 R135 rom_addr <= 0;
$ j7 F% ^% n* V5 i+ K4 ~# @9 [; {136 else if ( get_9point_vld)% b9 C8 B6 o; |' r2 \
137 case (i)
0 `( M% H1 Z0 q138 4'd0:
% J0 A# I* F8 H- B Z! C139 if(!(m==1 || n==1)) rom_addr <= (m-2)*cols + (n-1) -1; 0 v. Z. L8 Q8 h+ n+ {; c
140 L; W4 r, A9 m
141 4'd1:
9 }& V- E/ N3 N( A2 r142 if(!(m==1 )) rom_addr <= (m-2)*cols + n -1;
) q" k6 t' F: l" j7 k* t2 t143
0 H6 \2 d4 y% `, m' f+ V' |2 _- E144 4'd2:
2 F" \: v% `; _3 j145 if(!(m==1 || n==cols)) rom_addr <= (m-2)*cols + (n+1) -1;
( A& t& A; [3 ~: x3 u146
_. f2 J: P; c' O; U6 F147 4'd3:. ^* m1 Q# z+ L- c! B% L
148 if(!(n==1)) rom_addr <= (m-1)*cols + (n-1) -1;
8 u5 L) `9 \# Y1 x149 . u0 r: a- V6 ?( v) c% ^
150 4'd4:" C$ L; [5 K- D' |+ b6 f4 ^
151 rom_addr <= (m-1)*cols + n -1;
( E7 T" h& p* h' A3 C- D# A152 ) a2 N4 w% y, o1 Y x1 X1 H5 r
153 4'd5:
}+ j: E4 L% n, S1 Q% b) ?154 if(!(n==cols)) rom_addr <= (m-1)*cols + (n+1) -1; 9 K4 g2 r ~ E3 h- a* S
155
! z( w4 y* u5 r+ ~ Q, d1 E; w156 4'd6:
1 u ]3 [" `" S" E. c4 Z157 if(!(m==cols || n==1)) rom_addr <= m*cols + (n-1) -1; ) ~0 P6 e7 [& }) ?, e4 l
158 : g1 w7 ^! _" v
159 4'd7:
3 L( t; K' d5 ~) E; H160 if(!(m==cols)) rom_addr <= m*cols + n -1; / v+ M& { D0 |
161
3 P; o8 [) e5 R162 4'd8:
" t/ R$ I' S& h$ U/ L163 if(!(m==cols || n==cols)) rom_addr <= m*cols + (n+1) -1; - ^2 S! B: Y( [$ E8 @! O* {: @; y
164 " b8 @! C7 P6 k% K2 ^+ n0 {: F( f
165 default:;
% }' Y i9 |9 O166 " O! b( X8 z1 M# b
167 endcase
, w/ }% q0 W4 e* M k* H168 $ k1 y1 S1 T2 y3 T z: @ R
169 always @ ( posedge CLK or negedge RSTn )
3 C, _: }, e, v- f: h170 if (!RSTn)3 b; m$ r- m; c
171 begin+ i8 g' c" A: @ S3 t
172 a11 <= 0; 5 X9 u5 s" C- {0 P; Q
173 a12 <= 0; ! l2 d8 K/ S; \" k; P6 q! a5 h2 t
174 a13 <= 0; 0 M% v# g, Q1 k; p
175 a21 <= 0; & x( D' ^4 l' d. `, L) n
176 a22 <= 0;
4 Q1 n% k5 {; o1 K" L177 a23 <= 0;
' q- j/ K$ j& j( O178 a31 <= 0; ; W i: {) X( k% l
179 a32 <= 0; b3 i9 b% ], ~! \
180 a33 <= 0;
; E9 l) t. f! c. d7 C6 f181 end
5 W: t3 j8 O# J- [; s! G0 Z182 else if ( get_9point_vld )
2 V; R2 Q: l% W% x+ Z- [183
! x# a/ a. }# `& @) F184 case (i)
" T l8 o. {& j. ]9 v( R# z& y& ]185
5 y* X" y, {, ~6 C, h, m186 4'd2:( t l* Y; K# w# u
187 if ( m==1 || n==1 ) . O& q1 r- L% g
188 a11 <= 0;
9 c$ y2 G- _+ N" w& [189 else ( [& k$ R! X" r+ D3 k3 q% J7 P O% [
190 a11 <= rom_data_win;
; z! L4 \$ a) t' S191
# p, G/ {8 R, u1 C \5 T192 4'd3:: D, a2 b3 }$ W# K2 v# w" T) h
193 if ( m==1 ) a12 <= 0; ' |+ C4 Z' A+ E' y. R& r
194 else a12 <= rom_data_win; 0 X" j& R% n' u v9 Y" [
195
, B3 s6 r8 _$ {. W/ V; f196 4'd4:# [( c6 S7 b* i4 S9 P" }
197 if ( m==1 || n==cols ) a13 <= 0; $ h" p8 p# x2 j c
198 else a13 <= rom_data_win;
4 L7 u* F2 z @1 S199 # v( {* M' r8 Q' G, S
200 4'd5:
$ V, v! @. L9 i k: b5 Q1 D201 if ( n==1 ) a21 <= 0;
h z6 c# R) r6 J4 o# i202 else a21 <= rom_data_win; + j! N! J+ b# v9 E8 M$ v$ {
203 + F% k1 Q* I6 u' v& J
204 4'd6:8 b7 A0 @/ I# w% ~, n- I+ A
205 a22 <= rom_data_win;
% ]5 E/ {$ E% }. l206 5 |: C- a2 z" {7 a8 V
207 4'd7:
7 p' s( E- c+ h1 f# X! X208 if ( n==cols ) a23 <= 0;
, `$ x4 d7 C' }: E: f209 else a23 <= rom_data_win;
2 m8 E6 N# e9 ^/ S210
, L7 T8 e, b" K* m9 j% {211 4'd8:
6 ]8 f4 ?" ]1 i9 [212 if ( m==cols || n==1 ) a31 <= 0;
' a, G7 j4 g- ]213 else a31 <= rom_data_win;
: b2 C+ a# s+ n214 & p* T, ]/ t9 Q6 {
215 4'd9:
0 Q& ~4 N' X. t' v o- J216 if ( m==cols ) a32 <= 0;" J' a# Y4 y1 u( s1 y. ]
217 else a32 <= rom_data_win; _9 Q# d) ]& T3 O
218 , A% H, j8 @$ y4 l8 q
219 4'd10:# I7 h9 W* o* C0 ]
220 if ( m==cols || n==cols ) a33 <= 0; ! z0 o! ~& f8 G9 P' d p7 A. G @) y
221 else a33 <= rom_data_win; - {* R- [5 H. r! A2 b
222
0 S( q& K* ^2 |223 default:;) W* B& F8 b. @4 g( @
224 ) F# W8 L9 D2 Z
225 endcase. ?/ D; {0 b7 P) _9 y* e0 x& I5 X% R
226
, N/ L& U. b: K3 W7 H227 /**********************************************************************************************/- t9 P4 G& ]. ?, p2 ]8 H
228 4 j9 `- G* Q9 f
229 assign win_data_done_sig = isWinDone;
+ o7 \) i6 U9 J230 assign rom_addr_sig = rom_addr;
7 w! W( k! D6 U6 e/ X% b! `" ]231 / y* \( J) z# M. g- ^
232 assign data_out0 = a11;
" Z9 Z+ ?/ ?/ U' D' d9 F! M4 g233 assign data_out1 = a12;/ C' F8 L! j6 V9 ]
234 assign data_out2 = a13;
) n2 ~) ?% W; V0 M3 `* A6 C235 assign data_out3 = a21;
, Y7 |5 O0 I$ Q% O: c" k236 assign data_out4 = a22;
c8 P9 }1 G2 ]$ O4 w237 assign data_out5 = a23;4 Z+ H* f: B8 [3 F
238 assign data_out6 = a31;
3 Q) H: H4 h$ }+ m0 _- `- q% W: ^239 assign data_out7 = a32;
7 J7 ]8 k- R1 i$ z7 s240 assign data_out8 = a33;
3 D3 h& _% J( F2 Z241 - m+ l+ u' p7 H' i
242 /**********************************************************************************************/
/ Z [7 q: N0 f L5 f! X: o0 p243 # U) d( n( G% t9 M0 U; |
244 endmodule _- D% m1 }' ]3 O; I0 j
7 q" {- Z) n3 k3 O8 `7 V
) J" i- p8 i# _! ~
3)计数器控制模块,主要用于获得中心像素点的地址信息。
0 \8 k, B9 R3 o# g2 n; z9 i% i$ ~1 ?2 F* y4 W* [0 z
(1)系统模块开始信号之后开始获取第一个中心像素点,注意初始化信号值和系统开始的信号值的区别;
" q8 \# D( ~; N* Z" t
6 q( }) _/ m7 p0 u1 i( _1 ~(2)该时刻得到的的数据将在下一个时刻产生结果,该时刻的数据并没有改变;
6 K7 d' S; W/ k. v' I! i4 `% G8 M
z0 M9 E/ Z5 ? }(3)注意中心像素点的行、列位置信息的计算;7 {: C" \% n7 J9 k# v2 U4 z# X
4 m- M; Z" q2 C* U: T
`timescale 1ns / 1ps6 p0 h; H: k l1 I+ F2 `
//////////////////////////////////////////////////////////////////////////////////$ G' {0 ~1 G6 L4 i( _8 n
// Company:
' b$ X$ N- y) I: R9 l1 T// Engineer: * J7 L: O5 Q( w: }6 |
//
& K( p3 w3 L Z% x// Create Date: % i& k# |/ \$ A6 T! }$ P2 K, p/ S
// Design Name: g2 c2 b( i4 u/ Q( E/ I
// Module Name: counter_ctrl
; D$ {( ~1 d$ Z1 P/ d8 [// Project Name: # C& T2 H$ R- ?" D! {& }
// Target Devices:
$ E' j& l+ e( Z5 E/ R// Tool versions: 0 v5 U, z2 b/ j6 E5 W
// Description: 4 k; j2 X2 e$ n5 Z/ q& q
// M2 M- K, K$ P# ]9 r% W+ [% E
// Dependencies:
6 [+ j/ ^0 Q" A( b- i//' h! X. c3 |' ]: Y- N' Q
// Revision:
% j( S- l& p% z0 [9 D// Revision 0.01 - File Created
4 S+ I: V/ F' ^8 w8 a: k/ W// Additional Comments:
/ K3 t6 X4 F' l: a! a//* G7 n; {, |; i/ ?5 H+ C+ g5 @
//////////////////////////////////////////////////////////////////////////////////
: l b2 Y6 W6 ^3 k9 z+ S* ^0 [module counter_ctrl(2 c3 x: Z( V- B) O8 N# b: C9 p# [$ p# D
CLK,
1 z$ g6 a* H4 r( q9 [ RSTn,$ i1 B/ f& Z# G N, w
start_sig, //input-from top$ P; @; a% }+ Y1 u# [
nxt_pix_sig, //input-from --start next center point pixel# M$ \, g* Y" g W, d
cols, 5 y0 n6 g3 E: G, `7 H# i- q3 ~
column_addr_sig, //output
6 o4 B% m8 h' H) m# L3 { row_addr_sig, //output-to
& G9 ]" q4 k- E% ~& i pix_done_sig //output-to3 j9 J( {4 p, r+ B; N
); ?4 k+ t8 s- O$ |* t
* K& U$ V7 s+ H, u$ _
input CLK;
6 L* y( z5 B4 j ^6 h# c) s input RSTn;9 t8 J1 D& G7 G) Z; s( {- t
input start_sig;7 \: x! H5 l3 j" P- C: _ L$ d: T
input nxt_pix_sig;
/ R" b; j- C* T: N+ } input [9:0] cols;
/ {" t. F1 E/ a5 y
) g- A6 W0 a& J output pix_done_sig;
7 w# v; r7 c% [! ~ output [9:0] column_addr_sig; 4 C G) D1 d; g' P8 @8 c8 M
output [9:0] row_addr_sig;
) r0 a8 k+ l! X! G
3 K0 w: n! _1 `/***********************************************************************************************/
$ r0 a+ x, k1 j; k( A2 n5 a. n+ c. g5 i. F. M9 B4 J3 @/ y
reg isCtrlDone;5 t ]7 d! D" g6 m
//reg isWinStart;) Z1 o: I9 a* h4 Y; |
reg [17:0] imk; //The k-th pixel of the image
. ~0 f! B5 T- Q+ d reg [9:0] row_addr; // The row of the centeral pixel
1 \5 C' x; a9 Z9 I1 S) U5 `2 e reg [9:0] column_addr; // The column of the centeral pixel9 m: \4 Z9 p: M7 u9 c, ^
0 j( g+ O$ O+ {0 T5 L# c reg start_sig_d;
! l- [, n8 Y( |3 {6 }9 W I$ Y) \- V. _+ r8 I
wire start_sig_rising_vld;! u" C( q4 Z0 n. l: K H5 f! S, }
9 d; q- T+ f* N1 c3 ~9 \6 J always @ (posedge CLK or negedge RSTn) //Asynchronous reset
' |% P* V" _: t- r0 X if (!RSTn)
9 g7 h# Q" X5 A: c+ ]) z start_sig_d <= 0;
! ~2 a2 ] f! I6 L else
' q0 }2 |6 E& E! F' ?7 r start_sig_d <= start_sig;8 g- O; ]6 Q4 d& C8 t9 w
+ X5 P/ M/ `( P8 L% U
assign start_sig_rising_vld = start_sig & (~start_sig_d);
$ v# x# q: k+ B6 M( y& z8 O2 |$ Q4 U# X: \$ I2 y
always @ (posedge CLK or negedge RSTn) //Asynchronous reset8 d+ E. G) V! k! z% V- \$ h
if (!RSTn)( j" L i9 h( t3 U
begin
3 E; k ?) E' @. f( i imk <= 18'b0; 0 z2 @; ]8 Y$ g8 K% o: O' p
column_addr <= 10'b0;
& X& N' m- H# D% l6 n. Z row_addr <= 10'b0;
/ `, |' R8 U5 z; r% w' D isCtrlDone <= 1'b0;
$ Z# I5 V" \- [5 W; y; v end2 q# l0 @8 N, W7 A
else if (start_sig_rising_vld)
% i1 q6 A8 A; s9 g# Z! X begin
$ N& d- _* Q4 ~2 D" u4 O* o7 d imk <= 18'b1; : q, X, b% Y2 i, a8 H* P0 x
column_addr <= 10'b1; 4 ]% q- I, [( M1 O
row_addr <= 10'b1;# [! D5 W( T; @) ^ T! [! Z) p
isCtrlDone <= 1'b1;
' ?" J6 B- A x+ y, N f& H+ a end ! k. k" b! F6 P0 `
else if ( nxt_pix_sig )" I5 ]/ J- d k) o" S
begin 5 S" Z; n% B. ~1 k% A/ Q
imk <= imk + 1'b1;
4 E9 Z5 |3 \/ C7 @/ a row_addr <= imk / cols + 1; - a& f, d$ M% z8 K4 k5 q, Y
column_addr <= imk % cols + 1; 5 r! E! m. p3 @: @+ a1 `
isCtrlDone <= 1'b1; 7 `/ z# R3 }8 D* k
end( i, k$ b0 r2 k3 q4 ^) o
else isCtrlDone <= 1'b0;
7 e& k7 M( D5 Z e. F; e: C, [8 Q0 |/ o, A0 b
/*****************************************************************************************/4 ^# O+ `# \* o/ p, d
8 i, m n- p9 F& y. I: l! o assign row_addr_sig = row_addr;
4 g# N$ F6 C. Y" ~ assign column_addr_sig = column_addr;2 r8 Z# ^4 H9 L9 l! f R
assign pix_done_sig = isCtrlDone;( P3 u" q# T9 K5 S2 V6 B, _3 `
8 u& i5 [" z O5 J
/*****************************************************************************************/2 e; _, G% }6 h% {* j7 D4 O5 @
endmodule' r8 z+ w( R! U
3 N( u3 M2 @' ~6 [1 G# J0 O6 y
4) 3*3中值滤波模块" j0 E# c0 U B8 E5 e6 ]9 H
7 G1 E6 `, L1 o$ S w功能:得到某一中心像素点的3*3滑窗区域的灰度值的中值,作为中心像素点的值;% A$ @ q" m3 Y* Q; @; J2 S
$ f6 A: U5 e3 X8 x! \0 y
中值滤波原理,网上有很多,大家可以查看一下。( `6 [3 A: V2 X
( H) @1 ^, N# d8 |本项目采用的是快速中值滤波的方法。
1 u5 |3 D3 w5 ~- J! A- {/ Q7 Y) ?& n; k2 f% l* U- l# U' Z
(1)若是3*3窗口生成模块完成之后就计算下一个中心像素点,需要将该中心像素点的窗口元素锁存起来,以防计算过程中将这些元素掩盖,不能正确进行中值滤波的计算;/ l; R q5 w( k5 i. j( b
w4 j- p2 I+ t$ Nalways @ ( posedge CLK or negedge RSTn )8 x- `0 c7 O9 p! Q; i9 K
if (!RSTn)
. k3 V" N9 o& {" }/ j0 r: w/ i begin, Z" ~( B" P; W3 l' D
a11 <= 0;% ]5 I+ d b( n3 x0 {5 e
a12 <= 0;, r% y8 j1 S9 b: f" W3 A1 u
a13 <= 0;
9 K' T) s% P0 h7 f5 I/ R a21 <= 0;% i( z# S) V8 i" P* u/ l" Y
a22 <= 0;) p7 Q8 _ S0 l. w! ~( r1 d9 Y
a23 <= 0;7 x4 k0 {, g! h' g2 B8 m6 j
a31 <= 0;
7 B6 m3 x0 U3 L+ J, I5 a a32 <= 0;
F7 m6 ^2 z" r, K- O: h a33 <= 0;- V: U) Q1 J# f* P+ g% B
end0 L& ~7 a" {: [, l2 E0 n
else if (win_data_sig)" p9 y! c: Q4 S8 I3 V
begin
4 C; t5 X' z: P a11 <= data_in0;
$ A- U6 V! B' X! y5 R a12 <= data_in1;
. X+ l8 F0 D- f2 {9 j a13 <= data_in2;
+ l8 k0 N: O F, N. { a21 <= data_in3;- i" C% K3 I) `( s
a22 <= data_in4;- u: L3 o" A# @9 q
a23 <= data_in5;
; t- b g# Q# L, V9 L a31 <= data_in6;' J) }7 E2 X3 ^
a32 <= data_in7;# B, k$ s4 `/ d6 S0 x
a33 <= data_in8;
8 R8 \; `8 [6 R: F end. @) Z8 m1 d* |+ V x
0 j! A5 q8 z, y
' ?( Y7 I' y* f. H% R" f9 d- E(2)需要在时序的有效区域内进行计算,怎么设计信号的有效性;
G4 Q- `$ V( s3 ~) L4 n
( p+ j( q8 s) f* O( E3 K6 _( T+ c$ l' W always @ ( posedge CLK or negedge RSTn )
4 Q4 Z: m4 f" j+ ] if (!RSTn)
+ o7 q$ z5 m6 D& U1 I cal_vld <= 1'b0;
5 `; E- f3 L* @( ^- D8 M else if( win_data_sig )
) w, `% T; B$ ` cal_vld <= 1'b1;
! E. k) z! O0 b2 Q4 a7 w! l/ _ else if( i==3'd3 )
( t: j5 G( Y( ]5 ~+ W5 s" X3 X! j3 s cal_vld <= 0;
6 B1 k9 l) F( L# o0 V' e; q3 J! k' l
: I- [. e- u, d2 m(3)仿顺序操作可以分开进行;每一个时刻只进行一个操作,这样可能更明了(代码中没有这样做);
# T& g) j' r/ _) c6 `2 u. W" R) y8 w* [) u7 Z2 x! L9 C! m: Z
always @ ( posedge CLK or negedge RSTn )
" B* ]8 _1 H( J0 i+ d" R q if (!RSTn)& d' Y Q: E5 k- b# a
i <= 3'd0;
# k9 x0 \5 _3 Y. E. B" Z; j7 R# Y else if( cal_vld & ( i!=3 ) ), N+ v( S; g- x% D- |
i <= i + 1;; V3 ~2 d2 s8 H% K$ R; u1 q
else
! s0 M. ?) M, a( F, O) l+ Y9 B) i i <= 0;) W! L K/ c2 l1 ]
; @* z9 q$ k" |7 |
(4)verilog编程调用函数的方法,指出输入信号,函数内可以使用其他定义声明的信号,最后的输出信号作为调用函数的结果(突然想起来,如果输出信号有多个元素呢,又该怎么办呢?大家可以想想);
9 F6 ~/ B$ p( ^5 j K
5 J* A" F1 _/ e+ B; }) U# kfunction [7:0] max;//if the data is signed number, please add the char signed behind key function;
T1 g6 @0 [' V1 o. v7 s$ K input [7:0] a, b, c;
$ S/ C1 A& C3 C7 Z* ?% P begin' h2 W5 J- o: d( q& C4 Y/ @
max = (((a >= b) ? a : b) >= c ) ? ((a >= b) ? a : b) : c;! c1 r& L! M, D0 S& p
end
4 o( m3 h9 d, Hendfunction
2 K3 ^8 Y6 {/ O! O* G0 i6 ]3 ?( w( Q( `
该模块的代码:
; ?# x$ X: |! C7 Z/ ?1 h# K`timescale 1ns / 1ps, G2 `: p/ {; ]2 M
//////////////////////////////////////////////////////////////////////////////////3 K" q/ x9 n% B
// Company: ' j+ m4 w" R& e4 C6 W- Z! `
// Engineer:
1 T! Y! @/ S0 ^ u// , l/ a# j9 G9 j" x
// Create Date: ! @% j1 O6 I2 w
// Design Name:
+ L7 t! m; L; Z6 B' H// Module Name: medfilter3by3
3 ?8 D' a7 |, F3 b/ {! l* a: W// Project Name: 8 c, t3 e+ y7 m: Y6 l9 ~8 Z! R3 [
// Target Devices:
% k5 {( G, Y. o0 F// Tool versions: 8 Q) D" Q; m2 ]; k" G% O
// Description:
/ t. P7 f7 Q% B% ?) x: N* E//* c$ u7 r' @9 D0 @
// Dependencies: K8 A; G+ l* P
//
9 p% k! G7 _1 [3 m( w// Revision:
7 H" ]7 N T. T+ p& H// Revision 0.01 - File Created
4 |3 N9 V# ~" r// Additional Comments: ) f) a2 u/ X; l( S# K
/// R' b3 o5 X/ {9 G/ @# s
//////////////////////////////////////////////////////////////////////////////////7 `2 Q: ~! g1 W/ g1 ^5 e4 M1 _
module medfilter3by3(
' O& p8 a; D) g0 L& |: B1 ?" w CLK,
/ F. U2 r3 s2 @* G/ w! [& q5 g0 m& a RSTn," I5 n6 y" P7 N
win_data_sig, //input-from module of win3by3_gen;
) S R J5 v* F2 X3 f% K1 \2 w medfilt_done_sig, //output-to top;9 y- Z& _: E" d9 G* U9 j( ?
data_in0, //input-from module of win3by3_gen;& h( Q% z9 r% ?2 X5 b. A
data_in1,
0 ^3 u0 r$ {6 W6 S; u. G$ w; X) f data_in2,* j' B" v6 E; f2 d
data_in3,, M9 ]! j( T o
data_in4,3 g8 O, z0 V5 a6 V( }. e
data_in5,
, w/ ?4 e! o; I8 ~/ F data_in6,
0 S& \' h) Y, l: K2 ? data_in7,
- j/ Z, n7 w: b: H' l data_in8,
h# d" z8 O% p0 e& h9 d4 D medfilt_data_out //output-to top;
# z; |) b* k% q) u" P) q+ k );& z1 t5 i {1 b
& P% W; n, a: W/ H- d% a2 j) v
input CLK;
7 B. l; F1 {/ F+ @6 D input RSTn;; l6 f# W6 u% O8 A4 K2 }
input win_data_sig;8 q7 N3 T- o$ B9 i- [4 A+ w
input [7:0] data_in0; //output-to ;
j9 e4 z) _) k6 B, z. ~2 e- _ input [7:0] data_in1;3 W% p# c2 @; T
input [7:0] data_in2;6 j+ {# H5 r' g9 D1 O8 |* g
input [7:0] data_in3; K3 W# k# l2 o& O- p8 T) u# v
input [7:0] data_in4;
) b/ H2 ?+ b- E input [7:0] data_in5;
2 G" [+ W' X9 m, x1 W0 G input [7:0] data_in6;
& M, ?& l9 W6 E! F/ [ input [7:0] data_in7;
2 E0 N. `- |6 f: X7 T6 w4 m" | input [7:0] data_in8;
: j# d$ M7 u2 l, p' V( ?+ _+ ]' b) ?& {8 f- m
output medfilt_done_sig;
1 h; d) s3 A2 m1 G% ~ output [7:0] medfilt_data_out;% f! v+ _. O) k% ]
7 y) ]- D, p# J7 C* j" ?/******************************************************************************/ ( m2 q9 }9 o: E3 r9 K
reg [7:0] a11;) ~" ^' T+ S5 v7 F
reg [7:0] a12;
) Y* `' Q, O) e. }4 \1 O reg [7:0] a13;- C" S% v/ i6 y
reg [7:0] a21;
u' w) o1 o% h. l, S reg [7:0] a22;* O9 u+ e8 j& F- d
reg [7:0] a23;8 l7 `- j" Y( m& s, Z9 Y% U4 B
reg [7:0] a31;/ Z% \3 a u" \3 q! u+ k
reg [7:0] a32;
; h+ X0 F0 F' u3 B) z! i. u reg [7:0] a33;9 c/ g$ D. b% J B
/ L+ }- o* X! M0 L1 y% t+ G reg [7:0] b11;" B4 {1 p' J! ?8 C5 i" L
reg [7:0] b12;
1 b) O* r6 p$ U- P6 P k# X reg [7:0] b13;
* F% S1 c! c8 _2 { reg [7:0] b21;
, v; [' J: \7 W) L* E reg [7:0] b22;
& [/ c2 P& e* b+ H J reg [7:0] b23;1 e' T! @: Q& ~2 q: R; y$ u
reg [7:0] b31;8 _1 E" y' I5 C5 `' C
reg [7:0] b32;* j: S% z2 K; u/ Y% ? [/ h/ r
reg [7:0] b33;8 B3 Z9 [6 L: v* Q
( U/ \: k5 g. I4 \* ~- d
reg [7:0] c11;
* ] R) M' i6 n- U: ^ reg [7:0] c12;% M$ v( {" o$ W6 _
reg [7:0] c13;
1 D$ Q: ^# f. N9 f" o reg [7:0] c21;) W/ t/ V* ^9 y9 {
reg [7:0] c22;
$ K( L) P# P* A' K0 x3 p reg [7:0] c23;
0 u, G* x9 w( x, ] reg [7:0] c31;
7 v% a0 `+ ?3 F+ B reg [7:0] c32;5 ~* ~3 R$ b3 }" v) W
reg [7:0] c33;
9 [6 M5 Y' O% Q3 s( C
; c5 Z N( h! | reg [2:0] i;
0 L4 m+ S" V+ Z reg [7:0] medfilt_data;# b. c# P3 ?) T2 V
reg filt_done;
9 k4 w! @/ o1 N4 R5 d
+ E5 t7 P+ B, w# i& u5 |* w% r$ I7 T reg cal_vld;
* U8 {2 o) i+ }) q/ ^$ N1 j% i- h8 Z, q6 L0 e* D6 S
0 V% f1 U0 F& P, Lalways @ ( posedge CLK or negedge RSTn )
9 N9 C8 d: e/ ~) A8 w1 q5 M if (!RSTn)+ }3 W" \1 @, O0 Z# j% l, B8 }6 d
begin
1 D& ]0 C2 X/ O8 x; J& S a11 <= 0;+ @% {# z- s+ S7 d" D2 d
a12 <= 0;
x; \' n) |6 Q a13 <= 0;5 s! j2 i; d b/ r
a21 <= 0;5 a# r& i6 h: _! O; {
a22 <= 0;& `6 Z# A7 Q& X) ~5 O
a23 <= 0;
3 S1 U; ~, @" J0 S4 X' K F! G) w z a31 <= 0;
9 J5 }% g2 H k a a32 <= 0;; S, ]+ f' b- w% A$ n# j* A
a33 <= 0;; M# q$ q' R9 u5 d" R
end
/ B2 S4 Y; o5 _ else if (win_data_sig)$ ]) f. s( U# G9 g1 g
begin
% J* x a$ s2 Z2 [- g, [5 s a11 <= data_in0;/ M& j% P1 m4 {/ M: T
a12 <= data_in1;
4 i5 Z& a7 I9 h$ t- t6 ^ a13 <= data_in2;- e/ _1 l( [- |5 j3 y. v! W3 {
a21 <= data_in3;/ M* W, T' k" Q( H
a22 <= data_in4;
5 s2 l/ }% d6 f+ @. X' j a23 <= data_in5;9 T/ T$ X& U- R& C
a31 <= data_in6;# W9 `* ~" ^5 U8 S k" {' c% m/ P2 @1 A
a32 <= data_in7;
! `4 u% ^- D' z" e a33 <= data_in8;
, o) z/ ^6 Q/ f. P, U end7 C, ]% }' n2 m: p; b& w
4 E$ @' x' h [% K: y. D4 X always @ ( posedge CLK or negedge RSTn )
& \( P. Y( i" W# K+ w* o. D" Y if (!RSTn)
" k- T' I+ w* P. j1 x0 P7 q i <= 3'd0;
+ g& ~) T1 L3 K3 g; n; ]0 u0 Y else if( cal_vld & ( i!=3 ) )
4 G0 f* Q7 K M4 C' o" ] i <= i + 1;
0 A, H2 E9 d1 z5 w9 G2 y/ j else
% c! C, [9 t7 Y, j i <= 0;) q& a$ M2 {0 ~4 c% I# a) N
6 I1 U0 o o: m6 k3 U: n+ }
always @ ( posedge CLK or negedge RSTn )
; ?# {2 [' Q% H if (!RSTn)
$ m6 k; V" ] @# ]* V | cal_vld <= 1'b0;! {& _- L+ `+ T! {9 }
else if( win_data_sig )
1 ~8 o5 W4 l2 {( T8 [( _9 L# ] cal_vld <= 1'b1;
5 C1 b/ H3 P& E/ @ else if( i==3'd3 ); R0 Z; L! P" D$ i6 f
cal_vld <= 0;
6 K, Y( P7 L3 s' E5 g3 y, Q( ?3 f# O
* P. N1 _& d1 x, r8 D) q: N
always @ ( posedge CLK or negedge RSTn )& u, r' Y E% E( G- J7 J
if (!RSTn)
q- ^& @: j# X begin' W6 v& h8 m! a" y4 H/ k
filt_done <= 1'b0;1 ` z, L5 u/ m; ?
b11 <= 0;0 u) G: c2 X1 y) J' R
b12 <= 0;- I/ S5 A: {: K @2 ]
b13 <= 0;
: p8 s& O e- U b21 <= 0;
2 `( F% I; T, k7 M9 M b22 <= 0;
) X; t. z9 V" g/ { b23 <= 0;
' C& ?" ~/ l; U6 u" b b31 <= 0;
" S' ?$ Z$ a; a9 M9 s1 l. @ b32 <= 0;. l3 t; y0 M4 q% u
b33 <= 0;
& h; a' G3 v9 D, ]) b$ W5 s c11 <= 0;
- t, k1 K4 A0 a c12 <= 0;
6 C1 ?4 {& s0 N4 z( p+ d; y6 g c13 <= 0; y. K; v& l) F
c21 <= 0;
# q2 [ L/ w# k# ?3 T7 J- K c22 <= 0;
( I+ O: Q+ p5 e' { j c23 <= 0;
/ u2 t1 I3 Q4 R- p' k" q& S c31 <= 0;7 j5 y( R0 _! d1 _* p
c32 <= 0;0 b. S, \# J, z/ B$ i3 W' S3 V ]4 b
c33 <= 0;
0 A7 M/ z! q- ^% {, P3 T5 i0 y medfilt_data <= 0;
* z6 s" B* L0 x8 p8 i+ S' U end
( j1 {& P5 @% y9 N6 e: K else if( cal_vld )' ]4 V/ Z+ s3 n8 ?2 t" @" D
case(i)7 M2 `& t) p! u) l2 }' b
3'd0:' c% P, Y- t7 G# I3 y9 O) [2 U! b+ M
begin
2 G' ~4 u( Z1 l b11 <= max(a11, a21, a31); & s( B1 N# ]! n2 J* b; j7 w. i
b12 <= max(a12, a22, a32); 5 M6 g7 ]( e+ o. s9 U, f
b13 <= max(a13, a23, a33);! p! ]6 X9 N$ I
b21 <= med(a11, a21, a31);
2 d6 w% E6 Q8 Z6 {8 a b22 <= med(a12, a22, a32);
9 V. m, G& t, v1 q: V6 D% G b23 <= med(a13, a23, a33);
( ]& L' S/ t) u7 S5 Z1 d b31 <= min(a11, a21, a31); 9 ^/ k6 ]: [1 D
b32 <= min(a12, a22, a32); / `2 ~3 H' L3 r. Q, F) ^6 Q C
b33 <= min(a13, a23, a33);4 d, d- S: o% M! _- c3 Z# p% [, }4 C
end
; h0 J! c7 ]3 r6 Q$ K( t- e; S& `; w0 R
3'd1:* [ Q A! B0 Z$ W
begin; Q3 i% K0 r' N' w& k. t& H
c31 <= max(b31, b32, b33);$ Y# ` ^; [: m$ z
c22 <= med(b21, b22, b23);8 D7 s# D7 _ R5 r r" v1 H$ j" ^( z
c13 <= min(b11, b12, b13); ! C! W3 T; O. I+ `
end$ n# `) }' }9 u: d) a
) n( t: p# J4 g) o5 p
3'd2:- j1 Y$ |( N( y0 w0 m
begin5 ` J4 H4 j. v# N& h' h" U
medfilt_data <= med(c13, c22, c31);3 n: P4 |# Z5 h- o
filt_done<=1'b1;
/ u$ R4 [1 ]! [* U$ J. A end- }: [; p, x J' J* Y
, z) S' ^8 a$ w$ z+ ^4 t( @7 p
3'd3:
, D& b# e$ o; {' y; n+ p filt_done <= 1'b0; : r! C5 D" Q0 I# F( ^# u4 ?
- l8 A2 i. ]# U6 U8 q3 |( ?* P& @ default:;9 ~' ~. g/ j8 \# Y9 t7 V. O
& b2 X( N v+ `. i
endcase
2 v$ C0 Y x6 D1 T
3 I; J4 @* Z u+ c. d/************************************************************************************/ 7 c0 l" P/ F! T+ P& n1 F0 U* e; ^. d# A
6 c# B- t. h% `9 g" @8 V8 Cfunction [7:0] max;//if the data is signed number, please add the char signed behind key function;
5 ?9 k, y# \( B* Y9 v input [7:0] a, b, c;
2 Q' o; x A- r0 u! ?7 Q9 F E begin
' e" D/ ~% s& M2 t2 z max = (((a >= b) ? a : b) >= c ) ? ((a >= b) ? a : b) : c;( A7 I7 L. j9 G+ Q7 G3 R% f
end' g. v0 f4 {& u6 a" Y
endfunction, } u" Y1 K) _7 C. [' c
" @2 o: M l5 Q$ T) _! w1 x
function [7:0] med;
1 ?+ J! l7 y4 D/ F3 @& M2 k input [7:0] a, b, c;) D/ Z- `/ O' f0 D- ]: ?
begin
; K/ i. }$ q a/ `- N3 P0 k med = a < b ? (b < c ? b : a < c ? c : a) : (b > c ? b : a > c ? c : a);
& m( ]# |- [. ~ end4 z% T2 w7 ^ `/ J; f2 x
endfunction8 J( r5 p- F6 J3 d9 ]/ J
1 @; ?% _" g) y/ y c
function [7:0] min;/ c( R& e1 N) h2 _( v. Y# r6 ^
input [7:0] a, b, c;0 E7 Z/ E7 D1 h, U
begin
) g, i' {5 u' v; B) W min= (((a <= b) ? a : b) <= c ) ? ((a <= b) ? a : b) : c;2 v, W: c3 B4 u3 U# u# e& \
end* z1 m8 S) \$ r; Y
endfunction7 h; j7 ~. p- U4 ^- ]& O
1 U7 c( _( `; N" f
/************************************************************************************/ 1 l. G6 A3 o7 s# Y0 O5 @; `
0 b% [" S* j% ^5 u
assign medfilt_data_out = medfilt_data;
4 Y0 V1 ^" p0 }3 ]+ S assign medfilt_done_sig = filt_done;/ b3 q7 q! [& Y+ r5 h( L: M3 L
: c0 b* B" @% o$ @$ ^ ^/ E5 h
/**********************************************************************************/ * Q1 M& `! I4 D, H3 ?5 \5 g
; S8 L, b" H2 Sendmodule
+ f9 ?; ~+ ^# _, u y5 q' {! J( V/ [# R+ k
5)顶层模块,用于将低层的各个功能/控制模块衔接起来,得到结果;
% H @+ k: s5 O0 D# q/ G: V0 r7 e1 b
注意输入输出信号,以及不同模块之间是如何进行连线的。1 u9 ^# K) q5 C+ ~2 H( G& U7 g- ?
. Q' k0 N8 D+ U% f- j信号的名称尽量有其特别的意义,不要重复使用同一个信号名称,容易造成混乱;/ F0 w/ W3 H+ R5 d) e/ C( F' h
/ B) W& U8 ?3 w3 J( e& L
区别wire和reg类型数据的使用情况;$ h; C0 S; z1 e' u) O
( H8 y! ~# @7 Z Y: x& H) `6 }`timescale 1ns / 1ps
, b' }( A: H( i7 P' Z//////////////////////////////////////////////////////////////////////////////////
8 i8 ~9 S7 P! ]// Company:
0 V# Q0 C# X, P! U' a// Engineer: 9 @6 ]$ T8 L; j/ `
// ) C* t9 U8 Q" X7 V$ v6 c9 `
// Create Date: , Y* P# ?. `3 F. G; u4 |2 z5 H
// Design Name: 1 T, u1 [0 R5 l
// Module Name: medfilter2
- D% f" K, e- A' _( V8 B// Project Name: 5 I E5 g( L8 U9 h; A
// Target Devices:
: X" f& d' d7 n. ?# }8 Z// Tool versions:
2 l5 R- Z E) V6 b% r; R9 B// Description:
, e$ z3 J, G. A4 D* b//
8 K- X' Y l7 L! Q" K// Dependencies:
* l2 [. P- B$ \9 M7 g//
3 N- E/ F1 T! t// Revision: $ } H" `& G4 b3 r1 r8 E% i( `: e/ P
// Revision 0.01 - File Created0 I# V1 h" |$ e- l6 r' P. A! _
// Additional Comments: 2 r9 y+ K1 m; Z( I1 }3 S, z
//
4 M e/ E- H% O5 I$ ]& D//////////////////////////////////////////////////////////////////////////////////
* F" n' u; B6 Y* M- e/ a$ F; r- w( i+ g9 {4 p9 o% B! J
module medfilter2 7 x( U. l" a9 p4 @( E2 }
(
8 K U2 F3 y$ e7 q- y CLK, % G5 u& _: ^" s$ e2 b% J- R
RSTn,% g( f: `3 l9 M+ t6 g
Start_sig,' o# @6 j# v4 y9 E# o5 `6 D) A. i
Done_sig,5 A+ d( n3 p2 L2 ^
Data_out
7 N! l& ~& J/ e# Z' _# E: {);
2 ]% T' I( e; N) r9 C7 Z
8 J R* R1 a, `0 ]" l input CLK;
( P, b [+ T# W. Q0 c7 S) E input RSTn;. `. Y) }( d! c9 l% v0 b: b3 i
input Start_sig;/ L9 [) G3 J! r' O; n
output Done_sig;
, s' L% X0 }3 Q! m output [7:0] Data_out;$ i' o0 C) A6 A! D1 Q7 {3 b
# T! m" h7 [* v5 |# x! V. h /********************************************************************/* P( O% }2 u+ F5 Y% M
2 z7 i* W1 C4 p. m' C! d, b
wire [17:0] rom_addr; //1 b2 z1 @) `* ]/ c9 l
wire [7:0] rom_data; // % t& n5 s$ R1 E3 \7 ~4 r
. {3 P0 n/ ^' s& s5 J
rom_512by512 rom_512by512_inst
9 H* A) r9 M: l1 q4 g- o (
, ]! K8 I1 l, j' F! h, j .clka(CLK), //input clka;- U- w& L! t* g4 `" [' f( M
.addra(rom_addr), //input-from;
C* v0 f: L( o% l0 [& }+ w5 I .douta(rom_data) //output-to ; # I) U6 h+ w2 l! H, W& K% N6 e; e
);
$ m+ h) E" t: |4 B' x ?" E% D
# H5 [; q( a' `, T5 j4 t' C /******************************************************************************/2 S( s- {) J2 t2 a( h3 o
) o, P$ c7 @: _2 X! Y
//wire [7:0] win_data[8:0];
/ F( W1 m' i4 k( I/ L wire [7:0] data_out0; //output-to ;, `/ `% b# F, s8 T/ p
wire [7:0] data_out1;8 N) @. S8 @( p7 g" ~( ?
wire [7:0] data_out2;1 N& Z4 b, J% ]% U8 d5 g+ y
wire [7:0] data_out3;, y0 G( ~% o2 u0 e
wire [7:0] data_out4;
5 n! \7 L N6 {7 U# P0 F wire [7:0] data_out5;! N; S3 v& I& y
wire [7:0] data_out6;
3 H M7 u, [0 y4 Q0 E wire [7:0] data_out7;
; x. a6 F* L9 w, ?$ W' q( i3 a wire [7:0] data_out8;* W/ v1 t$ _7 S& r ~& h
wire win_done_sig;1 q0 v! ~7 ^: W, u
) ^8 L: G: G. j/ o1 p
wire [9:0] column_addr_sig;) [% a, @1 f; I! E/ w
wire [9:0] row_addr_sig;
: ~; w6 b; p _/ a: N0 N) g7 `( A% H2 ~/ q
win3by3_gen win3by3_gen_inst (6 F9 M c/ I S
.CLK(CLK),
% G. l* X+ {2 h- _) B9 e% I7 C, E' a+ q .RSTn(RSTn),# F/ d0 g2 o; k Q1 Z' _
.center_pix_sig(win_start_sig), //input-from ; ^2 u- W, B% O9 \$ c+ B
.cols(10'd512), // the column numbers of the input image
( P3 V) n* g7 y .rows(10'd512), // the row numbers of the input image+ x2 {( j5 Q! R3 u$ e7 i e
.rom_data_win(rom_data), //input-from ;
% G0 P9 i! A6 U& ? V7 @ .column_addr_sig(column_addr_sig), //input-from ; //output [9 : 0] addra;
$ P b8 v5 l7 r, f .row_addr_sig(row_addr_sig), //input-from ; //output [9 : 0] addra;
) W2 s! A: L* m! b .rom_addr_sig(rom_addr), //output-to ;
) A3 s9 w: D3 c/ `$ e .data_out0(data_out0), //output-to ;' a! n5 B0 j" m8 R) Y" u
.data_out1(data_out1),
' k6 h7 u" w* q. o$ r; c .data_out2(data_out2),3 p. j$ E3 Y/ ?& v# z+ H( @* C4 z% U5 X
.data_out3(data_out3),
, Y6 h" W$ V8 u1 { .data_out4(data_out4)," x" X* c) O4 m. t8 i( e
.data_out5(data_out5),
2 P- y: l9 e) I0 M* Z .data_out6(data_out6),
& q/ Z$ o* J7 b+ `( V .data_out7(data_out7),
, W4 L6 L) |' g .data_out8(data_out8),7 s# _# E2 @; n( t
.win_data_done_sig(win_done_sig) //output-to U4/U3; ) R) {7 R4 U/ X8 ~( V8 a
);! z$ J& P$ B) ?# K( e/ X, _. V
, U. @, @8 _' Q
/******************************************************************************/ 2 I k8 M$ G- { D6 a8 i
' y" q) e! h& s" L
counter_ctrl counter_ctrl_inst(* M" i, r" M4 h( P5 z
.CLK(CLK),& T: \; k1 p* K: i. g. k* X
.RSTn(RSTn),% B" y! {% l6 i' V2 R: T% x
.start_sig(Start_sig), //input-from top
& _& G: W x1 ~$ z .nxt_pix_sig(win_done_sig), //input-from
3 H2 Y$ Z, j8 V; c/ r- U .cols(10'd512),
& p" c, J) I) \. r .column_addr_sig(column_addr_sig), //output-to
+ i$ X& i0 {2 c, B4 a( i .row_addr_sig(row_addr_sig), //output-to ) j# x: S7 A* G7 y% |7 H$ D( \0 |! H
.pix_done_sig(win_start_sig) //output-to
* E, i& ]+ ]* S2 J );2 [* r* ^- R2 K* @) z
^- B: \! S) X7 W. T/*****************************************************************************/
, p0 w3 e# O7 u" x8 a/ D2 J+ \" M5 X- z
wire medfilt_done_sig;
# h5 r# X- {9 [" j4 i& swire [7:0] medfilt_data_wire;( c2 N; \: y$ ^! D; q! ~# p
* T! t |. P3 P' S/ nmedfilter3by3 medfilter3by3_inst
& b3 U/ X" G9 [' w(
% \) w) U4 l% a+ W' [ .CLK(CLK), r' A& K8 O# x2 j6 |6 L2 ~. \
.RSTn(RSTn),
4 m' I' q% N4 x f .win_data_sig(win_done_sig), //input-from;
$ B( u# V5 w3 ?& T .medfilt_done_sig(medfilt_done_sig), //output-to;
4 r3 W- `( H x. Q: g .data_in0(data_out0), //input-from ;
8 y! \5 f5 n E) [( I' {/ k0 R .data_in1(data_out1),
* b" Q! U- d2 I# L( `$ o) n8 f$ | .data_in2(data_out2),$ W! R; F$ e5 \% o% R
.data_in3(data_out3),
* C- q- V5 U! J7 ~' h5 X .data_in4(data_out4),# ], p; v) ~: `& I+ s# N9 `. X
.data_in5(data_out5),
$ [( Q- d8 N9 x: G1 p .data_in6(data_out6),
: G. y/ ~4 \( l .data_in7(data_out7),
! m* ?) @. \ | .data_in8(data_out8),8 p' p3 \# D6 u
.medfilt_data_out(medfilt_data_wire) //output-to top;
, C+ T! {1 E8 ?9 g);
! K% x5 l7 x; B) P9 b: z" J+ Y. ~- |4 x& R
/*********************************************************************/7 `' m z' P) P! k7 a+ A2 a8 \
wire Done_sig;/ V+ f. e: _( Q% e( a" W# b
wire [7:0] Data_out;
- |; _3 @8 {5 O; sassign Done_sig = medfilt_done_sig;5 `: l# s& `/ Q/ |' I
assign Data_out = medfilt_data_wire;
# W$ o2 e5 P- _$ e; Q" c' k
" ]; r+ |8 w" Z& W/**********************************************************************/$ Z# U' d; J n+ @9 T
endmodule3 ?5 {) N- ]% {
0 C9 C# O0 X4 i: P, x; h2 }
6)测试模块
4 |8 y4 p- L# M" f2 E# n% q8 g6 p9 Y2 l6 t" I* r6 u9 ?( d
如何将数据写入文件,需要定义文件的名称和类型;( N+ m# N& P( s) `# Q2 u
6 X- m" h, v9 G3 o( K7 |* H" [
integer fouti;% T8 B/ k/ N- ?, o, P; V
" Q2 }& T l/ O" S+ }( }需要在初始化部分打开文件:) |& Y- K( D3 [. Q
5 \. m4 L% t0 P8 ufouti = $fopen("medfilter2_re.txt");
& x( q7 s' Q, i4 H) x
9 ^- p u0 @; O' U2 F% F: `代码如下:1 Q/ w. U$ e Y h1 V
, o( O$ C+ l( d$ r5 z`timescale 1ns / 1ps
. v$ w+ k6 m3 L% O- ~9 M6 `# ~4 [9 I; |2 @$ i- U
////////////////////////////////////////////////////////////////////////////////
/ ?6 R2 G% F5 w. ]// Company: 3 R5 R3 n' P. H) F: w
// Engineer:: B; |% _( v0 r" Y8 S% e
//# l) H) f" e/ @
// Create Date:
, n% n7 t5 U2 x. {& V// Design Name: medfilter2+ n& o2 {: J2 i; n0 C+ O# n
// Module Name: E:/stereo_match_pro/stereo_match_FPGA0518/medfilter_tb.v ^, j) J3 b& u5 H1 ]3 o( o) c
// Project Name: stereo_match_FPGA0518
8 A9 }* B. b2 B% I6 w; _1 w/ o// Target Device:
: ^# p+ i( c8 h// Tool versions: 9 t# f) s8 j) L; z) S" ~
// Description: 0 @* J4 `4 |- H. D" t4 D3 e6 _+ {9 h
//
2 a" ~% F0 l; d4 \+ C// Verilog Test Fixture created by ISE for module: medfilter2+ }; t' {9 Z1 j5 n4 h! r/ R
//
* \8 I' f' e& I# w% P7 W7 `: R4 \" z// Dependencies:
: X+ ]" z' C# T6 R$ [9 R' B% R; }8 M//
8 a" V4 Z2 W6 T. o// Revision:
8 `, T8 L% \, w. G0 \9 N( y: \// Revision 0.01 - File Created
1 S2 X% r4 N5 ]// Additional Comments:
9 X5 C8 l0 I) B* L( v//
2 T) \0 J/ @. { v4 j////////////////////////////////////////////////////////////////////////////////
* M! h1 C6 U% _- x$ b
/ x. h3 k+ Q5 B3 pmodule medfilter_tb;+ I8 `- {1 ?, M
. m5 n _( W/ k* A* Y // Inputs; u6 p1 a9 x# q3 ~) D% |( c5 w7 t7 j
reg CLK;
9 S6 q, Y1 B/ ~0 ^& c reg RSTn;
3 z0 D Z4 N9 E* i/ w' s: n reg Start_sig;
9 h$ n2 J4 s- T3 _ reg [18:0] pix_cnt; //512*512=262144=100,0000,0000,0000,00009 g2 x- p7 | g1 B6 Z: B4 h L( [
$ F( h2 [$ ?" W, ~
, b" r$ ?( P7 S0 U // Outputs. h7 e% W' ]' Z* @. E2 q
wire Done_sig;9 \* D; K7 M2 H/ {( x r/ C4 c* _: R
wire [7:0] Data_out;% N" Z( _* ]& V) F- x( A
integer fouti;$ |5 d/ @; A* {: M1 y( V, N
7 T: Y3 Z/ v( {! z: P( \$ S9 a7 a: N; v* p+ Z# j4 F4 V
// Instantiate the Unit Under Test (UUT)
7 v/ X/ g6 e) \" c$ o' `; H2 }+ e7 v* u. q; C medfilter2 uut (" W2 [% ?* C( k9 K9 g) `
.CLK(CLK),
/ f u5 g6 W2 ~ .RSTn(RSTn), 6 P# U- |% p. ^6 [+ ~* P
.Start_sig(Start_sig), 1 H8 a$ Y& ^. y7 G
.Done_sig(Done_sig), % F1 l R( M& E; ?: o
.Data_out(Data_out)5 P, e |, C# |& H2 j' `4 O+ z. ~
);: @# A% e y. w+ S( @
; i* C& X! R. S7 y. m, @) h //assign Data_out = 0;# v* @7 I! ]! k; o. k( v
//assign Done_sig = 0;
0 y' y2 Q2 b' q8 e2 t
, q; J- I: K5 S" b initial begin5 `, `8 u: t" B7 R$ p9 y" n
// Initialize Inputs1 d& f% L. V1 J+ O5 B
CLK = 0;3 k' I' q* p- L2 f6 H$ R3 H4 W$ h
RSTn = 1;
6 d; m1 [0 ^6 I' ~3 E) i Start_sig = 0;& l- o+ u- E! _4 g- a0 y
# }. e4 d1 R. J9 W4 W' C* f! U% C
fouti = $fopen("medfilter2_re.txt");
7 Q. u4 u7 b7 E/ k* Z' H m7 `" g" s/ g9 K# n
// Wait 100 ns for global reset to finish
7 r. F" N' I' r6 G6 V, G #100; // To reset the system
. R; ?4 x$ F. n, h // Add stimulus here
! ]; e0 g4 U& \# U+ y RSTn = 0;
& k: T" e" [2 V5 r4 E" { Start_sig = 1;: f( M5 Y! [; H* n) V
pix_cnt = 0;
2 q$ f0 P1 p9 c8 x) v n5 H- Q* s* x1 Z
#100; // To start the system
5 X2 }+ V- @ T& J // Add stimulus here& Q1 i& W8 j; Q( p5 a G
RSTn = 1;% B1 d5 u+ x; i/ u. w3 b
pix_cnt = 1;6 Q2 u% _: L9 r. N \ H
+ n- [ S" K; l) o0 a& H& w end
0 e% R" \! {# O" E, S, [
5 T- O3 l, r$ E% c always #10 CLK = ~CLK;) Q' x, R* R/ e9 Y4 O+ X
1 ?% G! P& r$ k: h1 T( D3 A
always@(posedge CLK)
/ ^/ p9 b% t2 o2 V4 m- S. w begin
/ S$ R5 H2 K6 o& ?( w0 J if(Done_sig)3 t9 P5 ?8 w( C+ ?
pix_cnt <= pix_cnt + 1;5 P" O/ ?0 ]3 {* I, p) u
end
1 d+ H) b( `/ d/ l! x& `# D+ `* i7 P! `' g
always@(posedge CLK): y3 J, a" Z7 A+ \
begin6 p2 X, ~& B' S6 D4 o
if(pix_cnt == 19'd262145)
0 X: w$ f1 v/ H1 Y4 O7 c. A8 f; N begin
4 p8 {3 U0 s6 t- d: V! E Start_sig <= 0; k! @- I5 o- Q' P! o- ~
$display("Image Medfilter Completed!\n");
' b. T3 O. N. E. U, M0 k $display(</span><span style="color: #800000;">"</span><span style="color: #800000;">The all time is %d \n</span><span style="color: #800000;">"</span>,$time);
\6 r; t; s5 ?4 q+ N $stop;# q! q9 Y4 c: O' O1 m$ a/ `4 {
end
2 X* v) s! e% k5 R# ], v end
7 O) V) N0 V- i1 k+ E8 c* V, F# U
1 a' J4 y) y @4 K# i* S& J
* O3 I7 n. _/ Z3 v& Z$ b1 O k6 h4 L4 V C( @3 X3 V
always@(posedge CLK)" L7 ]) e& _+ d3 ~' n6 {3 e
begin
0 H# p w- Z3 q* c0 i/ r& O if(Done_sig)
) T. `9 G7 U; X/ I1 ] i" M+ `% x begin) K4 m" d! R. D* u0 o
$fwrite(fouti, "%d", Data_out, "\n");8 R$ I, m" P$ A" e D% |5 T2 l/ ]/ K. G
$display("%d",pix_cnt);
) p0 P& i ]. f& b" U. x end
- B- D# h5 _. H7 i' F end4 W7 J" I/ ?9 ^+ h, o/ O, ?
# K% W- q# Y' ], `endmodule
+ d3 Z7 h( \8 ~, P) d9 ~$ E. y* o b: v4 t! ]# P
整体的代码就是这样的。
* t+ X; d( ^( F
- I2 P4 }- l; W" B. ^! f, v3.对各个模块进行语法检查、波形仿真、时序设计、调试验证;: @- S) q" c$ L( W" f, J
7 ^. R8 i2 A4 J8 ?, h$ U) R
本人觉得原理清楚之后按部就班的编写代码还好,只是刚接触波形仿真和调试的时候是真心不顺心,还好有同事帮忙调试;在调试的过程中其实会学习到很多东西,很多经验,以及很简单的但你之前就是不知道的知识,这就是一个实践的过程,有时候你根本不知道错误在哪里,这怎么会是错误的呢,为什么不可以这样写,我觉得这样写才是正确的,这些就是在调试过程中本人的真实心情写照呀。可是,没有那么多为什么,verilog就是这样编程的,只是你不知道而已!这才是最伤人的,因为你不知道!5 z3 X+ @' g) S' g3 [% c
. o9 {) g8 X/ L! D3 p. Y
仿真调试的过程中遇到的问题以及解决方法有空专门写一篇,调试的过程中最好是一个一个模块的测试,特别是关键信号的数值,最好搞懂整体模块和各个模块的时序设计过程,推荐使用TimeDesigner进行波形的设计;另外还需要有关联的两个甚至多个不同模块信号的交叉仿真验证。& L% S* l3 W6 Y' |! q* z
. X+ l+ \. F- m0 I
4.与matlab的中值滤波结果进行比较! p: c0 ?" Q1 R [( z
4 |! z. j* r6 g1 f: a
使用matlab编程基于自带的中值滤波函数得到处理之后的图像与数据,并将verilog得到的滤波数据转换为图像,将二者进行比较。
; B5 Y5 ? |3 y5 n* J% P; }5 R% b; C$ x% k
使用matlab自带的中值滤波函数medfilt2生成原图像的灰度图像的滤波数据;( L" t7 V x, g/ k
; T: ?, R% G3 Q/ A2 L5 }
% mcode to median filter for one jpg image, and create a image data file2 C3 q0 K" `) G& X6 `9 x
src = imread('lena.jpg');5 l" c, S: Y* K9 v
gray = rgb2gray(src);. p4 P6 _# c& r
5 e& b* d: [' }% s3 x: Wmedfilt2im = medfilt2( gray );. G. O/ S. x+ R) x# ]- ]( l
[m, n] = size( medfilt2im ); % m行 n列: f4 H/ z2 P* B# q* I! C% z
H A1 t& P' H3 Z% z/ kN = m*n; %%数据的长度,即存储器深度。
& G: p$ K( Q$ g, [. {( Y8 }word_len = 8; %%每个单元的占据的位数,需自己设定2 n7 C# l' N+ l8 V0 e j3 ]: c; u
lena_gray = reshape(gray', 1, N);% 1行N列6 Z! Y3 { |( G# l9 \7 V( w! J6 P: F
lena_medfilt = reshape(medfilt2im', 1, N);% 1行N列8 N, b( F, H0 B$ w0 J4 B7 }
8 C9 n" R7 q7 W& W1 A' l/ g* x
fid_gray=fopen('lena_gray.txt', 'wt'); %打开文件
% [0 @' b5 X- k0 i" mfid_medfilt=fopen('lena_medfilt.txt', 'wt'); %打开文件" d- i2 q: f6 C6 M$ Z1 ~9 ^; R
% fprintf(fid, 'MEMORY_INITIALIZATION_RADIX=16;\n');
) r0 ]6 i* c: _, ` [7 Y% fprintf(fid, 'MEMORY_INITIALIZATION_VECTOR=\n');1 V7 C5 K9 D: m8 B% H8 k- k5 T! k
+ h$ ?4 ?8 l/ Y5 z. E
) U; b) C& ]% R3 q! o8 a/ t5 |, Yfor i = 1 : N-1
; j, ^5 ]7 ?1 g* l2 t' G) u+ X fprintf(fid_gray, '%d,\n', lena_gray(i));%使用%x表示十六进制数
& Z4 K l6 m( ~, Dend M1 q: K" W+ X+ T, H0 T" ], e
fprintf(fid_gray, '%d;\n', data(N)); %%输出结尾,每个数据后面用逗号或者空格或者换行符隔开,最后一个数据后面加分号
# u; C h% }, Z1 afclose(fid_gray); %%关闭文件
' {% M5 U% k [ ~# v; M ?: P4 b1 Y3 O3 S D
for i = 1 : N-1
# K; q O6 M, F+ B fprintf(fid_medfilt, '%d,\n', lena_medfilt(i));%使用%x表示十六进制数# ~4 \: a5 K, ]& ~
end
. x2 }4 Z' t5 w- E) Q$ V7 M/ tfprintf(fid_medfilt, '%d;\n', lena_medfilt(N)); %%输出结尾,每个数据后面用逗号或者空格或者换行符隔开,最后一个数据后面加分号! E2 X/ W0 Y/ d5 ~# l, o
fclose(fid_medfilt); %%关闭文件4 Z) c3 C' L3 y( a; d* e+ J
3 X5 I' g0 ~) x, S" L! P
将medfilt2函数和verilog产生的滤波数据转换为图像,并与matlab直接产生的滤波图像进行对比,代码如下:! W: k5 }. H2 T: W# X. B0 O( T/ d
3 `4 M$ ^ s# ~: i/ T( p4 h6 U% code to create image data from txt file1 x* }; N) I* x. T
clc;
8 Q. C4 r5 x& \/ [/ _. v, aclear all;
1 U1 X9 i0 J0 \, L" Rclose all;) K5 }; d$ F: j5 i
I_rgb = imread('lena.jpg');
6 V0 t g+ @- V8 J7 F1 @. msubplot(2, 3, 1), imshow(I_rgb), title('lena-rgb')" r, t" G* {7 p& D- I2 H' x
3 B5 r( \: P% l
I_gray = rgb2gray(I_rgb);3 v6 p, }+ z) y$ I
subplot(2, 3, 2), imshow(I_gray), title('lena-gray')/ w# m) X/ P& T3 o
* p4 t! V4 P+ a. H
medfilt_m_load = load('.\lena_medfilt.txt');7 x+ U- k4 c0 ?: q4 l* }
%medfilt_m_load = load('.\lena.coe');
% g* f# m' H4 V/ Y& e6 z4 w- k0 Umedfilt_v_load = load('.\medfilter2_reV1.txt'); % verilog 产生的中值滤波之后数据9 H3 a5 T; T6 T% q8 e
! X' }, m' r- |( M
medfilt2im = medfilt2( I_gray );3 }; h6 O S& s: g% [5 F' `+ A) k
subplot(2, 3, 3), imshow(medfilt2im), title('lena-medfilt2')
# S# A. U5 A& B* ]3 z3 A5 n
+ [& t0 }# y0 }( v9 Lm = 512;7 j% v( \6 i8 u; Q" H
n = 512;& [* C5 `" o7 d8 c: g. V g1 @
medfilt_m = reshape(medfilt_m_load, m, n);
) @% |( q. J( [! Z: }$ F/ m+ {6 r$ zmedfilt_v = reshape(medfilt_v_load, m, n);' W; k `9 P# \9 ?9 q& q
medfilt_m = uint8(medfilt_m');0 K5 D+ i: v( j" ?; Q1 g
medfilt_v = uint8(medfilt_v');) \0 M% L5 ~9 e4 S8 L/ Y, E2 _
; I3 ^: a& ~" P' `, o$ h
aa = medfilt2im - medfilt_m;- h8 Q7 l8 N3 F9 ?; _ ~
bb = medfilt2im - medfilt_v;: e' n, n' l# S1 m4 i9 B
cc = medfilt_m - medfilt_v;% c% }) g) ^6 P
# O; L5 a3 [% A: t4 G' }subplot(2, 3, 5), imshow(medfilt_m), title('medfilt-matlab');
! l$ }) w) Q# Asubplot(2, 3, 6), imshow(medfilt_v), title('medfilt-verilog');; J3 V6 v, ?+ Q9 `. `* ]
/ T- U! g( b, B3 u; {; ^" Y4 d6 e
显示的结果如下图所示:
% _5 {* f9 g! o: Q. s: [
% I1 @. C( k* r
" `" F# p! N0 ] }9 d结果:两种滤波产生的图像数据完全一致,不过感觉函数直接产生的图像颜色更深一些,不知道为什么。5 \( P$ F8 |6 A2 A
0 ^ g5 m- G7 y7 L! h& q, u6 N) Z
这里需要了解一下medfilt2这个函数的原理。结果数据表明,默认情况下该函数对图像边界采用的是补0的方法进行处理的。
$ C0 n& x* C7 J; P
* L3 M! [! k* b1 }* t0 N结论. S3 M+ p6 F% S
4 _8 c" l+ L2 X( m {- p' T
中值滤波终于告一段落了!简单的问题还是需要深入进去研究的,实践的过程中你才会发现自己之前了解的东西是多么的浅薄,对已知的知识掌握的是多么的流于表面!1 N& r: l8 C1 J& Z
5 R: A6 M0 v6 [2 R" c4 `# H最后结果的数据还是很让人开心的!
1 Y$ u- z2 ]/ h: L |
|