xref: /minix3/common/dist/zlib/contrib/dotzlib/DotZLib/CircularBuffer.cs (revision 44bedb31d842b4b0444105519bcf929a69fe2dc1)
1*44bedb31SLionel Sambuc //
2*44bedb31SLionel Sambuc // � Copyright Henrik Ravn 2004
3*44bedb31SLionel Sambuc //
4*44bedb31SLionel Sambuc // Use, modification and distribution are subject to the Boost Software License, Version 1.0.
5*44bedb31SLionel Sambuc // (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6*44bedb31SLionel Sambuc //
7*44bedb31SLionel Sambuc 
8*44bedb31SLionel Sambuc using System;
9*44bedb31SLionel Sambuc using System.Diagnostics;
10*44bedb31SLionel Sambuc 
11*44bedb31SLionel Sambuc namespace DotZLib
12*44bedb31SLionel Sambuc {
13*44bedb31SLionel Sambuc 
14*44bedb31SLionel Sambuc 	/// <summary>
15*44bedb31SLionel Sambuc 	/// This class implements a circular buffer
16*44bedb31SLionel Sambuc 	/// </summary>
17*44bedb31SLionel Sambuc 	internal class CircularBuffer
18*44bedb31SLionel Sambuc 	{
19*44bedb31SLionel Sambuc         #region Private data
20*44bedb31SLionel Sambuc         private int _capacity;
21*44bedb31SLionel Sambuc         private int _head;
22*44bedb31SLionel Sambuc         private int _tail;
23*44bedb31SLionel Sambuc         private int _size;
24*44bedb31SLionel Sambuc         private byte[] _buffer;
25*44bedb31SLionel Sambuc         #endregion
26*44bedb31SLionel Sambuc 
CircularBuffer(int capacity)27*44bedb31SLionel Sambuc         public CircularBuffer(int capacity)
28*44bedb31SLionel Sambuc         {
29*44bedb31SLionel Sambuc             Debug.Assert( capacity > 0 );
30*44bedb31SLionel Sambuc             _buffer = new byte[capacity];
31*44bedb31SLionel Sambuc             _capacity = capacity;
32*44bedb31SLionel Sambuc             _head = 0;
33*44bedb31SLionel Sambuc             _tail = 0;
34*44bedb31SLionel Sambuc             _size = 0;
35*44bedb31SLionel Sambuc         }
36*44bedb31SLionel Sambuc 
37*44bedb31SLionel Sambuc         public int Size { get { return _size; } }
38*44bedb31SLionel Sambuc 
Put(byte[] source, int offset, int count)39*44bedb31SLionel Sambuc         public int Put(byte[] source, int offset, int count)
40*44bedb31SLionel Sambuc         {
41*44bedb31SLionel Sambuc             Debug.Assert( count > 0 );
42*44bedb31SLionel Sambuc             int trueCount = Math.Min(count, _capacity - Size);
43*44bedb31SLionel Sambuc             for (int i = 0; i < trueCount; ++i)
44*44bedb31SLionel Sambuc                 _buffer[(_tail+i) % _capacity] = source[offset+i];
45*44bedb31SLionel Sambuc             _tail += trueCount;
46*44bedb31SLionel Sambuc             _tail %= _capacity;
47*44bedb31SLionel Sambuc             _size += trueCount;
48*44bedb31SLionel Sambuc             return trueCount;
49*44bedb31SLionel Sambuc         }
50*44bedb31SLionel Sambuc 
Put(byte b)51*44bedb31SLionel Sambuc         public bool Put(byte b)
52*44bedb31SLionel Sambuc         {
53*44bedb31SLionel Sambuc             if (Size == _capacity) // no room
54*44bedb31SLionel Sambuc                 return false;
55*44bedb31SLionel Sambuc             _buffer[_tail++] = b;
56*44bedb31SLionel Sambuc             _tail %= _capacity;
57*44bedb31SLionel Sambuc             ++_size;
58*44bedb31SLionel Sambuc             return true;
59*44bedb31SLionel Sambuc         }
60*44bedb31SLionel Sambuc 
Get(byte[] destination, int offset, int count)61*44bedb31SLionel Sambuc         public int Get(byte[] destination, int offset, int count)
62*44bedb31SLionel Sambuc         {
63*44bedb31SLionel Sambuc             int trueCount = Math.Min(count,Size);
64*44bedb31SLionel Sambuc             for (int i = 0; i < trueCount; ++i)
65*44bedb31SLionel Sambuc                 destination[offset + i] = _buffer[(_head+i) % _capacity];
66*44bedb31SLionel Sambuc             _head += trueCount;
67*44bedb31SLionel Sambuc             _head %= _capacity;
68*44bedb31SLionel Sambuc             _size -= trueCount;
69*44bedb31SLionel Sambuc             return trueCount;
70*44bedb31SLionel Sambuc         }
71*44bedb31SLionel Sambuc 
Get()72*44bedb31SLionel Sambuc         public int Get()
73*44bedb31SLionel Sambuc         {
74*44bedb31SLionel Sambuc             if (Size == 0)
75*44bedb31SLionel Sambuc                 return -1;
76*44bedb31SLionel Sambuc 
77*44bedb31SLionel Sambuc             int result = (int)_buffer[_head++ % _capacity];
78*44bedb31SLionel Sambuc             --_size;
79*44bedb31SLionel Sambuc             return result;
80*44bedb31SLionel Sambuc         }
81*44bedb31SLionel Sambuc 
82*44bedb31SLionel Sambuc     }
83*44bedb31SLionel Sambuc }
84