dol: initial dol commit
[jump.git] / dol / src / dol / visitor / hdsd / scd / scd_rem_fifo_out.cpp
diff --git a/dol/src/dol/visitor/hdsd/scd/scd_rem_fifo_out.cpp b/dol/src/dol/visitor/hdsd/scd/scd_rem_fifo_out.cpp
new file mode 100644 (file)
index 0000000..e6cb762
--- /dev/null
@@ -0,0 +1,69 @@
+#include "scd_rem_fifo_out.h"
+
+#include <cassert>
+
+#include "scd_logging.h"
+
+
+scd_rem_fifo_out::scd_rem_fifo_out(sc_module_name name, int size):
+    sc_prim_channel(name), _num_elements(0), _first(0), _size(size)
+{
+    assert(size > 0);
+    _data = new char[size];
+}
+
+
+scd_rem_fifo_out::~scd_rem_fifo_out()
+{
+    delete _data;
+}
+
+
+void scd_rem_fifo_out::write(char c)
+{
+    while (_num_elements == _size)
+        wait(_read_event);
+
+    _data[ (_first + _num_elements) % _size ] = c;
+    _num_elements++;
+}
+
+
+int scd_rem_fifo_out::wtest(int size)
+{
+    return (size <= _size - _num_elements) ? 1 : 0;
+}
+
+
+void scd_rem_fifo_out::reset() { _num_elements = _first = 0; }
+
+
+size_t scd_rem_fifo_out::available() const
+{
+    size_t avail;
+
+    if (_num_elements <= _size - _first)
+        avail = _num_elements;
+    else
+        avail = _size - _first;
+
+    return avail;
+}
+
+
+const void* scd_rem_fifo_out::send() const { return _data + _first; }
+
+
+void scd_rem_fifo_out::remove(size_t len)
+{
+    if (len == 0)
+        return;
+
+    assert(_num_elements >= len);
+
+    _first = (_first + len) % _size;
+
+    _num_elements -= len;
+
+    _read_event.notify();
+}