d1889fc445f4f2f6444a47171f399348fc481557
[calu.git] / 3b_sim / extensions / cuart.hpp
1 #include "../iext.hpp"
2
3 class Cuart : public Iext {
4         public:
5                 Cuart() : m_writeAddress(0), m_fetchCount(0), m_readCount(0), m_recRdy(0), m_txRdy(0), m_recVal(0), m_txVal(0) {};
6                 void applyTick() {};
7                 void loadData(const int address, CDat value);
8                 CDat readData(const int);
9                 void parseInput(const vector<string>& in);
10         private:
11                 int m_writeAddress, m_fetchCount, m_readCount;
12                 bool m_recRdy, m_txRdy;
13                 CDat m_recVal, m_txVal;
14 };
15
16
17 void Cuart::parseInput(const vector<string>& in)
18 {
19         if(in.size() > 1) {
20                 if((in[1].compare("h") == 0)) {
21                         cout << "UART:" << endl;
22                         cout << "\textension uart r 0xXX \t -- to load the module with a value" << endl;
23                         cout << "\textension uart f \t-- to load a value from the module" << endl;
24                 }
25         }
26         if(in.size() < 2) {
27                 return;
28         }
29         if(in[1].compare("uart") == 0) {
30                 if(in[2].compare("r") == 0) {
31                         if(in.size() < 3) {
32                                 return;
33                         }
34                         if(in[3].substr(0,2) == "0x") {
35                                 m_recVal = lexical_cast<uint32_from_hex>(in[3]);
36                         }
37                         else {
38                                 m_recVal = lexical_cast<unsigned int>(in[3]);
39                         }
40                         cout << "UART: loaded 0x" << std::hex << m_recVal << std::dec << endl;
41                         m_recRdy = 1;
42                         m_fetchCount = 0;
43                         m_readCount = 0;
44                 }
45                 else if(in[2].compare("f") == 0) {
46                         cout << "UART: sended 0x" << std::hex << m_txVal << std::dec << endl;
47                         m_txRdy = 0;
48                         m_fetchCount = 0;
49                         m_readCount = 0;
50                 }
51                 else if(in[2].compare("s") == 0) {
52                         cout << "UART:" << endl;
53                         cout << "\ttx busy: " << m_txRdy << endl;
54                         cout << "\trx_newdata: " << m_recRdy << endl;
55                 }
56         }
57 }
58
59 CDat Cuart::readData(const int address)
60 {
61         if(address == 0x2000) {
62                 //status - r only
63 /*              cout << "rx: " << m_recRdy << endl;
64                 cout << "tx: " << m_txRdy << endl;
65                 CDat helpme = m_recRdy;
66                 helpme <<= 1;
67                 helpme |= m_txRdy;
68                 cout << "rx<<1 | tx: " << helpme << endl;
69 */
70                 if(m_txRdy == 1) {
71                         m_fetchCount++;
72                 }
73                 if(m_recRdy == 0) {
74                         m_readCount++;
75                 }
76
77                 if(m_fetchCount >= 5) {
78                         m_fetchCount = 0;
79                         m_readCount = 0;
80                         m_txRdy = 0;
81                         cout << "UART: force fetched 0x" << std::hex << m_txVal << std::dec << endl;
82                 }
83                 if(m_readCount >= 5) {
84                         m_fetchCount = 0;
85                         m_readCount = 0;
86                         m_recRdy = 1;
87                         cout << "UART: force inserted 0x48 ('H')" << endl;
88                         m_recVal = 'H';
89                 }
90                 return (m_recRdy<<1)|(m_txRdy);
91         }
92         else if(address == 0x2008) {
93                 //trans - w only
94                 //data pointer
95         }
96         else if(address == 0x200c) {
97                 //recv - r only
98                 m_recRdy = 0;
99                 m_fetchCount = 0;
100                 m_readCount = 0;
101                 return m_recVal;
102         }
103         return 0;
104 }
105
106 void Cuart::loadData(const int address, CDat value)
107 {
108
109         if(address == 0x2000) {
110                 //status - r only
111         }
112         else if(address == 0x2008) {
113                 //trans - w only
114                 cout << "UART: byte ready to fetch" << endl;
115                 m_txVal = value;
116                 m_txRdy = 1;
117                 m_fetchCount = 0;
118                 m_readCount = 0;
119         }
120         else if(address == 0x200c) {
121                 //recv - r only
122         }
123 }