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

Subversion Repositories dblclockfft

[/] [dblclockfft/] [trunk/] [bench/] [cpp/] [mpy_tb.cpp] - Blame information for rev 6

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 6 dgisselq
////////////////////////////////////////////////////////////////////////////
2
//
3
// Filename:    mpy_tb.cpp
4
//
5
// Project:     A Doubletime Pipelined FFT
6
//
7
// Purpose:     A test-bench for the shift and add shiftaddmpy.v subfile of
8
//              the double clocked FFT.  This file may be run autonomously. 
9
//              If so, the last line output will either read "SUCCESS" on
10
//              success, or some other failure message otherwise.
11
//
12
//              This file depends upon verilator to both compile, run, and
13
//              therefore test shiftaddmpy.v
14
//
15
// Creator:     Dan Gisselquist, Ph.D.
16
//              Gisselquist Tecnology, LLC
17
//
18
///////////////////////////////////////////////////////////////////////////
19
//
20
// Copyright (C) 2015, Gisselquist Technology, LLC
21
//
22
// This program is free software (firmware): you can redistribute it and/or
23
// modify it under the terms of  the GNU General Public License as published
24
// by the Free Software Foundation, either version 3 of the License, or (at
25
// your option) any later version.
26
//
27
// This program is distributed in the hope that it will be useful, but WITHOUT
28
// ANY WARRANTY; without even the implied warranty of MERCHANTIBILITY or
29
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
30
// for more details.
31
//
32
// You should have received a copy of the GNU General Public License along
33
// with this program.  (It's in the $(ROOT)/doc directory, run make with no
34
// target there if the PDF file isn't present.)  If not, see
35
// <http://www.gnu.org/licenses/> for a copy.
36
//
37
// License:     GPL, v3, as defined and found on www.gnu.org,
38
//              http://www.gnu.org/licenses/gpl.html
39
//
40
//
41
///////////////////////////////////////////////////////////////////////////
42 3 dgisselq
#include "Vshiftaddmpy.h"
43
#include "verilated.h"
44
 
45
class   MPYTB {
46
public:
47
        Vshiftaddmpy    *mpy;
48
        long    vals[32];
49
        int     m_addr;
50
 
51
        MPYTB(void) {
52
                mpy = new Vshiftaddmpy;
53
 
54
                for(int i=0; i<32; i++)
55
                        vals[i] = 0;
56
                m_addr = 0;
57
        }
58
        ~MPYTB(void) {
59
                delete mpy;
60
        }
61
 
62
        void    tick(void) {
63
                mpy->i_clk = 0;
64
                mpy->eval();
65
                mpy->i_clk = 1;
66
                mpy->eval();
67
        }
68
 
69
        void    reset(void) {
70
                mpy->i_clk = 0;
71
                mpy->i_ce = 1;
72
                mpy->i_a = 0;
73
                mpy->i_b = 0;
74
 
75
                for(int k=0; k<20; k++)
76
                        tick();
77
        }
78
 
79
        bool    test(const int ia, const int ib) {
80
                bool    success;
81
                int     a, b;
82
                long    out;
83
 
84
                a = ia & 0x0ffff;
85
                b = ib & 0x0ffff;
86
                mpy->i_ce = 1;
87
                mpy->i_a = a & 0x0ffff;
88
                mpy->i_b = b & 0x0ffff;
89
 
90
                if (a&0x8000) a |= (-1 << 15);
91
                if (b&0x8000) b |= (-1 << 15);
92
 
93
                vals[m_addr&31] = (long)a * (long)b;
94
 
95
                tick();
96
 
97
                printf("k=%3d: A =%06x, B =%06x, ANS =%10lx, S=%3d,%3d,%3d,%3d, O = %8x\n",
98
                        m_addr, a & 0x0ffffff, b & 0x0ffffff,
99
                        vals[m_addr&31] & (~(-1l<<40)),
100
                        mpy->v__DOT__sgn,
101
                        mpy->v__DOT__r_s[0],
102
                        mpy->v__DOT__r_s[1],
103
                        mpy->v__DOT__r_s[2],
104
                        mpy->o_r);
105
 
106
                out = mpy->o_r;
107
                if (out & (1<<31)) out |= (-1 << 31);
108
 
109
                m_addr++;
110
 
111
                success = (m_addr < 20)||(out == vals[(m_addr-18)&31]);
112
                if (!success) {
113
                        fprintf(stderr, "WRONG ANSWER: %8lx != %8lx\n", vals[(m_addr-18)&0x01f], out);
114
                        exit(-1);
115
                }
116
 
117
                return success;
118
        }
119
};
120
 
121
int     main(int argc, char **argv, char **envp) {
122
        Verilated::commandArgs(argc, argv);
123
        MPYTB           *tb = new MPYTB;
124
 
125
        tb->reset();
126
 
127
        for(int k=0; k<15; k++) {
128
                int     a, b;
129
 
130
                a = (1<<k);
131
                b = 1;
132
                tb->test(a, b);
133
        }
134
 
135
        for(int k=0; k<15; k++) {
136
                int     a, b, out;
137
 
138
                a = (1<<15);
139
                b = (1<<k);
140
                tb->test(a, b);
141
        }
142
 
143
        for(int k=0; k<200; k++) {
144
                int     a, b, out;
145
 
146
                tb->test(rand(), rand());
147
        }
148
 
149
        delete  tb;
150
 
151 4 dgisselq
        printf("SUCCESS!\n");
152 3 dgisselq
        exit(0);
153
}

powered by: WebSVN 2.1.0

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