gem5  v22.1.0.0
scfx_mant.hh
Go to the documentation of this file.
1 /*****************************************************************************
2 
3  Licensed to Accellera Systems Initiative Inc. (Accellera) under one or
4  more contributor license agreements. See the NOTICE file distributed
5  with this work for additional information regarding copyright ownership.
6  Accellera licenses this file to you under the Apache License, Version 2.0
7  (the "License"); you may not use this file except in compliance with the
8  License. You may obtain a copy of the License at
9 
10  http://www.apache.org/licenses/LICENSE-2.0
11 
12  Unless required by applicable law or agreed to in writing, software
13  distributed under the License is distributed on an "AS IS" BASIS,
14  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
15  implied. See the License for the specific language governing
16  permissions and limitations under the License.
17 
18  *****************************************************************************/
19 
20 /*****************************************************************************
21 
22  scfx_mant.h -
23 
24  Original Author: Robert Graulich, Synopsys, Inc.
25  Martin Janssen, Synopsys, Inc.
26 
27  *****************************************************************************/
28 
29 /*****************************************************************************
30 
31  MODIFICATION LOG - modifiers, enter your name, affiliation, date and
32  changes you are making here.
33 
34  Name, Affiliation, Date:
35  Description of Modification:
36 
37  *****************************************************************************/
38 
39 // $Log: scfx_mant.h,v $
40 // Revision 1.2 2011/08/24 22:05:43 acg
41 // Torsten Maehne: initialization changes to remove warnings.
42 //
43 // Revision 1.1.1.1 2006/12/15 20:20:04 acg
44 // SystemC 2.3
45 //
46 // Revision 1.3 2006/01/13 18:53:58 acg
47 // Andy Goodrich: added $Log command so that CVS comments are reproduced in
48 // the source.
49 //
50 
51 #ifndef __SYSTEMC_EXT_DT_FX_SCFX_MANT_HH__
52 #define __SYSTEMC_EXT_DT_FX_SCFX_MANT_HH__
53 
54 #include "../../utils/endian.hh"
55 #include "../../utils/functions.hh"
56 #include "scfx_ieee.hh"
57 #include "scfx_utils.hh"
58 
59 namespace sc_dt
60 {
61 
62 // classes defined in this module
63 class scfx_mant;
64 class scfx_mant_ref;
65 
66 typedef unsigned int word; // Using int because of 64-bit machines.
67 typedef unsigned short half_word;
68 
69 // ----------------------------------------------------------------------------
70 // CLASS : scfx_mant
71 //
72 // Mantissa class.
73 // ----------------------------------------------------------------------------
74 
75 class scfx_mant
76 {
78  int m_size;
79 
80  public:
81  explicit scfx_mant(std::size_t);
82  scfx_mant(const scfx_mant &);
83 
85 
86  ~scfx_mant();
87 
88  void clear();
89 
90  void resize_to(int, int=0);
91 
92  int size() const;
93 
94  word operator [] (int) const;
95  word &operator [] (int);
96 
97  half_word half_at(int) const;
98  half_word &half_at(int);
99 
100  half_word *half_addr(int=0) const;
101 
102  private:
103  static word *alloc(std::size_t);
104  static void free(word *, std::size_t);
105 
106  static word *alloc_word(std::size_t size);
107  static void free_word(word *array, std::size_t size);
108 };
109 
110 
111 // IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII
112 
113 inline int scfx_mant::size() const { return m_size; }
114 
115 inline word *
116 scfx_mant::alloc(std::size_t size)
117 {
118 #if defined(SC_BOOST_BIG_ENDIAN )
119  return alloc_word(size) + (size - 1);
120 #elif defined(SC_BOOST_LITTLE_ENDIAN)
121  return alloc_word(size);
122 #endif
123 }
124 
125 inline void
126 scfx_mant::free(word *mant, std::size_t size)
127 {
128 #if defined(SC_BOOST_BIG_ENDIAN)
129  free_word(mant - (size - 1), size);
130 #elif defined(SC_BOOST_LITTLE_ENDIAN)
131  free_word(mant, size);
132 #endif
133 }
134 
135 inline word
137 {
138  SC_ASSERT_(i >= 0 && i < m_size, "mantissa index out of range");
139 #if defined(SC_BOOST_BIG_ENDIAN)
140  return m_array[-i];
141 #elif defined(SC_BOOST_LITTLE_ENDIAN)
142  return m_array[i];
143 #endif
144 }
145 
146 inline word &
148 {
149  SC_ASSERT_(i >= 0 && i < m_size, "mantissa index out of range");
150 #if defined(SC_BOOST_BIG_ENDIAN)
151  return m_array[-i];
152 #elif defined(SC_BOOST_LITTLE_ENDIAN)
153  return m_array[i];
154 #endif
155 }
156 
157 inline scfx_mant::scfx_mant(std::size_t size_) : m_array(0), m_size(size_)
158 {
159  m_array = alloc(size_);
160 }
161 
162 inline scfx_mant::scfx_mant(const scfx_mant &rhs) :
163  m_array(0), m_size(rhs.m_size)
164 {
165  m_array = alloc(m_size);
166  for (int i = 0; i < m_size; i++) {
167  (*this)[i] = rhs[i];
168  }
169 }
170 
171 inline scfx_mant &
173 {
174  if (&rhs != this) {
175  if (m_size != rhs.m_size) {
176  free(m_array, m_size);
177  m_array = alloc(m_size = rhs.m_size);
178  }
179 
180  for (int i = 0; i < m_size; i++) {
181  (*this)[i] = rhs[i];
182  }
183  }
184  return *this;
185 }
186 
188 {
189  if (m_array != 0) {
190  free(m_array, m_size);
191  }
192 }
193 
194 inline void
196 {
197  for (int i = 0; i < m_size; i++) {
198  (*this)[i] = 0;
199  }
200 }
201 
202 inline void
203 scfx_mant::resize_to(int size, int restore)
204 {
205  if (size == m_size) {
206  return;
207  }
208 
209  if (!m_array) {
210  m_array = alloc(m_size = size);
211  } else {
212  word* p = alloc(size);
213 
214  if (restore) {
215  int end = sc_min(size, m_size);
216  if (restore == 1) { // msb resized -> align at 0
217  for (int i = 0; i < size; i++) {
218  if (i < end) {
219 #if defined(SC_BOOST_BIG_ENDIAN)
220  p[-i] = m_array[-i];
221 #elif defined(SC_BOOST_LITTLE_ENDIAN)
222  p[i] = m_array[i];
223 #endif
224  } else {
225 #if defined(SC_BOOST_BIG_ENDIAN)
226  p[-i] = 0;
227 #elif defined(SC_BOOST_LITTLE_ENDIAN)
228  p[i] = 0;
229 #endif
230  }
231  }
232  } else { // lsb resized -> align at size - 1
233  for (int i = 0; i < size; i++) {
234  if (i < end) {
235 #if defined(SC_BOOST_BIG_ENDIAN)
236  p[-size + 1 + i] = m_array[-m_size + 1 + i];
237 #elif defined(SC_BOOST_LITTLE_ENDIAN)
238  p[size - 1 - i] = m_array[m_size - 1 - i];
239 #endif
240  } else {
241 #if defined(SC_BOOST_BIG_ENDIAN)
242  p[-size + 1 + i] = 0;
243 #elif defined(SC_BOOST_LITTLE_ENDIAN)
244  p[size - 1 - i] = 0;
245 #endif
246  }
247  }
248  }
249  }
250 
251  free(m_array, m_size);
252  m_array = p;
253  m_size = size;
254  }
255 }
256 
257 inline half_word
259 {
260  SC_ASSERT_((i >> 1) >= 0 && (i >> 1) < m_size,
261  "mantissa index out of range");
262 #if defined(SC_BOOST_BIG_ENDIAN)
263  return reinterpret_cast<half_word *>(m_array)[-i];
264 #elif defined(SC_BOOST_LITTLE_ENDIAN )
265  return reinterpret_cast<half_word *>(m_array)[i];
266 #endif
267 }
268 
269 inline half_word &
271 {
272  SC_ASSERT_((i >> 1) >= 0 && (i >> 1) < m_size,
273  "mantissa index out of range" );
274 #if defined(SC_BOOST_BIG_ENDIAN)
275  return reinterpret_cast<half_word *>(m_array)[-i];
276 #elif defined(SC_BOOST_LITTLE_ENDIAN)
277  return reinterpret_cast<half_word *>(m_array)[i];
278 #endif
279 }
280 
281 inline half_word *
283 {
284  SC_ASSERT_(i >= 0 && i < m_size, "mantissa index out of range");
285 #if defined(SC_BOOST_BIG_ENDIAN)
286  return reinterpret_cast<half_word *>(m_array - i) + 1;
287 #elif defined(SC_BOOST_LITTLE_ENDIAN)
288  return reinterpret_cast<half_word *>(m_array + i);
289 #endif
290 }
291 
292 // ----------------------------------------------------------------------------
293 // one's complement of a mantissa
294 // ----------------------------------------------------------------------------
295 
296 inline void
297 complement(scfx_mant &target, const scfx_mant &source, int size)
298 {
299  for (int i = 0; i < size; i++) {
300  target[i] = ~source[i];
301  }
302 }
303 
304 // ----------------------------------------------------------------------------
305 // increment mantissa
306 // ----------------------------------------------------------------------------
307 
308 inline void
310 {
311  for (int i = 0; i < mant.size(); i++) {
312  if (++mant[i]) {
313  break;
314  }
315  }
316 }
317 
318 // ----------------------------------------------------------------------------
319 // CLASS : scfx_mant_ref
320 //
321 // Mantissa reference class.
322 // ----------------------------------------------------------------------------
323 
325 {
328 
329  public:
330  scfx_mant_ref();
331  scfx_mant_ref(const scfx_mant &);
333 
336 
337  ~scfx_mant_ref();
338 
339  operator scfx_mant & ();
340 
341  word operator [] (int);
342 
343  private:
344  void remove_it();
345 
348 
349  void *operator new(std::size_t sz) { return ::operator new (sz); }
350 
351 };
352 
353 // IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII
354 
355 inline void
357 {
358  if (m_not_const) {
359  delete m_mant;
360  }
361 }
362 
363 inline scfx_mant_ref::scfx_mant_ref() : m_mant(0), m_not_const(false) {}
364 
366  m_mant(const_cast<scfx_mant *>(& mant)), m_not_const(false)
367 {}
368 
370  m_mant(mant), m_not_const(true)
371 {}
372 
373 inline scfx_mant_ref &
375 {
376  remove_it();
377 
378  m_mant = const_cast<scfx_mant *>(&mant);
379  m_not_const = false;
380 
381  return *this;
382 }
383 
384 inline scfx_mant_ref &
386 {
387  remove_it();
388 
389  m_mant = mant;
390  m_not_const = true;
391 
392  return *this;
393 }
394 
396 {
397  remove_it();
398 }
399 
400 inline scfx_mant_ref::operator scfx_mant & ()
401 {
402  // SC_ASSERT_(m_not_const, "not allowed to modify mant");
403  return *m_mant;
404 }
405 
406 inline word
408 {
409  return (*m_mant)[i];
410 }
411 
412 } // namespace sc_dt
413 
414 
415 #endif // __SYSTEMC_EXT_DT_FX_SCFX_MANT_HH__
word operator[](int)
Definition: scfx_mant.hh:407
scfx_mant_ref & operator=(const scfx_mant &)
Definition: scfx_mant.hh:374
scfx_mant * m_mant
Definition: scfx_mant.hh:326
scfx_mant_ref(const scfx_mant_ref &)
scfx_mant & operator=(const scfx_mant &)
Definition: scfx_mant.hh:172
word operator[](int) const
Definition: scfx_mant.hh:136
static word * alloc_word(std::size_t size)
Definition: scfx_mant.cc:82
half_word half_at(int) const
Definition: scfx_mant.hh:258
half_word * half_addr(int=0) const
Definition: scfx_mant.hh:282
static word * alloc(std::size_t)
Definition: scfx_mant.hh:116
int size() const
Definition: scfx_mant.hh:113
static void free(word *, std::size_t)
Definition: scfx_mant.hh:126
static void free_word(word *array, std::size_t size)
Definition: scfx_mant.cc:106
void resize_to(int, int=0)
Definition: scfx_mant.hh:203
scfx_mant(std::size_t)
Definition: scfx_mant.hh:157
Bitfield< 7 > i
Definition: misc_types.hh:67
Bitfield< 54 > p
Definition: pagetable.hh:70
Definition: sc_bit.cc:68
void complement(scfx_mant &target, const scfx_mant &source, int size)
Definition: scfx_mant.hh:297
unsigned short half_word
Definition: scfx_mant.hh:67
const T sc_min(const T &a, const T &b)
Definition: functions.hh:59
void inc(scfx_mant &mant)
Definition: scfx_mant.hh:309
unsigned int word
Definition: scfx_mant.hh:64
#define SC_ASSERT_(cnd, msg)
Definition: sc_fxdefs.hh:248

Generated on Wed Dec 21 2022 10:22:41 for gem5 by doxygen 1.9.1