Author Message
billy jones
Guest

 Buffer help please Posted: Wed Apr 21, 2004 3:32 am Hi all. Im new to PICs and C programming and I was wondering if anyone would be kind enough to explain to me how the buffer in the file EX_SISR.C works as Im having trouble understanding. Thanks Billy Ttelmah
Guest

Re: Buffer help please Posted: Wed Apr 21, 2004 4:39 am billy jones wrote: Hi all. Im new to PICs and C programming and I was wondering if anyone would be kind enough to explain to me how the buffer in the file EX_SISR.C works as Im having trouble understanding. Thanks Billy

Ouch!...
Ok. Let's split it up a little. Imagine you have an array of storage locations, callled 'buffer', and these are 'addressable', using a number. So:
buffer refers to the first location,
while
buffer[n] is the n+1'th location (arrays in C are 'zero referenced').

Now you have characters arriving from an external source, that need to be temporarily stored, and retrieved in the same order. So you have a pair of 'indexes' to the array, called 'in', and 'out'.
Now initially, you can just add characters to the array, by using:

buffer[in] = chr; //put 'chr' into the address 'in'
Then incrementing 'in', to point to the next location.

However, since the buffer cannot be of infinite size, you have to also handle the condition that 'in' can get to the end of the buffer. This is done by:

in = (++in % size);

where 'size' is the size of the buffer. The '%' symbol, means to generate the remainder, when the first number is divided by the second. So if the 'size' was 8, and in was 6, then the result would be:

6+1 = 7
7/8, = 0 remainder 7

So the result would be '7'.

However the next time the function is called, the maths goes:

7+1 = 8
8/8 = 1 remainder 0

So the result now is '0'.
Hence using this function makes 'in' (and 'out'), increment through the sequence:
0 1 2 3 4 5 6 7 0 1 2 3 4 ....

So now, the address used to store the character, will 'wrap' back to the start of the storage area, when it reaches the end.

The 'retrieval' operation, uses the 'out' address. When the first character is added, 'in' increments. Now the 'out' value and the 'in' value differ. This is used to detect that there is a character in the buffer. Hence you can test at any time for the buffer containing data, by coding:
if (in != out) - here the buffer has got data.
Alternatively if you want to wait till data arrives (as is done in the 'getc' function), if you code as:
while (in==out) - the code will wait here till a character arrives.

The two addresses 'chase' each other round the addresses allowed (hence such buffers are often called 'ring' buffers).

When you increment the 'in' value, if it 'catches up' with the output value, then the buffer is full. The CCS code handles this, by setting 'in' back to the last value if this happens, throwing away the newest character. I often handle this the opposite way, throwing away the 'oldest' character instead.
The operation to do this, is:
buff[in] = chr;
in = ++in % size;
if (in==out) out = ++out % size;

Now the use of the '%' operation, allows the buffer to be any size (5, 10, 20 characters etc.), but has the 'downside', that this involves more arithmetic than some alternatives.
The obvious alternative, is the binary '&' operation. If the buffer 'size' is only allowed to be a direct 'binary' power (so 2, 4, 8, 16, 32 bytes), then you can instead use:

in = ++in & (size-1);

This codes as just a couple of instructions, making for faster buffer handling. The '&' operator, only returns bits in the output, where bits are present in both input values. So, with 'size' = 8:
size-1 = 7 = 00000111
6 = 00000110 & 00000111 = 00000110 = 6
7 = 00000111 & 00000111 = 00000111 = 7
8 = 00001000 & 00000111 = 00000000 = 0

Giving the same 'wrap' effect.

If you do a search on 'ring buffers', you should find a lot more about this.

Best Wishes billy jones
Guest Posted: Wed Apr 21, 2004 10:02 am excellent stuff. thank you Display posts from previous: All Posts1 Day7 Days2 Weeks1 Month3 Months6 Months1 Year Oldest FirstNewest First
 All times are GMT - 6 Hours Page 1 of 1

 Jump to: Select a forum Software----------------General CCS C DiscussionCode LibraryEZ App Lynx Hardware----------------CCS ICD / Mach X / Load-n-Go
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum

Powered by phpBB © 2001, 2005 phpBB Group